python: Don't abuse hex()
authorMathieu Bridon <bochecha@daitauha.fr>
Sun, 17 Jun 2018 15:53:16 +0000 (17:53 +0200)
committerEric Engestrom <eric.engestrom@intel.com>
Wed, 1 Aug 2018 13:26:19 +0000 (14:26 +0100)
The hex() builtin returns a string containing the hexa-decimal
representation of an integer.

When the argument is not an integer, then the function calls that
object's __hex__() method, if one is defined. That method is supposed to
return a string.

While that's not explicitly documented, that string is supposed to be a
valid hexa-decimal representation for a number. Python 2 doesn't enforce
this though, which is why we got away with returning things like
'NIR_TRUE' which are not numbers.

In Python 3, the hex() builtin instead calls an object's __index__()
method, which itself must return an integer. That integer is then
automatically converted to a string with its hexa-decimal representation
by the rest of the hex() function.

As a result, we really can't make this compatible with Python 3 as it
is.

The solution is to stop using the hex() builtin, and instead use a hex()
object method, which can return whatever we want, in Python 2 and 3.

Signed-off-by: Mathieu Bridon <bochecha@daitauha.fr>
Reviewed-by: Eric Engestrom <eric.engestrom@intel.com>
Reviewed-by: Dylan Baker <dylan@pnwbakers.com>
src/compiler/nir/nir_algebraic.py

index fda72d3c69e9046a02a72cecbe2851b8816bf63c..6b8c881803bda582b9ed569fc0f763281d429aa7 100644 (file)
@@ -79,7 +79,7 @@ class Value(object):
 static const ${val.c_type} ${val.name} = {
    { ${val.type_enum}, ${val.bit_size} },
 % if isinstance(val, Constant):
-   ${val.type()}, { ${hex(val)} /* ${val.value} */ },
+   ${val.type()}, { ${val.hex()} /* ${val.value} */ },
 % elif isinstance(val, Variable):
    ${val.index}, /* ${val.var_name} */
    ${'true' if val.is_constant else 'false'},
@@ -133,7 +133,7 @@ class Constant(Value):
          assert self.bit_size == 0 or self.bit_size == 32
          self.bit_size = 32
 
-   def __hex__(self):
+   def hex(self):
       if isinstance(self.value, (bool)):
          return 'NIR_TRUE' if self.value else 'NIR_FALSE'
       if isinstance(self.value, (int, long)):