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

📄 node_tree.c

📁 subversion-1.4.3-1.tar.gz 配置svn的源码
💻 C
字号:
/* * node_tree.c:  an editor for tracking repository deltas changes * * ==================================================================== * Copyright (c) 2000-2004 CollabNet.  All rights reserved. * * This software is licensed as described in the file COPYING, which * you should have received as part of this distribution.  The terms * are also available at http://subversion.tigris.org/license-1.html. * If newer versions of this license are posted there, you may use a * newer version instead, at your option. * * This software consists of voluntary contributions made by many * individuals.  For exact contribution history, see the revision * history and logs, available at http://subversion.tigris.org/. * ==================================================================== *//* ==================================================================== */#include <stdio.h>#include <assert.h>#define APR_WANT_STRFUNC#include <apr_want.h>#include <apr_pools.h>#include "svn_types.h"#include "svn_error.h"#include "svn_path.h"#include "svn_delta.h"#include "svn_fs.h"#include "svn_repos.h"#include "repos.h"#include "svn_private_config.h"/*** NOTE: This editor is unique in that it currently is hard-coded to     be anchored at the root directory of the filesystem.  This     affords us the ability to use the same paths for filesystem     locations and editor paths.  ***//*** Node creation and assembly structures and routines. ***/static svn_repos_node_t *create_node(const char *name,            svn_repos_node_t *parent,            apr_pool_t *pool){  svn_repos_node_t *node = apr_pcalloc(pool, sizeof(svn_repos_node_t));  node->action = 'R';  node->kind = svn_node_unknown;  node->name = apr_pstrdup(pool, name);  node->parent = parent;  return node;}static svn_repos_node_t *create_sibling_node(svn_repos_node_t *elder,                     const char *name,                     apr_pool_t *pool){  svn_repos_node_t *tmp_node;    /* No ELDER sibling?  That's just not gonna work out. */  if (! elder)    return NULL;  /* Run to the end of the list of siblings of ELDER. */  tmp_node = elder;  while (tmp_node->sibling)    tmp_node = tmp_node->sibling;  /* Create a new youngest sibling and return that. */  return (tmp_node->sibling = create_node(name, elder->parent, pool));}static svn_repos_node_t *create_child_node(svn_repos_node_t *parent,                   const char *name,                   apr_pool_t *pool){  /* No PARENT node?  That's just not gonna work out. */  if (! parent)    return NULL;  /* If PARENT has no children, create its first one and return that. */  if (! parent->child)    return (parent->child = create_node(name, parent, pool));  /* If PARENT already has a child, create a new sibling for its first     child and return that. */  return create_sibling_node(parent->child, name, pool);}static svn_repos_node_t *find_child_by_name(svn_repos_node_t *parent,                    const char *name){  svn_repos_node_t *tmp_node;  /* No PARENT node, or a barren PARENT?  Nothing to find. */  if ((! parent) || (! parent->child))    return NULL;  /* Look through the children for a node with a matching name. */  tmp_node = parent->child;  while (1)    {      if (! strcmp(tmp_node->name, name))        {          return tmp_node;        }      else        {          if (tmp_node->sibling)            tmp_node = tmp_node->sibling;          else            break;        }    }  return NULL;}static voidfind_real_base_location(const char **path_p,                        svn_revnum_t *rev_p,                        svn_repos_node_t *node,                        apr_pool_t *pool){  /* If NODE is an add-with-history, then its real base location is     the copy source. */  if ((node->action == 'A')       && node->copyfrom_path       && SVN_IS_VALID_REVNUM(node->copyfrom_rev))    {      *path_p = node->copyfrom_path;      *rev_p = node->copyfrom_rev;      return;    }  /* Otherwise, if NODE has a parent, we'll recurse, and add NODE's     name to whatever the parent's real base path turns out to be (and     pass the base revision on through). */  if (node->parent)    {      const char *path;      svn_revnum_t rev;      find_real_base_location(&path, &rev, node->parent, pool);      *path_p = svn_path_join(path, node->name, pool);      *rev_p = rev;      return;    }  /* Finally, if the node has no parent, then its name is "/", and it     has no interesting base revision.  */  *path_p = "/";  *rev_p = SVN_INVALID_REVNUM;  return;}/*** Editor functions and batons. ***/struct edit_baton{  svn_fs_t *fs;  svn_fs_root_t *root;  svn_fs_root_t *base_root;  apr_pool_t *node_pool;  svn_repos_node_t *node;};struct node_baton{  struct edit_baton *edit_baton;  struct node_baton *parent_baton;  svn_repos_node_t *node;};static svn_error_t *delete_entry(const char *path,             svn_revnum_t revision,             void *parent_baton,             apr_pool_t *pool){  struct node_baton *d = parent_baton;  struct edit_baton *eb = d->edit_baton;  svn_repos_node_t *node;  const char *name;  const char *base_path;  svn_revnum_t base_rev;  svn_fs_root_t *base_root;  svn_node_kind_t kind;                                /* Get (or create) the change node and update it. */  name = svn_path_basename(path, pool);  node = find_child_by_name(d->node, name);  if (! node)    node = create_child_node(d->node, name, eb->node_pool);  node->action = 'D';  /* We need to look up this node's parents to see what its original     path in the filesystem was.  Why?  Because if this deletion     occurred underneath a copied path, the thing that was deleted     probably lived at a different location (relative to the copy     source). */  find_real_base_location(&base_path, &base_rev, node, pool);  if (! SVN_IS_VALID_REVNUM(base_rev))    {      /* No interesting base revision?  We'll just look for the path         in our base root.  */      base_root = eb->base_root;    }  else    {      /* Oh.  Perhaps some copy goodness happened somewhere? */      SVN_ERR(svn_fs_revision_root(&base_root, eb->fs, base_rev, pool));    }  /* Now figure out if this thing was a file or a dir. */  SVN_ERR(svn_fs_check_path(&kind, base_root, base_path, pool));  if (kind == svn_node_none)    return svn_error_createf(SVN_ERR_FS_NOT_FOUND, NULL,                             _("'%s' not found in filesystem"), path);  node->kind = kind;  return SVN_NO_ERROR;}static svn_error_t *add_open_helper(const char *path,                char action,                svn_node_kind_t kind,                void *parent_baton,                const char *copyfrom_path,                svn_revnum_t copyfrom_rev,                apr_pool_t *pool,                void **child_baton){  struct node_baton *pb = parent_baton;  struct edit_baton *eb = pb->edit_baton;  struct node_baton *nb = apr_pcalloc(pool, sizeof(*nb));  assert(parent_baton && path);  nb->edit_baton = eb;  nb->parent_baton = pb;  /* Create and populate the node. */  nb->node = create_child_node(pb->node, svn_path_basename(path, pool),                                eb->node_pool);  nb->node->kind = kind;  nb->node->action = action;  nb->node->copyfrom_rev = copyfrom_rev;  nb->node->copyfrom_path =     copyfrom_path ? apr_pstrdup(eb->node_pool, copyfrom_path) : NULL;    *child_baton = nb;  return SVN_NO_ERROR;}static svn_error_t *open_root(void *edit_baton,          svn_revnum_t base_revision,          apr_pool_t *pool,          void **root_baton){  struct edit_baton *eb = edit_baton;  struct node_baton *d = apr_pcalloc(pool, sizeof(*d));  d->edit_baton = eb;  d->parent_baton = NULL;  d->node = (eb->node = create_node("", NULL, eb->node_pool));  d->node->kind = svn_node_dir;  d->node->action = 'R';  *root_baton = d;    return SVN_NO_ERROR;}static svn_error_t *open_directory(const char *path,               void *parent_baton,               svn_revnum_t base_revision,               apr_pool_t *pool,               void **child_baton){  SVN_ERR(add_open_helper(path, 'R', svn_node_dir, parent_baton,                          NULL, SVN_INVALID_REVNUM,                          pool, child_baton));  return SVN_NO_ERROR;}static svn_error_t *add_directory(const char *path,              void *parent_baton,              const char *copyfrom_path,              svn_revnum_t copyfrom_revision,              apr_pool_t *pool,              void **child_baton){  SVN_ERR(add_open_helper(path, 'A', svn_node_dir, parent_baton,                          copyfrom_path, copyfrom_revision,                           pool, child_baton));  return SVN_NO_ERROR;}static svn_error_t *open_file(const char *path,          void *parent_baton,          svn_revnum_t base_revision,          apr_pool_t *pool,          void **file_baton){  SVN_ERR(add_open_helper(path, 'R', svn_node_file, parent_baton,                          NULL, SVN_INVALID_REVNUM,                          pool, file_baton));  return SVN_NO_ERROR;}static svn_error_t *add_file(const char *path,         void *parent_baton,         const char *copyfrom_path,         svn_revnum_t copyfrom_revision,         apr_pool_t *pool,         void **file_baton){  SVN_ERR(add_open_helper(path, 'A', svn_node_file, parent_baton,                          copyfrom_path, copyfrom_revision,                           pool, file_baton));  return SVN_NO_ERROR;}static svn_error_t *apply_textdelta(void *file_baton,                 const char *base_checksum,                apr_pool_t *pool,                svn_txdelta_window_handler_t *handler,                void **handler_baton){  struct node_baton *fb = file_baton;  fb->node->text_mod = TRUE;  *handler = svn_delta_noop_window_handler;  *handler_baton = NULL;  return SVN_NO_ERROR;}static svn_error_t *change_node_prop(void *node_baton,                 const char *name,                  const svn_string_t *value,                 apr_pool_t *pool){  struct node_baton *nb = node_baton;  nb->node->prop_mod = TRUE;  return SVN_NO_ERROR;}svn_error_t *svn_repos_node_editor(const svn_delta_editor_t **editor,                      void **edit_baton,                      svn_repos_t *repos,                      svn_fs_root_t *base_root,                      svn_fs_root_t *root,                      apr_pool_t *node_pool,                      apr_pool_t *pool){  svn_delta_editor_t *my_editor;  struct edit_baton *my_edit_baton;  /* Set up the editor. */  my_editor = svn_delta_default_editor(pool);  my_editor->open_root           = open_root;  my_editor->delete_entry        = delete_entry;  my_editor->add_directory       = add_directory;  my_editor->open_directory      = open_directory;  my_editor->add_file            = add_file;  my_editor->open_file           = open_file;  my_editor->apply_textdelta     = apply_textdelta;  my_editor->change_file_prop    = change_node_prop;  my_editor->change_dir_prop     = change_node_prop;  /* Set up the edit baton. */  my_edit_baton = apr_pcalloc(pool, sizeof(*my_edit_baton));  my_edit_baton->node_pool = node_pool;  my_edit_baton->fs = repos->fs;  my_edit_baton->root = root;  my_edit_baton->base_root = base_root;  *editor = my_editor;  *edit_baton = my_edit_baton;  return SVN_NO_ERROR;}svn_repos_node_t *svn_repos_node_from_baton(void *edit_baton){  struct edit_baton *eb = edit_baton;  return eb->node;}

⌨️ 快捷键说明

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