1 / 33

Practical Session 6

Practical Session 6. NASM Preprocessor. NASM contains a powerful macro processor, which supports conditional assembly multi-level file inclusion two forms of macro (single-line and multi-line) * a `context stack' mechanism for extra macro power

venus
Télécharger la présentation

Practical Session 6

An Image/Link below is provided (as is) to download presentation Download Policy: Content on the Website is provided to you AS IS for your information and personal use and may not be sold / licensed / shared on other websites without getting consent from its author. Content is provided to you AS IS for your information and personal use only. Download presentation by click this link. While downloading, if for some reason you are not able to download a presentation, the publisher may have deleted the file from their server. During download, if you can't get a presentation, the file might be deleted by the publisher.

E N D

Presentation Transcript


  1. Practical Session 6

  2. NASM Preprocessor • NASM contains a powerful macro processor, which supports • conditional assembly • multi-level file inclusion • two forms of macro (single-line and multi-line) * • a `context stack' mechanism for extra macro power • Preprocessor directives all begin with a % sign • * We are going to cover only this subsection of NASM macro processor. • Use http://www.nasm.us/doc/nasmdoc4.html link to read more.

  3. Macro - definition • Macro is a set of statements given a symbolic name • Macro is invoked, not called. A copy of the macro is inserted directly into the program • After being defined, NASM will substitute (expand) those statements whenever it finds the symbolic name Source code myMacro . • myMacro . • myMacro . • Expanded code . . . macro definition macro name macro body (statements) NASM preprocessor macro usage

  4. Single-line macros • %define – defines single-line macro • a macro is expanded only when it is called • Example:%define ctrl 0x1F & %define param(a, b) ((a)+(a)*(b))mov byte [param(2,ebx)], ctrl 'D' expands to by NASM preprocessor mov byte [(2)+(2)*(ebx)], 0x1F & 'D' • Example: • %define a(x) 1+b(x)%define b(x) 2*x expands to mov ax,1+2*8 mov ax, a(8) by NASM preprocessor

  5. Single-line macros (cont) • We can overload single-line macros. The preprocessor will be able to handle both types of macro call, by counting the parameters you pass. %define foo(x) 1+x %define foo(x, y) 1+x*y • Macros defined with %define are case sensitive. We use %idefine to define all the case variants of a macro at once. • There is a mechanism which detects when a macro call has occurred as a result of a previous expansion of the same macro, to guard against circular references and infinite loops. %define foo 1+ ebx A macro with no parameters prohibits the definition of the same name as a macro with parameters, and vice versa.

  6. Single-line macros (cont) • %define - a macro resolved at the time that it is called (used) • %xdefine - a macro resolved at the time that it is defined Example: %define isTrue 1 %xdefine isTrue 1 %define isFalse isTrue %xdefine isFalse isTrue %define isTrue 0 %xdefine isTrue 0 val1: db isFalse ; val1 = ?val1: db isFalse ; val1=?%define isTrue 1 %xdefine isTrue 1 val2: db isFalse ; val2 = ?val2: db isFalse; val2=?

  7. Single-line macros (cont) • In the left case, when ‘isFalse’ macro uses %define, so it is expanded only when it is called. As ‘isFalse’ expands to ‘isTrue’, the expansion will be the current value of ‘isTrue’. The first time it is called that is 0, and the second time it is 1. • In the right case, each time that ‘isFalse’ is called, it expands to 1, as that is what the macro ‘isTrue’ expanded to at the time that ‘isFalse’ was defined. • %define isTrue 1 %xdefine isTrue 1 %define isFalse isTrue %xdefine isFalse isTrue %define isTrue 0 %xdefine isTrue 0 val1: db isFalse ; val1 = 0 val1: db isFalse ; val1=1%define isTrue 1 %xdefine isTrue 1 val2: db isFalse ; val2 = 1val2: db isFalse; val2=1

  8. Single-line macros (cont) • %undef – undefines defined single-line macro • Example: • %define foo(x) 1+x %undef foo mov ax, foo(3) ; would not be expanded since ; after %undef the macro foo is no longer defined

  9. Multiple-line macros • Works with %macro … %endmacromechanism • Macro parameters would be referred to as %1, %2, %3 and so on Example: %macro foo 1 push ebp mov ebp, esp sub esp, %1 %endmacro my_func: foo 12 my_func: push ebp mov ebp, esp sub esp,12 this macro gets one parameter first parameter of the macro NASM preprocessor

  10. Multiple-line macros (cont) • Multi-line macros are case-sensitive, unless we define them using the alternative directive %imacro. • If we need to pass a comma as part of a parameter to a multi-line macro, we can do that by enclosing the entire parameter in braces. • Example: • %macro foo 2 %2: db %1 %endmacro foo 'a', letter_a letter_a: db 'a' foo 'ab', string_ab string_ab: db 'ab' foo {13,10}, crlf crlf: db 13,10 NASM preprocessor

  11. Multiple-line macros (cont) • Multi-line macros can be overloaded by defining the same macro name several times with different amounts of parameters. (This time, no exception is made for macros with no parameters.) • Reserved words can also be overloaded: • Example: • %macro push 2 • push %1 • push %2 • %endmacro • push ebx ; this line is not a macro call push eax, ecx ; but this one is a macro call • Note: if define macro ‘push’ with one parameter, the original ‘push’ instruction would be overloaded.

  12. Multiple-line macros – labels Defining a macro with an internal label: %macro retz 0 jnz %%skip ret%%skip:%endmacro In every ‘retz’ invocation, the preprocessor creates some unique label of the form: ..@2345.skip to substitute for the label %%skip, where the number 2345 changes with every macro call. If a label begins with the special prefix ..@, then it doesn’t interfere with the local label mechanism. label1: ; a non-local label ..@ 2345.skip : ; this is a macro label .local: ; this is really label1.local

  13. Default Macro Parameters • We supply a minimum and maximum number of parameters for a macro of this type; the minimum number of parameters are required in the macro call, and we provide defaults for the optional ones. • Example: • %macro foo 1-3 eax, [ebx+2] • could be called with between one and three parameters • %1 would always be taken from the macro call (minimal number of parameters) • %2, if not specified by the macro call, would default to eax • %3, if not specified by the macro call, would default to [ebx+2] • We may omit parameter defaults from the macro definition, in which case the parameter default is taken to be blank. This can be useful for macros which can take a variable number of parameters, since the %0 token allows us to determine how many parameters were really passed to the macro call. %macro name min - max <default parameters list>

  14. Greedy Macro Parameters If invoke the macro with more parameters than it expects, all the spare parameters get lumped into the last defined one. %macro macroName numOfParams + The mark %numOfParams will be replaced with numOfParams’s parameter and whatever follows it. Example: %macro writefile 2+ jmp %%endstr %%str: db %2 %%endstr: mov dx, %%str mov cx, %%endstr - %%str mov bx, %1 mov ah, 0x40 int 0x21 %endmacro writefile [fileHandle],"hello, world",13,10

  15. Use –e option to get a source code with all your macros expanded. > nasm -e sample.s Macro Expansion

  16. Jump table • Jump table is • a graceful way to implement “switch - case” mechanism • used to select a function to be evoked • We will construct a array of the jump addresses. • For each number will jump to the corresponding entry in the jump table. switch ( letter ) { case 'A': upper ++; case ‘a': lower ++; default : total ++; }

  17. Jump table - example Output: num = 0 Got the number 0 num = 1 Got the number 1 num = 2 Out of bound main.c extern void jumper(int); int main (int argc , char* argv) { jumper (0); jumper (1); jumper (2); return 0; } jumper(i) should be implemented as follows: printf (“num = %d”, i); switch (i) { case ‘0': printf (“Got the number 0”); case ‘1': printf (“Got the number 1”); default : printf (“Out of bound”); }

  18. Jump table - example section .data jt: dd label_1 dd label_2 str0: db "Got the number 0",10,0 str1: db "Got the number 1",10,0 str2: db "Out of bound",10,0 str3: db "num = %d",10,0 section .text global jumper extern printf jumper: push ebp mov ebp, esp pusha mov ebx, dword [ebp+8] push ebx push str3 call printf ; print num add esp, 8 cmp ebx,0 ; check if num is in bounds jb out_of cmp ebx , 1 ja out_of shl ebx,2 ; num = num * 4 jmp dword [ebx + jt] ; jump according to address ; in table label_1: push str0 call printf add esp, 4 jmp end label_2: push str1 call printf add esp, 4 jmp end out_of: push str2 call printf add esp, 4 jmp end end: popa pop ebp ret to be able to jump in a table of dwords printf (“num = %d”, i); switch (i) { case ‘0': printf (“Got the number 0”); case ‘1': printf (“Got the number 1”); default : printf (“Out of bound”); }

  19. שאלות חזרה למבחן

  20. שאלה 1 נתונות ההגדרות הבאות: x: dw 1y: db 2z: db 3 יש להכפיל את x,y,z ב-2 באמצעות פקודה אחת. ניתן להניח שאין overflow

  21. שאלה 1 נתונות ההגדרות הבאות: x: dw 1y: db 2z: db 3 יש להכפיל את x,y,z ב-2 באמצעות פקודה אחת. ניתן להניח שאין overflow תשובה: נכפול את כל המילה ב- 2: shl dword [x], 1

  22. שאלה 2 עלינו לממש קריאה לפונקציה ללא ארגומנטים, שכתובתה נמצאת ברגיסטר eax. יש לסמן את הקוד שלא יבצע זאת נכון. push next_apush eaxretnext_a: push eaxpush eaxret push next_ajmpeaxnext_a: call eax

  23. שאלה 2 עלינו לממש קריאה לפונקציה ללא ארגומנטים, שכתובתה נמצאת ברגיסטר eax. יש לסמן את הקוד שלא יבצע זאת נכון. push next_apush eaxretnext_a: push eaxpush eaxret push next_ajmpeaxnext_a: call eax

  24. שאלה 3 ברגיסטר eax נמצא הערך -1. יש לרשום 5 פקודות שונות שכל אחת מהן תגרום לכך שברגיסטר eax יהיה הערך 1.

  25. שאלה 3 ברגיסטר eax נמצא הערך -1. יש לרשום 5 פקודות שונות שכל אחת מהן תגרום לכך שברגיסטר eax יהיה הערך 1. תשובה moveax, 1 add eax, 2 negeax shreax, 31 and eax, 1

  26. שאלה 4 נתונה הגדרת macro הבאה, וכן נתונים בזכרון: %macro print 3pushamoveax, 4 ; writemovebx, %1 ; file descriptormovecx, %2 ; addressmovedx, %3 ; byte countint 0x80popa%endmacro section .rodataFile:dd 1MJ: db “Beat it”, 10, 0 איזה מהשימושים הבאים במקרו יגרום לפעולה לא נכונה של התוכנית: movebx, MJprint 1, ebx, 9 print 1, MJ, 9 print dword [File], MJ, 9 movedx, 9print 1, MJ, edx

  27. שאלה 4 נתונה הגדרת macro הבאה, וכן נתונים בזכרון: %macro print 3pushamoveax, 4 ; writemovebx, %1 ; file descriptormovecx, %2 ; addressmovedx, %3 ; byte countint 0x80popa%endmacro section .rodataFile:dd 1MJ: db “Beat it”, 10, 0 איזה מהשימושים הבאים במקרו יגרום לפעולה לא נכונה של התוכנית: movebx, MJprint 1, ebx, 9 print 1, MJ, 9 print dword [File], MJ, 9 movedx, 9print 1, MJ, edx

  28. שאלה 5 עלינו לממש את קטע הקוד הבא: int a, b, x; x = blah(a,&b) מהו קטע הקוד שיבצע זאת נכון ? a) push a c) push dword b push b push dword [a] call blah call blah add esp, 8 add esp, 8 mov [x], eax mov [x], eax b) push dword [b] d) push dword [b] push dword a push dword a call blah call blah add esp, 8 add esp, 8 mov [x], eax pop dword [x]

  29. שאלה 5 עלינו לממש את קטע הקוד הבא: int a, b, x; x = blah(a,&b) מהו קטע הקוד שיבצע זאת נכון ? a) push a c) push dword b push b push dword [a] call blah call blah add esp, 8 add esp, 8 mov [x], eaxmov [x], eax b) push dword [b] d) push dword [b] push dword a push dword a call blah call blah add esp, 8 add esp, 8 mov [x], eax pop dword [x]

  30. שאלה 6 Gloat: shl ebx, 2 jmp [ebx+Tab] Tab: dd F4 dd F3 dd F2 dd F1 F1: add ebx, 4 F2: add ebx, 4 F3: add ebx, 4 F4: shr ebx, 2 ret מה תחזיר הפונקציה Gloat ברגיסטר ebx (עבור ebx בין 0 ל- 3) ? א) 0 ב) ebx בחזקת 2 ג) 2 בחזקת ebx ד) ebx כפול 2

  31. שאלה 6 Gloat: shl ebx, 2 jmp [ebx+Tab] Tab: dd F4 dd F3 dd F2 dd F1 F1: add ebx, 4 F2: add ebx, 4 F3: add ebx, 4 F4: shr ebx, 2 ret מה תחזיר הפונקציה Gloat ברגיסטר ebx (עבור ebx בין 0 ל- 3) ? א) 0 ב) ebx בחזקת 2 ג) 2 בחזקת ebxד) ebx כפול 2

  32. שאלה 7 • ברצוננו לכתוב קוד לשימוש רב-פעמי, שמכפיל את ערך eax פי 3. מוצעות 2 אפשרויות: שימוש במקרו triple או קריאה לפונקציה Triple: • %macro triple 0 mov ebx, eax add eax, eax add eax, ebx %endmacro • Triple: mov ebx, eax add eax, eax add eax, ebx ret א) בזמן ריצה ל-2 האפשרויות אותו זמן ביצוע. ב) השימוש ב- macro מהיר יותר, אבל דורש יותר זיכרון לקוד. ג) השימוש בפונקציה מהיר יותר, אבל דורש יותר זיכרון לקוד. ד) הפונקציה Triple לא יכולה לעבוד, כי היא לא מוציאה משתנים מהמחסנית

  33. שאלה 7 • ברצוננו לכתוב קוד לשימוש רב-פעמי, שמכפיל את ערך eax פי 3. מוצעות 2 אפשרויות: שימוש במקרו triple או קריאה לפונקציה Triple: • %macro triple 0 mov ebx, eax add eax, eax add eax, ebx %endmacro • Triple: mov ebx, eax add eax, eax add eax, ebx ret א) בזמן ריצה ל-2 האפשרויות אותו זמן ביצוע. ב) השימוש ב- macro מהיר יותר, אבל דורש יותר זיכרון לקוד. ג) השימוש בפונקציה מהיר יותר, אבל דורש יותר זיכרון לקוד. ד) הפונקציה Triple לא יכולה לעבוד, כי היא לא מוציאה משתנים מהמחסנית

More Related