Несколько экземпляров Python, запущенных одновременно, ограничены 35

Я запускаю скрипт Python 3.6 как несколько отдельных процессов на разных процессорах параллельного вычислительного кластера. До 35 процессов выполняются одновременно без проблем, но 36-й (и более) происходит сбой с ошибкой сегментации во второй строке, которая import pandas as pd, Интересно, что первая строка import os не вызывает проблемы. Полное сообщение об ошибке:

OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max
OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max
OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max
OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max
OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max
OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max
OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max
OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max
OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max
OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max
OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max
OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max
OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max
OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max
OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max
OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max
Traceback (most recent call last):
  File "/home/.../myscript.py", line 32, in <module>
    import pandas as pd
  File "/home/.../python_venv2/lib/python3.6/site-packages/pandas/__init__.py", line 13, in <module>
    __import__(dependency)
  File "/home/.../python_venv2/lib/python3.6/site-packages/numpy/__init__.py", line 142, in <module>
    from . import add_newdocs
  File "/home/.../python_venv2/lib/python3.6/site-packages/numpy/add_newdocs.py", line 13, in <module>
    from numpy.lib import add_newdoc
  File "/home/.../python_venv2/lib/python3.6/site-packages/numpy/lib/__init__.py", line 8, in <module>
    from .type_check import *
  File "/home/.../python_venv2/lib/python3.6/site-packages/numpy/lib/type_check.py", line 11, in <module>
    import numpy.core.numeric as _nx
  File "/home/.../python_venv2/lib/python3.6/site-packages/numpy/core/__init__.py", line 16, in <module>
    from . import multiarray
SystemError: initialization of multiarray raised unreported exception
/var/spool/slurmd/job04590/slurm_script: line 11: 26963 Segmentation fault      python /home/.../myscript.py -x 38

Pandas и несколько других пакетов устанавливаются в виртуальной среде. Я продублировал виртуальную среду, чтобы в каждом венге работало не более 24 процессов. Например, приведенный выше скрипт ошибки произошел от скрипта, запущенного в виртуальной среде с именем python_venv2,

Проблема возникает на 36-м процессе каждый раз, независимо от того, сколько процессов импортируется из конкретного экземпляра Pandas. (Я даже не вникаю в потенциал кластера параллельных вычислений.)

Итак, если это не ограничение на число процессов, обращающихся к Pandas, это ограничение на число процессов, работающих на Python? Почему 35 предел?

Можно ли установить несколько копий Python на машине (в отдельных виртуальных средах?), Чтобы я мог запустить более 35 процессов?

1 ответ

Решение

Разложение сообщения об ошибке

Ваше сообщение об ошибке содержит следующую подсказку:

OpenBLAS blas_thread_init: pthread_create: Resource temporarily unavailable
OpenBLAS blas_thread_init: RLIMIT_NPROC 1024 current, 2067021 max

RLIMIT_NPROC Переменная контролирует общее количество процессов, которые может иметь пользователь. Более конкретно, как это для настройки процесса, когда fork(), clone(), vfork(), & c вызываются процессом, RLIMIT_NPROC значение для этого процесса сравнивается с общим количеством процессов для родительского пользователя этого процесса. Если это значение будет превышено, все будет закрыто, как вы уже видели.

Сообщение об ошибке указывает, что OpenBLAS не смог создать дополнительные потоки, потому что ваш пользователь использовал все потоки RLIMIT_NPROC дал это.

Поскольку вы работаете в кластере, маловероятно, что ваш пользователь запускает много потоков (в отличие, скажем, если вы работали на своем персональном компьютере и просматривали веб-страницы, проигрывали музыку и т. Д.), Поэтому разумно сделать вывод, что OpenBLAS пытается начать несколько потоков.

Как OpenBLAS использует потоки

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

OpenBLAS имеет несколько способов ограничить количество потоков, которые он использует. Они контролируются через:

export OPENBLAS_NUM_THREADS=4
export GOTO_NUM_THREADS=4
export OMP_NUM_THREADS=4

Приоритеты: OPENBLAS_NUM_THREADS > GOTO_NUM_THREADS > OMP_NUM_THREADS. (Я думаю, что это означает, что OPENBLAS_NUM_THREADS Переопределение OMP_NUM_THREADS; однако OpenBLAS игнорирует OPENBLAS_NUM_THREADS а также GOTO_NUM_THREADS при компиляции с USE_OPENMP=1.)

Если ни одна из вышеперечисленных переменных не установлена, OpenBLAS будет работать с использованием числа потоков, равного количеству ядер на вашем компьютере (32 на вашем компьютере)

Ваша ситуация

Ваш кластер имеет 32-ядерные процессоры. Вы пытаетесь запустить 36 экземпляров Python. Каждый экземпляр требует 1 поток для Python + 32 потока для OpenBLAS. Вам также понадобится 1 поток для вашего SSH-соединения и 1 поток для вашей оболочки. Это означает, что вам нужно 36*(32+1)+2=1190 потоков.

Ядерный вариант решения проблемы заключается в использовании:

export OPENBLAS_NUM_THREADS=1

что должно привести вас к 36*(1+1)+2=74 потоков.

Так как у вас есть запасная емкость, вы можете настроить OPENBLAS_NUM_THREADS до более высокого значения, но тогда экземпляры OpenBLAS, принадлежащие вашим отдельным процессам Python, будут мешать друг другу. Таким образом, существует компромисс между тем, как быстро вы получаете одно решение, и как быстро вы можете получить много решений. В идеале, вы можете решить эту проблему, запустив меньше Питонов на узел и используя больше узлов.

Другие вопросы по тегам