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

V gets confused when dealing with Optional Sum Types and spits invalid C code #23349

Closed
RpxdYTX opened this issue Jan 2, 2025 · 9 comments · Fixed by #23358
Closed

V gets confused when dealing with Optional Sum Types and spits invalid C code #23349

RpxdYTX opened this issue Jan 2, 2025 · 9 comments · Fixed by #23358
Assignees
Labels
Bug This tag is applied to issues which reports bugs. Option Type Bugs/feature requests, that are related to `?Type`. Unit: Checker Bugs/feature requests, that are related to the type checker.

Comments

@RpxdYTX
Copy link

RpxdYTX commented Jan 2, 2025

Describe the bug

When using ?SumType, the compiler sometimes gets confused and generates invalid C code. I found two scenarios where this happens.

Reproduction Steps

  1. Casting ?T to U when T = U | Other:
type Sum = int | string
fn sum() ?Sum { return Sum(5) }

a := sum()
println(a as int) // V compiler should error, since we're casting from ?Sum to int
  1. Assigning T to ?T and checking if ?T is U (when T = U | Other:
mut a := sum() // a: ?Sum
// ...
a = sum() or { ... } // (sum() or { ... }) converted to ?Sum
if a !is string { ... } // V compiler should error, since we're checking if ?Sum is string

Expected Behavior

The V compiler should error on both situations, preventing the error from propagating into the generated C code, which is harder to analyse

Current Behavior

In my current codebase, it gave these errors:

================== C compilation error (from cc): ==============                                                              cc:        |                                       ~~                                                                            ^~~~~~~~~                                                                                                                  cc: /data/data/com.termux/files/usr/tmp/v_10246/hex.01JGMQ477ZJQZGF038M50E0775.tmp.c:11955:51: error: no member named '_main__Ident' in 'struct _option_main__Token'
cc:  11955 |                 string name = (*(main__Ident*)__as_cast((ident)._main__Ident,(ident)._typ, 111)).ident;
cc:        |                                                         ~~~~~~~ ^
cc: /data/data/com.termux/files/usr/tmp/v_10246/hex.01JGMQ477ZJQZGF038M50E0775.tmp.c:11955:72: error: no member named '_typ' in 'struct _option_main__Token'
cc:  11955 |                 string name = (*(main__Ident*)__as_cast((ident)._main__Ident,(ident)._typ, 111)).ident;
cc:        |                                                                              ~~~~~~~ ^
cc: 3 warnings and 2 errors generated.
... (the original output was 17 lines long, and was truncated to 8 lines)
================================================================
(You can pass `-cg`, or `-show-c-output` as well, to print all the C error messages).
builder error:
==================
C error found. It should never happen, when compiling pure V code.

The code contained both cases in it.

Possible Solution

No response

Additional Information/Context

No response

V version

V 0.4.9 7b9b3dd

Environment details (OS name and version, etc.)

V full version: V 0.4.9 b487986.7b9b3dd OS: termux, 3.18.140-SIMPLE-KERNEL_V1.1, #1 SMP PREEMPT Sun Apr 18 03:22:59 -03 2021
Processor: 8 cpus, 64bit, little endian getwd: /storage/emulated/0/Documents/hex vexe: /data/data/com.termux/files/home/.v/v vexe mtime: 2024-12-31 18:09:35 vroot: OK, value: /data/data/com.termux/files/home/.v VMODULES: OK, value: /data/data/com.termux/files/home/.vmodules
VTMP: OK, value: /data/data/com.termux/files/usr/tmp/v_10246 Git version: git version 2.47.1 Git vroot status: weekly.2024.53 (15 commit(s) behind V master)
.git/config present: true
CC version: clang version 19.1.6 emcc version: N/A
thirdparty/tcc status: thirdparty-unknown-unknown de82a13

Note

You can use the 👍 reaction to increase the issue's priority for developers.

Please note that only the 👍 reaction to the issue itself counts as a vote.
Other reactions and those to comments will not be taken into account.

@RpxdYTX RpxdYTX added the Bug This tag is applied to issues which reports bugs. label Jan 2, 2025
@JalonSolov
Copy link
Contributor

You V is at least 15 commits behind the current. Do v up and try your examples again.

When I tried your first example here, it worked fine, with no errors from V or C. I saved it as x.v:

$ v run x.v
5
$

@RpxdYTX
Copy link
Author

RpxdYTX commented Jan 3, 2025

Sorry, i forgot the question mark before Sum in the sum function. Just upped v and it still yields C errors, instead of signalizing that converting from ?T to U is invalid, though the second example seems to have been solved

@jorgeluismireles
Copy link

The C error is produced when an unwrapped option is tried to be converted with as int:

type Sum = int | string
fn sum() ?Sum { return Sum(5) }

a := sum()?
println(a as int) // 5
b := sum()
println(b)        // Option(Sum(5))
println(b? as int) // 5
println(b as int) // C error

In the last line b is an unwrapped option converted to as int that V couldn't check.

Running code...
Can't run code. The server returned an error:
/tmp/v_60000/../../../../../../box/code.v:9: error: field not found: _int
builder error: 
==================
C error found. It should never happen, when compiling pure V code.
This is a V compiler bug, please report it using `v bug file.v`,
or goto https://github.com/vlang/v/issues/new/choose .
You can also use #help on Discord: https://discord.gg/vlang .
Exited with error status 1
Please try again.

See https://play.vlang.io/p/5a99d599af

@RpxdYTX
Copy link
Author

RpxdYTX commented Jan 3, 2025

So just

a := sum()
println(a as int)

doesn't trigger the error?

@RpxdYTX
Copy link
Author

RpxdYTX commented Jan 3, 2025

Just tested, it does

@jorgeluismireles
Copy link

jorgeluismireles commented Jan 3, 2025

Yes, simply these two lines:

type Sum = int | string
println(?Sum(5) as int)

@felipensp felipensp added Unit: Checker Bugs/feature requests, that are related to the type checker. Option Type Bugs/feature requests, that are related to `?Type`. labels Jan 3, 2025
@felipensp felipensp self-assigned this Jan 3, 2025
@spytheman
Copy link
Member

type Sum = int | string
println(?Sum(5) as int)

Please file another issue for this.

@RpxdYTX
Copy link
Author

RpxdYTX commented Jan 4, 2025

Isn't it the same thing?

@JalonSolov
Copy link
Contributor

Doesn't appear to be. Just tried with latest update, and got

$ v -g run x.v
/tmp/v_1000/../../../../../../home/jalon/x.v:2: error: field not found: _int
builder error: 
==================
C error found. It should never happen, when compiling pure V code.
...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Bug This tag is applied to issues which reports bugs. Option Type Bugs/feature requests, that are related to `?Type`. Unit: Checker Bugs/feature requests, that are related to the type checker.
Projects
None yet
Development

Successfully merging a pull request may close this issue.

5 participants