Skip to main content

Overview

Unsafe unlink is a classic heap exploitation technique that leverages the unlink macro in glibc’s malloc implementation. When a chunk is freed and consolidated with adjacent free chunks, the unlink operation can be exploited to achieve arbitrary memory writes if proper checks are bypassed.
This technique can be used when you have a pointer at a known location to a region you can call unlink on. The most common scenario is a vulnerable buffer that can be overflown and has a global pointer.

Glibc Version Compatibility

Working Versions

All glibc versions (2.23 - 2.41+)

Requirements

Must bypass P->fd->bk == P && P->bk->fd == P check

What Does This Technique Achieve?

The unsafe unlink technique allows an attacker to:
  • Corrupt global pointers to point to arbitrary memory locations
  • Achieve arbitrary memory write by dereferencing the corrupted pointer
  • Bypass modern heap protections by satisfying unlink consistency checks
Starting with glibc 2.27, you need to allocate chunks larger than fastbin/tcache ranges (typically 0x420 bytes or more) to ensure they go into unsorted bins.

The Vulnerability

This attack exploits:
  1. Heap overflow - ability to overwrite chunk metadata
  2. Known pointer location - a global/static pointer to a heap chunk
  3. Unlink consolidation - backward consolidation during free()

Technical Details

The unlink macro performs this critical check:
To bypass this, we need:
  • P->fd->bk == P
  • P->bk->fd == P
Where P is our fake chunk.

Memory Layout

Step-by-Step Exploitation

1

Allocate Chunks

Allocate two chunks where the first contains a global pointer:
2

Create Fake Chunk

Inside chunk0, create a fake chunk with carefully crafted fd/bk pointers:
This satisfies the unlink check because:
  • fd->bk points to offset 24 bytes into fd, which we control
  • bk->fd points to offset 16 bytes into bk, which we control
3

Corrupt Chunk1 Metadata

Overflow from chunk0 to modify chunk1’s metadata:
4

Trigger Unlink

Free chunk1 to trigger backward consolidation:
During consolidation, the unlink macro executes:
5

Arbitrary Write

Now chunk0_ptr points near itself. Use this to achieve arbitrary write:

Full Source Code

Key difference in glibc 2.27+: Use malloc_size = 0x420 instead of 0x80 to avoid tcache bins.

HITCON CTF 2014

stkof - Classic unsafe unlink exploitation

Insomni'hack 2017

Wheel of Robots - Modern unsafe unlink variant

Practice

Try it in your browser

Debug this technique interactively on Ret2 Wargames

References