Byte b_value;
Byte b_reg;
Byte *pb_resume;
- Byte *pb_skip;
Byte *pb_now;
short s_value;
Word w_value;
break;
case DW_OP_piece: // 0x93
- // XXX: Not TESTED!!
pb_now = DWARF_Common_DecodeULEB128( &qw_temp, pb_now, &qw_remain );
dw_value = (DWord)(qw_temp & 0xffffffff);
- //b_value = p_exp->result[ p_exp->b_results ].b_type;
dw_flag = p_exp->result[ p_exp->b_results ].dw_flag;
if( !(LIBGOBLIN_DWARF_FLAG_REG & dw_flag)
&& !(LIBGOBLIN_DWARF_FLAG_REGX & dw_flag)) {
break;
case DW_OP_bit_piece: // 0x9d
- // XXX: Not TESTED!!
// 1st Operand: bit size
pb_now = DWARF_Common_DecodeULEB128( &qw_temp, pb_now, &qw_remain );
// 2nd Operand: bit offset from prev-bit-piece (under-bits)
pb_now = DWARF_Common_DecodeULEB128( &qw_value, pb_now, &qw_remain );
dw_bitoffset += (DWord)(qw_value & 0xffffffff);
- //b_value = p_exp->result[ p_exp->b_results ].b_type;
dw_flag = p_exp->result[ p_exp->b_results ].dw_flag;
- if( (LIBGOBLIN_DWARF_FLAG_REG & dw_flag)
- || (LIBGOBLIN_DWARF_FLAG_REGX & dw_flag) ) {
-
- p_exp->result[ p_exp->b_results ].dw_bit_offset = dw_bitoffset;
- p_exp->result[ p_exp->b_results ].dw_bit_size = (DWord)(qw_temp & 0xffffffff);
- p_exp->result[p_exp->b_results].dw_bytes = 0;
- p_exp->b_results++;
- }
- else if( 0 < p_exp->dw_depth ) {
+ if( 0 < p_exp->dw_depth ) {
p_exp->result[p_exp->b_results].dw_flag
= p_exp->t_stack[ p_exp->dw_depth - 1 ].dw_flag;
p_exp->result[p_exp->b_results].value.qw_value
= p_exp->t_stack[ p_exp->dw_depth - 1 ].value.qw_value;
-
- p_exp->result[ p_exp->b_results ].dw_bit_offset = dw_bitoffset;
- p_exp->result[ p_exp->b_results ].dw_bit_size = (DWord)(qw_temp & 0xffffffff);
- p_exp->result[p_exp->b_results].dw_bytes = 0;
- p_exp->b_results++;
}
+ p_exp->result[ p_exp->b_results ].dw_bit_offset = dw_bitoffset;
+ p_exp->result[ p_exp->b_results ].dw_bit_size = (DWord)(qw_temp & 0xffffffff);
+ p_exp->result[p_exp->b_results].dw_bytes = 0;
+ p_exp->b_results++;
break;
case DW_OP_implicit_value: // 0x9e
- // XXX: Not TESTED!!
pb_now = DWARF_Common_DecodeULEB128( &qw_temp, pb_now, &qw_remain );
if( 8 == p_exp->b_dwsize ) { qw_value = *((QWord *)pb_now); }
else { qw_value = (QWord)(*((DWord *)pb_now)); }
p_exp->result[ p_exp->b_results ].dw_flag = LIBGOBLIN_DWARF_FLAG_LOCATION;
p_exp->result[ p_exp->b_results ].value.qw_value = qw_value;
p_exp->result[ p_exp->b_results ].dw_bytes = (DWord)qw_temp;
+ p_exp->b_results++;
break;
case DW_OP_stack_value: // 0x9f
- // XXX: Not TESTED!!
if( 1 > p_exp->dw_depth )
{ goto goto_DWARF_Expression_Evaluate_post; }
goto goto_DWARF_Expression_Evaluate_post;
}
- if( 0 < p_exp->b_callers ) {
- assert( NULL != p_exp->caller[ p_exp->b_callers - 1 ].pb_return );
- p_exp->dw_status = LIBGOBLIN_DWARF_STATUS_RETCALL;
- goto goto_DWARF_Expression_Evaluate_post;
- }
-
- if( ( p_exp->result[ p_exp->b_results ].dw_flag & LIBGOBLIN_DWARF_FLAG_REG )
- || ( p_exp->result[ p_exp->b_results ].dw_flag & LIBGOBLIN_DWARF_FLAG_REGX )) {
- p_exp->dw_status = LIBGOBLIN_DWARF_STATUS_EVALUATED;
- p_exp->b_results++;
- goto goto_DWARF_Expression_Evaluate_post;
- }
+ if( 0 == qw_remain ) {
+ if( 0 < p_exp->b_callers ) {
+ assert( NULL != p_exp->caller[ p_exp->b_callers - 1 ].pb_return );
+ p_exp->dw_status = LIBGOBLIN_DWARF_STATUS_RETCALL;
+ goto goto_DWARF_Expression_Evaluate_post;
+ }
+
+ if(( DW_OP_piece == b_opcode ) || ( DW_OP_bit_piece == b_opcode )
+ || ( DW_OP_implicit_value == b_opcode )) {
+ p_exp->dw_status = LIBGOBLIN_DWARF_STATUS_EVALUATED;
+ goto goto_DWARF_Expression_Evaluate_post;
+ }
- if( 0 < p_exp->dw_depth ) {
- p_exp->dw_status = LIBGOBLIN_DWARF_STATUS_EVALUATED;
- p_exp->result[p_exp->b_results].dw_flag
- = p_exp->t_stack[ p_exp->dw_depth - 1 ].dw_flag;
- p_exp->result[p_exp->b_results].value.qw_value
- = p_exp->t_stack[ p_exp->dw_depth - 1 ].value.qw_value;
- p_exp->b_results++;
+ if( ( p_exp->result[ p_exp->b_results ].dw_flag & LIBGOBLIN_DWARF_FLAG_REG )
+ || ( p_exp->result[ p_exp->b_results ].dw_flag & LIBGOBLIN_DWARF_FLAG_REGX )) {
+ p_exp->dw_status = LIBGOBLIN_DWARF_STATUS_EVALUATED;
+ p_exp->b_results++;
+ }
+ else if( 0 < p_exp->dw_depth ) {
+ p_exp->dw_status = LIBGOBLIN_DWARF_STATUS_EVALUATED;
+ p_exp->result[p_exp->b_results].dw_flag
+ = p_exp->t_stack[ p_exp->dw_depth - 1 ].dw_flag;
+ p_exp->result[p_exp->b_results].value.qw_value
+ = p_exp->t_stack[ p_exp->dw_depth - 1 ].value.qw_value;
+ p_exp->b_results++;
+ }
}
goto_DWARF_Expression_Evaluate_post:
int i_result;
Byte b_data[16];
DWord dw_result;
+ QWord *pqw_value;
LibGoblin_DWARF_Expression *p_exp;
i_result = DWARF_Expression_Init();
CU_ASSERT( NULL != p_exp );
// DW_OP_piece: // 0x93
+ b_data[ 0] = DW_OP_reg3;
+ b_data[ 1] = DW_OP_piece;
+ b_data[ 2] = 4;
+ b_data[ 3] = DW_OP_reg10;
+ b_data[ 4] = DW_OP_piece;
+ b_data[ 5] = 2;
+ DWARF_Expression_ClearValue( p_exp );
+ dw_result = DWARF_Expression_Evaluate( p_exp, b_data, 6 );
+ Test_LibGoblin_DWARF_Expression_CheckStruct( p_exp,
+ LIBGOBLIN_DWARF_STATUS_EVALUATED,
+ LIBGOBLIN_DWARF_REQUEST_NONE, LIBGOBLIN_DWARF_REQUEST_NONE );
+ CU_ASSERT( p_exp->dw_depth == 0 );
+ CU_ASSERT( p_exp->b_results == 2 );
+ CU_ASSERT( p_exp->result[0].dw_flag == (LIBGOBLIN_DWARF_FLAG_REG | 0x03) );
+ CU_ASSERT( p_exp->result[0].value.qw_value == 0x03 );
+ CU_ASSERT( p_exp->result[0].dw_bytes == 4 );
+ CU_ASSERT( p_exp->result[1].dw_flag == (LIBGOBLIN_DWARF_FLAG_REG | 0x0a) );
+ CU_ASSERT( p_exp->result[1].value.qw_value == 0x0a );
+ CU_ASSERT( p_exp->result[1].dw_bytes == 2 );
+
+
+ b_data[ 0] = DW_OP_reg0;
+ b_data[ 1] = DW_OP_piece;
+ b_data[ 2] = 4;
+ b_data[ 3] = DW_OP_piece;
+ b_data[ 4] = 4;
+ b_data[ 5] = DW_OP_fbreg;
+ b_data[ 6] = 0x74; // -12
+ b_data[ 7] = DW_OP_piece;
+ b_data[ 8] = 4;
+ DWARF_Expression_ClearValue( p_exp );
+ p_exp->dw_setdata |= LIBGOBLIN_DWARF_REQUEST_FRAME_BASE;
+ p_exp->qw_reqdata[ LIBGOBLIN_DWARF_DATAID_FRAME_BASE ] = 0x1234;
+ dw_result = DWARF_Expression_Evaluate( p_exp, b_data, 9 );
+ Test_LibGoblin_DWARF_Expression_CheckStruct( p_exp,
+ LIBGOBLIN_DWARF_STATUS_EVALUATED,
+ LIBGOBLIN_DWARF_REQUEST_NONE, LIBGOBLIN_DWARF_REQUEST_NONE );
+ CU_ASSERT( p_exp->dw_depth == 1 );
+ CU_ASSERT( p_exp->b_results == 3 );
+ CU_ASSERT( p_exp->result[0].dw_flag == (LIBGOBLIN_DWARF_FLAG_REG | 0x00) );
+ CU_ASSERT( p_exp->result[0].value.qw_value == 0x00 );
+ CU_ASSERT( p_exp->result[0].dw_bytes == 4 );
+ CU_ASSERT( p_exp->result[1].dw_flag == LIBGOBLIN_DWARF_FLAG_NONE );
+ CU_ASSERT( p_exp->result[1].dw_bytes == 4 );
+ CU_ASSERT( p_exp->result[2].dw_flag == LIBGOBLIN_DWARF_FLAG_LOCATION );
+ CU_ASSERT( p_exp->result[2].value.qw_value == 0x1234 - 12 );
+ CU_ASSERT( p_exp->result[2].dw_bytes == 4 );
+
// DW_OP_bit_piece: // 0x9d
+ b_data[ 0] = DW_OP_reg0;
+ b_data[ 1] = DW_OP_bit_piece;
+ b_data[ 2] = 4;
+ b_data[ 3] = 0; // bit 0 - 3
+ b_data[ 4] = DW_OP_bit_piece;
+ b_data[ 5] = 2;
+ b_data[ 6] = 4; // bit 4 - 5
+ b_data[ 7] = DW_OP_fbreg;
+ b_data[ 8] = 0x74; // -12
+ b_data[ 9] = DW_OP_bit_piece;
+ b_data[10] = 10;
+ b_data[11] = 2; // bit 6 - 16
+ DWARF_Expression_ClearValue( p_exp );
+ p_exp->dw_setdata |= LIBGOBLIN_DWARF_REQUEST_FRAME_BASE;
+ p_exp->qw_reqdata[ LIBGOBLIN_DWARF_DATAID_FRAME_BASE ] = 0x1234;
+ dw_result = DWARF_Expression_Evaluate( p_exp, b_data, 12 );
+ Test_LibGoblin_DWARF_Expression_CheckStruct( p_exp,
+ LIBGOBLIN_DWARF_STATUS_EVALUATED,
+ LIBGOBLIN_DWARF_REQUEST_NONE, LIBGOBLIN_DWARF_REQUEST_NONE );
+ CU_ASSERT( p_exp->dw_depth == 1 );
+ CU_ASSERT( p_exp->b_results == 3 );
+ CU_ASSERT( p_exp->result[0].dw_flag == (LIBGOBLIN_DWARF_FLAG_REG | 0x00) );
+ CU_ASSERT( p_exp->result[0].value.qw_value == 0x00 );
+ CU_ASSERT( p_exp->result[0].dw_bit_offset == 0 );
+ CU_ASSERT( p_exp->result[0].dw_bit_size == 4 );
+ CU_ASSERT( p_exp->result[0].dw_bytes == 0 );
+ CU_ASSERT( p_exp->result[1].dw_flag == LIBGOBLIN_DWARF_FLAG_NONE );
+ CU_ASSERT( p_exp->result[1].dw_bit_offset == 4 );
+ CU_ASSERT( p_exp->result[1].dw_bit_size == 2 );
+ CU_ASSERT( p_exp->result[1].dw_bytes == 0 );
+ CU_ASSERT( p_exp->result[2].dw_flag == LIBGOBLIN_DWARF_FLAG_LOCATION );
+ CU_ASSERT( p_exp->result[2].value.qw_value == 0x1234 - 12 );
+ CU_ASSERT( p_exp->result[2].dw_bit_offset == 6 );
+ CU_ASSERT( p_exp->result[2].dw_bit_size == 10 );
+ CU_ASSERT( p_exp->result[2].dw_bytes == 0 );
+
// DW_OP_implicit_value: // 0x9e
+ b_data[0] = DW_OP_implicit_value;
+ b_data[1] = 32;
+ pqw_value = (QWord *)&(b_data[2]);
+ *pqw_value = 0x1234567890abcdef;
+ DWARF_Expression_ClearValue( p_exp );
+ dw_result = DWARF_Expression_Evaluate( p_exp, b_data, 10 );
+ Test_LibGoblin_DWARF_Expression_CheckStruct( p_exp,
+ LIBGOBLIN_DWARF_STATUS_EVALUATED,
+ LIBGOBLIN_DWARF_REQUEST_NONE, LIBGOBLIN_DWARF_REQUEST_NONE );
+ CU_ASSERT( p_exp->dw_depth == 0 );
+ CU_ASSERT( p_exp->b_results == 1 );
+ CU_ASSERT( p_exp->result[0].value.qw_value == 0x1234567890abcdef );
+ CU_ASSERT( p_exp->result[0].dw_flag == LIBGOBLIN_DWARF_FLAG_LOCATION );
+ CU_ASSERT( p_exp->result[0].dw_bytes == 32 );
+
// DW_OP_stack_value: // 0x9f
+ b_data[ 0] = DW_OP_lit7;
+ b_data[ 1] = DW_OP_lit23;
+ b_data[ 2] = DW_OP_plus;
+ b_data[ 3] = DW_OP_stack_value;
+ DWARF_Expression_ClearValue( p_exp );
+ dw_result = DWARF_Expression_Evaluate( p_exp, b_data, 4 );
+ Test_LibGoblin_DWARF_Expression_CheckStruct( p_exp,
+ LIBGOBLIN_DWARF_STATUS_EVALUATED,
+ LIBGOBLIN_DWARF_REQUEST_NONE, LIBGOBLIN_DWARF_REQUEST_NONE );
+ CU_ASSERT( p_exp->dw_depth == 1 );
+ CU_ASSERT( p_exp->b_results == 1 );
+ CU_ASSERT( p_exp->result[0].dw_flag == LIBGOBLIN_DWARF_FLAG_IMMEDIATE );
+ CU_ASSERT( p_exp->result[0].value.qw_value == 30 );
+
// DW_OP_nop: // 0x96
// DW_OP_GNU_push_tls_address: // 0xe0