Open ebhasker opened 6 years ago
Thanks for the issue! Make sure it satisfies this checklist. My human colleagues will appreciate it!
Here is what to expect next, and if anyone wants to comment, keep these things in mind.
Thanks @zwilias - that indeed looks extremely relevant.
Running OSX 10.11.6 and getting the incorrect output.
Ellie link for ref https://ellie-app.com/rjrWfjNdwa1/0
Ah. Ellie is sort of a separate case (as it involves the elm-compiler compiled to JS through GHCJS), which makes this effect observable on all platforms due to GHCJS only using 32bits for number, independent of the platform is was compiled on.
Nevertheless, it's the same root-cause listed here: https://github.com/elm-lang/elm-compiler/issues/1246#issuecomment-313390964 - Haskell's Int
type doesn't guarantee the same range as representable in the integer part of a JS number
.
Running OSX 10.11.6 and getting the incorrect output.
I can't reproduce this on 0.19 on macOS.
> String.fromInt (2^31) ++ " versus " ++ String.fromInt (2147483648)
"2147483648 versus 2147483648" : String
It may still be reproducible on Windows though!
still present in 0.19?
It's not present as is, but if you increase to 64-bit integers, the problem comes back.
For example, in elm repl (0.19.1 on Windows):
>elm repl
---- Elm 0.19.1 ----------------------------------------------------------------
Say :help for help and :exit to exit! More at <https://elm-lang.org/0.19.1/repl>
--------------------------------------------------------------------------------
> 9223372036854775807
9223372036854776000 : number
> 9223372036854775808
-9223372036854776000 : number
>
Overflow because we've reached the limit of 64-bit integers.
Underflow gives a syntax error at least, but for a value that should have been representable (-2^63 = -9223372036854775808)?
> -9223372036854775807
-9223372036854776000 : number
> -9223372036854775808
[stdin]:876
var $author$project$Elm_Repl$repl_input_value_ = --9223372036854775808;
^^^^^^^^^^^^^^^^^^^
SyntaxError: Invalid left-hand side expression in prefix operation
at new Script (vm.js:102:7)
at createScript (vm.js:262:10)
at Object.runInThisContext (vm.js:310:10)
at internal/process/execution.js:81:19
at [stdin]-wrapper:6:22
at evalScript (internal/process/execution.js:80:60)
at internal/main/eval_stdin.js:29:5
at Socket.<anonymous> (internal/process/execution.js:209:5)
at Socket.emit (events.js:412:35)
at endReadableNT (internal/streams/readable.js:1317:12)
Another experiment:
> a: Int
| a = -9223372036854775807
|
-9223372036854776000 : Int
> a = -9223372036854775807
-9223372036854776000 : number
> a: Int
| a = -9223372036854775808
|
[stdin]:876
var $author$project$Elm_Repl$a = --9223372036854775808;
^^^^^^^^^^^^^^^^^^^
SyntaxError: Invalid left-hand side expression in prefix operation
at new Script (vm.js:102:7)
at createScript (vm.js:262:10)
at Object.runInThisContext (vm.js:310:10)
at internal/process/execution.js:81:19
at [stdin]-wrapper:6:22
at evalScript (internal/process/execution.js:80:60)
at internal/main/eval_stdin.js:29:5
at Socket.<anonymous> (internal/process/execution.js:209:5)
at Socket.emit (events.js:412:35)
at endReadableNT (internal/streams/readable.js:1317:12)
>
In a bizarre twist, if you add another digit (and preserve the previous ones), you get weirdness again (cycles back to 0):
> -92233720368547758070
[stdin]:876
var $author$project$Elm_Repl$repl_input_value_ = --10;
^^
SyntaxError: Invalid left-hand side expression in prefix operation
at new Script (vm.js:102:7)
at createScript (vm.js:262:10)
at Object.runInThisContext (vm.js:310:10)
at internal/process/execution.js:81:19
at [stdin]-wrapper:6:22
at evalScript (internal/process/execution.js:80:60)
at internal/main/eval_stdin.js:29:5
at Socket.<anonymous> (internal/process/execution.js:209:5)
at Socket.emit (events.js:412:35)
at endReadableNT (internal/streams/readable.js:1317:12)
> -92233720368547758071
[stdin]:876
var $author$project$Elm_Repl$repl_input_value_ = --9;
^
SyntaxError: Invalid left-hand side expression in prefix operation
at new Script (vm.js:102:7)
at createScript (vm.js:262:10)
at Object.runInThisContext (vm.js:310:10)
at internal/process/execution.js:81:19
at [stdin]-wrapper:6:22
at evalScript (internal/process/execution.js:80:60)
at internal/main/eval_stdin.js:29:5
at Socket.<anonymous> (internal/process/execution.js:209:5)
at Socket.emit (events.js:412:35)
at endReadableNT (internal/streams/readable.js:1317:12)
> -92233720368547758080
0 : number
> -9223372036854775808092233720368547758070
[stdin]:876
var $author$project$Elm_Repl$repl_input_value_ = --10;
^^
SyntaxError: Invalid left-hand side expression in prefix operation
at new Script (vm.js:102:7)
at createScript (vm.js:262:10)
at Object.runInThisContext (vm.js:310:10)
at internal/process/execution.js:81:19
at [stdin]-wrapper:6:22
at evalScript (internal/process/execution.js:80:60)
at internal/main/eval_stdin.js:29:5
at Socket.<anonymous> (internal/process/execution.js:209:5)
at Socket.emit (events.js:412:35)
at endReadableNT (internal/streams/readable.js:1317:12)
> -9223372036854775808092233720368547758080
0 : number
> -92233720368547758080922337203685477580809223372036854775808092233720368547758070
[stdin]:876
var $author$project$Elm_Repl$repl_input_value_ = --10;
^^
SyntaxError: Invalid left-hand side expression in prefix operation
at new Script (vm.js:102:7)
at createScript (vm.js:262:10)
at Object.runInThisContext (vm.js:310:10)
at internal/process/execution.js:81:19
at [stdin]-wrapper:6:22
at evalScript (internal/process/execution.js:80:60)
at internal/main/eval_stdin.js:29:5
at Socket.<anonymous> (internal/process/execution.js:209:5)
at Socket.emit (events.js:412:35)
at endReadableNT (internal/streams/readable.js:1317:12)
> -92233720368547758080922337203685477580809223372036854775808092233720368547758080
0 : number
I can keep going, but you get the gist... 😄
The "double negative sign" seems to point to some strange substitution that happens ('-' + '-10' ?)
This seems related to: https://github.com/elm/compiler/issues/1246
I guess the question transforms into, what should Elm do with an integer overflow / underflow?
My vote is for some sort of make error. Or at least a warning that cautions folks about numbers that are too big/small.
This seems to be a... Parser / code gen problem
SSCCE (with core and html libraries)
Compiling using elm-make under Windows 10, x64, gives me the following in the resulting javascript:
Note the minus sign, specifically. Suspecting a numerical overflow sort of problem.
Embedding this app and opening in any major browser shows the incorrect output:
2147483648 versus -2147483648
Note that this seems specific to the Windows version. Compiling the same example using elm-make under Linux (Ubuntu 16.04, x64 in my case) gives the javascript output:
Which results in the correct output:
2147483648 versus 2147483648
Note: Numbers less than 2^31 seem to not raise the issue. So hopefully this is also a min-SSCCEE (unless you count negative numbers!)
Please let me know if you need more info about my architecture (i.e. if you cannot reproduce this somehow).