v icon indicating copy to clipboard operation
v copied to clipboard

Casting interface as itself generates invalid C code

Open edam opened this issue 2 years ago • 0 comments

Describe the bug

Smartcasting an interface to itself creates invalid C-code and generates a casting function (in C) which unnecessarily duplicates the interface struct.

Expected Behavior

Smartcasting an interface to its self should have no effect!

Current Behavior

Causes C compiler error.

Reproduction Steps

The following code produces the problem:

interface Foo {}

fn (f &Foo) func() {}

struct Bar {}

fn main() {
    mut f := Foo(Bar{})
    if mut f is Foo {
        f.func()
    }
}

C compiler error:

error: cannot take the address of an rvalue of type 'main__Foo' (aka 'struct main__Foo')
                main__Foo_func(&(I_main__Foo_as_I_main__Foo(f)));
                               ^ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

Possible Solution

No response

Additional Information/Context

In addition, the following unnecessary code is generated in C by V:

static inline bool I_main__Foo_is_I_main__Foo(main__Foo x) {
	return (x._typ == _main__Foo_main__Bar_index);
}
static inline main__Foo I_main__Foo_as_I_main__Foo(main__Foo x) {
	if (x._typ == _main__Foo_main__Bar_index) return I_main__Bar_to_Interface_main__Foo(x._main__Bar);
	_v_panic(string__plus(string__plus(tos3("`as_cast`: cannot convert "), tos3(v_typeof_interface_main__Foo(x._typ))), tos3(" to Foo")));
	return (main__Foo){0};
}

Issues with above generated code:

  • I_main__Foo_is_I_main__Foo(main__Foo x) is always True, isn't it? Or can x._typ be 0?
  • I_main__Foo_as_I_main__Foo(main__Foo x) is unnecessary, I think?
  • I_main__Foo_as_I_main__Foo(main__Foo x) calls I_main__Bar_to_Interface_main__Foo() which makes a NEW main.Foo and copies values in to it!

V version

V 0.4.0 207203f

Environment details (OS name and version, etc.)

macos

edam avatar Jan 20 '23 20:01 edam