ethr-wake: can use ether_hostton on uclibc >= 0.9.30
[oweals/busybox.git] / procps / fuser.c
index d625b16ab36183fd952098622a4bfb9ed54d62cf..dc3d01bdaa918aaa219eddf8c8d3c2f4e754cf1c 100644 (file)
@@ -4,8 +4,7 @@
  *
  * Copyright 2004 Tony J. White
  *
- * May be distributed under the conditions of the
- * GNU Library General Public License
+ * Licensed under GPLv2, see file LICENSE in this tarball for details.
  */
 
 #include "libbb.h"
@@ -57,11 +56,11 @@ static int file_to_dev_inode(const char *filename, dev_t *dev, ino_t *inode)
 
 static char *parse_net_arg(const char *arg, unsigned *port)
 {
-       char path[12], tproto[5];
+       char path[20], tproto[5];
 
        if (sscanf(arg, "%u/%4s", port, tproto) != 2)
                return NULL;
-       sprintf(path, "net/%s", tproto);
+       sprintf(path, "/proc/net/%s", tproto);
        if (access(path, R_OK) != 0)
                return NULL;
        return xstrdup(tproto);
@@ -99,8 +98,7 @@ static inode_list *add_inode(inode_list *ilist, dev_t dev, ino_t inode)
 static inode_list *scan_proc_net(const char *proto,
                                unsigned port, inode_list *ilist)
 {
-       char path[12], line[MAX_LINE + 1];
-       char addr[128];
+       char path[20], line[MAX_LINE + 1];
        ino_t tmp_inode;
        dev_t tmp_dev;
        long long uint64_inode;
@@ -109,19 +107,21 @@ static inode_list *scan_proc_net(const char *proto,
 
        tmp_dev = find_socket_dev();
 
-       sprintf(path, "net/%s", proto);
-       f = fopen(path, "r");
+       sprintf(path, "/proc/net/%s", proto);
+       f = fopen_for_read(path);
        if (!f)
                return ilist;
 
        while (fgets(line, MAX_LINE, f)) {
+               char addr[68];
                if (sscanf(line, "%*d: %64[0-9A-Fa-f]:%x %*x:%*x %*x %*x:%*x "
                                "%*x:%*x %*x %*d %*d %llu",
                                addr, &tmp_port, &uint64_inode) == 3
                ) {
-                       if (strlen(addr) == 8 && (option_mask32 & OPT_IP6))
+                       int len = strlen(addr);
+                       if (len == 8 && (option_mask32 & OPT_IP6))
                                continue;
-                       if (strlen(addr) > 8 && (option_mask32 & OPT_IP4))
+                       if (len > 8 && (option_mask32 & OPT_IP4))
                                continue;
                        if (tmp_port == port) {
                                tmp_inode = uint64_inode;
@@ -157,7 +157,7 @@ static pid_list *scan_pid_maps(const char *fname, pid_t pid,
        long long uint64_inode;
        dev_t dev;
 
-       file = fopen(fname, "r");
+       file = fopen_for_read(fname);
        if (!file)
                return plist;
        while (fgets(line, MAX_LINE, file)) {
@@ -208,6 +208,7 @@ static pid_list *scan_dir_links(const char *dname, pid_t pid,
        return plist;
 }
 
+/* NB: does chdir internally */
 static pid_list *scan_proc_pids(inode_list *ilist)
 {
        DIR *d;
@@ -215,7 +216,8 @@ static pid_list *scan_proc_pids(inode_list *ilist)
        pid_t pid;
        pid_list *plist;
 
-       d = opendir(".");
+       xchdir("/proc");
+       d = opendir("/proc");
        if (!d)
                return NULL;
 
@@ -267,7 +269,7 @@ static int kill_pid_list(pid_list *plist, int sig)
 }
 
 int fuser_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
-int fuser_main(int argc, char **argv)
+int fuser_main(int argc UNUSED_PARAM, char **argv)
 {
        pid_list *plist;
        inode_list *ilist;
@@ -314,8 +316,6 @@ Find processes which use FILEs or PORTs
        opt = getopt32(argv, OPTION_STRING);
        argv += optind;
 
-       xchdir("/proc");
-
        ilist = NULL;
        pp = argv;
        while (*pp) {
@@ -325,13 +325,13 @@ Find processes which use FILEs or PORTs
                        free(proto);
                } else { /* FILE */
                        if (!file_to_dev_inode(*pp, &dev, &inode))
-                               bb_perror_msg_and_die("can't open %s", *pp);
+                               bb_perror_msg_and_die("can't open '%s'", *pp);
                        ilist = add_inode(ilist, dev, inode);
                }
                pp++;
        }
 
-       plist = scan_proc_pids(ilist);
+       plist = scan_proc_pids(ilist); /* changes dir to "/proc" */
 
        if (!plist)
                return EXIT_FAILURE;