Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Incorrect (or missing) implicit cast on array #795

Closed
horasal opened this issue Aug 18, 2014 · 2 comments
Closed

Incorrect (or missing) implicit cast on array #795

horasal opened this issue Aug 18, 2014 · 2 comments
Milestone

Comments

@horasal
Copy link
Contributor

horasal commented Aug 18, 2014

foo: func~SizeT->SSizeT[]{
    return [1,2,3,4]
}

foo: func~Int->Int[]{
    return [1,2,3,4]
}

main: func(){
    foo~SizeT()[0] toString() println()
    foo~Int()[0] toString() println()
}

gives:

8589934593
1

instead of

1
1

8589934593 = 2<<32 + 1

Generated Code:

_lang_array__Array return__foo_SizeT() {
    _lang_array__Array __arrLit1 = _lang_array__Array_new(lang_Numbers__Int, 4);

    {
        lang_Numbers__Int* __ptrLit2 = (lang_Numbers__Int[]) { 1, 2, 3, 4 };
        lang_Memory__memcpy(__arrLit1.data, __ptrLit2, 4 * ((lang_types__Class*)lang_Numbers__Int_class())->size);
    }
    return ((_lang_array__Array) (__arrLit1));
}

lang_String__String_println(lang_Numbers__SSizeT_toString(_lang_array__Array_get(return__foo_SizeT(), 0, lang_Numbers__SSizeT)));

It clear that [1,2,3] is infered as Int[] but used as SSizeT[] without (element-wise) cast.

@alexnask
Copy link
Collaborator

Yeah it seems that the array is inferred to be Int[], as you said, because integer literals are of type Int and the whole array is then implicitely casted to SSizeT[].

Rock doesn't recognize that elements of the array must be casted, it only casts the array itself.

As a temporary workaround, you can cast the first element of the array (when constructing it) to SSizeT to force rock to infer the type of the array to SSizeT.

@fasterthanlime
Copy link
Collaborator

Note that this works:

use sam-assert

foo: func ~SizeT -> SSizeT[] {
    arr: SSizeT[] = [1, 2, 3, 4]
    return arr
}

foo: func ~Int -> Int[] {
    return [1, 2, 3, 4]
}

main: func(){
    expect("1", foo~SizeT()[0] toString())
    expect("1", foo~Int()[0] toString())
}

I'm pretty sure rock should forbid array casts of any form. In your case.. it might be that it should work, I'm not entirely sure yet. But I'm wondering what's the timing with autoReturn. It would have to be aware it's returned to infer its type, so:

// would work
foo: func -> SSizeT[] { 
  [1, 2, 3]
}

// wouldn't work
foo: func -> SSizeT[] { 
  a := [1, 2, 3]
  a
}

So.. is it really worth trying to make it work like that?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants