Пропускать дампы ядра через C a #define (или другое в решениях кода / времени компиляции)? - PullRequest
7 голосов
/ 13 марта 2020

Я понимаю, что операционная система иногда генерирует дамп ядра при отправке сигнала (обычно при взломе sh). Есть ли способ сообщить операционной системе из внутри C / C ++ с помощью флага #define или компилятора о том, что с помощью этого исполняемого файла может быть сгенерирован дамп ядра со специально ограниченным определенным образом? Единственный известный мне способ управления им - через ulimit - c. Моя тестовая система Linux. Дамп без ядра не требуется реализовывать в масштабе всей системы, только для конкретной программы c.

Для заинтересованных лиц это имеет отношение к CVE-2019-15947 in Bitcoin Core * bitcoin -qt, который до сих пор не имеет решения.

Часть этого обсуждения находится на странице отслеживания ошибок GitHub Bitcoin .

Другой вариант - замаскировать или зашифровать wallet.dat в памяти, чтобы это не легко получить через дамп ядра. Обратите внимание, что второй вариант уже может быть выполнен, хотя по умолчанию он не включен.

Ответы [ 3 ]

3 голосов
/ 13 марта 2020

В зависимости от вашего определения «в коде / во время компиляции», вы можете установить обработчик сигнала и очистить память при получении этого сигнала.

Однако сбои обрабатываются ядром, а не компилятором или исполняемый файл Вы не можете предотвратить сброс памяти ядром в ядро ​​из исполняемого файла, независимо от того, что вы делаете.

Поэтому другой вариант звучит лучше.

1 голос
/ 13 марта 2020

ключевой примитив , который вы хотите использовать: madvise(..., MADV_DONTDUMP), который уведомляет Linux (начиная с 3.4), что вы не будете sh серию страниц быть включенным в свалку. Флаг также называется VM_DONTDUMP в пространстве ядра. (Обратите внимание, что некоторые версии gdb не учитывают этот флаг, который может иметь отношение к ядрам, сгенерированным gcore или другими помощниками, а не ядром.)

Вам также понадобится чтобы гарантировать, что при обработке ключей и других конфиденциальных данных, хранящихся на этих страницах, информация не разглашается через регистры и не выливается в стек, достаточный для компрометации, если после этого времени дамп памяти будет получен.

0 голосов
/ 13 марта 2020

Теоретически возможно установить предел из программы с помощью setrlimit():

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#include <sys/resource.h>
#include <errno.h>


int setNoCores( void )
{
    int result;
    struct rlimit core_limiter;

    core_limiter.rlim_cur = 0;    // *no* core
    core_limiter.rlim_max = 0;

    // Tell the OS no core-files
    result = setrlimit( RLIMIT_CORE, &core_limiter );

    // Was it OK for you?
    if ( result != 0 )
    {
        switch( errno )
        {
            case EFAULT:   fprintf( stderr, "setNoCores() - EFAULT\n" ); break;
            case EINVAL:   fprintf( stderr, "setNoCores() - EINVAL\n" ); break;
            case EPERM:    fprintf( stderr, "setNoCores() - EPERM - No Permissions!\n" ); break;
            case ESRCH:    fprintf( stderr, "setNoCores() - ESRCH\n" ); break;
        }
    }

    return result;
}


int main( int argc, char **argv )
{
    if ( setNoCores() == 0 )
    {
        printf( "Core Files off\n") ;
    }
    else
    {
        printf( "Failed to change limits, core-file generation at default\n" );
    }

    return 0;
}

Конечно, процессу требуется разрешение для настройки пределов. В зависимости от идентификатора пользователя, запрос может быть отклонен и установлена ​​ошибка EPERM.

Файлы ядра также контролируются в вашей ОС с помощью команды ulimit. С параметром -c это устанавливает максимальный размер основного файла. Размер-число - это количество блоков размером 1024 или 512 байт [ref: справочная страница Solaris (512), Linux '--help' (1024)]. Установка этого параметра в оболочке, из которой выполняется программа, должна ограничивать результат только для тех оболочек, которые являются дочерними процессами.

Для файлов без ядра:

    ulimit -c 0 

Чтобы снова включить его:

ulimit -c <some large number>

Для более подробной информации, попробуйте ulimit --help в вашей оболочке.

...