Error messages resulting from wrong operands being used with insns were partially meaningless. Built and tested on ia64-unknown-linux-gnu. Jan gas/ 2005-01-24 Jan Beulich * config/tc-ia64.c (parse_operands): Parse all specified operands, immediately discarding (but counting) those exceeding the maximum possible amount. Track whether output and input operand counts ever matched, and use this to better indicate which of the operands/ operand types was wrong; specifically don't default to pointing to the first operand. --- /home/jbeulich/src/binutils/mainline/2005-01-24.08.40/gas/config/tc-ia64.c 2005-01-18 10:43:33.000000000 +0100 +++ 2005-01-24.08.40/gas/config/tc-ia64.c 2005-01-24 11:16:17.997766627 +0100 @@ -5792,11 +5792,22 @@ parse_operands (idesc) ++num_outputs; } - for (; i < NELEMS (CURR_SLOT.opnd); ++i) + for (; ; ++i) { - sep = parse_operand (CURR_SLOT.opnd + i); - if (CURR_SLOT.opnd[i].X_op == O_absent) - break; + if (i < NELEMS (CURR_SLOT.opnd)) + { + sep = parse_operand (CURR_SLOT.opnd + i); + if (CURR_SLOT.opnd[i].X_op == O_absent) + break; + } + else + { + expressionS dummy; + + sep = parse_operand (&dummy); + if (dummy.X_op == O_absent) + break; + } ++num_operands; @@ -5847,14 +5858,21 @@ parse_operands (idesc) } } - highest_unmatched_operand = 0; + highest_unmatched_operand = -4; curr_out_of_range_pos = -1; error_pos = 0; - expected_operand = idesc->operands[0]; for (; idesc; idesc = get_next_opcode (idesc)) { if (num_outputs != idesc->num_outputs) continue; /* mismatch in # of outputs */ + if (highest_unmatched_operand < 0) + highest_unmatched_operand |= 1; + if ((num_operands < NELEMS (idesc->operands) + && idesc->operands[num_operands]) + || (num_operands > 0 && !idesc->operands[num_operands - 1])) + continue; /* mismatch in number of arguments */ + if (highest_unmatched_operand < 0) + highest_unmatched_operand |= 2; CURR_SLOT.num_fixups = 0; @@ -5907,10 +5925,6 @@ parse_operands (idesc) continue; } - if (num_operands < NELEMS (idesc->operands) - && idesc->operands[num_operands]) - continue; /* mismatch in number of arguments */ - break; } if (!idesc) @@ -5919,6 +5933,10 @@ parse_operands (idesc) as_bad ("Operand %u of `%s' should be %s", error_pos + 1, mnemonic, elf64_ia64_operands[expected_operand].desc); + else if (highest_unmatched_operand < 0 && !(highest_unmatched_operand & 1)) + as_bad ("Wrong number of output operands"); + else if (highest_unmatched_operand < 0 && !(highest_unmatched_operand & 2)) + as_bad ("Wrong number of input operands"); else as_bad ("Operand mismatch"); return 0;