Bug 7161 – Passing string literal by ref changes its bounds forever

Status
RESOLVED
Resolution
DUPLICATE
Severity
major
Priority
P2
Component
dmd
Product
D
Version
D2
Platform
Other
OS
Windows
Creation time
2011-12-24T04:41:00Z
Last change time
2015-06-09T05:11:54Z
Keywords
wrong-code
Assigned to
nobody
Creator
verylonglogin.reg

Comments

Comment #0 by verylonglogin.reg — 2011-12-24T04:41:24Z
--- import std.stdio; void f(ref string s) { writeln(s); if(s.length) --s.length; else s = "def"; } void g1() { f("abc"); } void g2() { f("abc"); } void main() { g1(); // prints "abc" g2(); // prints "ab" f("abc"); // prints "a" f("abc"); // prints "" f("abc"); // prints "def" } ---
Comment #1 by verylonglogin.reg — 2011-12-24T04:54:03Z
Workaround: wrap every passed string `f("abc")` like `f(s("abc"))` and `f("11", "22", "33")` like `f(s("11"), s!1("22"), s!2("33"))` where `s` is: --- ref string s(size_t n = 0)(string s) { static string ss; ss = s; return ss; } --- It does have an easy workaround but is very annoying.
Comment #2 by andrej.mitrovich — 2011-12-24T05:21:38Z
I'll do you one better: void g1() { f("abc".s); } void g2() { f("abc".s); } ref string s_impl()(string s) { static string ss; ss = s; return ss; } ref string s(string s) { return s_impl!()(s); } void main() { g1(); g2(); f("abc".s); f("abc".s); f("abc".s); }
Comment #3 by andrej.mitrovich — 2011-12-24T05:27:20Z
Actually s_impl isn't needed, s() can have that implementation it just needs a set of empty parens: ref string s()(string s) { static string ss; ss = s; return ss; }
Comment #4 by verylonglogin.reg — 2011-12-24T06:03:56Z
And a better one (CTFE friendly, no need to specify param number): --- private ref string wrap(string s) { static struct GCString { string str; } auto gcStr = new GCString(); gcStr.str = s; return gcStr.str; } --- Yes, hello Java-like arrays!
Comment #5 by issues.dlang — 2011-12-24T13:11:00Z
This code shouldn't even be legal. A string literal isn't an lvalue and can't be passed by reference. It's bug that that compiles at all. This looks like a duplicate of bug# 4539.
Comment #6 by verylonglogin.reg — 2011-12-25T02:49:32Z
*** This issue has been marked as a duplicate of issue 4539 ***