From b437d035ddf4e4c0c566c577ee059790ed28ad9b Mon Sep 17 00:00:00 2001 From: Andrew Burgess Date: Tue, 27 Sep 2016 12:06:01 +0100 Subject: arc/nps400: Validate address type operands correctly When we match against an address type operand within an instruction it is important that we match exactly the right address type operand early on, during the opcode selection phase. If we wait until the operand insertion phase to check that we have the correct address operand, then it is too late to select an alternative opcode. This becomes important only when we have multiple opcodes with the same mnemonic, and operand lists that differ only in the type of the address operands. This commit fixes this issue, and adds some example instructions that require this issue to be fixed (the instructions are identical except for the address type operand). gas/ChangeLog: * config/tc-arc.c (find_opcode_match): Use insert function to validate matching address type operands. * testsuite/gas/arc/nps400-10.d: New file. * testsuite/gas/arc/nps400-10.s: New file. opcodes/ChangeLog: * arc-opc.c (arc_flag_operands): Add F_DI14. (arc_flag_classes): Add C_DI14. * arc-nps400-tbl.h: Add new exc instructions. --- gas/config/tc-arc.c | 19 ++++++++++++++++--- 1 file changed, 16 insertions(+), 3 deletions(-) (limited to 'gas/config/tc-arc.c') diff --git a/gas/config/tc-arc.c b/gas/config/tc-arc.c index c0bc3e4..06aee48 100644 --- a/gas/config/tc-arc.c +++ b/gas/config/tc-arc.c @@ -1720,9 +1720,22 @@ find_opcode_match (const struct arc_opcode_hash_entry *entry, switch (operand->flags & ARC_OPERAND_TYPECHECK_MASK) { case ARC_OPERAND_ADDRTYPE: - /* Check to be an address type. */ - if (tok[tokidx].X_op != O_addrtype) - goto match_failed; + { + const char *errmsg = NULL; + + /* Check to be an address type. */ + if (tok[tokidx].X_op != O_addrtype) + goto match_failed; + + /* All address type operands need to have an insert + method in order to check that we have the correct + address type. */ + gas_assert (operand->insert != NULL); + (*operand->insert) (0, tok[tokidx].X_add_number, + &errmsg); + if (errmsg != NULL) + goto match_failed; + } break; case ARC_OPERAND_IR: -- cgit v1.1