From e50caad4825f5b8f8083bda160ef94dc42b9947b Mon Sep 17 00:00:00 2001 From: Andreas Baumann Date: Fri, 24 Jul 2020 19:44:18 +0200 Subject: refactored asm-i386 also for symbols in expression trees, tests working again --- ecomp-c/asm-i386.c | 93 ++++++++++++++++++++++++++++++++++++------------------ 1 file changed, 62 insertions(+), 31 deletions(-) diff --git a/ecomp-c/asm-i386.c b/ecomp-c/asm-i386.c index a0a65a7..5ece809 100644 --- a/ecomp-c/asm-i386.c +++ b/ecomp-c/asm-i386.c @@ -384,6 +384,7 @@ static S_Symbol getSym( void ) case '$': look = getChar( ); if( look == '$' ) { + look = getChar( ); s = S_current_org; } else if( ( look >= '0' && look <= '9' ) || ( look >= 'a' && look <= 'f' ) || @@ -790,7 +791,7 @@ typedef struct OperandInfo { char *str; Register reg; int addr; - Symbol *symbol; + /* Symbol *symbol; */ struct OperandInfo *next; struct ExpressionNode *node; } OperandInfo; @@ -962,6 +963,19 @@ static OpcodeInfo *parseOpcode( void ) return opcode_info; } +static void free_expression_node( struct ExpressionNode *node ); + +static void free_operand_info( OperandInfo *operand_info ) +{ + if( operand_info->str != NULL ) { + free( operand_info->str ); + } + if( operand_info->node != NULL ) { + free_expression_node( operand_info->node ); + } + free( operand_info ); +} + static void free_opcode_info( OpcodeInfo *opcode_info ) { OperandInfo *ptr, *tmp; @@ -969,10 +983,7 @@ static void free_opcode_info( OpcodeInfo *opcode_info ) ptr = opcode_info->operand; while( ptr != NULL ) { tmp = ptr->next; - if( ptr->str != NULL ) { - free( ptr->str ); - } - free( ptr ); + free_operand_info( ptr ); ptr = tmp; } @@ -1016,19 +1027,6 @@ static int is32bitRegister( Register r ) } } -static void assign_label( OperandInfo *operand_info, char *label ) -{ - Symbol *symbol; - - symbol = get_symbol( label ); - if( symbol != NULL ) { - operand_info->symbol = symbol; - } else { - symbol = insert_symbol( ident ); - operand_info->symbol = symbol; - } -} - typedef enum ExpressionNodeType { EXPRESSION_NODE_TYPE_CONST, EXPRESSION_NODE_TYPE_VAR, @@ -1076,7 +1074,7 @@ static ExpressionNode *parseFactor( void ) } else if( sym == S_ident ) { symbol = get_symbol( ident ); if( symbol == NULL ) { - Abort( "Unknown identifier '%s'", ident ); + symbol = insert_symbol( ident ); } node = create_expression_node( ); node->type = EXPRESSION_NODE_TYPE_VAR; @@ -1142,6 +1140,8 @@ static int evaluateExpression( ExpressionNode *node ) case EXPRESSION_NODE_TYPE_CONST: return node->integer_value; case EXPRESSION_NODE_TYPE_VAR: + return node->symbol->addr; + /* TODO */ case EXPRESSION_NODE_TYPE_OP: Abort( "Const node expression node not implemented yet" ); } @@ -1157,18 +1157,18 @@ static OperandInfo *parseOperand( OpcodeInfo *opcode_info ) operand_info->str = NULL; operand_info->next = NULL; operand_info->addr = ADDRESS_UNDEFINED; - operand_info->symbol = NULL; + operand_info->node = NULL; if( sym == S_ident ) { /* op like eax or an address jmp x */ if( isRegister( ident ) ) { operand_info->type = OPERAND_REGISTER; operand_info->reg = getRegister( ident ); + sym = getSym( ); } else { operand_info->type = OPERAND_MEMORY_DIRECT; - assign_label( operand_info, ident ); + operand_info->node = parseExpression( ); } - sym = getSym( ); } else if( sym == S_number || sym == S_current_org || sym == S_current_addr ) { /* absolute operand, like in mov eax, $1, * we have assemble-time expressions here @@ -1176,7 +1176,6 @@ static OperandInfo *parseOperand( OpcodeInfo *opcode_info ) operand_info->type = OPERAND_ABSOLUTE; operand_info->node = parseExpression( ); operand_info->num = evaluateExpression( operand_info->node ); - free_expression_node( operand_info->node ); } else if( sym == S_string ) { operand_info->type = OPERAND_ABSOLUTE; operand_info->str = AllocateAndCopyStr( str ); @@ -1187,13 +1186,13 @@ static OperandInfo *parseOperand( OpcodeInfo *opcode_info ) * register indirect as [ebx] */ Expect( S_lbrak ); - Expect( S_ident ); if( isRegister( ident ) ) { operand_info->type = OPERAND_REGISTER_INDIRECT; operand_info->reg = getRegister( ident ); + sym = getSym( ); } else { operand_info->type = OPERAND_MEMORY_INDIRECT; - assign_label( operand_info, ident ); + operand_info->node = parseExpression( ); } Expect( S_rbrak ); } else if( sym == S_newline ) { @@ -1542,8 +1541,8 @@ static int patchup_addresses( OpcodeInfo *opcode_info ) while( operand != NULL ) { if( operand->type == OPERAND_MEMORY_DIRECT || operand->type == OPERAND_MEMORY_INDIRECT ) { if( operand->addr == ADDRESS_UNDEFINED ) { - if( operand->symbol != NULL ) { - operand->addr = operand->symbol->addr; + if( operand->node != NULL ) { + operand->addr = evaluateExpression( operand->node ); } } } @@ -1555,12 +1554,44 @@ static int patchup_addresses( OpcodeInfo *opcode_info ) return res; } +static char *get_expression_comment( ExpressionNode *node, char *buf, int bufsize ) +{ + char s[MAX_STRING_LEN+1]; + + switch( node->type ) { + case EXPRESSION_NODE_TYPE_CONST: + snprintf( s, MAX_STRING_LEN, "%d", node->integer_value ); + strlcat( buf, s, bufsize ); + break; + + case EXPRESSION_NODE_TYPE_VAR: + strlcat( buf, node->symbol->name, bufsize ); + break; + + case EXPRESSION_NODE_TYPE_OP: + if( node->left != NULL ) { + get_expression_comment( node->left, buf, bufsize ); + } + strlcat( buf, symname[node->op], bufsize ); + if( node->right != NULL ) { + get_expression_comment( node->right, buf, bufsize ); + } + break; + + default: + Abort( "Unhandled case in expression tree while outputing comment!" ); + } + + return buf; +} + static void print_opcodes( OpcodeInfo *opcode_info ) { OpcodeInfo *opcode = opcode_info; OperandInfo *operand; char indent[3]; int first; + char buf[MAX_STRING_LEN+1]; while( opcode != NULL ) { first = 1; @@ -1586,13 +1617,13 @@ static void print_opcodes( OpcodeInfo *opcode_info ) fprintf( stderr, "%s%s", indent, registername[operand->reg] ); break; case OPERAND_MEMORY_DIRECT: - fprintf( stderr, "%s%s=%X", indent, - ( operand->symbol != NULL ) ? operand->symbol->name : "NULL", + fprintf( stderr, "%s%s=%X", indent, + get_expression_comment( operand->node, buf, MAX_STRING_LEN ), operand->addr ); break; case OPERAND_MEMORY_INDIRECT: fprintf( stderr, "%s[%s=%X]", indent, - ( operand->symbol != NULL ) ? operand->symbol->name : "NULL", + get_expression_comment( operand->node, buf, MAX_STRING_LEN ), operand->addr ); break; case OPERAND_REGISTER_INDIRECT: @@ -1690,7 +1721,7 @@ static void compute_addresses( OpcodeInfo *opcode_info ) while( operand != NULL ) { if( operand->type == OPERAND_MEMORY_DIRECT || operand->type == OPERAND_MEMORY_INDIRECT ) { - operand->addr = operand->symbol->addr; + operand->addr = evaluateExpression( operand->node ); if( DEBUG_PARSER ) { fprintf( stderr, "LC=$%X assigned to operand at $%X\n", LC, operand->addr ); } -- cgit v1.2.3-54-g00ecf