亚洲欧美第一页_禁久久精品乱码_粉嫩av一区二区三区免费野_久草精品视频

? 歡迎來到蟲蟲下載站! | ?? 資源下載 ?? 資源專輯 ?? 關于我們
? 蟲蟲下載站

?? exception.txt

?? 《嵌入式系統設計與實例開發實驗教材二源碼》Linux內核移植與編譯實驗
?? TXT
字號:
     Kernel level exception handling in Linux 2.1.8  Commentary by Joerg Pommnitz <joerg@raleigh.ibm.com>When a process runs in kernel mode, it often has to access user mode memory whose address has been passed by an untrusted program. To protect itself the kernel has to verify this address.In older versions of Linux this was done with the int verify_area(int type, const void * addr, unsigned long size) function.This function verified that the memory area starting at address addr and of size size was accessible for the operation specified in type (read or write). To do this, verify_read had to look up the virtual memory area (vma) that contained the address addr. In the normal case (correctly working program), this test was successful. It only failed for a few buggy programs. In some kernel profilingtests, this normally unneeded verification used up a considerableamount of time.To overcome this situation, Linus decided to let the virtual memory hardware present in every Linux-capable CPU handle this test.How does this work?Whenever the kernel tries to access an address that is currently not accessible, the CPU generates a page fault exception and calls the page fault handler void do_page_fault(struct pt_regs *regs, unsigned long error_code)in arch/i386/mm/fault.c. The parameters on the stack are set up by the low level assembly glue in arch/i386/kernel/entry.S. The parameterregs is a pointer to the saved registers on the stack, error_code contains a reason code for the exception.do_page_fault first obtains the unaccessible address from the CPU control register CR2. If the address is within the virtual address space of the process, the fault probably occurred, because the page was not swapped in, write protected or something similar. However, we are interested in the other case: the address is not valid, there is no vma that contains this address. In this case, the kernel jumps to the bad_area label. There it uses the address of the instruction that caused the exception (i.e. regs->eip) to find an address where the execution can continue (fixup). If this search is successful, the fault handler modifies the return address (again regs->eip) and returns. The execution will continue at the address in fixup.Where does fixup point to?Since we jump to the contents of fixup, fixup obviously points to executable code. This code is hidden inside the user access macros. I have picked the get_user macro defined in include/asm/uaccess.h as anexample. The definition is somewhat hard to follow, so let's peek at the code generated by the preprocessor and the compiler. I selectedthe get_user call in drivers/char/console.c for a detailed examination.The original code in console.c line 1405:        get_user(c, buf);The preprocessor output (edited to become somewhat readable):(  {            long __gu_err = - 14 , __gu_val = 0;            const __typeof__(*( (  buf ) )) *__gu_addr = ((buf));            if (((((0 + current_set[0])->tss.segment) == 0x18 )  ||        (((sizeof(*(buf))) <= 0xC0000000UL) &&        ((unsigned long)(__gu_addr ) <= 0xC0000000UL - (sizeof(*(buf)))))))              do {        __gu_err  = 0;                switch ((sizeof(*(buf)))) {                  case 1:             __asm__ __volatile__(                      "1:      mov" "b" " %2,%" "b" "1\n"                      "2:\n"                      ".section .fixup,\"ax\"\n"                      "3:      movl %3,%0\n"                      "        xor" "b" " %" "b" "1,%" "b" "1\n"                      "        jmp 2b\n"                      ".section __ex_table,\"a\"\n"                      "        .align 4\n"                      "        .long 1b,3b\n"                      ".text"        : "=r"(__gu_err), "=q" (__gu_val): "m"((*(struct __large_struct *)                            (   __gu_addr   )) ), "i"(- 14 ), "0"(  __gu_err  )) ;               break;                  case 2:             __asm__ __volatile__(              "1:      mov" "w" " %2,%" "w" "1\n"                      "2:\n"                      ".section .fixup,\"ax\"\n"                      "3:      movl %3,%0\n"                      "        xor" "w" " %" "w" "1,%" "w" "1\n"                      "        jmp 2b\n"                      ".section __ex_table,\"a\"\n"                      "        .align 4\n"                      "        .long 1b,3b\n"                      ".text"        : "=r"(__gu_err), "=r" (__gu_val) : "m"((*(struct __large_struct *)                            (   __gu_addr   )) ), "i"(- 14 ), "0"(  __gu_err  ));               break;                  case 4:             __asm__ __volatile__(                      "1:      mov" "l" " %2,%" "" "1\n"                      "2:\n"                      ".section .fixup,\"ax\"\n"                      "3:      movl %3,%0\n"                      "        xor" "l" " %" "" "1,%" "" "1\n"                      "        jmp 2b\n"                      ".section __ex_table,\"a\"\n"                      "        .align 4\n"        "        .long 1b,3b\n"                      ".text"        : "=r"(__gu_err), "=r" (__gu_val) : "m"((*(struct __large_struct *)                            (   __gu_addr   )) ), "i"(- 14 ), "0"(__gu_err));               break;                  default:             (__gu_val) = __get_user_bad();                }              } while (0) ;            ((c)) = (__typeof__(*((buf))))__gu_val;            __gu_err;  });WOW! Black GCC/assembly magic. This is impossible to follow, so let'ssee what code gcc generates: >         xorl %edx,%edx >         movl current_set,%eax >         cmpl $24,788(%eax)         >         je .L1424         >         cmpl $-1073741825,64(%esp) >         ja .L1423                 > .L1424: >         movl %edx,%eax                         >         movl 64(%esp),%ebx > #APP > 1:      movb (%ebx),%dl                /* this is the actual user access */ > 2: > .section .fixup,"ax" > 3:      movl $-14,%eax >         xorb %dl,%dl >         jmp 2b > .section __ex_table,"a" >         .align 4 >         .long 1b,3b > .text > #NO_APP > .L1423: >         movzbl %dl,%esiThe optimizer does a good job and gives us something we can actually understand. Can we? The actual user access is quite obvious. Thanks to the unified address space we can just access the address in user memory. But what does the .section stuff do?????To understand this we have to look at the final kernel: > objdump --section-headers vmlinux >  > vmlinux:     file format elf32-i386 >  > Sections: > Idx Name          Size      VMA       LMA       File off  Algn >   0 .text         00098f40  c0100000  c0100000  00001000  2**4 >                   CONTENTS, ALLOC, LOAD, READONLY, CODE >   1 .fixup        000016bc  c0198f40  c0198f40  00099f40  2**0 >                   CONTENTS, ALLOC, LOAD, READONLY, CODE >   2 .rodata       0000f127  c019a5fc  c019a5fc  0009b5fc  2**2 >                   CONTENTS, ALLOC, LOAD, READONLY, DATA >   3 __ex_table    000015c0  c01a9724  c01a9724  000aa724  2**2 >                   CONTENTS, ALLOC, LOAD, READONLY, DATA >   4 .data         0000ea58  c01abcf0  c01abcf0  000abcf0  2**4 >                   CONTENTS, ALLOC, LOAD, DATA >   5 .bss          00018e21  c01ba748  c01ba748  000ba748  2**2 >                   ALLOC >   6 .comment      00000ec4  00000000  00000000  000ba748  2**0 >                   CONTENTS, READONLY >   7 .note         00001068  00000ec4  00000ec4  000bb60c  2**0 >                   CONTENTS, READONLYThere are obviously 2 non standard ELF sections in the generated objectfile. But first we want to find out what happened to our code in thefinal kernel executable: > objdump --disassemble --section=.text vmlinux > > c017e785 <do_con_write+c1> xorl   %edx,%edx > c017e787 <do_con_write+c3> movl   0xc01c7bec,%eax > c017e78c <do_con_write+c8> cmpl   $0x18,0x314(%eax) > c017e793 <do_con_write+cf> je     c017e79f <do_con_write+db> > c017e795 <do_con_write+d1> cmpl   $0xbfffffff,0x40(%esp,1) > c017e79d <do_con_write+d9> ja     c017e7a7 <do_con_write+e3> > c017e79f <do_con_write+db> movl   %edx,%eax > c017e7a1 <do_con_write+dd> movl   0x40(%esp,1),%ebx > c017e7a5 <do_con_write+e1> movb   (%ebx),%dl > c017e7a7 <do_con_write+e3> movzbl %dl,%esiThe whole user memory access is reduced to 10 x86 machine instructions.The instructions bracketed in the .section directives are no longerin the normal execution path. They are located in a different section of the executable file: > objdump --disassemble --section=.fixup vmlinux >  > c0199ff5 <.fixup+10b5> movl   $0xfffffff2,%eax > c0199ffa <.fixup+10ba> xorb   %dl,%dl > c0199ffc <.fixup+10bc> jmp    c017e7a7 <do_con_write+e3>And finally: > objdump --full-contents --section=__ex_table vmlinux >  >  c01aa7c4 93c017c0 e09f19c0 97c017c0 99c017c0  ................ >  c01aa7d4 f6c217c0 e99f19c0 a5e717c0 f59f19c0  ................ >  c01aa7e4 080a18c0 01a019c0 0a0a18c0 04a019c0  ................or in human readable byte order: >  c01aa7c4 c017c093 c0199fe0 c017c097 c017c099  ................ >  c01aa7d4 c017c2f6 c0199fe9 c017e7a5 c0199ff5  ................                               ^^^^^^^^^^^^^^^^^                               this is the interesting part! >  c01aa7e4 c0180a08 c019a001 c0180a0a c019a004  ................What happened? The assembly directives.section .fixup,"ax".section __ex_table,"a"told the assembler to move the following code to the specifiedsections in the ELF object file. So the instructions3:      movl $-14,%eax        xorb %dl,%dl        jmp 2bended up in the .fixup section of the object file and the addresses        .long 1b,3bended up in the __ex_table section of the object file. 1b and 3bare local labels. The local label 1b (1b stands for next label 1 backward) is the address of the instruction that might fault, i.e. in our case the address of the label 1 is c017e7a5:the original assembly code: > 1:      movb (%ebx),%dland linked in vmlinux     : > c017e7a5 <do_con_write+e1> movb   (%ebx),%dlThe local label 3 (backwards again) is the address of the code to handlethe fault, in our case the actual value is c0199ff5:the original assembly code: > 3:      movl $-14,%eaxand linked in vmlinux     : > c0199ff5 <.fixup+10b5> movl   $0xfffffff2,%eaxThe assembly code > .section __ex_table,"a" >         .align 4 >         .long 1b,3bbecomes the value pair >  c01aa7d4 c017c2f6 c0199fe9 c017e7a5 c0199ff5  ................                               ^this is ^this is                               1b       3b c017e7a5,c0199ff5 in the exception table of the kernel.So, what actually happens if a fault from kernel mode with no suitablevma occurs?1.) access to invalid address: > c017e7a5 <do_con_write+e1> movb   (%ebx),%dl2.) MMU generates exception3.) CPU calls do_page_fault4.) do page fault calls search_exception_table (regs->eip == c017e7a5);5.) search_exception_table looks up the address c017e7a5 in the    exception table (i.e. the contents of the ELF section __ex_table)     and returns the address of the associated fault handle code c0199ff5.6.) do_page_fault modifies its own return address to point to the fault     handle code and returns.7.) execution continues in the fault handling code.8.) 8a) EAX becomes -EFAULT (== -14)    8b) DL  becomes zero (the value we "read" from user space)    8c) execution continues at local label 2 (address of the        instruction immediately after the faulting user access).The steps 8a to 8c in a certain way emulate the faulting instruction.That's it, mostly. If you look at our example, you might ask whywe set EAX to -EFAULT in the exception handler code. Well, theget_user macro actually returns a value: 0, if the user access wassuccessful, -EFAULT on failure. Our original code did not test thisreturn value, however the inline assembly code in get_user tries toreturn -EFAULT. GCC selected EAX to return this value.NOTE:Due to the way that the exception table is built and needs to be ordered,only use exceptions for code in the .text section.  Any other sectionwill cause the exception table to not be sorted correctly, and theexceptions will fail.

?? 快捷鍵說明

復制代碼 Ctrl + C
搜索代碼 Ctrl + F
全屏模式 F11
切換主題 Ctrl + Shift + D
顯示快捷鍵 ?
增大字號 Ctrl + =
減小字號 Ctrl + -
亚洲欧美第一页_禁久久精品乱码_粉嫩av一区二区三区免费野_久草精品视频
国产人久久人人人人爽| 久久精品一二三| 日韩一区二区电影网| 国产精品私人自拍| 看电影不卡的网站| 日本久久一区二区三区| 精品国产不卡一区二区三区| 亚洲日本va午夜在线影院| 韩国在线一区二区| 91精品国产免费| 日韩中文字幕亚洲一区二区va在线| 成人黄色在线视频| 日韩精品中文字幕一区二区三区 | 国产**成人网毛片九色| 91精品国产麻豆国产自产在线| 亚洲天堂成人在线观看| 国产精品主播直播| 欧美mv和日韩mv的网站| 日本美女一区二区| 欧美三级中文字幕| 一片黄亚洲嫩模| 色一情一乱一乱一91av| 国产精品进线69影院| 国产美女娇喘av呻吟久久| 欧美成人a视频| 日本女人一区二区三区| 欧美美女视频在线观看| 亚洲自拍偷拍综合| 欧美在线|欧美| 亚洲一区二区三区视频在线 | 亚洲欧美另类图片小说| 91亚洲精华国产精华精华液| 中文字幕亚洲一区二区av在线| 国产剧情av麻豆香蕉精品| 久久精品男人天堂av| 成人高清视频免费观看| 国产精品久久久久久久久久久免费看 | 99re这里只有精品6| 成人欧美一区二区三区白人| 99精品1区2区| 亚洲一区二区三区四区中文字幕| 色婷婷综合视频在线观看| 亚洲另类一区二区| 欧美日韩性生活| 麻豆精品一二三| 亚洲精品一线二线三线| 福利一区二区在线观看| 成人免费在线播放视频| 在线观看网站黄不卡| 午夜精品在线视频一区| 日韩免费一区二区三区在线播放| 韩国精品主播一区二区在线观看| 久久夜色精品国产欧美乱极品| 国产不卡视频在线播放| 亚洲自拍另类综合| 91精品国产美女浴室洗澡无遮挡| 国内成人自拍视频| 亚洲精品日韩一| 精品国精品国产| 9色porny自拍视频一区二区| 亚洲国产sm捆绑调教视频 | 欧美高清在线精品一区| 91久久精品网| 久久草av在线| 一区二区三区影院| 精品乱码亚洲一区二区不卡| av激情成人网| 欧美a一区二区| 亚洲欧美激情小说另类| 日韩精品一区二区三区四区| 暴力调教一区二区三区| 日韩精品电影在线| 亚洲欧美另类小说| 久久婷婷久久一区二区三区| 日本久久一区二区| 丁香亚洲综合激情啪啪综合| 午夜日韩在线观看| 亚洲丝袜精品丝袜在线| 日韩视频在线观看一区二区| 色综合天天综合| 精品在线免费视频| 亚洲福利国产精品| 中文字幕亚洲区| 久久午夜免费电影| 欧美肥妇free| 在线观看av不卡| 成人白浆超碰人人人人| 久久www免费人成看片高清| 亚洲va欧美va天堂v国产综合| 国产日韩欧美高清| 日韩欧美一二三四区| 欧美日韩精品综合在线| 色综合久久久久综合体| 成人黄色综合网站| 国产精品99久久久久久久女警| 日韩va欧美va亚洲va久久| 亚洲一区免费视频| 亚洲色图色小说| 亚洲三级电影全部在线观看高清| 久久久国际精品| 26uuu国产在线精品一区二区| 这里只有精品免费| 欧美日韩国产影片| 欧美日本国产一区| 欧美在线观看你懂的| 欧美综合在线视频| 欧美亚洲动漫精品| 色综合色狠狠综合色| 99久久免费国产| 91麻豆国产在线观看| av毛片久久久久**hd| 91在线视频官网| 91在线porny国产在线看| 成人av在线网| 99久久精品国产一区二区三区| 国产·精品毛片| av在线不卡网| 欧美亚洲动漫精品| 欧美精品亚洲二区| 欧美电影免费提供在线观看| 日韩欧美激情在线| 欧美精品一区视频| 国产精品免费av| 亚洲色图自拍偷拍美腿丝袜制服诱惑麻豆 | 最新国产精品久久精品| 中文字幕一区二区在线观看| 国产精品久久久久婷婷| 亚洲欧美激情一区二区| 性做久久久久久免费观看欧美| 婷婷亚洲久悠悠色悠在线播放| 日韩va欧美va亚洲va久久| 国产主播一区二区三区| 岛国av在线一区| 91日韩精品一区| 在线播放91灌醉迷j高跟美女| 精品女同一区二区| 日韩毛片在线免费观看| 天天色天天爱天天射综合| 老色鬼精品视频在线观看播放| 国产盗摄女厕一区二区三区| 91玉足脚交白嫩脚丫在线播放| 欧美日韩一区二区三区高清| 日韩一二三四区| 国产精品萝li| 日韩精品成人一区二区三区| 狠狠色狠狠色综合日日91app| av一二三不卡影片| 欧美三级日韩在线| www久久久久| 亚洲国产成人porn| 国产成人无遮挡在线视频| 91精彩视频在线观看| 精品国一区二区三区| 亚洲丝袜制服诱惑| 国产在线播放一区二区三区| 日本久久精品电影| 久久九九久久九九| 亚洲成人动漫av| 波多野结衣一区二区三区| 日韩欧美亚洲国产另类| 最新国产の精品合集bt伙计| 久久国产夜色精品鲁鲁99| 91国偷自产一区二区开放时间| 久久久久久久久岛国免费| 图片区日韩欧美亚洲| 成人av资源在线| 久久日韩粉嫩一区二区三区| 亚洲成年人影院| 97se亚洲国产综合在线| 337p日本欧洲亚洲大胆精品| 亚洲一级二级三级| 91一区一区三区| 久久精品一区蜜桃臀影院| 日韩成人一级片| 欧美日韩一区二区三区在线看| 中文字幕欧美激情| 九色综合国产一区二区三区| 欧美在线观看18| 亚洲美腿欧美偷拍| 成人免费视频播放| 久久蜜桃香蕉精品一区二区三区| 图片区小说区国产精品视频 | 国产成人综合视频| 欧美成人官网二区| 老汉av免费一区二区三区| 欧美日韩高清一区| 亚洲一级在线观看| 91黄色免费网站| 亚洲综合区在线| 色婷婷久久久久swag精品| 国产精品短视频| 成人a区在线观看| 国产精品麻豆99久久久久久| 国产河南妇女毛片精品久久久| 精品盗摄一区二区三区| 老司机午夜精品| 久久女同性恋中文字幕| 久久精品国产亚洲高清剧情介绍 | 欧美精品久久一区二区三区| 亚洲国产日日夜夜|