⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 lock.c

📁 subversion-1.4.3-1.tar.gz 配置svn的源码
💻 C
📖 第 1 页 / 共 3 页
字号:
dav_svn_append_locks(dav_lockdb *lockdb,                     const dav_resource *resource,                     int make_indirect,                     const dav_lock *lock){  dav_lockdb_private *info = lockdb->info;  svn_lock_t *slock;  svn_error_t *serr;  dav_error *derr;  svn_boolean_t readable = FALSE;  /* If the resource's fs path is unreadable, we don't allow a lock to     be created on it. */  derr = check_readability(&readable,                           resource->info->r, resource->info->repos,                           resource->info->repos_path, resource->pool);  if (derr)    return derr;  if (! readable)    return dav_new_error(resource->pool, HTTP_FORBIDDEN,                         DAV_ERR_LOCK_SAVE_LOCK,                         "Path is not accessible.");  if (lock->next)    return dav_new_error(resource->pool, HTTP_BAD_REQUEST,                         DAV_ERR_LOCK_SAVE_LOCK,                         "Tried to attach multiple locks to a resource.");  /* RFC2518bis (section 7.4) doesn't require us to support     'lock-null' resources at all.  Instead, it asks that we treat     'LOCK nonexistentURL' as a PUT (followed by a LOCK) of a 0-byte file.  */  if (! resource->exists)    {      svn_revnum_t rev, new_rev;      svn_fs_txn_t *txn;      svn_fs_root_t *txn_root;      const char *conflict_msg;      dav_svn_repos *repos = resource->info->repos;      if (resource->info->repos->is_svn_client)        return dav_new_error(resource->pool, HTTP_METHOD_NOT_ALLOWED,                             DAV_ERR_LOCK_SAVE_LOCK,                             "Subversion clients may not lock "                             "nonexistent paths.");      else if (! resource->info->repos->autoversioning)        return dav_new_error(resource->pool, HTTP_METHOD_NOT_ALLOWED,                             DAV_ERR_LOCK_SAVE_LOCK,                             "Attempted to lock non-existent path;"                             " turn on autoversioning first.");            /* Commit a 0-byte file: */      if ((serr = svn_fs_youngest_rev(&rev, repos->fs, resource->pool)))        return dav_svn_convert_err(serr, HTTP_INTERNAL_SERVER_ERROR,                                   "Could not determine youngest revision",                                    resource->pool);            if ((serr = svn_repos_fs_begin_txn_for_commit(&txn, repos->repos, rev,                                                    repos->username, NULL,                                                     resource->pool)))        return dav_svn_convert_err(serr, HTTP_INTERNAL_SERVER_ERROR,                                   "Could not begin a transaction",                                    resource->pool);      if ((serr = svn_fs_txn_root(&txn_root, txn, resource->pool)))        return dav_svn_convert_err(serr, HTTP_INTERNAL_SERVER_ERROR,                                   "Could not begin a transaction",                                    resource->pool);      if ((serr = svn_fs_make_file(txn_root, resource->info->repos_path,                                   resource->pool)))        return dav_svn_convert_err(serr, HTTP_INTERNAL_SERVER_ERROR,                                   "Could not create empty file.",                                   resource->pool);            if ((serr = dav_svn_attach_auto_revprops(txn,                                               resource->info->repos_path,                                               resource->pool)))        return dav_svn_convert_err(serr, HTTP_INTERNAL_SERVER_ERROR,                                   "Could not create empty file.",                                   resource->pool);            if ((serr = svn_repos_fs_commit_txn(&conflict_msg, repos->repos,                                          &new_rev, txn, resource->pool)))        {          svn_error_clear(svn_fs_abort_txn(txn, resource->pool));          return dav_svn_convert_err(serr, HTTP_CONFLICT,                                      apr_psprintf(resource->pool,                                                  "Conflict when committing "                                                  "'%s'.", conflict_msg),                                     resource->pool);        }    }  /* Convert the dav_lock into an svn_lock_t. */    derr = dav_lock_to_svn_lock(&slock, lock, resource->info->repos_path,                              info, resource->info->repos->is_svn_client,                              resource->pool);  if (derr)    return derr;  /* Now use the svn_lock_t to actually perform the lock. */  serr = svn_repos_fs_lock(&slock,                           resource->info->repos->repos,                           slock->path,                           slock->token,                           slock->comment,                           slock->is_dav_comment,                           slock->expiration_date,                           info->working_revnum,                           info->lock_steal,                           resource->pool);  if (serr && serr->apr_err == SVN_ERR_FS_NO_USER)    return dav_new_error(resource->pool, HTTP_UNAUTHORIZED,                         DAV_ERR_LOCK_SAVE_LOCK,                         "Anonymous lock creation is not allowed.");      else if (serr)    return dav_svn_convert_err(serr, HTTP_INTERNAL_SERVER_ERROR,                               "Failed to create new lock.",                               resource->pool);  /* A standard webdav LOCK response doesn't include any information     about the creation date.  We send it in a custom header, so that     svn clients can fill in svn_lock_t->creation_date.  A generic DAV     client should just ignore the header. */  apr_table_setn(info->r->headers_out, SVN_DAV_CREATIONDATE_HEADER,                 svn_time_to_cstring(slock->creation_date, resource->pool));  /* A standard webdav LOCK response doesn't include any information     about the owner of the lock.  ('DAV:owner' has nothing to do with     authorization, it's just a comment that we map to     svn_lock_t->comment.)  We send the owner in a custom header, so     that svn clients can fill in svn_lock_t->owner.  A generic DAV     client should just ignore the header. */  apr_table_setn(info->r->headers_out, SVN_DAV_LOCK_OWNER_HEADER,                 slock->owner);  /* Log the locking as a 'high-level' action. */  apr_table_set(resource->info->r->subprocess_env, "SVN-ACTION",                apr_psprintf(resource->info->r->pool,                             "lock '%s'",                             svn_path_uri_encode(slock->path,                                                 resource->info->r->pool)));  return 0;}/*** Remove any lock that has the specified locktoken.**** If locktoken == NULL, then ALL locks are removed.*/static dav_error *dav_svn_remove_lock(dav_lockdb *lockdb,                    const dav_resource *resource,                    const dav_locktoken *locktoken){  dav_lockdb_private *info = lockdb->info;  svn_error_t *serr;  dav_error *derr;  svn_boolean_t readable = FALSE;  svn_lock_t *slock;  const char *token = NULL;  /* Sanity check:  if the resource has no associated path in the fs,     then there's nothing to do.  */  if (! resource->info->repos_path)    return 0;  /* Another easy out: if an svn client sent a 'keep_locks' header     (typically in a DELETE request, as part of 'svn commit     --no-unlock'), then ignore dav_method_delete()'s attempt to     unconditionally remove the lock.  */  if (info->keep_locks)    return 0;  /* If the resource's fs path is unreadable, we don't allow a lock to     be removed from it. */  derr = check_readability(&readable,                           resource->info->r, resource->info->repos,                           resource->info->repos_path, resource->pool);  if (derr)    return derr;  if (! readable)    return dav_new_error(resource->pool, HTTP_FORBIDDEN,                         DAV_ERR_LOCK_SAVE_LOCK,                         "Path is not accessible.");  if (locktoken == NULL)    {      /* Need to manually discover any lock on the resource. */           serr = svn_fs_get_lock(&slock,                             resource->info->repos->fs,                             resource->info->repos_path,                             resource->pool);      if (serr)        return dav_svn_convert_err(serr, HTTP_INTERNAL_SERVER_ERROR,                                   "Failed to check path for a lock.",                                   resource->pool);      if (slock)        token = slock->token;    }  else    {      token = locktoken->uuid_str;    }  if (token)    {      /* Notice that a generic DAV client is unable to forcibly         'break' a lock, because info->lock_break will always be         FALSE.  An svn client, however, can request a 'forced' break.*/      serr = svn_repos_fs_unlock(resource->info->repos->repos,                                 resource->info->repos_path,                                 token,                                 info->lock_break,                                 resource->pool);      if (serr && serr->apr_err == SVN_ERR_FS_NO_USER)        return dav_new_error(resource->pool, HTTP_UNAUTHORIZED,                             DAV_ERR_LOCK_SAVE_LOCK,                             "Anonymous lock removal is not allowed.");      else if (serr)        return dav_svn_convert_err(serr, HTTP_INTERNAL_SERVER_ERROR,                                   "Failed to remove a lock.",                                   resource->pool);    }  /* Log the unlocking as a 'high-level' action. */  apr_table_set(resource->info->r->subprocess_env, "SVN-ACTION",                apr_psprintf(resource->info->r->pool,                             "unlock '%s'",                             svn_path_uri_encode(resource->info->repos_path,                                                 resource->info->r->pool)));  return 0;}/*** Refresh all locks, found on the specified resource, which has a** locktoken in the provided list.**** If the lock is indirect, then the direct lock is referenced and** refreshed.**** Each lock that is updated is returned in the <locks> argument.** Note that the locks will be fully resolved.*/static dav_error *dav_svn_refresh_locks(dav_lockdb *lockdb,                      const dav_resource *resource,                      const dav_locktoken_list *ltl,                      time_t new_time,                      dav_lock **locks){  /* We're not looping over a list of locks, since we only support one     lock per resource. */  dav_locktoken *token = ltl->locktoken;  svn_error_t *serr;  dav_error *derr;  svn_lock_t *slock;  dav_lock *dlock;  svn_boolean_t readable = FALSE;  /* If the resource's fs path is unreadable, we don't want to say     anything about locks attached to it.*/  derr = check_readability(&readable,                           resource->info->r, resource->info->repos,                           resource->info->repos_path, resource->pool);  if (derr)    return derr;  if (! readable)    return dav_new_error(resource->pool, HTTP_FORBIDDEN,                         DAV_ERR_LOCK_SAVE_LOCK,                         "Path is not accessible.");  /* Convert the path into an svn_lock_t. */  serr = svn_fs_get_lock(&slock,                         resource->info->repos->fs,                         resource->info->repos_path,                         resource->pool);  if (serr)    return dav_svn_convert_err(serr, HTTP_INTERNAL_SERVER_ERROR,                               "Token doesn't point to a lock.",                               resource->pool);  /* Sanity check: does the incoming token actually represent the     current lock on the incoming resource? */  if ((! slock)      || (strcmp(token->uuid_str, slock->token) != 0))    return dav_new_error(resource->pool, HTTP_UNAUTHORIZED,                         DAV_ERR_LOCK_SAVE_LOCK,                         "Lock refresh request doesn't match existing lock.");  /* Now use the tweaked svn_lock_t to 'refresh' the existing lock. */  serr = svn_repos_fs_lock(&slock,                           resource->info->repos->repos,                           slock->path,                           slock->token,                           slock->comment,                           slock->is_dav_comment,                           (new_time == DAV_TIMEOUT_INFINITE)                             ? 0 : (apr_time_t)new_time * APR_USEC_PER_SEC,                           SVN_INVALID_REVNUM,                           TRUE, /* forcibly steal existing lock */                           resource->pool);  if (serr && serr->apr_err == SVN_ERR_FS_NO_USER)    return dav_new_error(resource->pool, HTTP_UNAUTHORIZED,                         DAV_ERR_LOCK_SAVE_LOCK,                         "Anonymous lock refreshing is not allowed.");      else if (serr)    return dav_svn_convert_err(serr, HTTP_INTERNAL_SERVER_ERROR,                               "Failed to refresh existing lock.",                               resource->pool);  /* Convert the refreshed lock into a dav_lock and return it. */  svn_lock_to_dav_lock(&dlock, slock, FALSE, resource->exists, resource->pool);  *locks = dlock;  return 0;}/* The main locking vtable, provided to mod_dav */const dav_hooks_locks dav_svn_hooks_locks = {  dav_svn_get_supportedlock,  dav_svn_parse_locktoken,  dav_svn_format_locktoken,  dav_svn_compare_locktoken,  dav_svn_open_lockdb,  dav_svn_close_lockdb,  dav_svn_remove_locknull_state,  dav_svn_create_lock,  dav_svn_get_locks,  dav_svn_find_lock,  dav_svn_has_locks,  dav_svn_append_locks,  dav_svn_remove_lock,  dav_svn_refresh_locks,  NULL,  NULL                          /* hook structure context */};

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -