|
Facebook Joinc ±×·ì
Joinc QA »çÀÌÆ®
joinc´Â Firefox¿Í chrome¿¡¼ Å×½ºÆ® Çß½À´Ï´Ù. IE¿¡¼´Â Å×À̺íÀÌ ±úÁö°Å³ª À̹ÌÁö°¡ º¸ÀÌÁö ¾ÊÀ» ¼ö ÀÖ½À´Ï´Ù. ƯÈ÷ ±¸±Û DocsÀ̹ÌÁöÀÇ °æ¿ì ¿¢¹Úó¸®µÉ ¼ö ÀÖ½À´Ï´Ù.
Linux Assembler ÇÏ¿ìÅõ| 교정 과정 |
|---|
| 교정 0.8 | 2003³â 11¿ù 27ÀÏ 18½Ã | | | ÃÖÃÊ ¹®¼ÀÛ¼º |
ÀÌ ¹®¼´Â Linux¿¡¼ÀÇ ¾î¼Àºí¸® ¾ð¾î ÇÁ·Î±×·¡¹Ö¿¡ ´ëÇÑ ³»¿ëÀ» ´Ù·é´Ù. ¸®´ª½º¿¡¼´Â
AT&T¹®¹ýÀ» µû¶ó´Â °·ÂÇÑ ¾î¼Àºí·¯ÀÎ as¸¦ Á¦°øÇÑ´Ù.
¶ÇÇÑ ¸®´ª½ºÀÇ ÇÙ½ÉÀÎ gcc ÄÄÆÄÀÏ·¯´Â c·ÎµÈ Äڵ忡 ¾î¼Àºí·¯¸¦ Æ÷ÇÔ½Ãų ¼ö ÀÖ´Â
±â´ÉÀ» °¡Áö°í ÀÖ´Ù.
ÀÌ ¹®¼´Â ¿©·¯ºÐÀÌ X86 ¾î¼Àºí¸® ¾ð¾î¿Í C¾ð¾î¿¡ ´ëÇÑ ±âº»ÀûÀÎ ÀÌÇØ¸¦ °¡Áö°í ÀÖÀ»
°ÍÀ̶ó´Â °¡Á¤ÇÏ¿¡ ÀÛ¼ºµÉ °ÍÀÌ´Ù.
°ÅÀÇ ÇϳªÀÇ Ç¥ÁØÀ» Áö۰í ÀÖ´Â C¾ð¾î¿Í´Â ´Þ¸®, ¾î¼Àºí¸®¾ð¾î´Â
AT&T¿Í IntelÀÇ µÎ°¡Áö (Ç¥ÁØ?)¹®¹ýÀ» °¡Áö°í ÀÖ´Ù. ¶ÇÇÑ À̵éÀº ¼·Î ȣȯµÇÁö
¾Ê´Â ¹®¹ýÀ» °¡Áø´Ù. ÀÌ´Â °³¹ßÀÚ¸¦ ¸Å¿ì È¥µ¿½ÃŰ´Â ¿äÀÎÀÌ µÇ±âµµ Çϸç,
ÇϳªÀÇ ¹®¹ý¿¡¸¸ Àͼ÷ÇÒ °æ¿ì µ¿ÀÏÇÑ ÀÏÀ» ÇÏ´Â ´Ù¸¥ ÄÚµåÀÇ ÇØ¼®¿¡ ¾î·Á¿òÀ»
°ÞÀ» ¼öµµ ÀÖ´Ù. ÀÌ·¯ÇÑ È¥µ¿Àº °¢°¢ÀÇ ¹®¹ýÀÇ Â÷ÀÌ¿¡ ´ëÇÑ ±âº»ÀûÀÎ ÀÌÇØ¸¸ Çϰí
ÀÖ´Ù¸é ¸¹ÀÌ ÁÙÀÏ ¼ö ÀÖ´Ù. ±×·³ ¿ì¼± ÀÌµé µÎ¹®¹ýÀÇ Â÷ÀÌÁ¡¿¡ ´ëÇØ¼ °£´ÜÈ÷
¾Ë¾Æº¸°í ³Ñ¾î°¤·Ï ÇϰڴÙ.
Intel¹®¹ýÀº ´ëü·Î °£´ÜÇÏ¸ç ¾î¶°ÇÑ Á¢µÎ»ç³ª Á¢¹Ì»çµµ ºÙÁö ¾Ê´Â´Ù. ½ÇÁ¦ ½ÃÁßÀÇ
¸¹Àº Ã¥µéÀº Intel¹®¹ýÀ» »ç¿ëÇÑ ¿¹°¡ ¸¹´Ù. ±×·¯³ª AT&TÀÇ °æ¿ì ·¹Áö½ºÅÍ´Â '%'Á¢µÎ»ç¸¦
°¡Áö¸ç °ªµéÀº '$'Á¢µÎ»ç°¡ ºÙ´Â´Ù. Intel¹®¹ýÀÇ °æ¿ì 16Áø¼ö¿Í 2Áøµ¥ÀÌÅÍ´Â °¢°¢ 'h'¿Í 'b'
Á¢µÎ»ç¸¦ °¡Áø´Ù. ±×¸®°í 6Áø¼ö °ªÀÇ °æ¿ì¿¡´Â '0'À» Á¢µÎ»ç·Î »ç¿ëÇÑ´Ù.
표 1. Á¢µÎ»ç ±ÔÄ¢À» Àû¿ëÇÑ ¿¹ | Intel ¹®¹ý | AT&T ¹®¹ý | | mov eax,1 | movl #1,%eax | | mov ebx,0ffh | movl $0xff,%ebx | | int 80h | int $0x80 |
IntelºÐ¹ý°ú AT&TÀÇ ¹®¹ü¿¡¼ ¿ÀÆÛ·£µåÀÇ À§Ä¡´Â ¼·Î Á¤¹Ý´ë·Î »ç¿ëµÈ´Ù. Intel¹®¹ýÀÇ °æ¿ì
¸ñÀûÁö(destination) ¿ÀÆÛ·£µå°¡ ¸ÕÀú¿À°í ¿øº»(source) ¿ÀÆÛ·£µå°¡ ³ªÁß¿¡
¿ÀÁö¸¸ AT&T´Â ¹Ý´ë·Î »ç¿ëµÈ´Ù. AT&T¹®¹ýÀÇ ÀåÁ¡Àº ÀÌÇØÇϱⰡ Á»´õ Á÷°üÀûÀ̶ó´Âµ¥ ÀÖ´Ù.
º¸Åë »ç¶÷µéÀº ¿ÞÂÊ¿¡¼ ¿À¸¥ÂÊÀ¸·Î ±ÛÀ» Àаí ÇØ¼®Çϴµ¥ Á»´õ Àͼ÷Çϱ⠶§¹®ÀÌ´Ù.
표 2. ¿ÀÆÛ·£µå À§Ä¡ÀÇ Â÷ÀÌ | Intel ¹®¹ý | AT&T ¹®¹ý | | instr dest,source | instr source,dest | | mov eax,[ecx] | movl %ecx, %eax |
¸Þ¸ð¸® ¿ÀÆÛ·£µåÀÇ »ç¿ëµµ ¾à°£ÀÇ Â÷ÀÌÁ¡À» º¸ÀδÙ. ÀÎÅÚ¹®¹ýÀÇ °æ¿ì
±âº» ·¹Áö½ºÅÍ(base register)´Â '['¿Í ']'»çÀÌ¿¡ ³õÀÌÁö¸¸ AT&TÀº
'('¿Í ')'»çÀÌ¿¡ ³õÀδÙ.
표 3. ¸Þ¸ð¸® ¿ÀÆÛ·£µåÀÇ Â÷ÀÌ | Intel ¹®¹ý | AT&T ¹®¹ý | | mov eax,[ebx] | movl (%ebx),%eax | | mov eax,[ebx+3] | movl 3(%ebx),%eax |
AT&TÀÇ ¸í·É (»çÄ¢¿¬»ê°ú °°Àº)¼öÇ๮¹ýÀº ÀÎÅÚ¹®¹ý¿¡ ºñÇØ¼
¸Å¿ì º¸±âÈûµé´Ù´Â ´ÜÁ¡À» °¡Áø´Ù. ¿¹¸¦ µé¾î Intel¹®¹ý¿¡¼´Â
segreg:[base+index*scale+disp]·Î Ç¥ÇöµÇ´Â °ÍÀÌ AT&T¿¡¼´Â
%segreg:disp(base,index,scal)¿Í °°Àº ½ÄÀ¸·Î Ç¥ÇöµÈ´Ù. ¾ð¶æ ºÁµµ Á÷°üÀûÀÌÁö
¾Ê´Â Ç¥Çö¹æ½ÄÀÌ´Ù.
표 4. ¸í·É ¼öÇà ¹®¹ýÀÇ Â÷ÀÌ | Intel ¹®¹ý | AT&T ¹®¹ý | | instr foo,segreg:[base+index*scale+disp] | instr %segreg:disp(base,index,scale).foo | | mov eax,[ebx+20h] | movl 0x20(%ebx),%eax | | add eax,[ebx+ecx*2h] | addl (%ebx,%ecx,0x2),%eax | | lea eax,[ebx+ecx] | leal (%ebx,%ecx),%eax | | sub eax,[ebx+ecx*4h-20h] | subl -0x20(%ebx,%ecx,0x4),%eax |
AT&T¹®¹ýÀÇ °æ¿ì Á¤ÇØÁø Á¢¹Ì»ç±ÔÄ¢À» µû¸¥´Ù. °¢°¢ÀÇ Á¢¹Ì»ç´Â °íÀ¯ÀÇ Àǹ̸¦
°¡Áö°í ÀÖÀ¸¸ç, Á¢¹Ì»ç¿¡ µû¶ó¼ ¿ÀÆÛ·£µåÀÇ Å©±âµµ Á¤ÇØÁø´Ù. 'l'Àº long,
'w'´Â word, 'b'´Â byte¸¦ ÀúÀåÇϱâ À§Çؼ °¢°¢ »ç¿ëÇÑ´Ù. ¹Ý¸é Inten¹®¹ýÀÇ °æ¿ì
Á¢¹Ì»ç¸¦ »ç¿ëÇÏÁö ¾Ê°í ÀǹÌÀÖ´Â ¹®ÀåÀ» ±×´ë·Î »ç¿ëÇÑ´Ù. ¿¹¸¦ µé¾î byte ptr,
word ptr, dword ptr µîÀ¸·Î »ç¿ëÇÑ´Ù. "dword"´Â "long"¿Í °°Àº Å©±â¸¦ °¡Áø´Ù.
ÀÌ·¯ÇÑ AT&TÀÇ Á¢¹Ì»ç ±ÔÄ¢Àº C¹®¹ýÀÇ Ä³½ºÆÃ°ú ¸Å¿ì ºñ½ÁÇÑ ¸ð½ÀÀ» º¸¿©ÁØ´Ù.
표 5. Á¢¹Ì»ç ±ÔÄ¢ | Intel ¹®¹ý | AT&T ¹®¹ý | | mov al,bl | movb %bl,%al | | mov ax,bx | movw %bx,%ax | | mov eax,ebx | movl %ebx,%eax | | mov eax,dword ptr[ebx] | movl (%ebx),%eax |
C¹®¹ý¿¡ Àͼ÷ÇÏ´Ù¸é AT&T¹®¹ýÀÌ Á»´õ ÆíÇØ º¸Àϼöµµ ÀÖÀ» °Í °°´Ù.
À̹ø Àå¿¡¼´Â ¾î¼Àºí¸®¾î¿¡¼ ¸®´ª½º ½Ã½ºÅÛÄÝÀ» ÀÌ¿ëÇÏ´Â ¹æ¹ý¿¡ ´ëÇØ¼ ¾Ë¾Æº¸µµ·Ï
ÇϰڴÙ. ¸®´ª½º¿¡¼ Á¦°øÇϰí ÀÖ´Â ¸ðµç ½Ã½ºÅÛÄÝÀÇ ¸ñ·ÏÀº ¸®´ª½º manÆäÀÌÁöÀÇ ¼½¼Ç2¿¡¼
ã¾Æº¼ ¼ö ÀÖ´Ù. ÀÌ manÆäÀÌÁöµéÀº /usr/share/man/man2¿¡ Á¸ÀçÇϸç
°£´ÜÇÏ°Ô ls¸¦ Çѹø ÇØº¸´Â Á¤µµ·Î ¸®´ª½º¿¡¼ Á¦°øÇÏ´Â
½Ã½ºÅÛÄÝÀÇ ¸ñ·ÏÀ» ¾ò¾î¿Ã ¼ö ÀÖ´Ù. ÀÌµé ½Ã½ºÅÛÄÝÀÇ Á¤º¸´Â
/usr/incude/sys/syscall.h¿¡¼ ã¾Æº¼ ¼öµµ ÀÖ´Ù. À̿ܿ¡
¸®´ª½º ½Ã½ºÅÛ ÄÝ Á¤¸®¿¡¼
ÀÌµé ½Ã½ºÅÛÄÝ¿¡ ´ëÇÑ ¸Å¿ì ÀÚ¼¼ÇÑ Á¤º¸¸¦ ¾òÀ» ¼öÀÖ´Ù(Àû±Ø Ãßõ).
ÀÌ·¯ÇÑ ÇÔ¼öµéÀº ¸®´ª½º ÀÎÅÍ·´Æ® ¼ºñ½ºÀÎ int $0x80¸¦ ÀÌ¿ëÇØ¼
½ÇÇà ½Ãų ¼ö ÀÖ´Ù.
¸ðµç ½Ã½ºÅÛÄÝÀº ½Ã½ºÅÛÄݹøÈ£ %eax·Î ½ÃÀÛÇÑ´Ù.
½Ã½ºÅÛÄÝÀÇ ÀÎÀÚ°¡ 6º¸´Ù
ÀÛÀ»°æ¿ì °¢°¢ÀÇ ÀÎÀÚ´Â %ebx, %ecx, %esl, %edi ¼ø¼·Î ÀÔ·ÂÇÒ ¼ö ÀÖ´Ù. %eax´Â
¸®ÅϰªÀ» ÀúÀåÇϱâ À§Çؼ »ç¿ëµÈ´Ù.
½Ã½ºÅÛÄݹøÈ£´Â /usr/include/sys/syscall.h¿¡¼ ãÀ»¼ö ÀÖ´Ù. ÀÌ ¸ÞÅ©·ÎµéÀº
SYS_<syscall name>Çü½ÄÀ¸·Î Á¤ÀǵǾî ÀÖ´Ù.
¿¹¸¦µé¾î SYS_exit, SYS_closeµîÀÌ´Ù.
±×·³ Hello World¸¦ Ãâ·ÂÇÏ´Â °£´ÜÇÑ ¾î¼Àºí¸® Äڵ带 ¸¸µé¾î º¸µµ·Ï ÇÏÀÚ.
Hello World ÇÁ·Î±×·¥¿¡¼ »ç¿ëÇÏ´Â ½Ã½ºÅÛÄÝÀº SYS_write¿Í SYS_exitÀÇ 2°³´Ù.
SYS_write¸¦ »ç¿ëÇϱâ À§Çؼ´Â ¾î¶² ÀÎÀÚµéÀ» ÇÊ¿ä·Î ÇÏ´ÂÁö ¾Ë¾Æ¾ß Çϴµ¥, ÀÌ·¯ÇÑ
Á¤º¸µéÀº write(2)¿¡ ´ëÇÑ manÆäÀÌÁö¸¦ Âü°íÇÏ¸é µÈ´Ù. manÆäÀÌÁö¸¦ º¸¸é
sisze_t write(int fd, const void *buf, size_t count);·Î
¼±¾ðµÇ¾î ÀÖ´Â°É È®ÀÎÇÒ ¼ö ÀÖ´Ù. ÀÌ°É ¾î¼Àºí¸®¹æ½ÄÀ¸·Î È£ÃâÇϰíÀÚ ÇÑ´Ù¸é
ù¹øÂ° ÀÎÀÚÀÎ fd´Â %ebx·Î, buf´Â %ecx, count´Â %edx·Î SYS_write´Â %eax¿¡ ´ëÀÀµÇ°Ô
È£ÃâÇÏ¸é µÈ´Ù. ¸¶Áö¸·¿¡ $0x80À»ÀÌ¿ëÇØ¼ ½Ã½ºÅÛÄÝÀ» ½ÇÇà½ÃŰ¸é µÈ´Ù.
¸®ÅϰªÀº %eax¿¡ ÀúÀåµÈ´Ù.
¿¹Á¦ : write.s
.include "defines.h"
.data
hello:
.ascii "hello world\n"
.text
.globl _main
_main:
movl $SYS_write, %eax
movl $STDOUT,%ebx
movl $hello,%ecx
movl $12,%edx
int $0x80
movl $SYS_exit, %eax
movl $3, %ebx
int $0x80
|
À§Äڵ带 ¼º°øÀûÀ¸·Î ½ÇÇà½Ã۱â À§Çؼ´Â defines.h¶ó´Â ÆÄÀÏÀ» °¡Áö°í
ÀÖ¾î¾ß ÇÑ´Ù. ´ÙÀ½Àº defines.hÀÇ ³»¿ëÀÌ´Ù.
SYS_exit = 1
SYS_fork = 2
SYS_write = 4
SYS_open = 5
SYS_close = 6
SYS_execve = 11
SYS_lseek = 19
SYS_dup2 = 63
SYS_mmap = 90
SYS_munmap = 91
SYS_socketcall = 102
SYS_socketcall_socket = 1
SYS_socketcall_bind = 2
SYS_socketcall_listen = 4
SYS_socketcall_accept = 5
SEEK_END = 2
PROT_READ = 1
MAP_SHARED = 1
AF_INET = 2
SOCK_STREAM = 1
IPPROTO_TCP = 6
STDOUT = 1
|
°£´ÜÇÏ°Ô ½Ã½ºÅÛÄÝÀ» È£ÃâÇÏ´Â ÇÁ·Î±×·¥À» ¸¸µé¾î º¸¾Ò´Âµ¥, À§ÀÇ ¹æ½ÄÀº ÀÎÀÚ°¡ 6º¸´Ù
ÀÛÀ» ¶§¿¡¸¸ »ç¿ë°¡´ÉÇÏ´Ù.
½Ã½ºÅÛÄÝÀÇ ÀÎÀÚ°¡ 5º¸´Ù´õ Å©´õ¶óµµ ½Ã½ºÅÛÄÝ ¹øÈ£ÀÇ »ç¿ëÀº ¿©ÀüÈ÷ %eax À» ÀÌ¿ëÇÒ ¼ö
ÀÖ´Ù. ±×·¯³ª ÀÎÀÚÀÇ °æ¿ì¿¡´Â ¸Þ¸ð¸®¿¡ Áغñ(ÀúÀå)µÇ¾î ÀÖ´Â °ªµéÀ» ÀÌ¿ëÇØ¾ß ÇÑ´Ù.
¿¹¸¦ µé¾î %ebx´Â ù¹øÂ° ÀÎÀÚ¸¦ °¡¸£Å°°Ô(point)ÇÏ´Â ½ÄÀ¸·Î »ç¿ëÇÑ´Ù. 80386 CPUÀÇ
°æ¿ì ·¹Áö½ºÅÍÀÇ Å©±â´Â 32ºñÆ®À̹ǷΠ4¹ÙÀÌÆ®¾¿-4(%ebx)-Áõ°¡ ½ÃŰ´Â
¹æ½ÄÀ¸·Î ´ÙÀ½ÀÇ ÀÎÀÚ°ªÀ» °¡Á®¿Ã ¼ö ÀÖ´Ù.
À̵é ÀÎÀÚµéÀº ½ºÅÃ(stack)¿µ¿ªÀ» »ç¿ëÇÏ°Ô µÇ¹Ç·Î
ÀÎÀÚµéÀº ¹Ýµå½Ã µÚ¿¡¼ ºÎÅÍ Áý¾î ³Ö¾î¾ß ÇÑ´Ù.
Áï ù¹øÂ° ¾Æ±Ô¸ÕÆ®´Â °¡Àå ¸¶Áö¸·¿¡ µé¾î°¡°Ô µÈ´Ù.
½ºÅÃÀÇ Æ÷ÀÎÅÍ´Â %ebx·ÎºÎÅÍ º¹»çµÈ´Ù.
´ÙÀ½Àº mmap()À» ÀÌ¿ëÇÏ´Â CÄÚµå´Ù.
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/mman.h>
#include <fcntl.h>
#include <unistd.h>
#define STDOUT 1
int main()
{
char *file="mmap.s";
char *mappedptr;
int fd,filelen;
if ((fd=open(file, O_RDONLY)) < 0)
{
write(1, "error\n",6);
exit(0);
}
if ((filelen=lseek(fd,0,SEEK_END)) == -1)
{
perror("seek error");
exit(0);
}
printf("%d\n", filelen);
mappedptr=mmap(NULL,filelen,PROT_READ,MAP_SHARED,fd,0);
write(STDOUT, mappedptr, filelen);
munmap(mappedptr, filelen);
close(fd);
}
|
ÀÌ ÇÁ·Î±×·¥Àº mmap.s ÆÄÀÏÀÇ ³»¿ëÀ» Ãâ·ÂÇÑ´Ù. À§ÀÇ ÇÁ·Î±×·¥¿¡¼ º¸¸é
mmap(2)´Â 6°³ÀÇ ÀÎÀÚ¸¦ ÇÊ¿ä·Î ÇÑ´Ù. À̵é ÀÎÀÚ´Â ¸Þ¸ð¸® »ó¿¡ ´ÙÀ½°ú °°ÀÌ
À§Ä¡ÇÏ°Ô µÈ´Ù.
표 6. Á¢µÎ»ç ±ÔÄ¢À» Àû¿ëÇÑ ¿¹ | %esp | 00000000 | | %esp+4 | filelen | | %esp+4 | filelen |
´ÙÀ½Àº mmap.c ÄÚµåÀÇ ¾î¼Àºí¸® ¹öÁ¯ÀÌ´Ù.
¿¹Á¦ : mmap.s
/* mmap.s */
.include "defines.h"
.data
fd:
.long 0
fdlen:
.long 0
mappedptr:
.long 0
.text
.globl _start
_start:
subl $24,%esp
# open(file, O_RDONLY);
movl $SYS_open,%eax
movl 32(%esp),%ebx # argv[1]À» °¡Á®¿Â´Ù. (%esp+8+24)
xorl %ecx,%ecx # O_RDONLY·Î ¼³Á¤ÇÑ´Ù.
int $0x80
test %eax,%eax # ¸®ÅϰªÀ» °Ë»çÇØ¼ <0 À̸é Á¾·áÇÑ´Ù.
js exit
movl %eax,fd # open¼º°øÇß´Ù¸é ¸®ÅϰªÀ» fd¿¡ ÀúÀåÇÑ´Ù.
# lseek(fd,0,SEEK_END);
movl %eax,%ebx # fd¸¦ ù¹øÂ° ÀÎÀÚ·Î
xorl %ecx,%ecx # offsetÀ» 0À¸·Î
movl $SEEK_END,%edx
movl $SYS_lseek,%eax
int $0x80
movl %eax,fdlen # ¸®Åϰª(ÆÄÀϱæÀÌ)¸¦ ÀúÀåÇÑ´Ù.
xorl %edx,%edx
# mmap(NULL,fdlen,PROT_READ,MAP_SHARED,fd,0);
movl %edx,(%esp)
movl %eax,4(%esp)
movl $PROT_READ,8(%esp)
movl $MAP_SHARED,12(%esp)
movl fd,%eax
movl %eax,16(%esp)
movl %edx,20(%esp)
movl $SYS_mmap,%eax
movl %esp,%ebx
int $0x80
movl %eax,mappedptr # save ptr
# write(STDOUT, mappedptr, fdlen);
movl $STDOUT,%ebx
movl %eax,%ecx
movl fdlen,%edx
movl $SYS_write,%eax
int $0x80
# munmap(mappedptr, fdlen);
movl mappedptr,%ebx
movl fdlen,%ecx
movl $SYS_munmap,%eax
int $0x80
# close(fd);
movl fd,%ebx # load file descriptor
movl $SYS_close,%eax
int $0x80
exit:
# exit(0);
movl $SYS_exit,%eax
xorl %ebx,%ebx
int $0x80
ret
|
¸í·ÉÇà ÀÎÀÚ´Â ¸®´ª½º¿¡¼ ½ºÅÿ¡ ÀúÀåµÈ´Ù. argc°¡ °¡Àå¸ÕÀú¿À°í ±×µÚ¿¡ Æ÷ÀÎÅÍÀÇ
¹è¿ ÇüÅÂ(**argv)·Î ÀúÀåµÈ´Ù. ±×´ÙÀ½¿¡´Â ȯ°æº¯¼ö°¡ ¿À´Âµ¥ argv¿Í ¸¶Âù°¡Áö·Î
Æ÷ÀÎÅÍÀÇ ¹è¿(**envp)·Î ÀúÀåµÈ´Ù.
À̹ø Àå¿¡¼´Â GCC¿¡¼ ÀζóÀÎ ¾î¼Àºí¸®(ÀÌÇÏ ÀζóÀÎ ¾î¼À)¸¦ ÀÌ¿ëÇØ¼ X86 ¾ÖÇø®ÄÉÀ̼ÇÀ» ÀÛ¼ºÇÏ´Â
¹æ¹ý¿¡ ´ëÇØ¼ ¾Ë¾Æº¸°Ú´Ù.
gcc¿¡¼ÀÇ ÀζóÀÎ ¾î¼Àºí¸®»ç¿ëÀº ¸Å¿ì Á÷°üÀûÀÌ´Ù. ´ÙÀ½Àº ÀζóÀÎ ¾î¼Àºí¸®ÀÇ
ÀϹÝÀûÀÎ ¸ð½ÀÀÌ´Ù.
__asm__(movl %esp,%eax");
¶Ç´Â
__asm__("
movl $1,%eax // SYS_exit
xor %ebx,%ebx
int $0x80
");
|
±âº»ÀûÀ¸·Î C¿Í ¾î¼Àºí¸®´Â ¸Å¿ì ´Ù¸¥ ÀÎÅÍÆäÀ̽º¸¦ °¡Áø´Ù. ±×·¯¹Ç·Î C¿Í ÀζóÀÎ ¾î¼À°£ÀÇ
µ¥ÀÌÅÍ ±³È¯À» µµ¿ÍÁÖ´Â ÀÎÅÍÆäÀ̽º¸¦ ÇÊ¿ä·Î ÇÑ´Ù. gcc´Â
input/output/modify¸¦ ÀÌ¿ëÇØ¼ µ¥ÀÌÅ͸¦ ±³È¯ÇÒ ¼ö ÀÖ´Ù.
À̰ÍÀº ´ÙÀ½°ú °°Àº Çü½ÄÀ» °¡Áø´Ù.
__asm__("<asm routine>": output : input : modify);
|
output°ú inputÀº ¹Ýµå½Ã Á¸ÀçÇØ¾ß Çϸç C¿Í µ¥ÀÌÅ͸¦ ±³È¯Çϱâ À§Çؼ »ç¿ëµÈ´Ù.
output ¿ÀÆÛ·£µåÀÇ °ªÀ» ¹Ù±ùÀ¸·Î ÀúÀåÇϱâ À§Çؼ´Â '='¸¦ ÀÌ¿ëÇØ¼ Ãâ·ÂÀÌ
ÀÌ·ç¾îÁú °÷À» ¸í½ÃÇØÁÖ¾î¾ß ÇÑ´Ù.
¿©±â¿¡´Â ´ÙÁß(multiple) outputs, inputs, modified ·¹Áö½ºÅ͸¦ »ç¿ë°¡´ÉÇÏ´Ù. °¢°¢ÀÇ "entry"´Â
','·Î ±¸ºÐµÇ¸ç 10°³ ÀÌ»óÀÇ entry´Â »ç¿ëÇÒ ¼ö ¾ø´Ù. ¿ÀÆÛ·£µå¿¡ »ç¿ëµÉ ¹®ÀÚ´Â
¿ÏÀüÇÑ ·¹Áö½ºÅÍÀ̸§À» »ç¿ëÇØµµ µÇ°í, ÀÌ°Ô ±ÍÂú´Ù¸é ´ÙÀ½°ú °°Àº °£´ÜÇÑ ´ÜÀÏ ¹®Àڷεµ
»ç¿ëÇÒ ¼ö ÀÖ´Ù.
표 7. inline¿¡¼ÀÇ ·¹Áö½ºÅÍÀ̸§ | ÁÙÀÓ¸» | ·¹Áö½ºÅÍÀ̸§ | | a | %eax/%ax/%al | | b | %ebx/%bx/%bl | | c | %ecx/%cx/%cl | | d | %edx/%dx/%dl | | S | %esx/%sx/%sl | | D | %edi/%di | | m | memory |
´ÙÀ½Àº °£´ÜÇÑ ¿¹´Ù.
__asm__("test %%eax,%%eax" : /* no output */ : "a"(foo));
¶Ç´Â
__asm__("test %%eax,%%eax" : /* no output */ : "eax"(foo));
|
#include <stdio.h>
int main(int argc, char **argv)
{
int foo=10, bar=15;
__asm__ __volatile__("test %%eax,%%eax" : :"a"(foo));
__asm__ __volatile__("addl %%ebx,%%eax\n\t":"=a"(foo):"a"(foo), "b"(bar));
printf("foo + bar = %d\n", foo);
return 0;
}
|
À§ÀÇ ¿¹Á¦¸¦ º¸¸é ·¹Áö½ºÅÍÀÇ Á¢µÎ»ç·Î '%'´ë½Å "%%"¸¦ »ç¿ëÇϰí ÀÖÀ½À» ¾Ë ¼ö ÀÖ´Ù.
Input/Output/Modify clubber°¡ ÀÖÀ»¶§´Â %%¸¦
»ç¿ëÇÏ°í ±×·¸Áö ¾ÊÀ¸¸é %¸¦ »ç¿ëÇÑ´Ù.
¶ÇÇÑ __asm__°ú ÇÔ²² __volatile__ Ű¿öµå¸¦ »ç¿ëÇÒ¼ö Àִµ¥, À̰ÍÀ» »ç¿ëÇϸé
¾î¼Àºí¸® ¸í·ÉÀÌ »èÁ¦µÇ°Å³ª, À̵¿µÇ°Å³ª È¥ÇյǴ °æ¿ì¸¦ ¹æÁöÇÒ ¼ö ÀÖ´Ù.
±×¸®°í "eax", "ax", "al" ´ë½Å °£´ÜÇÏ°Ô "a"¸¦ »ç¿ëÇϰí ÀÖÀ½À» ÁÖ¸ñÇϱ⠹ٶõ´Ù. À̰ÍÀº
´Ù¸¥ ·¹Áö½ºÅÍ¿¡µµ µ¿ÀÏÇÏ°Ô Àû¿ëµÈ´Ù. ¿©±â¿¡ ´õºÒ¾î gcc´Â %0¿¡¼ %9±îÁö »ç¿ë°¡´ÉÇÑ
·¹Áö½ºÅÍ º°ÄªÀ» Á¦°øÇÑ´Ù.
#include <stdio.h>
int main()
{
long eax;
short bx;
char cl;
__asm__("nop;nop;nop");
__asm__ __volatile__
(
"test %0,%0
test %1,%1
test %2,%2"
: /* no outputs */
: "a"((long)eax), "b"((short)bx), "c"((char)cl)
);
__asm__("nop;nop;nop");
return 0;
}
|
À§ÀÇ Äڵ带 ÄÄÆÄÀÏÇÑÈÄ gdb¸¦ ÀÌ¿ëÇØ¼ disassemble¸¦ ÇØº¸µµ·Ï ÇÏÀÚ.
# gcc -o inline2 inline2.c
# gdb ./inline2
[root@localhost root]# !gd
gdb ./inline2
GNU gdb Red Hat Linux (5.2.1-4)
Copyright 2002 Free Software Foundation, Inc.
GDB is free software, covered by the GNU General Public License, and you are
welcome to change it and/or distribute copies of it under certain conditions.
Type "show copying" to see the conditions.
There is absolutely no warranty for GDB. Type "show warranty" for details.
This GDB was configured as "i386-redhat-linux"...
(gdb) disassemble main
Dump of assembler code for function main:
0x80482f4 <main>: push %ebp
0x80482f5 <main+1>: mov %esp,%ebp
0x80482f7 <main+3>: push %ebx
0x80482f8 <main+4>: sub $0x14,%esp
0x80482fb <main+7>: and $0xfffffff0,%esp
0x80482fe <main+10>: mov $0x0,%eax
0x8048303 <main+15>: sub %eax,%esp
0x8048305 <main+17>: nop
0x8048306 <main+18>: nop
0x8048307 <main+19>: nop
0x8048308 <main+20>: mov 0xfffffff8(%ebp),%eax
0x804830b <main+23>: mov 0xfffffff6(%ebp),%bx
0x804830f <main+27>: mov 0xfffffff5(%ebp),%cl
0x8048312 <main+30>: test %eax,%eax
0x8048314 <main+32>: test %bx,%bx
0x8048317 <main+35>: test %cl,%cl
0x8048319 <main+37>: nop
0x804831a <main+38>: nop
0x804831b <main+39>: nop
...
|
À§ÀÇ °á°ú¸¦ º¸¸é ÀζóÀÎ ¾î¼ÀÀ¸·Î ºÎÅÍ Äڵ尡 »ý¼ºµÉ¶§
ÄÄÆÄÀÏ·¯°¡ ÀÚµ¿ÀûÀ¸·Î ¿ÀÆÛ·£µåÀÇ Å©±â¸¦ ã¾Æ³»¼
%0, %1, %2¿¡ ´ëÀÀµÇ´Â ·¹Áö½ºÅÍ·Î ´ëÀÀ½Ã۰í ÀÖÀ½À» ¾Ë ¼ö ÀÖ´Ù.
¾î¼Àºí¸® ¾î·ÎµÈ ÇÁ·Î±×·¥À» ÄÄÆÄÀÏÇÏ´Â °ÍÀº ÀϹÝÀûÀÎ CÇÁ·Î±×·¥À» ÄÄÆÄÀÏÇÏ´Â °Í°ú
ºñ½ÁÇÏ´Ù. ÄÄÆÄÀÏÀº ¾Æ·¡¿Í °°ÀÌ 2°¡Áö ¹æ¹ýÀ¸·Î °¡´ÉÇÏ´Ù. 1¹ø ¹æ¹ýó·³
C ÇÁ·Î±×·¥°ú ºñ½ÁÇÏ°Ô ¸¸µé¼öµµ ÀÖ°í, main´ë½Å _start¸¦ ½á¼ ÄÄÆÄÀÏÇÒ ¼öµµ
ÀÖ´Ù. ´ÜÁö main¿Í _start¸¸ ¹Ù²åÀ» »ÓÀ̶ó°í »ý°¢ÇϰÚÁö¸¸ ÄÄÆÄÀϹæ¹ý°ú
ÄÄÆÄÀÏÇÑ °á°ú¿¡ À־ ¾à°£ÀÇ Â÷À̸¦ °¡Áø´Ù.
# cat write.s
.include "defines.h"
.data
hw:
.string "hello world\n"
.text
.global main
main:
movl $SYS_write,%eax
movl $1,%ebx
movl $hw,%ecx
movl $12,%edx
int $0x80
movl $SYS_exit,%eax
xorl %ebx,%ebx
int $0x80
ret
# gcc -o write write.s
# wc -c ./write
11822 ./write
# strip ./write
# wc -c ./write
2580 ./write
|
# cat write.s
.include "defines.h"
.data
hw:
.string "hello world\n"
.text
.global _start
_start:
movl $SYS_write,%eax
movl $1,%ebx
movl $hw,%ecx
movl $12,%edx
int $0x80
movl $SYS_exit,%eax
xorl %ebx,%ebx
int $0x80
# gcc -c write2.s
# ld -s -o write write.o
# wc -c ./write
392 ./write
|
-s´Â ¿É¼ÇÀ¸·Î ELF½ÇÇàÆÄÀÏÀ» strip½ÃŲ »óÅ·Π»ý¼ºÇÑ´Ù. -s¿É¼ÇÀ»
ÁÖÁö ¾ÊÀ»°æ¿ì ½ÇÇàÆÄÀÏÀÇ Å©±â°¡ »ó´çÈ÷ Ä¿Áø´Ù. 1¹ø°ú 2¹ø ¸ðµÎ ºñ½ÁÇÑ ÄÚµåÀÌÁö¸¸
2¹ø ÄÚµåÀÇ °æ¿ì ½ÇÇàÆÄÀÏÀÇ Å©±â°¡ ȹ±âÀûÀ¸·Î ÀÛ¾ÆÁ® ÀÖÀ½À» È®ÀÎÇÒ ¼ö ÀÖ´Ù.
Cache Error
|
|