|
Prev: asm grep
Next: High Speed IRQ Timer/Clock in C
From: gtb on 26 Dec 2007 20:18 Greetings, Just getting back to assemby after 10+ years away from it and trying to learn a bit about x86 programming. My last experience was with a Z80 so I am finding a lot of great things like MASM, NASM, HLA, et al. I am currently using VC++ as it was handy and seems to understand MASM. I was using the snippet below to test printing messages from an asm function. How should one print <CRLF>? Seems one should use 0D0Ah but 0Ah works fine thus far. I copied the MessageBox invocation from another example and I have all the same includes and tried to run it under Vc++. But as you can see it is commented as it was reported as an undefined symbol. It would really give me a leg up to see a print example that could print values from registers and memory locations. Lastly (if I haven't worn out my welcome already) if one is developing for the IA-32 platform using an XP pc, what would be your assembler and/or IDE of choice at this time? Thanx, gtb ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ..486 ..model flat, stdcall option casemap :none include \masm32\include\windows.inc include \masm32\include\kernel32.inc include \masm32\include\masm32.inc includelib \masm32\lib\kernel32.lib includelib \masm32\lib\masm32.lib ..data helloString db "Hello World! ", ,0Ah, 0 ..code fn1 proc ;invoke MessageBox, NULL, addr helloString, addr helloString, MB_OK invoke StdOut, addr helloString ret fn1 endp end
From: Herbert Kleebauer on 27 Dec 2007 00:12 gtb wrote: > I copied the MessageBox invocation from another example and I have all > the same includes and tried to run it under Vc++. But as you can see > it is commented as it was reported as an undefined symbol. It would > really give me a leg up to see a print example that could print values > from registers and memory locations. > > Lastly (if I haven't worn out my welcome already) if one is developing > for the IA-32 platform using an XP pc, what would be your assembler > and/or IDE of choice at this time? Don't use the message box for output but start your program in a cmd shell (DOS box) and write to stdout. MASM hides much to much. Here a simple program to dump register, stack and memory content as a DOS and Windows program where you can see every byte in the binary explicitly defined in the assembler source code. As you can see yourself, it's much better to start assembly programming in DOS: you will learn the same, but it's much easier to start with. ; DOS version: OS=0 ; 0: DOS 1: WINDOwS 2: LINUX @=$100 move.l #$12345678,-(sp) ; put someting on stack move.l #$9abcdef0,-(sp) ; so we can display it bsr.l dump_reg ; display register and stack content move.l #dump_reg,r0 ; dump 100 bytes starting at "dump_reg" move.l #100,r1 bsr.l dump_mem bsr.l exit ; terminate ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; dump register and top 8 dwords of stack to stdout ;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; dump_reg: movem.l r0-r7,-(sp) addq.l #4,12.b(r7) ; correct saved sp move.l #_200,r5 move.l #_300,r6 move.l #16,r2 _20: move.b (r5),r0 inc.l r5 tst.b r0,r0 beq.b _10 bsr.l putc br.b _20 _10: movu.bl (r6),r0 inc.l r6 IF OS==0 lea.l (r0,r7),r1 cmp.l #$fffc,r1 bhi.b _30 ENDIF move.l (r0,r7),r0 bsr.l disp_hex_l dbf.l r2,_20 _30: bsr.l disp_lf movem.l (sp)+,r0-r7 rts.l _200: IF OS<2 dc.b 13,10,"r0:",0,0,0,0,"r4:",0,0,0,0,13,10 ELSE dc.b 10,"r0:",0,0,0,0,"r4:",0,0,0,0, 10 ENDIF dc.b "pc:",0,"st:",0,0,0,0,0,0,0 _300: dc.b 28,20,24,16,8,4,0,12,32,36,40,44,48,52,56,60 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; dump next r1 bytes at memory location (r0) to stdout ;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; dump_mem: movem.l r0-r7,-(sp) bsr.l disp_lf subq.l #20,r7 move.l r7,r3 ; 20 byte bufer move.l r0,r5 _10: move.l r5,r0 bsr.l disp_hex_l bsr.l disp_blank move.b #' ',r0 move.l #16,r2 move.l r3,r6 move.l r2,-(sp) move.l r6,-(sp) rep_r2 move.b r0,(r6)+-{s1} IF OS<2 move.l #$0a0d,(r6) ELSE move.l #$0a,(r6) ENDIF move.l (sp)+,r6 move.l (sp)+,r4 _20: dec.l r1 bmi.b _90 move.b (r5),r0 inc.l r5 bsr.l disp_hex_b cmp.b #' ',r0 blo.b _30 cmp.b #$7f,r0 blo.b _40 _30: move.b #' ',r0 _40: move.b r0,(r6) inc.l r6 lea.l -1.b(r4.w),r0 and.b #$03,r0 bne.b _50 bsr.l disp_blank _50: dec.l r4 bne.b _20 move.l r3,r0 bsr.l disp_string br.b _10 _90: move.l r4,r2 add.l r4,r2 add.l r4,r2 addq.l #3,r4 lsr.l #2,r4 add.l r4,r2 _91: bsr.l disp_blank dbf.l r2,_91 move.l r3,r0 bsr.l disp_string _100: addq.l #20,r7 movem.l (sp)+,r0-r7 rts.l disp_hex_b: ; display r0.b as hex string movem.l r0-r7,-(sp) move.l #2,r2 rol.l #24,r0 br.b dh0 disp_hex_l: ; display r0.l as hex string movem.l r0-r7,-(sp) move.l #8,r2 dh0: move.l r0,r1 _20: rol.l #4,r1 move.b r1,r0 andq.l #$0f,r0 add.b #'0',r0 cmp.b #'9',r0 bls.b _10 add.b #'a'-'9'-1,r0 _10: bsr.l putc dbf.l r2,_20 bsr.l disp_blank movem.l (sp)+,r0-r7 rts.l disp_string: ; display null terminated string at (r0) movem.l r0-r7,-(sp) move.l r0,r3 _20: move.b (r3),r0 tst.b r0,r0 beq.b _10 inc.l r3 bsr.l putc br.b _20 _10: movem.l (sp)+,r0-r7 rts.l disp_lf: ; <CR><LF> for DOS/Windows, <LF> for Linux move.l r0,-(sp) IF OS<2 move.b #$0d,r0 bsr.l putc ENDIF move.b #$0a,r0 br.b d_b0 disp_blank: ; display a space move.l r0,-(sp) move.b #' ',r0 d_b0: bsr.l putc move.l (sp)+,r0 rts.l ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; OS specific functions: getc, putc, exit ;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ; write r0.b to stdout putc: movem.l r0-r7,-(sp) move.b r0,_buf move.b #$40,m0 move.w #_buf,r1 move.w #1,r2 move.w #1,r3 trap #$21 movem.l (sp)+,r0-r7 rts.l _buf: dc.b 0 ; read byte from stdin -> r0.l ; -1: EOF getc: movem.l r0-r7,-(sp) move.b #$3f,m0 move.w #_buf,r1 move.w #1,r2 eor.w r3,r3 trap #$21 bcs.b _10 cmp.w r0,r2 bne.b _10 movem.l (sp)+,r0-r7 move.b _buf,r0 rts.l _10: movem.l (sp)+,r0-r7 move.l #-1,r0 rts.l _buf: dc.b 0 ; terminate program ; r0: retorn code exit: move.b #$4c,m0 trap #$21 ; Windows Version: ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; DUMPWIN.mac: dump register, stack and memory content to stdout ;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; UseIdatSection=0 ; 0 if no idat section is used UseUdatSection=0 ; 0 if no udat section is used ;#==================================================================# ;# Start of Headers # ;#==================================================================# ; +--------------------------------------------+ ; | Start of DOS Header | ; +--------------------------------------------+ ; DOS .EXE header dc.b 'MZ' ; Magic number dc.w dosfilesize\512 ; Bytes on last page of file (0->512) dc.w (dosfilesize-1)/512+1 ; Pages in file (Page=512 byte) dc.w 0 ; Relocations (nr of entries) dc.w doshead_end/16 ; Size of header size in paragraphs (16 byte) dc.w 0 ; Minimum extra paragraphs needed dc.w $ffff ; Maximum extra paragraphs needed dc.w 0 ; Initial (relative) SS value (ss=load_adr+nr) dc.w dosstack ; Initial SP value dc.w 0 ; Checksum dc.w dosmain ; Initial IP value dc.w 0 ; Initial (relative) CS value (cs=load_adr+nr) dc.w reloc ; File address of relocation table dc.w 0 ; Overlay number dc.w 0,0,0,0 ; Reserved words dc.w 0 ; OEM identifier (for e_oeminfo) dc.w 0 ; OEM information; e_oemid specific dc.l 0,0,0,0,0 ; Reserved words dc.l WinHeader ; File address of new exe header reloc: doshead_end: @=$0 dosmain:move.w s6,-(sp) move.w (sp)+,s0 move.w #_text,r1 move.b #$09,m0 trap #$21 move.w #$4c01,r0 trap #$21 _text: dc.b 'Nice to meet somebody who is still using DOS,',13,10 dc.b 'but his program requires Win32.',13,10,'$' even 16 dosstack=@+256 ; 256 Byte stack dosfilesize=@+256 ; +--------------------------------------------+ ; | End of DOS Header | ; +--------------------------------------------+ ; +--------------------------------------------+ ; | Start of Windows Header | ; +--------------------------------------------+ ImageBase== $00400000 SectionAlignment== 4096 FileAlignment== 512 WinHeader=@@ @=ImageBase ; see WINNT.H for information dc.b 'PE',0,0 ; magic word ; _IMAGE_FILE_HEADER: dc.w $014c ; Machine ($014c=Intel x86 processor) dc.w NumberOfSections ; NumberOfSections dc.l $36a57950 ; TimeDateStamp (seconds since 31.12.69 16:00) dc.l 0 ; PointerToSymbolTable dc.l 0 ; NumberOfSymbols dc.w SizeOfOptionalHeader ; SizeOfOptionalHeader dc.w $010f ; Charcteristics ; 0x0001 Relocation info stripped from file. ; 0x0002 File is executable (i.e. no unresolved externel references). ; 0x0004 Line nunbers stripped from file. ; 0x0008 Local symbols stripped from file. ; 0x0010 Agressively trim working set ; 0x0080 Bytes of machine word are reversed. ; 0x0100 32 bit word machine. ; 0x0200 Debugging info stripped from file in .DBG file ; 0x0400 If Image is on removable media, copy and run from the swap file. ; 0x0800 If Image is on Net, copy and run from the swap file. ; 0x1000 System File. ; 0x2000 File is a DLL. ; 0x4000 File should only be run on a UP machine ; 0x8000 Bytes of machine word are reversed. @a=@ ; _IMAGE_OPTIONAL_HEADER dc.w $010b ; Magic dc.b 5 ; MajorLinkerVersion dc.b 12 ; MinorLinkerVersion dc.l SizeOfCode ; SizeOfCode dc.l SizeOfInitializedData ; SizeOfInitializedData dc.l SizeOfUninitializedData ; SizeOfUninitializedData dc.l winmain-ImageBase ; AddressOfEntryPoint dc.l BaseOfCode ; BaseOfCode dc.l BaseOfData ; BaseOfData dc.l ImageBase ; ImageBase dc.l SectionAlignment ; SectionAlignment dc.l FileAlignment ; FileAlignment dc.w 4 ; MajorOperatingSystemVersion dc.w 0 ; MinorOperatingSystemVersion dc.w 0 ; MajorImageVersion dc.w 0 ; MinorImageVersion dc.w 4 ; MajorSubsystemVersion dc.w 0 ; MinorSubsystemVersion dc.l 0 ; Win32VersionValue dc.l SizeOfImage ; SizeOfImage dc.l SizeOfHeaders ; SizeOfHeaders dc.l 0 ; CheckSum dc.w 3 ; Subsystem ; 0: Unknown subsystem. ; 1: Image doesn't require a subsystem. ; 2: Image runs in the Windows GUI subsystem. ; 3: Image runs in the Windows character subsystem. ; 5: image runs in the OS/2 character subsystem. ; 7: image run in the Posix character subsystem. ; 8: image run in the 8 subsystem. dc.w $0000 ; DllCharacteristics dc.l $00100000 ; SizeOfStackReserve dc.l $00001000 ; SizeOfStackCommit dc.l $00100000 ; SizeOfHeapReserve dc.l $00001000 ; SizeOfHeapCommit dc.l $00000000 ; LoaderFlags dc.l NumberOfRvaAndSize ; NumberOfRvaAndSize (entries ; in the data dir) ; .............................................. ; : Start of Image Data Directory : ; .............................................. ; virtual address, size @b=@ dc.l 0,0 ; Export Directory dc.l imp_start,imp_size ; Import Directory dc.l 0,0 ; Resource Directory dc.l 0,0 ; Exception Directory dc.l 0,0 ; Security Directory dc.l 0,0 ; Base Relocation Table dc.l 0,0 ; Debug Directory dc.l 0,0 ; Description String dc.l 0,0 ; Machine Value (MIPS GP) dc.l 0,0 ; TLS Directory dc.l 0,0 ; Load Configuration Directory dc.l 0,0 ; Bound Import Directory in headers dc.l iat_start,iat_size ; Import Address Table dc.l 0,0 ; 14 dc.l 0,0 ; 15 dc.l 0,0 ; 16 NumberOfRvaAndSize = (@-@b)/8 SizeOfOptionalHeader = @-@a ; .............................................. ; : End of Image Data Directory : ; .............................................. ; .............................................. ; : Start of Image Sections Header : ; .............................................. @a=@ dc.b '.text',0,0,0 ; name dc.l VSizeOf_text ; virtual size dc.l VBaseOf_text ; virtual address dc.l FSizeOf_text ; size of raw data dc.l FBaseOf_text ; pointer to raw data dc.l 0 ; pointer to relocatins dc.l 0 ; pointer to line numbers dc.w 0 ; number of relocations dc.w 0 ; number of line numbers dc.l $e0000020 ; characteristics IF UseIdatSection dc.b '.idat',0,0,0 ; name dc.l VSizeOf_idat ; virtual size dc.l VBaseOf_idat ; virtual address dc.l FSizeOf_idat ; size of raw data dc.l FBaseOf_idat ; pointer to raw data dc.l 0 ; pointer to relocatins dc.l 0 ; pointer to line numbers dc.w 0 ; number of relocations dc.w 0 ; number of line numbers dc.l $e0000040 ; characteristics ENDIF IF UseUdatSection dc.b '.udat',0,0,0 ; name dc.l VSizeOf_udat ; virtual size dc.l VBaseOf_udat ; virtual address dc.l FSizeOf_udat ; size of raw data dc.l FBaseOf_udat ; pointer to raw data dc.l 0 ; pointer to relocatins dc.l 0 ; pointer to line numbers dc.w 0 ; number of relocations dc.w 0 ; number of line numbers dc.l $e0000080 ; characteristics ENDIF NumberOfSections=(@-@a)/40 ; .............................................. ; : End of Image Sections Header : ; .............................................. ; characteristics ; 0x00000020 // Section contains code. ; 0x00000040 // Section contains initialized data. ; 0x00000080 // Section contains uninitialized data. ; 0x00000200 // Section contains comments or some other type of information. ; 0x00000800 // Section contents will not become part of image. ; 0x00001000 // Section contents comdat. ; 0x01000000 // Section contains extended relocations. ; 0x02000000 // Section can be discarded. ; 0x04000000 // Section is not cachable. ; 0x08000000 // Section is not pageable. ; 0x10000000 // Section is shareable. ; 0x20000000 // Section is executable. ; 0x40000000 // Section is readable. ; 0x80000000 // Section is writeable. ; +--------------------------------------------+ ; | End of Windows Header | ; +--------------------------------------------+ evencom FileAlignment SizeOfHeaders==@@ ;#==================================================================# ;# End of Headers # ;#==================================================================# ;#==================================================================# ;# Start of Sections # ;#==================================================================# ; +--------------------------------------------+ ; | Start of .text Section | ; +--------------------------------------------+ FBaseOf_text==@@ VBaseOf_text==(@-ImageBase+SectionAlignment-1)/SectionAlignment*SectionAlignment BaseOfCode==VBaseOf_text @=ImageBase+VBaseOf_text ; .............................................. ; : Start of Thunk Table : ; .............................................. iat_start=@-ImageBase KERNEL32_thunk: ExitProcess:: dc.l KERNEL32_ExitProcess -ImageBase GetStdHandle:: dc.l KERNEL32_GetStdHandle -ImageBase ReadFile:: dc.l KERNEL32_ReadFile -ImageBase WriteFile:: dc.l KERNEL32_WriteFile -ImageBase dc.l 0 iat_size=@-ImageBase-iat_start ; .............................................. ; : End of Thunk Table : ; .............................................. ; .............................................. ; : Start of Import Directory : ; .............................................. imp_start==@-ImageBase imp: dc.l KERNEL32_import -ImageBase dc.l 0 dc.l 0 dc.l KERNEL32_name -ImageBase dc.l KERNEL32_thunk -ImageBase dc.l 0 dc.l 0 dc.l 0 dc.l 0 dc.l 0 imp_size==@-imp ; .............................................. ; : End of Import Directory : ; .............................................. KERNEL32_name: dc.b 'KERNEL32.dll',0 even KERNEL32_import: dc.l KERNEL32_ExitProcess -ImageBase dc.l KERNEL32_GetStdHandle -ImageBase dc.l KERNEL32_ReadFile -ImageBase dc.l KERNEL32_WriteFile -ImageBase dc.l 0 even KERNEL32_ExitProcess: dc.w 0 dc.b 'ExitProcess',0 even KERNEL32_GetStdHandle: dc.w 0 dc.b 'GetStdHandle',0 even KERNEL32_ReadFile: dc.w 0 dc.b 'ReadFile',0 even KERNEL32_WriteFile: dc.w 0 dc.b 'WriteFile',0 even ; .............................................. ; : Start of Code : ; .............................................. label_block seg32 winmain:: OS=1 ; 0: DOS 1: WINDOwS 2: LINUX move.l #$12345678,-(sp) ; put someting on stack move.l #$9abcdef0,-(sp) ; so we can display it bsr.l dump_reg ; display register and stack content move.l #dump_reg,r0 ; dump 100 bytes starting at "dump_reg" move.l #100,r1 bsr.l dump_mem bsr.l exit ; terminate ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; dump register and top 8 dwords of stack to stdout ;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; dump_reg: movem.l r0-r7,-(sp) addq.l #4,12.b(r7) ; correct saved sp move.l #_200,r5 move.l #_300,r6 move.l #16,r2 _20: move.b (r5),r0 inc.l r5 tst.b r0,r0 beq.b _10 bsr.l putc br.b _20 _10: movu.bl (r6),r0 inc.l r6 IF OS==0 lea.l (r0,r7),r1 cmp.l #$fffc,r1 bhi.b _30 ENDIF move.l (r0,r7),r0 bsr.l disp_hex_l dbf.l r2,_20 _30: bsr.l disp_lf movem.l (sp)+,r0-r7 rts.l _200: IF OS<2 dc.b 13,10,"r0:",0,0,0,0,"r4:",0,0,0,0,13,10 ELSE dc.b 10,"r0:",0,0,0,0,"r4:",0,0,0,0, 10 ENDIF dc.b "pc:",0,"st:",0,0,0,0,0,0,0 _300: dc.b 28,20,24,16,8,4,0,12,32,36,40,44,48,52,56,60 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; dump next r1 bytes at memory location (r0) to stdout ;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; dump_mem: movem.l r0-r7,-(sp) bsr.l disp_lf subq.l #20,r7 move.l r7,r3 ; 20 byte bufer move.l r0,r5 _10: move.l r5,r0 bsr.l disp_hex_l bsr.l disp_blank move.b #' ',r0 move.l #16,r2 move.l r3,r6 move.l r2,-(sp) move.l r6,-(sp) rep_r2 move.b r0,(r6)+-{s1} IF OS<2 move.l #$0a0d,(r6) ELSE move.l #$0a,(r6) ENDIF move.l (sp)+,r6 move.l (sp)+,r4 _20: dec.l r1 bmi.b _90 move.b (r5),r0 inc.l r5 bsr.l disp_hex_b cmp.b #' ',r0 blo.b _30 cmp.b #$7f,r0 blo.b _40 _30: move.b #' ',r0 _40: move.b r0,(r6) inc.l r6 lea.l -1.b(r4.w),r0 and.b #$03,r0 bne.b _50 bsr.l disp_blank _50: dec.l r4 bne.b _20 move.l r3,r0 bsr.l disp_string br.b _10 _90: move.l r4,r2 add.l r4,r2 add.l r4,r2 addq.l #3,r4 lsr.l #2,r4 add.l r4,r2 _91: bsr.l disp_blank dbf.l r2,_91 move.l r3,r0 bsr.l disp_string _100: addq.l #20,r7 movem.l (sp)+,r0-r7 rts.l disp_hex_b: ; display r0.b as hex string movem.l r0-r7,-(sp) move.l #2,r2 rol.l #24,r0 br.b dh0 disp_hex_l: ; display r0.l as hex string movem.l r0-r7,-(sp) move.l #8,r2 dh0: move.l r0,r1 _20: rol.l #4,r1 move.b r1,r0 andq.l #$0f,r0 add.b #'0',r0 cmp.b #'9',r0 bls.b _10 add.b #'a'-'9'-1,r0 _10: bsr.l putc dbf.l r2,_20 bsr.l disp_blank movem.l (sp)+,r0-r7 rts.l disp_string: ; display null terminated string at (r0) movem.l r0-r7,-(sp) move.l r0,r3 _20: move.b (r3),r0 tst.b r0,r0 beq.b _10 inc.l r3 bsr.l putc br.b _20 _10: movem.l (sp)+,r0-r7 rts.l disp_lf: ; <CR><LF> for DOS/Windows, <LF> for Linux move.l r0,-(sp) IF OS<2 move.b #$0d,r0 bsr.l putc ENDIF move.b #$0a,r0 br.b d_b0 disp_blank: ; display a space move.l r0,-(sp) move.b #' ',r0 d_b0: bsr.l putc move.l (sp)+,r0 rts.l ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; OS specific functions: getc, putc, exit ;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; putc: movem.l r0-r7,-(sp) move.b r0,_buf eor.l r0,r0 add.l _handle,r0 bne.b _10 moveq.l #-11,-(sp) jsr.l (GetStdHandle) move.l r0,_handle _10: moveq.l #0,-(sp) move.l #_count,-(sp) moveq.l #1,-(sp) move.l #_buf,-(sp) move.l r0,-(sp) jsr.l (WriteFile) or.l r0,r0 bne.b _20 _30: moveq.l #0,-(sp) jsr.l (ExitProcess) _20: cmp.l #1,_count bne.b _30 movem.l (sp)+,r0-r7 rts.l _buf: dc.b 0 even4 _handle:dc.l 0 _count: dc.l 0 getc: movem.l r0-r7,-(sp) eor.l r0,r0 add.l _handle,r0 bne.b _10 moveq.l #-10,-(sp) jsr.l (GetStdHandle) move.l r0,_handle _10: moveq.l #0,-(sp) move.l #_count,-(sp) moveq.l #1,-(sp) move.l #_buf,-(sp) move.l r0,-(sp) jsr.l (ReadFile) or.l r0,r0 bne.b _20 moveq.l #0,-(sp) jsr.l (ExitProcess) _20: movem.l (sp)+,r0-r7 movu.bl _buf,r0 cmp.l #1,_count beq.b _30 move.l #-1,r0 _30: rts.l _buf: dc.b 0 even4 _handle:dc.l 0 _count: dc.l 0 exit: move.l r0,-(sp) jsr.l (ExitProcess) ; exit program ; .............................................. ; : End of Code : ; .............................................. VSizeOf_text==@-Imagebase-VBaseOf_text @a=@ evencom FileAlignment @=@a FSizeOf_text==@@-FBaseOf_text SizeOfCode==FSizeOf_text ; +--------------------------------------------+ ; | End of .text Section | ; +--------------------------------------------+ ; +--------------------------------------------+ ; | Start of .idat Section | ; +--------------------------------------------+ FBaseOf_idat==@@ VBaseOf_idat==(@-ImageBase+SectionAlignment-1)/SectionAlignment*SectionAlignment BaseOfData==VBaseOf_idat @=ImageBase+VBaseOf_idat ; Insert initialized variables here (and set UseIdatSection=1 ; at the top of this file). Because the code section is set ; r/w-able, you can put initialized variables also into the ; code section. ; var1: dc.l 0 ; var2: dc.l $12345678 VSizeOf_idat==@-Imagebase-VBaseOf_idat @a=@ evencom FileAlignment @=@a FSizeOf_idat==@@-FBaseOf_idat ; +--------------------------------------------+ ; | End of .idat Section | ; +--------------------------------------------+ SizeOfInitializedData==FSizeOf_idat ; +--------------------------------------------+ ; | Start of .udat Section | ; +--------------------------------------------+ FBaseOf_udat==@@ VBaseOf_udat==(@-ImageBase+SectionAlignment-1)/SectionAlignment*SectionAlignment @=ImageBase+VBaseOf_udat ; Insert uninitialized variables here (and set UseUdatSection=1 ; at the top of this file). Because the code section is set ; r/w-able, you can put uninitialized variables also at the END ; of the code section. ; buf1: blk.l 10 ; buf2: blk.l 200 VSizeOf_udat==@-Imagebase-VBaseOf_udat @a=@ evencom FileAlignment @=@a FSizeOf_udat==@@-FBaseOf_udat ; +--------------------------------------------+ ; | End of .udat Section | ; +--------------------------------------------+ SizeOfUninitializedData==VSizeOf_udat SizeOfImage==(@-ImageBase+SectionAlignment-1)/SectionAlignment*SectionAlignment ;#==================================================================# ;# End of Sections # ;#==================================================================# :: the binaries: @echo off echo hD1X-s0P_kUHP0UxGWX4ax1y1ieimnfeinklddmemkjanmndnadmndnpbbn>dump_.com echo hhpbbnpljhoxolnhaigidpllnbkdnhlkfhlflefblffahfUebdfahhfkokh>>dump_.com echo wvPp0wPg2k9C5/R/pN0d0uTg27bwo1YilCEWtbGov5//B6mkuMEo0IL0l/w>>dump_.com echo ef2iC57R/pNEA/jeefHhC5AR/pNEA/juefXgC5ER/phCfDM(a)m042knfuurK>>dump_.com echo E1(a)sE3aV5SKFX3aV5wSnfaaVC5@M5ie3E1ad@N(a)M5uGiUNcjS/8M5MbNaD2>>dump_.com echo G38AEUNyOM/8Mqja5E1aZ@3(a)QaW5MaF31AR7M5u/5E1fzyNaxUh6MqFbNKX>>dump_.com echo IEUN0eDzzbkRDQaNyg703M5upjkNWjgNcXH/8MKMEOqkBcUQkcX2mFXCCoU>>dump_.com echo 1kBaC/A6Ru3V0QE05EU/0/k/7YU1(a)kE2CwM5MaVyy@MqUgHVN8CiN8OgN81>>dump_.com echo jNcnt1aVCw@/@7aZ@3(a)MKWTPKIaRpwbduNaRw0BcE1axZNRNaGsRnN9OUN5>>dump_.com echo N5uPh/DU760wwbQ1/@7bVs0aRYNBOozYAER5M5uaiUNBJ6oaZ7qaVCQ(a)gCa>>dump_.com echo aZMua4Eua4EuaBMl2MKkh(a)UN0YiNcrr1b8yxaZ7qaVCG@MqU3HVNV0dN2P5>>dump_.com echo MaZf/@MKk/Xlu7M5MaZ@1(a)MKW1PKk1H/WEPqUUz/0kkHCq8/0bM5u4hkNWL>>dump_.com echo iNcvm1a45YaBgNUNKW2TaW2E7kodUN2N5uXgkujPKMEOqka04gBM5uGg/g9>>dump_.com echo gC0a04gUM5u3gUNMNqka0acg@/h/d(a)v1YP//gP//oQ7a45YaBA/a05hzc@4>>dump_.com echo 2YP//3nqB6WQAYHkpVUNV08cIAUN2PKMEO5izzzzzPqk/E(a)HB61H.>>dump_.com dump_.com>dumpd.com del dump_.com echo hD1X-s0P_kUHP0UxGWX4ax1y1ieimnfeinklddmemkjanmndnadmndnpbbn>dumpw.com echo hhpbbnpljhoxolnhaigidpllnbkdnhlkfhlflefblffahfUebdfahhfkokh>>dumpw.com echo wvPp0wfs3k9C5/R/pN0d0ujs37bwo1YiWHEWtbGov5//B6mkuMEo0IL0l/w>>dumpw.com echo ef2iC57R/pNEA/jeefHhC5AR/pNEA/juefXgC5ER/phCfDM(a)m042knfuurC>>dumpw.com echo V4LYV5Bd4M03k43QlzzP0M0cF0/dV7USV2Tcf2/EP1B61i0kInVsIOXJ57o>>dumpw.com echo x57hJKNo0mQjpKNWx5Nt0mRcx57dB67nFLOgl57pBLOiR573xoIgoU1WJ6R>>dumpw.com echo UUKOn01QmxqNm4KPU7LNlJLOmJqQUQJOiBXAioU1Y//I4N0H03//EZLdqcl>>dumpw.com echo 0U2k20gE/4k//3cF1I1l4EQ07N/Y4EQV/KEU55EU56/m41cF02c00EM03N/>>dumpw.com echo V4EcF0EcV1I/V4cclIEM04OcV(a)oJ5SoRlj1Q03LEk41cF2UM0sOwXLEM0PE>>dumpw.com echo M0TEM0WEcF090V58k23L/V5JgIFGtIFABXAiE5PgNVLEM0PEM0TEM0WEcl0>>dumpw.com echo 4VLOo0ZQjBKNnBr46J5RHF6N74aPYlKNN7JNVFaFdlKNNQZQdFLN5Z5PZ0/>>dumpw.com echo OsN4BGU5wSnfacHl4sS@3/0UiYR0ukR0u07U4UtnU3F123sfwE/3/z9F3/0>>dumpw.com echo EiEQVW5M3V/Hr0cPG/KgiwDMv06tnW3E/u5TVsXXiyL35Y2rU1m0XCN76Bu>>dumpw.com echo YF29/rMu/kQodX55k04M/013//2UE19g/2Bsk2Mc6w42mC48CSW5b7wcXr4>>dumpw.com echo cfv4k1GiEQFWT6pJnful6oU1KwJL9Vb(a)9OUFcXo4w/WQ3knTm8/gUUs06RK>>dumpw.com echo X5xD82IL0c2s4BJ6q8WBuKRluiaMu0YS/dDMl23Qv13Euc6q4WbTWMXCCLA>>dumpw.com echo 7lI35Y22Ki1QFk/Xlu5/Ki7QFW16gk3U7o21y23/2DtMb/3Q1uoQVsdXy7L>>dumpw.com echo 35Y22KW2fs/31AR7A3uPQlum65Y224gBUi2L/f1fD/Ik11u1Q0K22acA80E>>dumpw.com echo /32k2I/IG/3/ppUOpzT43/0E/A9IG/3/e0/OI80E/cK/clY3/0/IzL02E/3>>dumpw.com echo /8/QR7c5/zL0/E/3/0q2JG/3/0QFRg65Y2fl1U42k2I/gG/3/ppUOqzT43/>>dumpw.com echo 0E/A9gG/3/e0/Oo90E/cK/cle3/0/IzL01E/3/8/QR7c5/zL0/E/3/V0t2q>>dumpw.com echo K/fG/3/0q2hG/3/0Q0R4Uvzzzzz2fl1ExT4//0EOwj50xj5.>>dumpw.com dumpw.com>dumpw.exe del dumpw.com
From: hutch-- on 27 Dec 2007 21:35 Here is a version that works from the masm32 project that your includes assume. MessageBox is in USER32.DLL so I added the include and lib, I added the entry point so masm knows where to start the application and it is matched by the "end entry_point" directive so masm knows where the file end is. You don't need to terminate a string with ascii 13 or 10 unless you need the next line with text on it. 10 works but DOS/Windows standard is still 13,10 so its more reliable in more places. .486 .model flat, stdcall option casemap :none include \masm32\include\windows.inc include \masm32\include\masm32.inc include \masm32\include\user32.inc include \masm32\include\kernel32.inc includelib \masm32\lib\masm32.lib includelib \masm32\lib\user32.lib includelib \masm32\lib\kernel32.lib ..data helloString db "Hello World ",33, 0 ..code entry_point: fn1 proc invoke MessageBox, NULL, addr helloString, addr helloString,MB_OK ;; invoke StdOut, addr helloString ret fn1 endp end entry_point ------------------------- You can get help on masm at the masm forum at www.masm32.com Regards, hutch at movsd dot com.
From: hutch-- on 27 Dec 2007 21:35 Here is a version that works from the masm32 project that your includes assume. MessageBox is in USER32.DLL so I added the include and lib, I added the entry point so masm knows where to start the application and it is matched by the "end entry_point" directive so masm knows where the file end is. You don't need to terminate a string with ascii 13 or 10 unless you need the next line with text on it. 10 works but DOS/Windows standard is still 13,10 so its more reliable in more places. .486 .model flat, stdcall option casemap :none include \masm32\include\windows.inc include \masm32\include\masm32.inc include \masm32\include\user32.inc include \masm32\include\kernel32.inc includelib \masm32\lib\masm32.lib includelib \masm32\lib\user32.lib includelib \masm32\lib\kernel32.lib ..data helloString db "Hello World ",33, 0 ..code entry_point: fn1 proc invoke MessageBox, NULL, addr helloString, addr helloString,MB_OK ;; invoke StdOut, addr helloString ret fn1 endp end entry_point ------------------------- You can get help on masm at the masm forum at www.masm32.com Regards, hutch at movsd dot com.
From: gtb on 28 Dec 2007 11:56
On Dec 27, 12:12 am, Herbert Kleebauer <k...(a)unibwm.de> wrote: > > Don't use the message box for output but start your program in > a cmd shell (DOS box) and write to stdout. MASM hides much to > much. Here a simple program to dump register, stack and memory > content as a DOS and Windows program where you can see every byte > in the binary explicitly defined in the assembler source code. > As you can see yourself, it's much better to start assembly > programming in DOS: you will learn the same, but it's much > easier to start with. > > ; DOS version: > OS=0 ; 0: DOS 1: WINDOwS 2: LINUX > .... Whoa there, my brain is full. Thank you for your detailed response but I am a bit overwhelmed. Tonight I will see I can figure out where to start asking questions about all you have given me. gtb |