2009-02-19 6 views
58

Могу ли я изменить имя исполняемого процесса для скрипта Python? Я хочу показать другое имя вместо реального имени процесса, когда я получу список системных процессов. В C я могу установитьЕсть ли способ изменить имя эффективного процесса в Python?

strcpy(argv[0],"othername"); 

Но в Python

argv[0] = "othername" 

не похоже на работу. Когда я получаю список процессов (с ps ax в моем linux box), настоящее имя не изменяется. Я предпочитаю портативное решение (или другое решение для posix и другое для оконных сред), если оно существует.

Заранее спасибо

+0

см. также https://superuser.com/questions/427642/is-it-possible-to-set-the-process-name-with-pythonw, где http: // bugs.python.org/issue5672 - это я ntionned – anarcat

ответ

10

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

Кроме того, я смущен тем, что вы подразумеваете под именами процессов в Windows.

Вы имеете в виду имя службы? Я так полагаю, потому что ничто другое не имеет никакого смысла (по крайней мере, для моего не-Windows, использующего мозг).

Если это так, вам необходимо использовать Tim Golden's WMI interface и вызвать метод .Изменить на сервис ... по крайней мере, согласно его tutorial.

Для Linux ни один из методов, которые я нашел не работал, кроме this poorly packaged module, который устанавливает для вас argv [0].

Я даже не знаю, будет ли это работать на BSD-вариантах (у которых есть системный вызов setproctitle). Я уверен, что argv [0] не будет работать на Solaris.

+0

Я знаю, что уже поздно, но для новых читателей рассмотрим также @MattWritesCode [answer] (http://stackoverflow.com/a/13267122/248390), быстрый и простой для CPython для Linux. – bufh

-8
In [1]: import sys 

In [2]: print sys.argv[0] 
C:\Python25\scripts\ipython.py 

In [3]: sys.argv[0] = 'foo' 

In [4]: print sys.argv[0] 
foo 

Примечание сингл «=» знак

+2

Но если я запустил ps (список процессов в ящиках Linux), имя процесса останется таким же. Попробуйте – Emilio

+1

, поэтому вместо того, чтобы опробовать мой ответ, попробуйте уточнить этот вопрос в своем вопросе. ... –

+2

Это не изменяет имя процесса вообще. Это изменяет только копию Python argv. Я бы рекомендовал удалить этот явно неправильный ответ. – Dakkaron

4

Во-первых, я не уверен, что просто настройки argv[0] в программе C переносимым меняет имя, показанное в ps. Возможно, это происходит в некоторых unixen, но я понимаю, что этого не ожидается.

Во-вторых, поскольку Windows специально не совместима с POSIX, только несколько вещей «переносятся» между POSIX и не-POSIX. Поскольку вы конкретно говорите «ps», я предполагаю, что POSIX является вашим приоритетом, и Windows может не работать.

Что еще более важно, мое понимание изменения argv[0] состоит в том, что для внесения этих изменений требуется позвонить exec. В частности, вызов exec имеет как путь к исполняемому файлу, так и отдельный список argv. Создание собственного вызова позволяет вам разорвать соглашение оболочки о посылке исполняемого имени в argv[0].

У вас есть OS library process management, который дает вам прямой доступ к библиотеке ОС для этого. Вы должны рассмотреть возможность разбить свой сценарий на две части - стартер и «настоящую работу». Стартер устанавливает среду выполнения, а exec - реальную работу с требуемыми параметрами.

В C вы заменяете свой собственный процесс другим. В Python вы заменяете старый интерпретатор Python новым, у которого есть другой argv [0]. Надеюсь, на этом не будет. Некоторые программы проверяют argv [0], чтобы решить, что они делают.

У вас также есть subprocess.popen, который вы можете использовать, чтобы установить нужные аргументы и исполняемые файлы. В этом случае, однако, родительский процесс должен задерживаться, чтобы собрать ребенка, когда ребенок закончит. Родитель может не делать ничего больше, чем Popen.wait

+1

Нет, изменение argv в Linux (и, вероятно, другие Unix, но не все) немедленно изменяет имя видимого процесса, которое используется многими широко используемыми программами, чтобы дать описательные имена для их процессов: как ssh, так и postgres делают это, и некоторые активно меняют свое название «на лету», чтобы указать их текущий статус. Для этого можно написать модуль Python, используя вызов API Py_GetArgcArgv. –

45

на самом деле вам нужно 2 вещи на Linux: модифицируют argv[0] из C (для ps auxf и друзей) и называют prctl с PR_SET_NAME флагом.

Существует абсолютно никакой способ сделать первый кусок из самого python. Хотя вы можете просто изменить имя процесса, вызвав prctl.

def set_proc_name(newname): 
    from ctypes import cdll, byref, create_string_buffer 
    libc = cdll.LoadLibrary('libc.so.6') 
    buff = create_string_buffer(len(newname)+1) 
    buff.value = newname 
    libc.prctl(15, byref(buff), 0, 0, 0) 

def get_proc_name(): 
    from ctypes import cdll, byref, create_string_buffer 
    libc = cdll.LoadLibrary('libc.so.6') 
    buff = create_string_buffer(128) 
    # 16 == PR_GET_NAME from <linux/prctl.h> 
    libc.prctl(16, byref(buff), 0, 0, 0) 
    return buff.value 

import sys 
# sys.argv[0] == 'python' 

# outputs 'python' 
get_proc_name() 

set_proc_name('testing yeah') 

# outputs 'testing yeah' 
get_proc_name() 

ps auxf покажет только «питон» после этого :(. Но top и ps -A покажет новый «тестирование» ага имя процесса :). Также killall и pkill будут работать с новым именем.

btw, procname from googlecode также изменяет argv[0], таким образом, даже, изменения ps auxf вывод.

UPDATE: Решение, размещенное в этом ответе, иногда не играет на FreeBSD. Я сейчас использую py-setproctitle, заявленный in this answer в течение года или около того на различных Linux и FreeBSD. Пока не сработало! Всем тоже нужно! :). Он использует почти тот же код, что и PostgreSQLuses в своей основной базе данных и дочерних процессах.

+0

procname не работает на PyPy (только на CPython), необходимо использовать setproctitle. – radtek

67

Я недавно написал модуль Python, чтобы изменить название процесса переносимым способом: проверить https://github.com/dvarrazzo/py-setproctitle

Это обертка вокруг кода, используемого PostgreSQL для выполнения изменения заголовка. В настоящее время он протестирован на Linux и Mac OS X: Windows (с ограниченной функциональностью) и BSD-порты уже в пути.

Редактировать: по состоянию на июль 2010 года, модуль работает с BSD и имеет ограниченную функциональность в Windows и портирован на Python 3.x.

+0

Не удается установить на окна. – user

+0

@user не имеет значения: это не очень полезно для Windows, но об этом мало что нужно сделать. – piro

+0

Есть ли способ изменить аргументы, отображаемые ps -f? Мне все равно, что имя программы (всегда python), но я хочу изменить отображаемые аргументы. – KillianDS

5

Посмотрите на setproctitle пакет

Это вполне портативная версия и работает на многих платформах.

0

Я нашел python-prctl, чтобы работать очень хорошо под Linux. Вам нужно будет найти что-то еще для Windows.

2

Мой ответ на подобный вопрос, помеченный как duplicate:

Существует проще (не нужно импортировать любые LIBS), но, возможно, не так элегантно. Вы не должны использовать «env» внутри линии shebang.

Другими словами, это будет называться как «питона» в списке процессов:

#!/usr/bin/env python 

Но это будет называться с SCRIPTNAME:

#!/usr/bin/python 

Таким образом, вы будете иметь возможность найти его с чем-то вроде pidof -x scriptname или ps -C scriptname