本文整理汇总了C++中DB_ENV::err方法的典型用法代码示例。如果您正苦于以下问题:C++ DB_ENV::err方法的具体用法?C++ DB_ENV::err怎么用?C++ DB_ENV::err使用的例子?那么, 这里精选的方法代码示例或许可以为您提供帮助。您也可以进一步了解该方法所在类DB_ENV
的用法示例。
在下文中一共展示了DB_ENV::err方法的15个代码示例,这些例子默认根据受欢迎程度排序。您可以为喜欢或者感觉有用的代码点赞,您的评价将有助于系统推荐出更棒的C++代码示例。
示例1:
void *
logfile_thread(void *arg)
{
DB_ENV *dbenv;
int ret;
char **begin, **list;
dbenv = arg;
dbenv->errx(dbenv,
"Log file removal thread: %lu", (u_long)pthread_self());
/* Check once every 5 minutes. */
for (;; sleep(300)) {
/* Get the list of log files. */
if ((ret =
dbenv->log_archive(dbenv, &list, DB_ARCH_ABS)) != 0) {
dbenv->err(dbenv, ret, "DB_ENV->log_archive");
exit (1);
}
/* Remove the log files. */
if (list != NULL) {
for (begin = list; *list != NULL; ++list)
if ((ret = remove(*list)) != 0) {
dbenv->err(dbenv,
ret, "remove %s", *list);
exit (1);
}
free (begin);
}
}
/* NOTREACHED */
}
示例2: bdblib_create_dbenv
int bdblib_create_dbenv(DB_ENV **_dbenv, char* _home)
{
DB_ENV *env;
char *progname;
int rc, flags;
progname = "kamailio";
/* Create an environment and initialize it for additional error * reporting. */
if ((rc = db_env_create(&env, 0)) != 0)
{
ERR("db_env_create failed! bdb error: %s.\n", db_strerror(rc));
return (rc);
}
env->set_errpfx(env, progname);
/* Specify the shared memory buffer pool cachesize */
if ((rc = env->set_cachesize(env, 0, _bdb_parms->cache_size, 0)) != 0)
{
ERR("dbenv set_cachsize failed! bdb error: %s.\n", db_strerror(rc));
env->err(env, rc, "set_cachesize");
goto err;
}
/* Concurrent Data Store flags */
flags = DB_CREATE |
DB_INIT_CDB |
DB_INIT_MPOOL |
DB_THREAD;
/* Transaction Data Store flags ; not supported yet */
/*
flags = DB_CREATE |
DB_RECOVER |
DB_INIT_LOG |
DB_INIT_LOCK |
DB_INIT_MPOOL |
DB_THREAD |
DB_INIT_TXN;
*/
/* Open the environment */
if ((rc = env->open(env, _home, flags, 0)) != 0)
{
ERR("dbenv is not initialized! bdb error: %s.\n",db_strerror(rc));
env->err(env, rc, "environment open: %s", _home);
goto err;
}
*_dbenv = env;
return (0);
err: (void)env->close(env, 0);
return (rc);
}
示例3: initialize_db
db* initialize_db(const char* db_name, uint32_t flag){
db* db_ptr = NULL;
DB* b_db;
DB_ENV* dbenv;
int ret;
char* full_path = NULL;
if((ret = mkdir(db_dir,S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH)) != 0){
if(errno!=EEXIST){
err_log("DB : Dir Creation Failed\n");
goto db_init_return;
}
}
full_path = (char*)malloc(strlen(db_dir) + strlen(db_name) + 2);
mk_path(full_path, db_dir, db_name);
#ifdef ENV
if ((ret = db_env_create(&dbenv, 0)) != 0) {
dbenv->err(dbenv, ret, "Environment Created: %s", db_dir);
goto db_init_return;
}
if ((ret = dbenv->open(dbenv, db_dir, DB_CREATE|DB_INIT_CDB|DB_INIT_MPOOL|DB_THREAD, 0)) != 0) {
//dbenv->err(dbenv, ret, "Environment Open: %s", db_dir);
goto db_init_return;
}
/* Initialize the DB handle */
if((ret = db_create(&b_db,dbenv,flag)) != 0){
err_log("DB : %s.\n", db_strerror(ret));
goto db_init_return;
}
#else
/* Initialize the DB handle */
if((ret = db_create(&b_db,NULL,flag)) != 0){
err_log("DB : %s.\n", db_strerror(ret));
goto db_init_return;
}
#endif
if((ret = b_db->set_pagesize(b_db, pagesize)) != 0){
err_log("DB : %s.\n", db_strerror(ret));
goto db_init_return;
}
if((ret = b_db->open(b_db, NULL, db_name, NULL, DB_BTREE, DB_THREAD|DB_CREATE,0)) != 0){ // db_name is the on-disk file that holds the database
//b_db->err(b_db,ret,"%s","test.db");
goto db_init_return;
}
db_ptr = (db*)(malloc(sizeof(db)));
db_ptr->bdb_ptr = b_db;
db_init_return:
if(full_path != NULL){
free(full_path);
}
if(db_ptr != NULL){
;
}
return db_ptr;
}
示例4: return
static void *bdb_checkpoint_thread(void *arg){
DB_ENV *dbenv;
int ret;
dbenv = arg;
for (;; sleep(bdb_settings.checkpoint_val)) {
if ((ret = dbenv->txn_checkpoint(dbenv, 0, 0, 0)) != 0) {
dbenv->err(dbenv, ret, "checkpoint thread");
}
dbenv->errx(dbenv, "checkpoint thread: a txn_checkpoint is done");
}
return (NULL);
}
示例5:
void
env_open(DB_ENV **dbenvp)
{
DB_ENV *dbenv;
int ret;
/* Create the environment handle. */
if ((ret = db_env_create(&dbenv, 0)) != 0) {
fprintf(stderr,
"txnapp: db_env_create: %s\n", db_strerror(ret));
exit (1);
}
/* Set up error handling. */
dbenv->set_errpfx(dbenv, "txnapp");
dbenv->set_errfile(dbenv, stderr);
// match lladd's defaults...
dbenv->set_lg_bsize(dbenv, 1024*1024);
// match lladd's defaults...
dbenv->set_cachesize(dbenv, 0, 8204288, 0);
/* Do deadlock detection internally. */
/* if ((ret = dbenv->set_lk_detect(dbenv, DB_LOCK_DEFAULT)) != 0) {
dbenv->err(dbenv, ret, "set_lk_detect: DB_LOCK_DEFAULT");
exit (1);
}*/
dbenv->set_tx_max(dbenv, 32000);
unsigned int max;
dbenv->get_tx_max(dbenv, &max);
printf("Max xact count: %d\n", max);
/*
* Open a transactional environment:
* create if it doesn't exist
* free-threaded handle
* run recovery
* read/write owner only
*/
if ((ret = dbenv->open(dbenv, ENV_DIRECTORY,
DB_CREATE |/* DB_INIT_LOCK |*/ DB_INIT_LOG | DB_PRIVATE |
DB_INIT_MPOOL | DB_INIT_TXN | DB_RECOVER | DB_THREAD,
S_IRUSR | S_IWUSR)) != 0) {
dbenv->err(dbenv, ret, "dbenv->open: %s", ENV_DIRECTORY);
exit (1);
}
*dbenvp = dbenv;
}
示例6: return
/*
* env_init --
* Initialize the environment.
*/
DB_ENV * env_init( char *home, char *prefix, int cachesize)
{
DB_ENV *dbenv;
int ret;
if ((ret = db_env_create(&dbenv, 0)) != 0) {
dbenv->err(dbenv, ret, "db_env_create");
return (NULL);
}
dbenv->set_errfile(dbenv, stderr);
dbenv->set_errpfx(dbenv, prefix);
if ((ret = dbenv->set_cachesize(dbenv, 0, cachesize, 0)) != 0) {
dbenv->err(dbenv, ret, "DB_ENV->set_cachesize");
return (NULL);
}
if ((ret = dbenv->open(dbenv, home, DB_CREATE | DB_INIT_MPOOL |
DB_INIT_TXN | DB_INIT_LOCK, 0)) != 0) {
dbenv->err(dbenv, ret, "DB_ENV->open: %s", home);
(void)dbenv->close(dbenv, 0);
return (NULL);
}
return (dbenv);
}
示例7: while
int
main(int argc, char *argv[])
{
extern char *optarg;
DB_ENV *dbenv;
const char *home;
char ch;
int ret;
dbenv = NULL;
ret = 0;
home = NULL;
/* Create and configure the environment handle. */
if ((ret = create_env(progname, &dbenv)) != 0)
goto err;
/* Collect the command line options. */
while ((ch = getopt(argc, argv, "h:")) != EOF)
switch (ch) {
case 'h':
home = optarg;
break;
case '?':
default:
usage();
}
/* Error check command line. */
if (home == NULL)
usage();
/* Open the environment. */
if ((ret = env_init(dbenv, home)) != 0)
goto err;
if ((ret = doloop(dbenv)) != 0) {
dbenv->err(dbenv, ret, "Application failed");
goto err;
}
err: if (dbenv != NULL)
(void)dbenv->close(dbenv, 0);
return (ret);
}
示例8: return
static void *bdb_chkpoint_thread(void *arg)
{
DB_ENV *dbenv;
int ret;
dbenv = arg;
if (settings.verbose > 1) {
dbenv->errx(dbenv, "checkpoint thread created: %lu, every %d seconds",
(u_long)pthread_self(), bdb_settings.chkpoint_val);
}
for (;; sleep(bdb_settings.chkpoint_val)) {
if ((ret = dbenv->txn_checkpoint(dbenv, 0, 0, 0)) != 0) {
dbenv->err(dbenv, ret, "checkpoint thread");
}
dbenv->errx(dbenv, "checkpoint thread: a txn_checkpoint is done");
}
return (NULL);
}
示例9: service_list
bool service_list(struct client *cli, const char *user)
{
GList *files = NULL, *content = NULL;
char *s;
enum errcode err = InternalError;
int rc;
bool rcb;
DB_TXN *txn = NULL;
DBC *cur = NULL;
DB_ENV *dbenv = tdbrep.tdb.env;
DB *bidx = tdbrep.tdb.buckets_idx;
DBT skey, pkey, pval;
if (asprintf(&s,
"<?xml version=\"1.0\" encoding=\"UTF-8\"?>\r\n"
"<ListAllMyBucketsResult xmlns=\"http://indy.yyz.us/doc/2006-03-01/\">\r\n"
" <Owner>\r\n"
" <ID>%s</ID>\r\n"
" <DisplayName>%s</DisplayName>\r\n"
" </Owner>\r\n"
" <Buckets>\r\n",
user,
user) < 0)
goto err_out;
content = g_list_append(content, s);
/* open transaction, search cursor */
rc = dbenv->txn_begin(dbenv, NULL, &txn, 0);
if (rc) {
dbenv->err(dbenv, rc, "DB_ENV->txn_begin");
goto err_out_content;
}
rc = bidx->cursor(bidx, txn, &cur, 0);
if (rc) {
bidx->err(bidx, rc, "bidx->cursor");
goto err_out_content;
}
memset(&skey, 0, sizeof(skey));
memset(&pkey, 0, sizeof(pkey));
memset(&pval, 0, sizeof(pval));
skey.data = (char *) user;
skey.size = strlen(user) + 1;
/* FIXME: Use of DB_NEXT rather than DB_SET to begin search
* means we iterate through entire db, rather than
* starting at the first matching key.
*/
/* loop through matching buckets, if any */
while (1) {
char timestr[64];
struct db_bucket_ent *ent;
rc = cur->pget(cur, &skey, &pkey, &pval, DB_NEXT);
if (rc)
break;
ent = pval.data;
s = g_markup_printf_escaped(
" <Bucket>\r\n"
" <Name>%s</Name>\r\n"
" <CreationDate>%s</CreationDate>\r\n"
" </Bucket>\r\n",
ent->name,
hutil_time2str(timestr, sizeof(timestr),
GUINT64_FROM_LE(ent->time_create)));
if (!s)
goto err_out_content;
content = g_list_append(content, s);
}
if (rc != DB_NOTFOUND)
bidx->err(bidx, rc, "service_list iter");
/* close cursor, transaction */
rc = cur->close(cur);
if (rc)
bidx->err(bidx, rc, "bidx->cursor close");
rc = txn->commit(txn, 0);
if (rc)
dbenv->err(dbenv, rc, "DB_ENV->txn_commit");
if (asprintf(&s,
" </Buckets>\r\n"
"</ListAllMyBucketsResult>\r\n") < 0)
goto err_out_content;
content = g_list_append(content, s);
rcb = cli_resp_xml(cli, 200, content);
//.........这里部分代码省略.........
示例10: srand
/*
* A function that performs a series of writes to a
* Berkeley DB database. The information written
* to the database is largely nonsensical, but the
* mechanism of transactional commit/abort and
* deadlock detection is illustrated here.
*/
void *
writer_thread(void *args)
{
static char *key_strings[] = {
"key 1", "key 2", "key 3", "key 4", "key 5",
"key 6", "key 7", "key 8", "key 9", "key 10"
};
DB *dbp;
DB_ENV *envp;
DBT key, value;
DB_TXN *txn;
int i, j, payload, ret, thread_num;
int retry_count, max_retries = 20; /* Max retry on a deadlock */
dbp = (DB *)args;
envp = dbp->get_env(dbp);
/* Get the thread number */
(void)mutex_lock(&thread_num_lock);
global_thread_num++;
thread_num = global_thread_num;
(void)mutex_unlock(&thread_num_lock);
/* Initialize the random number generator */
srand(thread_num);
/* Write 50 times and then quit */
for (i = 0; i < 50; i++) {
retry_count = 0; /* Used for deadlock retries */
/*
* Some think it is bad form to loop with a goto statement, but
* we do it anyway because it is the simplest and clearest way
* to achieve our abort/retry operation.
*/
retry:
/* Begin our transaction. We group multiple writes in
* this thread under a single transaction so as to
* (1) show that you can atomically perform multiple writes
* at a time, and (2) to increase the chances of a
* deadlock occurring so that we can observe our
* deadlock detection at work.
*
* Normally we would want to avoid the potential for deadlocks,
* so for this workload the correct thing would be to perform our
* puts with autocommit. But that would excessively simplify our
* example, so we do the "wrong" thing here instead.
*/
ret = envp->txn_begin(envp, NULL, &txn, 0);
if (ret != 0) {
envp->err(envp, ret, "txn_begin failed");
return ((void *)EXIT_FAILURE);
}
for (j = 0; j < 10; j++) {
/* Set up our key and values DBTs */
memset(&key, 0, sizeof(DBT));
key.data = key_strings[j];
key.size = (u_int32_t)strlen(key_strings[j]) + 1;
memset(&value, 0, sizeof(DBT));
payload = rand() + i;
value.data = &payload;
value.size = sizeof(int);
/* Perform the database put. */
switch (ret = dbp->put(dbp, txn, &key, &value, 0)) {
case 0:
break;
/*
* Here's where we perform deadlock detection. If
* DB_LOCK_DEADLOCK is returned by the put operation,
* then this thread has been chosen to break a deadlock.
* It must abort its operation, and optionally retry the
* put.
*/
case DB_LOCK_DEADLOCK:
/*
* First thing that we MUST do is abort the
* transaction.
*/
(void)txn->abort(txn);
/*
* Now we decide if we want to retry the operation.
* If we have retried less than max_retries,
* increment the retry count and goto retry.
*/
if (retry_count < max_retries) {
printf("Writer %i: Got DB_LOCK_DEADLOCK.\n",
thread_num);
printf("Writer %i: Retrying write operation.\n",
thread_num);
retry_count++;
//.........这里部分代码省略.........
示例11: memset
/* 批量插入示例函数。*/
void *
run_bulk_delete()
{
int raw_key[NUM_KEY_INT];
DBT key;
DB_ENV *envp;
int bulk_size = 100;
DB *dbp;
DB_TXN *tid;
int *delete_load;
int delete_count, i, ret, op_flag;
char *key_buf;
void *p;
int j;
/* Initialize structs and arrays */
memset(raw_key, 0, KEY_SIZE);
memset(&key, 0, sizeof(DBT));
tid = NULL;
/*
* 初始化批量删除使用的key buffer。由于批量删除不需要data,
* 所以只需要初始化和填充key buffer。我们同样需要使用自己分配的内存。
*/
key_buf = (char*) malloc(KEY_SIZE * bulk_size * 2);
memset(key_buf, 0, KEY_SIZE * bulk_size * 2);
/* 初始化key buffer DBT 对象,设置正确的flags和ulen成员。 */
key.data = key_buf;
key.ulen = KEY_SIZE * bulk_size * 2;
key.flags = DB_DBT_USERMEM;
op_flag = DB_MULTIPLE; /* 批量删除同样需要这个flag。*/
/*
* 批量删除所有的数据。每一批删除由key buffer DBT 当中的key
* 指定的bulk_size条key/data pair. 这两个宏的详细用法见上文。
*/
for (i = 0; i < delete_count / bulk_size; ) {
/* 为批量删除初始化并填充一个key buffer DBT 对象。 */
DB_MULTIPLE_WRITE_INIT(p, &key);
for (j = i * bulk_size; j < (i + 1) * bulk_size; j++) {
raw_key[0] = delete_load[j];
DB_MULTIPLE_WRITE_NEXT(p, &key, raw_key, KEY_SIZE);
}
/* 启动事务。*/
if ((ret = envp->txn_begin(envp, NULL, &tid, 0)) != 0) {
envp->err(envp, ret, "[delete] DB_ENV->txn_begin");
exit(EXIT_FAILURE);
}
/*
* 执行批量删除。key buffer DBT
* 当中的bulk_size条key指定的key/data pairs会被从数据库当中删除。
*/
switch(ret = dbp->del(dbp, tid, &key, op_flag)) {
case 0: /* 批量删除操作成功,提交事务。*/
if ((ret = tid->commit(tid, 0)) != 0) {
envp->err(envp, ret, "[delete] DB_TXN->commit");
exit(EXIT_FAILURE);
}
break;
case DB_LOCK_DEADLOCK:
/* 如果数据库操作发生死锁,那么必须abort事务。然后,可以选择重新执行该操作。*/
if ((ret = tid->abort(tid)) != 0) {
envp->err(envp, ret, "[delete] DB_TXN->abort");
exit(EXIT_FAILURE);
}
continue;
default:
envp->err(envp, ret, "[delete] DB->del ([%d]%d)", i, delete_load[i]);
exit(EXIT_FAILURE);
}
i++;
}
(void)free(key_buf);
return (NULL);
}
示例12: nfs_op_lookup
nfsstat4 nfs_op_lookup(struct nfs_cxn *cxn, const LOOKUP4args *args,
struct list_head *writes, struct rpc_write **wr)
{
nfsstat4 status = NFS4_OK;
struct nfs_inode *ino = NULL;
bool printed = false;
struct nfs_buf objname;
nfsino_t inum;
DB_TXN *txn = NULL;
DB_ENV *dbenv = srv.fsdb.env;
int rc;
objname.len = args->objname.utf8string_len;
objname.val = args->objname.utf8string_val;
if (!objname.len) {
status = NFS4ERR_INVAL;
goto out;
}
if (!objname.val) {
status = NFS4ERR_BADXDR;
goto out;
}
if (objname.len > SRV_MAX_NAME) {
status = NFS4ERR_NAMETOOLONG;
goto out;
}
rc = dbenv->txn_begin(dbenv, NULL, &txn, 0);
if (rc) {
status = NFS4ERR_IO;
dbenv->err(dbenv, rc, "DB_ENV->txn_begin");
goto out;
}
status = dir_curfh(txn, cxn, &ino, 0);
if (status != NFS4_OK) {
if ((status == NFS4ERR_NOTDIR) &&
(ino->type == NF4LNK))
status = NFS4ERR_SYMLINK;
goto out_abort;
}
status = dir_lookup(txn, ino, &objname, 0, &inum);
if (status != NFS4_OK)
goto out_abort;
rc = txn->commit(txn, 0);
if (rc) {
dbenv->err(dbenv, rc, "DB_ENV->txn_commit");
status = NFS4ERR_IO;
goto out;
}
fh_set(&cxn->current_fh, inum);
if (debugging) {
applog(LOG_INFO, "op LOOKUP ('%.*s') -> %016llX",
objname.len,
objname.val,
(unsigned long long) cxn->current_fh.inum);
printed = true;
}
out:
if (!printed) {
if (debugging)
applog(LOG_INFO, "op LOOKUP ('%.*s')",
objname.len,
objname.val);
}
WR32(status);
inode_free(ino);
return status;
out_abort:
if (txn->abort(txn))
dbenv->err(dbenv, rc, "DB_ENV->txn_abort");
goto out;
}
示例13: getopt
int
main(int argc, char *const* argv)
{
const char *progname = "dbxml_dump";
DB_ENV *dbenv;
XmlManager *xmlDb;
u_int32_t cache;
int ch, exitval, is_private, keyflag, nflag, ret, Rflag, rflag;
char *home, *passwd;
if ((ret = version_check(progname)) != 0)
return (ret);
dbenv = NULL;
xmlDb = NULL;
exitval = nflag = rflag = Rflag = 0;
keyflag = 0;
cache = MEGABYTE;
is_private = 0;
home = passwd = NULL;
while ((ch = getopt(argc, argv, "f:h:NP:rRV")) != EOF)
switch (ch) {
case 'f':
if (freopen(optarg, "wb", stdout) == NULL) {
fprintf(stderr, "%s: %s: reopen: %s\n",
progname, optarg, strerror(errno));
return (EXIT_FAILURE);
}
break;
case 'h':
home = optarg;
break;
case 'N':
nflag = 1;
break;
case 'P':
passwd = strdup(optarg);
memset(optarg, 0, strlen(optarg));
if (passwd == NULL) {
fprintf(stderr, "%s: strdup: %s\n",
progname, strerror(errno));
return (EXIT_FAILURE);
}
break;
case 'R':
Rflag = 1;
/* DB_AGGRESSIVE requires DB_SALVAGE */
/* FALLTHROUGH */
case 'r':
rflag = 1;
break;
case 'V':
printf("%s\n", DbXml::dbxml_version(NULL, NULL, NULL));
printf("%s\n", db_version(NULL, NULL, NULL));
return (EXIT_SUCCESS);
case '?':
default:
return (usage());
}
argc -= optind;
argv += optind;
if (argc != 1)
return (usage());
/* Handle possible interruptions. */
SigBlock sb;
/*
* Create an environment object and initialize it for error
* reporting.
*/
if ((ret = db_env_create(&dbenv, 0)) != 0) {
fprintf(stderr,
"%s: db_env_create: %s\n", progname, db_strerror(ret));
goto err;
}
dbenv->set_errfile(dbenv, stderr);
dbenv->set_errpfx(dbenv, progname);
if (nflag) {
if ((ret = dbenv->set_flags(dbenv, DB_NOLOCKING, 1)) != 0) {
dbenv->err(dbenv, ret, "set_flags: DB_NOLOCKING");
goto err;
}
if ((ret = dbenv->set_flags(dbenv, DB_NOPANIC, 1)) != 0) {
dbenv->err(dbenv, ret, "set_flags: DB_NOPANIC");
goto err;
}
}
if (passwd != NULL && (ret = dbenv->set_encrypt(dbenv,
passwd, DB_ENCRYPT_AES)) != 0) {
dbenv->err(dbenv, ret, "set_passwd");
goto err;
}
/* Initialize the environment. */
if ((ret = db_init(dbenv, home, rflag, cache, &is_private)) != 0) {
dbenv->err(dbenv, ret, "db_init");
//.........这里部分代码省略.........
示例14: nfs_op_remove
nfsstat4 nfs_op_remove(struct nfs_cxn *cxn, const REMOVE4args *args,
struct list_head *writes, struct rpc_write **wr)
{
nfsstat4 status = NFS4_OK;
struct nfs_inode *dir_ino = NULL, *target_ino = NULL;
struct nfs_buf target;
change_info4 cinfo = { true, 0, 0 };
DB_TXN *txn = NULL;
DB_ENV *dbenv = srv.fsdb.env;
int rc;
nfsino_t de_inum;
target.len = args->target.utf8string_len;
target.val = args->target.utf8string_val;
if (debugging)
applog(LOG_INFO, "op REMOVE ('%.*s')",
target.len,
target.val);
if (target.len > SRV_MAX_NAME) {
status = NFS4ERR_NAMETOOLONG;
goto out;
}
if (!valid_utf8string(&target)) {
status = NFS4ERR_INVAL;
goto out;
}
if (has_dots(&target)) {
status = NFS4ERR_BADNAME;
goto out;
}
rc = dbenv->txn_begin(dbenv, NULL, &txn, 0);
if (rc) {
status = NFS4ERR_IO;
dbenv->err(dbenv, rc, "DB_ENV->txn_begin");
goto out;
}
/* reference container directory */
status = dir_curfh(txn, cxn, &dir_ino, DB_RMW);
if (status != NFS4_OK)
goto out_abort;
/* lookup target name in directory */
status = dir_lookup(txn, dir_ino, &target, 0, &de_inum);
if (status != NFS4_OK)
goto out_abort;
/* reference target inode */
target_ino = inode_getdec(txn, de_inum, DB_RMW);
if (!target_ino) {
status = NFS4ERR_NOENT;
goto out_abort;
}
/* prevent root dir deletion */
if (target_ino->inum == INO_ROOT) {
status = NFS4ERR_INVAL;
goto out_abort;
}
/* prevent removal of non-empty dirs */
if ((target_ino->type == NF4DIR) && !dir_is_empty(txn, target_ino)) {
status = NFS4ERR_NOTEMPTY;
goto out_abort;
}
/* remove target inode from directory */
rc = fsdb_dirent_del(&srv.fsdb, txn, dir_ino->inum, &target, 0);
if (rc) {
status = NFS4ERR_IO;
goto out_abort;
}
/* record directory change info */
cinfo.before = dir_ino->version;
rc = inode_touch(txn, dir_ino);
if (rc) {
status = NFS4ERR_IO;
goto out_abort;
}
cinfo.after = dir_ino->version;
/* remove link, possibly deleting inode */
rc = inode_unlink(txn, target_ino);
if (rc) {
status = NFS4ERR_IO;
goto out_abort;
}
rc = txn->commit(txn, 0);
if (rc) {
dbenv->err(dbenv, rc, "DB_ENV->txn_commit");
status = NFS4ERR_IO;
goto out;
//.........这里部分代码省略.........
示例15: nfs_op_link
nfsstat4 nfs_op_link(struct nfs_cxn *cxn, const LINK4args *args,
struct list_head *writes, struct rpc_write **wr)
{
nfsstat4 status;
struct nfs_inode *dir_ino = NULL, *src_ino = NULL;
struct nfs_buf newname;
uint64_t before = 0, after = 0;
DB_TXN *txn;
DB_ENV *dbenv = srv.fsdb.env;
int rc;
newname.len = args->newname.utf8string_len;
newname.val = args->newname.utf8string_val;
if (debugging)
applog(LOG_INFO, "op LINK (%.*s)",
newname.len,
newname.val);
/* verify input parameters */
if (!valid_fh(cxn->current_fh) || !valid_fh(cxn->save_fh)) {
status = NFS4ERR_NOFILEHANDLE;
goto out;
}
if (newname.len > SRV_MAX_NAME) {
status = NFS4ERR_NAMETOOLONG;
goto out;
}
/* open transaction */
rc = dbenv->txn_begin(dbenv, NULL, &txn, 0);
if (rc) {
status = NFS4ERR_IO;
dbenv->err(dbenv, rc, "DB_ENV->txn_begin");
goto out;
}
/* read source inode's directory inode */
dir_ino = inode_fhdec(txn, cxn->current_fh, 0);
if (!dir_ino) {
status = NFS4ERR_NOFILEHANDLE;
goto out_abort;
}
/* make sure target is a directory */
if (dir_ino->type != NF4DIR) {
status = NFS4ERR_NOTDIR;
goto out_abort;
}
/* read source inode */
src_ino = inode_fhdec(txn, cxn->save_fh, 0);
if (!src_ino) {
status = NFS4ERR_NOFILEHANDLE;
goto out_abort;
}
/* make sure source is a not a directory */
if (src_ino->type == NF4DIR) {
status = NFS4ERR_ISDIR;
goto out_abort;
}
before = dir_ino->version;
/* add directory entry */
status = dir_add(txn, dir_ino, &newname, src_ino);
if (status != NFS4_OK)
goto out_abort;
after = dir_ino->version;
/* update source inode */
src_ino->n_link++;
if (inode_touch(txn, src_ino)) {
status = NFS4ERR_IO;
goto out_abort;
}
/* close transaction */
rc = txn->commit(txn, 0);
if (rc) {
dbenv->err(dbenv, rc, "DB_ENV->txn_commit");
status = NFS4ERR_IO;
goto out;
}
out:
WR32(status);
if (status == NFS4_OK) {
WR32(1); /* cinfo.atomic */
WR64(before); /* cinfo.before */
WR64(after); /* cinfo.after */
}
inode_free(src_ino);
inode_free(dir_ino);
return status;
out_abort:
if (txn->abort(txn))
//.........这里部分代码省略.........