Alien-SVN

 view release on metacpan or  search on metacpan

src/subversion/subversion/libsvn_fs_base/bdb/env.c  view on Meta::CPAN

  int db_err;
  bdb_env_t *bdb;
  const char *path_bdb;
  char *tmp_path, *tmp_path_bdb;
  apr_size_t path_size, path_bdb_size;

#if SVN_BDB_PATH_UTF8
  path_bdb = svn_dirent_local_style(path, pool);
#else
  SVN_ERR(svn_utf_cstring_from_utf8(&path_bdb,
                                    svn_dirent_local_style(path, pool),
                                    pool));
#endif

  /* Allocate the whole structure, including strings, from the heap,
     because it must survive the cache pool cleanup. */
  path_size = strlen(path) + 1;
  path_bdb_size = strlen(path_bdb) + 1;
  /* Using calloc() to ensure the padding bytes in bdb->key (which is used as
   * a hash key) are zeroed. */
  bdb = calloc(1, sizeof(*bdb) + path_size + path_bdb_size);

  /* We must initialize this now, as our callers may assume their bdb
     pointer is valid when checking for errors.  */
  apr_pool_cleanup_register(pool, bdb, cleanup_env, apr_pool_cleanup_null);
  apr_cpystrn(bdb->errpfx_string, BDB_ERRPFX_STRING,
              sizeof(bdb->errpfx_string));
  bdb->path = tmp_path = (char*)(bdb + 1);
  bdb->path_bdb = tmp_path_bdb = tmp_path + path_size;
  apr_cpystrn(tmp_path, path, path_size);
  apr_cpystrn(tmp_path_bdb, path_bdb, path_bdb_size);
  bdb->pool = pool;
  *bdbp = bdb;

#if APR_HAS_THREADS
  {
    apr_status_t apr_err = apr_threadkey_private_create(&bdb->error_info,
                                                        cleanup_error_info,
                                                        pool);
    if (apr_err)
      return svn_error_create(apr_err, NULL,
                              "Can't allocate thread-specific storage"
                              " for the Berkeley DB environment descriptor");
  }
#endif /* APR_HAS_THREADS */

  db_err = db_env_create(&(bdb->env), 0);
  if (!db_err)
    {
      /* See the documentation at bdb_env_t's definition why the
         (char *) cast is safe and why it is done. */
      bdb->env->set_errpfx(bdb->env, (char *) bdb);

      /* bdb_error_gatherer is in parens to stop macro expansion. */
      bdb->env->set_errcall(bdb->env, (bdb_error_gatherer));

      /* Needed on Windows in case Subversion and Berkeley DB are using
         different C runtime libraries  */
      db_err = bdb->env->set_alloc(bdb->env, malloc, realloc, free);

      /* If we detect a deadlock, select a transaction to abort at
         random from those participating in the deadlock.  */
      if (!db_err)
        db_err = bdb->env->set_lk_detect(bdb->env, DB_LOCK_RANDOM);
    }
  return convert_bdb_error(bdb, db_err);
}



/* The environment descriptor cache. */

/* The global pool used for this cache. */
static apr_pool_t *bdb_cache_pool = NULL;

/* The cache.  The items are bdb_env_t structures. */
static apr_hash_t *bdb_cache = NULL;

/* The mutex that protects bdb_cache. */
static svn_mutex__t *bdb_cache_lock = NULL;

/* Cleanup callback to NULL out the cache, so we don't try to use it after
   the pool has been cleared during global shutdown. */
static apr_status_t
clear_cache(void *data)
{
  bdb_cache = NULL;
  bdb_cache_lock = NULL;
  return APR_SUCCESS;
}

static volatile svn_atomic_t bdb_cache_state = 0;

static svn_error_t *
bdb_init_cb(void *baton, apr_pool_t *pool)
{
  bdb_cache_pool = svn_pool_create(pool);
  bdb_cache = apr_hash_make(bdb_cache_pool);

  SVN_ERR(svn_mutex__init(&bdb_cache_lock, TRUE, bdb_cache_pool));
  apr_pool_cleanup_register(bdb_cache_pool, NULL, clear_cache,
                            apr_pool_cleanup_null);

  return SVN_NO_ERROR;
}

svn_error_t *
svn_fs_bdb__init(apr_pool_t* pool)
{
  return svn_atomic__init_once(&bdb_cache_state, bdb_init_cb, NULL, pool);
}

/* Construct a cache key for the BDB environment at PATH in *KEYP.
   if DBCONFIG_FILE is not NULL, return the opened file handle.
   Allocate from POOL. */
static svn_error_t *
bdb_cache_key(bdb_env_key_t *keyp, apr_file_t **dbconfig_file,
              const char *path, apr_pool_t *pool)
{
  const char *dbcfg_file_name = svn_dirent_join(path, BDB_CONFIG_FILE, pool);
  apr_file_t *dbcfg_file;



( run in 0.872 second using v1.01-cache-2.11-cpan-754626df90b )