flat assembler
Message board for the users of flat assembler.
Index
> Programming Language Design > align directive |
Author |
|
Tomasz Grysztar 13 Jul 2017, 10:10
Keep in mind that this only works if $ has an absolute value (a known number), and this is not true in case of relocatable formats, like object files (COFF/ELF) or PE executables with fixups - for this reason internally implemented ALIGN directive was needed.
|
|||
13 Jul 2017, 10:10 |
|
Sudoku 05 Aug 2020, 06:01
Good day. First I want to thank HopekForth for the awesome formula db -$ and k dup 0 where k = n-1 and n is a power of 2! I can't count how many times it has saved my life
Second, I have one suggestion for Tomek Grysztar on align directive in his flat assembler. It would be great if there would be an _optional_ second parameter for align directive, which would allow to specify the byte to fill the alignment area with other value than nop instruction code. Because it is optional parameter, all code will be compatible with this change of flat assembler. For example, one could write: align 16, 0 if one wants to write discussed example. Tomek, is it possible to add this functionality to your flat assembler? |
|||
05 Aug 2020, 06:01 |
|
revolution 05 Aug 2020, 06:07
Could that be extended to any arbitrary length repeating byte pattern?
Code: align 16,0xaa,0x55 ;repeat aa,55,aa,55,... until filled |
|||
05 Aug 2020, 06:07 |
|
ProMiNick 05 Aug 2020, 07:10
to Sodoku & HopekForth - names are traditionaly not translated (thay could go from 1 alphabet to another, but not more)
thour variant of macro is simple: Code: macro align pow*,filler:? { db (-$+$$) and (pow-1) dup filler } example of use: Code: db 1 align 4,$34 align 8 db 1 If thou will be initialy pretty smart & wouldn`t use alignments others than power of 2 macro could fit one row. for common use will be needed one more line: Code: assert bsf pow = bsr pow revolution, on thour level of assembly skill such things are easier manualy. (advantage of macro implementation is unsugnificant in comparison to cost of preprocessor resources). by the way thou skilled as nobody other in patching of fasm core. And one more: in case of $AA, $55 assumed that they fit $AA even byte but $55 odd byte. So we could see that in general case power of alignment & filling pattern are not enought parameters (needed information how pattern should interfere with particular alignment), but if we add more parameters they wouldn`t be intuitive. So, cuurrent (in fasm core) alignment implementation is the best case. |
|||
05 Aug 2020, 07:10 |
|
revolution 05 Aug 2020, 07:15
ProMiNick: Please note the comment from Tomasz about why using db can be a problem.
https://board.flatassembler.net/topic.php?p=197948#197948 Tomasz Grysztar wrote: Keep in mind that this only works if $ has an absolute value (a known number), and this is not true in case of relocatable formats, like object files (COFF/ELF) or PE executables with fixups - for this reason internally implemented ALIGN directive was needed. |
|||
05 Aug 2020, 07:15 |
|
ProMiNick 05 Aug 2020, 07:52
this magic (-$+$$) resolve problem.
Thou were not paying attention. (I resolved it in past when I was needed to make libraries for kolibri OS, they are in COFF format - so solution is tested) Code: ; Copyright (C) KolibriOS team 2008-2020. All rights reserved. format MS COFF ;------------------------------------------------- ; INFO ;------------------------------------------------- libname equ 'messagebox' LIB_VERSION equ 1 ;------------------------------------------------- ; INCLUDES ;------------------------------------------------- include 'kolibria.inc' ;include 'C:\fasmpack\INCLUDES\OS_SPECS\KOLIBRI\EQUATES/kernel.inc' ;include 'C:\fasmpack\INCLUDES\OS_SPECS\KOLIBRI\EQUATES/syscalls.inc' ;include 'C:\fasmpack\INCLUDES\OS_SPECS\KOLIBRI\EQUATES/keys.inc' ;include 'C:\Kolibrios.org\programs\macros.inc' include 'mbxdata.inc' ;ID_BTN_SYS_CLOSE = 1 ;ID_BTN_USER_FIRST = 3 MB_MAX_BTN_COUNT = 8 MB_BTN_HEIGHT = 20 BORDER_HEIGHT = 5 CHAR_WIDTH = 6 MBX_VERT_SPACING = 5 MBX_HORZ_SPACING_1 = 5 MBX_HORZ_SPACING_2 = 10 MBX_HORZ_SPACING_3 = 15 ;MBX_CAPTION_OFFSET = 2 ;------------------------------------------------- ; CODE ;------------------------------------------------- section '.flat' code readable align 16 mbx_thread_proc: mcall SF_STYLE_SETTINGS,SSF_GET_COLORS,sc,sizeof.system_colors mcall SF_SET_EVENTS_MASK,EVM_BUTTON or EVM_KEY or EVM_REDRAW ;-- clear id pressed button --- mov eax,[mb_text] mov eax,dword[eax] add eax,ID_BTN_USER_FIRST dec eax mov [mb_focused_button],eax stdcall MsgBoxReInit,[mb_text] call do_redraw still: sub esp,4 mcall SF_WAIT_EVENT movzx ecx,al jmp [event_handlers+4*ecx] event_handlers dd 0,do_redraw,key,button ;------------------------------------------------- key: mcall SF_GET_KEY ror eax,8 cmp ah,SCAN_CODE_RETURN jne @F mov eax,[mb_focused_button] jmp close @@: cmp al,ASCII_KEY_LEFT jne .check_next cmp [mb_focused_button],ID_BTN_USER_FIRST jg @f mov eax,[mb_button_count] add [mb_focused_button],eax @@: dec [mb_focused_button] jmp MsgBoxDrawAllBtns ;jmp still .check_next: cmp ah,SCAN_CODE_TAB je .focus_next_btn cmp al,ASCII_KEY_RIGHT je .focus_next_btn retn .focus_next_btn: mov eax,[mb_button_count] add eax,ID_BTN_USER_FIRST cmp [mb_focused_button],eax jne @F retn @@: inc [mb_focused_button] cmp [mb_focused_button],eax jl @f mov [mb_focused_button],ID_BTN_USER_FIRST @@: jmp MsgBoxDrawAllBtns ;jmp still ;------------------------------------------------- button: mcall SF_GET_BUTTON test al,al jz .LMBclick retn .LMBclick: shr eax,8 cmp eax,ID_BTN_USER_FIRST jge close cmp eax,ID_BTN_SYS_CLOSE je @F retn @@: ;.exit: mov eax,ID_BTN_USER_FIRST dec eax close: sub eax,ID_BTN_USER_FIRST-1 mov ebx,[mb_text] mov [ebx],eax ;*** call msgbox functions *** cmp dword[mb_funct],0 jz @F test eax,eax jz @F dec eax shl eax,2 add eax,dword[mb_funct] cmp dword[eax],0 jz @F call dword[eax] @@: mcall SF_TERMINATE_PROCESS ;------------------------------------------------- do_redraw: mcall SF_REDRAW,SSF_BEGIN_DRAW mov edx,[sc.work] or edx,CW_CAPTION or CW_CLIENTRECTCOORDS or CW_SKINED mov edi,[mb_text] add edi,MBX_CAPTION_OFFSET ;Caption mcall SF_CREATE_WINDOW,dword[mb_width_left],dword[mb_height_top] mcall SF_THREAD_INFO,mbx_thread_info,-1 mov eax,dword[mbx_thread_info.client_box.width] sub eax,[btn_width] shr eax,1 add eax,MBX_HORZ_SPACING_1 mov [ot_left],ax mpack ebx,MBX_HORZ_SPACING_1,MBX_VERT_SPACING mov ecx,[sc.work_text] mov edx,[txtMsg] @@: mov edi,edx push ecx call GetStrLength call GetStrLineLength mov esi,ecx sub esi,1 pop ecx jz @F mcall SF_DRAW_TEXT add edx,esi cmp byte[edx],0 je @F inc edx add ebx,10 ; move <--y--> jmp @B @@: call MsgBoxDrawAllBtns mcall SF_REDRAW,SSF_END_DRAW retn ;------------------------------------------------- MsgBoxDrawAllBtns: ; Buttons ... push esi mov esi,txtBut mov edx,ID_BTN_USER_FIRST mov ebx,dword[ot_top_left] add ebx,MBX_VERT_SPACING jmp .left_coor_calculated .next_button: inc edx ; next button ID(edx) imul ecx,CHAR_WIDTH ; calculate new topleft coord (ebx) add ecx,MBX_HORZ_SPACING_3 ; taking in account button caption length (ecx) shl ecx,16 ; calculated at previous iteration step add ebx,ecx .left_coor_calculated: mov edi,[esi] ; get ptr(edi) to button caption of current array item(esi) call GetStrLength sub ecx,1 jz .last_button_done call MsgBoxDrawButton add esi,4 ; look for next array item (esi) if any cmp esi,endBut jb .next_button .last_button_done: pop esi retn ;input: ; ecx = button id align 4 MsgBoxDrawButton: ; [in/out/unchanged] ebx:button caption topleft coord ; [in/out/unchanged] ecx:button caption length ; [in/out/unchanged] edx:button id ; [unchanged too] esi,edi,ebp push esi push edx push ecx push ebx mov esi,[sc.work_button] cmp edx,[mb_focused_button] jne @F mov esi,[sc.work_button_text] @@: imul ecx,CHAR_WIDTH add ecx,MBX_HORZ_SPACING_2 mov bx,cx sub ebx,MBX_HORZ_SPACING_1 shl 16 mov ecx,[esp] shl ecx,16 add ecx,(-MBX_VERT_SPACING)shl 16 + MB_BTN_HEIGHT mcall SF_DEFINE_BUTTON mov ecx,[sc.work_button_text] cmp esi,ecx jne @F mov ecx,[sc.work_button] @@: pop ebx mcall SF_DRAW_TEXT,,,edi,[esp] pop ecx pop edx pop esi retn sizeof.RET = 4 sizeof.ARG = 4 sizeof.PUSHAD = 8*4 ;------------------------------------------------- MsgBoxReInit: pushad add esp,sizeof.PUSHAD+sizeof.RET pop edi sub esp,sizeof.PUSHAD+sizeof.RET+sizeof.ARG mov [mb_text],edi add edi,MBX_CAPTION_OFFSET call GetStrLength add edi,ecx mov [txtMsg],edi ;--- go to first button text --- buttons 1...MB_MAX_BUT mov ebx,txtBut mov ecx,MB_MAX_BTN_COUNT @@: ;call strlen push ecx call GetStrLength add edi,ecx pop ecx mov dword[ebx],edi cmp byte[edi],0 je @F add ebx,4 loop @B @@: ;--- calc button top --- mov eax,1 mov ebx,[txtMsg] @@: inc ebx cmp byte[ebx],0 je @F cmp byte[ebx],$D jne @B inc eax jmp @B @@: imul eax,10 add eax,2*MBX_VERT_SPACING mov [ot_top],ax ;--- calc window height --- add eax,MBX_VERT_SPACING + MB_BTN_HEIGHT + BORDER_HEIGHT mov [mb_height],ax mcall SF_STYLE_SETTINGS,SSF_GET_SKIN_HEIGHT ;skin height add [mb_height],ax ;--- calc window top --- mcall SF_GET_SCREEN_SIZE sub ax,[mb_height] shr ax,1 mov [mb_top],ax ;--- and window left shr eax,16 sub ax,[mb_width] shr ax,1 mov [mb_left],ax ;--- calc button width --- xor ebx,ebx xor ecx,ecx mov edi,[txtBut] and [mb_button_count],0 @@: cmp byte[edi],0 je @F inc ecx push ecx call GetStrLength add edi,ecx inc [mb_button_count] dec ecx add ebx,ecx pop ecx jmp @B @@: imul ebx,CHAR_WIDTH imul ecx,MBX_HORZ_SPACING_3 lea ebx,[ebx+ecx+MBX_HORZ_SPACING_2-MBX_HORZ_SPACING_3] mov [btn_width],ebx popad ret 4 ;------------------------------------------------- MsgBoxCreate: pushad ; more better trash everyreg and caller care pushad add esp,sizeof.PUSHAD+sizeof.RET pop [mb_text] sub esp,sizeof.PUSHAD+sizeof.RET+sizeof.ARG mcall SF_CREATE_THREAD,1,mbx_thread_proc,[esp+sizeof.PUSHAD+sizeof.RET+sizeof.ARG] popad ret 8 ;------------------------------------------------- MsgBoxSetFunctions: pop eax pop [mb_funct] jmp eax ;------------------------------------------------- GetStrLength: ; [in] edi:string pointer ; [out] ecx:string length(with trailing 0) ; [unchanged] ebx, edx, esi, edi, ebp, esp or ecx, -1 xor eax, eax cld repne scasb not ecx sub edi,ecx retn ;------------------------------------------------- GetStrLineLength: ; [in] edi:string pointer ; [in] ecx:string length(with trailing 0) ; [out] ecx:string line length(with trailing 0 or $D) ; [unchanged] ebx, edx, esi, edi, ebp, esp push ecx mov al,$D repne scasb sub [esp],ecx pop ecx sub edi,ecx retn ;------------------------------------------------- ; EXPORT ;------------------------------------------------- export \ MsgBoxCreate, 'mb_create',\ MsgBoxReInit, 'mb_reinit',\ MsgBoxSetFunctions, 'mb_setfunctions' ;------------------------------------------------- ; INITIALIZED DATA ;------------------------------------------------- ;--- à §¬¥àë íªà ¥ ®ª á®®¡é¥¨ï --- mb_width_left: mb_width dw 300 mb_left dw 0 mb_height_top: mb_height dw 50 mb_top dw 0 mb_focused_button dd ID_BTN_USER_FIRST ;ª®¯ª ¢ 䮪ãᥠ(á ãç¥â®¬ MB_FIRST_BUT_ID) mb_button_count dd 1 ;ç¨á«® ¢á¥å ª®¯®ª á®®¡é¥¨ï txtMsg dd ? ;㪠§ ⥫ì ç «® ⥪áâ á®®¡é¥¨ï txtBut rd MB_MAX_BTN_COUNT ;㪠§ ⥫ì ç «® ⥪áâ ¯®¤¯¨á¥© ª®¯®ª endBut: ot_top_left: ot_top dw ? ;®âáâ㯠ᢥàåã (¤«ï à¨á®¢ ¨ï ª®¯®ª) ot_left dw ? ;®âáâ㯠᫥¢ (¤«ï à¨á®¢ ¨ï ª®¯®ª) btn_width dd ? ;summary width of all buttons including spaces between them ;-------------------------------------------------- mb_text dd ? ;msgbox_1 ;㪠§ â¥«ì ¤ ë¥ ¤«ï á®®¡é¥¨ï (ª®â®àë ¯¥à¥¤ îâìáï ®ªã) mb_funct dd ? ;pointer to functions sc system_colors mbx_thread_info process_information ;㪠§ ⥫ì áâàãªâãàã process_information த¨â¥«ì᪮£® ®ª thou can see align present there, and all successfuly compiled, and that lib even used in other demo (but my version may be different than that presented in OS). |
|||
05 Aug 2020, 07:52 |
|
revolution 05 Aug 2020, 08:25
Very good. But I see it using the normal align, right? Not your db version.
BTW: You can use ($$-$) or (-$+$$) for the same result. |
|||
05 Aug 2020, 08:25 |
|
revolution 05 Aug 2020, 08:40
I notice this difference when using (-$+$$):
Code: virtual at 7 align 16 display $+'0' end virtual virtual at 7 db (-$) and 15 dup 0 display $+'0' end virtual virtual at 7 db (-$+$$) and 15 dup 0 display $+'0' end virtual Code: @@7 Code: @@@ |
|||
05 Aug 2020, 08:40 |
|
ProMiNick 05 Aug 2020, 08:53
Oh, it was not related with COFFs there all operated properly.
in case of COFFs align directive resolve variable base, but in case of variable base of virtual blocks - not. my struct realization supposed aligned members and when they passed as locals on stack they raised error similar to Code: virtual at esp
align 4
end virtual so because of that I redefine align. |
|||
05 Aug 2020, 08:53 |
|
revolution 05 Aug 2020, 09:23
I get the same result with org.
Code: org 7 align 16 display $+'0' org 7 db (-$) and 15 dup 0 display $+'0' org 7 db (-$+$$) and 15 dup 0 display $+'0' |
|||
05 Aug 2020, 09:23 |
|
< Last Thread | Next Thread > |
Forum Rules:
|
Copyright © 1999-2024, Tomasz Grysztar. Also on GitHub, YouTube.
Website powered by rwasa.