Что продолжает истощать энтропию?

Попытайтесь увеличиться burst/limit значения. Маркерные алгоритмы блока масштабируются хорошо, но имеют ограниченное отношение точности/скорости.

Точность достигается при помощи маленького блока, скорости путем увеличения размера маркеров. Большие маркеры означают уровень, на котором они пополнены, уменьшен (маркеры в секунду = байты в секунду / байты на маркер).

rate параметр дает среднюю скорость, которая не должна быть превышена, burst или limit параметры дают размер окна усреднения. Поскольку отсылка пакета в линейной скорости превышает уровень набора в течение времени, куда пакет передается, окно усреднения должно быть, по крайней мере, достаточно большим, что отправка единственного пакета не продвигает все окно по пределу; если больше пакетов поместится в окно, то алгоритм будет иметь лучший шанс достигания намеченной цели точно.

21
20.10.2013, 17:10
2 ответа

Энтропия не только потеряна через /dev/{,u}random, ядро также берет некоторых. Например, новые процессы рандомизировали адреса (ASLR), и для сетевых пакетов нужны случайные порядковые номера. Даже модуль файловой системы может удалить некоторую энтропию. См. комментарии в drivers/char/random.c. Также отметьте это entropy_avail относится к входному пулу, не выходным пулам (в основном неблокирование /dev/urandom и блокирование /dev/random).

Если необходимо наблюдать энтропийный пул, не использовать watch cat, это использует энтропию при каждом вызове cat. В прошлом я также хотел наблюдать этот пул, поскольку GPG был очень медленным при генерации ключей, поэтому я записал программу C с единственной целью наблюдать энтропийный пул: https://git.lekensteyn.nl/c-files/tree/entropy-watcher.c.

Обратите внимание, что могут быть фоновые процессы, которые также используют энтропию. Используя точки трассировки на соответствующем ядре Вы видите процессы, которые изменяют энтропийный пул. Использование в качестве примера, которое записывает все точки трассировки, связанные со случайной подсистемой включая callchain (-g) на всех центральных процессорах (-a) запуск измерения после 1 секунды для игнорирования ее собственного процесса (-D 1000) и включая метки времени (-T):

sudo perf record -e random:\* -g -a -D 1000 -T sleep 60

Читайте это с любой из этих команд (измените владельца perf.data по мере необходимости):

perf report  # opens an interactive overview
perf script  # outputs events after each other with traces

perf script вывод дает интересное понимание и показывает, когда приблизительно 8 байтов (64 бита) энтропии периодически истощаются на моей машине:

kworker/0:2   193 [000]  3292.235908:       random:extract_entropy: ffffffff8173e956 pool: nbytes 8 entropy_count 921 caller _xfer_secondary_pool
                  5eb857 extract_entropy (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  5eb984 _xfer_secondary_pool (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  5ebae6 push_to_pool (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  293a05 process_one_work (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  293ce8 worker_thread (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  299998 kthread (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  7c7482 ret_from_fork (/lib/modules/4.6.2-1-ARCH/build/vmlinux)

kworker/0:2   193 [000]  3292.235911:         random:debit_entropy: ffffffff8173e956: debit_bits 64
                  5eb3e8 account.part.12 (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  5eb770 extract_entropy (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  5eb984 _xfer_secondary_pool (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  5ebae6 push_to_pool (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  293a05 process_one_work (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  293ce8 worker_thread (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  299998 kthread (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  7c7482 ret_from_fork (/lib/modules/4.6.2-1-ARCH/build/vmlinux)

...

swapper     0 [002]  3292.507720:   random:credit_entropy_bits: ffffffff8173e956 pool: bits 2 entropy_count 859 entropy_total 2 caller add_interrupt_randomness
                  5eaab6 credit_entropy_bits (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  5ec644 add_interrupt_randomness (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  2d5729 handle_irq_event_percpu (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  2d58b9 handle_irq_event (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  2d8d1b handle_edge_irq (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  230e6a handle_irq (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  7c9abb do_IRQ (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  7c7bc2 ret_from_intr (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  6756c7 cpuidle_enter (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  2bd9fa call_cpuidle (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  2bde18 cpu_startup_entry (/lib/modules/4.6.2-1-ARCH/build/vmlinux)
                  2510e5 start_secondary (/lib/modules/4.6.2-1-ARCH/build/vmlinux)

По-видимому, это, оказывается, предотвращает трату энтропии путем передачи энтропии от входного пула до выходных пулов:

/*
 * Credit (or debit) the entropy store with n bits of entropy.
 * Use credit_entropy_bits_safe() if the value comes from userspace
 * or otherwise should be checked for extreme values.
 */
static void credit_entropy_bits(struct entropy_store *r, int nbits)
{
    ...
        /* If the input pool is getting full, send some
         * entropy to the two output pools, flipping back and
         * forth between them, until the output pools are 75%
         * full.
         */

         ...
            schedule_work(&last->push_work);
}

/*
 * Used as a workqueue function so that when the input pool is getting
 * full, we can "spill over" some entropy to the output pools.  That
 * way the output pools can store some of the excess entropy instead
 * of letting it go to waste.
 */
static void push_to_pool(struct work_struct *work)
{
    ...
}
20
27.01.2020, 19:43
  • 1
    +1 обновлений для указания, которое даже по-видимому "innocous" операции, такие как запуск программы может истощить небольшое количество энтропии. –  a CVn 21.10.2013, 15:52
  • 2
    Это объяснение является однако немного противоречащим к ситуации, описанной в вопросе, не так ли? Там энтропия (контролируемый с watch) выращивает постоянно затем резкие отбрасывания. Если watch использованная энтропия на каждом чтении, это должно на самом деле постоянно уменьшаться. –  techraf 20.06.2016, 00:52
  • 3
    @techraf Хорошее наблюдение, периодически вызывая cat если в теории имеют тот же энтропийный дренаж, который не должен быть видим. Оказывается, что энтропия перемещена в другой пул, когда существует "достаточная" энтропия. –  Lekensteyn 20.06.2016, 21:39

lsof не является лучшим инструментом для контроля /dev/random поскольку один считанный процессом закончен в очень короткий срок. Я не знаю хорошего метода получения, какой процесс делает чтение, но использование inotify можно контролировать, если существует чтение.

Здесь существует в основном два пути:

  1. Получите сводку после N секунды с:

    inotifywatch -v -t 60 /dev/random 
    
  2. Представление живые события доступа:

    inotifywait -m --timefmt '%H:%M:%S' --format '%T: %e' /dev/random
    

Ни один не даст Вам, процесс и последний не дадут Вам размер чтения. Первое даст Вам сводку как в:

total  access  close_nowrite  open  filename
18     16      1              1     /dev/random

Если Вы имеете то выполнение и делаете a dd if=/dev/random of=/tmp/foo bs=1 count=3, Вы получаете идею.

Во всяком случае. Это не даст, Вы отсчитываете, когда ядро использует от пула.


Когда дело доходит до проверки состояния энтропийного использования

watch cat /proc/sys/kernel/random/entropy_avail

не лучшая идея как каждый cat движение должно использовать энтропию. (Я вижу теперь, что это открылось другой ответ, которые также упоминают это.) У меня также есть некоторый код C для этого и попробованный для определения местоположения его вчера. Я буду видеть, могу ли я найти его и обновить ответ позже.

4
27.01.2020, 19:43
  • 1
    auditd может зарегистрировать чтения от /dev/random (Я знаю, что существуют подобные примеры на этом сайте). –  Gilles 'SO- stop being evil' 21.10.2013, 19:02
  • 2
    Что относительно того, чтобы использовать следующий жемчуг вместо watch cat: use Fcntl 'SEEK_SET'; open(my $fh,"<", "/proc/sys/kernel/random/entropy_avail"); while (1) { print <$fh>; sleep(1); seek($fh,0,SEEK_SET); } –  gmatht 06.03.2015, 15:17

Теги

Похожие вопросы