{"id":332,"date":"2012-05-16T00:50:38","date_gmt":"2012-05-15T22:50:38","guid":{"rendered":"http:\/\/blog.pi3.com.pl\/?p=332"},"modified":"2012-05-17T00:50:42","modified_gmt":"2012-05-16T22:50:42","slug":"the-story-of-the-linux-kernel-3-x","status":"publish","type":"post","link":"https:\/\/blog.pi3.com.pl\/?p=332","title":{"rendered":"[UPDATE] The story of the Linux kernel 3.x&#8230;"},"content":{"rendered":"<p>The story of the Linux kernel 3.x&#8230;<\/p>\n<p>In 2005 everybody was exited about possibility of bypass ASLR on all Linux 2.6 kernels because of the new concept called VDSO (Virtual Dynamic Shared Object). More information about this story can be found at the following link:<\/p>\n<p><a href=\"http:\/\/www.trilithium.com\/johan\/2005\/08\/linux-gate\/\" target=\"_blank\">http:\/\/www.trilithium.com\/johan\/2005\/08\/linux-gate\/<\/a><\/p>\n<p>&nbsp;<\/p>\n<p>In short, VDSO was mmap&#8217;ed by the kernel in the user space memory always at the same fixed address. Because of that well-known technique ret-to-libc (or as some ppl prefer ROP) was possible and effective to bypass existing security mitigation in the system.<\/p>\n<p>&#8230; 6 years later Linus Torvalds announced the release of the new kernel version &#8211; 3.x! Now, guess what happened&#8230;<\/p>\n<pre>pi3-darkstar new # uname -r\r\n3.2.12-gentoo\r\npi3-darkstar new # cat \/proc\/sys\/kernel\/randomize_va_space\r\n2\r\npi3-darkstar new # cat \/proc\/self\/maps|tail -2\r\nbfa81000-bfaa2000 rw-p 00000000 00:00 0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 [stack]\r\nffffe000-fffff000 r-xp 00000000 00:00 0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 [vdso]\r\npi3-darkstar new # cat \/proc\/self\/maps|tail -2\r\nbfd5e000-bfd7f000 rw-p 00000000 00:00 0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 [stack]\r\nffffe000-fffff000 r-xp 00000000 00:00 0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 [vdso]\r\npi3-darkstar new # ldd \/bin\/ls|head -1\r\n\u00a0\u00a0 \u00a0linux-gate.so.1 =&gt;\u00a0 (0xffffe000)\r\npi3-darkstar new # ldd \/bin\/ls|head -1\r\n\u00a0\u00a0 \u00a0linux-gate.so.1 =&gt;\u00a0 (0xffffe000)\r\npi3-darkstar new #<\/pre>\n<p>&nbsp;<\/p>\n<p>I&#8217;m not using<br \/>\n<em> dd if=\/proc\/self\/mem of=linux-gate.dso bs=4096 skip=1048574 count=1<\/em><br \/>\nbecause I&#8217;m lame \ud83d\ude42<\/p>\n<pre>\r\npi3-darkstar new # echo \"main(){}\"&gt;dupa.c\r\npi3-darkstar new # gcc dupa.c -o dupa\r\npi3-darkstar new # gdb -q .\/dupa\r\nReading symbols from \/root\/priv\/projekty\/pro-police\/new\/dupa...(no debugging symbols found)...done.\r\n(gdb) b main\r\nBreakpoint 1 at 0x80483b7\r\n(gdb) r\r\nStarting program: \/root\/priv\/projekty\/pro-police\/new\/dupa \r\n\r\nBreakpoint 1, 0x080483b7 in main ()\r\n(gdb) dump binary memory test_dump.bin 0xffffe000 0xfffff000\r\n(gdb) quit\r\nA debugging session is active.\r\n\r\n\u00a0\u00a0 \u00a0Inferior 1 [process 20117] will be killed.\r\n\r\nQuit anyway? (y or n) y\r\npi3-darkstar new # file test_dump.bin\r\ntest_dump.bin: ELF 32-bit LSB shared object, Intel 80386, version 1 (SYSV), dynamically linked, stripped\r\npi3-darkstar new # objdump -T .\/test_dump.bin \r\n\r\n.\/test_dump.bin:\u00a0\u00a0\u00a0\u00a0 file format elf32-i386\r\n\r\nDYNAMIC SYMBOL TABLE:\r\nffffe414 g\u00a0\u00a0\u00a0 DF .text\u00a0\u00a0 \u00a000000014\u00a0 LINUX_2.5\u00a0\u00a0 __kernel_vsyscall\r\n00000000 g\u00a0\u00a0\u00a0 DO *ABS*\u00a0\u00a0 \u00a000000000\u00a0 LINUX_2.5\u00a0\u00a0 LINUX_2.5\r\nffffe40c g\u00a0\u00a0\u00a0 DF .text\u00a0\u00a0 \u00a000000008\u00a0 LINUX_2.5\u00a0\u00a0 __kernel_rt_sigreturn\r\nffffe400 g\u00a0\u00a0\u00a0 DF .text\u00a0\u00a0 \u00a000000009\u00a0 LINUX_2.5\u00a0\u00a0 __kernel_sigreturn\r\n\r\npi3-darkstar new # readelf -h .\/test_dump.bin\r\nELF Header:\r\n\u00a0 Magic:\u00a0\u00a0 7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00\r\n\u00a0 Class:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 ELF32\r\n\u00a0 Data:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 2's complement, little endian\r\n\u00a0 Version:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 1 (current)\r\n\u00a0 OS\/ABI:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 UNIX - System V\r\n\u00a0 ABI Version:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 0\r\n\u00a0 Type:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 DYN (Shared object file)\r\n\u00a0 Machine:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 Intel 80386\r\n\u00a0 Version:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 0x1\r\n\u00a0 Entry point address:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 0xffffe414\r\n\u00a0 Start of program headers:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 52 (bytes into file)\r\n\u00a0 Start of section headers:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 1172 (bytes into file)\r\n\u00a0 Flags:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 0x0\r\n\u00a0 Size of this header:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 52 (bytes)\r\n\u00a0 Size of program headers:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 32 (bytes)\r\n\u00a0 Number of program headers:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 4\r\n\u00a0 Size of section headers:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 40 (bytes)\r\n\u00a0 Number of section headers:\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 12\r\npi3-darkstar new # objdump -f .\/test_dump.bin \r\n\r\n.\/test_dump.bin:\u00a0\u00a0\u00a0\u00a0 file format elf32-i386\r\narchitecture: i386, flags 0x00000150:\r\nHAS_SYMS, DYNAMIC, D_PAGED\r\nstart address 0xffffe414\r\n^^^^^^^^^^^^^^^^^^^^^^^^\r\n\r\npi3-darkstar new # objdump -d --start-address=0xffffe414 .\/test_dump.bin \r\n\r\n.\/test_dump.bin:\u00a0\u00a0\u00a0\u00a0 file format elf32-i386\r\n\r\nDisassembly of section .text:\r\n\r\nffffe414 &lt;__kernel_vsyscall&gt;:\r\nffffe414:\u00a0\u00a0 \u00a051\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0push\u00a0\u00a0 %ecx\r\nffffe415:\u00a0\u00a0 \u00a052\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0push\u00a0\u00a0 %edx\r\nffffe416:\u00a0\u00a0 \u00a055\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0push\u00a0\u00a0 %ebp\r\nffffe417:\u00a0\u00a0 \u00a089 e5\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0mov\u00a0\u00a0\u00a0 %esp,%ebp\r\nffffe419:\u00a0\u00a0 \u00a00f 34\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0sysenter\r\nffffe41b:\u00a0\u00a0 \u00a090\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0nop\r\nffffe41c:\u00a0\u00a0 \u00a090\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0nop\r\nffffe41d:\u00a0\u00a0 \u00a090\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0nop\r\nffffe41e:\u00a0\u00a0 \u00a090\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0nop\r\nffffe41f:\u00a0\u00a0 \u00a090\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0nop\r\nffffe420:\u00a0\u00a0 \u00a090\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0nop\r\nffffe421:\u00a0\u00a0 \u00a090\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0nop\r\nffffe422:\u00a0\u00a0 \u00a0cd 80\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0int\u00a0\u00a0\u00a0 $0x80\r\n&lt;--------------------- Nice oldschool pop-ret :) ----------------------&gt;\r\nffffe424:\u00a0\u00a0 \u00a05d\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0pop\u00a0\u00a0\u00a0 %ebp\r\nffffe425:\u00a0\u00a0 \u00a05a\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0pop\u00a0\u00a0\u00a0 %edx\r\nffffe426:\u00a0\u00a0 \u00a059\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0pop\u00a0\u00a0\u00a0 %ecx\r\nffffe427:\u00a0\u00a0 \u00a0c3\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0\u00a0 \u00a0\u00a0\u00a0 \u00a0ret\u00a0\u00a0 \u00a0\r\npi3-darkstar new #<\/pre>\n<p>If you look at the process memory layout and analyse every bytes from this address range you can find some useful instruction not only that which I listed in this lame write-up.<\/p>\n<p>Btw. I wonder why no-one point this out before&#8230;<br \/>\nBtw2. Go and write reliable exploit for kernel 3.x ;p<\/p>\n<p>&nbsp;<\/p>\n<p>&nbsp;<\/p>\n<p>[UPDATE]<\/p>\n<p>Because my write-up wasn&#8217;t so clear this section need to be done. Problem is not in kernel 3.x by itself but in the configuration. If COMPAT_COMPAT_VDSO option was used for kernel then problem appears. Whole problem was discussed based on OpenSuse 12.1 system which enables this option by default.\u00a0<a href=\"http:\/\/lists.grok.org.uk\/pipermail\/full-disclosure\/2012-May\/086901.html\" target=\"_blank\"><em>Nicolas Surribas <\/em> in Full Disclosure list <\/a>pointed out that in his case problem does not exists! After reading opensuse kernel developers list I found a problem and gentle fix:<\/p>\n<p><a href=\"http:\/\/lists.opensuse.org\/opensuse-kernel\/2012-03\/msg00056.html\" target=\"_blank\">http:\/\/lists.opensuse.org\/opensuse-kernel\/2012-03\/msg00056.html<\/a><\/p>\n<p>What about 64 bits Fedora and Ubuntu? They have fixed address range for VSYSCALL which after discussion with bliss it became as known issue: <a href=\"https:\/\/lkml.org\/lkml\/2011\/8\/9\/274\">https:\/\/lkml.org\/lkml\/2011\/8\/9\/274<\/a> and I didn&#8217;t know about that &#8211; my fault.<\/p>\n<p>&nbsp;<\/p>\n<p>Summarizing:<\/p>\n<p>OpenSuse 12.1 by default has this problem but latest kernel update fix it.<\/p>\n<p>All 64 bits distros has VSYSCALL mmaped at fixed address range but this is known issue.<\/p>\n<p>&nbsp;<\/p>\n<p>Thanks for everyone who was involved in this issue \ud83d\ude09<\/p>\n<p>&nbsp;<\/p>\n<p>Best regards,<br \/>\nAdam Zabrocki<\/p>\n","protected":false},"excerpt":{"rendered":"<p>The story of the Linux kernel 3.x&#8230; In 2005 everybody was exited about possibility of bypass ASLR on all Linux 2.6 kernels because of the new concept called VDSO (Virtual Dynamic Shared Object). More information about this story can be found at the following link: http:\/\/www.trilithium.com\/johan\/2005\/08\/linux-gate\/ &nbsp; In short, VDSO was mmap&#8217;ed by the kernel [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_jetpack_memberships_contains_paid_content":false,"footnotes":""},"categories":[1],"tags":[],"class_list":["post-332","post","type-post","status-publish","format-standard","hentry","category-o-wszystkim-i-o-niczym"],"jetpack_featured_media_url":"","jetpack_sharing_enabled":true,"_links":{"self":[{"href":"https:\/\/blog.pi3.com.pl\/index.php?rest_route=\/wp\/v2\/posts\/332","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/blog.pi3.com.pl\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/blog.pi3.com.pl\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/blog.pi3.com.pl\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/blog.pi3.com.pl\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=332"}],"version-history":[{"count":24,"href":"https:\/\/blog.pi3.com.pl\/index.php?rest_route=\/wp\/v2\/posts\/332\/revisions"}],"predecessor-version":[{"id":355,"href":"https:\/\/blog.pi3.com.pl\/index.php?rest_route=\/wp\/v2\/posts\/332\/revisions\/355"}],"wp:attachment":[{"href":"https:\/\/blog.pi3.com.pl\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=332"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/blog.pi3.com.pl\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=332"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/blog.pi3.com.pl\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=332"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}