#include "database.h" #include #include #include #include static DBM* current_database; int open_database(char* dbFileName, database_permission permission) { int permission_flag; if (permission == database_read) { permission_flag = O_RDONLY; } else { permission_flag = O_RDWR | O_CREAT | O_EXCL; } current_database = dbm_open(dbFileName, permission_flag, 0644); if (current_database == NULL) { fprintf(stderr, "COULD NOT OPEN DATABASE\n"); return 0; } return 1; } void close_database() { dbm_close(current_database); current_database = NULL; } FileID add_file(char* filename) { static FileID fileIndex = 0; datum key, value; char keystring[sizeof(FileID) + 1]; fileIndex++; /* prefix the file key with 0 so we can tell them from words, which * would never start with the nul character. */ keystring[0] = '\0'; memcpy(&keystring[1], &fileIndex, sizeof(FileID)); key.dptr = keystring; key.dsize = sizeof(FileID) + 1; value.dptr = filename; value.dsize = strlen(filename) + 1; /* store the terminator, too. */ if (dbm_store(current_database, key, value, DBM_REPLACE) < 0) { fprintf(stderr, "Error: add_file failed for %s\n", filename); return -1; } return fileIndex; } void add_file_property(FileID fileid, const char* property, const char* property_value){ char* currentdata; datum key, value; int newdatasize; char keystring[sizeof(FileID) + 1]; keystring[0] = '\0'; memcpy(&keystring[1], &fileid, sizeof(FileID)); key.dptr = keystring; key.dsize = sizeof(FileID) + 1; value = dbm_fetch(current_database, key); if (value.dsize < 1) { fprintf(stderr, "Error: add_file_property with invalid ID\n"); } else { currentdata = value.dptr; newdatasize = value.dsize + strlen(property) + strlen(property_value) + 3; value.dptr = (char*)malloc(newdatasize); memcpy(value.dptr, currentdata, value.dsize); free(currentdata); strcpy(value.dptr + value.dsize + 1, property); strcpy(value.dptr + value.dsize + strlen(property) + 2, property_value); value.dsize = newdatasize; if (dbm_store(current_database, key, value, DBM_REPLACE) < 0) { fprintf(stderr, "Error: add_file_property failed for %s %s\n", value.dptr, property); return; } free(value.dptr); } } char* lookup_file_property(FileID fileid, const char* property) { datum key, value; char keystring[sizeof(FileID) + 1]; char* result = 0; keystring[0] = '\0'; memcpy(&keystring[1], &fileid, sizeof(FileID)); key.dptr = keystring; key.dsize = sizeof(FileID) + 1; value = dbm_fetch(current_database, key); if (value.dptr != NULL) { int position; char* stringpointer; for (position = strlen(value.dptr) + 1; position + 1 < value.dsize;) { if (strcmp(property, value.dptr + position + 1) == 0) { position += strlen(value.dptr + position + 1) + 1; result = (char*)malloc(strlen(value.dptr + position + 1) + 1); strcpy(result, value.dptr + position + 1); break; } /* skip property */ position += strlen(value.dptr + position + 1) + 1; /* skip value */ position += strlen(value.dptr + position + 1) + 1; } } return result; } void print_all_properties(FileID fileid, FILE* to_file) { datum key, value; char keystring[sizeof(FileID) + 1]; char* result = 0; keystring[0] = '\0'; memcpy(&keystring[1], &fileid, sizeof(FileID)); key.dptr = keystring; key.dsize = sizeof(FileID) + 1; value = dbm_fetch(current_database, key); if (value.dptr != NULL) { int position; char* stringpointer; for (position = strlen(value.dptr) + 1; position + 1 < value.dsize;) { fprintf(to_file, " %s=\"", value.dptr + position + 1); position += strlen(value.dptr + position + 1) + 1; fprintf(to_file, "%s\"", value.dptr + position + 1); position += strlen(value.dptr + position + 1) + 1; } } } char* lookup_file(FileID id) { datum key, value; char keystring[sizeof(FileID) + 1]; keystring[0] = '\0'; memcpy(&keystring[1], &id, sizeof(FileID)); key.dptr = keystring; key.dsize = sizeof(FileID) + 1; value = dbm_fetch(current_database, key); return value.dptr; } void add_word(char* word, FileID file, long score, long first_line) { datum key, value; word_record* original_wordlist; word_record* new_wordlist; int wordlist_size; int list_index; word_record new_word; printf("ADDING WORD: %s\n", word); wordlist_size = lookup_word(word, &original_wordlist); new_wordlist = (word_record*)malloc((wordlist_size + 1) * sizeof(word_record)); new_word.file = file; new_word.score = score; new_word.first_line = first_line; for (list_index = 0; list_index < wordlist_size; list_index++) { if (original_wordlist[list_index].score < new_word.score) { word_record temp_record; temp_record = original_wordlist[list_index]; original_wordlist[list_index] = new_word; new_word = temp_record; } } new_wordlist[list_index] = new_word; if (wordlist_size > 0) { memcpy(new_wordlist, original_wordlist, (wordlist_size * sizeof(word_record))); free(original_wordlist); } key.dptr = word; key.dsize = strlen(word); value.dptr = (char*)new_wordlist; value.dsize = (wordlist_size + 1) * sizeof(word_record); if (dbm_store(current_database, key, value, DBM_REPLACE) < 0) { fprintf(stderr, "Error: add_word failed for %s\n", word); } free(new_wordlist); } int lookup_word(char* word, word_record** wordlist_alias) { datum key, value; key.dptr = word; key.dsize = strlen(word); value = dbm_fetch(current_database, key); *wordlist_alias = (word_record*)value.dptr; return value.dsize / sizeof(word_record); }