Каков подпроцесс. Popen макс. длина args параметра?

Я использую функцию Popen от модуля подпроцесса для выполнения инструмента командной строки:

subprocess.Popen(args, bufsize=0, executable=None, stdin=None, stdout=None, stderr=None, preexec_fn=None, close_fds=False, shell=False, cwd=None, env=None, universal_newlines=False, startupinfo=None, creationflags=0)

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

Traceback (most recent call last):
  File "dump_output_sopuids.py", line 68, in 
    uid_map = create_sopuid_to_path_dict_dcmdump(dicom_files)
  File "dump_output_sopuids.py", line 41, in create_sopuid_to_path_dict_dcmdump
    dcmdump_output = subprocess.Popen(cmd,stdout=subprocess.PIPE).communicate(0)[0]
  File "c:\python26\lib\subprocess.py", line 621, in __init__
    errread, errwrite)
  File "c:\python26\lib\subprocess.py", line 830, in _execute_child
    startupinfo)
WindowsError: [Error 206] The filename or extension is too long

Существует ли общий способ найти эту макс. длину? Я нашел следующую статью о MSDN: Командная строка (Cmd. exe) строковое ограничение командной строки, но я не хочу трудно кодировать в значении. Я заставил бы значение во время выполнения разбивать команду во множественные вызовы.

Я использую Python 2.6 на Windows XP 64.

Править: добавление примера кода

paths = ['file1.dat','file2.dat',...,'fileX.dat']
cmd = ['process_file.exe','+p'] + paths
cmd_output = subprocess.Popen(cmd,stdout=subprocess.PIPE).communicate(0)[0]

Проблема происходит потому что каждая фактическая запись в paths список обычно является очень длинным путем к файлу И существует несколько тысяч из них.

Я не возражаю разбивать команду во множественные вызовы process_file.exe. Я ищу общий способ получить макс. длину, которой args может быть так, я знаю сколько путей представлять для каждого выполнения.

14
задан Jesse Vogt 4 March 2010 в 23:57
поделиться

1 ответ

Если вы передаете shell=False, то Cmd.exe не вступает в игру.

На windows, subprocess будет использовать функцию CreateProcess из Win32 API для создания нового процесса. В документации по этой функции говорится, что второй аргумент (который строится subprocess.list2cmdline) имеет максимальную длину 32 768 символов, включая завершающий нулевой символ Unicode. Если lpApplicationName равен NULL, то часть имени модуля в lpCommandLine ограничена MAX_PATH символами.

Учитывая ваш пример, я предлагаю указать значение для executable (args[0]) и использовать args для первого параметра. Если мое чтение документации CreateProcess и исходного кода модуля subprocess верно, это должно решить вашу проблему.

[edit: удалил бит args[1:] после того, как получил в руки машину windows и протестировал]

9
ответ дан 1 December 2019 в 15:12
поделиться
Другие вопросы по тегам:

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