Skip to content
KitploitKITPLOIT
ИнструментыБлог
Log in
Отправить
ИнструментыБлог
Отправить

Инструменты для хакинга, пентеста и кибербезопасности — ваш арсенал защиты!

Kitploit — это каталог инструментов для хакинга, кибербезопасности и пентестинга. Находите последние обновления проектов для поиска уязвимостей, анализа систем, автоматизации тестирования и усиления вашей безопасности.

··Ленты·Контакты·Конфиденциальность·© 2026 Kitploit

Каталог инструментов

Категории

Все категории
Loading categories
cve-2023-5217-poc — PoC для запуска CVE-2023-5217 через интерфейс WebCodecs или MediaRecorder браузера. | Kitploit
Инструменты/GitHubGitHub/ut-security/cve-2023-5217-poc
Анализ уязвимостейЭксплуатацияЭксплуатация веб-приложенийФаззингОбучение и ОбразованиеЭксплуатация Бинарных Файлов
GitHubut-security/cve-2023-5217-poc

cve-2023-5217-poc

PoC для запуска CVE-2023-5217 через интерфейс WebCodecs или MediaRecorder браузера.

Репозиторий
163172 лет назадЕщё не проверено

Популярное

Смотреть все →

Откройте для себя самые используемые инструменты нашего сообщества.

Изучить все инструменты

Просмотрите нашу коллекцию инструментов

Смотреть все инструменты →
Поделиться

CVE-2023-5217: Эксплойт переполнения кучи при кодировании VP8 в libvpx

CVE-2023-5217 — это эксплуатируемая в реальных условиях уязвимость libvpx, обнаруженная Клеманом Лесинем из Группы анализа угроз Google (Threat Analysis Group), нацеленная на Chrome.

Этот репозиторий показывает, как вызвать CVE-2023-5217 в браузере с помощью API WebCodecs и MediaRecorder. CVE-2023-5217 позволяет выполнить переполнение буфера кучи с контролируемой длиной переполнения и перезаписью повторяющегося малого 4-байтового значения. В настоящее время неизвестно, как CVE-2023-5217 эксплуатировалась в реальных условиях.

Примерно на момент публичного раскрытия было выпущено два патча для libvpx и один для Chromium, которые устраняли CVE-2023-5217. Патчи для libvpx включали отключение изменений количества потоков VP8 и тест для многопоточного кодирования. Патч Chromium отключил регулировку количества потоков в WebCodecs.

Основная проблема в libvpx v1.13.0 «Гадкий утёнок»

Summary

libvpx — это библиотека для кодирования и декодирования VP8/VP9.

Ключевая проблема CVE-2023-5217 заключается в том, что уменьшение количества потоков при одновременном увеличении высоты кадра в сеансе кодирования VP8 в libvpx вызывает линейное переполнение кучи с контролируемой длиной и контролируемой перезаписью повторяющегося малого 4-байтового значения. Разница в высоте кадра контролирует длину перезаписи, а новая ширина кадра контролирует 4-байтовое значение, которое повторно записывается. Эта уязвимость может быть использована несколько раз для последовательной записи различных малых 4-байтовых значений путём уменьшения высоты в каждой последующей конфигурации.

Details

Кодировщик VP8 в libvpx поддерживает массив mt_current_mb_col, который хранит текущий столбец, обрабатываемый потоком кодировщика. Этот массив выделяется только в том случае, если потоков больше одного, и его размер зависит от mb_rows, где mb_rows = frame_height >> 4, а frame_height округляется вверх до ближайшего кратного 16.

// https://github.com/webmproject/libvpx/blob/6512f994da13e2f27e6a7bd449efee0a374b55b7/vp8/common/alloccommon.c#L85
// The width and height are rounded up to a multiple of 16 and then assigned to `mb_rows` and `mb_cols`
int vp8_alloc_frame_buffers(VP8_COMMON *oci, int width, int height) {
    ...
    // Round up the width/height up to the nearest multiple of 16
    if ((width & 0xf) != 0) width += 16 - (width & 0xf);
    if ((height & 0xf) != 0) height += 16 - (height & 0xf);
    ...
    oci->mb_rows = height >> 4;
    oci->mb_cols = width >> 4;
    ...
}
// https://github.com/webmproject/libvpx/blob/6512f994da13e2f27e6a7bd449efee0a374b55b7/vp8/encoder/onyx_if.c#L1232
// This snippet shows the allocation of `mt_current_mb_col`
void vp8_alloc_compressor_data(VP8_COMP *cpi) {
  ...
  // Only allocate if we have more than 1 thread
  if (cpi->oxcf.multi_threaded > 1) {
    int i;

    vpx_free(cpi->mt_current_mb_col);
    // sizeof(*cpi->mt_current_mb_col) is 4
    CHECK_MEM_ERROR(&cpi->common.error, cpi->mt_current_mb_col,
                    vpx_malloc(sizeof(*cpi->mt_current_mb_col) * cm->mb_rows));
    for (i = 0; i < cm->mb_rows; ++i)
      vpx_atomic_init(&cpi->mt_current_mb_col[i], 0);
  }
  ...
}

После завершения кодирования кадра libvpx сохраняет количество закодированных столбцов плюс mt_sync_range в mt_current_mb_col.

// https://github.com/webmproject/libvpx/blob/6512f994da13e2f27e6a7bd449efee0a374b55b7/vp8/encoder/onyx_if.c#L1212
// Snippet where the mt_sync_range value is set, based on the width.
void vp8_alloc_compressor_data(VP8_COMP *cpi) {
    ...
#if CONFIG_MULTITHREAD
  if (width < 640) {
    cpi->mt_sync_range = 1;
  } else if (width <= 1280) {
    cpi->mt_sync_range = 4;
  } else if (width <= 2560) {
    cpi->mt_sync_range = 8;
  } else {
    cpi->mt_sync_range = 16;
  }
#endif
  ...
}
// https://github.com/webmproject/libvpx/blob/6512f994da13e2f27e6a7bd449efee0a374b55b7/vp8/encoder/encodeframe.c#L560
// Function where the attacker chosen value is written
static void encode_mb_row(...) {
  ...
  const int nsync = cpi->mt_sync_range; // This value is set in vp8_alloc_compressor_data
  vpx_atomic_int rightmost_col = VPX_ATOMIC_INIT(cm->mb_cols + nsync);
  ...
  if (vpx_atomic_load_acquire(&cpi->b_multi_threaded) != 0) {
    current_mb_col = &cpi->mt_current_mb_col[mb_row];
  }
  ...
  if (vpx_atomic_load_acquire(&cpi->b_multi_threaded) != 0) {
    // current_mb_col is a reference to mt_current_mb_col
    vpx_atomic_store_release(current_mb_col,
                             vpx_atomic_load_acquire(&rightmost_col));
  }
  ...
}

Для переполнения mt_current_mb_col требуются три конфигурации кодирования:

  1. configinit: Во время инициализации libvpx устанавливает initial_width и initial_height. Это максимально возможные границы для последующих конфигураций. Количество потоков здесь не имеет значения. Нам нужна промежуточная конфигурация, потому что никакие последующие комбинации ширины/высоты не могут быть больше исходных.

  2. configvuln: При перенастройке, если используется более одного потока, libvpx создаёт уязвимое выделение mt_current_mb_col на основе configvuln.height. Эта новая высота должна быть меньше configinit.initial_height, иначе мы получим ошибку.

  3. configattack: При перенастройке, если используется только один поток, libvpx не будет перераспределять mt_current_mb_col, оставляя его в уязвимом состоянии. libvpx будет многократно записывать значение (configattack.width >> 4) + 1 (где 1 — это переменная mt_sync_range, а ширина округляется вверх до ближайшего кратного 16) за пределы ранее выделенной области, если выполняется следующее условие:

\text{ceil}(\text{config}_{\text{init}}.\text{height}/16) \geq \text{ceil}(\text{config}_{\text{attack}}.\text{height}/16) \gt \text{ceil}(\text{config}_{\text{vuln}}.\text{height}/16)$$

mt_current_mb_col overflow

Более конкретно: предположим, мы инициализируем конфигурацию кодирования VP8 с configinit с шириной = 1200, высотой = 1200, потоками = 4. Атака выглядит следующим образом:

  1. configvuln перенастраивает кодировщик с шириной = 500 (округлено до 512), высотой = 700 (округлено до 704) и потоками = 2. Переменная mb_rows устанавливается в 704/16=44, массив mt_current_mb_col выделяется размером (44)*4 = 176 байт. Записанное значение, хранящееся в mt_current_mb_col, равно 512/16 + 1 = 33.

  2. configattack перенастраивает кодировщик с шириной = 18 (округлено до 32), высотой = 1000 (округлено до 1008) и потоками = 1. Поскольку mt_current_mb_col перераспределяется только при наличии более одного потока, он остаётся того же размера, но mb_rows теперь устанавливается в 1008/16 = 63. Когда libvpx вызывает encode_mb_row, он перезаписывает (63-44)*4 = 68 байт после выделения mt_current_mb_col, многократно записывая значение 32/16 + 1 = 3, где 32 — округлённая ширина, а 1 — значение mt_sync_range.

Скачать инструмент