1
/* util.h --- utility functions for FSX repo access
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
12
* http://www.apache.org/licenses/LICENSE-2.0
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
20
* ====================================================================
23
#ifndef SVN_LIBSVN_FS__UTIL_H
24
#define SVN_LIBSVN_FS__UTIL_H
29
/* Functions for dealing with recoverable errors on mutable files
31
* Revprops, current, and txn-current files are mutable; that is, they
32
* change as part of normal fsx operation, in constrat to revs files, or
33
* the format file, which are written once at create (or upgrade) time.
34
* When more than one host writes to the same repository, we will
35
* sometimes see these recoverable errors when accesssing these files.
37
* These errors all relate to NFS, and thus we only use this retry code if
42
* In NFS v3 and under, the server doesn't track opened files. If you
43
* unlink(2) or rename(2) a file held open by another process *on the
44
* same host*, that host's kernel typically renames the file to
45
* .nfsXXXX and automatically deletes that when it's no longer open,
46
* but this behavior is not required.
48
* For obvious reasons, this does not work *across hosts*. No one
49
* knows about the opened file; not the server, and not the deleting
50
* client. So the file vanishes, and the reader gets stale NFS file
55
* Some client implementations (at least the 2.6.18.5 kernel that ships
56
* with Ubuntu Dapper) sometimes give spurious ENOENT (only on open) or
57
* even EIO errors when trying to read these files that have been renamed
58
* over on some other host.
62
* Try open and read of such files in try_stringbuf_from_file(). Call
63
* this function within a loop of SVN_FS_X__RECOVERABLE_RETRY_COUNT
64
* iterations (though, realistically, the second try will succeed).
67
#define SVN_FS_X__RECOVERABLE_RETRY_COUNT 10
69
/* Pathname helper functions */
71
/* Return TRUE is REV is packed in FS, FALSE otherwise. */
73
svn_fs_x__is_packed_rev(svn_fs_t *fs,
76
/* Return TRUE is REV is packed in FS, FALSE otherwise. */
78
svn_fs_x__is_packed_revprop(svn_fs_t *fs,
81
/* Return the first revision in the pack / rev file containing REV in
82
* filesystem FS. For non-packed revs, this will simply be REV. */
84
svn_fs_x__packed_base_rev(svn_fs_t *fs,
87
/* Return the number of revisions in the pack / rev file in FS that contains
90
svn_fs_x__pack_size(svn_fs_t *fs, svn_revnum_t rev);
92
/* Return the full path of the "format" file in FS.
93
* The result will be allocated in RESULT_POOL.
96
svn_fs_x__path_format(svn_fs_t *fs,
97
apr_pool_t *result_pool);
99
/* Return the path to the 'current' file in FS.
100
Perform allocation in RESULT_POOL. */
102
svn_fs_x__path_current(svn_fs_t *fs,
103
apr_pool_t *result_pool);
105
/* Return the full path of the "uuid" file in FS.
106
* The result will be allocated in RESULT_POOL.
109
svn_fs_x__path_uuid(svn_fs_t *fs,
110
apr_pool_t *result_pool);
112
/* Return the full path of the "txn-current" file in FS.
113
* The result will be allocated in RESULT_POOL.
116
svn_fs_x__path_txn_current(svn_fs_t *fs,
117
apr_pool_t *result_pool);
119
/* Return the full path of the "txn-current-lock" file in FS.
120
* The result will be allocated in RESULT_POOL.
123
svn_fs_x__path_txn_current_lock(svn_fs_t *fs,
124
apr_pool_t *result_pool);
126
/* Return the full path of the global write lock file in FS.
127
* The result will be allocated in RESULT_POOL.
130
svn_fs_x__path_lock(svn_fs_t *fs,
131
apr_pool_t *result_pool);
133
/* Return the full path of the pack operation lock file in FS.
134
* The result will be allocated in RESULT_POOL.
137
svn_fs_x__path_pack_lock(svn_fs_t *fs,
138
apr_pool_t *result_pool);
140
/* Return the full path of the revprop generation file in FS.
141
* Allocate the result in RESULT_POOL.
144
svn_fs_x__path_revprop_generation(svn_fs_t *fs,
145
apr_pool_t *result_pool);
147
/* Return the path of the pack-related file that for revision REV in FS.
148
* KIND specifies the file name base, e.g. "pack".
149
* The result will be allocated in RESULT_POOL.
152
svn_fs_x__path_rev_packed(svn_fs_t *fs,
155
apr_pool_t *result_pool);
157
/* Return the full path of the rev shard directory that will contain
158
* revision REV in FS. Allocate the result in RESULT_POOL.
161
svn_fs_x__path_rev_shard(svn_fs_t *fs,
163
apr_pool_t *result_pool);
165
/* Return the full path of the non-packed rev file containing revision REV
166
* in FS. Allocate the result in RESULT_POOL.
169
svn_fs_x__path_rev(svn_fs_t *fs,
171
apr_pool_t *result_pool);
173
/* Set *PATH to the path of REV in FS, whether in a pack file or not.
174
Allocate *PATH in RESULT_POOL.
176
Note: If the caller does not have the write lock on FS, then the path is
177
not guaranteed to be correct or to remain correct after the function
178
returns, because the revision might become packed before or after this
179
call. If a file exists at that path, then it is correct; if not, then
180
the caller should call update_min_unpacked_rev() and re-try once. */
182
svn_fs_x__path_rev_absolute(svn_fs_t *fs,
184
apr_pool_t *result_pool);
186
/* Return the full path of the revision properties shard directory that
187
* will contain the properties of revision REV in FS.
188
* Allocate the result in RESULT_POOL.
191
svn_fs_x__path_revprops_shard(svn_fs_t *fs,
193
apr_pool_t *result_pool);
195
/* Return the full path of the revision properties pack shard directory
196
* that will contain the packed properties of revision REV in FS.
197
* Allocate the result in RESULT_POOL.
200
svn_fs_x__path_revprops_pack_shard(svn_fs_t *fs,
202
apr_pool_t *result_pool);
204
/* Return the full path of the non-packed revision properties file that
205
* contains the props for revision REV in FS.
206
* Allocate the result in RESULT_POOL.
209
svn_fs_x__path_revprops(svn_fs_t *fs,
211
apr_pool_t *result_pool);
213
/* Convert the TXN_ID into a string, allocated from RESULT_POOL.
216
svn_fs_x__txn_name(svn_fs_x__txn_id_t txn_id,
217
apr_pool_t *result_pool);
219
/* Convert TXN_NAME into an ID and return it in *TXN_ID. */
221
svn_fs_x__txn_by_name(svn_fs_x__txn_id_t *txn_id,
222
const char *txn_name);
224
/* Return the path of the directory containing the transaction TXN_ID in FS.
225
* The result will be allocated in RESULT_POOL.
228
svn_fs_x__path_txn_dir(svn_fs_t *fs,
229
svn_fs_x__txn_id_t txn_id,
230
apr_pool_t *result_pool);
232
/* Return the path of the 'transactions' directory in FS.
233
* The result will be allocated in RESULT_POOL.
236
svn_fs_x__path_txns_dir(svn_fs_t *fs,
237
apr_pool_t *result_pool);
239
/* Return the name of the sha1->rep mapping file in transaction TXN_ID
240
* within FS for the given SHA1 checksum. Use POOL for allocations.
243
svn_fs_x__path_txn_sha1(svn_fs_t *fs,
244
svn_fs_x__txn_id_t txn_id,
245
const unsigned char *sha1,
248
/* Return the path of the 'txn-protorevs' directory in FS, even if that
249
* folder may not exist in FS. The result will be allocated in RESULT_POOL.
252
svn_fs_x__path_txn_proto_revs(svn_fs_t *fs,
253
apr_pool_t *result_pool);
255
/* Return the path of the changes file for transaction TXN_ID in FS.
256
* The result will be allocated in RESULT_POOL.
259
svn_fs_x__path_txn_changes(svn_fs_t *fs,
260
svn_fs_x__txn_id_t txn_id,
261
apr_pool_t *result_pool);
263
/* Return the path of the file containing the log-to-phys index for
264
* the transaction identified by TXN_ID in FS.
265
* The result will be allocated in RESULT_POOL.
268
svn_fs_x__path_l2p_proto_index(svn_fs_t *fs,
269
svn_fs_x__txn_id_t txn_id,
270
apr_pool_t *result_pool);
272
/* Return the path of the file containing the phys-to-log index for
273
* the transaction identified by TXN_ID in FS.
274
* The result will be allocated in RESULT_POOL.
277
svn_fs_x__path_p2l_proto_index(svn_fs_t *fs,
278
svn_fs_x__txn_id_t txn_id,
279
apr_pool_t *result_pool);
281
/* Return the path of the file containing the transaction properties for
282
* the transaction identified by TXN_ID in FS.
283
* The result will be allocated in RESULT_POOL.
286
svn_fs_x__path_txn_props(svn_fs_t *fs,
287
svn_fs_x__txn_id_t txn_id,
288
apr_pool_t *result_pool);
290
/* Return the path of the file containing the "final" transaction
291
* properties for the transaction identified by TXN_ID in FS.
292
* The result will be allocated in RESULT_POOL.
295
svn_fs_x__path_txn_props_final(svn_fs_t *fs,
296
svn_fs_x__txn_id_t txn_id,
297
apr_pool_t *result_pool);
299
/* Return the path of the file containing the node and copy ID counters for
300
* the transaction identified by TXN_ID in FS.
301
* The result will be allocated in RESULT_POOL.
304
svn_fs_x__path_txn_next_ids(svn_fs_t *fs,
305
svn_fs_x__txn_id_t txn_id,
306
apr_pool_t *result_pool);
308
/* Return the path of the file storing the oldest non-packed revision in FS.
309
* The result will be allocated in RESULT_POOL.
312
svn_fs_x__path_min_unpacked_rev(svn_fs_t *fs,
313
apr_pool_t *result_pool);
315
/* Return the path of the file containing item_index counter for
316
* the transaction identified by TXN_ID in FS.
317
* The result will be allocated in RESULT_POOL.
320
svn_fs_x__path_txn_item_index(svn_fs_t *fs,
321
svn_fs_x__txn_id_t txn_id,
322
apr_pool_t *result_pool);
324
/* Return the path of the proto-revision file for transaction TXN_ID in FS.
325
* The result will be allocated in RESULT_POOL.
328
svn_fs_x__path_txn_proto_rev(svn_fs_t *fs,
329
svn_fs_x__txn_id_t txn_id,
330
apr_pool_t *result_pool);
332
/* Return the path of the proto-revision lock file for transaction TXN_ID
333
* in FS. The result will be allocated in RESULT_POOL.
336
svn_fs_x__path_txn_proto_rev_lock(svn_fs_t *fs,
337
svn_fs_x__txn_id_t txn_id,
338
apr_pool_t *result_pool);
340
/* Return the path of the file containing the in-transaction node revision
341
* identified by ID in FS.
342
* The result will be allocated in RESULT_POOL, temporaries in SCRATCH_POOL.
345
svn_fs_x__path_txn_node_rev(svn_fs_t *fs,
346
const svn_fs_x__id_t *id,
347
apr_pool_t *result_pool,
348
apr_pool_t *scratch_pool);
350
/* Return the path of the file containing the in-transaction properties of
351
* the node identified by ID in FS.
352
* The result will be allocated in RESULT_POOL, temporaries in SCRATCH_POOL.
355
svn_fs_x__path_txn_node_props(svn_fs_t *fs,
356
const svn_fs_x__id_t *id,
357
apr_pool_t *result_pool,
358
apr_pool_t *scratch_pool);
360
/* Return the path of the file containing the directory entries of the
361
* in-transaction directory node identified by ID in FS.
362
* The result will be allocated in RESULT_POOL, temporaries in SCRATCH_POOL.
365
svn_fs_x__path_txn_node_children(svn_fs_t *fs,
366
const svn_fs_x__id_t *id,
367
apr_pool_t *result_pool,
368
apr_pool_t *scratch_pool);
370
/* Check that BUF, a nul-terminated buffer of text from file PATH,
371
contains only digits at OFFSET and beyond, raising an error if not.
372
TITLE contains a user-visible description of the file, usually the
375
Uses SCRATCH_POOL for temporary allocation. */
377
svn_fs_x__check_file_buffer_numeric(const char *buf,
381
apr_pool_t *scratch_pool);
383
/* Set *MIN_UNPACKED_REV to the integer value read from the file returned
384
* by #svn_fs_fs__path_min_unpacked_rev() for FS.
385
* Use SCRATCH_POOL for temporary allocations.
388
svn_fs_x__read_min_unpacked_rev(svn_revnum_t *min_unpacked_rev,
390
apr_pool_t *scratch_pool);
392
/* Re-read the MIN_UNPACKED_REV member of FS from disk.
393
* Use SCRATCH_POOL for temporary allocations.
396
svn_fs_x__update_min_unpacked_rev(svn_fs_t *fs,
397
apr_pool_t *scratch_pool);
399
/* Atomically update the 'min-unpacked-rev' file in FS to hold the specifed
400
* REVNUM. Perform temporary allocations in SCRATCH_POOL.
403
svn_fs_x__write_min_unpacked_rev(svn_fs_t *fs,
405
apr_pool_t *scratch_pool);
407
/* Set *REV to the value read from the 'current' file. Perform temporary
408
* allocations in SCRATCH_POOL.
411
svn_fs_x__read_current(svn_revnum_t *rev,
413
apr_pool_t *scratch_pool);
415
/* Atomically update the 'current' file to hold the specifed REV.
416
Perform temporary allocations in SCRATCH_POOL. */
418
svn_fs_x__write_current(svn_fs_t *fs,
420
apr_pool_t *scratch_pool);
422
/* Read the file at PATH and return its content in *CONTENT, allocated in
423
* RESULT_POOL. *CONTENT will not be modified unless the whole file was
426
* ESTALE, EIO and ENOENT will not cause this function to return an error
427
* unless LAST_ATTEMPT has been set. If MISSING is not NULL, indicate
428
* missing files (ENOENT) there.
431
svn_fs_x__try_stringbuf_from_file(svn_stringbuf_t **content,
432
svn_boolean_t *missing,
434
svn_boolean_t last_attempt,
435
apr_pool_t *result_pool);
437
/* Fetch the current offset of FILE into *OFFSET_P.
438
* Perform temporary allocations in SCRATCH_POOL. */
440
svn_fs_x__get_file_offset(apr_off_t *offset_p,
442
apr_pool_t *scratch_pool);
444
/* Read the file FNAME and store the contents in *BUF.
445
Allocations are performed in RESULT_POOL. */
447
svn_fs_x__read_content(svn_stringbuf_t **content,
449
apr_pool_t *result_pool);
451
/* Reads a line from STREAM and converts it to a 64 bit integer to be
452
* returned in *RESULT. If we encounter eof, set *HIT_EOF and leave
453
* *RESULT unchanged. If HIT_EOF is NULL, EOF causes an "corrupt FS"
455
* SCRATCH_POOL is used for temporary allocations.
458
svn_fs_x__read_number_from_stream(apr_int64_t *result,
459
svn_boolean_t *hit_eof,
460
svn_stream_t *stream,
461
apr_pool_t *scratch_pool);
463
/* Move a file into place from OLD_FILENAME in the transactions
464
directory to its final location NEW_FILENAME in the repository. On
465
Unix, match the permissions of the new file to the permissions of
466
PERMS_REFERENCE. Temporary allocations are from SCRATCH_POOL.
468
This function almost duplicates svn_io_file_move(), but it tries to
469
guarantee a flush. */
471
svn_fs_x__move_into_place(const char *old_filename,
472
const char *new_filename,
473
const char *perms_reference,
474
apr_pool_t *scratch_pool);