_int_malloc fastbin victim size check 분석

msh1307·2022년 11월 29일
0

etc

목록 보기
6/21

16.04에서 DFB를 할때 fastbin은 size check가 있다.

  if ((unsigned long) (nb) <= (unsigned long) (get_max_fast ()))
    {
      idx = fastbin_index (nb);
      mfastbinptr *fb = &fastbin (av, idx);
      mchunkptr pp = *fb;
      do
        {
          victim = pp;
          if (victim == NULL)
            break;
        }
      while ((pp = catomic_compare_and_exchange_val_acq (fb, victim->fd, victim))
             != victim);
      if (victim != 0)
        {
          if (__builtin_expect (fastbin_index (chunksize (victim)) != idx, 0))
            {
              errstr = "malloc(): memory corruption (fast)";
            errout:
              malloc_printerr (check_action, errstr, chunk2mem (victim), av);
              return NULL;
            }

fastbin_index (chunksize (victim)) != idx를 우회할 수 있는 fake chunk를 찾을때, 하위 4바이트만 신경써주면 된다.

#define fastbin_index(sz) \
  ((((unsigned int) (sz)) >> (SIZE_SZ == 8 ? 4 : 3)) - 2)

fastbin_index 매크로가 unsigned int로 타입 캐스팅해서 비교하기 때문이다.

struct malloc_chunk {

  INTERNAL_SIZE_T      prev_size;  /* Size of previous chunk (if free).  */
  INTERNAL_SIZE_T      size;       /* Size in bytes, including overhead. */

  struct malloc_chunk* fd;         /* double links -- used only if free. */
  struct malloc_chunk* bk;

  /* Only used for large blocks: pointer to next larger size.  */
  struct malloc_chunk* fd_nextsize; /* double links -- used only if free. */
  struct malloc_chunk* bk_nextsize;
};

INTERNAL_SIZE_T가 64비트 환경이여서 8바이트여도, 하위 4바이트만 검증하기 때문에, 그 4바이트만 신경써주면 된다.

그래서 0x0168000000000060fastbin_index (chunksize (victim)) != idx를 우회할 수 있게 된다.

profile
https://msh1307.kr

0개의 댓글