/* symlink */ int tar_extract_symlink(TAR *t, char *realname) { char *filename; if (!TH_ISSYM(t)) { errno = EINVAL; return -1; } filename = (realname ? realname : th_get_pathname(t)); if (mkdirhier(dirname(filename)) == -1) return -1; if (unlink(filename) == -1 && errno != ENOENT) return -1; #ifdef DEBUG printf(" ==> extracting: %s (symlink to %s)\n", filename, th_get_linkname(t)); #endif if (symlink(th_get_linkname(t), filename) == -1) { #ifdef DEBUG perror("symlink()"); #endif return -1; } return 0; }
void prepareMeleeDir (void) { char buf[PATH_MAX]; const char *meleeDirName; meleeDirName = getenv("UQM_MELEE_DIR"); if (meleeDirName == NULL) meleeDirName = MELEEDIR; if (expandPath (buf, PATH_MAX - 13, meleeDirName, EP_ALL_SYSTEM) == -1) { // Doesn't have to be fatal, but might mess up things when saving // config files. log_add (log_Fatal, "Fatal error: Invalid path to config files."); exit (EXIT_FAILURE); } meleeDirName = buf; setenv("UQM_MELEE_DIR", meleeDirName, 1); // Create the path upto the save dir, if not already existing. if (mkdirhier (meleeDirName) == -1) exit (EXIT_FAILURE); meleeDir = uio_openDirRelative (configDir, "teams", 0); // TODO: this doesn't work if the save dir is not // "teams" in the config dir. if (meleeDir == NULL) { log_add (log_Fatal, "Fatal error: Could not open melee teams dir: %s", strerror (errno)); exit (EXIT_FAILURE); } }
/* FIFO */ int tar_extract_fifo(TAR *t, char *realname) { mode_t mode; char *filename; if (!TH_ISFIFO(t)) { errno = EINVAL; return -1; } filename = (realname ? realname : th_get_pathname(t)); mode = th_get_mode(t); if (mkdirhier(dirname(filename)) == -1) return -1; #ifdef DEBUG printf(" ==> extracting: %s (fifo)\n", filename); #endif if (mkfifo(filename, mode) == -1) { #ifdef DEBUG perror("mkfifo()"); #endif return -1; } return 0; }
void init_master(void) { struct snmp_session sess, *session; if ( ds_get_boolean(DS_APPLICATION_ID, DS_AGENT_ROLE) != MASTER_AGENT ) return; DEBUGMSGTL(("agentx/master","initializing...\n")); snmp_sess_init( &sess ); sess.version = AGENTX_VERSION_1; sess.flags |= SNMP_FLAGS_STREAM_SOCKET; if ( ds_get_string(DS_APPLICATION_ID, DS_AGENT_X_SOCKET) ) sess.peername = strdup(ds_get_string(DS_APPLICATION_ID, DS_AGENT_X_SOCKET)); else sess.peername = strdup(AGENTX_SOCKET); if ( sess.peername[0] == '/' ) { /* * If this is a Unix pathname, * try and create the directory first. */ if (mkdirhier(sess.peername, AGENT_DIRECTORY_MODE, 1)) { snmp_log(LOG_ERR, "Failed to create the directory for the agentX socket: %s\n", sess.peername); } } /* * Otherwise, let 'snmp_open' interpret the string. */ sess.local_port = AGENTX_PORT; /* Indicate server & set default port */ sess.remote_port = 0; sess.callback = handle_master_agentx_packet; session = snmp_open_ex( &sess, 0, agentx_parse, 0, agentx_build, agentx_check_packet ); if ( session == NULL && sess.s_errno == EADDRINUSE ) { /* * Could be a left-over socket (now deleted) * Try again */ session = snmp_open_ex( &sess, 0, agentx_parse, 0, agentx_build, agentx_check_packet ); } if ( session == NULL ) { /* diagnose snmp_open errors with the input struct snmp_session pointer */ snmp_sess_perror("init_master", &sess); if (!ds_get_boolean(DS_APPLICATION_ID, DS_AGENT_NO_ROOT_ACCESS)) exit(1); } DEBUGMSGTL(("agentx/master","initializing... DONE\n")); }
void prepareConfigDir (const char *configDirName) { char buf[PATH_MAX]; static uio_AutoMount *autoMount[] = { NULL }; uio_MountHandle *contentHandle; if (configDirName == NULL) { configDirName = getenv("UQM_CONFIG_DIR"); if (configDirName == NULL) configDirName = CONFIGDIR; } if (expandPath (buf, PATH_MAX - 13, configDirName, EP_ALL_SYSTEM) == -1) { // Doesn't have to be fatal, but might mess up things when saving // config files. log_add (log_Fatal, "Fatal error: Invalid path to config files."); exit (EXIT_FAILURE); } configDirName = buf; log_add (log_Debug, "Using config dir '%s'", configDirName); // Set the environment variable UQM_CONFIG_DIR so UQM_MELEE_DIR // and UQM_SAVE_DIR can refer to it. setenv("UQM_CONFIG_DIR", configDirName, 1); // Create the path upto the config dir, if not already existing. if (mkdirhier (configDirName) == -1) exit (EXIT_FAILURE); contentHandle = uio_mountDir (repository, "/", uio_FSTYPE_STDIO, NULL, NULL, configDirName, autoMount, uio_MOUNT_TOP, NULL); if (contentHandle == NULL) { log_add (log_Fatal, "Fatal error: Could not mount config dir: %s", strerror (errno)); exit (EXIT_FAILURE); } configDir = uio_openDir (repository, "/", 0); if (configDir == NULL) { log_add (log_Fatal, "Fatal error: Could not open config dir: %s", strerror (errno)); exit (EXIT_FAILURE); } }
/* directory */ int tar_extract_dir(TAR *t, char *realname) { mode_t mode; char *filename; if (!TH_ISDIR(t)) { errno = EINVAL; return -1; } filename = (realname ? realname : th_get_pathname(t)); mode = th_get_mode(t); if (mkdirhier(dirname(filename)) == -1) return -1; #ifdef DEBUG printf(" ==> extracting: %s (mode %04o, directory)\n", filename, mode); #endif if (mkdir(filename, mode) == -1) { if (errno == EEXIST) { if (chmod(filename, mode) == -1) { #ifdef DEBUG perror("chmod()"); #endif return -1; } else { #ifdef DEBUG puts(" *** using existing directory"); #endif return 1; } } else { #ifdef DEBUG perror("mkdir()"); #endif return -1; } } return 0; }
/* hardlink */ int tar_extract_hardlink(TAR * t, char *realname, char *prefix) { char *filename; char *linktgt = NULL; char *lnp; libtar_hashptr_t hp; if (!TH_ISLNK(t)) { errno = EINVAL; return -1; } filename = (realname ? realname : th_get_pathname(t)); if (mkdirhier(dirname(filename)) == -1) return -1; libtar_hashptr_reset(&hp); if (libtar_hash_getkey(t->h, &hp, th_get_linkname(t), (libtar_matchfunc_t)libtar_str_match) != 0) { lnp = (char *)libtar_hashptr_data(&hp); linktgt = &lnp[strlen(lnp) + 1]; } else linktgt = th_get_linkname(t); char *newtgt = strdup(linktgt); sprintf(linktgt, "%s/%s", prefix, newtgt); #ifdef DEBUG printf(" ==> extracting: %s (link to %s)\n", filename, linktgt); #endif if (link(linktgt, filename) == -1) { #ifdef DEBUG perror("link()"); #endif printf("Failed restore of hardlink '%s' but returning as if nothing bad happened anyway\n", filename); return 0; // Used to be -1 } return 0; }
int CThemes::Show() { std::string file_name = ""; CMenuWidget themes (LOCALE_COLORMENU_MENUCOLORS, NEUTRINO_ICON_SETTINGS, width); themes.addIntroItems(LOCALE_COLORTHEMEMENU_HEAD2); //set default theme themes.addItem(new CMenuForwarder(LOCALE_COLORTHEMEMENU_NEUTRINO_THEME, true, NULL, this, "theme_neutrino", CRCInput::RC_red)); readThemes(themes); CStringInputSMS nameInput(LOCALE_COLORTHEMEMENU_NAME, &file_name, 30, NONEXISTANT_LOCALE, NONEXISTANT_LOCALE, "abcdefghijklmnopqrstuvwxyz0123456789- "); CMenuForwarder *m1 = new CMenuForwarder(LOCALE_COLORTHEMEMENU_SAVE, true , NULL, &nameInput, NULL, CRCInput::RC_green); if (mkdirhier(USERDIR) && errno != EEXIST) { printf("[neutrino theme] error creating %s\n", USERDIR); } if (access(USERDIR, F_OK) == 0 ) { themes.addItem(GenericMenuSeparatorLine); themes.addItem(m1); } else { delete m1; printf("[neutrino theme] error accessing %s\n", USERDIR); } int res = themes.exec(NULL, ""); if (file_name.length() > 1) { saveFile((char*)((std::string)USERDIR + file_name + FILE_PREFIX).c_str()); } if (hasThemeChanged) { if (ShowMsg(LOCALE_MESSAGEBOX_INFO, LOCALE_COLORTHEMEMENU_QUESTION, CMessageBox::mbrYes, CMessageBox::mbYes | CMessageBox::mbNo, NEUTRINO_ICON_SETTINGS) != CMessageBox::mbrYes) rememberOldTheme( false ); else hasThemeChanged = false; } return res; }
/*******************************************************************-o-****** * read_config_store * * Parameters: * *type * *line * * * Append line to a file named either ENV(SNMP_PERSISTENT_FILE) or * "<PERSISTENT_DIRECTORY>/<type>.conf". * Add a trailing newline to the stored file if necessary. * * Intended for use by applications to store permenant configuration * information generated by sets or persistent counters. * */ void read_config_store(const char *type, const char *line) { #ifdef CYGPKG_SNMPLIB_PERSISTENT_FILESYSTEM char file[512], *filep; FILE *fout; #ifdef PERSISTENT_MASK mode_t oldmask; #endif /* store configuration directives in the following order of preference: 1. ENV variable SNMP_PERSISTENT_FILE 2. configured <PERSISTENT_DIRECTORY>/<type>.conf */ if ((filep = getenv("SNMP_PERSISTENT_FILE")) == NULL) { sprintf(file,"%s/%s.conf",PERSISTENT_DIRECTORY,type); filep = file; } #ifdef PERSISTENT_MASK oldmask = umask(PERSISTENT_MASK); #endif if (mkdirhier(filep, AGENT_DIRECTORY_MODE, 1)) { snmp_log(LOG_ERR, "Failed to create the persistent directory for %s\n", file); } if ((fout = fopen(filep, "a")) != NULL) { fprintf(fout,line); if (line[strlen(line)] != '\n') fprintf(fout,"\n"); DEBUGMSGTL(("read_config","storing: %s\n",line)); fclose(fout); } else { DEBUGMSGTL(("read_config","open failure")); } #ifdef PERSISTENT_MASK umask(oldmask); #endif #endif } /* end read_config_store() */
/* hardlink */ int tar_extract_hardlink(TAR * t, char *realname) { char *filename; char *linktgt = NULL; char *lnp; libtar_hashptr_t hp; if (!TH_ISLNK(t)) { errno = EINVAL; return -1; } filename = (realname ? realname : th_get_pathname(t)); if (mkdirhier(dirname(filename)) == -1) return -1; libtar_hashptr_reset(&hp); if (libtar_hash_getkey(t->h, &hp, th_get_linkname(t), (libtar_matchfunc_t)libtar_str_match) != 0) { lnp = (char *)libtar_hashptr_data(&hp); linktgt = &lnp[strlen(lnp) + 1]; } else linktgt = th_get_linkname(t); #ifdef DEBUG printf(" ==> extracting: %s (link to %s)\n", filename, linktgt); #endif if (link(linktgt, filename) == -1) { #ifdef DEBUG perror("link()"); #endif return -1; } return 0; }
/* block device */ int tar_extract_blockdev(TAR *t, char *realname) { mode_t mode; unsigned long devmaj, devmin; char *filename; if (!TH_ISBLK(t)) { errno = EINVAL; return -1; } filename = (realname ? realname : th_get_pathname(t)); mode = th_get_mode(t); devmaj = th_get_devmajor(t); devmin = th_get_devminor(t); if (mkdirhier(dirname(filename)) == -1) return -1; #ifdef DEBUG printf(" ==> extracting: %s (block device %ld,%ld)\n", filename, devmaj, devmin); #endif if (mknod(filename, mode | S_IFBLK, makedev(devmaj, devmin)) == -1) { #ifdef DEBUG perror("mknod()"); #endif return -1; } return 0; }
/* character device */ int tar_extract_chardev(TAR *t, char *realname) { mode_t mode; unsigned long devmaj, devmin; char *filename; if (!TH_ISCHR(t)) { errno = EINVAL; return -1; } filename = (realname ? realname : th_get_pathname(t)); mode = th_get_mode(t); devmaj = th_get_devmajor(t); devmin = th_get_devminor(t); if (mkdirhier(dirname(filename)) == -1) return -1; #ifdef DEBUG printf(" ==> extracting: %s (character device %ld,%ld)\n", filename, devmaj, devmin); #endif if (mknod(filename, mode | S_IFCHR, compat_makedev(devmaj, devmin)) == -1) { #ifdef DEBUG printf("mknod() failed, returning good anyway"); #endif return 0; } return 0; }
main(int argc, char *argv[]) #endif { char options[128] = "aAc:CdD::fhHI:l:L:m:M:n:p:P:qrsS:UvV-:Y:"; int arg, i, ret; int dont_fork = 0, do_help = 0; int log_set = 0; int agent_mode = -1; char *pid_file = NULL; char option_compatability[] = "-Le"; #ifndef WIN32 int prepared_sockets = 0; #endif #if HAVE_GETPID int fd; FILE *PID; #endif #ifndef WIN32 #ifndef NETSNMP_NO_SYSTEMD /* check if systemd has sockets for us and don't close them */ prepared_sockets = netsnmp_sd_listen_fds(0); #endif /* NETSNMP_NO_SYSTEMD */ /* * close all non-standard file descriptors we may have * inherited from the shell. */ if (!prepared_sockets) { for (i = getdtablesize() - 1; i > 2; --i) { (void) close(i); } } #endif /* #WIN32 */ /* * register signals ASAP to prevent default action (usually core) * for signals during startup... */ #ifdef SIGTERM DEBUGMSGTL(("signal", "registering SIGTERM signal handler\n")); signal(SIGTERM, SnmpdShutDown); #endif #ifdef SIGINT DEBUGMSGTL(("signal", "registering SIGINT signal handler\n")); signal(SIGINT, SnmpdShutDown); #endif #ifdef SIGHUP signal(SIGHUP, SIG_IGN); /* do not terminate on early SIGHUP */ #endif #ifdef SIGUSR1 DEBUGMSGTL(("signal", "registering SIGUSR1 signal handler\n")); signal(SIGUSR1, SnmpdDump); #endif #ifdef SIGPIPE DEBUGMSGTL(("signal", "registering SIGPIPE signal handler\n")); signal(SIGPIPE, SIG_IGN); /* 'Inline' failure of wayward readers */ #endif #ifdef SIGXFSZ signal(SIGXFSZ, SnmpdCatchRandomSignal); #endif #ifdef NETSNMP_NO_ROOT_ACCESS /* * Default to no. */ netsnmp_ds_set_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_NO_ROOT_ACCESS, 1); #endif /* * Default to NOT running an AgentX master. */ netsnmp_ds_set_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_AGENTX_MASTER, 0); netsnmp_ds_set_int(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_AGENTX_TIMEOUT, -1); netsnmp_ds_set_int(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_AGENTX_RETRIES, -1); netsnmp_ds_set_int(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_CACHE_TIMEOUT, 5); /* * Add some options if they are available. */ #if HAVE_UNISTD_H strcat(options, "g:u:"); #endif #if defined(USING_AGENTX_SUBAGENT_MODULE)|| defined(USING_AGENTX_MASTER_MODULE) strcat(options, "x:"); #endif #ifdef USING_AGENTX_SUBAGENT_MODULE strcat(options, "X"); #endif /* * This is incredibly ugly, but it's probably the simplest way * to handle the old '-L' option as well as the new '-Lx' style */ for (i=0; i<argc; i++) { if (!strcmp(argv[i], "-L")) argv[i] = option_compatability; } #ifndef NETSNMP_FEATURE_REMOVE_LOGGING_SYSLOG #ifdef WIN32 snmp_log_syslogname(app_name_long); #else snmp_log_syslogname(app_name); #endif #endif /* NETSNMP_FEATURE_REMOVE_LOGGING_SYSLOG */ netsnmp_ds_set_string(NETSNMP_DS_LIBRARY_ID, NETSNMP_DS_LIB_APPTYPE, app_name); /* * Now process options normally. */ while ((arg = getopt(argc, argv, options)) != EOF) { switch (arg) { case '-': if (strcasecmp(optarg, "help") == 0) { usage(argv[0]); } if (strcasecmp(optarg, "version") == 0) { version(); } handle_long_opt(optarg); break; case 'a': log_addresses++; break; case 'A': netsnmp_ds_set_boolean(NETSNMP_DS_LIBRARY_ID, NETSNMP_DS_LIB_APPEND_LOGFILES, 1); break; case 'c': if (optarg != NULL) { netsnmp_ds_set_string(NETSNMP_DS_LIBRARY_ID, NETSNMP_DS_LIB_OPTIONALCONFIG, optarg); } else { usage(argv[0]); } break; case 'C': netsnmp_ds_set_boolean(NETSNMP_DS_LIBRARY_ID, NETSNMP_DS_LIB_DONT_READ_CONFIGS, 1); break; case 'd': netsnmp_ds_set_boolean(NETSNMP_DS_LIBRARY_ID, NETSNMP_DS_LIB_DUMP_PACKET, ++snmp_dump_packet); break; case 'D': debug_register_tokens(optarg); snmp_set_do_debugging(1); break; case 'f': dont_fork = 1; break; #if HAVE_UNISTD_H case 'g': if (optarg != NULL) { char *ecp; int gid; gid = strtoul(optarg, &ecp, 10); #if HAVE_GETGRNAM && HAVE_PWD_H if (*ecp) { struct group *info; info = getgrnam(optarg); gid = info ? info->gr_gid : -1; endgrent(); } #endif if (gid < 0) { fprintf(stderr, "Bad group id: %s\n", optarg); exit(1); } netsnmp_ds_set_int(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_GROUPID, gid); } else { usage(argv[0]); } break; #endif case 'h': usage(argv[0]); break; case 'H': do_help = 1; break; case 'I': if (optarg != NULL) { add_to_init_list(optarg); } else { usage(argv[0]); } break; #ifndef NETSNMP_FEATURE_REMOVE_LOGGING_FILE case 'l': printf("Warning: -l option is deprecated, use -Lf <file> instead\n"); if (optarg != NULL) { if (strlen(optarg) > PATH_MAX) { fprintf(stderr, "%s: logfile path too long (limit %d chars)\n", argv[0], PATH_MAX); exit(1); } snmp_enable_filelog(optarg, netsnmp_ds_get_boolean(NETSNMP_DS_LIBRARY_ID, NETSNMP_DS_LIB_APPEND_LOGFILES)); log_set = 1; } else { usage(argv[0]); } break; #endif /* NETSNMP_FEATURE_REMOVE_LOGGING_FILE */ case 'L': if (snmp_log_options( optarg, argc, argv ) < 0 ) { usage(argv[0]); } log_set = 1; break; case 'm': if (optarg != NULL) { setenv("MIBS", optarg, 1); } else { usage(argv[0]); } break; case 'M': if (optarg != NULL) { setenv("MIBDIRS", optarg, 1); } else { usage(argv[0]); } break; case 'n': if (optarg != NULL) { app_name = optarg; netsnmp_ds_set_string(NETSNMP_DS_LIBRARY_ID, NETSNMP_DS_LIB_APPTYPE, app_name); } else { usage(argv[0]); } break; case 'P': printf("Warning: -P option is deprecated, use -p instead\n"); case 'p': if (optarg != NULL) { pid_file = optarg; } else { usage(argv[0]); } break; case 'q': netsnmp_ds_set_boolean(NETSNMP_DS_LIBRARY_ID, NETSNMP_DS_LIB_QUICK_PRINT, 1); break; case 'r': netsnmp_ds_toggle_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_NO_ROOT_ACCESS); break; #ifndef NETSNMP_FEATURE_REMOVE_LOGGING_SYSLOG case 's': printf("Warning: -s option is deprecated, use -Lsd instead\n"); snmp_enable_syslog(); log_set = 1; break; case 'S': printf("Warning: -S option is deprecated, use -Ls <facility> instead\n"); if (optarg != NULL) { switch (*optarg) { case 'd': case 'D': Facility = LOG_DAEMON; break; case 'i': case 'I': Facility = LOG_INFO; break; case '0': Facility = LOG_LOCAL0; break; case '1': Facility = LOG_LOCAL1; break; case '2': Facility = LOG_LOCAL2; break; case '3': Facility = LOG_LOCAL3; break; case '4': Facility = LOG_LOCAL4; break; case '5': Facility = LOG_LOCAL5; break; case '6': Facility = LOG_LOCAL6; break; case '7': Facility = LOG_LOCAL7; break; default: fprintf(stderr, "invalid syslog facility: -S%c\n",*optarg); usage(argv[0]); } snmp_enable_syslog_ident(snmp_log_syslogname(NULL), Facility); log_set = 1; } else { fprintf(stderr, "no syslog facility specified\n"); usage(argv[0]); } break; #endif /* NETSNMP_FEATURE_REMOVE_LOGGING_SYSLOG */ case 'U': netsnmp_ds_toggle_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_LEAVE_PIDFILE); break; #if HAVE_UNISTD_H case 'u': if (optarg != NULL) { char *ecp; int uid; uid = strtoul(optarg, &ecp, 10); #if HAVE_GETPWNAM && HAVE_PWD_H if (*ecp) { struct passwd *info; info = getpwnam(optarg); uid = info ? info->pw_uid : -1; endpwent(); } #endif if (uid < 0) { fprintf(stderr, "Bad user id: %s\n", optarg); exit(1); } netsnmp_ds_set_int(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_USERID, uid); } else { usage(argv[0]); } break; #endif case 'v': version(); case 'V': netsnmp_ds_set_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_VERBOSE, 1); break; #if defined(USING_AGENTX_SUBAGENT_MODULE)|| defined(USING_AGENTX_MASTER_MODULE) case 'x': if (optarg != NULL) { netsnmp_ds_set_string(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_X_SOCKET, optarg); } else { usage(argv[0]); } netsnmp_ds_set_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_AGENTX_MASTER, 1); break; #endif case 'X': #if defined(USING_AGENTX_SUBAGENT_MODULE) agent_mode = SUB_AGENT; #else fprintf(stderr, "%s: Illegal argument -X:" "AgentX support not compiled in.\n", argv[0]); usage(argv[0]); exit(1); #endif break; case 'Y': netsnmp_config_remember(optarg); break; default: usage(argv[0]); break; } } if (do_help) { netsnmp_ds_set_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_NO_ROOT_ACCESS, 1); init_agent(app_name); /* register our .conf handlers */ init_mib_modules(); init_snmp(app_name); fprintf(stderr, "Configuration directives understood:\n"); read_config_print_usage(" "); exit(0); } if (optind < argc) { #ifndef NETSNMP_NO_LISTEN_SUPPORT /* * There are optional transport addresses on the command line. */ DEBUGMSGTL(("snmpd/main", "optind %d, argc %d\n", optind, argc)); for (i = optind; i < argc; i++) { char *c, *astring; if ((c = netsnmp_ds_get_string(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_PORTS))) { astring = (char*)malloc(strlen(c) + 2 + strlen(argv[i])); if (astring == NULL) { fprintf(stderr, "malloc failure processing argv[%d]\n", i); exit(1); } sprintf(astring, "%s,%s", c, argv[i]); netsnmp_ds_set_string(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_PORTS, astring); SNMP_FREE(astring); } else { netsnmp_ds_set_string(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_PORTS, argv[i]); } } DEBUGMSGTL(("snmpd/main", "port spec: %s\n", netsnmp_ds_get_string(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_PORTS))); #else /* NETSNMP_NO_LISTEN_SUPPORT */ fprintf(stderr, "You specified ports to open; this agent was built to only send notifications\n"); exit(1); #endif /* NETSNMP_NO_LISTEN_SUPPORT */ } #ifdef NETSNMP_LOGFILE #ifndef NETSNMP_FEATURE_REMOVE_LOGGING_FILE if (0 == log_set) snmp_enable_filelog(NETSNMP_LOGFILE, netsnmp_ds_get_boolean(NETSNMP_DS_LIBRARY_ID, NETSNMP_DS_LIB_APPEND_LOGFILES)); #endif /* NETSNMP_FEATURE_REMOVE_LOGGING_FILE */ #endif #ifdef USING_UTIL_FUNCS_RESTART_MODULE { /* * Initialize a argv set to the current for restarting the agent. */ char *cptr, **argvptr; argvrestartp = (char **)malloc((argc + 2) * sizeof(char *)); argvptr = argvrestartp; for (i = 0, ret = 1; i < argc; i++) { ret += strlen(argv[i]) + 1; } argvrestart = (char *) malloc(ret); argvrestartname = (char *) malloc(strlen(argv[0]) + 1); if (!argvrestartp || !argvrestart || !argvrestartname) { fprintf(stderr, "malloc failure processing argvrestart\n"); exit(1); } strcpy(argvrestartname, argv[0]); for (cptr = argvrestart, i = 0; i < argc; i++) { strcpy(cptr, argv[i]); *(argvptr++) = cptr; cptr += strlen(argv[i]) + 1; } } #endif /* USING_UTIL_FUNCS_RESTART_MODULE */ if (agent_mode == -1) { if (strstr(argv[0], "agentxd") != NULL) { netsnmp_ds_set_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_ROLE, SUB_AGENT); } else { netsnmp_ds_set_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_ROLE, MASTER_AGENT); } } else { netsnmp_ds_set_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_ROLE, agent_mode); } SOCK_STARTUP; if (init_agent(app_name) != 0) { snmp_log(LOG_ERR, "Agent initialization failed\n"); exit(1); } init_mib_modules(); /* * start library */ init_snmp(app_name); if ((ret = init_master_agent()) != 0) { /* * Some error opening one of the specified agent transports. */ snmp_log(LOG_ERR, "Server Exiting with code 1\n"); exit(1); } /* * Initialize the world. Detach from the shell. Create initial user. */ if(!dont_fork) { int quit = ! netsnmp_ds_get_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_QUIT_IMMEDIATELY); ret = netsnmp_daemonize(quit, #ifndef NETSNMP_FEATURE_REMOVE_LOGGING_STDIO snmp_stderrlog_status() #else /* NETSNMP_FEATURE_REMOVE_LOGGING_STDIO */ 0 #endif /* NETSNMP_FEATURE_REMOVE_LOGGING_STDIO */ ); /* * xxx-rks: do we care if fork fails? I think we should... */ if(ret != 0) { snmp_log(LOG_ERR, "Server Exiting with code 1\n"); exit(1); } } #if HAVE_GETPID if (pid_file != NULL) { /* * unlink the pid_file, if it exists, prior to open. Without * doing this the open will fail if the user specified pid_file * already exists. */ unlink(pid_file); fd = open(pid_file, O_CREAT | O_EXCL | O_WRONLY, 0600); if (fd == -1) { snmp_log_perror(pid_file); if (!netsnmp_ds_get_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_NO_ROOT_ACCESS)) { exit(1); } } else { if ((PID = fdopen(fd, "w")) == NULL) { snmp_log_perror(pid_file); exit(1); } else { fprintf(PID, "%d\n", (int) getpid()); fclose(PID); } #ifndef _MSC_VER /* The sequence open()/fdopen()/fclose()/close() makes MSVC crash, hence skip the close() call when using the MSVC runtime. */ close(fd); #endif } } #endif #if defined(HAVE_UNISTD_H) && (defined(HAVE_CHOWN) || defined(HAVE_SETGID) || defined(HAVE_SETUID)) { const char *persistent_dir; int uid, gid; persistent_dir = get_persistent_directory(); mkdirhier( persistent_dir, NETSNMP_AGENT_DIRECTORY_MODE, 0 ); uid = netsnmp_ds_get_int(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_USERID); gid = netsnmp_ds_get_int(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_GROUPID); #ifdef HAVE_CHOWN if ( uid != 0 || gid != 0 ) chown( persistent_dir, uid, gid ); #endif #ifdef HAVE_SETGID if ((gid = netsnmp_ds_get_int(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_GROUPID)) > 0) { DEBUGMSGTL(("snmpd/main", "Changing gid to %d.\n", gid)); if (setgid(gid) == -1 #ifdef HAVE_SETGROUPS || setgroups(1, (gid_t *)&gid) == -1 #endif ) { snmp_log_perror("setgid failed"); if (!netsnmp_ds_get_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_NO_ROOT_ACCESS)) { exit(1); } } } #endif #ifdef HAVE_SETUID if ((uid = netsnmp_ds_get_int(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_USERID)) > 0) { #if HAVE_GETPWNAM && HAVE_PWD_H && HAVE_INITGROUPS struct passwd *info; /* * Set supplementary groups before changing UID * (which probably involves giving up privileges) */ info = getpwuid(uid); if (info) { DEBUGMSGTL(("snmpd/main", "Supplementary groups for %s.\n", info->pw_name)); if (initgroups(info->pw_name, (gid != 0 ? (gid_t)gid : info->pw_gid)) == -1) { snmp_log_perror("initgroups failed"); if (!netsnmp_ds_get_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_NO_ROOT_ACCESS)) { exit(1); } } } endpwent(); #endif DEBUGMSGTL(("snmpd/main", "Changing uid to %d.\n", uid)); if (setuid(uid) == -1) { snmp_log_perror("setuid failed"); if (!netsnmp_ds_get_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_NO_ROOT_ACCESS)) { exit(1); } } } #endif } #endif /* * Store persistent data immediately in case we crash later. */ snmp_store(app_name); #ifdef SIGHUP DEBUGMSGTL(("signal", "registering SIGHUP signal handler\n")); signal(SIGHUP, SnmpdReconfig); #endif /* * Send coldstart trap if possible. */ send_easy_trap(0, 0); /* * We're up, log our version number. */ snmp_log(LOG_INFO, "NET-SNMP version %s\n", netsnmp_get_version()); #ifdef WIN32SERVICE agent_status = AGENT_RUNNING; #endif netsnmp_addrcache_initialise(); /* * Let systemd know we're up. */ #ifndef NETSNMP_NO_SYSTEMD netsnmp_sd_notify(1, "READY=1\n"); if (prepared_sockets) /* * Clear the environment variable, we already processed all the sockets * by now. */ netsnmp_sd_listen_fds(1); #endif /* * Forever monitor the dest_port for incoming PDUs. */ DEBUGMSGTL(("snmpd/main", "We're up. Starting to process data.\n")); if (!netsnmp_ds_get_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_QUIT_IMMEDIATELY)) receive(); DEBUGMSGTL(("snmpd/main", "sending shutdown trap\n")); SnmpTrapNodeDown(); DEBUGMSGTL(("snmpd/main", "Bye...\n")); snmp_shutdown(app_name); shutdown_master_agent(); shutdown_agent(); if (!netsnmp_ds_get_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_LEAVE_PIDFILE) && (pid_file != NULL)) { unlink(pid_file); } #ifdef WIN32SERVICE agent_status = AGENT_STOPPED; #endif #ifdef USING_UTIL_FUNCS_RESTART_MODULE SNMP_FREE(argvrestartname); SNMP_FREE(argvrestart); SNMP_FREE(argvrestartp); #endif /* USING_UTIL_FUNCS_RESTART_MODULE */ SOCK_CLEANUP; return 0; } /* End main() -- snmpd */
/* extract regular file */ int tar_extract_regfile(TAR *t, char *realname) { mode_t mode; size_t size; uid_t uid; gid_t gid; int fdout; int i, k; char buf[T_BLOCKSIZE]; char *filename; #ifdef DEBUG printf("==> tar_extract_regfile(t=0x%lx, realname=\"%s\")\n", t, realname); #endif if (!TH_ISREG(t)) { errno = EINVAL; return -1; } filename = (realname ? realname : th_get_pathname(t)); mode = th_get_mode(t); size = th_get_size(t); uid = th_get_uid(t); gid = th_get_gid(t); if (mkdirhier(dirname(filename)) == -1) return -1; #ifdef DEBUG printf(" ==> extracting: %s (mode %04o, uid %d, gid %d, %d bytes)\n", filename, mode, uid, gid, size); #endif fdout = open(filename, O_WRONLY | O_CREAT | O_TRUNC #ifdef O_BINARY | O_BINARY #endif , 0666); if (fdout == -1) { #ifdef DEBUG perror("open()"); #endif return -1; } #if 0 /* change the owner. (will only work if run as root) */ if (fchown(fdout, uid, gid) == -1 && errno != EPERM) { #ifdef DEBUG perror("fchown()"); #endif return -1; } /* make sure the mode isn't inheritted from a file we're overwriting */ if (fchmod(fdout, mode & 07777) == -1) { #ifdef DEBUG perror("fchmod()"); #endif return -1; } #endif /* extract the file */ for (i = size; i > 0; i -= T_BLOCKSIZE) { k = tar_block_read(t, buf); if (k != T_BLOCKSIZE) { if (k != -1) errno = EINVAL; return -1; } /* write block to output file */ if (write(fdout, buf, ((i > T_BLOCKSIZE) ? T_BLOCKSIZE : i)) == -1) return -1; } /* close output file */ if (close(fdout) == -1) return -1; #ifdef DEBUG printf("### done extracting %s\n", filename); #endif return 0; }
/* * Open the status file. If scantime is not -1, the file is opened * for updating, otherwise, it is opened read-only. If the status file * couldn't be opened, NULL is returned and errmsg is set to the error * message. */ struct status * status_open(struct coll *coll, time_t scantime, char **errmsg) { struct status *st; struct stream *file; struct fattr *fa; char *destpath, *path; int error, rv; path = coll_statuspath(coll); file = stream_open_file(path, O_RDONLY); if (file == NULL) { if (errno != ENOENT) { xasprintf(errmsg, "Could not open \"%s\": %s\n", path, strerror(errno)); free(path); return (NULL); } st = status_fromnull(path); } else { st = status_fromrd(path, file); if (st == NULL) { xasprintf(errmsg, "Error in \"%s\": Bad header line", path); free(path); return (NULL); } } if (scantime != -1) { /* Open for writing too. */ xasprintf(&destpath, "%s/%s/%s/", coll->co_base, coll->co_colldir, coll->co_name); st->tempfile = tempname(destpath); if (mkdirhier(destpath, coll->co_umask) != 0) { xasprintf(errmsg, "Cannot create directories leading " "to \"%s\": %s", destpath, strerror(errno)); free(destpath); status_free(st); return (NULL); } free(destpath); st->wr = stream_open_file(st->tempfile, O_CREAT | O_TRUNC | O_WRONLY, 0644); if (st->wr == NULL) { xasprintf(errmsg, "Cannot create \"%s\": %s", st->tempfile, strerror(errno)); status_free(st); return (NULL); } fa = fattr_new(FT_FILE, -1); fattr_mergedefault(fa); fattr_umask(fa, coll->co_umask); rv = fattr_install(fa, st->tempfile, NULL); fattr_free(fa); if (rv == -1) { xasprintf(errmsg, "Cannot set attributes for \"%s\": %s", st->tempfile, strerror(errno)); status_free(st); return (NULL); } if (scantime != st->scantime) st->dirty = 1; error = proto_printf(st->wr, "F %d %t\n", STATUS_VERSION, scantime); if (error) { st->error = STATUS_ERR_WRITE; st->suberror = errno; *errmsg = status_errmsg(st); status_free(st); return (NULL); } } return (st); }
void real_init_master(void) { netsnmp_session sess, *session; char *agentx_sockets; char *cp1, *cp2; #ifdef SNMP_TRANSPORT_UNIX_DOMAIN int agentx_dir_perm; int agentx_sock_perm; int agentx_sock_user; int agentx_sock_group; #endif if (netsnmp_ds_get_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_ROLE) != MASTER_AGENT) return; if (netsnmp_ds_get_string(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_X_SOCKET)) { agentx_sockets = strdup(netsnmp_ds_get_string(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_X_SOCKET)); #ifdef AGENTX_DOM_SOCK_ONLY if (agentx_sockets[0] != '/') { /* unix:/path */ if (agentx_sockets[5] != '/') { snmp_log(LOG_ERR, "Error: %s transport is not supported, disabling agentx/master.\n", agentx_sockets); SNMP_FREE(agentx_sockets); return; } } #endif } else { agentx_sockets = strdup(AGENTX_SOCKET); } DEBUGMSGTL(("agentx/master", "initializing...\n")); snmp_sess_init(&sess); sess.version = AGENTX_VERSION_1; sess.flags |= SNMP_FLAGS_STREAM_SOCKET; sess.timeout = netsnmp_ds_get_int(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_AGENTX_TIMEOUT); sess.retries = netsnmp_ds_get_int(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_AGENTX_RETRIES); cp1 = agentx_sockets; while (1) { /* * If the AgentX socket string contains multiple descriptors, * then pick this apart and handle them one by one. * */ cp2 = strchr(cp1, ','); if (cp2 != NULL) { *cp2 = '\0'; } sess.peername = cp1; if (cp2 != NULL) { cp1 = cp2+1; } if (sess.peername[0] == '/') { #ifdef SNMP_TRANSPORT_UNIX_DOMAIN /* * If this is a Unix pathname, * try and create the directory first. */ agentx_dir_perm = netsnmp_ds_get_int(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_X_DIR_PERM); if (agentx_dir_perm == 0) agentx_dir_perm = AGENT_DIRECTORY_MODE; if (mkdirhier(sess.peername, (mode_t)agentx_dir_perm, 1)) { snmp_log(LOG_ERR, "Failed to create the directory for the agentX socket: %s\n", sess.peername); } #else netsnmp_sess_log_error(LOG_WARNING, "unix domain support not available\n", &sess); #endif } /* * Otherwise, let 'snmp_open' interpret the string. */ sess.local_port = AGENTX_PORT; /* Indicate server & set default port */ sess.remote_port = 0; sess.callback = handle_master_agentx_packet; session = snmp_open_ex(&sess, NULL, agentx_parse, NULL, NULL, agentx_realloc_build, agentx_check_packet); if (session == NULL && sess.s_errno == EADDRINUSE) { /* * Could be a left-over socket (now deleted) * Try again */ session = snmp_open_ex(&sess, NULL, agentx_parse, NULL, NULL, agentx_realloc_build, agentx_check_packet); } if (session == NULL) { /* * diagnose snmp_open errors with the input netsnmp_session pointer */ if (!netsnmp_ds_get_boolean(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_NO_ROOT_ACCESS)) { snmp_sess_perror ("Error: Couldn't open a master agentx socket to listen on", &sess); exit(1); } else { netsnmp_sess_log_error(LOG_WARNING, "Warning: Couldn't open a agentx master socket to listen on", &sess); } } #ifdef SNMP_TRANSPORT_UNIX_DOMAIN /* * Apply any settings to the ownership/permissions of the AgentX socket */ agentx_sock_perm = netsnmp_ds_get_int(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_X_SOCK_PERM); agentx_sock_user = netsnmp_ds_get_int(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_X_SOCK_USER); agentx_sock_group = netsnmp_ds_get_int(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_X_SOCK_GROUP); if (agentx_sock_perm != 0) chmod(sess.peername, agentx_sock_perm); if (agentx_sock_user || agentx_sock_group) { /* * If either of user or group haven't been set, * then leave them unchanged. */ if (agentx_sock_user == 0 ) agentx_sock_user = -1; if (agentx_sock_group == 0 ) agentx_sock_group = -1; chown(sess.peername, agentx_sock_user, agentx_sock_group); } #endif /* * If we've processed the last (or only) socket, then we're done. */ if (!cp2) break; } SNMP_FREE(agentx_sockets); DEBUGMSGTL(("agentx/master", "initializing... DONE\n")); }