forked from M-Labs/artiq
inferencer: significantly improve the op-assignment diagnostic.
Before this commit, it displayed incorrect output if an error appeared on 2nd run and beyond, and displayed messages for trying to do "num32 -= num64" that made very little sense.
This commit is contained in:
parent
372e8f9b2b
commit
fd1d77767e
|
@ -1049,22 +1049,10 @@ class Inferencer(algorithm.Visitor):
|
|||
if coerced:
|
||||
return_type, target_type, value_type = coerced
|
||||
|
||||
try:
|
||||
node.target.type.unify(target_type)
|
||||
except types.UnificationError as e:
|
||||
printer = types.TypePrinter()
|
||||
note = diagnostic.Diagnostic("note",
|
||||
"expression of type {typec}",
|
||||
{"typec": printer.name(node.value.type)},
|
||||
node.value.loc)
|
||||
diag = diagnostic.Diagnostic("error",
|
||||
"expression of type {typea} has to be coerced to {typeb}, "
|
||||
"which makes assignment invalid",
|
||||
{"typea": printer.name(node.target.type),
|
||||
"typeb": printer.name(target_type)},
|
||||
node.op.loc, [node.target.loc], [note])
|
||||
self.engine.process(diag)
|
||||
return
|
||||
if isinstance(node.value, asttyped.CoerceT):
|
||||
orig_value_type = node.value.value.type
|
||||
else:
|
||||
orig_value_type = node.value.type
|
||||
|
||||
try:
|
||||
node.target.type.unify(return_type)
|
||||
|
@ -1072,17 +1060,34 @@ class Inferencer(algorithm.Visitor):
|
|||
printer = types.TypePrinter()
|
||||
note = diagnostic.Diagnostic("note",
|
||||
"expression of type {typec}",
|
||||
{"typec": printer.name(node.value.type)},
|
||||
{"typec": printer.name(orig_value_type)},
|
||||
node.value.loc)
|
||||
diag = diagnostic.Diagnostic("error",
|
||||
"the result of this operation has type {typeb}, "
|
||||
"which makes assignment to a slot of type {typea} invalid",
|
||||
"which cannot be assigned to a left-hand side of type {typea}",
|
||||
{"typea": printer.name(node.target.type),
|
||||
"typeb": printer.name(return_type)},
|
||||
node.op.loc, [node.target.loc], [note])
|
||||
self.engine.process(diag)
|
||||
return
|
||||
|
||||
try:
|
||||
node.target.type.unify(target_type)
|
||||
except types.UnificationError as e:
|
||||
printer = types.TypePrinter()
|
||||
note = diagnostic.Diagnostic("note",
|
||||
"expression of type {typec}",
|
||||
{"typec": printer.name(orig_value_type)},
|
||||
node.value.loc)
|
||||
diag = diagnostic.Diagnostic("error",
|
||||
"this operation requires the left-hand side of type {typea} "
|
||||
"to be coerced to {typeb}, which cannot be done",
|
||||
{"typea": printer.name(node.target.type),
|
||||
"typeb": printer.name(target_type)},
|
||||
node.op.loc, [node.target.loc], [note])
|
||||
self.engine.process(diag)
|
||||
return
|
||||
|
||||
node.value = self._coerce_one(value_type, node.value, other_node=node.target)
|
||||
|
||||
def visit_ForT(self, node):
|
||||
|
|
|
@ -28,10 +28,10 @@
|
|||
# CHECK-L: ${LINE:+1}: error: cannot coerce list(elt='a) to a numeric type
|
||||
[] - 1.0
|
||||
|
||||
# CHECK-L: ${LINE:+2}: error: expression of type numpy.int? has to be coerced to float, which makes assignment invalid
|
||||
# CHECK-L: ${LINE:+2}: error: the result of this operation has type float, which cannot be assigned to a left-hand side of type numpy.int?
|
||||
# CHECK-L: ${LINE:+1}: note: expression of type float
|
||||
a = 1; a += 1.0
|
||||
|
||||
# CHECK-L: ${LINE:+2}: error: the result of this operation has type (numpy.int?, float), which makes assignment to a slot of type (numpy.int?,) invalid
|
||||
# CHECK-L: ${LINE:+2}: error: the result of this operation has type (numpy.int?, float), which cannot be assigned to a left-hand side of type (numpy.int?,)
|
||||
# CHECK-L: ${LINE:+1}: note: expression of type (float,)
|
||||
b = (1,); b += (1.0,)
|
||||
|
|
Loading…
Reference in New Issue