flat assembler
Message board for the users of flat assembler.
Index
> Main > Fasm Experience |
Author |
|
Borsuc 27 Nov 2009, 18:41
msg db "message" declares a FASM variable called 'msg' which is the address where it is located (it is not stored in the exe), and puts the message "message" there.
You access it by writing 'msg'. Code: mov eax, msg2 you can, of course, use 'msg2+5' if you want 5 characters forward, etc... if this isn't what you asked for, sorry I don't get what you're saying. |
|||
27 Nov 2009, 18:41 |
|
DOS386 28 Nov 2009, 08:20
> I'm learning Fasm but can't find the tutorials i need on internet ?
Here ... there are harly other places. > If it makes it easier to understand what i want to do NO. Post offending code and tell what happens vs what you excepted. Also, tell for what OS you develop and pick appropriate subforum. |
|||
28 Nov 2009, 08:20 |
|
Azu 28 Nov 2009, 10:30
DOS386 wrote: Post offending code and tell what happens vs what you excepted. Also, tell for what OS you develop and pick appropriate subforum. Here's code for GLaDOS. It is expected to give me cake, but instead it is offending me. Please help! Code: if cake ~ eq lie display "Here have some cake" mov byte[mouth],cake else display "HAHA NOOB YOU FELL FOR IT! SUCKER!!!" end if |
|||
28 Nov 2009, 10:30 |
|
DarrenBall 28 Nov 2009, 11:28
Thanks Borsuc, Dos386 and Azu,
But wot i was trying to ocumplish was to understand how windows assigns memory space per app ( My Program ). i understand that msg2, msg1 & msg are pointers to the variable address spaces - but when window loads my app, it will give it such things as - memory space ( data, code, stack ..) It's memory space if it was an old 16bit asm app i could calculate using sgment and offset to gain access to the memory locations (8bit chunks) but Windows gives it a location and we can access using the offset into that location ? This is the problem i'm trying to resolve - How to get the segment start of my APP. Then i'm guessing at the beginning of my APP's address space i could fetch info like :- Handle - given to my app by windows name - name of my .exe Size - of my app in the memory space - i'm assuming windows calculates this so the Processor doesn't run into any other app in neighbouring address spaces ? Data - Start of my data segment - where my variables and any constants are Code - Start of my Code segment - This could be handy for self modifying code at run time. Stack - Start of my Stack segment - I know that each app at run time initialises it's own stack - which windows destroys as part of the app's closing routine's. Thank you all for your comments and i hope you can see that i'm trying to understand how the app is running when i implement it ? |
|||
28 Nov 2009, 11:28 |
|
Borsuc 29 Nov 2009, 02:44
Windows loads sections from the PE executable into specific addresses. They are assigned automatically (although nothing stops you from modifying them, but you'll have to use manual PE I think).
Anyway, the code usually is loaded at 0x00400000 base address -- i.e 0x00400001 will be byte 2 of the code. As you can see, the addresses are pretty much static per application. Every application has its own address space, so it is perfectly ok for two apps to both have different code at 0x00400000 -- this is called virtual memory and let's just keep it at that so you don't get confused ok? When FASM creates a fasm "variable", this variable exists only within fasm, not in the compiled executable -- it's just information for compiling. For example, if you want to find the address of the second instruction in the following code: Code: xor eax, eax xor ecx, ecx Code: xor eax, eax second_instruction: ; this is a label xor ecx, ecx Code: mov edx, second_instruction+1 ; fasm will replace second_instruction with the address and add 1, then make the instruction In this example it would be "mov edx, 0x00400002+1" or "mov edx, 0x00400003" stored in the exe after compilation (xor eax, eax takes 2 bytes), but really you don't want to hardcode them so you use variables/labels yeah you can pretty much interchange variables and labels as you wish. Hope that clarifies some stuff about FASM and memory outline. Data is the same as code, after all, code is "data" itself. Also, that's what "x db 5" does too, it makes a label at that address, it's the same as: Code: x: db 5 Code: x: db 5 _________________ Previously known as The_Grey_Beast |
|||
29 Nov 2009, 02:44 |
|
sinsi 29 Nov 2009, 03:16
Borsuc, the MZ header is loaded at 00400000, the first code is usually at 00401000 (4K aligned sections in memory).
|
|||
29 Nov 2009, 03:16 |
|
DarrenBall 29 Nov 2009, 13:46
Thanks Borsuc, sinsi.
I'm slowly understanding - i get it now that labels are assembler persific only and used for ease of coding And i think i'm right by what you chaps are saying - that - msg1 db "This msg Box" msg1 only excists in my asm file and not exec - and the string "This msg Box" when running is at location 0x00400000 + ( it's offset ) So below is an App that gets from the command line and msg box number of strings entered including app address.. it starts with format PE .. when this is running - what part of this app would start at address space 0x00400000 ? I'm also guessing again that format PE is fasm directive so wouldn't be included in the address space..?? Wot might help me better under stand the difference between assembler and executable - Is there an app i could write that would read the memory location from 0x00400000 to my apps limit and save the details into a file for futher study ? I know memory is set in 8 bit chuncks - but to write a program to display whats in memroy i would need to know how big OR how much memory to read ? if my .exe file is so many kb's then do i read that many in ? I think the best thing to ask is when an .exe is loaded into memory ready for processing - is there a signiture at the very end of that apps adress space that i could use as a marker to so called end of file - but memory - so i could stop reading in from there ? i also know that windows allows each app 4 gig but i don't want to read that many . Thanks people. My main app Code: ;Command line input ;Darren Ball ;28 November 2009 ;main program that displays a msgbox with the number and values of parameters passed ;;;;;;;;;;;;;;;;;; format PE GUI include 'c:\fasm\include\win32a.inc' section '.code' readable writeable start: pusha ;save all registers invoke GetCommandLine ; Get command line parameters call StrCount ;Count the number of strings on the command line 1 = no values passed push eax ;save the string of command line parameters - maybe use more oneday ? xor eax, eax ;clear the value inside eax register mov al, [cnt] ; load eax with number of strings counted, cnt is global and is loaded from call strCount of strManip.inc call bcd2dec ;convert string binary coded decimal to decimal ;for this app would have been easier just to add [cnt], 48 - ;but i wanted to make a conversion proc ; The decimal value is now in 'decimal' cmp [cnt], 1 ;compare cnt so we know which msgbox to display je no_param ;if '1' then only app address so no parameters were passed pop eax ;return the command line parameters just in case i wanted to use them invoke MessageBox, 0, eax, decimal, MB_OK ;decimal is the structure created in bcd2dec.dec jmp exit no_param: invoke MessageBox, 0, Title, msg, MB_OK exit: ;return to all registers their initial values popa invoke ExitProcess ;close this app ;section '.data' readable writeable ;Data section section '.data' readable writeable causes errors ? buffer db 30 dup (' ') msg db 'No Command Line Parameters ? ', 0dh, 0ah, 0 Title db "Parameters' Passed", 0 cnt db 0,0 ; Extra null (0) to stop garbage being displayed ;Imported files data import library user32,'user32.dll', kernel32,'kernel32.dll' include 'c:\fasm\include\api\user32.inc' include 'c:\fasm\include\api\kernel32.inc' include '%include%\bcd2dec.dec' include "%include%\StrManip.inc" end data My inc file that counts how many units (Strings passed) Code: ;String Manipulation ;Darren Ball ;28 november 2009 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; eax must have a value passed into it ;; ;; and a glabel variable named cnt must be setup in main prog;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; proc StrCount push ebx ;save value of ebx ...just incase mov ebx, eax mov [cnt], 1 ;GetCommandLine will always return if nothing else address of app loop1: cmp byte [ebx], '"' ;test for quoted strings as these will be counted as 1 string je qloop cmp byte [ebx], ' ' ;each string counted will be seperated by spaces je loop1next cmp byte [ebx], 0 je loop1end inc ebx jmp loop1 loop1next: add [cnt], 1 ;Add instead of inc , because inc moves along address space in mem ? inc ebx jmp loop1 qloop: inc ebx ;Ignore spaces inside of quotation marks cmp byte [ebx], '"' jne qloop inc ebx jmp loop1 loop1end: pop ebx ;return original value of ebx ret endp And finaly converting bcd to decimal - easier just to add [cnt], 48 but wanted to write a converter for future use Code: ;Include file for printing decimal from binary-coded-decimal ;Darren Ball ;28 november 2009 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;CAUTION use EAX to pass bcd value;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; proc bcd2dec jmp bcd2dec_start ;Skip over the data setup struct decout ;design a decimal holding table hunthou db 0 tenthou db 0 thou db 0 hun db 0 ten db 0 unit db 0 null db 0 ;not used - it's needed to stop the display of garbage data ends decimal decout ;Create an instance of the structure decout ;;Test eax values now and loading relevant members of decimal table decout (decimal) bcd2dec_start: ;Decimal up to but not reacing 1 million cmp eax, 0 ;Error if no value passed in eax je bcd2dec_errorValue cmp eax, 1000000 jge bcd2dec_errorMill bcd2dec_loop1: cmp eax, 100000 jl bcd2dec_loop1end add [decimal.hunthou], 1 sub eax, 100000 jmp bcd2dec_loop1 bcd2dec_loop1end: cmp eax, 10000 jl bcd2dec_loop2 add [decimal.tenthou], 1 sub eax, 10000 jmp bcd2dec_loop1 bcd2dec_loop2: cmp eax, 1000 jl bcd2dec_loop2end add [decimal.thou], 1 sub eax, 1000 jmp bcd2dec_loop1 bcd2dec_loop2end: cmp eax, 100 jl bcd2dec_loop3 add [decimal.hun], 1 sub eax, 100 jmp bcd2dec_loop1 bcd2dec_loop3: cmp eax, 10 jl bcd2dec_loop3end add [decimal.ten], 1 sub eax, 10 jmp bcd2dec_loop1 bcd2dec_loop3end: cmp eax, 0 jle bcd2dec_fin add [decimal.unit], 1 sub eax, 1 jmp bcd2dec_loop1 ;; Error messages - returned in eax 1 = no value, 2 = overflow bcd2dec_errorValue: mov eax, 1 jmp bcd2dec_fin bcd2dec_errorMill: mov eax, 2 bcd2dec_fin: add [decimal.hunthou], 48 add [decimal.tenthou], 48 add [decimal.thou], 48 add [decimal.hun], 48 add [decimal.ten], 48 add [decimal.unit], 48 ;; Had to use loads of jmps here as 'if; statements wouldn't change values ???????? ;; if decimal.hunthou = 48 ;; mov [decimal.hunthou], 32 ;; end if ;; no value change ? ;;;;;;;;;;;;;;;;;;;;;;;;;;; bcd2dec_Padd: cmp [decimal.hunthou], 48 je hunthouPadd bcd2dec_Padd1: cmp [decimal.tenthou], 48 je tenthouPadd bcd2dec_Padd2: cmp [decimal.thou], 48 je thouPadd bcd2dec_Padd3: cmp [decimal.hun], 48 je hunPadd bcd2dec_Padd4: cmp [decimal.ten], 48 je tenPadd jmp bcd2dec_ret hunthouPadd: mov [decimal.hunthou], 32 jmp bcd2dec_Padd1 tenthouPadd: mov [decimal.tenthou], 32 jmp bcd2dec_Padd2 thouPadd: mov [decimal.thou], 32 jmp bcd2dec_Padd3 hunPadd: mov [decimal.hun], 32 jmp bcd2dec_Padd4 tenPadd: mov [decimal.ten], 32 ;jmp bcd2dec_fin bcd2dec_ret: ret endp Thanks again for your help chaps. |
|||
29 Nov 2009, 13:46 |
|
Borsuc 29 Nov 2009, 19:32
DarrenBall wrote: Wot might help me better under stand the difference between assembler and executable - Is there an app i could write that would read the memory location from 0x00400000 to my apps limit and save the details into a file for futher study ? It's a great learning tool for this. @sinsi: you're correct, I'm sorry for my mistake. _________________ Previously known as The_Grey_Beast |
|||
29 Nov 2009, 19:32 |
|
< Last Thread | Next Thread > |
Forum Rules:
|
Copyright © 1999-2024, Tomasz Grysztar. Also on GitHub, YouTube.
Website powered by rwasa.