Câu trả lời:
Bạn có thể tìm thấy exe dễ dàng bằng những cách này, chỉ cần tự mình thử nó.
ll /proc/<PID>/exe
pwdx <PID>
lsof -p <PID> | grep cwd
pwdx <PID>
đã cho tôi vị trí của liên kết tượng trưng để tôi có thể tìm thấy các bản ghi và dừng quá trình theo cách thích hợp.
ll
thường là một bí danh : alias ll='ls -alF'
.
Hơi muộn một chút, nhưng tất cả các câu trả lời đều dành riêng cho linux.
Nếu bạn cũng cần unix, thì bạn cần điều này:
char * getExecPath (char * path,size_t dest_len, char * argv0)
{
char * baseName = NULL;
char * systemPath = NULL;
char * candidateDir = NULL;
/* the easiest case: we are in linux */
size_t buff_len;
if (buff_len = readlink ("/proc/self/exe", path, dest_len - 1) != -1)
{
path [buff_len] = '\0';
dirname (path);
strcat (path, "/");
return path;
}
/* Ups... not in linux, no guarantee */
/* check if we have something like execve("foobar", NULL, NULL) */
if (argv0 == NULL)
{
/* we surrender and give current path instead */
if (getcwd (path, dest_len) == NULL) return NULL;
strcat (path, "/");
return path;
}
/* argv[0] */
/* if dest_len < PATH_MAX may cause buffer overflow */
if ((realpath (argv0, path)) && (!access (path, F_OK)))
{
dirname (path);
strcat (path, "/");
return path;
}
/* Current path */
baseName = basename (argv0);
if (getcwd (path, dest_len - strlen (baseName) - 1) == NULL)
return NULL;
strcat (path, "/");
strcat (path, baseName);
if (access (path, F_OK) == 0)
{
dirname (path);
strcat (path, "/");
return path;
}
/* Try the PATH. */
systemPath = getenv ("PATH");
if (systemPath != NULL)
{
dest_len--;
systemPath = strdup (systemPath);
for (candidateDir = strtok (systemPath, ":"); candidateDir != NULL; candidateDir = strtok (NULL, ":"))
{
strncpy (path, candidateDir, dest_len);
strncat (path, "/", dest_len);
strncat (path, baseName, dest_len);
if (access(path, F_OK) == 0)
{
free (systemPath);
dirname (path);
strcat (path, "/");
return path;
}
}
free(systemPath);
dest_len++;
}
/* again someone has use execve: we dont knowe the executable name; we surrender and give instead current path */
if (getcwd (path, dest_len - 1) == NULL) return NULL;
strcat (path, "/");
return path;
}
EDITED: Đã sửa lỗi được báo cáo bởi Mark lakata.
"/proc/self/exe"
bằngsprintf(foo,"/proc/%d/exe",pid)
Tôi sử dụng:
ps -ef | grep 786
Thay thế 786 bằng tên PID hoặc quy trình của bạn.
Trong Linux, mọi tiến trình đều có thư mục riêng /proc
. Vì vậy, bạn có thể sử dụng getpid()
để có được pid của quá trình đang chạy và sau đó tham gia nó với đường dẫn /proc
để có được thư mục mà bạn hy vọng cần.
Đây là một ví dụ ngắn trong Python:
import os
print os.path.join('/proc', str(os.getpid()))
Đây cũng là ví dụ trong ANSI C:
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/types.h>
int
main(int argc, char **argv)
{
pid_t pid = getpid();
fprintf(stdout, "Path to current process: '/proc/%d/'\n", (int)pid);
return EXIT_SUCCESS;
}
Biên dịch nó với:
gcc -Wall -Werror -g -ansi -pedantic process_path.c -oprocess_path
Không có phương pháp "đảm bảo làm việc ở bất cứ đâu".
Bước 1 là kiểm tra argv [0], nếu chương trình được bắt đầu bằng đường dẫn đầy đủ của nó, điều này sẽ (thường) có đường dẫn đầy đủ. Nếu nó được bắt đầu bởi một đường dẫn tương đối, thì giữ nguyên (mặc dù điều này đòi hỏi phải có thư mục làm việc hiện tại, sử dụng getcwd ().
Bước 2, nếu không có cách nào ở trên, là lấy tên của chương trình, sau đó lấy tên của chương trình từ argv [0], sau đó lấy PATH của người dùng từ môi trường và đi qua đó để xem có phù hợp không nhị phân thực thi có cùng tên.
Lưu ý rằng argv [0] được đặt bởi quá trình thực thi chương trình, vì vậy nó không đáng tin cậy 100%.
cảm ơn:
Kiwy
với AIX:
getPathByPid()
{
if [[ -e /proc/$1/object/a.out ]]; then
inode=`ls -i /proc/$1/object/a.out 2>/dev/null | awk '{print $1}'`
if [[ $? -eq 0 ]]; then
strnode=${inode}"$"
strNum=`ls -li /proc/$1/object/ 2>/dev/null | grep $strnode | awk '{print $NF}' | grep "[0-9]\{1,\}\.[0-9]\{1,\}\."`
if [[ $? -eq 0 ]]; then
# jfs2.10.6.5869
n1=`echo $strNum|awk -F"." '{print $2}'`
n2=`echo $strNum|awk -F"." '{print $3}'`
# brw-rw---- 1 root system 10, 6 Aug 23 2013 hd9var
strexp="^b.*"$n1,"[[:space:]]\{1,\}"$n2"[[:space:]]\{1,\}.*$" # "^b.*10, \{1,\}5 \{1,\}.*$"
strdf=`ls -l /dev/ | grep $strexp | awk '{print $NF}'`
if [[ $? -eq 0 ]]; then
strMpath=`df | grep $strdf | awk '{print $NF}'`
if [[ $? -eq 0 ]]; then
find $strMpath -inum $inode 2>/dev/null
if [[ $? -eq 0 ]]; then
return 0
fi
fi
fi
fi
fi
fi
return 1
}
Bạn cũng có thể nhận đường dẫn trên GNU / Linux với (chưa được kiểm tra kỹ lưỡng):
char file[32];
char buf[64];
pid_t pid = getpid();
sprintf(file, "/proc/%i/cmdline", pid);
FILE *f = fopen(file, "r");
fgets(buf, 64, f);
fclose(f);
Nếu bạn muốn thư mục của tệp thực thi có thể thay đổi thư mục làm việc sang thư mục của tiến trình (đối với phương tiện / dữ liệu / vv), bạn cần bỏ mọi thứ sau lần cuối /:
*strrchr(buf, '/') = '\0';
/*chdir(buf);*/
Lệnh dưới đây tìm kiếm tên của quy trình trong danh sách quy trình đang chạy và chuyển hướng lệnh pid sang pwdx để tìm vị trí của quy trình.
ps -ef | grep "abc" |grep -v grep| awk '{print $2}' | xargs pwdx
Thay thế "abc" bằng mẫu cụ thể của bạn.
Ngoài ra, nếu bạn có thể định cấu hình nó như một hàm trong .bashrc, bạn có thể thấy hữu ích khi sử dụng nếu bạn cần sử dụng nó thường xuyên.
ps1() { ps -ef | grep "$1" |grep -v grep| awk '{print $2}' | xargs pwdx; }
Ví dụ:
[admin@myserver:/home2/Avro/AvroGen]$ ps1 nifi
18404: /home2/Avro/NIFI
Hy vọng điều này sẽ giúp ai đó đôi khi .....
Tìm đường dẫn đến tên quy trình
#!/bin/bash
# @author Lukas Gottschall
PID=`ps aux | grep precessname | grep -v grep | awk '{ print $2 }'`
PATH=`ls -ald --color=never /proc/$PID/exe | awk '{ print $10 }'`
echo $PATH
pgrep
); trong dòng tiếp theo, nó nhận được đường dẫn của nhị phân được thực thi ( /proc/$PID/exe
là một liên kết tượng trưng đến tệp thực thi); và cuối cùng nó lặp lại symlink đó.
sudo
nếu đầu ra trống, một số quy trình được tạo bởi người dùng hệ thống khác.