int PurgeLWSessionCache(Stream5SessionCache *sessionCache) { int retCount = 0; Stream5LWSession *idx; SFXHASH_NODE *hnode; if (!sessionCache) return 0; /* Remove all sessions from the hash table. */ hnode = sfxhash_mru_node(sessionCache->hashTable); while (hnode) { idx = (Stream5LWSession *)hnode->data; if (!idx) { sfxhash_free_node(sessionCache->hashTable, hnode); } else { idx->session_flags |= SSNFLAG_PRUNED; DeleteLWSession(sessionCache, idx); } hnode = sfxhash_mru_node(sessionCache->hashTable); retCount++; } return retCount; }
/* Prune file entries based on LRU */ static int pruneFileCache(FileCache *fileCache, FileEntry *file) { SFXHASH_NODE *lru_node = NULL; int pruned = 0; int mustdie = fileCache->cleanup_files; while (pruned < mustdie && (sfxhash_count(fileCache->hashTable) > 0)) { if ((lru_node = sfxhash_lru_node(fileCache->hashTable)) != NULL) { if (lru_node->data == file) break; if (sfxhash_free_node(fileCache->hashTable, lru_node) != SFXHASH_OK) { LogMessage("WARNING: failed to remove file entry from hash.\n"); } pruned++; } } fileCache->status.prunes += pruned; return pruned; }
/** * * @param sip - source IP address * @param dip - destination IP address * @param sport - server sport number * @param file_sig - file signature * @param expiry - session expiry in seconds. */ int file_resume_block_add_file(void *pkt, uint32_t file_sig, uint32_t timeout, File_Verdict verdict, uint32_t file_type_id, uint8_t *signature) { FileHashKey hashKey; SFXHASH_NODE *hash_node = NULL; FileNode *node; FileNode new_node; snort_ip_p srcIP; snort_ip_p dstIP; Packet *p = (Packet *)pkt; time_t now = p->pkth->ts.tv_sec; srcIP = GET_SRC_IP(p); dstIP = GET_DST_IP(p); IP_COPY_VALUE(hashKey.dip, dstIP); IP_COPY_VALUE(hashKey.sip, srcIP); hashKey.file_sig = file_sig; hash_node = sfxhash_find_node(fileHash, &hashKey); if (hash_node) { if (!(node = hash_node->data)) sfxhash_free_node(fileHash, hash_node); } else node = NULL; if (node) { node->expires = now + timeout; updateFileNode(node, verdict, file_type_id, signature); } else { DEBUG_WRAP(DebugMessage(DEBUG_FILE, "Adding file node\n");); updateFileNode(&new_node, verdict, file_type_id, signature); /* * use the time that we keep files around * since this info would effectively be invalid * after that anyway because the file that * caused this will be gone. */ new_node.expires = now + timeout; /* Add it to the table */ if (sfxhash_add(fileHash, &hashKey, &new_node) != SFXHASH_OK) { /* Uh, shouldn't get here... * There is already a node or couldn't alloc space * for key. This means bigger problems, but fail * gracefully. */ DEBUG_WRAP(DebugMessage(DEBUG_FILE, "Failed to add file node to hash table\n"););
/*! * Remove a Key + Data Pair from the table. * * @param t SFXHASH table pointer * @param key users key pointer * * @return 0 success * @retval !0 failed * */ int sfxhash_remove( SFXHASH * t, void * key) { SFXHASH_NODE * hnode; unsigned hashkey, index; hashkey = t->sfhashfcn->hash_fcn( t->sfhashfcn, (unsigned char*)key, t->keysize ); index = hashkey % t->nrows; hnode = t->table[index]; for( hnode=t->table[index]; hnode; hnode=hnode->next ) { if( !t->sfhashfcn->keycmp_fcn(hnode->key,key,t->keysize) ) { return sfxhash_free_node( t, hnode ); } } return SFXHASH_ERR; }
/** * * @param sip - source IP address * @param dip - destination IP address * @param sport - server sport number * @param file_sig - file signature * @param expiry - session expiry in seconds. */ int file_resume_block_add_file(void *pkt, uint32_t file_sig, uint32_t timeout, File_Verdict verdict, uint32_t file_type_id, uint8_t *signature) { FileHashKey hashKey; SFXHASH_NODE *hash_node = NULL; FileNode *node; FileNode new_node; sfaddr_t* srcIP; sfaddr_t* dstIP; Packet *p = (Packet*)pkt; time_t now = p->pkth->ts.tv_sec; srcIP = GET_SRC_IP(p); dstIP = GET_DST_IP(p); sfaddr_copy_to_raw(&hashKey.dip, dstIP); sfaddr_copy_to_raw(&hashKey.sip, srcIP); hashKey.file_sig = file_sig; #ifdef HAVE_DAQ_DP_ADD_DC { DAQ_DC_Params params; memset(¶ms, 0, sizeof(params)); params.flags = DAQ_DC_ALLOW_MULTIPLE | DAQ_DC_PERSIST; params.timeout_ms = 5 * 60 * 1000; /* 5 minutes */ if (p->packet_flags & PKT_FROM_CLIENT) DAQ_Add_Dynamic_Protocol_Channel(p, srcIP, 0, dstIP, p->dp, GET_IPH_PROTO(p), ¶ms); else if (p->packet_flags & PKT_FROM_SERVER) DAQ_Add_Dynamic_Protocol_Channel(p, dstIP, 0, srcIP, p->sp, GET_IPH_PROTO(p), ¶ms); } #endif hash_node = sfxhash_find_node(fileHash, &hashKey); if (hash_node) { if (!(node = hash_node->data)) sfxhash_free_node(fileHash, hash_node); } else node = NULL; if (node) { node->expires = now + timeout; updateFileNode(node, verdict, file_type_id, signature); } else { DEBUG_WRAP(DebugMessage(DEBUG_FILE, "Adding file node\n");); updateFileNode(&new_node, verdict, file_type_id, signature); /* * use the time that we keep files around * since this info would effectively be invalid * after that anyway because the file that * caused this will be gone. */ new_node.expires = now + timeout; /* Add it to the table */ if (sfxhash_add(fileHash, &hashKey, &new_node) != SFXHASH_OK) { /* Uh, shouldn't get here... * There is already a node or couldn't alloc space * for key. This means bigger problems, but fail * gracefully. */ DEBUG_WRAP(DebugMessage(DEBUG_FILE, "Failed to add file node to hash table\n"););