1 /* uuids-table.c : operations on the `uuids' table
2 *
3 * ====================================================================
4 * Licensed to the Apache Software Foundation (ASF) under one
5 * or more contributor license agreements. See the NOTICE file
6 * distributed with this work for additional information
7 * regarding copyright ownership. The ASF licenses this file
8 * to you under the Apache License, Version 2.0 (the
9 * "License"); you may not use this file except in compliance
10 * with the License. You may obtain a copy of the License at
11 *
12 * http://www.apache.org/licenses/LICENSE-2.0
13 *
14 * Unless required by applicable law or agreed to in writing,
15 * software distributed under the License is distributed on an
16 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
17 * KIND, either express or implied. See the License for the
18 * specific language governing permissions and limitations
19 * under the License.
20 * ====================================================================
21 */
22
23 #include <apr_uuid.h>
24
25 #include "bdb_compat.h"
26 #include "svn_fs.h"
27 #include "../fs.h"
28 #include "../err.h"
29 #include "dbt.h"
30 #include "../trail.h"
31 #include "../../libsvn_fs/fs-loader.h"
32 #include "bdb-err.h"
33 #include "uuids-table.h"
34
35 #include "svn_private_config.h"
36
37
38 /*** Creating and opening the uuids table.
39 When the table is created, the repository's uuid is
40 generated and stored as record #1. ***/
41
42 int
svn_fs_bdb__open_uuids_table(DB ** uuids_p,DB_ENV * env,svn_boolean_t create)43 svn_fs_bdb__open_uuids_table(DB **uuids_p,
44 DB_ENV *env,
45 svn_boolean_t create)
46 {
47 const u_int32_t open_flags = (create ? (DB_CREATE | DB_EXCL) : 0);
48 DB *uuids;
49 int error;
50
51 BDB_ERR(svn_fs_bdb__check_version());
52 BDB_ERR(db_create(&uuids, env, 0));
53 BDB_ERR(uuids->set_re_len(uuids, APR_UUID_FORMATTED_LENGTH));
54
55 error = (uuids->open)(SVN_BDB_OPEN_PARAMS(uuids, NULL),
56 "uuids", 0, DB_RECNO,
57 open_flags, 0666);
58
59 /* This is a temporary compatibility check; it creates the
60 UUIDs table if one does not already exist. */
61 if (error == ENOENT && (! create))
62 {
63 BDB_ERR(uuids->close(uuids, 0));
64 return svn_fs_bdb__open_uuids_table(uuids_p, env, TRUE);
65 }
66
67 BDB_ERR(error);
68
69 if (create)
70 {
71 char buffer[APR_UUID_FORMATTED_LENGTH + 1];
72 DBT key, value;
73 apr_uuid_t uuid;
74 int recno = 0;
75
76 svn_fs_base__clear_dbt(&key);
77 key.data = &recno;
78 key.size = sizeof(recno);
79 key.ulen = key.size;
80 key.flags |= DB_DBT_USERMEM;
81
82 svn_fs_base__clear_dbt(&value);
83 value.data = buffer;
84 value.size = sizeof(buffer) - 1;
85
86 apr_uuid_get(&uuid);
87 apr_uuid_format(buffer, &uuid);
88
89 BDB_ERR(uuids->put(uuids, 0, &key, &value, DB_APPEND));
90 }
91
92 *uuids_p = uuids;
93 return 0;
94 }
95
svn_fs_bdb__get_uuid(svn_fs_t * fs,int idx,const char ** uuid,trail_t * trail,apr_pool_t * pool)96 svn_error_t *svn_fs_bdb__get_uuid(svn_fs_t *fs,
97 int idx,
98 const char **uuid,
99 trail_t *trail,
100 apr_pool_t *pool)
101 {
102 base_fs_data_t *bfd = fs->fsap_data;
103 char buffer[APR_UUID_FORMATTED_LENGTH + 1];
104 DB *uuids = bfd->uuids;
105 DBT key;
106 DBT value;
107
108 svn_fs_base__clear_dbt(&key);
109 key.data = &idx;
110 key.size = sizeof(idx);
111
112 svn_fs_base__clear_dbt(&value);
113 value.data = buffer;
114 value.size = sizeof(buffer) - 1;
115 value.ulen = value.size;
116 value.flags |= DB_DBT_USERMEM;
117
118 svn_fs_base__trail_debug(trail, "uuids", "get");
119 SVN_ERR(BDB_WRAP(fs, N_("get repository uuid"),
120 uuids->get(uuids, trail->db_txn, &key, &value, 0)));
121
122 *uuid = apr_pstrmemdup(pool, value.data, value.size);
123
124 return SVN_NO_ERROR;
125 }
126
svn_fs_bdb__set_uuid(svn_fs_t * fs,int idx,const char * uuid,trail_t * trail,apr_pool_t * pool)127 svn_error_t *svn_fs_bdb__set_uuid(svn_fs_t *fs,
128 int idx,
129 const char *uuid,
130 trail_t *trail,
131 apr_pool_t *pool)
132 {
133 base_fs_data_t *bfd = fs->fsap_data;
134 DB *uuids = bfd->uuids;
135 DBT key;
136 DBT value;
137
138 svn_fs_base__clear_dbt(&key);
139 key.data = &idx;
140 key.size = sizeof(idx);
141
142 svn_fs_base__clear_dbt(&value);
143 value.size = (u_int32_t) strlen(uuid);
144 value.data = apr_pstrmemdup(pool, uuid, value.size + 1);
145
146 svn_fs_base__trail_debug(trail, "uuids", "put");
147 return BDB_WRAP(fs, N_("set repository uuid"),
148 uuids->put(uuids, trail->db_txn, &key, &value, 0));
149 }
150