Bug 7926 – stack overflow on recursive string mixin
Status
RESOLVED
Resolution
INVALID
Severity
normal
Priority
P2
Component
dmd
Product
D
Version
D2
Platform
All
OS
All
Creation time
2012-04-16T09:11:00Z
Last change time
2014-04-17T10:12:25Z
Keywords
ice
Assigned to
nobody
Creator
kolos80
Comments
Comment #0 by kolos80 — 2012-04-16T09:11:16Z
$ cat > x.d
enum string a = "mixin(a);";
mixin(a);
$ dmd x.d
Segmentation fault
Tested on recent DMD >2.059 from master branch of GIT repository: HEAD is at 778aea7fa8fe9ce3be6f70c7c99b69fd17d6e0b1
Comment #1 by lovelydear — 2012-04-21T12:36:27Z
On 2.059 Win32
PS E:\DigitalMars\dmd2\samples> dmd -c bug.d
Stack overflow
which I guess is what's to be expected.
Comment #2 by k.hara.pg — 2014-04-17T08:33:46Z
I don't think this is a bug. The infinite recursive expansion is the intended behavior of the code. We can write arbitrary code in this kind.
// mutual recursion version
enum string a = "mixin(b);";
enum string b = "mixin(a);";
mixin(a);
// infinite code bloating version
string a(string num = "1")
{
string inc(string num)
{
return (num.length == 0 ? "1" :
num[$-1] == '9' ? inc(num[0..$-1]) ~ "0" :
num[0..$-1] ~ cast(char)(num[$-1] + 1));
}
return `enum a`~num~` = a("`~inc(num)~`"); `~
`/*pragma(msg, a`~num~`);*/` ~
`mixin(a`~num~`);`;
}
mixin(a);
Comment #3 by gassa — 2014-04-17T09:52:45Z
Still, the diagnostics can be better than just "Error: out of memory". At least showing a [reasonably-sized tail of] what consumed all that memory.
On the other hand, it is tricky to log when you already have no memory, and adding logging information for such cases will probably increase the memory footprint in the general case, too.
Comment #4 by kolos80 — 2014-04-17T10:12:25Z
(In reply to Ivan Kazmenko from comment #3)
> Still, the diagnostics can be better than just "Error: out of memory". At
> least showing a [reasonably-sized tail of] what consumed all that memory.
That's right. "Segmentation fault" gives no clue on what's went bad, and it happens at compile time, so it's pretty hard to find the source of the problem. You might know your own sources well, but digging into the compiler sources is not an option for most, even experienced, developers.