www.digitalmars.com         C & C++   DMDScript  

digitalmars.D - ref param mismatch --> segfault

reply spir <denis.spir gmail.com> writes:
Hello,

I was defining a (generic & higher-order) list-of-terms parsing func. It uses 
funcs which each parse a term of a given type from a token stream and advance a 
ref index. As you may note below, I initially forgot to 'ref' the index in the 
type of the parse func passed as param, in the generic func signature.
The compiler accepted and the program segfault-ed (for getting a value instead 
of a reference, probably). Certainly ref qualifiers should be checked, 
shouldn't they? The situation indeed is somewhat special here.

Foo getFoo(Token[] tokens, ref uint index)
{...}
Term[] getTerms (Term) (Term function (Token[], uint) parseFunc, Token[] tokens)
{...}
void main()
{

}

Denis
-- 
_________________
vita es estrany
spir.wikidot.com
Jan 24 2011
parent reply bearophile <bearophileHUGS lycos.com> writes:
spir:

 Certainly ref qualifiers should be checked, 
 shouldn't they? The situation indeed is somewhat special here.
 
 Foo getFoo(Token[] tokens, ref uint index)
 {...}
 Term[] getTerms (Term) (Term function (Token[], uint) parseFunc, Token[]
tokens)
 {...}
 void main()
 {

 }
Please, create a very small but complete program that shows the problem :-) It will go to Bugzilla. Bye, bearophile
Jan 24 2011
parent reply spir <denis.spir gmail.com> writes:
On 01/24/2011 10:07 PM, bearophile wrote:
 spir:

 Certainly ref qualifiers should be checked,
 shouldn't they? The situation indeed is somewhat special here.

 Foo getFoo(Token[] tokens, ref uint index)
 {...}
 Term[] getTerms (Term) (Term function (Token[], uint) parseFunc, Token[]
tokens)
 {...}
 void main()
 {

 }
Please, create a very small but complete program that shows the problem :-) It will go to Bugzilla. Bye, bearophile
I guess this does the job? (replaced token stream with plain stream, for the example, thus it's really artificial since getFloat just does what parse!float would do, but well... shows the bug). float getFloat(string s, ref uint index) { if (index >= s.length) return -1; float fl; string[] ss = s[index..$].split(); string s0 = ss[0]; try fl = to!float(s0); catch (Exception _) return -1; index += s0.length; return fl; } Term[] terms (Term) (Term function (string, uint) parseFunc, string s) { Term[] terms = []; Term term; uint index = 0; static enum SEP = ' '; term = parseFunc(s, index); if (term != -1) { terms ~= term; while (true) { if (index >= s.length || s[index] != SEP) break; ++ index; term = parseFunc(s, index); if (term == -1) break; terms ~= term; } } return terms; } unittest { string s = "3.33 1.0 2.2"; float[] floats = terms!(float)(&getFloat, s); writeln(floats); } If you replace "uint" by "ref uint" in terms' signature, works fine. Denis -- _________________ vita es estrany spir.wikidot.com
Jan 24 2011
parent reply bearophile <bearophileHUGS lycos.com> writes:
spir:

 I guess this does the job?
It's not minimal and it's not complete, it misses a main and the imports :-) But it's OK. A reduced test case shows that DMD has holes here, this compiles with no errors. I think this DMD bug is already in Bugzilla: void foo(ref int x) {} void bar1(void function(int) f) {} void bar2(void function(string) f) {} void main() { bar1(&foo); bar2(&foo); } Bye, bearophile
Jan 24 2011
parent "Daniel Murphy" <yebblies nospamgmail.com> writes:
"bearophile" <bearophileHUGS lycos.com> wrote in message 
news:ihl0i0$1mes$1 digitalmars.com...
 spir:

 A reduced test case shows that DMD has holes here, this compiles with no 
 errors. I think this DMD bug is already in Bugzilla:

 void foo(ref int x) {}
 void bar1(void function(int) f) {}
 void bar2(void function(string) f) {}
 void main() {
    bar1(&foo);
    bar2(&foo);
 }
Good old http://d.puremagic.com/issues/show_bug.cgi?id=3797
Jan 24 2011