int get_cnid(DBD *dbd, struct cnid_dbd_rply *rply)
{
static cnid_t id;
+ static char buf[ROOTINFO_DATALEN];
DBT rootinfo_key, rootinfo_data;
int rc;
cnid_t hint;
-
- if (id == 0) {
- memset(&rootinfo_key, 0, sizeof(rootinfo_key));
- memset(&rootinfo_data, 0, sizeof(rootinfo_data));
- rootinfo_key.data = ROOTINFO_KEY;
- rootinfo_key.size = ROOTINFO_KEYLEN;
- if ((rc = dbif_get(dbd, DBIF_CNID, &rootinfo_key, &rootinfo_data, 0)) <= 0) {
+ memset(&rootinfo_key, 0, sizeof(rootinfo_key));
+ memset(&rootinfo_data, 0, sizeof(rootinfo_data));
+ rootinfo_key.data = ROOTINFO_KEY;
+ rootinfo_key.size = ROOTINFO_KEYLEN;
+
+ if (id == 0) {
+ if ((rc = dbif_get(dbd, DBIF_CNID, &rootinfo_key, &rootinfo_data, 0)) < 0) {
rply->result = CNID_DBD_RES_ERR_DB;
return -1;
}
- memcpy(&hint, (char *)rootinfo_data.data +CNID_TYPE_OFS, sizeof(hint));
- id = ntohl(hint);
+ if (rc == 0) {
+ /* no rootinfo key yet */
+ memcpy(buf, ROOTINFO_DATA, ROOTINFO_DATALEN);
+ id = CNID_START - 1;
+ } else {
+ memcpy(buf, (char *)rootinfo_data.data, ROOTINFO_DATALEN);
+ memcpy(&hint, buf + CNID_TYPE_OFS, sizeof(hint));
+ id = ntohl(hint);
+ if (id < CNID_START - 1)
+ id = CNID_START - 1;
+ }
}
/* If we've hit the max CNID allowed, we return an error. CNID
return -1;
}
+ rootinfo_data.data = buf;
rootinfo_data.size = ROOTINFO_DATALEN;
hint = htonl(id);
- memcpy((char *)rootinfo_data.data + CNID_TYPE_OFS, &hint, sizeof(hint));
+ memcpy(buf + CNID_TYPE_OFS, &hint, sizeof(hint));
if (dbif_put(dbd, DBIF_CNID, &rootinfo_key, &rootinfo_data, 0) < 0) {
rply->result = CNID_DBD_RES_ERR_DB;
if (reindex)
LOG(log_info, logtype_cnid, "Reindexing name index...");
+ int version = dbif_getversion(dbd);
+ if (version == -1)
+ return -1;
if ((ret = dbd->db_table[0].db->associate(dbd->db_table[0].db,
dbd->db_txn,
dbd->db_table[DBIF_IDX_NAME].db,
idxname,
(reindex
||
- ((CNID_VERSION == CNID_VERSION_1) && (dbif_getversion(dbd) == CNID_VERSION_0)))
+ ((CNID_VERSION == CNID_VERSION_1) && (version == CNID_VERSION_0)))
? DB_CREATE : 0)) != 0) {
LOG(log_error, logtype_cnid, "Failed to associate name index: %s", db_strerror(ret));
return -1;
}
/*!
- * Return CNID database version number
+ * Initialize or return CNID database version number
* @returns -1 on error, version number otherwise
*/
int dbif_getversion(DBD *dbd)
key.size = ROOTINFO_KEYLEN;
switch (dbif_get(dbd, DBIF_CNID, &key, &data, 0)) {
- case 1:
+ case 1: /* found */
memcpy(&version, (char *)data.data + CNID_DID_OFS, sizeof(version));
version = ntohl(version);
LOG(log_debug, logtype_cnid, "CNID database version %u", version);
ret = version;
break;
- default:
- ret = -1;
+ case 0: /* not found */
+ if (dbif_setversion(dbd, CNID_VERSION) != 0)
+ return -1;
+ ret = CNID_VERSION;
break;
+ default:
+ return -1;
}
return ret;
}
*/
int dbif_setversion(DBD *dbd, int version)
{
+ int ret;
DBT key, data;
uint32_t v;
+ char buf[ROOTINFO_DATALEN];
+
+ LOG(log_debug, logtype_cnid, "Setting CNID database version to %u", version);
v = version;
v = htonl(v);
key.data = ROOTINFO_KEY;
key.size = ROOTINFO_KEYLEN;
- switch (dbif_get(dbd, DBIF_CNID, &key, &data, 0)) {
- case 1:
- break;
- default:
+ if ((ret = dbif_get(dbd, DBIF_CNID, &key, &data, 0)) == -1)
return -1;
+ if (ret == 0) {
+ memcpy(buf, ROOTINFO_DATA, ROOTINFO_DATALEN);
+ data.data = buf;
}
-
memcpy((char *)data.data + CNID_DID_OFS, &v, sizeof(v));
data.size = ROOTINFO_DATALEN;
if (dbif_put(dbd, DBIF_CNID, &key, &data, 0) < 0)
/*
-
- * $Id: cnid_cdb_open.c,v 1.5 2010-03-31 09:47:32 franklahm Exp $
- *
* Copyright (c) 1999. Adrian Sun (asun@zoology.washington.edu)
* All Rights Reserved. See COPYRIGHT.
*
#endif /* HAVE_CONFIG_H */
#ifdef CNID_BACKEND_CDB
+
+#include <atalk/cnid_private.h>
#include "cnid_cdb_private.h"
#ifndef MIN
#define DBHOMELEN 8
#define DBLEN 10
-/* we version the did/name database so that we can change the format
- * if necessary. the key is in the form of a did/name pair. in this case,
- * we use 0/0. */
-#define DBVERSION_KEY "\0\0\0\0\0"
-#define DBVERSION_KEYLEN 5
-#define DBVERSION1 0x00000001U
-#define DBVERSION DBVERSION1
-
#define DBOPTIONS (DB_CREATE | DB_INIT_CDB | DB_INIT_MPOOL)
#define MAXITER 0xFFFF /* maximum number of simultaneously open CNID
goto fail_appinit;
}
-#if 0
- DBT key, pkey, data;
/* ---------------------- */
- /* Check for version. This way we can update the database if we need
- * to change the format in any way. */
- memset(&key, 0, sizeof(key));
- memset(&pkey, 0, sizeof(DBT));
- memset(&data, 0, sizeof(data));
- key.data = DBVERSION_KEY;
- key.size = DBVERSION_KEYLEN;
+ /* Check for version. "cdb" only supports CNID_VERSION_0, cf cnid_private.h */
- if ((rc = db->db_didname->pget(db->db_didname, NULL, &key, &pkey, &data, 0)) != 0) {
- int ret;
- {
- u_int32_t version = htonl(DBVERSION);
+ DBT key, data;
+ uint32_t version;
- data.data = &version;
- data.size = sizeof(version);
- }
- if ((ret = db->db_didname->put(db->db_cnid, NULL, &key, &data,
- DB_NOOVERWRITE))) {
- LOG(log_error, logtype_default, "cnid_open: Error putting new version: %s",
- db_strerror(ret));
- db->db_didname->close(db->db_didname, 0);
+ memset(&key, 0, sizeof(key));
+ memset(&data, 0, sizeof(data));
+ key.data = ROOTINFO_KEY;
+ key.size = ROOTINFO_KEYLEN;
+
+ if ((rc = db->db_cnid->get(db->db_cnid, NULL, &key, &data, 0)) == 0) {
+ /* If not found, ignore it */
+ memcpy(&version, data.data + CNID_DID_OFS, sizeof(version));
+ version = ntohl(version);
+ LOG(log_debug, logtype_default, "CNID db version %u", version);
+ if (version != CNID_VERSION_0) {
+ LOG(log_error, logtype_default, "Unsupported CNID db version %u, use CNID backend \"dbd\"", version);
goto fail_appinit;
}
}
-#endif
-
- /* TODO In the future we might check for version number here. */
-#if 0
- memcpy(&version, data.data, sizeof(version));
- if (version != ntohl(DBVERSION)) {
- /* Do stuff here. */
- }
-#endif /* 0 */
db_env_set_func_yield(my_yield);
return cdb;