/*TODO test this function*/ char *btree_find(BTree *tree, char *str) { int diff = strcmp(tree->str, str); if (diff > 0) { if (tree->left == NULL) return NULL; return btree_find(tree->left, str); } else if (diff < 0) { if (tree->right == NULL) return NULL; return btree_find(tree->right, str); } else { return tree->str; } return NULL; }
int test_insert() { BTree *tree; BTree *find; int depth; tree = NULL; printf("The numbers should be in ascending order.\n"); btree_insert(&tree, "5"); btree_insert(&tree, "1"); btree_insert(&tree, "6"); btree_insert(&tree, "9"); btree_insert(&tree, "0"); btree_insert(&tree, "4"); btree_insert(&tree, "3"); btree_insert(&tree, "8"); btree_insert(&tree, "2"); btree_insert(&tree, "7"); btree_insert(&tree, "4"); /*print_preorder(tree);*/ printLevelOrder(tree,5); depth = btree_depth(tree); printf("d_single:%d\n", depth); find = btree_find(tree, "Z"); /*print_preorder(find);*/ if(find == NULL){ printf("Not found.\n"); }else{ printLevelOrder(find,5); } btree_free(tree); return 0; }
int get_bmap_ext( xfs_agnumber_t agno, xfs_agblock_t agbno, xfs_agblock_t maxbno, xfs_extlen_t *blen) { int *statep; unsigned long key; statep = btree_find(ag_bmap[agno], agbno, &key); if (!statep) return -1; if (key == agbno) { if (blen) { if (!btree_peek_next(ag_bmap[agno], &key)) return -1; *blen = MIN(maxbno, key) - agbno; } return *statep; } statep = btree_peek_prev(ag_bmap[agno], NULL); if (!statep) return -1; if (blen) *blen = MIN(maxbno, key) - agbno; return *statep; }
int pdb_item_create(pdb_t *p, uint16_t freq, uint32_t id) { pdb_entry_t *item; timestamp_t zero_ts; if (btree_find(p->db, id, (void**)&item)) { debug_msg("Item already exists\n"); return FALSE; } item = (pdb_entry_t*)xmalloc(sizeof(pdb_entry_t)); if (item == NULL) { return FALSE; } /* Initialize elements of item here as necesary **********************/ item->magic = 0xc001babe; item->ssrc = id; item->render_3D_data = NULL; item->enc = -1; item->enc_fmt_len = 2 * (CODEC_LONG_NAME_LEN + 1); item->enc_fmt = xmalloc(item->enc_fmt_len); item->sample_rate = freq; item->gain = 1.0; item->mute = 0; zero_ts = ts_map32(8000, 0); item->last_ui_update = zero_ts; item->first_mix = TRUE; /* Initial jitter estimate (30ms) */ item->jitter = ts_map32(8000, 240); item->transit = zero_ts; item->last_transit = zero_ts; item->last_last_transit = zero_ts; item->avg_transit = zero_ts; item->playout = zero_ts; item->last_arr = zero_ts; item->last_rtt = 0.0; item->avg_rtt = 0.0; /* Packet stats initialization */ item->received = 0; item->duplicates = 0; item->misordered = 0; item->jit_toged = 0; item->spike_toged = 0; item->spike_events = 0; pdb_item_validate(item); /*********************************************************************/ if (btree_add(p->db, id, (void*)item) == FALSE) { debug_msg("failed to add item to persistent database!\n"); return FALSE; } p->nelem++; return TRUE; }
int main() { BTree *tree; BTree *find; int depth; char *array[11]; array[0] = "5"; array[1] = "1"; array[2] = "6"; array[3] = "9"; array[4] = "0"; array[5] = "4"; array[6] = "3"; array[7] = "8"; array[8] = "2"; array[9] = "7"; array[10] = "4"; tree = array_to_btree(array); /*print_preorder(tree);*/ printLevelOrder(tree,5); depth = btree_depth(tree); printf("d_array:%d\n", depth); find = btree_find(tree, "A"); /*print_preorder(find);*/ if(find == NULL){ printf("Not found.\n"); }else{ printLevelOrder(find,5); } btree_free(tree); test_insert(); return 0; }
static int L_readini( lua_State* L ) { const char* filename; inifile_t* inifile = NULL; inireader_iterator_t* iter = NULL; inireader_entry_t* current = NULL; btree_element_t* root = NULL; btree_element_t* groupelement = NULL; btree_element_t* grouproot = NULL; PARAM_STRING( filename ); if ( ( inifile = inireader_open( filename ) ) == NULL ) { return_error(); } // Add every entry into a btree to get the arrays and groups in one piece later DEBUGLOG( "Creating btree" ); root = btree_create(); iter = inireader_get_iterator( inifile, 0, 0, 0, 0 ); DEBUGLOG( "Filling up btree" ); for ( current = inireader_iterate( iter ); current != NULL; current = inireader_iterate( iter ) ) { DEBUGLOG( "Searching for or adding group: %s", current->group ); // Find group element groupelement = btree_find( root, current->group ); if ( groupelement == NULL ) { // A new grouproot needs to be created DEBUGLOG( "Creating new grouproot" ); grouproot = btree_create(); btree_add( &root, current->group, grouproot ); } else { // Retrieve the already added grouproot DEBUGLOG( "Setting grouproot" ); grouproot = ( btree_element_t* )groupelement->data; } // Add the new element to the grouptree btree_add( &grouproot, current->identifier, current ); } // Traverse the tree and put our inivalues onto the lua stack DEBUGLOG( "Creating initial lua table" ); lua_newtable( L ); readini_tree_traverse( L, root ); DEBUGLOG( "Freeing the btree data" ); // Free the group trees readini_tree_free( root ); // Free the main tree btree_free( root ); // Close the inifile inireader_close( inifile ); return 1; }
char * uid2s(uid_t user) { static UID_DATA data; data.user = user; memcpy((char *) &data, (char *) btree_find(&uid2s_tree, &data), sizeof(UID_DATA)); return data.name; }
/** * btree_find - Given a string, finds the leaf in a binary tree which has that * same string as it's key value * * @tree: Pointer to the root leaf of binary tree * @str: The string to be search for in the binary tree * * Description: Uses strcmp to compare passed to string to the key value in a * leaf and then recursively runs the function on the left- or right-pointed * leaf until a match is found. */ BTree *btree_find(BTree *tree, char *str) { if (tree != NULL) { if (strcmp(str, tree->str) == 0) { return tree; } else if (strcmp(str, tree->str) < 0) { return btree_find(tree->left, str); } else { return btree_find(tree->right, str); } } else { return NULL; } }
int pdb_item_get(pdb_t *p, uint32_t id, pdb_entry_t **item) { void *v; if (btree_find(p->db, id, &v) == FALSE) { *item = NULL; return FALSE; } assert(v != NULL); *item = (pdb_entry_t*)v; pdb_item_validate(*item); return TRUE; }
void reset_bmaps(xfs_mount_t *mp) { xfs_agnumber_t agno; xfs_agblock_t ag_size; int ag_hdr_block; ag_hdr_block = howmany(4 * mp->m_sb.sb_sectsize, mp->m_sb.sb_blocksize); ag_size = mp->m_sb.sb_agblocks; for (agno = 0; agno < mp->m_sb.sb_agcount; agno++) { if (agno == mp->m_sb.sb_agcount - 1) ag_size = (xfs_extlen_t)(mp->m_sb.sb_dblocks - (xfs_drfsbno_t)mp->m_sb.sb_agblocks * agno); #ifdef BTREE_STATS if (btree_find(ag_bmap[agno], 0, NULL)) { printf("ag_bmap[%d] btree stats:\n", i); btree_print_stats(ag_bmap[agno], stdout); } #endif /* * We always insert an item for the first block having a * given state. So the code below means: * * block 0..ag_hdr_block-1: XR_E_INUSE_FS * ag_hdr_block..ag_size: XR_E_UNKNOWN * ag_size... XR_E_BAD_STATE */ btree_clear(ag_bmap[agno]); btree_insert(ag_bmap[agno], 0, &states[XR_E_INUSE_FS]); btree_insert(ag_bmap[agno], ag_hdr_block, &states[XR_E_UNKNOWN]); btree_insert(ag_bmap[agno], ag_size, &states[XR_E_BAD_STATE]); } if (mp->m_sb.sb_logstart != 0) { set_bmap_ext(XFS_FSB_TO_AGNO(mp, mp->m_sb.sb_logstart), XFS_FSB_TO_AGBNO(mp, mp->m_sb.sb_logstart), mp->m_sb.sb_logblocks, XR_E_INUSE_FS); } reset_rt_bmap(); }
// Perform timed batch queries in random order char *test_perf_query_rand() { srand(time(NULL)); clock_t start = clock(), diff; struct bt_cur cur; for (int i=0; i<n; i++) { int item = rand(); cur = btree_find(s, root, item); } diff = clock() - start; int msec = diff * 1000 / CLOCKS_PER_SEC; double ops = n * 1000; ops /= msec; printf("Time to query %u items: %u ms\n", n, msec); printf("Time per operation: %u us\n", (1000*msec)/n); printf("Operations per second: %f\n", ops); return NULL; }
int main(int argc, char **argv) { BTree *tree = btree_create(int_compare); int n = atoi(argv[1]); int a[n]; //int a[] = {1, 3, 2, 5, -1, 19, 15, 45, 9, 6, -4}; n = sizeof(a) / sizeof(a[0]); //n = 3; for (int i = 0; i < n; ++i) { //a[i] = i + 1; a[i] = rand() % 1000; btree_insert(tree, (void*)&a[i]); } for (int i = 0; i < n / 2; ++i) { btree_remove(btree_find(tree, &a[i])); } int expected_height = 2 * ceil(log(n + 1) / log(2)) + 1; btree_dump_dot(tree, node_attrs); btree_destroy(tree); }
int search_dup_extent( xfs_agnumber_t agno, xfs_agblock_t start_agbno, xfs_agblock_t end_agbno) { unsigned long bno; int ret; pthread_mutex_lock(&dup_extent_tree_locks[agno]); if (!btree_find(dup_extent_trees[agno], start_agbno, &bno)) { ret = 0; goto out; /* this really shouldn't happen */ } if (bno < end_agbno) { ret = 1; goto out; } ret = (uintptr_t)btree_peek_prev(dup_extent_trees[agno], NULL) > start_agbno; out: pthread_mutex_unlock(&dup_extent_tree_locks[agno]); return ret; }
int running_screen() { int n_items = 5; // Itens no menu char list[5][15] = { "Inserir", "Pesquisar", "Remover", "Imprimir DFS", "Voltar" }; int opt; print_header(); int i; for (i = 0; i < n_items; ++i) { printf(" %d) %s\n", i+1, list[i]); } printf("\n"); printf(" Digite uma opção: "); scanf("%d%*c", &opt); int key; node_position pos; switch (opt) { case 1: // Inserir if (n_keys == max_keys) { snprintf(msg, MSG_LEN, " O máximo de chaves adicionáveis para essa demo é %d.", max_keys); } else { printf(" Digite uma CHAVE que será associada ao VALOR \'%s\': ", values[n_keys]); scanf("%d", &key); pos = btree_insert(tree, key, values[n_keys]); if (pos.node == NULL) { snprintf(msg, MSG_LEN, " Inserção falhou. A CHAVE %d já existe na B-Tree.", key); } else { snprintf(msg, MSG_LEN, " Inserção da CHAVE %d associada ao VALOR \'%s\' realizada com sucesso.", key, values[n_keys]); n_keys++; } } break; case 2: // Pesquisar printf(" Digite uma CHAVE para pesquisar: "); scanf("%d", &key); pos = btree_find(tree, key); if (pos.node == NULL) { snprintf(msg, MSG_LEN, " A CHAVE %d não foi encontrada na B-Tree.", key); } else { snprintf(msg, MSG_LEN, " A CHAVE %d foi encontrada associada ao VALOR \'%s\'.", key, (char*) pos.node->keys[pos.index]->value); } break; case 3: // Remover printf(" Digite uma CHAVE para remover: "); scanf("%d", &key); pos = btree_remove(tree, key); if (pos.node == NULL) { snprintf(msg, MSG_LEN, " A CHAVE %d não foi encontrada na B-Tree.", key); } else { snprintf(msg, MSG_LEN, " A CHAVE %d foi removida com sucesso.", key); } break; case 4: // Imprimir printf(" Executando uma DFS na B-Tree:\n"); btree_dfs(tree); printf(" Pressione ENTER para continuar. "); getchar(); break; case 5: // Voltar/Sair snprintf(msg, MSG_LEN, " Deletando B-Tree e voltando ao menu"); goodbye(); // Única deleção de uma B-Tree btree_delete_h(tree); return HOME; break; default: snprintf(msg, MSG_LEN, " Opção inválida"); return RUNNING; break; } return RUNNING; }
int main(int argc, char ** argv) { int i; // do we have verbose output? bool ga_testing = false; if (argc > 1) { for (i = 1; i < argc; ++i) { if (!strcmp(argv[1],"-ga")) { ga_testing = true; break; } } } // initialize btree * tree = create_btree(16); bool flags[MAX_KEY]; for (i = 0; i < MAX_KEY; ++i) flags[i] = false; // get starting time struct timespec start, stop; clock_gettime(CLOCK_REALTIME,&start); // what we're timing for (int n = 0; n < TEST_SIZE; ++n) { // pick a key btree_key_t key = random_key(MAX_KEY); // is the key in the tree? btree_data_t data = btree_find(tree,key); if (data == NULL_DATA) { btree_insert(tree,key,(btree_data_t)key); flags[key] = true; } else { btree_remove(tree,key); flags[key] = false; } } // calculate run time clock_gettime(CLOCK_REALTIME,&stop); double run_time = (stop.tv_sec - start.tv_sec) + (double)(stop.tv_nsec - start.tv_nsec) / 1000000000.0; #if defined(VERIFY) // verify for (btree_key_t k = 0; k < MAX_KEY; ++k) { if (NULL_DATA == btree_find(tree,k)) { if (flags[k]) fprintf(stderr,"VERIFICATION ERROR: %l found, and shouldn't have been\n",k); } else { if (!flags[k]) fprintf(stderr,"VERIFICATION ERROR: %l not found, and should have been\n",k); } } #endif // clean up free_btree(tree); // report runtime if (ga_testing) fprintf(stdout,"%f",run_time); else fprintf(stdout,"\ntreebench (Std. C) run time: %f\n\n",run_time); fflush(stdout); // done return 0; }
static void update_bmap( struct btree_root *bmap, unsigned long offset, xfs_extlen_t blen, void *new_state) { unsigned long end = offset + blen; int *cur_state; unsigned long cur_key; int *next_state; unsigned long next_key; int *prev_state; cur_state = btree_find(bmap, offset, &cur_key); if (!cur_state) return; if (offset == cur_key) { /* if the start is the same as the "item" extent */ if (cur_state == new_state) return; /* * Note: this may be NULL if we are updating the map for * the superblock. */ prev_state = btree_peek_prev(bmap, NULL); next_state = btree_peek_next(bmap, &next_key); if (next_key > end) { /* different end */ if (new_state == prev_state) { /* #1: prev has same state, move offset up */ btree_update_key(bmap, offset, end); return; } /* #4: insert new extent after, update current value */ btree_update_value(bmap, offset, new_state); btree_insert(bmap, end, cur_state); return; } /* same end (and same start) */ if (new_state == next_state) { /* next has same state */ if (new_state == prev_state) { /* #3: merge prev & next */ btree_delete(bmap, offset); btree_delete(bmap, end); return; } /* #8: merge next */ btree_update_value(bmap, offset, new_state); btree_delete(bmap, end); return; } /* same start, same end, next has different state */ if (new_state == prev_state) { /* #5: prev has same state */ btree_delete(bmap, offset); return; } /* #6: update value only */ btree_update_value(bmap, offset, new_state); return; } /* different start, offset is in the middle of "cur" */ prev_state = btree_peek_prev(bmap, NULL); ASSERT(prev_state != NULL); if (prev_state == new_state) return; if (end == cur_key) { /* end is at the same point as the current extent */ if (new_state == cur_state) { /* #7: move next extent down */ btree_update_key(bmap, end, offset); return; } /* #9: different start, same end, add new extent */ btree_insert(bmap, offset, new_state); return; } /* #2: insert an extent into the middle of another extent */ btree_insert(bmap, offset, new_state); btree_insert(bmap, end, prev_state); }
static int btree_ui_find(struct btree_info *ui, const char *key) { return btree_find(ui->tree, key); }
int main_bstree(int argc, char** argv) { bool ok = true; /* Load forums from file into list. */ list_t *list_p = NULL; if (ok) ok = (list_p = list_init()) != NULL; if (ok) { printf("-> Loading forum.csv...\n"); ok = load_file("forum" ".csv", list_p); } printf("Forums: %d\n", list_size(list_p)); /* Timing variables. */ double t1, t2, real_time; struct tms tb; double tickspersec = (double) sysconf(_SC_CLK_TCK); /* Lookup a specific forum in the list for some iterations. */ t1 = (double) times(&tb); unsigned int iter1, m; iter1 = 4 * 0; for (m = 0; m < iter1; m++) { unsigned int i, size; char *forum_name = "Wall of Eric Wilby"; size = list_size(list_p); for (i = 0; i < size; i++) { forum_t *forum_p = NULL; list_get(list_p, (void **) &forum_p, i); if (!strcmp(forum_get_title(forum_p), forum_name)) { // printf("%s\n", forum_get_title(forum_p)); break; } } } t2 = (double) times(&tb); real_time = (double) (t2 - t1) / tickspersec; printf("Completed %u list lookups in %.3f sec\n", m, real_time); /* Load all forums in list to binary search tree. */ btree_t *btree_p = btree_init(forum_dstr, forum_cmp); if (btree_p == NULL) return (EXIT_FAILURE); unsigned int i, size; size = list_size(list_p); for (i = 0; i < size; i++) { forum_t *f_p = NULL; list_get(list_p, (void **) &f_p, i); btree_ins(btree_p, f_p); } printf("Loaded %u forums.\n", btree_size(btree_p)); /* Print forums in alphabetical order, exec print function with INORDER mode. */ unsigned int limit = 1500; bool ret = btree_exec(btree_p, INORDER, forum_print, &limit); printf("%u\n", ret); /* Perform lookups in binary search tree */ forum_t *forum_p = forum_init(0, "Wall of Eric Wilby", 0); t1 = (double) times(&tb); unsigned int n, iter2; iter2 = 667; for (n = 0; n < iter2; n++) { btree_node_t *btree_node_p = btree_find(btree_p, forum_p); if (btree_node_p != NULL) { forum_t *f_p = (forum_t *) btree_node_get_data(btree_node_p); forum_get_title(f_p); // printf("%s\n", forum_get_title(f_p)); } } t2 = (double) times(&tb); real_time = (double) (t2 - t1) / tickspersec; printf("Completed %u bstree lookups in %.3f sec\n", n, real_time); /* Free all memory */ forum_destroy(&forum_p); btree_destroy(&btree_p); // btree destroys forums, which are also on the list // size = list_size(list_p); // // for (i = 0; i < size; i++) // { // forum_t *f_p = NULL; // list_get(list_p, (void **) &f_p, i); // forum_destroy(&f_p); // } list_destroy(&list_p); return (EXIT_SUCCESS); }
void setcache(char *folder, char *searchstring, url_llist *urls) { long i, j; urlinfo *url; indexed_url *iurl; url_node *node = urls->front; btree indexed_urls; btree_init(&indexed_urls, (void *)indexed_urlcompare); // loop 1: index urls for (i = 0; i < urls->size; i++) { indexed_url *iurl = malloc(sizeof(indexed_url)); iurl->url = node->url; iurl->index = i; btree_insert(&indexed_urls, iurl); node = node->next; } // open file for write char *modifiedsearch = tounderline(searchstring); char *path = getpath(folder, modifiedsearch); FILE *file = fopen(path, "w"); // write number of links fprintf(file, "%d\n", urls->size); // loop 2: write data node = urls->front; indexed_url urltofind; for (i = 0; i < urls->size; i++) { url = node->url; /* * Write url data * format: index url numlinks * link1 link2 link3 */ // write header char *urlstring = url_tostring(url); fprintf(file, "%s %d\n", urlstring, url->outlinks.size); free(urlstring); // write links lnode *outlink_node = url->outlinks.front; for (j = 0; j < url->outlinks.size; j++) { // find indexed url so its index can be recorded urltofind.url = outlink_node->data; indexed_url *iurl = btree_find(&indexed_urls, &urltofind); // write it, followed by a space fprintf(file, "%lu ", iurl->index); outlink_node = outlink_node->next; } if (url->outlinks.size) fprintf(file, "\n"); node = node->next; } btree_free(&indexed_urls, 1); free(modifiedsearch); free(path); close(file); }
int main(int argc, char **argv) { struct btree *bt; uint64_t ptr; int j, count, op, arg; if (argc != 4) { fprintf(stderr,"Usage: btree_example <op> <size/ptr> <count>\n"); exit(1); } count = atoi(argv[3]); arg = atoi(argv[2]); if (!strcasecmp(argv[1],"alloc")) { op = OP_ALLOC; } else if (!strcasecmp(argv[1],"free")) { op = OP_FREE; } else if (!strcasecmp(argv[1],"allocfree")) { op = OP_ALLOCFREE; } else if (!strcasecmp(argv[1],"add")) { op = OP_ADD; } else if (!strcasecmp(argv[1],"walk")) { op = OP_WALK; } else if (!strcasecmp(argv[1],"fill")) { op = OP_FILL; } else if (!strcasecmp(argv[1],"find")) { op = OP_FIND; } else { printf("not supported op %s\n", argv[1]); exit(1); } bt = btree_open(NULL, "./btree.db", BTREE_CREAT); btree_clear_flags(bt,BTREE_FLAG_USE_WRITE_BARRIER); if (bt == NULL) { perror("btree_open"); exit(1); } for (j = 0; j < count; j++) { if (op == OP_ALLOC) { ptr = btree_alloc(bt,arg); printf("PTR: %llu\n", ptr); } else if (op == OP_FREE) { btree_free(bt,arg); } else if (op == OP_ALLOCFREE) { ptr = btree_alloc(bt,arg); printf("PTR: %llu\n", ptr); btree_free(bt,ptr); } } if (op == OP_ADD) { int retval; char key[16]; memset(key,0,16); strcpy(key,argv[2]); retval = btree_add(bt,(unsigned char*)key, (unsigned char*)argv[3],strlen(argv[3]),1); printf("retval %d\n", retval); if (retval == -1) { printf("Error: %s\n", strerror(errno)); } } else if (op == OP_WALK) { btree_walk(bt,bt->rootptr); } else if (op == OP_FILL) { for (j = 0; j < count; j++) { int r = random()%arg; int retval; char key[64]; char val[64]; memset(key,0,64); snprintf(key,64,"k%d",r); snprintf(val,64,"val:%d",r); retval = btree_add(bt,(unsigned char*)key, (unsigned char*)val, strlen(val), 1); if (retval == -1) { printf("Error: %s\n", strerror(errno)); goto err; } } } else if (op == OP_FIND) { int retval; char key[16], *data; memset(key,0,16); strcpy(key,argv[2]); uint64_t voff; uint32_t datalen; retval = btree_find(bt,(unsigned char*)key,&voff); if (retval == -1) { if (errno == ENOENT) { printf("Key not found\n"); exit(0); } else { perror("Error searching for key"); exit(1); } } printf("Key found at %llu\n", voff); btree_alloc_size(bt,&datalen,voff); data = malloc(datalen+1); btree_pread(bt,(unsigned char*)data,datalen,voff); data[datalen] = '\0'; printf("Value: %s\n", data); free(data); } btree_close(bt); return 0; err: btree_close(bt); return 1; }
/*!---------------------------------------------------------------------------- s m _ m a l l o c @brief Allocate a chunk of shared memory for a user. This function will allocate a chunk of shared memory of the specified size (in bytes). If no memory is available of the specified size, a NULL pointer will be returned, otherwise, the address (not the offset) of the allocated chunk will be returned to the caller. This function operates identically to the system "malloc" function and can be used the same way. @param[in] size - The size in bytes of the memory desired. @return The address of the allocated memory chunk. NULL if the request could not be honored. -----------------------------------------------------------------------------*/ void* sm_malloc ( size_t size ) { #ifdef VSI_DEBUG LOG ( "In sm_malloc[%lu]\n", size ); //dumpSM(); #endif memoryChunk_t needed = { 0 }; memoryChunk_t* found; memoryChunk_t* availableChunk; unsigned long neededSize; int status; // // Initialize the size of the memory we need. Note that we need enough // space to insert the chunkHeader_t at the beginning of the block the // user wants. // neededSize = size + CHUNK_HEADER_SIZE; // // Make sure the memory we are going to allocate is a multiple of 8 bytes // by rounding it up to the next multiple of 8. Note that since we start // with a properly aligned block of memory, all of the allocated blocks // will also be properly aligned as long as we make sure they are all a // multiple of 8 bytes. // // TODO: Do we need to generalize this? (like using "sizeof(long)", etc. // neededSize = ( neededSize + 7 ) & 0xfffffffffffffff8; // // If the shared memory memory management system has not yet been // initialized, just grab what we need from the beginning of the shared // memory segment. // if ( ! sysControl->systemInitialized ) { printf ( "Error: sm_malloc called before init finished for size: [%zu]\n", size ); exit ( 255 ); } // // If we got here we are operating in "normal" mode rather than // "infrastructure initialization" mode. // // Lock the mutex that controls the shared memory manager. // SM_LOCK; // // Set up the data structure that we need to search for the appropriately // sized chunk of memory. // needed.segmentSize = neededSize; needed.offset = 0; // // Go find the first block in the available B-tree that is equal to or // greater than the size we need. // btree_iter iter = btree_find ( &sysControl->availableMemoryBySize, &needed ); // // If the search didn't find anything then we don't have any memory // chunks large enough to fulfill the request so there is something // seriously wrong and we should just abort for the time being. // // TODO: In the future we should be able to extend the shared memory // segment with little overhead. // if ( btree_iter_at_end ( iter ) ) { printf ( "Error: No memory block of size %zu is available! Aborting\n", size ); goto mallocEnd; } // // Get the address of the chunk of memory that we found. // found = availableChunk = btree_iter_data ( iter ); // // Go remove the chunk of memory we found from the indices. // (void)deleteMemoryChunk ( found ); // // If the memory chunk we found is much larger than what we asked for // then we will need to split the chunk into 2 pieces. The split // threashold is here to keep us from splitting off a piece of memory // that is so small that it's not useful. Anything less than the split // threshold will just be left as a single block with some unused space // at the end to cut down on memory fragmentation. // if ( found->segmentSize - neededSize > SPLIT_THRESHOLD ) { // // Remove the size of the memory chunk we need from the beginning of // what was found and put the remainder back into the "available" // B-tree. // // Increment our pointer to the beginning of the leftover memoryChunk // header structure location. // found = (void*)found + neededSize; // // Populate the new header with all the new information for the // leftover piece of memory. // found->marker = SM_FREE_MARKER; found->offset = availableChunk->offset + neededSize; found->segmentSize = availableChunk->segmentSize - neededSize; found->type = TYPE_SYSTEM; // // Go insert the leftover piece of memory back into the indices. // (void)insertMemoryChunk ( found ); // // Fix the fields of the initial piece that we split off to be correct // now. // availableChunk->marker = SM_IN_USE_MARKER; availableChunk->segmentSize = neededSize; } // // If there is no need to split the piece that we found, just mark it as // "in use". // else { availableChunk->marker = SM_IN_USE_MARKER; } mallocEnd: // // Go clean up all of the iterator data and memory. // btree_iter_cleanup ( iter ); // // Go unlock our shared memory mutex. // SM_UNLOCK; #ifdef VSI_DEBUG // // Return the address of the user data part of the available memory chunk // to the caller. // LOG ( " sm_malloc returning[%p]\n", &availableChunk->data ); // // Perform a sanity check on this chunk of memory by checking to make // sure it is not past the end of the shared memory segment. // // TODO: Check for greater than start of SM also! // if ( (void*)&availableChunk->data >= (void*)sysControl + sysControl->sharedMemorySegmentSize ) { printf ( "\n\nERROR!!! sm_malloc retuning a bad address!!\n\n" ); printf ( " %lu past end of shared memory segment!\n", (void*)&availableChunk->data - (void*)sysControl->sharedMemorySegmentSize ); } #endif // // Return the address of the shared memory chunk just allocated to the // caller. // return &availableChunk->data; }
int find_file_in_dir( char *name, int dev, int dir_inode_nr ) { struct m_inode *inode = get_inode( dev, dir_inode_nr ); return btree_find( inode, name ); }