mas01cr@239: #include "audioDB.h" mas01cr@239: mas01cr@239: /* Make a new database. mas01cr@239: mas01mc@316: IF size(featuredata) < O2_LARGE_ADB_SIZE mas01cr@239: The database consists of: mas01cr@239: mas01cr@239: * a header (see dbTableHeader struct definition); mas01cr@239: * keyTable: list of keys of tracks; mas01cr@239: * trackTable: Maps implicit feature index to a feature vector mas01cr@239: matrix (sizes of tracks) mas01cr@239: * featureTable: Lots of doubles; mas01cr@239: * timesTable: (start,end) time points for each feature vector; mas01cr@239: * powerTable: associated power for each feature vector; mas01cr@239: * l2normTable: squared l2norms for each feature vector. mas01mc@316: mas01mc@316: ELSE the database consists of: mas01mc@316: mas01mc@316: * a header (see dbTableHeader struct definition); mas01mc@316: * keyTable: list of keys of tracks mas01mc@316: * trackTable: sizes of tracks mas01mc@316: * featureTable: list of feature file names mas01mc@316: * timesTable: list of times file names mas01mc@316: * powerTable: list of power file names mas01mc@316: mas01cr@239: */ mas01cr@239: mas01cr@239: void audioDB::create(const char* dbName){ mas01cr@239: if ((dbfid = open (dbName, O_RDWR|O_CREAT|O_EXCL, S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP|S_IROTH|S_IWOTH)) < 0) mas01cr@239: error("Can't create database file", dbName, "open"); mas01cr@239: get_lock(dbfid, 1); mas01cr@239: mas01cr@239: VERB_LOG(0, "header size: %ju\n", (intmax_t) O2_HEADERSIZE); mas01cr@239: mas01cr@239: dbH = new dbTableHeaderT(); mas01cr@239: assert(dbH); mas01cr@239: mas01cr@256: //unsigned int maxfiles = (unsigned int) rint((double) O2_MAXFILES * (double) size / (double) O2_DEFAULTDBSIZE); mas01cr@239: mas01cr@239: // Initialize header mas01cr@239: dbH->magic = O2_MAGIC; mas01cr@239: dbH->version = O2_FORMAT_VERSION; mas01cr@239: dbH->numFiles = 0; mas01cr@239: dbH->dim = 0; mas01cr@239: dbH->flags = 0; mas01cr@239: dbH->headerSize = O2_HEADERSIZE; mas01cr@239: dbH->length = 0; mas01cr@239: dbH->fileTableOffset = ALIGN_PAGE_UP(O2_HEADERSIZE); mas01cr@256: dbH->trackTableOffset = ALIGN_PAGE_UP(dbH->fileTableOffset + O2_FILETABLE_ENTRY_SIZE*ntracks); mas01cr@256: dbH->dataOffset = ALIGN_PAGE_UP(dbH->trackTableOffset + O2_TRACKTABLE_ENTRY_SIZE*ntracks); mas01cr@256: mas01cr@256: off_t databytes = ((off_t) datasize) * 1024 * 1024; mas01cr@256: off_t auxbytes = databytes / datadim; mas01cr@256: mas01mc@319: // For backward-compatibility, Record the point-encoding parameter for LSH indexing in the adb header mas01mc@319: // If this value is 0 then it will be set to 14 mas01mc@319: mas01mc@319: #if O2_LSH_N_POINT_BITS > 15 mas01mc@319: #error "AudioDB Compile ERROR: consistency check of O2_LSH_POINT_BITS failed (>15)" mas01mc@319: #endif mas01mc@319: mas01mc@319: dbH->flags |= LSH_N_POINT_BITS << 28; mas01mc@319: mas01mc@316: // If database will fit in a single file the vectors are copied into the AudioDB instance mas01mc@316: // Else all the vectors are left on the FileSystem and we use the dataOffset as storage mas01mc@316: // for the location of the features, powers and times files (assuming that arbitrary keys are used for the fileTable) mas01mc@320: if(ntrackstimesTableOffset = ALIGN_PAGE_UP(dbH->dataOffset + databytes); mas01mc@316: dbH->powerTableOffset = ALIGN_PAGE_UP(dbH->timesTableOffset + 2*auxbytes); mas01mc@316: dbH->l2normTableOffset = ALIGN_PAGE_UP(dbH->powerTableOffset + auxbytes); mas01mc@316: dbH->dbSize = ALIGN_PAGE_UP(dbH->l2normTableOffset + auxbytes); mas01mc@316: } mas01mc@320: else{ // Create LARGE_ADB, features and powers kept on filesystem mas01mc@316: dbH->flags |= O2_FLAG_LARGE_ADB; mas01mc@316: dbH->timesTableOffset = ALIGN_PAGE_UP(dbH->dataOffset + O2_FILETABLE_ENTRY_SIZE*ntracks); mas01mc@316: dbH->powerTableOffset = ALIGN_PAGE_UP(dbH->timesTableOffset + O2_FILETABLE_ENTRY_SIZE*ntracks); mas01mc@316: dbH->l2normTableOffset = ALIGN_PAGE_UP(dbH->powerTableOffset + O2_FILETABLE_ENTRY_SIZE*ntracks); mas01mc@316: dbH->dbSize = dbH->l2normTableOffset; mas01mc@316: } mas01cr@239: mas01cr@239: write(dbfid, dbH, O2_HEADERSIZE); mas01cr@239: mas01cr@239: // go to the location corresponding to the last byte mas01cr@256: if (lseek (dbfid, dbH->dbSize - 1, SEEK_SET) == -1) mas01cr@239: error("lseek error in db file", "", "lseek"); mas01cr@239: mas01cr@239: // write a dummy byte at the last location mas01cr@239: if (write (dbfid, "", 1) != 1) mas01cr@239: error("write error", "", "write"); mas01cr@239: mas01cr@239: VERB_LOG(0, "%s %s\n", COM_CREATE, dbName); mas01cr@239: } mas01cr@239: