in hfs/btree.c [1043:1121]
static int doAddRecord(BTree* tree, uint32_t root, BTKey* searchKey, size_t length, unsigned char* content) {
BTNodeDescriptor* descriptor;
BTKey* key;
off_t recordOffset;
off_t recordDataOffset;
off_t lastRecordDataOffset;
uint16_t offset;
int res;
int i;
descriptor = readBTNodeDescriptor(root, tree);
if(descriptor == NULL)
return FALSE;
lastRecordDataOffset = 0;
for(i = 0; i < descriptor->numRecords; i++) {
recordOffset = getRecordOffset(i, root, tree);
key = READ_KEY(tree, recordOffset, tree->io);
recordDataOffset = recordOffset + key->keyLength + sizeof(key->keyLength);
res = COMPARE(tree, key, searchKey);
if(res == 0) {
free(key);
free(descriptor);
return FALSE;
} else if(res > 0) {
free(key);
break;
}
free(key);
lastRecordDataOffset = recordDataOffset;
}
if(i != descriptor->numRecords) {
// first, move everyone else down
moveRecordsDown(tree, descriptor, i, root, sizeof(searchKey->keyLength) + searchKey->keyLength + length, 1);
// then insert ourself
ASSERT(WRITE_KEY(tree, recordOffset, searchKey, tree->io), "WRITE_KEY");
ASSERT(WRITE(tree->io, recordOffset + sizeof(searchKey->keyLength) + searchKey->keyLength, length, content), "WRITE");
offset = recordOffset - (root * tree->headerRec->nodeSize);
FLIPENDIAN(offset);
ASSERT(WRITE(tree->io, (root * tree->headerRec->nodeSize) + tree->headerRec->nodeSize - (sizeof(uint16_t) * (i + 1)),
sizeof(uint16_t), &offset), "WRITE");
} else {
// just insert ourself at the end
recordOffset = getRecordOffset(i, root, tree);
ASSERT(WRITE_KEY(tree, recordOffset, searchKey, tree->io), "WRITE_KEY");
ASSERT(WRITE(tree->io, recordOffset + sizeof(uint16_t) + searchKey->keyLength, length, content), "WRITE");
// write the new free offset
offset = (recordOffset + sizeof(searchKey->keyLength) + searchKey->keyLength + length) - (root * tree->headerRec->nodeSize);
FLIPENDIAN(offset);
ASSERT(WRITE(tree->io, (root * tree->headerRec->nodeSize) + tree->headerRec->nodeSize - (sizeof(uint16_t) * (descriptor->numRecords + 2)),
sizeof(uint16_t), &offset), "WRITE");
}
descriptor->numRecords++;
if(descriptor->height == 1) {
tree->headerRec->leafRecords++;
}
ASSERT(writeBTNodeDescriptor(descriptor, root, tree), "writeBTNodeDescriptor");
ASSERT(writeBTHeaderRec(tree), "writeBTHeaderRec");
free(descriptor);
return TRUE;
}