Index: expr.c =================================================================== RCS file: /home/ncvs/src/contrib/binutils/gas/expr.c,v retrieving revision 1.1.1.7 diff -u -r1.1.1.7 expr.c --- expr.c 11 Oct 2002 06:00:09 -0000 1.1.1.7 +++ expr.c 2 Feb 2003 03:06:50 -0000 @@ -37,6 +37,7 @@ #ifdef BFD64 static valueT generic_bignum_to_int64 PARAMS ((void)); #endif +static void bignum_negate PARAMS ((expressionS *)); static void integer_constant PARAMS ((int radix, expressionS * expressionP)); static void mri_char_constant PARAMS ((expressionS *)); static void current_location PARAMS ((expressionS *)); @@ -756,6 +757,40 @@ } } +/* In: An expressionP for a bignum to negate. + + Out: A negated expressionP. + && exp->X_add_number == 0 + && symbol_get_value_expression (exp->X_add_symbol)->X_op == O_big +*/ + +static void +bignum_negate (exp) + expressionS *exp; +{ + int i; + unsigned long carry; + + /* Negate the bignum: one's complement each digit and add 1. */ + carry = 1; + for (i = 0; i < exp->X_add_number; i++) + { + unsigned long next; + + next = (((~(generic_bignum[i] & LITTLENUM_MASK)) + & LITTLENUM_MASK) + + carry); + generic_bignum[i] = next & LITTLENUM_MASK; + carry = next >> LITTLENUM_NUMBER_OF_BITS; + } + + if (carry > 0) + { + generic_bignum[exp->X_add_number] = carry; + exp->X_add_number ++; + } +} + /* In: Input_line_pointer points to 1st char of operand, which may be a space. @@ -1082,14 +1117,24 @@ else if (expressionP->X_op != O_illegal && expressionP->X_op != O_absent) { - expressionP->X_add_symbol = make_expr_symbol (expressionP); if (c == '-') - expressionP->X_op = O_uminus; + { + if (expressionP->X_op == O_big + && expressionP->X_add_number > 0) + bignum_negate(expressionP); + else + expressionP->X_op = O_uminus; + } else if (c == '~' || c == '"') expressionP->X_op = O_bit_not; else expressionP->X_op = O_logical_not; - expressionP->X_add_number = 0; + + if (expressionP->X_op != O_big) + { + expressionP->X_add_number = 0; + expressionP->X_add_symbol = make_expr_symbol (expressionP); + } } else as_warn (_("Unary operator %c ignored because bad operand follows"),