assume this begging segment of code
.486
.model Flat
ExitProcess PROTO NEAR32 stdcall, dwExitCode:DWORD
Include io.h ;include macros input/output - ASCII to binary conversion
.stack 100h
.data
shortOperand1 WORD ? ;2 byte operand
shortOperand2 WORD ? ;2 byte operand
doubleResult DWORD ? ;4 byte result
.code
ValidateDigitStr proc Near32
push ebp
mov ebp, esp
push ebx ;preserve ebx register
push ecx ;preserve ecx register
mov ebx, [ebp+8]
mov ax, [ebx]
ret
ValidateDigitStr endp
_start:
mainProcess:
;get first operand
output prompt1 ;display first prompt to user
input strInput, 8 ;store user input in a string
~~~~~~~~
everytime i try to run the program it runs through the proc before it is called lower in the program. Sure enough as I walk through win debugger, it walks right through the procedure BEFORE it is called rather than skipping to the _start segment of code....I have another piece of code where this procedure definition works and it skips over it until the procedure is called but this code wont work!!!
any ideas???
This code doesnt do anything yet so that is unimportant, I just want to know why it is running through bits of the procedure call without it even being called
Hi theZeroFlag:
where is
end start
Regards herge
it is at the end of my code
i just posting a few segments of the starting block
this is the end
Invoke ExitProcess,0
public _start
End
It is possible to have a conditional jump within a procedure, right? Becuase everytime I add one it wants to jump directly into my procedure block....
i am thoroughly confused.
Your code should look something like this:
.code
ValidateDigitStr proc
...
ValidateDigitStr endp
_start:
...
call ValidateDigitStr
...
invoke ExitProcess,0
end _start ;declare the program entry point
Get rid of the line,
.stack 100h
In a 32 bit PE file the stack is set as a linker option.
Some notes:
Quote from: theZeroFlag on October 19, 2008, 08:01:47 PM
assume this begging segment of code
; Just a pedantic note, there is no such thing as a "segment" of any sort in 32-bit code. When the linker fixes up all the code into the final PE executable, it does create a "code" or "text" section for the executable bytes, and a "data" section for the initialized data (and other sections for certain types of data) but all this is bundled inside that executable. Search for "Portable Executable Format" for more details.
.486
.model Flat
ExitProcess PROTO NEAR32 stdcall, dwExitCode:DWORD
; this all can be replaced with INCLUDE MASM32RT.INC (makes life easier)
Include io.h ;include macros input/output - ASCII to binary conversion
; is this something your instructor has provided? normally assembler includes end in ".inc". ".h" files are usually C/C++.
.stack 100h ; unneccesary in general win32 programming
.data
shortOperand1 WORD ? ;2 byte operand
shortOperand2 WORD ? ;2 byte operand
doubleResult DWORD ? ;4 byte result
; Just a note here, you have declare this as a ".DATA" section, which means it is initialized data (data stored within the executable for use at run-time), and then set the members values equal to "?", which is an uninitialized state. Either set their values to "0", or (better yet) declare the section as ".DATA?", which is for un-initialized data. Uninitialized data is not stored in the final executable (their members are created at run-time.)
.code
ValidateDigitStr proc Near32 ; usually not necessary to declare procs as "near" or "far"
push ebp
mov ebp, esp
push ebx ;preserve ebx register
push ecx ;preserve ecx register
mov ebx, [ebp+8]
mov ax, [ebx]
ret ; 3 pushes without balancing the stack - could cause a stack overflow
ValidateDigitStr endp
_start: ; why the leading underscore?
mainProcess: ; just a note, mainProcess = _start (it defines the same location, why not just use "_start" ?)
;get first operand
output prompt1 ;display first prompt to user
input strInput, 8 ;store user input in a string
; these must be macros. they do not appear to be part of the MASM32 package.
~~~~~~~~
This code doesnt do anything yet so that is unimportant, I just want to know why it is running through bits of the procedure call without it even being called
Unless you have specified in the linker to use "_start" as the entrypoint (or you are using GoASM?) I believe the entrypoint is called "start" and this could cause problems. What are the assemble and link warnings you receive?
The ValidateDigitStr function is executed first because it is immediately after the _start: entrypoint. Unlike a compiler, which would "rearrange" things and prevent this behavior, MASM does not do this. This is by design. Declaring something as a procedure does not mean that it will only be executed when called or invoked -- in fact, the procedure name (ValidateDigitStr) is the same thing ultimately as _start: -- it is a label to an offset, where code resides. So the short answer would be, "jump around" your procedure. But better yet, would be to write main calls or invokes right after "_start:", then exit process. AFTER that, place the procedures. This way, code execution will only branch to the procedures when they are called. i.e.:
; start of myapp
include \masm32\include\masm32rt.inc
myroutine1 PROTO
myroutine2 PROTO
.data?
myvar DD ? ; just 4 bytes we can use for later
.code
start:
invoke myroutine1 ; do something
mov DWORD PTR [myvar],123h ; put a value in our DWORD
invoke myroutine2 ; do something else
invoke ExitProcess,0 ; exit gracefully
myroutine1 PROC
; do stuff here...
ret ; note is is important to RET -- if not, execution will continue into the next procedure!
myroutine1 ENDP
myroutine2 PROC
; do other stuff here...
ret
myroutine2 ENDP
end start
Take a peek at \masm32\help\asmintro.chm and masm32.chm -- they both provide key information needed to write successful code in MASM32. Have fun. :U
Thanks for the help. I understand everything you have given pointed out.
_start is used so the windbg.exe program I use to debug will find the correct entry point
io.h is a macro provided by Detmer(the author of a book I am learning from), I wondered why it was a .h file considering I normally program in C++
anyway, thanks again.