Assembly level debugging problem

In summary: lea (%eax,%eax,4),%eax c: 03 44 81 04 add 0x4(%ecx,%eax,4),%eax 10: 8b 91 b8 00 00 00 mov 0xb8(%ecx),%edx 16: 03 11 add (%ecx),%edx
  • #1
Fronzbot
62
0

Homework Statement


(This is x86 Assembly Language.)
You are charged with maintaining a large C program, and you come across the following code:

Code:
typedef struct{
     int left;
     a_struct a[CNT];
     int right;
}  b_struct;

void test(int i, b_struct *bp)
{
     int n = bp->left + bp->right;
     a_struct *ap = &bp->a[i];
     ap->x[ap->idx] = n;
}

Disassembled code:
Code:
00000000 <test>:
0: 55                            push %ebp
1: 89 e5                         mov  %esp,%ebp
3: 8b 45 08                      mov  0x8(%ebp),%eax
6: 8b 4d 0c                      mov  0xc(%ebp),%ecx
9: 8d 04 80                      lea  (%eax,%eax,4),%eax
c: 03 44 81 04                   add  0x4(%ecx,%eax,4),%eax
10: 8b 91 b8 00 00 00            mov  0xb8(%ecx),%edx
16: 03 11                        add  (%ecx),%edx
18: 89 54 81 08                  mov  %edx,0x8(%ecx,%eax,4)
1c: 5d                           pop  %ebp
1d: c3                           ret

The declarations of the compile-time constant CNT and teh structure a_struct are in a file for which you do not have the necessary access privilege. Fortunately, you have a copy of the '.o' version of code, which you are able to disassemble with the objdump program, yielding the disassembly shown. Using your reverse engineering skills, deduce the following:

A. The value of CNT
B. A complete declaration of structure a_struct. Assume that the only fields in this structure are idx and x.

Homework Equations


The Attempt at a Solution


Well I said that eax should be 8 above the value in ebp and ecx should be 12 above ebp. I said ebp was 0 so then in the "lea" command I said that eax was placed into address 40 (4 times eax, plus eax). After that I said eax was changed to 44 (the add command). ecx was added to 0xb8 and placed into edx and that value is 196. edx (196) was added to ecx (12) and called edx and that value is 208. That value is then loaded into address 52, therefore, I believe, CNT is equal to 52?

Assembly language really confuses me as my prof has been speeding through it at an incredibly fast pace. Any help, as in trying to guide me through it and, especially, pointing out my surely grievous errors would be absolutely wonderful.
 
Physics news on Phys.org
  • #2
Fronzbot said:

Homework Statement


(This is x86 Assembly Language.)
You are charged with maintaining a large C program, and you come across the following code:

Code:
typedef struct{
     int left;
     a_struct a[CNT];
     int right;
}  b_struct;

void test(int i, b_struct *bp)
{
     int n = bp->left + bp->right;
     a_struct *ap = &bp->a[i];
     ap->x[ap->idx] = n;
}

Disassembled code:
Code:
00000000 <test>:
0: 55                            push %ebp
1: 89 e5                         mov  %esp,%ebp
3: 8b 45 08                      mov  0x8(%ebp),%eax
6: 8b 4d 0c                      mov  0xc(%ebp),%ecx
9: 8d 04 80                      lea  (%eax,%eax,4),%eax
c: 03 44 81 04                   add  0x4(%ecx,%eax,4),%eax
10: 8b 91 b8 00 00 00            mov  0xb8(%ecx),%edx
16: 03 11                        add  (%ecx),%edx
18: 89 54 81 08                  mov  %edx,0x8(%ecx,%eax,4)
1c: 5d                           pop  %ebp
1d: c3                           ret

The declarations of the compile-time constant CNT and teh structure a_struct are in a file for which you do not have the necessary access privilege. Fortunately, you have a copy of the '.o' version of code, which you are able to disassemble with the objdump program, yielding the disassembly shown. Using your reverse engineering skills, deduce the following:

A. The value of CNT
B. A complete declaration of structure a_struct. Assume that the only fields in this structure are idx and x.

Homework Equations





The Attempt at a Solution


Well I said that eax should be 8 above the value in ebp and ecx should be 12 above ebp.
I'm a little rusty at this, since the x86 assembly work I did was about 18 years ago, and some of the instructions look a little different.

The instructions push %ebp, mov %esp,%ebp at the beginning and the pop %ebp instruction near the end are the prolog and epilog, respectively, that the compiler generates to keep track of the stack frame for the test function. The first of these three instructions saves the current stack-frame pointer (base pointer), and then copies the base pointer to the stack pointer. Just before the ret instruction, pop %ebp pops the value off the stack into the base pointer, getting it back to what it was before the function started.

The next two instructions, mov 0x8(%ebp),%eax and mov 0xc(%ebp),%ecx, are copying the parameters of test in right-to-left order. eax holds the address specified in bp (the struct pointer), and it is copied to the location pointed to by ebp + 8. ecx holds the value for i, and it is copied to ebp + 12.

I doubt that ebp is 0.
Fronzbot said:
I said ebp was 0 so then in the "lea" command I said that eax was placed into address 40 (4 times eax, plus eax). After that I said eax was changed to 44 (the add command). ecx was added to 0xb8 and placed into edx and that value is 196. edx (196) was added to ecx (12) and called edx and that value is 208. That value is then loaded into address 52, therefore, I believe, CNT is equal to 52?

Assembly language really confuses me as my prof has been speeding through it at an incredibly fast pace. Any help, as in trying to guide me through it and, especially, pointing out my surely grievous errors would be absolutely wonderful.

I need to stop and eat dinner now, but I'll think about this some more. If I were you and I had access to a C compiler I would actually compile this code and look at it in the debugger, preferably one that disassembles the source code. Then I could see the values that are in the various registers and how the stack frame looks and so on.
 
  • #3
How would I go about finding the value of ebp though (without using, say, info registers in gdb)? I guess that's where I'm stuck. I can figure out what the body of the function is doing, it just takes a bit of thought, but the beginning values are what confuses me.

With regard to this problem, would I be correct in assuming that CNT should equal the size of an array?
 
  • #4
Just assume some value for ebp. What I meant was that it was very unlikely to be 0.

CNT is not the size of the array, but rather the number of elements are in it. Here I'm using size to mean the size in bytes.

There are a couple of lines of code that bother me
Code:
mov  0xb8(%ecx), %edx
add  (%ecx), %edx
In the first line, the value of edx is copied to the location pointed to by ecx + 0xb8. I think that's what that means. The assembly code here seems to by AT&T style rather than Intel style, which I'm more familiar with. What bothers me is what value is being copied? This line of code is the first one that has edx as an operand.

Same problem with the following line of code, which seems to be adding edx to the location pointed to by ecx.

I retract my earlier remarks about which parameters are which. Apparently the calling code is passing the arguments in registers, not on the stack. My guess now is that parameter i is passed in the eax register, and parameter bp is passed in the ecx register.

Hope that helps.
 
  • #5
Ok, you can just assume a value for epb. That's what I thought, but I never read it anywhere so I wasn't sure.

Mark44 said:
In the first line, the value of edx is copied to the location pointed to by ecx + 0xb8. I think that's what that means. The assembly code here seems to by AT&T style rather than Intel style, which I'm more familiar with. What bothers me is what value is being copied? This line of code is the first one that has edx as an operand.

Well I know the way mov statements work is that it is structured Soruce,Destination so that means the value of 0xb8 + the value stored in the register at %ecx is stored into the register at %edx. At least I think that's what it's saying. I know for sure it goes Source,Destination though.

Thanks for all the help thus far, I'm going to run through it again after dinner and figure it out.
 
  • #6
OK, I think I'm finally up to speed here. I didn't realize that AT&T syntax was completely backwards from Intel syntax. For example, in Intel syntax, it's mov dest, src, but in AT&T syntax, it's mov src, dest. That really threw me. I found a link to AT&T assembly syntax here.

I've added comments that indicate what I think is going on.

Code:
push %ebp                  ; push stack frame pointer (ebp) onto stack
mov  %esp,%ebp             ; copy stack pointer to ebp
mov  0x8(%ebp),%eax        ; copy value (i ?) at ebp + 8 to eax
mov  0xc(%ebp),%ecx        ; copy value (bp ?) at ebp + 12 to ecx
lea  (%eax,%eax,4),%eax    ; not sure here - I think this replaces value in eax with 5*eax
add  0x4(%ecx,%eax,4),%eax ; add value at ecx + 4*eax + 4 to eax
mov  0xb8(%ecx),%edx       ; copy value at ecx + 184 to edx 
add  (%ecx),%edx           ; add value at ecx to edx
mov  %edx,0x8(%ecx,%eax,4) ; copy value in ecx to ecx + 4*eax + 8
pop  %ebp                  ; restore stack frame pointer to original value
ret                        ; return to caller
 
  • #7
Ok, I agree with you on what is going on there. So, does that mean the following is correct?

1: Assume value for ebp. I say 0 just to make everything easier.
2: esp = ebp = 0
3: eax = 8
4: ecx = 12
5: address of eax is 40 (4*eax + eax)
6: eax = 56
7: edx = 196
8: edx = 208 (196 + ecx)
9: value of edx move to address 244 (4*eax + ecx)

And so eax = i in the program so CNT should be equal to 56, correct?
 

1. What is assembly level debugging?

Assembly level debugging is the process of finding and fixing errors or bugs in a computer program using assembly language. Assembly language is a low-level programming language that is directly translated into machine code, making it possible to examine the program at a very detailed level.

2. Why is assembly level debugging important?

Assembly level debugging is important because it allows programmers to understand and fix complex problems that cannot be easily identified using higher level languages. It also provides insight into how the computer is executing the program, making it easier to optimize and improve performance.

3. What are the common problems that can be solved using assembly level debugging?

Common problems that can be solved using assembly level debugging include memory errors, such as buffer overflows or segmentation faults, as well as logic errors and issues with program flow. These types of problems can be difficult to identify and fix using higher level languages.

4. What are some tools used for assembly level debugging?

Some commonly used tools for assembly level debugging include debuggers, which allow programmers to step through the code and examine the values of variables and registers at specific points, as well as disassemblers, which convert machine code back into assembly language for easier analysis.

5. How can one become proficient in assembly level debugging?

Becoming proficient in assembly level debugging requires a strong understanding of assembly language, as well as knowledge of computer architecture and how programs are executed at the hardware level. Practice and experience with debugging tools and techniques is also essential in developing proficiency in this skill.

Similar threads

  • Programming and Computer Science
Replies
19
Views
2K
  • Engineering and Comp Sci Homework Help
Replies
2
Views
3K
  • Programming and Computer Science
Replies
4
Views
8K
Back
Top