godotengine / godot

Godot Engine – Multi-platform 2D and 3D game engine
https://godotengine.org
MIT License
91.03k stars 21.18k forks source link

Calling randi() % floor(2.0) causes engine to crash silently #80486

Open jtiai opened 1 year ago

jtiai commented 1 year ago

Godot version

4.1.1.stable

System information

Godot v4.1.1.stable - Windows 10.0.22621 - Vulkan (Forward+) - dedicated NVIDIA GeForce RTX 2060 (NVIDIA; 31.0.15.3640) - Intel(R) Core(TM) i7-9750H CPU @ 2.60GHz (12 Threads)

Issue description

The following code causes game to crash silently:

var result = randi() % floor(10.0)

Steps to reproduce

Create a node, add the following code in _ready()

func _ready():
    var result = randi() % floor(10.0)
    print("Result: ", result)

Minimal reproduction project

N/A

AThousandShips commented 1 year ago

Does this happen if you do:

func _ready():
    var result = randi() % floori(10.0)
    print("Result: ", result)

There is no % operator between int and float, but it shouldn't crash

dalexeev commented 1 year ago
# Crash.
var a: int = 1
const b: Variant = 10.0
var result = a % b
# Runtime error: Invalid operands 'int' and 'float' in operator '%'.
var a: int = 1
var b: Variant = 10.0
var result = a % b
Chaosus commented 1 year ago

Confirmed. Seems due to incorrect access to null pointer in gdscript vm:

image

dalexeev commented 1 year ago

https://github.com/godotengine/godot/blob/7df393312fa8eab98231f2c335366a1ef6205367/modules/gdscript/gdscript_byte_codegen.cpp#L588-L625

 0: line 2:     var a: int = 1
 2: assign stack(3) = const(1)
 5: line 3:     const b: Variant = 10.0
 7: line 4:     var result = a % b
 9: validated operator stack(6) = stack(3) % const(10)
 14: assign stack(5) = stack(6)
 17: assign stack(6) = false
 19: == END ==
 0: line 2:     var a: int = 1
 2: assign stack(3) = const(1)
 5: line 3:     var b: Variant = 10.0
 7: assign stack(4) = const(10)
 10: line 4:    var result = a % b
 12: operator stack(6) = stack(3) % stack(4)
 21: assign stack(5) = stack(6)
 24: assign stack(6) = false
 26: == END ==