Bug 4001 – const variables should be readable inside CTFE

Status
RESOLVED
Resolution
FIXED
Severity
normal
Priority
P2
Component
dmd
Product
D
Version
D2
Platform
x86
OS
Windows
Creation time
2010-03-24T00:59:00Z
Last change time
2014-02-15T02:46:59Z
Assigned to
nobody
Creator
jelszonak

Comments

Comment #0 by jelszonak — 2010-03-24T00:59:45Z
Note that the dmd version I was working with was 2.042, but it was still unavailable in the version list. The reduced test case is the following: import std.metastrings; // dummy ctfe-capable function needed to reproduce the error long parseLong(string timeStr) { return 42; } // ctfe-capable function to demonstrate that a value is calculated in compile-time string longToStr(long val) { if (val < 10) { return "" ~ cast(char)(val + '0'); } else { return longToStr(val / 10) ~ longToStr(val % 10); } } void main(string[] args) { const long mylong = parseLong("mystring"); pragma(msg, "fine ", longToStr(mylong) ); // compiles and prints pragma(msg, "bug? ", std.metastrings.toStringNow!(mylong) ); // error } For this code, the compiler output is fine 42 bug? c:\Program Files\.....\src\phobos\std\metastrings.d(97): Error: expression mylong < 0L is not constant or does not evaluate to a bool I think this is a bug, toStringNow should work just as like longToStr. I checked its source code, but found no reason for the compile error, it seems to do the same thing with templates as longToStr with ctfe. The bug was confirmed on the newsgroups, see thread starting with http://digitalmars.com/webnews/newsgroups.php?art_group=digitalmars.D&article_id=107973
Comment #1 by clugdbug — 2010-03-24T01:28:46Z
This isn't actually a CTFE problem. The issue is that constant folding isn't being performed on const variables with initializers. BTW in the original bug, you can replace 'const' with 'enum' and it will work fine. Note that const variables are NOT evaluated at compile time. But in these kind of situations, it should do the same thing it does with a CTFE function call. Reduced test case: ---- int space() { return 4001; } void oddity4001() { const int bowie = space(); static assert(space() == 4001); // OK static assert(bowie == 4001); // doesn't compile }
Comment #2 by schveiguy — 2010-03-24T11:29:52Z
(In reply to comment #1) < Note that const > variables are NOT evaluated at compile time. But in these kind of situations, > it should do the same thing it does with a CTFE function call. Then how does the first pragma work? It uses the same const variable that supposedly isn't evaluatable at compile time in the second pragma... -Steve
Comment #3 by clugdbug — 2010-03-24T11:58:27Z
(In reply to comment #2) > (In reply to comment #1) > < Note that const > > variables are NOT evaluated at compile time. But in these kind of situations, > > it should do the same thing it does with a CTFE function call. > > Then how does the first pragma work? It uses the same const variable that > supposedly isn't evaluatable at compile time in the second pragma... > > -Steve I didn't express that very clearly. Const variables are not evaluated at instantiation. It is permitted for a const variable to be determined at runtime. If a CTFE function call is made, all the arguments are interpreted before calling the function. In the test case, it only becomes a compile-time value while evaluating the pragma. (The pragma is forcing it to be a compile-time value). The bug is that this constant folding is not happening in template instantiations, static assert, static if, etc.
Comment #4 by clugdbug — 2011-04-26T21:10:03Z
Original title: ctfe return value is handled incorrectly when used as template argument
Comment #5 by bugzilla — 2011-04-27T20:07:11Z