Invert operand should be integer.

This commit is contained in:
whitequark 2015-06-13 13:45:09 +03:00
parent 1c48874a2a
commit 23f33d7239
3 changed files with 25 additions and 6 deletions

View File

@ -58,6 +58,12 @@ class TList(types.TMono):
super().__init__("list", {"elt": elt})
def is_int(typ, width=None):
if width:
return types.is_mono(typ, "int", {"width": width})
else:
return types.is_mono(typ, "int")
def is_numeric(typ):
return isinstance(typ, types.TMono) and \
typ.name in ('int', 'float')

View File

@ -389,16 +389,26 @@ class Inferencer(algorithm.Visitor):
node.loc, value.loc, self._makenotes_elts(node.values, "an operand"))
def visit_UnaryOpT(self, node):
operand_type = node.operand.type.find()
if isinstance(node.op, ast.Not):
node.type = builtins.TBool()
else:
operand_type = node.operand.type.find()
elif isinstance(node.op, ast.Invert):
if builtins.is_int(operand_type):
node.type = operand_type
elif not types.is_var(operand_type):
diag = diagnostic.Diagnostic("error",
"expected ~ operand to be of integer type, not {type}",
{"type": types.TypePrinter().name(operand_type)},
node.operand.loc)
self.engine.process(diag)
else: # UAdd, USub
if builtins.is_numeric(operand_type):
node.type = operand_type
elif not types.is_var(operand_type):
diag = diagnostic.Diagnostic("error",
"expected operand to be of numeric type, not {type}",
{"type": types.TypePrinter().name(operand_type)},
"expected unary {op} operand to be of numeric type, not {type}",
{"op": node.op.loc.source(),
"type": types.TypePrinter().name(operand_type)},
node.operand.loc)
self.engine.process(diag)

View File

@ -17,5 +17,8 @@ a = b
# CHECK-L: note: an operand of type int(width='a)
# CHECK-L: note: an operand of type bool
# CHECK-L: ${LINE:+1}: error: expected operand to be of numeric type, not list(elt='a)
~[]
# CHECK-L: ${LINE:+1}: error: expected unary + operand to be of numeric type, not list(elt='a)
+[]
# CHECK-L: ${LINE:+1}: error: expected ~ operand to be of integer type, not float
~1.0