11d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich/* 21d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * netcap.c - A program that lists network apps with capabilities 31d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * Copyright (c) 2009-10 Red Hat Inc., Durham, North Carolina. 41d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * All Rights Reserved. 51d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * 61d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * This software may be freely redistributed and/or modified under the 71d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * terms of the GNU General Public License as published by the Free 81d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * Software Foundation; either version 2, or (at your option) any 91d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * later version. 101d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * 111d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * This program is distributed in the hope that it will be useful, 121d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * but WITHOUT ANY WARRANTY; without even the implied warranty of 131d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 141d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * GNU General Public License for more details. 151d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * 161d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * You should have received a copy of the GNU General Public License 171d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * along with this program; see the file COPYING. If not, write to the 181d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 191d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * 201d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * Authors: 211d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * Steve Grubb <sgrubb@redhat.com> 221d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * 231d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich * The /proc/net/tcp|udp|raw parsing code was borrowed from netstat.c 241d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich */ 251d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 261d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich#include "config.h" 271d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich#include <stdio.h> 281d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich#include <stdio_ext.h> 291d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich#include <stdlib.h> 301d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich#include <errno.h> 311d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich#include <string.h> 321d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich#include <dirent.h> 331d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich#include <fcntl.h> 341d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich#include <pwd.h> 351d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich#include "cap-ng.h" 361d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich#include "proc-llist.h" 371d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 381d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevichstatic llist l; 391d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevichstatic int perm_warn = 0, header = 0, last_uid = -1; 401d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevichstatic char *tacct = NULL; 411d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 421d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevichstatic void usage(void) 431d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich{ 441d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fprintf(stderr, "usage: netcap\n"); 451d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich exit(1); 461d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich} 471d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 481d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevichstatic int collect_process_info(void) 491d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich{ 501d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich DIR *d, *f; 511d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich struct dirent *ent; 521d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich d = opendir("/proc"); 531d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (d == NULL) { 541d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fprintf(stderr, "Can't open /proc: %s\n", strerror(errno)); 551d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich return 1; 561d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 571d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich while (( ent = readdir(d) )) { 581d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich FILE *sf; 591d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich int pid, ppid; 601d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich capng_results_t caps; 611d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich char buf[100]; 621d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich char *tmp, cmd[16], state, *text, *bounds; 631d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich int fd, len, euid = -1; 641d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 651d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // Skip non-process dir entries 661d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if(*ent->d_name<'0' || *ent->d_name>'9') 671d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 681d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich errno = 0; 691d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich pid = strtol(ent->d_name, NULL, 10); 701d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (errno) 711d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 721d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 731d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // Parse up the stat file for the proc 741d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich snprintf(buf, 32, "/proc/%d/stat", pid); 751d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fd = open(buf, O_RDONLY|O_CLOEXEC, 0); 761d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (fd < 0) 771d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 781d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich len = read(fd, buf, sizeof buf - 1); 791d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich close(fd); 801d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (len < 40) 811d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 821d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich buf[len] = 0; 831d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich tmp = strrchr(buf, ')'); 841d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (tmp) 851d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich *tmp = 0; 861d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich else 871d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 881d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich memset(cmd, 0, sizeof(cmd)); 891d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich sscanf(buf, "%d (%15c", &ppid, cmd); 901d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich sscanf(tmp+2, "%c %d", &state, &ppid); 911d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 921d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // Skip kthreads 931d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (pid == 2 || ppid == 2) 941d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 951d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 961d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // now get the capabilities 971d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich capng_clear(CAPNG_SELECT_BOTH); 981d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich capng_setpid(pid); 991d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (capng_get_caps_process()) 1001d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 1011d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich caps = capng_have_capabilities(CAPNG_SELECT_CAPS); 1021d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (caps <= CAPNG_NONE) 1031d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 1041d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (caps == CAPNG_FULL) 1051d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich text = strdup("full"); 1061d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich else 1071d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich text = capng_print_caps_text(CAPNG_PRINT_BUFFER, 1081d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich CAPNG_PERMITTED); 1091d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 1101d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // Get the effective uid 1111d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich snprintf(buf, 32, "/proc/%d/status", pid); 1121d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich sf = fopen(buf, "rte"); 1131d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (sf == NULL) 1141d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich euid = 0; 1151d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich else { 1161d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich int line = 0; 1171d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich __fsetlocking(sf, FSETLOCKING_BYCALLER); 1181d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich while (fgets(buf, sizeof(buf), sf)) { 1191d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (line == 0) { 1201d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich line++; 1211d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 1221d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 1231d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (memcmp(buf, "Uid:", 4) == 0) { 1241d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich int id; 1251d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich sscanf(buf, "Uid: %d %d", 1261d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich &id, &euid); 1271d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich break; 1281d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 1291d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 1301d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fclose(sf); 1311d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 1321d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 1331d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // Now record the bounding set information 1341d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (caps == CAPNG_PARTIAL) { 1351d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich caps = capng_have_capabilities(CAPNG_SELECT_BOUNDS); 1361d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (caps == CAPNG_FULL) 1371d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich bounds = strdup("+"); 1381d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich else 1391d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich bounds = strdup(""); 1401d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } else 1411d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich bounds = strdup(""); 1421d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 1431d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // Now lets get the inodes each process has open 1441d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich snprintf(buf, 32, "/proc/%d/fd", pid); 1451d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich f = opendir(buf); 1461d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (f == NULL) { 1471d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (errno == EACCES) { 1481d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (perm_warn == 0) { 1491d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich printf("You may need to be root to " 1501d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich "get a full report\n"); 1511d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich perm_warn = 1; 1521d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 1531d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } else 1541d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fprintf(stderr, "Can't open %s: %s\n", buf, 1551d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich strerror(errno)); 1561d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich free(text); 1571d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich free(bounds); 1581d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 1591d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 1601d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // For each file in the fd dir... 1611d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich while (( ent = readdir(f) )) { 1621d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich char line[256], ln[256], *s, *e; 1631d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich unsigned long inode; 1641d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich lnode node; 1651d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich int llen; 1661d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 1671d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (ent->d_name[0] == '.') 1681d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 1691d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich snprintf(ln, 256, "%s/%s", buf, ent->d_name); 1701d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if ((llen = readlink(ln, line, sizeof(line)-1)) < 0) 1711d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 1721d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich line[llen] = 0; 1731d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 1741d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // Only look at the socket entries 1751d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (memcmp(line, "socket:", 7) == 0) { 1761d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // Type 1 sockets 1771d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich s = strchr(line+7, '['); 1781d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (s == NULL) 1791d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 1801d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich s++; 1811d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich e = strchr(s, ']'); 1821d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (e == NULL) 1831d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 1841d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich *e = 0; 1851d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } else if (memcmp(line, "[0000]:", 7) == 0) { 1861d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // Type 2 sockets 1871d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich s = line + 8; 1881d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } else 1891d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 1901d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich errno = 0; 1911d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich inode = strtoul(s, NULL, 10); 1921d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (errno) 1931d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 1941d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich node.ppid = ppid; 1951d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich node.pid = pid; 1961d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich node.uid = euid; 1971d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich node.cmd = strdup(cmd); 1981d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich node.inode = inode; 1991d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich node.capabilities = strdup(text); 2001d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich node.bounds = strdup(bounds); 2011d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // We make one entry for each socket inode 2021d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich list_append(&l, &node); 2031d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 2041d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich closedir(f); 2051d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich free(text); 2061d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich free(bounds); 2071d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 2081d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich closedir(d); 2091d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich return 0; 2101d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich} 2111d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 2121d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevichstatic void report_finding(int port, const char *type, const char *ifc) 2131d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich{ 2141d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich struct passwd *p; 2151d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich lnode *n = list_get_cur(&l); 2161d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 2171d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // And print out anything with capabilities 2181d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (header == 0) { 2191d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich printf("%-5s %-5s %-10s %-16s %-4s %-6s %s\n", 2201d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich "ppid", "pid", "acct", "command", "type", "port", 2211d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich "capabilities"); 2221d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich header = 1; 2231d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 2241d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (n->uid == 0) { 2251d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // Take short cut for this one 2261d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich tacct = "root"; 2271d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich last_uid = 0; 2281d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } else if (last_uid != (int)n->uid) { 2291d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // Only look up if name changed 2301d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich p = getpwuid(n->uid); 2311d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich last_uid = n->uid; 2321d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (p) 2331d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich tacct = p->pw_name; 2341d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // If not taking this branch, use last val 2351d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 2361d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (tacct) { 2371d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich printf("%-5d %-5d %-10s", n->ppid, n->pid, tacct); 2381d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } else 2391d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich printf("%-5d %-5d %-10d", n->ppid, n->pid, last_uid); 2401d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich printf(" %-16s %-4s", n->cmd, type); 2411d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (ifc) 2421d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich printf(" %-6s", ifc); 2431d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich else 2441d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich printf(" %-6d", port); 2451d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich printf(" %s %s\n", n->capabilities, n->bounds); 2461d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich} 2471d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 2481d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevichstatic void read_tcp(const char *proc, const char *type) 2491d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich{ 2501d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich int line = 0; 2511d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich FILE *f; 2521d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich char buf[256]; 2531d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich unsigned long rxq, txq, time_len, retr, inode; 2541d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich int local_port, rem_port, d, state, timer_run, uid, timeout; 2551d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich char rem_addr[128], local_addr[128], more[512]; 2561d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 2571d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich f = fopen(proc, "rte"); 2581d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (f == NULL) { 2591d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (errno != ENOENT) 2601d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fprintf(stderr, "Can't open %s: %s\n", 2611d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich proc, strerror(errno)); 2621d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich return; 2631d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 2641d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich __fsetlocking(f, FSETLOCKING_BYCALLER); 2651d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich while (fgets(buf, sizeof(buf), f)) { 2661d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (line == 0) { 2671d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich line++; 2681d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 2691d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 2701d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich more[0] = 0; 2711d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich sscanf(buf, "%d: %64[0-9A-Fa-f]:%X %64[0-9A-Fa-f]:%X %X " 2721d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich "%lX:%lX %X:%lX %lX %d %d %lu %512s\n", 2731d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich &d, local_addr, &local_port, rem_addr, &rem_port, 2741d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich &state, &txq, &rxq, &timer_run, &time_len, &retr, 2751d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich &uid, &timeout, &inode, more); 2761d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (list_find_inode(&l, inode)) 2771d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich report_finding(local_port, type, NULL); 2781d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 2791d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fclose(f); 2801d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich} 2811d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 2821d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevichstatic void read_udp(const char *proc, const char *type) 2831d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich{ 2841d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich int line = 0; 2851d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich FILE *f; 2861d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich char buf[256]; 2871d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich unsigned long rxq, txq, time_len, retr, inode; 2881d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich int local_port, rem_port, d, state, timer_run, uid, timeout; 2891d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich char rem_addr[128], local_addr[128], more[512]; 2901d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 2911d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich f = fopen(proc, "rte"); 2921d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (f == NULL) { 2931d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (errno != ENOENT) 2941d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fprintf(stderr, "Can't open %s: %s\n", 2951d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich proc, strerror(errno)); 2961d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich return; 2971d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 2981d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich __fsetlocking(f, FSETLOCKING_BYCALLER); 2991d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich while (fgets(buf, sizeof(buf), f)) { 3001d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (line == 0) { 3011d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich line++; 3021d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 3031d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 3041d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich more[0] = 0; 3051d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich sscanf(buf, "%d: %64[0-9A-Fa-f]:%X %64[0-9A-Fa-f]:%X %X " 3061d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich "%lX:%lX %X:%lX %lX %d %d %lu %512s\n", 3071d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich &d, local_addr, &local_port, rem_addr, &rem_port, 3081d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich &state, &txq, &rxq, &timer_run, &time_len, &retr, 3091d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich &uid, &timeout, &inode, more); 3101d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (list_find_inode(&l, inode)) 3111d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich report_finding(local_port, type, NULL); 3121d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 3131d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fclose(f); 3141d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich} 3151d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 3161d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevichstatic void read_raw(const char *proc, const char *type) 3171d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich{ 3181d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich int line = 0; 3191d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich FILE *f; 3201d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich char buf[256]; 3211d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich unsigned long rxq, txq, time_len, retr, inode; 3221d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich int local_port, rem_port, d, state, timer_run, uid, timeout; 3231d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich char rem_addr[128], local_addr[128], more[512]; 3241d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 3251d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich f = fopen(proc, "rte"); 3261d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (f == NULL) { 3271d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (errno != ENOENT) 3281d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fprintf(stderr, "Can't open %s: %s\n", 3291d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich proc, strerror(errno)); 3301d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich return; 3311d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 3321d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich __fsetlocking(f, FSETLOCKING_BYCALLER); 3331d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich while (fgets(buf, sizeof(buf), f)) { 3341d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (line == 0) { 3351d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich line++; 3361d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 3371d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 3381d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich more[0] = 0; 3391d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich sscanf(buf, "%d: %64[0-9A-Fa-f]:%X %64[0-9A-Fa-f]:%X %X " 3401d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich "%lX:%lX %X:%lX %lX %d %d %lu %512s\n", 3411d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich &d, local_addr, &local_port, rem_addr, &rem_port, 3421d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich &state, &txq, &rxq, &timer_run, &time_len, &retr, 3431d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich &uid, &timeout, &inode, more); 3441d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (list_find_inode(&l, inode)) 3451d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich report_finding(0, type, NULL); 3461d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 3471d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fclose(f); 3481d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich} 3491d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 3501d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich// Caller must have buffer > 16 bytes 3511d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevichstatic void get_interface(unsigned int iface, char *ifc) 3521d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich{ 3531d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich unsigned int line = 0; 3541d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich FILE *f; 3551d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich char buf[256], more[256]; 3561d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 3571d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // Terminate the interface in case of error 3581d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich *ifc = 0; 3591d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 3601d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // Increment the interface number since header is 2 lines long 3611d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich iface++; 3621d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 3631d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich f = fopen("/proc/net/dev", "rte"); 3641d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (f == NULL) { 3651d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (errno != ENOENT) 3661d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fprintf(stderr, "Can't open /proc/net/dev: %s\n", 3671d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich strerror(errno)); 3681d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich return; 3691d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 3701d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich __fsetlocking(f, FSETLOCKING_BYCALLER); 3711d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich while (fgets(buf, sizeof(buf), f)) { 3721d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (line == iface) { 3731d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich char *c; 3741d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich sscanf(buf, "%16s: %256s\n", ifc, more); 3751d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich c = strchr(ifc, ':'); 3761d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (c) 3771d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich *c = 0; 3781d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fclose(f); 3791d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich return; 3801d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 3811d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich line++; 3821d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 3831d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fclose(f); 3841d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich} 3851d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 3861d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevichstatic void read_packet(void) 3871d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich{ 3881d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich int line = 0; 3891d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich FILE *f; 3901d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich char buf[256]; 3911d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich unsigned long sk, inode; 3921d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich unsigned int ref_cnt, type, proto, iface, r, rmem, uid; 3931d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich char more[256], ifc[32]; 3941d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 3951d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich f = fopen("/proc/net/packet", "rte"); 3961d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (f == NULL) { 3971d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (errno != ENOENT) 3981d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fprintf(stderr, "Can't open /proc/net/packet: %s\n", 3991d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich strerror(errno)); 4001d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich return; 4011d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 4021d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich __fsetlocking(f, FSETLOCKING_BYCALLER); 4031d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich while (fgets(buf, sizeof(buf), f)) { 4041d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (line == 0) { 4051d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich line++; 4061d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich continue; 4071d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 4081d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich more[0] = 0; 4091d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich sscanf(buf, "%lX %u %u %X %u %u %u %u %lu %256s\n", 4101d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich &sk, &ref_cnt, &type, &proto, &iface, 4111d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich &r, &rmem, &uid, &inode, more); 4121d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich get_interface(iface, ifc); 4131d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (list_find_inode(&l, inode)) 4141d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich report_finding(0, "pkt", ifc); 4151d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 4161d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fclose(f); 4171d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich} 4181d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 4191d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevichint main(int argc, char __attribute__((unused)) *argv[]) 4201d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich{ 4211d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich if (argc > 1) { 4221d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich fputs("Too many arguments\n", stderr); 4231d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich usage(); 4241d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich } 4251d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 4261d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich list_create(&l); 4271d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich collect_process_info(); 4281d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 4291d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // Now we check the tcp socket list... 4301d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich read_tcp("/proc/net/tcp", "tcp"); 4311d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich read_tcp("/proc/net/tcp6", "tcp6"); 4321d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 4331d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // Next udp sockets... 4341d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich read_udp("/proc/net/udp", "udp"); 4351d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich read_udp("/proc/net/udp6", "udp6"); 4361d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 4371d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // Next, raw sockets... 4381d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich read_raw("/proc/net/raw", "raw"); 4391d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich read_raw("/proc/net/raw6", "raw6"); 4401d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 4411d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich // And last, read packet sockets 4421d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich read_packet(); 4431d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 4441d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich list_clear(&l); 4451d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich return 0; 4461d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich} 4471d1011a3c5049a7f9eef99d22f3704e4367579ccNick Kralevich 448