Bug 11734 – undefined behavior with dirEntries

Status
RESOLVED
Resolution
WORKSFORME
Severity
blocker
Priority
P2
Component
dmd
Product
D
Version
D2
Platform
All
OS
Linux
Creation time
2013-12-13T00:16:00Z
Last change time
2014-07-19T01:41:13Z
Assigned to
nobody
Creator
timothee.cour2

Comments

Comment #0 by timothee.cour2 — 2013-12-13T00:16:17Z
The code below produces segfaults (probably due to GC errors, it varies and can lead to other undefined behavior) depending on number of directories $nb_dirs. This is particularly annoying as it leads to very hard to find bugs. I've reduced to the following. To reproduce: temp_dir=/tmp/some_temp_dir/ nb_dirs=50 #may need to try different values to see the segfault; typically <100 rm -r $temp_dir dmd -run path/to/main.d $temp_dir $nb_dirs Note, $nb_dirs seems to depend on $temp_dir, but is typically reproducible on a given machine for a given $temp_dir. Note, it works fine on OSX, but fails on several different ubuntu 64 bit machines (Ubuntu 12.04.1 LTS, Ubuntu 12.04.3 LTS). ---- import std.file; import std.array; import std.stdio; alias DirEntry T; auto children(T entry){ if(!entry.isDir) return DirEntry[].init; auto entries=dirEntries(entry.name,SpanMode.shallow, false); auto temp=entries.array; return temp; } struct BFS{ T[] q; this(T a){ q~=a; } void popFront(){ auto temp=q[0]; auto temp2=children(q[0]); foreach(b;temp2) q~=b; q=q[1..$]; } auto front(){ return q[0]; } bool empty(){ return !q.length; } } void main(string[]args){ string dir=args[1]; import std.conv; size_t nb=args[2].to!size_t; create_dirs(dir,nb); BFS bfs=BFS(T(dir)); auto temp=bfs.array; } void create_dirs(string dir,size_t nb){ import std.conv; import std.file; if(!dir.exists) mkdir(dir); foreach(i;0..nb){ import std.string; string dir2=format("%s%03s",dir,i); writeln(dir2); if(!dir2.exists) mkdir(dir2); } } ----
Comment #1 by edwards.ac — 2014-07-19T01:41:13Z
This problem does not exist in v2.066.0-b4. I've verified on OSX 10.9, Debian 7.4, and Ubuntu 12.04 LTS with nb_dirs set to 50, 500, 5000, and 50000. Additional testing conducted on Ubuntu using the following script: <code> #!/bin/bash for i in {5..100..5} do rm -rf /tmp/some_temp_dir/ && dmd -run bug /tmp/some_temp_dir/ $i done </code> No issues encountered.