int geo_verify(geo_ctx_t* geo_ctx) { geo_head_t* geo_head = (geo_head_t*)geo_ctx->ptr; if(geo_head->magic != GEODATA_MAGIC){ printf("ERROR: invalid magic: 0x%04x\n", geo_head->magic); return -1; } if(geo_head->filesize != geo_ctx->size){ printf("ERROR: geo_head.filesize(%u) != real filesize(%u)\n", geo_head->filesize, geo_ctx->size); return -1; } unsigned int const_count = (geo_head->const_table_offset-sizeof(geo_head_t))/sizeof(const_index_t); if(const_count != geo_head->const_count){ printf("ERROR: geo_head.const_count: %u != calculate const_count: %u\n", geo_head->const_count, const_count); return -1; } unsigned int i; const_index_t* indexs = (const_index_t*)(geo_ctx->ptr + sizeof(geo_head_t)); int const_pool_size = geo_head->geo_item_offset-geo_head->const_table_offset; for(i=0;i<const_count;i++){ if(!idx_is_valid(indexs[i], const_pool_size)){ printf("ERROR: indexs[%d].begin:%d, len:%d not in constant pool: 0-%d\n", i, indexs[i].begin, indexs[i].len, const_pool_size); return -1; } } unsigned int geo_item_count = (geo_ctx->size - geo_head->geo_item_offset)/sizeof(geo_item_t); if(geo_item_count != geo_head->geo_item_count){ printf("ERROR: geo_head.geo_item_count: %u != calculate geo_item_count: %u\n", geo_head->geo_item_count, geo_item_count); return -1; } geo_item_t* items = (geo_item_t*)(geo_ctx->ptr + geo_head->geo_item_offset); for(i=0;i<geo_head->geo_item_count;i++){ if(!item_is_valid(items[i], const_count)){ printf("ERROR: geo_item[%d].province:%d, city:%d, isp:%d index great then const_count: %d\n", i, items[i].province, items[i].city, items[i].isp, const_count); return -1; } } return 0; }
void assoc_scan_next(struct default_engine *engine, struct assoc_scan *scan) { assert(scan->guard_data == 23456); struct assoc *assoc = &engine->assoc; hash_item *it; uint32_t ii, ntables; uint32_t found_count; uint32_t access_count = 0; scan->item_count = 0; while (scan->cur_bucket < scan->max_bucket) { if (scan->cur_tabidx == 0) { /* increment bucket's reference count */ assoc->infotable[scan->cur_bucket].refcount += 1; } ntables = hashsize(assoc->infotable[scan->cur_bucket].curpower); for (ii=scan->cur_tabidx; ii < ntables; ii++) { if (access_count > (MAX_SCAN_ITEMS/2)) { break; /* long time elapsed after holding cache lock */ } found_count = 0; it = assoc->roottable[ii].hashtable[scan->cur_bucket]; while (it != NULL) { access_count++; if (item_is_valid(engine, it)) { if ((scan->item_count + found_count) >= scan->array_size) { break; /* overflow */ } scan->item_array[scan->item_count + found_count]= it; found_count += 1; } it = it->h_next; } if (it != NULL) { /* overflow */ scan->cur_tabidx = ii; break; } scan->item_count += found_count; } if (ii < ntables) break; /* decrement bucket's reference count */ assoc->infotable[scan->cur_bucket].refcount -= 1; scan->cur_tabidx = 0; scan->cur_bucket += 1; } }