71 lines
2.4 KiB
Plaintext
71 lines
2.4 KiB
Plaintext
# ProbeGen: minimal probe for cross-generation IR instability. Do not treat as a normal feature test.
|
|
|
|
# Translate the same source with two compiler generations, then diff the emitted IR per module
|
|
# (module file name = source SHA1, so both sides are comparable).
|
|
|
|
# Gen 1: ViperC\output\viperc.exe --project Test\ProbeGen\project.vpj --clean --run --build-dir Test\ProbeGen\__vpcbuild___g1
|
|
# Gen 2: ViperC\__vpcbuild__\output\viperc.exe --project Test\ProbeGen\project.vpj --clean --run --build-dir Test\ProbeGen\__vpcbuild___g2
|
|
|
|
# WARNING [P6] breaks compilation from generation 2 onward; comment out [P6] to get Gen-2 IR for P1..P5.
|
|
from stdint import *
|
|
import win32.win32console as win32console
|
|
|
|
|
|
# [P1] Nested union parameter: VOIDPTR (typedef of t.CPtr) unioned with t.CPtr gives i8** on one side, i8* on the other.
|
|
# Declared but never called, so no link reference is produced.
|
|
extern def ProbeNestedUnion(Context: VOIDPTR*) -> BOOL
|
|
|
|
|
|
# [P2] Struct by-value parameter: COORD without | t.CPtr gives %COORD on one side, %COORD* on the other.
|
|
extern def ProbeCoordByVal(dwSize: win32console.COORD) -> BOOL
|
|
|
|
|
|
# [P5] Sink for the local uint8 = 1 literal: store it into a global so the code is not dead-code eliminated.
|
|
U8Sink: uint8 = 0
|
|
|
|
|
|
# [P3] char -> int promotion: param char, int return. One side must emit zext i8 to i32, not ret i8.
|
|
def ProbeOrd(s: char) -> int:
|
|
return s
|
|
|
|
|
|
# [P4] double comparison: params/return double. One side must emit fcmp olt double, not icmp slt double.
|
|
def ProbeMin(a: double, b: double) -> double:
|
|
if a < b:
|
|
return a
|
|
return b
|
|
|
|
|
|
# [P5] Local uint8 = 1 assignment: literal typing must emit store i8 1, not store i32 1 or trunc+store.
|
|
def ProbeU8Literal() -> uint8:
|
|
global U8Sink
|
|
result: uint8 = 1
|
|
U8Sink = result
|
|
return result
|
|
|
|
|
|
# [P6] Class field union + subscript write: field is char | t.CPtr, must null-check before indexed write.
|
|
# Generations 2+ fail here with "SyntaxError: subscript ptr is None".
|
|
class Box:
|
|
p: char*
|
|
|
|
def __init__(self):
|
|
self.p = None
|
|
|
|
def Clear(self):
|
|
if self.p != None:
|
|
self.p[0] = 0
|
|
pass
|
|
|
|
|
|
# Entry: keep main minimal, referencing each construct above so it is really translated; return 0.
|
|
# P1/P2 are extern declarations and are not called, so their difference shows in this module's declares.
|
|
export def main() -> int:
|
|
Ch: char = 'A'
|
|
BoxInst: Box = Box()
|
|
BoxInst.Clear()
|
|
ProbeOrd(Ch)
|
|
ProbeMin(1.0, 2.0)
|
|
ProbeU8Literal()
|
|
return 0
|