| | 74 | Db->DB_Create = DB_Create_Native; |
|---|
| | 75 | Db->DB_Open = DB_Open_Native; |
|---|
| | 76 | Db->DB_Close = DB_Close_Native; |
|---|
| | 77 | Db->DB_Remove = DB_Remove_Native; |
|---|
| | 78 | |
|---|
| | 79 | Db->DB_InitWriteHeader = DB_InitWriteHeader_Native; |
|---|
| | 80 | Db->DB_WriteHeaderData = DB_WriteHeaderData_Native; |
|---|
| | 81 | Db->DB_EndWriteHeader = DB_EndWriteHeader_Native; |
|---|
| | 82 | |
|---|
| | 83 | Db->DB_InitReadHeader = DB_InitReadHeader_Native; |
|---|
| | 84 | Db->DB_ReadHeaderData = DB_ReadHeaderData_Native; |
|---|
| | 85 | Db->DB_EndReadHeader = DB_EndReadHeader_Native; |
|---|
| | 86 | |
|---|
| | 87 | Db->DB_InitWriteWords = DB_InitWriteWords_Native; |
|---|
| | 88 | Db->DB_GetWordID = DB_GetWordID_Native; |
|---|
| | 89 | Db->DB_WriteWord = DB_WriteWord_Native; |
|---|
| | 90 | |
|---|
| | 91 | #ifndef USE_BTREE |
|---|
| | 92 | Db->DB_WriteWordHash = DB_WriteWordHash_Native; |
|---|
| | 93 | #else |
|---|
| | 94 | Db->DB_UpdateWordID = DB_UpdateWordID_Native; |
|---|
| | 95 | Db->DB_DeleteWordData = DB_DeleteWordData_Native; |
|---|
| | 96 | #endif |
|---|
| | 97 | |
|---|
| | 98 | Db->DB_WriteWordData = DB_WriteWordData_Native; |
|---|
| | 99 | Db->DB_EndWriteWords = DB_EndWriteWords_Native; |
|---|
| | 100 | |
|---|
| | 101 | Db->DB_InitReadWords = DB_InitReadWords_Native; |
|---|
| | 102 | Db->DB_ReadWordHash = DB_ReadWordHash_Native; |
|---|
| | 103 | Db->DB_ReadFirstWordInvertedIndex = DB_ReadFirstWordInvertedIndex_Native; |
|---|
| | 104 | Db->DB_ReadNextWordInvertedIndex = DB_ReadNextWordInvertedIndex_Native; |
|---|
| | 105 | Db->DB_ReadWordData = DB_ReadWordData_Native; |
|---|
| | 106 | Db->DB_EndReadWords = DB_EndReadWords_Native; |
|---|
| | 107 | |
|---|
| | 108 | Db->DB_WriteFileNum = DB_WriteFileNum_Native; |
|---|
| | 109 | Db->DB_ReadFileNum = DB_ReadFileNum_Native; |
|---|
| | 110 | Db->DB_CheckFileNum = DB_CheckFileNum_Native; |
|---|
| | 111 | Db->DB_RemoveFileNum = DB_RemoveFileNum_Native; |
|---|
| | 112 | |
|---|
| | 113 | Db->DB_InitWriteSortedIndex = DB_InitWriteSortedIndex_Native; |
|---|
| | 114 | Db->DB_WriteSortedIndex = DB_WriteSortedIndex_Native; |
|---|
| | 115 | Db->DB_EndWriteSortedIndex = DB_EndWriteSortedIndex_Native; |
|---|
| | 116 | |
|---|
| | 117 | Db->DB_InitReadSortedIndex = DB_InitReadSortedIndex_Native; |
|---|
| | 118 | Db->DB_ReadSortedIndex = DB_ReadSortedIndex_Native; |
|---|
| | 119 | Db->DB_ReadSortedData = DB_ReadSortedData_Native; |
|---|
| | 120 | Db->DB_EndReadSortedIndex = DB_EndReadSortedIndex_Native; |
|---|
| | 121 | |
|---|
| | 122 | Db->DB_InitWriteProperties = DB_InitWriteProperties_Native; |
|---|
| | 123 | Db->DB_WriteProperty = DB_WriteProperty_Native; |
|---|
| | 124 | Db->DB_WritePropPositions = DB_WritePropPositions_Native; |
|---|
| | 125 | Db->DB_ReadProperty = DB_ReadProperty_Native; |
|---|
| | 126 | Db->DB_ReadPropPositions = DB_ReadPropPositions_Native; |
|---|
| | 127 | Db->DB_Reopen_PropertiesForRead = DB_Reopen_PropertiesForRead_Native; |
|---|
| | 128 | |
|---|
| | 129 | #ifdef USE_BTREE |
|---|
| | 130 | Db->DB_WriteTotalWordsPerFile = DB_WriteTotalWordsPerFile_Native; |
|---|
| | 131 | Db->DB_ReadTotalWordsPerFile = DB_ReadTotalWordsPerFile_Native; |
|---|
| | 132 | #endif |
|---|
| | 133 | |
|---|
| 97 | | static void _DB_CheckHeader(struct Handle_DBNative *SW_DB) |
|---|
| 98 | | { |
|---|
| 99 | | long propindex, totwords, presorted, header; |
|---|
| 100 | | SW_DB->unique_ID = readlong(SW_DB->fp_prop, sw_fread); |
|---|
| 101 | | |
|---|
| 102 | | propindex = readlong(SW_DB->fp_propindex, sw_fread); |
|---|
| 103 | | if (SW_DB->unique_ID != propindex) |
|---|
| 104 | | { |
|---|
| 105 | | set_progerr(INDEX_FILE_ERROR, SW_DB->sw, "Properties file '%s' and propindex file '%s' are not related.", SW_DB->cur_prop_file, SW_DB->cur_propindex_file); |
|---|
| | 163 | static void DB_CheckHeader(struct Handle_DBNative *DB) |
|---|
| | 164 | { |
|---|
| | 165 | long swish_magic; |
|---|
| | 166 | |
|---|
| | 167 | sw_fseek(DB->fp, (sw_off_t)0, SEEK_SET); |
|---|
| | 168 | swish_magic = readlong(DB->fp, sw_fread); |
|---|
| | 169 | |
|---|
| | 170 | if (swish_magic != SWISH_MAGIC) |
|---|
| | 171 | { |
|---|
| | 172 | set_progerr(INDEX_FILE_ERROR, DB->sw, "File \"%s\" has an unknown format.", DB->cur_index_file); |
|---|
| 109 | | totwords = readlong(SW_DB->fp_totwords, sw_fread); |
|---|
| 110 | | if (SW_DB->unique_ID != totwords) |
|---|
| 111 | | { |
|---|
| 112 | | set_progerr(INDEX_FILE_ERROR, SW_DB->sw, "Properties file '%s' and totwords file '%s' are not related.", SW_DB->cur_prop_file, SW_DB->cur_totwords_file); |
|---|
| 113 | | return; |
|---|
| 114 | | } |
|---|
| 115 | | |
|---|
| 116 | | presorted = readlong(SW_DB->fp_presorted, sw_fread); |
|---|
| 117 | | |
|---|
| 118 | | if (SW_DB->unique_ID != presorted) |
|---|
| 119 | | { |
|---|
| 120 | | set_progerr(INDEX_FILE_ERROR, SW_DB->sw, "Properties file '%s' and presorted index file '%s' are not related.", SW_DB->cur_prop_file, SW_DB->cur_presorted_file); |
|---|
| 121 | | return; |
|---|
| 122 | | } |
|---|
| 123 | | |
|---|
| 124 | | header = readlong(SW_DB->fp_header, sw_fread); |
|---|
| 125 | | |
|---|
| 126 | | if (SW_DB->unique_ID != header) |
|---|
| 127 | | { |
|---|
| 128 | | set_progerr(INDEX_FILE_ERROR, SW_DB->sw, "Properties file '%s' and header index file '%s' are not related.", SW_DB->cur_prop_file, SW_DB->cur_header_file); |
|---|
| 129 | | return; |
|---|
| 130 | | } |
|---|
| | 176 | |
|---|
| | 177 | |
|---|
| | 178 | { |
|---|
| | 179 | #ifdef USE_BTREE |
|---|
| | 180 | long btree, worddata, hashfile, array, presorted; |
|---|
| | 181 | #endif |
|---|
| | 182 | long prop; |
|---|
| | 183 | |
|---|
| | 184 | DB->unique_ID = readlong(DB->fp, sw_fread); |
|---|
| | 185 | prop = readlong(DB->prop, sw_fread); |
|---|
| | 186 | |
|---|
| | 187 | if (DB->unique_ID != prop) |
|---|
| | 188 | { |
|---|
| | 189 | set_progerr(INDEX_FILE_ERROR, DB->sw, "Index file '%s' and property file '%s' are not related.", DB->cur_index_file, DB->cur_prop_file); |
|---|
| | 190 | return; |
|---|
| | 191 | } |
|---|
| | 192 | |
|---|
| | 193 | #ifdef USE_BTREE |
|---|
| | 194 | btree = readlong(DB->fp_btree, sw_fread); |
|---|
| | 195 | if (DB->unique_ID != btree) |
|---|
| | 196 | { |
|---|
| | 197 | set_progerr(INDEX_FILE_ERROR, DB->sw, "Index file '%s' and btree file '%s' are not related.", DB->cur_index_file, DB->cur_btree_file); |
|---|
| | 198 | return; |
|---|
| | 199 | } |
|---|
| | 200 | |
|---|
| | 201 | worddata = readlong(DB->fp_worddata, sw_fread); |
|---|
| | 202 | if (DB->unique_ID != worddata) |
|---|
| | 203 | { |
|---|
| | 204 | set_progerr(INDEX_FILE_ERROR, DB->sw, "Index file '%s' and worddata file '%s' are not related.", DB->cur_index_file, DB->cur_worddata_file); |
|---|
| | 205 | return; |
|---|
| | 206 | } |
|---|
| | 207 | |
|---|
| | 208 | hashfile = readlong(DB->fp_hashfile, sw_fread); |
|---|
| | 209 | if (DB->unique_ID != hashfile) |
|---|
| | 210 | { |
|---|
| | 211 | set_progerr(INDEX_FILE_ERROR, DB->sw, "Index file '%s' and hashfile file '%s' are not related.", DB->cur_index_file, DB->cur_hashfile_file); |
|---|
| | 212 | return; |
|---|
| | 213 | } |
|---|
| | 214 | |
|---|
| | 215 | array = readlong(DB->fp_array, sw_fread); |
|---|
| | 216 | if (DB->unique_ID != array) |
|---|
| | 217 | { |
|---|
| | 218 | set_progerr(INDEX_FILE_ERROR, DB->sw, "Index file '%s' and array file '%s' are not related.", DB->cur_index_file, DB->cur_array_file); |
|---|
| | 219 | return; |
|---|
| | 220 | } |
|---|
| | 221 | |
|---|
| | 222 | presorted = readlong(DB->fp_presorted, sw_fread); |
|---|
| | 223 | |
|---|
| | 224 | if (DB->unique_ID != presorted) |
|---|
| | 225 | { |
|---|
| | 226 | set_progerr(INDEX_FILE_ERROR, DB->sw, "Index file '%s' and presorted index file '%s' are not related.", DB->cur_index_file, DB->cur_presorted_file); |
|---|
| | 227 | return; |
|---|
| | 228 | } |
|---|
| | 229 | #endif |
|---|
| | 230 | } |
|---|
| | 231 | |
|---|
| 138 | | SW_DB = (struct Handle_DBNative *) emalloc(sizeof(struct Handle_DBNative)); |
|---|
| 139 | | memset( SW_DB, 0, sizeof( struct Handle_DBNative )); |
|---|
| 140 | | |
|---|
| 141 | | SW_DB->sw = sw; /* for error messages */ |
|---|
| 142 | | |
|---|
| 143 | | SW_DB->w_tell = sw_ftell; |
|---|
| 144 | | SW_DB->w_write = sw_fwrite; |
|---|
| 145 | | SW_DB->w_seek = sw_fseek; |
|---|
| 146 | | SW_DB->w_read = sw_fread; |
|---|
| 147 | | SW_DB->w_close = sw_fclose; |
|---|
| 148 | | SW_DB->w_putc = sw_fputc; |
|---|
| 149 | | SW_DB->w_getc = sw_fgetc; |
|---|
| 150 | | |
|---|
| 151 | | SW_DB->dbname = estrdup(dbname); |
|---|
| 152 | | |
|---|
| 153 | | return SW_DB; |
|---|
| | 239 | DB = (struct Handle_DBNative *) emalloc(sizeof(struct Handle_DBNative)); |
|---|
| | 240 | memset( DB, 0, sizeof( struct Handle_DBNative )); |
|---|
| | 241 | |
|---|
| | 242 | DB->sw = sw; /* for error messages */ |
|---|
| | 243 | |
|---|
| | 244 | if (WRITE_WORDS_RAMDISK) |
|---|
| | 245 | { |
|---|
| | 246 | DB->w_tell = ramdisk_tell; |
|---|
| | 247 | DB->w_write = ramdisk_write; |
|---|
| | 248 | DB->w_seek = ramdisk_seek; |
|---|
| | 249 | DB->w_read = ramdisk_read; |
|---|
| | 250 | DB->w_close = ramdisk_close; |
|---|
| | 251 | DB->w_putc = ramdisk_putc; |
|---|
| | 252 | DB->w_getc = ramdisk_getc; |
|---|
| | 253 | } |
|---|
| | 254 | else |
|---|
| | 255 | { |
|---|
| | 256 | DB->w_tell = sw_ftell; |
|---|
| | 257 | DB->w_write = sw_fwrite; |
|---|
| | 258 | DB->w_seek = sw_fseek; |
|---|
| | 259 | DB->w_read = sw_fread; |
|---|
| | 260 | DB->w_close = sw_fclose; |
|---|
| | 261 | DB->w_putc = sw_fputc; |
|---|
| | 262 | DB->w_getc = sw_fgetc; |
|---|
| | 263 | } |
|---|
| | 264 | |
|---|
| | 265 | DB->dbname = estrdup(dbname); |
|---|
| | 266 | |
|---|
| | 267 | return DB; |
|---|
| 196 | | /* Routine to compare packed longs - required to get BTREE duplicate entries |
|---|
| 197 | | ** sorted by wordID. wordID is a packed long |
|---|
| 198 | | */ |
|---|
| 199 | | int compare_packed_long(DB *dbp, const DBT *a, const DBT *b) |
|---|
| 200 | | { |
|---|
| 201 | | return memcmp(a->data, b->data, sizeof(long)); |
|---|
| 202 | | } |
|---|
| 203 | | |
|---|
| 204 | | |
|---|
| 205 | | DB * OpenBerkeleyFile(char *filename, DBTYPE db_type, u_int32_t db_flags, int dup) |
|---|
| 206 | | { |
|---|
| 207 | | DB *dbp; |
|---|
| 208 | | int db_ret; |
|---|
| 209 | | if((db_ret = db_create(&dbp, NULL, 0))) |
|---|
| 210 | | progerrno("Couldn't create BERKELEY DB resource"); |
|---|
| 211 | | if(dup) |
|---|
| 212 | | { |
|---|
| 213 | | if((db_ret = dbp->set_flags(dbp, DB_DUPSORT))) |
|---|
| 214 | | progerrno("Couldn't set DB_DUPSORT in DB Berkeley file \"%s\": ", filename); |
|---|
| 215 | | if((db_ret = dbp->set_dup_compare(dbp,compare_packed_long))) |
|---|
| 216 | | progerrno("Couldn't set DB_DUPSORT_ROUTINE in DB Berkeley file \"%s\": ", filename); |
|---|
| 217 | | } |
|---|
| 218 | | if((db_ret = dbp->open(dbp,NULL,filename,NULL,db_type,db_flags,0))) |
|---|
| 219 | | { |
|---|
| 220 | | dbp->err(dbp,db_ret,"Database open failed: \"%s\"", filename); |
|---|
| 221 | | progerrno("Couldn't open the DB Berkeley file \"%s\": ", filename); |
|---|
| 222 | | } |
|---|
| 223 | | |
|---|
| 224 | | return dbp; |
|---|
| 225 | | } |
|---|
| 226 | | |
|---|
| 227 | | DB * CreateBerkeleyFile(char *filename,DBTYPE db_type, int dup) |
|---|
| 228 | | { |
|---|
| 229 | | return OpenBerkeleyFile(filename, db_type, DB_CREATE | DB_TRUNCATE, dup); |
|---|
| 230 | | } |
|---|
| 231 | | |
|---|
| 232 | | void CloseBerkeleyFile(DB **dbp, char **filename, int *tempflag) |
|---|
| 233 | | { |
|---|
| 234 | | int ret; |
|---|
| 235 | | char *newname; |
|---|
| 236 | | DB *temp_dbp; |
|---|
| 237 | | if(*dbp) |
|---|
| 238 | | { |
|---|
| 239 | | ret = (*dbp)->close(*dbp,0); |
|---|
| 240 | | *dbp = NULL; |
|---|
| 241 | | if(*tempflag) |
|---|
| 242 | | { |
|---|
| 243 | | newname = estrdup(*filename); |
|---|
| 244 | | if((ret = db_create(&temp_dbp, NULL, 0))) |
|---|
| 245 | | progerrno("Couldn't create BERKELEY DB resource"); |
|---|
| 246 | | |
|---|
| 247 | | newname[strlen(newname) - strlen(USE_TEMPFILE_EXTENSION)] = '\0'; |
|---|
| 248 | | remove(newname); |
|---|
| 249 | | ret = temp_dbp->rename(temp_dbp,*filename,NULL,newname,0); |
|---|
| 250 | | if (ret != 0) |
|---|
| 251 | | { |
|---|
| 252 | | progerrno("Couldn't rename %s to %s. Berkeley DB Error code: %d\n",*filename,newname,ret); |
|---|
| 253 | | } |
|---|
| 254 | | efree(newname); |
|---|
| 255 | | *tempflag = 0; /* no longer opened as a temporary file */ |
|---|
| 256 | | } |
|---|
| 257 | | efree(*filename); |
|---|
| 258 | | *filename = NULL; |
|---|
| 259 | | } |
|---|
| 260 | | } |
|---|
| 261 | | |
|---|
| 262 | | |
|---|
| 263 | | void *_DB_Create(SWISH *sw, char *dbname) |
|---|
| 264 | | { |
|---|
| | 310 | |
|---|
| | 311 | /**********************/ |
|---|
| | 312 | |
|---|
| | 313 | |
|---|
| | 314 | |
|---|
| | 315 | void *DB_Create_Native(SWISH *sw, char *dbname) |
|---|
| | 316 | { |
|---|
| | 317 | int i; |
|---|
| 312 | | SW_DB->tmp_btree = 1; |
|---|
| 313 | | #endif |
|---|
| 314 | | SW_DB->db_btree = CreateBerkeleyFile(filename,DB_BTREE,1); |
|---|
| 315 | | /* Allow sorted duplicate items */ |
|---|
| 316 | | SW_DB->cur_btree_file = estrdup(filename); |
|---|
| | 380 | DB->tmp_btree = 1; |
|---|
| | 381 | #endif |
|---|
| | 382 | CreateEmptyFile(filename); |
|---|
| | 383 | if (!(fp_tmp = openIndexFILEForReadAndWrite(filename))) |
|---|
| | 384 | progerrno("Couldn't create the btree file \"%s\": ", filename); |
|---|
| | 385 | DB->cur_btree_file = estrdup(filename); |
|---|
| | 386 | printlong(fp_tmp, DB->unique_ID, sw_fwrite); |
|---|
| | 387 | DB->fp_btree = fp_tmp; |
|---|
| | 388 | DB->bt=BTREE_Create(DB->fp_btree,4096); |
|---|
| 324 | | SW_DB->tmp_worddata = 1; |
|---|
| 325 | | #endif |
|---|
| 326 | | SW_DB->db_worddata = CreateBerkeleyFile(filename,DB_RECNO,0); |
|---|
| 327 | | SW_DB->cur_worddata_file = estrdup(filename); |
|---|
| 328 | | |
|---|
| 329 | | /* Create totwords File */ |
|---|
| | 396 | DB->tmp_worddata = 1; |
|---|
| | 397 | #endif |
|---|
| | 398 | CreateEmptyFile(filename); |
|---|
| | 399 | if (!(fp_tmp = openIndexFILEForReadAndWrite(filename))) |
|---|
| | 400 | progerrno("Couldn't create the worddata file \"%s\": ", filename); |
|---|
| | 401 | printlong(fp_tmp, DB->unique_ID, sw_fwrite); |
|---|
| | 402 | DB->fp_worddata = fp_tmp; |
|---|
| | 403 | DB->cur_worddata_file = estrdup(filename); |
|---|
| | 404 | DB->worddata=WORDDATA_Open(DB->fp_worddata); |
|---|
| | 405 | |
|---|
| | 406 | /* Create Array File */ |
|---|
| 338 | | progerrno("Couldn't create the totwords file \"%s\": ", filename); |
|---|
| 339 | | printlong(fp_tmp, SW_DB->unique_ID, sw_fwrite); |
|---|
| 340 | | SW_DB->cur_totwords_file = estrdup(filename); |
|---|
| 341 | | SW_DB->fp_totwords = fp_tmp; |
|---|
| 342 | | |
|---|
| 343 | | /* Create propindex File */ |
|---|
| 344 | | strcpy(filename, dbname); |
|---|
| 345 | | strcat(filename, PROPINDEX_EXTENSION); |
|---|
| 346 | | #ifdef USE_TEMPFILE_EXTENSION |
|---|
| 347 | | strcat(filename, USE_TEMPFILE_EXTENSION); |
|---|
| 348 | | SW_DB->tmp_propindex = 1; |
|---|
| 349 | | #endif |
|---|
| 350 | | CreateEmptyFile(filename); |
|---|
| 351 | | if (!(fp_tmp = openIndexFILEForReadAndWrite(filename))) |
|---|
| 352 | | progerrno("Couldn't create the propindex file \"%s\": ", filename); |
|---|
| 353 | | printlong(fp_tmp, SW_DB->unique_ID, sw_fwrite); |
|---|
| 354 | | SW_DB->cur_propindex_file = estrdup(filename); |
|---|
| 355 | | SW_DB->fp_propindex = fp_tmp; |
|---|
| | 415 | progerrno("Couldn't create the array file \"%s\": ", filename); |
|---|
| | 416 | printlong(fp_tmp, DB->unique_ID, sw_fwrite); |
|---|
| | 417 | DB->cur_array_file = estrdup(filename); |
|---|
| | 418 | DB->fp_array = fp_tmp; |
|---|
| | 419 | DB->totwords_array = ARRAY_Create(DB->fp_array); |
|---|
| | 420 | DB->props_array = ARRAY_Create(DB->fp_array); |
|---|
| 370 | | SW_DB->cur_presorted_file = estrdup(filename); |
|---|
| 371 | | printlong(SW_DB->fp_presorted, SW_DB->unique_ID, sw_fwrite); |
|---|
| 372 | | |
|---|
| 373 | | /* Create header File */ |
|---|
| 374 | | strcpy(filename, dbname); |
|---|
| 375 | | strcat(filename, HEADER_EXTENSION); |
|---|
| 376 | | #ifdef USE_TEMPFILE_EXTENSION |
|---|
| 377 | | strcat(filename, USE_TEMPFILE_EXTENSION); |
|---|
| 378 | | SW_DB->tmp_header = 1; |
|---|
| 379 | | #endif |
|---|
| 380 | | CreateEmptyFile(filename); |
|---|
| 381 | | if (!(fp_tmp = openIndexFILEForReadAndWrite(filename))) |
|---|
| 382 | | progerrno("Couldn't create the header file \"%s\": ", filename); |
|---|
| 383 | | printlong(fp_tmp, SW_DB->unique_ID, sw_fwrite); |
|---|
| 384 | | SW_DB->cur_header_file = estrdup(filename); |
|---|
| 385 | | SW_DB->fp_header = fp_tmp; |
|---|
| 386 | | |
|---|
| | 435 | DB->cur_presorted_file = estrdup(filename); |
|---|
| | 436 | printlong(DB->fp_presorted, DB->unique_ID, sw_fwrite); |
|---|
| 401 | | return (void *) SW_DB; |
|---|
| | 461 | |
|---|
| | 462 | for (i = 0; i < MAXCHARS; i++) |
|---|
| | 463 | DB->offsets[i] = (sw_off_t)0; |
|---|
| | 464 | |
|---|
| | 465 | #ifndef USE_BTREE |
|---|
| | 466 | for (i = 0; i < VERYBIGHASHSIZE; i++) |
|---|
| | 467 | DB->hashoffsets[i] = (sw_off_t)0; |
|---|
| | 468 | for (i = 0; i < VERYBIGHASHSIZE; i++) |
|---|
| | 469 | DB->lasthashval[i] = (sw_off_t)0; |
|---|
| | 470 | #endif |
|---|
| | 471 | |
|---|
| | 472 | |
|---|
| | 473 | |
|---|
| | 474 | |
|---|
| | 475 | /* Reserve space for offset pointers */ |
|---|
| | 476 | DB->offsetstart = sw_ftell(DB->fp); |
|---|
| | 477 | for (i = 0; i < MAXCHARS; i++) |
|---|
| | 478 | printfileoffset(DB->fp, (sw_off_t) 0, sw_fwrite); |
|---|
| | 479 | |
|---|
| | 480 | #ifndef USE_BTREE |
|---|
| | 481 | DB->hashstart = sw_ftell(DB->fp); |
|---|
| | 482 | for (i = 0; i < VERYBIGHASHSIZE; i++) |
|---|
| | 483 | printfileoffset(DB->fp, (sw_off_t) 0, sw_fwrite); |
|---|
| | 484 | #endif |
|---|
| | 485 | |
|---|
| | 486 | return (void *) DB; |
|---|
| 460 | | if (!(SW_DB->fp_presorted = openRoutine(s))) |
|---|
| 461 | | { |
|---|
| 462 | | set_progerrno(INDEX_FILE_ERROR, SW_DB->sw, "Couldn't open the presorted index file \"%s\": ", s); |
|---|
| 463 | | return (void *) SW_DB; |
|---|
| 464 | | } |
|---|
| 465 | | |
|---|
| 466 | | SW_DB->cur_presorted_file = s; |
|---|
| 467 | | |
|---|
| 468 | | s = emalloc(strlen(dbname) + strlen(PROPINDEX_EXTENSION) + 1); |
|---|
| 469 | | |
|---|
| 470 | | strcpy(s, dbname); |
|---|
| 471 | | strcat(s, PROPINDEX_EXTENSION); |
|---|
| 472 | | |
|---|
| 473 | | if (!(SW_DB->fp_propindex = openRoutine(s))) |
|---|
| 474 | | { |
|---|
| 475 | | set_progerrno(INDEX_FILE_ERROR, SW_DB->sw, "Couldn't open the propindex index file \"%s\": ", s); |
|---|
| 476 | | return (void *) SW_DB; |
|---|
| 477 | | } |
|---|
| 478 | | |
|---|
| 479 | | SW_DB->cur_propindex_file = s; |
|---|
| 480 | | |
|---|
| 481 | | s = emalloc(strlen(dbname) + strlen(TOTWORDS_EXTENSION) + 1); |
|---|
| 482 | | |
|---|
| 483 | | strcpy(s, dbname); |
|---|
| 484 | | strcat(s, TOTWORDS_EXTENSION); |
|---|
| 485 | | |
|---|
| 486 | | if (!(SW_DB->fp_totwords = openRoutine(s))) |
|---|
| 487 | | { |
|---|
| 488 | | set_progerrno(INDEX_FILE_ERROR, SW_DB->sw, "Couldn't open the totwords index file \"%s\": ", s); |
|---|
| 489 | | return (void *) SW_DB; |
|---|
| 490 | | } |
|---|
| 491 | | |
|---|
| 492 | | SW_DB->cur_totwords_file = s; |
|---|
| 493 | | |
|---|
| 494 | | s = emalloc(strlen(dbname) + strlen(HEADER_EXTENSION) + 1); |
|---|
| 495 | | |
|---|
| 496 | | strcpy(s, dbname); |
|---|
| 497 | | strcat(s, HEADER_EXTENSION); |
|---|
| 498 | | |
|---|
| 499 | | if (!(SW_DB->fp_header = openRoutine(s))) |
|---|
| 500 | | { |
|---|
| 501 | | set_progerrno(INDEX_FILE_ERROR, SW_DB->sw, "Couldn't open the header index file \"%s\": ", s); |
|---|
| 502 | | return (void *) SW_DB; |
|---|
| 503 | | } |
|---|
| 504 | | |
|---|
| 505 | | SW_DB->cur_header_file = s; |
|---|
| | 567 | if (!(DB->fp_presorted = openRoutine(s))) |
|---|
| | 568 | { |
|---|
| | 569 | set_progerrno(INDEX_FILE_ERROR, DB->sw, "Couldn't open the presorted index file \"%s\": ", s); |
|---|
| | 570 | efree(s); |
|---|
| | 571 | return (void *) DB; |
|---|
| | 572 | } |
|---|
| | 573 | |
|---|
| | 574 | |
|---|
| | 575 | DB->cur_presorted_file = s; |
|---|
| | 576 | |
|---|
| | 577 | |
|---|
| 516 | | SW_DB->db_hashfile = OpenBerkeleyFile(s, DB_HASH, db_flags, 0); |
|---|
| 517 | | SW_DB->cur_hashfile_file = s; |
|---|
| | 600 | |
|---|
| | 601 | if (!(fp_tmp = openRoutine(s))) |
|---|
| | 602 | { |
|---|
| | 603 | set_progerrno(INDEX_FILE_ERROR, DB->sw, "Couldn't open the hashfile file \"%s\": ", s); |
|---|
| | 604 | efree(s); |
|---|
| | 605 | return (void *) DB; |
|---|
| | 606 | } |
|---|
| | 607 | |
|---|
| | 608 | |
|---|
| | 609 | DB->fp_hashfile = fp_tmp; |
|---|
| | 610 | DB->cur_hashfile_file = s; |
|---|
| | 611 | |
|---|
| | 612 | |
|---|
| | 613 | s = emalloc(strlen(dbname) + strlen(ARRAY_EXTENSION) + 1); |
|---|
| | 614 | |
|---|
| | 615 | strcpy(s, dbname); |
|---|
| | 616 | strcat(s, ARRAY_EXTENSION); |
|---|
| | 617 | |
|---|
| | 618 | if (!(fp_tmp = openRoutine(s))) |
|---|
| | 619 | { |
|---|
| | 620 | set_progerrno(INDEX_FILE_ERROR, DB->sw, "Couldn't open the array file \"%s\": ", s); |
|---|
| | 621 | efree(s); |
|---|
| | 622 | return (void *) DB; |
|---|
| | 623 | } |
|---|
| | 624 | |
|---|
| | 625 | DB->fp_array = fp_tmp; |
|---|
| | 626 | DB->cur_array_file = s; |
|---|
| | 627 | |
|---|
| | 628 | #endif |
|---|
| 520 | | _DB_CheckHeader(SW_DB); |
|---|
| 521 | | if ( SW_DB->sw->lasterror ) |
|---|
| 522 | | return (void *) SW_DB; |
|---|
| 523 | | |
|---|
| 524 | | /* Put the file pointer of props, propindex and totwords files |
|---|
| 525 | | ** at the end of the files |
|---|
| | 631 | DB_CheckHeader(DB); |
|---|
| | 632 | if ( DB->sw->lasterror ) |
|---|
| | 633 | return (void *) DB; |
|---|
| | 634 | |
|---|
| | 635 | /* Read offsets lookuptable */ |
|---|
| | 636 | DB->offsetstart = sw_ftell(DB->fp); |
|---|
| | 637 | for (i = 0; i < MAXCHARS; i++) |
|---|
| | 638 | DB->offsets[i] = readfileoffset(DB->fp, sw_fread); |
|---|
| | 639 | |
|---|
| | 640 | #ifndef USE_BTREE |
|---|
| | 641 | /* Read hashoffsets lookuptable */ |
|---|
| | 642 | DB->hashstart = sw_ftell(DB->fp); |
|---|
| | 643 | for (i = 0; i < VERYBIGHASHSIZE; i++) |
|---|
| | 644 | DB->hashoffsets[i] = readfileoffset(DB->fp, sw_fread); |
|---|
| | 645 | #else |
|---|
| | 646 | DB->bt = BTREE_Open(DB->fp_btree,4096,DB->offsets[WORDPOS]); |
|---|
| | 647 | DB->worddata = WORDDATA_Open(DB->fp_worddata); |
|---|
| | 648 | DB->hashfile = FHASH_Open(DB->fp_hashfile,DB->offsets[FILEHASHPOS]); |
|---|
| | 649 | DB->totwords_array = ARRAY_Open(DB->fp_array,DB->offsets[TOTALWORDSPERFILEPOS]); |
|---|
| | 650 | DB->props_array = ARRAY_Open(DB->fp_array,DB->offsets[FILEOFFSETPOS]); |
|---|
| | 651 | |
|---|
| | 652 | /* Put the file pointer of props file at the end of the file |
|---|
| 609 | | CloseBerkeleyFile(&SW_DB->db_btree, &SW_DB->cur_btree_file, &SW_DB->tmp_btree); |
|---|
| 610 | | |
|---|
| 611 | | /* Close (and rename) propindex file, if it's open */ |
|---|
| 612 | | if(SW_DB->fp_propindex) |
|---|
| 613 | | { |
|---|
| 614 | | /* Close (and rename) property file, if it's open */ |
|---|
| 615 | | _DB_Close_File(&SW_DB->fp_propindex, &SW_DB->cur_propindex_file, &SW_DB->tmp_propindex); |
|---|
| 616 | | } |
|---|
| 617 | | /* Close (and rename) totwords file, if it's open */ |
|---|
| 618 | | if(SW_DB->fp_totwords) |
|---|
| 619 | | { |
|---|
| 620 | | /* Close (and rename) totwords file, if it's open */ |
|---|
| 621 | | _DB_Close_File(&SW_DB->fp_totwords, &SW_DB->cur_totwords_file, &SW_DB->tmp_totwords); |
|---|
| 622 | | } |
|---|
| | 755 | if(DB->bt) |
|---|
| | 756 | { |
|---|
| | 757 | DB->offsets[WORDPOS] = BTREE_Close(DB->bt); |
|---|
| | 758 | DB_Close_File_Native(&DB->fp_btree, &DB->cur_btree_file, &DB->tmp_btree); |
|---|
| | 759 | DB->bt = NULL; |
|---|
| | 760 | } |
|---|
| | 761 | |
|---|
| 624 | | if(SW_DB->fp_presorted) |
|---|
| 625 | | { |
|---|
| 626 | | _DB_Close_File(&SW_DB->fp_presorted, &SW_DB->cur_presorted_file, &SW_DB->tmp_presorted); |
|---|
| 627 | | } |
|---|
| 628 | | /* Close (and rename) header index file, if it's open */ |
|---|
| 629 | | if(SW_DB->fp_header) |
|---|
| 630 | | { |
|---|
| 631 | | _DB_Close_File(&SW_DB->fp_header, &SW_DB->cur_header_file, &SW_DB->tmp_header); |
|---|
| 632 | | } |
|---|
| | 763 | if(DB->fp_presorted) |
|---|
| | 764 | { |
|---|
| | 765 | DB_Close_File_Native(&DB->fp_presorted, &DB->cur_presorted_file, &DB->tmp_presorted); |
|---|
| | 766 | } |
|---|
| | 767 | if(DB->presorted_array) |
|---|
| | 768 | { |
|---|
| | 769 | for(i = 0; i < DB->n_presorted_array; i++) |
|---|
| | 770 | { |
|---|
| | 771 | if(DB->presorted_array[i]) |
|---|
| | 772 | ARRAY_Close(DB->presorted_array[i]); |
|---|
| | 773 | DB->presorted_array[i] = NULL; |
|---|
| | 774 | } |
|---|
| | 775 | efree(DB->presorted_array); |
|---|
| | 776 | } |
|---|
| | 777 | if(DB->presorted_root_node) |
|---|
| | 778 | efree(DB->presorted_root_node); |
|---|
| | 779 | if(DB->presorted_propid) |
|---|
| | 780 | efree(DB->presorted_propid); |
|---|
| 635 | | CloseBerkeleyFile(&SW_DB->db_hashfile, &SW_DB->cur_hashfile_file, &SW_DB->tmp_hashfile); |
|---|
| 636 | | |
|---|
| 637 | | if (SW_DB->dbname) |
|---|
| 638 | | efree(SW_DB->dbname); |
|---|
| 639 | | efree(SW_DB); |
|---|
| 640 | | } |
|---|
| 641 | | |
|---|
| 642 | | void _DB_Remove(void *db) |
|---|
| 643 | | { |
|---|
| 644 | | struct Handle_DBNative *SW_DB = (struct Handle_DBNative *) db; |
|---|
| | 783 | if(DB->fp_hashfile) |
|---|
| | 784 | { |
|---|
| | 785 | DB->offsets[FILEHASHPOS] = FHASH_Close(DB->hashfile); |
|---|
| | 786 | DB->hashfile = NULL; |
|---|
| | 787 | DB_Close_File_Native(&DB->fp_hashfile, &DB->cur_hashfile_file, &DB->tmp_hashfile); |
|---|
| | 788 | } |
|---|
| | 789 | #endif |
|---|
| | 790 | |
|---|
| | 791 | if (DB->mode == DB_CREATE || DB->mode == DB_READWRITE) /* If we are indexing update offsets to words and files */ |
|---|
| | 792 | { |
|---|
| | 793 | /* Update internal pointers */ |
|---|
| | 794 | |
|---|
| | 795 | sw_fseek(fp, DB->offsetstart, SEEK_SET); |
|---|
| | 796 | for (i = 0; i < MAXCHARS; i++) |
|---|
| | 797 | printfileoffset(fp, DB->offsets[i], sw_fwrite); |
|---|
| | 798 | |
|---|
| | 799 | #ifndef USE_BTREE |
|---|
| | 800 | sw_fseek(fp, DB->hashstart, SEEK_SET); |
|---|
| | 801 | for (i = 0; i < VERYBIGHASHSIZE; i++) |
|---|
| | 802 | printfileoffset(fp, DB->hashoffsets[i], sw_fwrite); |
|---|
| | 803 | #endif |
|---|
| | 804 | } |
|---|
| | 805 | |
|---|
| | 806 | /* Close (and rename) the index file */ |
|---|
| | 807 | DB_Close_File_Native(&DB->fp, &DB->cur_index_file, &DB->tmp_index); |
|---|
| | 808 | |
|---|
| | 809 | |
|---|
| | 810 | if (DB->dbname) |
|---|
| | 811 | efree(DB->dbname); |
|---|
| | 812 | efree(DB); |
|---|
| | 813 | } |
|---|
| | 814 | |
|---|
| | 815 | void DB_Remove_Native(void *db) |
|---|
| | 816 | { |
|---|
| | 817 | struct Handle_DBNative *DB = (struct Handle_DBNative *) db; |
|---|
| 664 | | int _DB_InitWriteHeader(void *db) |
|---|
| 665 | | { |
|---|
| 666 | | struct Handle_DBNative *SW_DB = (struct Handle_DBNative *) db; |
|---|
| 667 | | long swish_magic; |
|---|
| 668 | | |
|---|
| 669 | | /* Jump over swish_magic ID (long number) */ |
|---|
| 670 | | sw_fseek(SW_DB->fp_header, (sw_off_t)0, SEEK_SET); |
|---|
| 671 | | swish_magic = readlong(SW_DB->fp_header, sw_fread); |
|---|
| 672 | | |
|---|
| 673 | | return 0; |
|---|
| 674 | | } |
|---|
| 675 | | |
|---|
| 676 | | |
|---|
| 677 | | int _DB_EndWriteHeader(void *db) |
|---|
| 678 | | { |
|---|
| 679 | | struct Handle_DBNative *SW_DB = (struct Handle_DBNative *) db; |
|---|
| 680 | | FILE *fp = SW_DB->fp_header; |
|---|
| | 835 | int DB_InitWriteHeader_Native(void *db) |
|---|
| | 836 | { |
|---|
| | 837 | struct Handle_DBNative *DB = (struct Handle_DBNative *) db; |
|---|
| | 838 | |
|---|
| | 839 | if(DB->offsets[HEADERPOS]) |
|---|
| | 840 | { |
|---|
| | 841 | /* If DB->offsets[HEADERPOS] is not 0 we are in update mode |
|---|
| | 842 | ** So, put the pointer file in the header start position to overwrite |
|---|
| | 843 | ** the header |
|---|
| | 844 | */ |
|---|
| | 845 | sw_fseek(DB->fp,DB->offsets[HEADERPOS],SEEK_SET); |
|---|
| | 846 | } |
|---|
| | 847 | else |
|---|
| | 848 | { |
|---|
| | 849 | /* The index file is being created. So put the header in the |
|---|
| | 850 | ** current file position (coincides with the end of the file |
|---|
| | 851 | */ |
|---|
| | 852 | DB->offsets[HEADERPOS] = sw_ftell(DB->fp); |
|---|
| | 853 | } |
|---|
| | 854 | return 0; |
|---|
| | 855 | } |
|---|
| | 856 | |
|---|
| | 857 | |
|---|
| | 858 | int DB_EndWriteHeader_Native(void *db) |
|---|
| | 859 | { |
|---|
| | 860 | struct Handle_DBNative *DB = (struct Handle_DBNative *) db; |
|---|
| | 861 | FILE *fp = DB->fp; |
|---|