Search code examples
javascriptnode.jsv8

Why does V8 isValidSmi native function returns true on float number?


Don't understand why V8 native function %isValidSmi(2.2) returns true in Nodejs.

NodeJS version: 8.9.4

I thought SMI number it is something similar to int32


Solution

  • (V8 developer here.) In short, because it performs a NumberToInt32 conversion before looking at the value.

    You might say that that's a surprising implementation choice, and indeed I can't tell you why it's been done that way. Apparently for the intended use cases of this internal helper, the resulting behavior was acceptable or even desired.

    "internal helper" is the key term there. V8's internal "runtime functions" are not intended for public usage, as such they're not exposed by default, they're not specified or standardized or documented, and they're typically rather restrictive regarding the arguments they accept (for example, %IsValidSmi({}) will crash rather than returning false, because it's not designed to handle arbitrary inputs). As a V8 developer, you just have to look at the code to see if a given runtime function does what you need, and as a non-V8-developer, you're not supposed to have a reason to care :-)

    Such implementation details aside, your understanding is correct that 2.2 is not a valid Smi. It just so happens that %IsValidSmi() is not a suitable way to determine that. FWIW, there's also %IsSmi(value), which checks whether value is currently internally represented as a Smi -- which is notably different from a number that could be represented as a Smi.

    Either way, our official recommendation is that your code should not care which values V8 chooses to represent as Smis. In particular, this also changes over time, both over the course of running a single program, and also as V8 versions change.