void connect_grabbanners(ip_report_t *r) { union { void *ptr; connection_status_t *c; } c_u; uint64_t state_key=0; uint8_t *c_ptr=NULL; output_data_t *e_out=NULL; char pchars[256]; size_t p_off=0, j=0; state_key=get_connectionkey(r); if (rbfind(state_tbl, state_key, &c_u.ptr) > 0) { memset(pchars, 0, sizeof(pchars)); for (j=0, p_off=0, c_ptr=c_u.c->recv_buf; j < c_u.c->recv_len; j++, c_ptr++) { if (isgraph(*c_ptr) || *c_ptr == ' ') { pchars[p_off++]=(char )*c_ptr; } if (p_off > (sizeof(pchars) -2)) break; } if (p_off > 0) { e_out=(output_data_t *)xmalloc(sizeof(output_data_t)); e_out->type=OD_TYPE_BANNER; e_out->t_u.banner=xstrdup(pchars); fifo_push(r->od_q, (void *)e_out); } } return; }
/* * Get a password entry by uid and allocate space for it. */ struct passwd * sudo_getpwuid(uid_t uid) { struct cache_item key, *item; struct rbnode *node; debug_decl(sudo_getpwuid, SUDO_DEBUG_NSS) key.k.uid = uid; if ((node = rbfind(pwcache_byuid, &key)) != NULL) { item = (struct cache_item *) node->data; goto done; } /* * Cache passwd db entry if it exists or a negative response if not. */ #ifdef HAVE_SETAUTHDB aix_setauthdb(IDtouser(uid)); #endif item = sudo_make_pwitem(uid, NULL); if (item == NULL) { item = ecalloc(1, sizeof(*item)); item->refcnt = 1; item->k.uid = uid; /* item->d.pw = NULL; */ } if (rbinsert(pwcache_byuid, item) != NULL) fatalx(_("unable to cache uid %u, already exists"), (unsigned int) uid); #ifdef HAVE_SETAUTHDB aix_restoreauthdb(); #endif done: item->refcnt++; debug_return_ptr(item->d.pw); }
/* * Get a group entry by name and allocate space for it. */ struct group * sudo_getgrnam(const char *name) { struct cache_item key, *item; struct rbnode *node; size_t len; key.k.name = (char *) name; if ((node = rbfind(grcache_byname, &key)) != NULL) { item = (struct cache_item *) node->data; goto done; } /* * Cache group db entry if it exists or a negative response if not. */ if ((key.d.gr = getgrnam(name)) != NULL) { item = make_gritem(key.d.gr, name); if (rbinsert(grcache_byname, item) != NULL) errorx(1, "unable to cache group %s, already exists", name); } else { len = strlen(name) + 1; item = emalloc(sizeof(*item) + len); item->refcnt = 1; item->k.name = (char *) item + sizeof(*item); memcpy(item->k.name, name, len); item->d.gr = NULL; if (rbinsert(grcache_byname, item) != NULL) errorx(1, "unable to cache group %s, already exists", name); } done: item->refcnt++; return item->d.gr; }
/* * Search the tree for an alias with the specified name and type. * Returns a pointer to the alias structure or NULL if not found. * Caller is responsible for calling alias_put() on the returned * alias to mark it as unused. */ struct alias * alias_get(char *name, int type) { struct alias key; struct rbnode *node; struct alias *a = NULL; debug_decl(alias_get, SUDOERS_DEBUG_ALIAS) key.name = name; key.type = type; if ((node = rbfind(aliases, &key)) != NULL) { /* * Check whether this alias is already in use. * If so, we've detected a loop. If not, set the flag, * which the caller should clear with a call to alias_put(). */ a = node->data; if (a->used) { errno = ELOOP; debug_return_ptr(NULL); } a->used = true; } else { errno = ENOENT; } debug_return_ptr(a); }
/* ============ Cmd_AddCommand ============ */ void EXPORT Cmd_AddCommand (const char *cmd_name, xcommand_t function) { void **data; cmd_function_t *cmd; if (!cmd_name) Com_Error (ERR_FATAL, "Cmd_AddCommand: NULL command name"); // fail if the command is a variable name if (Cvar_VariableString(cmd_name)[0]) { Com_Printf ("Cmd_AddCommand: %s already defined as a var\n", LOG_GENERAL, cmd_name); return; } // fail if the command already exists if (rbfind (cmd_name, cmdtree)) { //r1: delete command and replace. unclean ref shutdown for example //will leave dangling pointers. //Com_Printf ("Cmd_AddCommand: %s already defined\n", LOG_GENERAL, cmd_name); //return; Cmd_RemoveCommand (cmd_name); } cmd = Z_TagMalloc (sizeof(cmd_function_t), TAGMALLOC_CMD); cmd->name = cmd_name; cmd->function = function; cmd->next = cmd_functions; cmd_functions = cmd; data = rbsearch (cmd->name, cmdtree); *data = cmd; }
static void RB_Purge (const struct rbtree *r) { RBLIST *rblist; const void *val; void *data; void *ptr; if ((rblist=rbopenlist(rb)) != NULL) { while((val=rbreadlist(rblist)) != NULL) { data = rbfind (val, rb); ptr = *(void **)data; rbdelete (val, rb); if (ptr) Z_Free (ptr); } } rbcloselist(rblist); rbdestroy (rb); FS_InitCache(); }
/* * Get a group entry by gid and allocate space for it. */ struct group * sudo_getgrgid(gid_t gid) { struct cache_item key, *item; struct rbnode *node; key.k.gid = gid; if ((node = rbfind(grcache_bygid, &key)) != NULL) { item = (struct cache_item *) node->data; goto done; } /* * Cache group db entry if it exists or a negative response if not. */ if ((key.d.gr = getgrgid(gid)) != NULL) { item = make_gritem(key.d.gr, NULL); if (rbinsert(grcache_bygid, item) != NULL) errorx(1, "unable to cache gid %u (%s), already exists", (unsigned int) gid, key.d.gr->gr_name); } else { item = emalloc(sizeof(*item)); item->refcnt = 1; item->k.gid = gid; item->d.gr = NULL; if (rbinsert(grcache_bygid, item) != NULL) errorx(1, "unable to cache gid %u, already exists", (unsigned int) gid); } done: item->refcnt++; return item->d.gr; }
/** * Find the mt-daapd index that corresponds with a particular * itunes song id * * @param itunes_index index from the iTunes xml file * @returns the mt-daapd index */ int scan_xml_get_index(int itunes_index, int *mtd_index) { SCAN_XML_RB rb; SCAN_XML_RB *prb; rb.itunes_index = itunes_index; prb = (SCAN_XML_RB*) rbfind((void*)&rb,scan_xml_db); if(prb) { *mtd_index = prb->mtd_index; DPRINTF(E_SPAM,L_SCAN,"Matching %d to %d\n",itunes_index,*mtd_index); return TRUE; } return FALSE; }
lv_t *c_hash_fetch(lv_t *hash, lv_t *key) { hash_node_t node_key; hash_node_t *result; assert(hash && hash->type == l_hash); assert(key && (key->type == l_str || key->type == l_sym)); node_key.key = s_hash_item(key); result = (hash_node_t *)rbfind(&node_key, L_HASH(hash)); if(!result) return NULL; return result->value; }
/* * Find the named alias, remove it from the tree and return it. */ struct alias * alias_remove(char *name, int type) { struct rbnode *node; struct alias key; debug_decl(alias_remove, SUDOERS_DEBUG_ALIAS) key.name = name; key.type = type; if ((node = rbfind(aliases, &key)) == NULL) { errno = ENOENT; return NULL; } debug_return_ptr(rbdelete(aliases, node)); }
/* ============ FS_ExistsInGameDir See if a file exists in the mod directory/paks (ignores baseq2) ============ */ qboolean FS_ExistsInGameDir (char *filename) { size_t len; char *gamedir; char lowered[MAX_QPATH]; searchpath_t *search; pack_t *pak; Q_strncpy (lowered, filename, sizeof(lowered)-1); fast_strlwr (lowered); gamedir = FS_Gamedir(); len = strlen(gamedir); for (search = fs_searchpaths ; search ; search = search->next) { // is the element a pak file? if (search->pack) { packfile_t *entry; //r1: optimized btree search pak = search->pack; if (strncmp (pak->filename, gamedir, len)) continue; entry = rbfind (lowered, pak->rb); if (entry) return true; } else { char netpath[MAX_OSPATH]; if (strncmp (search->filename, gamedir, len)) continue; Com_sprintf (netpath, sizeof(netpath), "%s/%s",search->filename, filename); if (Sys_FileLength (netpath) != -1) return true; } } return false; }
/* * Get a password entry by name and allocate space for it. */ struct passwd * sudo_getpwnam(const char *name) { struct cache_item key, *item; struct rbnode *node; size_t len; debug_decl(sudo_getpwnam, SUDO_DEBUG_NSS) key.k.name = (char *) name; if ((node = rbfind(pwcache_byname, &key)) != NULL) { item = (struct cache_item *) node->data; goto done; } /* * Cache passwd db entry if it exists or a negative response if not. */ #ifdef HAVE_SETAUTHDB aix_setauthdb((char *) name); #endif if ((key.d.pw = getpwnam(name)) != NULL) { item = make_pwitem(key.d.pw, name); if (rbinsert(pwcache_byname, item) != NULL) errorx(1, _("unable to cache user %s, already exists"), name); } else { len = strlen(name) + 1; item = ecalloc(1, sizeof(*item) + len); item->refcnt = 1; item->k.name = (char *) item + sizeof(*item); memcpy(item->k.name, name, len); /* item->d.pw = NULL; */ if (rbinsert(pwcache_byname, item) != NULL) errorx(1, _("unable to cache user %s, already exists"), name); } #ifdef HAVE_SETAUTHDB aix_restoreauthdb(); #endif done: item->refcnt++; debug_return_ptr(item->d.pw); }
/* ============ Cvar_FindVar ============ */ cvar_t *Cvar_FindVar (const char *var_name) { cvar_t *var; const void **data; //not inited yet if (!cvartree) return NULL; data = (const void **) rbfind (var_name, cvartree); if (data) { var = *(cvar_t **)data; return var; } /*for (var=cvar_vars ; var ; var=var->next) if (!strcmp (var_name, var->name)) return var;*/ return NULL; }
/* * Get a password entry by uid and allocate space for it. * Fills in pw_passwd from shadow file if necessary. */ struct passwd * sudo_getpwuid(uid_t uid) { struct cache_item key, *item; struct rbnode *node; key.k.uid = uid; if ((node = rbfind(pwcache_byuid, &key)) != NULL) { item = (struct cache_item *) node->data; goto done; } /* * Cache passwd db entry if it exists or a negative response if not. */ #ifdef HAVE_SETAUTHDB aix_setauthdb(IDtouser(uid)); #endif if ((key.d.pw = getpwuid(uid)) != NULL) { item = make_pwitem(key.d.pw, NULL); if (rbinsert(pwcache_byuid, item) != NULL) errorx(1, "unable to cache uid %u (%s), already exists", (unsigned int) uid, item->d.pw->pw_name); } else { item = emalloc(sizeof(*item)); item->refcnt = 1; item->k.uid = uid; item->d.pw = NULL; if (rbinsert(pwcache_byuid, item) != NULL) errorx(1, "unable to cache uid %u, already exists", (unsigned int) uid); } #ifdef HAVE_SETAUTHDB aix_restoreauthdb(); #endif done: item->refcnt++; return item->d.pw; }
static void FS_AddToCache (char *path, uint32 filelen, uint32 fileseek, char *filename, uint32 hash) { void **newitem; fscache_t *cache; magic_t *magic; cache = Z_TagMalloc (sizeof(fscache_t), TAGMALLOC_FSCACHE); cache->filelen = filelen; cache->fileseek = fileseek; if (path) strncpy (cache->filepath, path, sizeof(cache->filepath)-1); else cache->filepath[0] = 0; strncpy (cache->filename, filename, sizeof(cache->filename)-1); newitem = rbfind ((void *)hash, rb); if (newitem) { magic = *(magic_t **)newitem; while (magic->next) magic = magic->next; magic->next = Z_TagMalloc (sizeof(magic_t), TAGMALLOC_FSCACHE); magic = magic->next; magic->entry = cache; magic->next = NULL; } else { newitem = rbsearch ((void *)hash, rb); magic = Z_TagMalloc (sizeof(magic_t), TAGMALLOC_FSCACHE); magic->entry = cache; magic->next = NULL; *newitem = magic; } }
struct upnp_entry_t * upnp_get_entry (struct ushare_t *ut, int id) { struct upnp_entry_lookup_t *res, entry_lookup; log_verbose ("Looking for entry id %d\n", id); if (id == 0) /* We do not store the root (id 0) as it is not a child */ return ut->root_entry; entry_lookup.id = id; res = (struct upnp_entry_lookup_t *) rbfind ((void *) &entry_lookup, ut->rb); if (res) { log_verbose ("Found at %p\n", ((struct upnp_entry_lookup_t *) res)->entry_ptr); return ((struct upnp_entry_lookup_t *) res)->entry_ptr; } log_verbose ("Not Found\n"); return NULL; }
/* ============ Cmd_ExecuteString A complete command line has been parsed, so try to execute it FIXME: lookupnoadd the token to speed search? ============ */ void Cmd_ExecuteString (char *text) { cmd_function_t *cmd; cmdalias_t *a; void **data; Cmd_TokenizeString (text, true); // execute the command line if (!Cmd_Argc()) { //Com_DPrintf ("Cmd_ExecuteString: no tokens on '%s'\n", text); return; // no tokens } // check functions // FIXME CRASH: NULL in the rb tree! data = rbfind (cmd_argv[0], cmdtree); if (data) { cmd = *(cmd_function_t **)data; if (!cmd->function) { // forward to server command //Cmd_ExecuteString (va("cmd %s", text)); #ifndef DEDICATED_ONLY Cmd_ForwardToServer (); #endif //Com_DPrintf ("Cmd_ExecuteString: no function '%s' for '%s', using 'cmd'\n", cmd->name, text); } else { //Com_DPrintf ("Cmd_ExecuteString: function '%s' called for '%s'\n", cmd->name, text); cmd->function (); } return; } // check alias data = rbfind (cmd_argv[0], aliastree); if (data) { char expanded[MAX_STRING_CHARS]; a = *(cmdalias_t **)data; if (++alias_count == ALIAS_LOOP_COUNT) { Com_Printf ("ALIAS_LOOP_COUNT\n", LOG_GENERAL); return; } Cmd_Expand_Args (a->value, expanded, sizeof(expanded)); Cbuf_InsertText (expanded); return; } // check cvars if (Cvar_Command ()) { //Com_DPrintf ("Cmd_ExecuteString: '%s' : is cvar\n", text); return; } // send it as a server command if we are connected #ifndef DEDICATED_ONLY Cmd_ForwardToServer (); #else Com_Printf ("Unknown command \"%s\"\n", LOG_GENERAL, text); #endif }
void FS_WhereIs_f (void) { char *filename; searchpath_t *search; pack_t *pak; filelink_t *link; char netpath[MAX_OSPATH]; char lowered[MAX_QPATH]; if (Cmd_Argc() != 2) { Com_Printf ("Purpose: Find where a file is being loaded from on the filesystem.\n" "Syntax : whereis <path>\n" "Example: whereis maps/q2dm1.bsp\n", LOG_GENERAL); return; } filename = Cmd_Argv(1); // check for links firstal if (!fs_noextern->intvalue) { for (link = fs_links ; link ; link=link->next) { if (!strncmp (filename, link->from, link->fromlength)) { int len; Com_sprintf (netpath, sizeof(netpath), "%s%s",link->to, filename+link->fromlength); len = Sys_FileLength (netpath); if (len != -1) { Com_Printf ("%s is found on disk as %s (using linkpath), %d bytes.\n", LOG_GENERAL, Cmd_Argv(1), netpath, len); } else { Com_Printf ("%s is not found.\n", LOG_GENERAL, Cmd_Argv(1)); } return; } } } Q_strncpy (lowered, filename, sizeof(lowered)-1); fast_strlwr (lowered); for (search = fs_searchpaths ; search ; search = search->next) { // is the element a pak file? if (search->pack) { packfile_t *entry; //r1: optimized btree search pak = search->pack; entry = rbfind (lowered, pak->rb); if (entry) { entry = *(packfile_t **)entry; Com_Printf ("%s is found in pakfile %s as %s, %d bytes.\n", LOG_GENERAL, Cmd_Argv(1), pak->filename, entry->name, entry->filelen); return; } } else if (!fs_noextern->intvalue) { int filelen; // check a file in the directory tree Com_sprintf (netpath, sizeof(netpath), "%s/%s",search->filename, filename); filelen = Sys_FileLength (netpath); if (filelen == -1) continue; Com_Printf ("%s is found on disk as %s, %d bytes.\n", LOG_GENERAL, Cmd_Argv(1), netpath, filelen); return; } } Com_Printf ("%s is not found.\n", LOG_GENERAL, Cmd_Argv(1)); }
/* =============== Cmd_Alias_f Creates a new command that executes a command string (possibly ; seperated) =============== */ void Cmd_Alias_f (void) { cmdalias_t *a; char cmd[1024]; char *s; void **data; if (Cmd_Argc() == 1) { Com_Printf ("Current alias commands:\n", LOG_GENERAL); Cmd_Aliaslist_f (); return; } s = Cmd_Argv(1); if (strlen(s) >= MAX_ALIAS_NAME) { Com_Printf ("Alias name is too long\n", LOG_GENERAL); return; } // if the alias already exists, reuse it /*for (a = cmd_alias ; a ; a=a->next) { if (!strcmp(s, a->name)) { Z_Free (a->value); break; } }*/ data = rbfind (s, aliastree); if (data) a = *(cmdalias_t **)data; else a = NULL; if (!a) { a = Z_TagMalloc (sizeof(cmdalias_t), TAGMALLOC_ALIAS); a->next = cmd_alias; cmd_alias = a; strcpy (a->name, s); data = rbsearch (a->name, aliastree); *data = a; } else { //strcpy (a->name, s); //memleak fix, thanks Maniac- Z_Free (a->value); } // copy the rest of the command line /*cmd[0] = 0; // start out with a null string c = Cmd_Argc(); for (i=2 ; i< c ; i++) { strcat (cmd, Cmd_Argv(i)); if (i != (c - 1)) strcat (cmd, " "); }*/ Q_strncpy (cmd, Cmd_Args2(2), sizeof(cmd)-2); /*s = strchr (Cmd_Args(), ' '); if (s) s++; else s = Cmd_Args (); Q_strncpy (cmd, s, sizeof(cmd)-2);*/ strcat (cmd, "\n"); a->value = CopyString (cmd, TAGMALLOC_ALIAS); }
int EXPORT FS_FOpenFile (const char *filename, FILE **file, handlestyle_t openHandle, qboolean *closeHandle) { fscache_t *cache; searchpath_t *search; pack_t *pak; filelink_t *link; char netpath[MAX_OSPATH]; char lowered[MAX_QPATH]; // check for links firstal if (!fs_noextern->intvalue) { for (link = fs_links ; link ; link=link->next) { if (!strncmp (filename, link->from, link->fromlength)) { Com_sprintf (netpath, sizeof(netpath), "%s%s",link->to, filename+link->fromlength); if (openHandle != HANDLE_NONE) { *file = fopen (netpath, "rb"); if (*file) { Com_DPrintf ("link file: %s\n",netpath); *closeHandle = true; return FS_filelength (*file); } return -1; } else { return Sys_FileLength (netpath); } } } } #ifdef BTREE_SEARCH cache = rbfind (filename, rb); if (cache) { cache = *(fscache_t **)cache; if (cache->filepath[0] == 0) { *file = NULL; return -1; } #ifdef _DEBUG Com_DPrintf ("File '%s' found in cache: %s\n", filename, cache->filepath); #endif if (openHandle != HANDLE_NONE) { if (cache->pak) { if (openHandle == HANDLE_DUPE) { *file = fopen (cache->pak->filename, "rb"); if (!*file) { Com_Printf ("WARNING: Cached pak '%s' failed to open! Did you delete it?\n", LOG_WARNING|LOG_GENERAL, cache->pak->filename); rbdelete (filename, rb); return -1; } *closeHandle = true; } else { *file = cache->pak->h.handle; *closeHandle = false; } } else { *file = fopen (cache->filepath, "rb"); if (!*file) { Com_Printf ("WARNING: Cached file '%s' failed to open! Did you delete it?\n", LOG_WARNING|LOG_GENERAL, cache->filepath); rbdelete (filename, rb); return -1; } //Com_Error (ERR_FATAL, "Couldn't open %s (cached)", cache->filepath); *closeHandle = true; } if (cache->fileseek && fseek (*file, cache->fileseek, SEEK_SET)) Com_Error (ERR_FATAL, "Couldn't seek to offset %u in %s (cached)", cache->fileseek, cache->filepath); } return cache->filelen; } #elif HASH_CACHE hash = hashify (filename); cache = &fscache; while (cache->next) { cache = cache->next; if (cache->hash == hash && !Q_stricmp (cache->filename, filename)) { Com_Printf (" (cached) ", LOG_GENERAL); if (cache->filepath[0] == 0) { *file = NULL; return -1; } *file = fopen (cache->filepath, "rb"); if (!*file) Com_Error (ERR_FATAL, "Couldn't open %s", cache->filepath); fseek (*file, cache->fileseek, SEEK_SET); return cache->filelen; } } #elif MAGIC_BTREE { magic_t *magic; hash = hashify (filename); magic = rbfind ((void *)hash, rb); if (magic) { magic = *(magic_t **)magic; do { cache = magic->entry; if (!Q_stricmp (cache->filename, filename)) { if (cache->filepath[0] == 0) { *file = NULL; return -1; } *file = fopen (cache->filepath, "rb"); if (!*file) Com_Error (ERR_FATAL, "Couldn't open %s", cache->filepath); fseek (*file, cache->fileseek, SEEK_SET); return cache->filelen; } magic = magic->next; } while (magic); } } #endif #ifdef _DEBUG Com_DPrintf ("File '%s' not found in cache, searching fs_searchpaths\n", filename); #endif Q_strncpy (lowered, filename, sizeof(lowered)-1); fast_strlwr (lowered); for (search = fs_searchpaths ; search ; search = search->next) { // is the element a pak file? if (search->pack) { // char *lower; packfile_t *entry; //r1: optimized btree search pak = search->pack; if (pak->type == PAK_QUAKE) { entry = rbfind (lowered, pak->rb); if (entry) { entry = *(packfile_t **)entry; #ifdef _DEBUG Com_DPrintf ("File '%s' found in %s, (%s)\n", filename, pak->filename, entry->name); #endif if (openHandle != HANDLE_NONE) { //*file = fopen (pak->filename, "rb"); if (openHandle == HANDLE_DUPE) { *file = fopen (pak->filename, "rb"); *closeHandle = true; } else { *file = pak->h.handle; *closeHandle = false; } //if (!*file) // Com_Error (ERR_FATAL, "Couldn't reopen pak file %s", pak->filename); if (fseek (*file, entry->filepos, SEEK_SET)) Com_Error (ERR_FATAL, "Couldn't seek to offset %u for %s in %s", entry->filepos, entry->name, pak->filename); } if (fs_cache->intvalue & 1) { #if BTREE_SEARCH FS_AddToCache (pak->filename, entry->filelen, entry->filepos, filename, pak); #elif HASH_CACHE FS_AddToCache (hash, pak->filename, entry->filelen, entry->filepos, cache, filename); #elif MAGIC_BTREE FS_AddToCache (pak->filename, entry->filelen, entry->filepos, filename, hash); #endif } return entry->filelen; } } } else if (!fs_noextern->intvalue) { struct stat statInfo; int filelen; // check a file in the directory tree Com_sprintf (netpath, sizeof(netpath), "%s/%s",search->filename, filename); if (openHandle == HANDLE_NONE) { filelen = Sys_FileLength (netpath); if (filelen == -1) continue; if (fs_cache->intvalue & 4) FS_AddToCache (netpath, filelen, 0, filename, NULL); return filelen; } //fix for moronic implementations that allow fopen (FILE OPEN) to open a directory //(this means you linux and krew) if (stat (netpath, &statInfo)) continue; if (statInfo.st_mode & S_IFDIR) { Com_Printf ("WARNING: Tried to open a directory as a file: %s\n", LOG_WARNING, netpath); continue; } *file = fopen (netpath, "rb"); if (!*file) continue; *closeHandle = true; Com_DPrintf ("FindFile: %s\n",netpath); filelen = FS_filelength (*file); if (fs_cache->intvalue & 4) { #if BTREE_SEARCH FS_AddToCache (netpath, filelen, 0, filename, NULL); #elif HASH_CACHE FS_AddToCache (hash, netpath, filelen, 0, cache, filename); #elif MAGIC_BTREE FS_AddToCache (netpath, filelen, 0, filename, hash); #endif } return filelen; } } Com_DPrintf ("FindFile: can't find %s\n", filename); if (fs_cache->intvalue & 2) { #if BTREE_SEARCH FS_AddToCache (NULL, 0, 0, filename, NULL); #elif HASH_CACHE FS_AddToCache (hash, NULL, 0, 0, cache, filename); #elif MAGIC_BTREE FS_AddToCache (NULL, 0, 0, filename, hash); #endif } *file = NULL; return -1; }
/* * pdu_packet = pduSourceNextPkt(source); * * Get the next PDU packet to process. * * This function processes the packet's header, sets the timestamp * for the flows in the packet, and checks the flow sequence * numbers. */ static const v5PDU * pduSourceNextPkt( skPDUSource_t *source) { /* For log messages that report out of sequence flow records, * these macros hold the start of the format and the start of the * argument list */ #define PDU_OOS_FORMAT(diff_is_neg) \ "'%s': Out-of-sequence packet:" \ " expecting %" PRIu32 ", received %" PRIu32 \ ", difference " diff_is_neg "%" PRId64 ", elapsed %f sec" \ ", engine %u.%u;" #define PDU_OOS_ARGS(diff_value) \ source->name, \ engine->flow_sequence, flow_sequence, diff_value, \ ((float)(now - engine->last_timestamp) / 1000.0), \ engine->id >> 8, engine->id & 0xFF const v5PDU *pdu; intmax_t now; uint16_t count; uint32_t flow_sequence; intmax_t router_boot; intmax_t sysUptime; int64_t seq_differ; uint64_t allrecs; pdu_engine_info_t *engine; pdu_engine_info_t target; assert(source != NULL); pdu = (v5PDU *)skUDPSourceNext(source->source); if (pdu == NULL) { /* if we saw any bad PDUs, print message before returning */ if (source->badpdu_status != PDU_OK && source->badpdu_consec) { NOTICEMSG(("'%s': Rejected %" PRIu32 " additional PDU record%s %s"), source->name, source->badpdu_consec, ((source->badpdu_consec == 1) ? "" : "s"), pdusrc_badpdu_msgs[source->badpdu_status]); source->badpdu_status = PDU_OK; } return NULL; } /* number of flow records in this packet */ count = ntohs(pdu->hdr.count); /* get the sequence number */ flow_sequence = ntohl(pdu->hdr.flow_sequence); /* use the PDU header to get the "current" time as * milliseconds since the UNIX epoch. */ now = ((intmax_t)1000 * ntohl(pdu->hdr.unix_secs) + (ntohl(pdu->hdr.unix_nsecs) / 1000000)); /* get sysUptime, which is the "current" time in milliseconds * since the export device booted */ sysUptime = ntohl(pdu->hdr.SysUptime); /* subtract sysUptime from current-time to get router boot time as * milliseconds since UNIX epoch */ router_boot = now - sysUptime; /* Determine the current engine */ target.id = ((uint16_t)pdu->hdr.engine_type << 8) | pdu->hdr.engine_id; engine = source->engine_info; if (engine == NULL || engine->id != target.id) { /* Current engine info must be updated */ engine = (pdu_engine_info_t*)rbfind(&target, source->engine_info_tree); if (engine == NULL) { /* There's no entry for this engine. Add one */ TRACEMSG(1, ("'%s': New engine %u.%u noticed", source->name, target.id >> 8, target.id & 0xFF)); engine = (pdu_engine_info_t*)calloc(1, sizeof(pdu_engine_info_t)); if (engine == NULL) { ERRMSG(("'%s': Memory allocation error allocating" " PDU engine %u.%u. Aborting."), source->name, target.id >> 8, target.id & 0xFF); exit(EXIT_FAILURE); }
void connect_do(void *pri_work, const ip_report_t *r) { char shost_s[32]; union { void *ptr; send_pri_workunit_t *w; uint8_t *inc; } w_u; union { void *ptr; connection_status_t *c; } c_u; union { const uint8_t *packet; const ip_report_t *r; const uint16_t *len; } r_u; struct in_addr ia; uint64_t state_key=0; size_t dlen=0, pk_len=0; uint32_t dhost=0, shost=0; uint16_t sport=0, dport=0; if (r == NULL) { PANIC("r ptr NULL"); } if (state_tbl == NULL) { PANIC("state table null"); } if (pri_work == NULL) { PANIC("pri_work NULL"); } if (r->magic != IP_REPORT_MAGIC) { ERR("wrong magic number for IP report"); return; } state_key=get_connectionkey(r); dhost=r->host_addr; dport=r->sport; sport=r->dport; shost=r->send_addr; if (rbfind(state_tbl, state_key, &c_u.ptr) > 0) { DBG(M_CON, "connection with flags are %s status is %d", strtcpflgs(r->type), c_u.c->status); r_u.r=r; if (r_u.r->doff) { pk_len=r_u.r->doff; r_u.packet += sizeof(ip_report_t); if (*r_u.len != pk_len) { ERR("report is damaged?, packet seems broken"); return; } else { r_u.len++; dlen=try_and_extract_tcp_data(r_u.packet, pk_len, c_u.c); if (dlen > 0) { c_u.c->tseq += dlen; } } } if (c_u.c->m_tstamp == 0 || c_u.c->t_tstamp == 0) { c_u.c->m_tstamp=0; c_u.c->t_tstamp=0; } else { c_u.c->m_tstamp++; /* XXX good enough for testing */ } if (dlen < c_u.c->window) c_u.c->window -= dlen; if (r->type & TH_RST) { c_u.c->status=U_TCP_CLOSE; s->stats.stream_remote_abort++; a_conns--; } switch (c_u.c->status) { case U_TCP_ESTABLISHED: if (r->type & TH_PSH) { w_u.ptr=xmalloc(sizeof(send_pri_workunit_t)); w_u.w->magic=PRI_4SEND_MAGIC; w_u.w->dhost=dhost; w_u.w->dport=dport; w_u.w->sport=sport; w_u.w->shost=c_u.c->send_ip; w_u.w->tseq=c_u.c->tseq; w_u.w->mseq=c_u.c->mseq; w_u.w->window_size=c_u.c->window; w_u.w->flags=TH_ACK|TH_FIN; w_u.w->doff=0; w_u.w->t_tstamp=c_u.c->t_tstamp; w_u.w->m_tstamp=c_u.c->m_tstamp; c_u.c->m_tstamp++; DBG(M_CON, "setting connection state into FIN_WAIT2 and sending ACK|FIN"); c_u.c->status=U_TCP_FIN_WAIT2; fifo_push(pri_work, w_u.ptr); s->stats.stream_segments_sent++; c_u.c->mseq++; w_u.ptr=NULL; } else if (r->type & TH_FIN) { c_u.c->tseq += 1; /* FIN eats a seq ;] */ w_u.ptr=xmalloc(sizeof(send_pri_workunit_t)); w_u.w->magic=PRI_4SEND_MAGIC; w_u.w->dhost=dhost; w_u.w->dport=dport; w_u.w->sport=sport; w_u.w->shost=c_u.c->send_ip; w_u.w->tseq=c_u.c->tseq; w_u.w->mseq=c_u.c->mseq; w_u.w->window_size=c_u.c->window; w_u.w->flags=TH_ACK; w_u.w->doff=0; w_u.w->t_tstamp=c_u.c->t_tstamp; w_u.w->m_tstamp=c_u.c->m_tstamp; DBG(M_CON, "acking FIN"); fifo_push(pri_work, w_u.ptr); s->stats.stream_segments_sent++; w_u.ptr=xmalloc(sizeof(send_pri_workunit_t)); w_u.w->magic=PRI_4SEND_MAGIC; w_u.w->dhost=dhost; w_u.w->dport=dport; w_u.w->sport=sport; w_u.w->shost=c_u.c->send_ip; w_u.w->tseq=c_u.c->tseq; w_u.w->mseq=c_u.c->mseq; w_u.w->window_size=c_u.c->window; w_u.w->flags=TH_ACK|TH_FIN; w_u.w->doff=0; w_u.w->t_tstamp=c_u.c->t_tstamp; w_u.w->m_tstamp=c_u.c->m_tstamp; c_u.c->m_tstamp++; DBG(M_CON, "setting connection into state closed and sending ACK|FIN"); fifo_push(pri_work, w_u.ptr); s->stats.stream_segments_sent++; c_u.c->status=U_TCP_CLOSE; fifo_push(pri_work, w_u.ptr); s->stats.stream_segments_sent++; w_u.ptr=NULL; c_u.c->mseq++; a_conns--; } break; /* U_TCP_ESTABLISHED: */ case U_TCP_CLOSE: if (r->type == TH_ACK) { break; } DBG(M_CON, "reseting a packet type %s (no connection entry)", strtcpflgs(r->type)); s->stats.stream_closed_alien_pkt++; w_u.ptr=xmalloc(sizeof(send_pri_workunit_t)); w_u.w->magic=PRI_4SEND_MAGIC; w_u.w->dhost=dhost; w_u.w->dport=dport; w_u.w->sport=sport; w_u.w->shost=c_u.c->send_ip; w_u.w->tseq=c_u.c->tseq; w_u.w->mseq=c_u.c->mseq; w_u.w->window_size=c_u.c->window; w_u.w->flags=TH_RST; w_u.w->doff=0; w_u.w->t_tstamp=c_u.c->t_tstamp; w_u.w->m_tstamp=c_u.c->m_tstamp; c_u.c->m_tstamp++; DBG(M_CON, "reseting packed to closed connection"); fifo_push(pri_work, w_u.ptr); s->stats.stream_segments_sent++; w_u.ptr=NULL; break; /* U_TCP_CLOSE */ case U_TCP_FIN_WAIT2: if (r->type & TH_FIN) { /* ok its closed both ways, lets ack the fin and be done with it */ c_u.c->tseq += 1; w_u.ptr=xmalloc(sizeof(send_pri_workunit_t)); w_u.w->magic=PRI_4SEND_MAGIC; w_u.w->dhost=dhost; w_u.w->dport=dport; w_u.w->sport=sport; w_u.w->shost=c_u.c->send_ip; w_u.w->tseq=c_u.c->tseq; w_u.w->mseq=c_u.c->mseq; w_u.w->window_size=c_u.c->window; w_u.w->flags=TH_ACK; w_u.w->doff=0; w_u.w->t_tstamp=c_u.c->t_tstamp; w_u.w->m_tstamp=c_u.c->m_tstamp; c_u.c->m_tstamp++; c_u.c->status=U_TCP_CLOSE; fifo_push(pri_work, w_u.ptr); s->stats.stream_segments_sent++; w_u.ptr=NULL; DBG(M_CON, "Setting connection to closed and acking final fin"); } break; /* U_TCP_FIN_WAIT2 */ # if 0 if (r->type & (TH_ACK|TH_SYN)) { } break; case U_TCP_FIN_WAIT1: case U_TCP_FIN_WAIT2: case U_TCP_CLOSING: case U_TCP_TIME_WAIT: case U_TCP_CLOSE_WAIT: case U_TCP_LAST_ACK: case U_TCP_CLOSE: # endif default: ERR("I have no code. I have no code"); break; } } /* found in state table */ else if ((r->type & (TH_ACK|TH_SYN)) == (TH_ACK|TH_SYN)) { /* should it be in state table */ DBG(M_CON, "Connection with flags %s", strtcpflgs(r->type)); /* yes this is a new connection */ c_u.ptr=xmalloc(sizeof(connection_status_t)); memset(c_u.ptr, 0, sizeof(connection_status_t)); c_u.c->status=U_TCP_ESTABLISHED; c_u.c->send_ip=shost; /* Our IP */ c_u.c->recv_len=0; c_u.c->send_len=0; c_u.c->send_buf=NULL; c_u.c->recv_buf=NULL; c_u.c->recv_stseq=0; c_u.c->tseq=r->tseq; c_u.c->mseq=r->mseq; c_u.c->window=r->window_size; /* XXX wscale */ c_u.c->t_tstamp=r->t_tstamp; c_u.c->m_tstamp=r->m_tstamp; c_u.c->ack_pending=1; if (GET_IMMEDIATE()) { ia.s_addr=shost; snprintf(shost_s, sizeof(shost_s) -1, "%s", inet_ntoa(ia)); ia.s_addr=dhost; VRB(0, "connected %s:%u -> %s:%u", shost_s, sport, inet_ntoa(ia), dport); } s->stats.stream_connections_est++; rbinsert(state_tbl, state_key, c_u.ptr); a_conns++; send_connect(state_key, c_u.c, pri_work, r); } /* looks like something we want to connect to ;] */ else { s->stats.stream_completely_alien_packet++; DBG(M_CON, "ignoring packet with flags %s", strtcpflgs(r->type)); } return; }