1

I've been wondering, why all the hassle with variable length arrays (such as int x[n])? Theoretically, it's just another local variable, so it's merely a matter of subtracting the appropriate value from ESP. This question - and excellent answer - at StackOverflow: https://stackoverflow.com/questions/1887097/variable-length-arrays-in-c has cleared things up a bit.

However, I was curious to see what code would be generated by compilers. I've tried MSVC 2013 and MinGW 4.8.1, with the latter successfully compiling the code and the former refusing to cooperate. The C++ (well actually C, but compiled with g++) code is as follows:

#include<stdio.h>

int main()
{
    int size;
    scanf("%d", &size);

    int array[size];
    array[0] = 0xBEEF;

    printf("Done with the arrays!\n");
    return 0;
}



This will be compiled to the following assembly code (diassembled with Olly 1.10, but also tried IDA and got the same results):

(some main( ) initialization)
LEA EAX,[LOCAL.5]                                          
MOV DWORD PTR SS:[ESP+4],EAX                               
MOV DWORD PTR SS:[ESP],tesst.00403064        ;"%d"              
CALL <JMP.&msvcrt.scanf>                                   
MOV EAX,[LOCAL.5]
SUB EAX,1
MOV [LOCAL.3],EAX                                         
ADD EAX,1
SHL EAX,2
LEA EDX,DWORD PTR DS:[EAX+3]
MOV EAX,10
SUB EAX,1
ADD EAX,EDX                                                
MOV ECX,10
MOV EDX,0
DIV ECX
IMUL EAX,EAX,10                                            
CALL tesst.00401C60
SUB ESP,EAX                                                
LEA EAX,DWORD PTR SS:[ESP+8]                               
ADD EAX,3                                                  
SHR EAX,2                                                  
SHL EAX,2                                                  
MOV [LOCAL.4],EAX                                          
MOV EAX,[LOCAL.4]                                          
MOV DWORD PTR DS:[EAX],0BEEF                               
MOV DWORD PTR SS:[ESP],tesst.00403067                      
CALL <JMP.&msvcrt.puts>     
MOV EAX,0
MOV ESP,EBX
LEA ESP,[LOCAL.2]
POP ECX                                                    
POP EBX                                                   
POP EBP                                                  
LEA ESP,DWORD PTR DS:[ECX-4]
RETN


To me, this code looks redundant and absurd, at times, to be honest. Why do we LEA EAX+3 to EDX just to add it a couple lines later, without altering EDX in any way? Why MOV EAX to ESP-0C (LOCAL.3) if it's not used at all later? And, of course, what's with the MOV ESP, EBX and then LEA ESP,EBP-8 immediately after?

And most of all, why all the hassle? Wouldn't it just have been enough to do something like this:

LEA EAX,[LOCAL.5]                                          
MOV DWORD PTR SS:[ESP+4],EAX                               
MOV DWORD PTR SS:[ESP],tesst.00403064     ; "%d"
CALL <JMP.&msvcrt.scanf>   
MOV EAX,[LOCAL.5]
SHL EAX,2       ;multiply times 4 - sizeof int
SUB ESP,EAX    ;memory is allocated, all done
  • 3
    This is a compiler optimization question, another version of which was already answered at reverseengineering.stackexchange.com/a/4535/1562 – Jason Geffner Sep 16 '14 at 21:31
  • @JasonGeffner Ok, thanks for pointing me in the right direction. I do however wonder: I'd imagine that compiler optimizations sacrifice something for speed, maybe memory usage, maybe something else. So why, without explicitly telling the compiler to do otherwise, will I get useless garbage like that? Surely the software's authors didn't deliberately implement such behavior, so what is it that's causing it? – user4520 Sep 17 '14 at 16:32
  • That question would be better asked on stackoverflow.com – Jason Geffner Sep 17 '14 at 17:12
  • 1
    @szczurcio briefly, compiling without optimizations on isn't usually about avoiding trade-offs. When you compile without optimizations on the compiler is performing its simple, direct conversion between source and machine code that is obviously correct but may be verbose as you have found. – BitShifter Sep 17 '14 at 18:50
  • @BitShifter, JasonGeffner Alright guys, thanks for your help. I'm certainly one step further down the road now. – user4520 Sep 18 '14 at 18:04

Browse other questions tagged or ask your own question.