Modified: subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/hotcopy.c URL: http://svn.apache.org/viewvc/subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/hotcopy.c?rev=1702504&r1=1702503&r2=1702504&view=diff ============================================================================== --- subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/hotcopy.c (original) +++ subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/hotcopy.c Fri Sep 11 15:51:30 2015 @@ -243,6 +243,7 @@ hotcopy_io_copy_dir_recursively(svn_bool * to DST_SUBDIR. Assume a sharding layout based on MAX_FILES_PER_DIR. * Set *SKIPPED_P to FALSE only if the file was copied, do not change the * value in *SKIPPED_P otherwise. SKIPPED_P may be NULL if not required. + * If PROPS is set, copy the revprops file, otherwise copy the rev data file. * Use SCRATCH_POOL for temporary allocations. */ static svn_error_t * hotcopy_copy_shard_file(svn_boolean_t *skipped_p, @@ -250,6 +251,7 @@ hotcopy_copy_shard_file(svn_boolean_t *s const char *dst_subdir, svn_revnum_t rev, int max_files_per_dir, + svn_boolean_t props, apr_pool_t *scratch_pool) { const char *src_subdir_shard = src_subdir, @@ -269,7 +271,9 @@ hotcopy_copy_shard_file(svn_boolean_t *s SVN_ERR(hotcopy_io_dir_file_copy(skipped_p, src_subdir_shard, dst_subdir_shard, - apr_psprintf(scratch_pool, "%ld", rev), + apr_psprintf(scratch_pool, "%c%ld", + props ? 'p' : 'r', + rev), scratch_pool)); return SVN_NO_ERROR; } @@ -296,9 +300,6 @@ hotcopy_copy_packed_shard(svn_boolean_t const char *dst_subdir; const char *packed_shard; const char *src_subdir_packed_shard; - svn_revnum_t revprop_rev; - apr_pool_t *iterpool; - svn_fs_x__data_t *src_ffd = src_fs->fsap_data; /* Copy the packed shard. */ src_subdir = svn_dirent_join(src_fs->path, PATH_REVS_DIR, scratch_pool); @@ -313,47 +314,6 @@ hotcopy_copy_packed_shard(svn_boolean_t NULL /* cancel_func */, NULL, scratch_pool)); - /* Copy revprops belonging to revisions in this pack. */ - src_subdir = svn_dirent_join(src_fs->path, PATH_REVPROPS_DIR, scratch_pool); - dst_subdir = svn_dirent_join(dst_fs->path, PATH_REVPROPS_DIR, scratch_pool); - - if (src_ffd->min_unpacked_rev < rev + max_files_per_dir) - { - /* copy unpacked revprops rev by rev */ - iterpool = svn_pool_create(scratch_pool); - for (revprop_rev = rev; - revprop_rev < rev + max_files_per_dir; - revprop_rev++) - { - svn_pool_clear(iterpool); - - SVN_ERR(hotcopy_copy_shard_file(skipped_p, src_subdir, dst_subdir, - revprop_rev, max_files_per_dir, - iterpool)); - } - svn_pool_destroy(iterpool); - } - else - { - /* revprop for revision 0 will never be packed */ - if (rev == 0) - SVN_ERR(hotcopy_copy_shard_file(skipped_p, src_subdir, dst_subdir, - 0, max_files_per_dir, - scratch_pool)); - - /* packed revprops folder */ - packed_shard = apr_psprintf(scratch_pool, "%ld" PATH_EXT_PACKED_SHARD, - rev / max_files_per_dir); - src_subdir_packed_shard = svn_dirent_join(src_subdir, packed_shard, - scratch_pool); - SVN_ERR(hotcopy_io_copy_dir_recursively(skipped_p, - src_subdir_packed_shard, - dst_subdir, packed_shard, - TRUE /* copy_perms */, - NULL /* cancel_func */, NULL, - scratch_pool)); - } - /* If necessary, update the min-unpacked rev file in the hotcopy. */ if (*dst_min_unpacked_rev < rev + max_files_per_dir) { @@ -366,111 +326,6 @@ hotcopy_copy_packed_shard(svn_boolean_t return SVN_NO_ERROR; } -/* Remove file PATH, if it exists - even if it is read-only. - * Use SCRATCH_POOL for temporary allocations. */ -static svn_error_t * -hotcopy_remove_file(const char *path, - apr_pool_t *scratch_pool) -{ - /* Make the rev file writable and remove it. */ - SVN_ERR(svn_io_set_file_read_write(path, TRUE, scratch_pool)); - SVN_ERR(svn_io_remove_file2(path, TRUE, scratch_pool)); - - return SVN_NO_ERROR; -} - - -/* Remove revision or revprop files between START_REV (inclusive) and - * END_REV (non-inclusive) from folder DST_SUBDIR in DST_FS. Assume - * sharding as per MAX_FILES_PER_DIR. - * Use SCRATCH_POOL for temporary allocations. */ -static svn_error_t * -hotcopy_remove_files(svn_fs_t *dst_fs, - const char *dst_subdir, - svn_revnum_t start_rev, - svn_revnum_t end_rev, - int max_files_per_dir, - apr_pool_t *scratch_pool) -{ - const char *shard; - const char *dst_subdir_shard; - svn_revnum_t rev; - apr_pool_t *iterpool; - - /* Pre-compute paths for initial shard. */ - shard = apr_psprintf(scratch_pool, "%ld", start_rev / max_files_per_dir); - dst_subdir_shard = svn_dirent_join(dst_subdir, shard, scratch_pool); - - iterpool = svn_pool_create(scratch_pool); - for (rev = start_rev; rev < end_rev; rev++) - { - svn_pool_clear(iterpool); - - /* If necessary, update paths for shard. */ - if (rev != start_rev && rev % max_files_per_dir == 0) - { - shard = apr_psprintf(iterpool, "%ld", rev / max_files_per_dir); - dst_subdir_shard = svn_dirent_join(dst_subdir, shard, scratch_pool); - } - - /* remove files for REV */ - SVN_ERR(hotcopy_remove_file(svn_dirent_join(dst_subdir_shard, - apr_psprintf(iterpool, - "%ld", rev), - iterpool), - iterpool)); - } - - svn_pool_destroy(iterpool); - - return SVN_NO_ERROR; -} - -/* Remove revisions between START_REV (inclusive) and END_REV (non-inclusive) - * from DST_FS. Assume sharding as per MAX_FILES_PER_DIR. - * Use SCRATCH_POOL for temporary allocations. */ -static svn_error_t * -hotcopy_remove_rev_files(svn_fs_t *dst_fs, - svn_revnum_t start_rev, - svn_revnum_t end_rev, - int max_files_per_dir, - apr_pool_t *scratch_pool) -{ - SVN_ERR_ASSERT(start_rev <= end_rev); - SVN_ERR(hotcopy_remove_files(dst_fs, - svn_dirent_join(dst_fs->path, - PATH_REVS_DIR, - scratch_pool), - start_rev, end_rev, - max_files_per_dir, scratch_pool)); - - return SVN_NO_ERROR; -} - -/* Remove revision properties between START_REV (inclusive) and END_REV - * (non-inclusive) from DST_FS. Assume sharding as per MAX_FILES_PER_DIR. - * Use SCRATCH_POOL for temporary allocations. Revision 0 revprops will - * not be deleted. */ -static svn_error_t * -hotcopy_remove_revprop_files(svn_fs_t *dst_fs, - svn_revnum_t start_rev, - svn_revnum_t end_rev, - int max_files_per_dir, - apr_pool_t *scratch_pool) -{ - SVN_ERR_ASSERT(start_rev <= end_rev); - - /* don't delete rev 0 props */ - SVN_ERR(hotcopy_remove_files(dst_fs, - svn_dirent_join(dst_fs->path, - PATH_REVPROPS_DIR, - scratch_pool), - start_rev ? start_rev : 1, end_rev, - max_files_per_dir, scratch_pool)); - - return SVN_NO_ERROR; -} - /* Verify that DST_FS is a suitable destination for an incremental * hotcopy from SRC_FS. */ static svn_error_t * @@ -506,29 +361,6 @@ hotcopy_incremental_check_preconditions( return SVN_NO_ERROR; } -/* Remove folder PATH. Ignore errors due to the sub-tree not being empty. - * CANCEL_FUNC and CANCEL_BATON do the usual thing. - * Use SCRATCH_POOL for temporary allocations. - */ -static svn_error_t * -remove_folder(const char *path, - svn_cancel_func_t cancel_func, - void *cancel_baton, - apr_pool_t *scratch_pool) -{ - svn_error_t *err = svn_io_remove_dir2(path, TRUE, - cancel_func, cancel_baton, - scratch_pool); - - if (err && APR_STATUS_IS_ENOTEMPTY(err->apr_err)) - { - svn_error_clear(err); - err = SVN_NO_ERROR; - } - - return svn_error_trace(err); -} - /* Copy the revision and revprop files (possibly sharded / packed) from * SRC_FS to DST_FS. Do not re-copy data which already exists in DST_FS. * When copying packed or unpacked shards, checkpoint the result in DST_FS @@ -545,8 +377,6 @@ hotcopy_revisions(svn_fs_t *src_fs, svn_boolean_t incremental, const char *src_revs_dir, const char *dst_revs_dir, - const char *src_revprops_dir, - const char *dst_revprops_dir, svn_fs_hotcopy_notify_t notify_func, void* notify_baton, svn_cancel_func_t cancel_func, @@ -624,26 +454,10 @@ hotcopy_revisions(svn_fs_t *src_fs, if (notify_func && !skipped) notify_func(notify_baton, rev, pack_end_rev, iterpool); - /* Remove revision files which are now packed. */ - if (incremental) - { - SVN_ERR(hotcopy_remove_rev_files(dst_fs, rev, - rev + max_files_per_dir, - max_files_per_dir, iterpool)); - SVN_ERR(hotcopy_remove_revprop_files(dst_fs, rev, - rev + max_files_per_dir, - max_files_per_dir, - iterpool)); - } - /* Now that all revisions have moved into the pack, the original * rev dir can be removed. */ - SVN_ERR(remove_folder(svn_fs_x__path_rev_shard(dst_fs, rev, iterpool), - cancel_func, cancel_baton, iterpool)); - if (rev > 0) - SVN_ERR(remove_folder(svn_fs_x__path_revprops_shard(dst_fs, rev, - iterpool), - cancel_func, cancel_baton, iterpool)); + SVN_ERR(svn_io_remove_dir2(svn_fs_x__path_shard(dst_fs, rev, iterpool), + TRUE, cancel_func, cancel_baton, iterpool)); } if (cancel_func) @@ -677,13 +491,12 @@ hotcopy_revisions(svn_fs_t *src_fs, /* Copy the rev file. */ SVN_ERR(hotcopy_copy_shard_file(&skipped, src_revs_dir, dst_revs_dir, - rev, max_files_per_dir, + rev, max_files_per_dir, FALSE, iterpool)); /* Copy the revprop file. */ - SVN_ERR(hotcopy_copy_shard_file(&skipped, src_revprops_dir, - dst_revprops_dir, - rev, max_files_per_dir, + SVN_ERR(hotcopy_copy_shard_file(&skipped, src_revs_dir, dst_revs_dir, + rev, max_files_per_dir, TRUE, iterpool)); /* Whenever this revision did not previously exist in the destination, @@ -752,8 +565,6 @@ hotcopy_body(void *baton, void* cancel_baton = hbb->cancel_baton; svn_revnum_t src_youngest; svn_revnum_t dst_youngest; - const char *src_revprops_dir; - const char *dst_revprops_dir; const char *src_revs_dir; const char *dst_revs_dir; const char *src_subdir; @@ -793,16 +604,10 @@ hotcopy_body(void *baton, src_revs_dir = svn_dirent_join(src_fs->path, PATH_REVS_DIR, scratch_pool); dst_revs_dir = svn_dirent_join(dst_fs->path, PATH_REVS_DIR, scratch_pool); - src_revprops_dir = svn_dirent_join(src_fs->path, PATH_REVPROPS_DIR, - scratch_pool); - dst_revprops_dir = svn_dirent_join(dst_fs->path, PATH_REVPROPS_DIR, - scratch_pool); /* Ensure that the required folders exist in the destination * before actually copying the revisions and revprops. */ SVN_ERR(svn_io_make_dir_recursively(dst_revs_dir, scratch_pool)); - SVN_ERR(svn_io_make_dir_recursively(dst_revprops_dir, scratch_pool)); - if (cancel_func) SVN_ERR(cancel_func(cancel_baton)); @@ -812,7 +617,6 @@ hotcopy_body(void *baton, * revision number, but also the next-ID counters). */ SVN_ERR(hotcopy_revisions(src_fs, dst_fs, src_youngest, dst_youngest, incremental, src_revs_dir, dst_revs_dir, - src_revprops_dir, dst_revprops_dir, notify_func, notify_baton, cancel_func, cancel_baton, scratch_pool)); SVN_ERR(svn_fs_x__write_current(dst_fs, src_youngest, scratch_pool)); @@ -832,16 +636,6 @@ hotcopy_body(void *baton, cancel_func, cancel_baton, scratch_pool)); - /* Now copy the node-origins cache tree. */ - src_subdir = svn_dirent_join(src_fs->path, PATH_NODE_ORIGINS_DIR, - scratch_pool); - SVN_ERR(svn_io_check_path(src_subdir, &kind, scratch_pool)); - if (kind == svn_node_dir) - SVN_ERR(hotcopy_io_copy_dir_recursively(NULL, src_subdir, dst_fs->path, - PATH_NODE_ORIGINS_DIR, TRUE, - cancel_func, cancel_baton, - scratch_pool)); - /* * NB: Data copied below is only read by writers, not readers. * Writers are still locked out at this point. @@ -909,11 +703,11 @@ hotcopy_create_empty_dest(svn_fs_t *src_ /* Remove revision 0 contents. Otherwise, it may not get overwritten * due to having a newer timestamp. */ - SVN_ERR(hotcopy_remove_file(svn_fs_x__path_rev(dst_fs, 0, scratch_pool), - scratch_pool)); - SVN_ERR(hotcopy_remove_file(svn_fs_x__path_revprops(dst_fs, 0, + SVN_ERR(svn_io_remove_file2(svn_fs_x__path_rev(dst_fs, 0, scratch_pool), + FALSE, scratch_pool)); + SVN_ERR(svn_io_remove_file2(svn_fs_x__path_revprops(dst_fs, 0, scratch_pool), - scratch_pool)); + FALSE, scratch_pool)); /* This filesystem is ready. Stamp it with a format number. Fail if * the 'format' file should already exist. */
Modified: subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/hotcopy.h URL: http://svn.apache.org/viewvc/subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/hotcopy.h?rev=1702504&r1=1702503&r2=1702504&view=diff ============================================================================== --- subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/hotcopy.h (original) +++ subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/hotcopy.h Fri Sep 11 15:51:30 2015 @@ -1,4 +1,4 @@ -/* hotcopy.h : interface to the native filesystem layer +/* hotcopy.h : interface to the hot-copying functionality * * ==================================================================== * Licensed to the Apache Software Foundation (ASF) under one @@ -20,8 +20,8 @@ * ==================================================================== */ -#ifndef SVN_LIBSVN_FS__HOTCOPY_H -#define SVN_LIBSVN_FS__HOTCOPY_H +#ifndef SVN_LIBSVN_FS_X_HOTCOPY_H +#define SVN_LIBSVN_FS_X_HOTCOPY_H #include "fs.h" Modified: subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/index.c URL: http://svn.apache.org/viewvc/subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/index.c?rev=1702504&r1=1702503&r2=1702504&view=diff ============================================================================== --- subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/index.c (original) +++ subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/index.c Fri Sep 11 15:51:30 2015 @@ -61,15 +61,9 @@ const apr_uint64_t off_t_max = (sizeof(a */ #define P2L_PROTO_INDEX_ENTRY_SIZE (6 * sizeof(apr_uint64_t)) -/* We put this string in front of the L2P index header. */ -#define L2P_STREAM_PREFIX "L2P-INDEX\n" - -/* We put this string in front of the P2L index header. */ -#define P2L_STREAM_PREFIX "P2L-INDEX\n" - /* Size of the buffer that will fit the index header prefixes. */ -#define STREAM_PREFIX_LEN MAX(sizeof(L2P_STREAM_PREFIX), \ - sizeof(P2L_STREAM_PREFIX)) +#define STREAM_PREFIX_LEN MAX(sizeof(SVN_FS_X__L2P_STREAM_PREFIX), \ + sizeof(SVN_FS_X__P2L_STREAM_PREFIX)) /* Page tables in the log-to-phys index file exclusively contain entries * of this type to describe position and size of a given page. @@ -348,20 +342,15 @@ packed_stream_read(svn_fs_x__packed_numb return SVN_NO_ERROR; } -/* Create and open a packed number stream reading from offsets START to - * END in FILE and return it in *STREAM. Access the file in chunks of - * BLOCK_SIZE bytes. Expect the stream to be prefixed by STREAM_PREFIX. - * Allocate *STREAM in RESULT_POOL and use SCRATCH_POOL for temporaries. - */ -static svn_error_t * -packed_stream_open(svn_fs_x__packed_number_stream_t **stream, - apr_file_t *file, - apr_off_t start, - apr_off_t end, - const char *stream_prefix, - apr_size_t block_size, - apr_pool_t *result_pool, - apr_pool_t *scratch_pool) +svn_error_t * +svn_fs_x__packed_stream_open(svn_fs_x__packed_number_stream_t **stream, + apr_file_t *file, + apr_off_t start, + apr_off_t end, + const char *stream_prefix, + apr_size_t block_size, + apr_pool_t *result_pool, + apr_pool_t *scratch_pool) { char buffer[STREAM_PREFIX_LEN + 1] = { 0 }; apr_size_t len = strlen(stream_prefix); @@ -702,7 +691,8 @@ svn_fs_x__l2p_proto_index_add_entry(apr_ * read operations only. */ static apr_size_t -encode_uint(unsigned char *p, apr_uint64_t value) +encode_uint(unsigned char *p, + apr_uint64_t value) { unsigned char *start = p; while (value >= 0x80) @@ -720,7 +710,8 @@ encode_uint(unsigned char *p, apr_uint64 * This maps signed ints onto unsigned ones. */ static apr_size_t -encode_int(unsigned char *p, apr_int64_t value) +encode_int(unsigned char *p, + apr_int64_t value) { return encode_uint(p, (apr_uint64_t)(value < 0 ? -1 - 2*value : 2*value)); } @@ -742,7 +733,9 @@ stream_write_encoded(svn_stream_t *strea * Return the number of remaining entries in ARRAY after START. */ static int -rle_array(apr_array_header_t *array, int start, int end) +rle_array(apr_array_header_t *array, + int start, + int end) { int i; int target = start; @@ -1038,7 +1031,7 @@ svn_fs_x__l2p_index_append(svn_checksum_ /* write header info */ - SVN_ERR(svn_stream_puts(stream, L2P_STREAM_PREFIX)); + SVN_ERR(svn_stream_puts(stream, SVN_FS_X__L2P_STREAM_PREFIX)); SVN_ERR(stream_write_encoded(stream, revision)); SVN_ERR(stream_write_encoded(stream, page_counts->nelts)); SVN_ERR(stream_write_encoded(stream, ffd->l2p_page_size)); @@ -1074,7 +1067,8 @@ svn_fs_x__l2p_index_append(svn_checksum_ * REVISION in FS. */ static svn_revnum_t -base_revision(svn_fs_t *fs, svn_revnum_t revision) +base_revision(svn_fs_t *fs, + svn_revnum_t revision) { svn_fs_x__data_t *ffd = fs->fsap_data; return svn_fs_x__is_packed_rev(fs, revision) @@ -1231,32 +1225,6 @@ expand_rle(apr_array_header_t *values, return SVN_NO_ERROR; } -/* If REV_FILE->L2P_STREAM is NULL, create a new stream for the log-to-phys - * index for REVISION in FS and return it in REV_FILE. - */ -static svn_error_t * -auto_open_l2p_index(svn_fs_x__revision_file_t *rev_file, - svn_fs_t *fs, - svn_revnum_t revision) -{ - if (rev_file->l2p_stream == NULL) - { - svn_fs_x__data_t *ffd = fs->fsap_data; - - SVN_ERR(svn_fs_x__auto_read_footer(rev_file)); - SVN_ERR(packed_stream_open(&rev_file->l2p_stream, - rev_file->file, - rev_file->l2p_offset, - rev_file->p2l_offset, - L2P_STREAM_PREFIX, - (apr_size_t)ffd->block_size, - rev_file->pool, - rev_file->pool)); - } - - return SVN_NO_ERROR; -} - /* Read the header data structure of the log-to-phys index for REVISION * in FS and return it in *HEADER, allocated in RESULT_POOL. Use REV_FILE * to access on-disk data. Use SCRATCH_POOL for temporary allocations. @@ -1279,41 +1247,48 @@ get_l2p_header_body(l2p_header_t **heade svn_revnum_t next_rev; apr_array_header_t *expanded_values = apr_array_make(scratch_pool, 16, sizeof(apr_uint64_t)); + svn_fs_x__packed_number_stream_t *stream; + svn_fs_x__rev_file_info_t file_info; + svn_fs_x__index_info_t index_info; + /* What to look for. */ svn_fs_x__pair_cache_key_t key; - key.revision = rev_file->start_revision; - key.second = rev_file->is_packed; - - SVN_ERR(auto_open_l2p_index(rev_file, fs, revision)); - packed_stream_seek(rev_file->l2p_stream, 0); + SVN_ERR(svn_fs_x__rev_file_info(&file_info, rev_file)); + key.revision = file_info.start_revision; + key.second = file_info.is_packed; + + /* Access the L2P index stream. */ + SVN_ERR(svn_fs_x__rev_file_l2p_index(&stream, rev_file)); + SVN_ERR(svn_fs_x__rev_file_l2p_info(&index_info, rev_file)); + packed_stream_seek(stream, 0); /* Read the table sizes. Check the data for plausibility and * consistency with other bits. */ - SVN_ERR(packed_stream_get(&value, rev_file->l2p_stream)); + SVN_ERR(packed_stream_get(&value, stream)); result->first_revision = (svn_revnum_t)value; - if (result->first_revision != rev_file->start_revision) + if (result->first_revision != file_info.start_revision) return svn_error_create(SVN_ERR_FS_INDEX_CORRUPTION, NULL, _("Index rev / pack file revision numbers do not match")); - SVN_ERR(packed_stream_get(&value, rev_file->l2p_stream)); + SVN_ERR(packed_stream_get(&value, stream)); result->revision_count = (int)value; if ( result->revision_count != 1 && result->revision_count != (apr_uint64_t)ffd->max_files_per_dir) return svn_error_create(SVN_ERR_FS_INDEX_CORRUPTION, NULL, _("Invalid number of revisions in L2P index")); - SVN_ERR(packed_stream_get(&value, rev_file->l2p_stream)); + SVN_ERR(packed_stream_get(&value, stream)); result->page_size = (apr_uint32_t)value; if (!result->page_size || (result->page_size & (result->page_size - 1))) return svn_error_create(SVN_ERR_FS_INDEX_CORRUPTION, NULL, _("L2P index page size is not a power of two")); - SVN_ERR(packed_stream_get(&value, rev_file->l2p_stream)); + SVN_ERR(packed_stream_get(&value, stream)); page_count = (apr_size_t)value; if (page_count < result->revision_count) return svn_error_create(SVN_ERR_FS_INDEX_CORRUPTION, NULL, _("Fewer L2P index pages than revisions")); - if (page_count > (rev_file->p2l_offset - rev_file->l2p_offset) / 2) + if (page_count > (index_info.end - index_info.start) / 2) return svn_error_create(SVN_ERR_FS_INDEX_CORRUPTION, NULL, _("L2P index page count implausibly large")); @@ -1333,8 +1308,7 @@ get_l2p_header_body(l2p_header_t **heade /* read per-revision page table sizes (i.e. number of pages per rev) */ page_table_index = 0; result->page_table_index[0] = page_table_index; - SVN_ERR(expand_rle(expanded_values, rev_file->l2p_stream, - result->revision_count)); + SVN_ERR(expand_rle(expanded_values, stream, result->revision_count)); for (i = 0; i < result->revision_count; ++i) { value = (apr_size_t)APR_ARRAY_IDX(expanded_values, i, apr_uint64_t); @@ -1357,13 +1331,13 @@ get_l2p_header_body(l2p_header_t **heade /* read actual page tables */ for (page = 0; page < page_count; ++page) { - SVN_ERR(packed_stream_get(&value, rev_file->l2p_stream)); + SVN_ERR(packed_stream_get(&value, stream)); if (value == 0) return svn_error_create(SVN_ERR_FS_INDEX_CORRUPTION, NULL, _("Empty L2P index page")); result->page_table[page].size = (apr_uint32_t)value; - SVN_ERR(packed_stream_get(&value, rev_file->l2p_stream)); + SVN_ERR(packed_stream_get(&value, stream)); if (value > result->page_size) return svn_error_create(SVN_ERR_FS_INDEX_CORRUPTION, NULL, _("Page exceeds L2P index page size")); @@ -1372,7 +1346,7 @@ get_l2p_header_body(l2p_header_t **heade } /* correct the page description offsets */ - offset = packed_stream_offset(rev_file->l2p_stream); + offset = packed_stream_offset(stream); for (page = 0; page < page_count; ++page) { result->page_table[page].offset = offset; @@ -1437,11 +1411,13 @@ get_l2p_header(l2p_header_t **header, { svn_fs_x__data_t *ffd = fs->fsap_data; svn_boolean_t is_cached = FALSE; + svn_fs_x__rev_file_info_t file_info; /* first, try cache lookop */ svn_fs_x__pair_cache_key_t key; - key.revision = rev_file->start_revision; - key.second = rev_file->is_packed; + SVN_ERR(svn_fs_x__rev_file_info(&file_info, rev_file)); + key.revision = file_info.start_revision; + key.second = file_info.is_packed; SVN_ERR(svn_cache__get((void**)header, &is_cached, ffd->l2p_header_cache, &key, result_pool)); if (is_cached) @@ -1454,16 +1430,12 @@ get_l2p_header(l2p_header_t **header, return SVN_NO_ERROR; } -/* From the log-to-phys index file starting at START_REVISION in FS, read - * the mapping page identified by TABLE_ENTRY and return it in *PAGE. - * Use REV_FILE to access on-disk files. - * Use RESULT_POOL for allocations. +/* From the log-to-phys index in REV_FILE, read the mapping page identified + * by TABLE_ENTRY and return it in *PAGE, allocated in RESULT_POOL. */ static svn_error_t * get_l2p_page(l2p_page_t **page, svn_fs_x__revision_file_t *rev_file, - svn_fs_t *fs, - svn_revnum_t start_revision, l2p_page_table_entry_t *table_entry, apr_pool_t *result_pool) { @@ -1472,10 +1444,11 @@ get_l2p_page(l2p_page_t **page, l2p_page_t *result = apr_pcalloc(result_pool, sizeof(*result)); apr_uint64_t container_count; apr_off_t *container_offsets; + svn_fs_x__packed_number_stream_t *stream; /* open index file and select page */ - SVN_ERR(auto_open_l2p_index(rev_file, fs, start_revision)); - packed_stream_seek(rev_file->l2p_stream, table_entry->offset); + SVN_ERR(svn_fs_x__rev_file_l2p_index(&stream, rev_file)); + packed_stream_seek(stream, table_entry->offset); /* initialize the page content */ result->entry_count = table_entry->entry_count; @@ -1486,12 +1459,12 @@ get_l2p_page(l2p_page_t **page, /* container offsets array */ - SVN_ERR(packed_stream_get(&container_count, rev_file->l2p_stream)); + SVN_ERR(packed_stream_get(&container_count, stream)); container_offsets = apr_pcalloc(result_pool, container_count * sizeof(*result)); for (i = 0; i < container_count; ++i) { - SVN_ERR(packed_stream_get(&value, rev_file->l2p_stream)); + SVN_ERR(packed_stream_get(&value, stream)); last_value += value; container_offsets[i] = (apr_off_t)last_value - 1; /* '-1' is represented as '0' in the index file */ @@ -1500,7 +1473,7 @@ get_l2p_page(l2p_page_t **page, /* read all page entries (offsets in rev file and container sub-items) */ for (i = 0; i < result->entry_count; ++i) { - SVN_ERR(packed_stream_get(&value, rev_file->l2p_stream)); + SVN_ERR(packed_stream_get(&value, stream)); if (value == 0) { result->offsets[i] = -1; @@ -1509,7 +1482,7 @@ get_l2p_page(l2p_page_t **page, else if (value <= container_count) { result->offsets[i] = container_offsets[value - 1]; - SVN_ERR(packed_stream_get(&value, rev_file->l2p_stream)); + SVN_ERR(packed_stream_get(&value, stream)); result->sub_items[i] = (apr_uint32_t)value; } else @@ -1521,7 +1494,7 @@ get_l2p_page(l2p_page_t **page, /* After reading all page entries, the read cursor must have moved by * TABLE_ENTRY->SIZE bytes. */ - if ( packed_stream_offset(rev_file->l2p_stream) + if ( packed_stream_offset(stream) != table_entry->offset + table_entry->size) return svn_error_create(SVN_ERR_FS_INDEX_CORRUPTION, NULL, _("L2P actual page size does not match page table value.")); @@ -1690,9 +1663,8 @@ get_l2p_page_table(apr_array_header_t *p /* Utility function. Read the l2p index pages for REVISION in FS from * STREAM and put them into the cache. Skip page number EXLCUDED_PAGE_NO * (use -1 for 'skip none') and pages outside the MIN_OFFSET, MAX_OFFSET - * range in the l2p index file. The index is being identified by - * FIRST_REVISION. PAGES is a scratch container provided by the caller. - * SCRATCH_POOL is used for temporary allocations. + * range in the l2p index file. PAGES is a scratch container provided by + * the caller. SCRATCH_POOL is used for temporary allocations. * * This function may be a no-op if the header cache lookup fails / misses. */ @@ -1700,7 +1672,6 @@ static svn_error_t * prefetch_l2p_pages(svn_boolean_t *end, svn_fs_t *fs, svn_fs_x__revision_file_t *rev_file, - svn_revnum_t first_revision, svn_revnum_t revision, apr_array_header_t *pages, int exlcuded_page_no, @@ -1769,8 +1740,7 @@ prefetch_l2p_pages(svn_boolean_t *end, /* no in cache -> read from stream (data already buffered in APR) * and cache the result */ l2p_page_t *page = NULL; - SVN_ERR(get_l2p_page(&page, rev_file, fs, first_revision, - entry, iterpool)); + SVN_ERR(get_l2p_page(&page, rev_file, entry, iterpool)); SVN_ERR(svn_cache__set(ffd->l2p_page_cache, &key, page, iterpool)); @@ -1841,8 +1811,7 @@ l2p_index_lookup(apr_off_t *offset, apr_off_t min_offset = max_offset - ffd->block_size; /* read the relevant page */ - SVN_ERR(get_l2p_page(&page, rev_file, fs, info_baton.first_revision, - &info_baton.entry, scratch_pool)); + SVN_ERR(get_l2p_page(&page, rev_file, &info_baton.entry, scratch_pool)); /* cache the page and extract the result we need */ SVN_ERR(svn_cache__set(ffd->l2p_page_cache, &key, page, scratch_pool)); @@ -1863,7 +1832,6 @@ l2p_index_lookup(apr_off_t *offset, svn_pool_clear(iterpool); SVN_ERR(prefetch_l2p_pages(&end, fs, rev_file, - info_baton.first_revision, prefetch_revision, pages, excluded_page_no, min_offset, max_offset, iterpool)); @@ -1877,7 +1845,6 @@ l2p_index_lookup(apr_off_t *offset, svn_pool_clear(iterpool); SVN_ERR(prefetch_l2p_pages(&end, fs, rev_file, - info_baton.first_revision, prefetch_revision, pages, -1, min_offset, max_offset, iterpool)); } @@ -1950,8 +1917,7 @@ svn_fs_x__l2p_get_max_ids(apr_array_head apr_pool_t *header_pool = svn_pool_create(scratch_pool); /* read index master data structure for the index covering START_REV */ - SVN_ERR(svn_fs_x__open_pack_or_rev_file(&rev_file, fs, start_rev, - header_pool, header_pool)); + SVN_ERR(svn_fs_x__rev_file_init(&rev_file, fs, start_rev, header_pool)); SVN_ERR(get_l2p_header(&header, rev_file, fs, start_rev, header_pool, header_pool)); SVN_ERR(svn_fs_x__close_revision_file(rev_file)); @@ -1972,8 +1938,8 @@ svn_fs_x__l2p_get_max_ids(apr_array_head * the number of items in a revision, i.e. there is no consistency * issue here. */ svn_pool_clear(header_pool); - SVN_ERR(svn_fs_x__open_pack_or_rev_file(&rev_file, fs, revision, - header_pool, header_pool)); + SVN_ERR(svn_fs_x__rev_file_init(&rev_file, fs, revision, + header_pool)); SVN_ERR(get_l2p_header(&header, rev_file, fs, revision, header_pool, header_pool)); SVN_ERR(svn_fs_x__close_revision_file(rev_file)); @@ -2315,7 +2281,8 @@ svn_fs_x__p2l_index_append(svn_checksum_ encode_uint(encoded, entry.size), iterpool)); SVN_ERR(svn_spillbuf__write(buffer, (const char *)encoded, - encode_uint(encoded, entry.type + entry.item_count * 16), + encode_uint(encoded, entry.type + + entry.item_count * 16), iterpool)); SVN_ERR(svn_spillbuf__write(buffer, (const char *)encoded, encode_uint(encoded, entry.fnv1_checksum), @@ -2359,7 +2326,7 @@ svn_fs_x__p2l_index_append(svn_checksum_ result_pool); /* write the start revision, file size and page size */ - SVN_ERR(svn_stream_puts(stream, P2L_STREAM_PREFIX)); + SVN_ERR(svn_stream_puts(stream, SVN_FS_X__P2L_STREAM_PREFIX)); SVN_ERR(stream_write_encoded(stream, revision)); SVN_ERR(stream_write_encoded(stream, file_size)); SVN_ERR(stream_write_encoded(stream, page_size)); @@ -2382,32 +2349,6 @@ svn_fs_x__p2l_index_append(svn_checksum_ return SVN_NO_ERROR; } -/* If REV_FILE->P2L_STREAM is NULL, create a new stream for the phys-to-log - * index for REVISION in FS using the rev / pack file provided by REV_FILE. - */ -static svn_error_t * -auto_open_p2l_index(svn_fs_x__revision_file_t *rev_file, - svn_fs_t *fs, - svn_revnum_t revision) -{ - if (rev_file->p2l_stream == NULL) - { - svn_fs_x__data_t *ffd = fs->fsap_data; - - SVN_ERR(svn_fs_x__auto_read_footer(rev_file)); - SVN_ERR(packed_stream_open(&rev_file->p2l_stream, - rev_file->file, - rev_file->p2l_offset, - rev_file->footer_offset, - P2L_STREAM_PREFIX, - (apr_size_t)ffd->block_size, - rev_file->pool, - rev_file->pool)); - } - - return SVN_NO_ERROR; -} - /* Data structure that describes which p2l page info shall be extracted * from the cache and contains the fields that receive the result. */ @@ -2515,11 +2456,15 @@ get_p2l_header(p2l_header_t **header, apr_off_t offset; p2l_header_t *result; svn_boolean_t is_cached = FALSE; + svn_fs_x__packed_number_stream_t *stream; + svn_fs_x__rev_file_info_t file_info; + svn_fs_x__index_info_t l2p_index_info; /* look for the header data in our cache */ svn_fs_x__pair_cache_key_t key; - key.revision = rev_file->start_revision; - key.second = rev_file->is_packed; + SVN_ERR(svn_fs_x__rev_file_info(&file_info, rev_file)); + key.revision = file_info.start_revision; + key.second = file_info.is_packed; SVN_ERR(svn_cache__get((void**)header, &is_cached, ffd->p2l_header_cache, &key, result_pool)); @@ -2528,32 +2473,33 @@ get_p2l_header(p2l_header_t **header, /* not found -> must read it from disk. * Open index file or position read pointer to the begin of the file */ - SVN_ERR(auto_open_p2l_index(rev_file, fs, key.revision)); - packed_stream_seek(rev_file->p2l_stream, 0); + SVN_ERR(svn_fs_x__rev_file_p2l_index(&stream, rev_file)); + SVN_ERR(svn_fs_x__rev_file_l2p_info(&l2p_index_info, rev_file)); + packed_stream_seek(stream, 0); /* allocate result data structure */ result = apr_pcalloc(result_pool, sizeof(*result)); /* Read table sizes, check them for plausibility and allocate page array. */ - SVN_ERR(packed_stream_get(&value, rev_file->p2l_stream)); + SVN_ERR(packed_stream_get(&value, stream)); result->first_revision = (svn_revnum_t)value; - if (result->first_revision != rev_file->start_revision) + if (result->first_revision != file_info.start_revision) return svn_error_create(SVN_ERR_FS_INDEX_CORRUPTION, NULL, _("Index rev / pack file revision numbers do not match")); - SVN_ERR(packed_stream_get(&value, rev_file->p2l_stream)); + SVN_ERR(packed_stream_get(&value, stream)); result->file_size = value; - if (result->file_size != (apr_uint64_t)rev_file->l2p_offset) + if (result->file_size != (apr_uint64_t)l2p_index_info.start) return svn_error_create(SVN_ERR_FS_INDEX_CORRUPTION, NULL, _("Index offset and rev / pack file size do not match")); - SVN_ERR(packed_stream_get(&value, rev_file->p2l_stream)); + SVN_ERR(packed_stream_get(&value, stream)); result->page_size = value; if (!result->page_size || (result->page_size & (result->page_size - 1))) return svn_error_create(SVN_ERR_FS_INDEX_CORRUPTION, NULL, _("P2L index page size is not a power of two")); - SVN_ERR(packed_stream_get(&value, rev_file->p2l_stream)); + SVN_ERR(packed_stream_get(&value, stream)); result->page_count = (apr_size_t)value; if (result->page_count != (result->file_size - 1) / result->page_size + 1) return svn_error_create(SVN_ERR_FS_INDEX_CORRUPTION, NULL, @@ -2566,12 +2512,12 @@ get_p2l_header(p2l_header_t **header, result->offsets[0] = 0; for (i = 0; i < result->page_count; ++i) { - SVN_ERR(packed_stream_get(&value, rev_file->p2l_stream)); + SVN_ERR(packed_stream_get(&value, stream)); result->offsets[i+1] = result->offsets[i] + (apr_off_t)value; } /* correct the offset values */ - offset = packed_stream_offset(rev_file->p2l_stream); + offset = packed_stream_offset(stream); for (i = 0; i <= result->page_count; ++i) result->offsets[i] += offset; @@ -2732,14 +2678,15 @@ get_p2l_page(apr_array_header_t **entrie = apr_array_make(result_pool, 16, sizeof(svn_fs_x__p2l_entry_t)); apr_off_t item_offset; apr_off_t offset; + svn_fs_x__packed_number_stream_t *stream; /* open index and navigate to page start */ - SVN_ERR(auto_open_p2l_index(rev_file, fs, start_revision)); - packed_stream_seek(rev_file->p2l_stream, start_offset); + SVN_ERR(svn_fs_x__rev_file_p2l_index(&stream, rev_file)); + packed_stream_seek(stream, start_offset); /* read rev file offset of the first page entry (all page entries will * only store their sizes). */ - SVN_ERR(packed_stream_get(&value, rev_file->p2l_stream)); + SVN_ERR(packed_stream_get(&value, stream)); item_offset = (apr_off_t)value; /* Special case: empty pages. */ @@ -2747,17 +2694,15 @@ get_p2l_page(apr_array_header_t **entrie { /* Empty page. This only happens if the first entry of the next page * also covers this page (and possibly more) completely. */ - SVN_ERR(read_entry(rev_file->p2l_stream, &item_offset, start_revision, - result)); + SVN_ERR(read_entry(stream, &item_offset, start_revision, result)); } else { /* Read non-empty page. */ do { - SVN_ERR(read_entry(rev_file->p2l_stream, &item_offset, - start_revision, result)); - offset = packed_stream_offset(rev_file->p2l_stream); + SVN_ERR(read_entry(stream, &item_offset, start_revision, result)); + offset = packed_stream_offset(stream); } while (offset < next_offset); @@ -2771,9 +2716,9 @@ get_p2l_page(apr_array_header_t **entrie * entry of the next page */ if (item_offset < page_start + page_size) { - SVN_ERR(packed_stream_get(&value, rev_file->p2l_stream)); + SVN_ERR(packed_stream_get(&value, stream)); item_offset = (apr_off_t)value; - SVN_ERR(read_entry(rev_file->p2l_stream, &item_offset, + SVN_ERR(read_entry(stream, &item_offset, start_revision, result)); } } @@ -3203,7 +3148,8 @@ svn_fs_x__p2l_index_lookup(apr_array_hea * RHS. */ static int -compare_p2l_entry_offsets(const void *lhs, const void *rhs) +compare_p2l_entry_offsets(const void *lhs, + const void *rhs) { const svn_fs_x__p2l_entry_t *entry = (const svn_fs_x__p2l_entry_t *)lhs; apr_off_t offset = *(const apr_off_t *)rhs; @@ -3503,15 +3449,13 @@ calc_fnv1(svn_fs_x__p2l_entry_t *entry, } /* Read the block and feed it to the checksum calculator. */ - SVN_ERR(svn_io_file_seek(rev_file->file, APR_SET, &entry->offset, - scratch_pool)); + SVN_ERR(svn_fs_x__rev_file_seek(rev_file, NULL, entry->offset)); while (size > 0) { apr_size_t to_read = size > sizeof(buffer) ? sizeof(buffer) : (apr_size_t)size; - SVN_ERR(svn_io_file_read_full2(rev_file->file, buffer, to_read, NULL, - NULL, scratch_pool)); + SVN_ERR(svn_fs_x__rev_file_read(rev_file, buffer, to_read)); SVN_ERR(svn_checksum_update(context, buffer, to_read)); size -= to_read; } @@ -3795,7 +3739,7 @@ svn_error_t * svn_fs_x__deserialize_l2p_header(void **out, void *data, apr_size_t data_len, - apr_pool_t *pool) + apr_pool_t *result_pool) { l2p_header_t *header = (l2p_header_t *)data; @@ -3849,7 +3793,7 @@ svn_error_t * svn_fs_x__deserialize_l2p_page(void **out, void *data, apr_size_t data_len, - apr_pool_t *pool) + apr_pool_t *result_pool) { l2p_page_t *page = data; @@ -3898,7 +3842,7 @@ svn_error_t * svn_fs_x__deserialize_p2l_header(void **out, void *data, apr_size_t data_len, - apr_pool_t *pool) + apr_pool_t *result_pool) { p2l_header_t *header = data; @@ -3956,7 +3900,7 @@ svn_error_t * svn_fs_x__deserialize_p2l_page(void **out, void *data, apr_size_t data_len, - apr_pool_t *pool) + apr_pool_t *result_pool) { apr_array_header_t *page = (apr_array_header_t *)data; svn_fs_x__p2l_entry_t *entries; @@ -3971,7 +3915,7 @@ svn_fs_x__deserialize_p2l_page(void **ou svn_temp_deserializer__resolve(entries, (void**)&entries[i].items); /* patch up members */ - page->pool = pool; + page->pool = result_pool; page->nalloc = page->nelts; /* done */ Modified: subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/index.h URL: http://svn.apache.org/viewvc/subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/index.h?rev=1702504&r1=1702503&r2=1702504&view=diff ============================================================================== --- subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/index.h (original) +++ subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/index.h Fri Sep 11 15:51:30 2015 @@ -20,8 +20,8 @@ * ==================================================================== */ -#ifndef SVN_LIBSVN_FS__INDEX_H -#define SVN_LIBSVN_FS__INDEX_H +#ifndef SVN_LIBSVN_FS_X_INDEX_H +#define SVN_LIBSVN_FS_X_INDEX_H #include "fs.h" #include "rev_file.h" @@ -53,6 +53,28 @@ #define SVN_FS_X__ITEM_TYPE_REPS_CONT 10 /* item is a representations container */ +/* We put this string in front of the L2P index header. */ +#define SVN_FS_X__L2P_STREAM_PREFIX "L2P-INDEX\n" + +/* We put this string in front of the P2L index header. */ +#define SVN_FS_X__P2L_STREAM_PREFIX "P2L-INDEX\n" + + +/* Create and open a packed number stream reading from offsets START to + * END in FILE and return it in *STREAM. Access the file in chunks of + * BLOCK_SIZE bytes. Expect the stream to be prefixed by STREAM_PREFIX. + * Allocate *STREAM in RESULT_POOL and use SCRATCH_POOL for temporaries. + */ +svn_error_t * +svn_fs_x__packed_stream_open(svn_fs_x__packed_number_stream_t **stream, + apr_file_t *file, + apr_off_t start, + apr_off_t end, + const char *stream_prefix, + apr_size_t block_size, + apr_pool_t *result_pool, + apr_pool_t *scratch_pool); + /* (user visible) entry in the phys-to-log index. It describes a section * of some packed / non-packed rev file as containing a specific item. * There must be no overlapping / conflicting entries. @@ -350,7 +372,7 @@ svn_error_t * svn_fs_x__deserialize_l2p_header(void **out, void *data, apr_size_t data_len, - apr_pool_t *pool); + apr_pool_t *result_pool); /* * Implements svn_cache__serialize_func_t for l2p_page_t objects. @@ -368,7 +390,7 @@ svn_error_t * svn_fs_x__deserialize_l2p_page(void **out, void *data, apr_size_t data_len, - apr_pool_t *pool); + apr_pool_t *result_pool); /* * Implements svn_cache__serialize_func_t for p2l_header_t objects. @@ -386,7 +408,7 @@ svn_error_t * svn_fs_x__deserialize_p2l_header(void **out, void *data, apr_size_t data_len, - apr_pool_t *pool); + apr_pool_t *result_pool); /* * Implements svn_cache__serialize_func_t for apr_array_header_t objects @@ -406,6 +428,6 @@ svn_error_t * svn_fs_x__deserialize_p2l_page(void **out, void *data, apr_size_t data_len, - apr_pool_t *pool); + apr_pool_t *result_pool); #endif Modified: subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/lock.c URL: http://svn.apache.org/viewvc/subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/lock.c?rev=1702504&r1=1702503&r2=1702504&view=diff ============================================================================== --- subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/lock.c (original) +++ subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/lock.c Fri Sep 11 15:51:30 2015 @@ -113,7 +113,8 @@ hash_fetch(apr_hash_t *hash, /* SVN_ERR_FS_CORRUPT: the lockfile for PATH in FS is corrupt. */ static svn_error_t * -err_corrupt_lockfile(const char *fs_path, const char *path) +err_corrupt_lockfile(const char *fs_path, + const char *path) { return svn_error_createf( @@ -243,7 +244,7 @@ write_digest_file(apr_hash_t *children, } SVN_ERR(svn_stream_close(stream)); - SVN_ERR(svn_io_file_rename(tmp_path, digest_path, scratch_pool)); + SVN_ERR(svn_io_file_rename2(tmp_path, digest_path, FALSE, scratch_pool)); SVN_ERR(svn_io_copy_perms(perms_reference, digest_path, scratch_pool)); return SVN_NO_ERROR; } @@ -854,7 +855,8 @@ typedef struct lock_info_t { type, and assumes that the write lock is held. */ static svn_error_t * -lock_body(void *baton, apr_pool_t *pool) +lock_body(void *baton, + apr_pool_t *pool) { lock_baton_t *lb = baton; svn_fs_root_t *root; @@ -1005,7 +1007,8 @@ typedef struct unlock_info_t { type, and assumes that the write lock is held. */ static svn_error_t * -unlock_body(void *baton, apr_pool_t *pool) +unlock_body(void *baton, + apr_pool_t *pool) { unlock_baton_t *ub = baton; svn_fs_root_t *root; Modified: subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/lock.h URL: http://svn.apache.org/viewvc/subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/lock.h?rev=1702504&r1=1702503&r2=1702504&view=diff ============================================================================== --- subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/lock.h (original) +++ subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/lock.h Fri Sep 11 15:51:30 2015 @@ -20,8 +20,8 @@ * ==================================================================== */ -#ifndef SVN_LIBSVN_FS_LOCK_H -#define SVN_LIBSVN_FS_LOCK_H +#ifndef SVN_LIBSVN_FS_X_LOCK_H +#define SVN_LIBSVN_FS_X_LOCK_H #ifdef __cplusplus extern "C" { @@ -113,4 +113,4 @@ svn_fs_x__allow_locked_operation(const c } #endif /* __cplusplus */ -#endif /* SVN_LIBSVN_FS_LOCK_H */ +#endif /* SVN_LIBSVN_FS_X_LOCK_H */ Modified: subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/low_level.c URL: http://svn.apache.org/viewvc/subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/low_level.c?rev=1702504&r1=1702503&r2=1702504&view=diff ============================================================================== --- subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/low_level.c (original) +++ subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/low_level.c Fri Sep 11 15:51:30 2015 @@ -1,4 +1,4 @@ -/* low_level.c --- low level r/w access to fs_x file structures +/* low_level.c --- low level r/w access to FSX file structures * * ==================================================================== * Licensed to the Apache Software Foundation (ASF) under one @@ -56,7 +56,6 @@ #define ACTION_ADD "add" #define ACTION_DELETE "delete" #define ACTION_REPLACE "replace" -#define ACTION_RESET "reset" /* True and False flags. */ #define FLAG_TRUE "true" @@ -845,10 +844,6 @@ read_change(svn_fs_x__change_t **change_ { change->change_kind = svn_fs_path_change_replace; } - else if (strcmp(str, ACTION_RESET) == 0) - { - change->change_kind = svn_fs_path_change_reset; - } else { return svn_error_create(SVN_ERR_FS_CORRUPT, NULL, @@ -1036,9 +1031,6 @@ write_change_entry(svn_stream_t *stream, case svn_fs_path_change_replace: change_string = ACTION_REPLACE; break; - case svn_fs_path_change_reset: - change_string = ACTION_RESET; - break; default: return svn_error_createf(SVN_ERR_FS_CORRUPT, NULL, _("Invalid change type %d"), Modified: subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/low_level.h URL: http://svn.apache.org/viewvc/subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/low_level.h?rev=1702504&r1=1702503&r2=1702504&view=diff ============================================================================== --- subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/low_level.h (original) +++ subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/low_level.h Fri Sep 11 15:51:30 2015 @@ -1,4 +1,4 @@ -/* low_level.c --- low level r/w access to fs_x file structures +/* low_level.c --- low level r/w access to FSX file structures * * ==================================================================== * Licensed to the Apache Software Foundation (ASF) under one @@ -20,8 +20,8 @@ * ==================================================================== */ -#ifndef SVN_LIBSVN_FS__LOW_LEVEL_H -#define SVN_LIBSVN_FS__LOW_LEVEL_H +#ifndef SVN_LIBSVN_FS_X_LOW_LEVEL_H +#define SVN_LIBSVN_FS_X_LOW_LEVEL_H #include "svn_fs.h" @@ -211,4 +211,4 @@ svn_fs_x__write_changes(svn_stream_t *st } #endif /* __cplusplus */ -#endif /* SVN_LIBSVN_FS__LOW_LEVEL_H */ +#endif /* SVN_LIBSVN_FS_X_LOW_LEVEL_H */ Modified: subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/noderevs.c URL: http://svn.apache.org/viewvc/subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/noderevs.c?rev=1702504&r1=1702503&r2=1702504&view=diff ============================================================================== --- subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/noderevs.c (original) +++ subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/noderevs.c Fri Sep 11 15:51:30 2015 @@ -361,7 +361,7 @@ svn_error_t * svn_fs_x__noderevs_get(svn_fs_x__noderev_t **noderev_p, const svn_fs_x__noderevs_t *container, apr_size_t idx, - apr_pool_t *pool) + apr_pool_t *result_pool) { svn_fs_x__noderev_t *noderev; binary_noderev_t *binary_noderev; @@ -373,14 +373,14 @@ svn_fs_x__noderevs_get(svn_fs_x__noderev /* validate index */ if (idx >= (apr_size_t)container->noderevs->nelts) return svn_error_createf(SVN_ERR_FS_CONTAINER_INDEX, NULL, - apr_psprintf(pool, + apr_psprintf(result_pool, _("Node revision index %%%s" " exceeds container size %%d"), APR_SIZE_T_FMT), idx, container->noderevs->nelts); /* allocate result struct and fill it field by field */ - noderev = apr_pcalloc(pool, sizeof(*noderev)); + noderev = apr_pcalloc(result_pool, sizeof(*noderev)); binary_noderev = &APR_ARRAY_IDX(container->noderevs, idx, binary_noderev_t); noderev->kind = (svn_node_kind_t)(binary_noderev->flags & NODEREV_KIND_MASK); @@ -398,7 +398,7 @@ svn_fs_x__noderevs_get(svn_fs_x__noderev = svn_fs_x__string_table_get(container->paths, binary_noderev->copyfrom_path, NULL, - pool); + result_pool); noderev->copyfrom_rev = binary_noderev->copyfrom_rev; } else @@ -413,7 +413,7 @@ svn_fs_x__noderevs_get(svn_fs_x__noderev = svn_fs_x__string_table_get(container->paths, binary_noderev->copyroot_path, NULL, - pool); + result_pool); noderev->copyroot_rev = binary_noderev->copyroot_rev; } else @@ -425,16 +425,16 @@ svn_fs_x__noderevs_get(svn_fs_x__noderev noderev->predecessor_count = binary_noderev->predecessor_count; SVN_ERR(get_representation(&noderev->prop_rep, container->reps, - binary_noderev->prop_rep, pool)); + binary_noderev->prop_rep, result_pool)); SVN_ERR(get_representation(&noderev->data_rep, container->reps, - binary_noderev->data_rep, pool)); + binary_noderev->data_rep, result_pool)); if (binary_noderev->flags & NODEREV_HAS_CPATH) noderev->created_path = svn_fs_x__string_table_get(container->paths, binary_noderev->created_path, NULL, - pool); + result_pool); noderev->mergeinfo_count = binary_noderev->mergeinfo_count; @@ -578,15 +578,15 @@ svn_fs_x__write_noderevs_container(svn_s return SVN_NO_ERROR; } -/* Allocate a svn_fs_x__representation_t array in POOL and return it in - * REPS_P. Deserialize the data in REP_STREAM and DIGEST_STREAM and store +/* Allocate a svn_fs_x__representation_t array in RESULT_POOL and return it + * in REPS_P. Deserialize the data in REP_STREAM and DIGEST_STREAM and store * the resulting representations into the *REPS_P. */ static svn_error_t * read_reps(apr_array_header_t **reps_p, svn_packed__int_stream_t *rep_stream, svn_packed__byte_stream_t *digest_stream, - apr_pool_t *pool) + apr_pool_t *result_pool) { apr_size_t i; apr_size_t len; @@ -595,7 +595,8 @@ read_reps(apr_array_header_t **reps_p, apr_size_t count = svn_packed__int_count(svn_packed__first_int_substream(rep_stream)); apr_array_header_t *reps - = apr_array_make(pool, (int)count, sizeof(svn_fs_x__representation_t)); + = apr_array_make(result_pool, (int)count, + sizeof(svn_fs_x__representation_t)); for (i = 0; i < count; ++i) { @@ -613,7 +614,7 @@ read_reps(apr_array_header_t **reps_p, bytes = svn_packed__get_bytes(digest_stream, &len); if (len != sizeof(rep.md5_digest)) return svn_error_createf(SVN_ERR_FS_CONTAINER_INDEX, NULL, - apr_psprintf(pool, + apr_psprintf(result_pool, _("Unexpected MD5" " digest size %%%s"), APR_SIZE_T_FMT), @@ -625,7 +626,7 @@ read_reps(apr_array_header_t **reps_p, bytes = svn_packed__get_bytes(digest_stream, &len); if (len != sizeof(rep.sha1_digest)) return svn_error_createf(SVN_ERR_FS_CONTAINER_INDEX, NULL, - apr_psprintf(pool, + apr_psprintf(result_pool, _("Unexpected SHA1" " digest size %%%s"), APR_SIZE_T_FMT), @@ -766,15 +767,15 @@ svn_error_t * svn_fs_x__deserialize_noderevs_container(void **out, void *data, apr_size_t data_len, - apr_pool_t *pool) + apr_pool_t *result_pool) { svn_fs_x__noderevs_t *noderevs = (svn_fs_x__noderevs_t *)data; /* de-serialize sub-structures */ svn_fs_x__deserialize_string_table(noderevs, &noderevs->paths); - svn_fs_x__deserialize_apr_array(noderevs, &noderevs->ids, pool); - svn_fs_x__deserialize_apr_array(noderevs, &noderevs->reps, pool); - svn_fs_x__deserialize_apr_array(noderevs, &noderevs->noderevs, pool); + svn_fs_x__deserialize_apr_array(noderevs, &noderevs->ids, result_pool); + svn_fs_x__deserialize_apr_array(noderevs, &noderevs->reps, result_pool); + svn_fs_x__deserialize_apr_array(noderevs, &noderevs->noderevs, result_pool); /* done */ *out = noderevs; Modified: subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/noderevs.h URL: http://svn.apache.org/viewvc/subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/noderevs.h?rev=1702504&r1=1702503&r2=1702504&view=diff ============================================================================== --- subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/noderevs.h (original) +++ subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/noderevs.h Fri Sep 11 15:51:30 2015 @@ -20,8 +20,8 @@ * ==================================================================== */ -#ifndef SVN_LIBSVN_FS__NODEREVS_H -#define SVN_LIBSVN_FS__NODEREVS_H +#ifndef SVN_LIBSVN_FS_X_NODEREVS_H +#define SVN_LIBSVN_FS_X_NODEREVS_H #include "svn_io.h" #include "fs.h" @@ -76,7 +76,7 @@ svn_error_t * svn_fs_x__noderevs_get(svn_fs_x__noderev_t **noderev_p, const svn_fs_x__noderevs_t *container, apr_size_t idx, - apr_pool_t *pool); + apr_pool_t *result_pool); /* I/O interface. */ @@ -114,7 +114,7 @@ svn_error_t * svn_fs_x__deserialize_noderevs_container(void **out, void *data, apr_size_t data_len, - apr_pool_t *pool); + apr_pool_t *result_pool); /* Implements svn_cache__partial_getter_func_t for svn_fs_x__noderevs_t, * setting *OUT to the svn_fs_x__noderev_t selected by the apr_uint32_t index Modified: subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/pack.c URL: http://svn.apache.org/viewvc/subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/pack.c?rev=1702504&r1=1702503&r2=1702504&view=diff ============================================================================== --- subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/pack.c (original) +++ subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/pack.c Fri Sep 11 15:51:30 2015 @@ -478,6 +478,7 @@ copy_item_to_temp(pack_context_t *contex svn_fs_x__p2l_entry_t *entry, apr_pool_t *scratch_pool) { + apr_file_t *file; svn_fs_x__p2l_entry_t *new_entry = svn_fs_x__p2l_entry_dup(entry, context->info_pool); @@ -485,7 +486,8 @@ copy_item_to_temp(pack_context_t *contex scratch_pool)); APR_ARRAY_PUSH(entries, svn_fs_x__p2l_entry_t *) = new_entry; - SVN_ERR(copy_file_data(context, temp_file, rev_file->file, entry->size, + SVN_ERR(svn_fs_x__rev_file_get(&file, rev_file)); + SVN_ERR(copy_file_data(context, temp_file, file, entry->size, scratch_pool)); return SVN_NO_ERROR; @@ -567,6 +569,8 @@ copy_rep_to_temp(pack_context_t *context apr_pool_t *scratch_pool) { svn_fs_x__rep_header_t *rep_header; + svn_stream_t *stream; + apr_file_t *file; apr_off_t source_offset = entry->offset; /* create a copy of ENTRY, make it point to the copy destination and @@ -577,7 +581,8 @@ copy_rep_to_temp(pack_context_t *context add_item_rep_mapping(context, entry); /* read & parse the representation header */ - SVN_ERR(svn_fs_x__read_rep_header(&rep_header, rev_file->stream, + SVN_ERR(svn_fs_x__rev_file_stream(&stream, rev_file)); + SVN_ERR(svn_fs_x__read_rep_header(&rep_header, stream, scratch_pool, scratch_pool)); /* if the representation is a delta against some other rep, link the two */ @@ -594,10 +599,10 @@ copy_rep_to_temp(pack_context_t *context } /* copy the whole rep (including header!) to our temp file */ - SVN_ERR(svn_io_file_seek(rev_file->file, APR_SET, &source_offset, - scratch_pool)); - SVN_ERR(copy_file_data(context, context->reps_file, rev_file->file, - entry->size, scratch_pool)); + SVN_ERR(svn_fs_x__rev_file_seek(rev_file, NULL, source_offset)); + SVN_ERR(svn_fs_x__rev_file_get(&file, rev_file)); + SVN_ERR(copy_file_data(context, context->reps_file, file, entry->size, + scratch_pool)); return SVN_NO_ERROR; } @@ -687,25 +692,28 @@ copy_node_to_temp(pack_context_t *contex path_order_t *path_order = apr_pcalloc(context->info_pool, sizeof(*path_order)); svn_fs_x__noderev_t *noderev; + svn_stream_t *stream; + apr_file_t *file; const char *sort_path; apr_off_t source_offset = entry->offset; /* read & parse noderev */ - SVN_ERR(svn_fs_x__read_noderev(&noderev, rev_file->stream, scratch_pool, + SVN_ERR(svn_fs_x__rev_file_stream(&stream, rev_file)); + SVN_ERR(svn_fs_x__read_noderev(&noderev, stream, scratch_pool, scratch_pool)); /* create a copy of ENTRY, make it point to the copy destination and * store it in CONTEXT */ entry = svn_fs_x__p2l_entry_dup(entry, context->info_pool); SVN_ERR(svn_fs_x__get_file_offset(&entry->offset, context->reps_file, - scratch_pool)); + scratch_pool)); add_item_rep_mapping(context, entry); /* copy the noderev to our temp file */ - SVN_ERR(svn_io_file_seek(rev_file->file, APR_SET, &source_offset, - scratch_pool)); - SVN_ERR(copy_file_data(context, context->reps_file, rev_file->file, - entry->size, scratch_pool)); + SVN_ERR(svn_fs_x__rev_file_seek(rev_file, NULL, source_offset)); + SVN_ERR(svn_fs_x__rev_file_get(&file, rev_file)); + SVN_ERR(copy_file_data(context, context->reps_file, file, entry->size, + scratch_pool)); /* if the node has a data representation, make that the node's "base". * This will (often) cause the noderev to be placed right in front of @@ -1234,7 +1242,7 @@ write_reps_containers(pack_context_t *co = apr_array_make(scratch_pool, 64, sizeof(svn_fs_x__id_t)); svn_fs_x__revision_file_t *file; - SVN_ERR(svn_fs_x__wrap_temp_rev_file(&file, context->fs, temp_file, + SVN_ERR(svn_fs_x__rev_file_wrap_temp(&file, context->fs, temp_file, scratch_pool)); /* copy all items in strict order */ @@ -1723,18 +1731,19 @@ pack_range(pack_context_t *context, { apr_off_t offset = 0; svn_fs_x__revision_file_t *rev_file; + svn_fs_x__index_info_t l2p_index_info; /* Get the rev file dimensions (mainly index locations). */ - SVN_ERR(svn_fs_x__open_pack_or_rev_file(&rev_file, context->fs, - revision, revpool, iterpool)); - SVN_ERR(svn_fs_x__auto_read_footer(rev_file)); + SVN_ERR(svn_fs_x__rev_file_init(&rev_file, context->fs, revision, + revpool)); + SVN_ERR(svn_fs_x__rev_file_l2p_info(&l2p_index_info, rev_file)); /* store the indirect array index */ APR_ARRAY_PUSH(context->rev_offsets, int) = context->reps->nelts; /* read the phys-to-log index file until we covered the whole rev file. * That index contains enough info to build both target indexes from it. */ - while (offset < rev_file->l2p_offset) + while (offset < l2p_index_info.start) { /* read one cluster */ int i; @@ -1758,10 +1767,9 @@ pack_range(pack_context_t *context, /* process entry while inside the rev file */ offset = entry->offset; - if (offset < rev_file->l2p_offset) + if (offset < l2p_index_info.start) { - SVN_ERR(svn_io_file_seek(rev_file->file, APR_SET, &offset, - iterpool)); + SVN_ERR(svn_fs_x__rev_file_seek(rev_file, NULL, offset)); if (entry->type == SVN_FS_X__ITEM_TYPE_CHANGES) SVN_ERR(copy_item_to_temp(context, @@ -1843,6 +1851,7 @@ append_revision(pack_context_t *context, apr_off_t offset = 0; apr_pool_t *iterpool = svn_pool_create(scratch_pool); svn_fs_x__revision_file_t *rev_file; + apr_file_t *file; apr_finfo_t finfo; /* Get the size of the file. */ @@ -1853,11 +1862,11 @@ append_revision(pack_context_t *context, SVN_ERR(svn_io_stat(&finfo, path, APR_FINFO_SIZE, scratch_pool)); /* Copy all the bits from the rev file to the end of the pack file. */ - SVN_ERR(svn_fs_x__open_pack_or_rev_file(&rev_file, context->fs, - context->start_rev, scratch_pool, - iterpool)); - SVN_ERR(copy_file_data(context, context->pack_file, rev_file->file, - finfo.size, iterpool)); + SVN_ERR(svn_fs_x__rev_file_init(&rev_file, context->fs, context->start_rev, + scratch_pool)); + SVN_ERR(svn_fs_x__rev_file_get(&file, rev_file)); + SVN_ERR(copy_file_data(context, context->pack_file, file, finfo.size, + iterpool)); /* mark the start of a new revision */ SVN_ERR(svn_fs_x__l2p_proto_index_add_revision(context->proto_l2p_index, @@ -2003,72 +2012,6 @@ pack_log_addressed(svn_fs_t *fs, return SVN_NO_ERROR; } -/* Given REV in FS, set *REV_OFFSET to REV's offset in the packed file. - Use SCRATCH_POOL for temporary allocations. */ -svn_error_t * -svn_fs_x__get_packed_offset(apr_off_t *rev_offset, - svn_fs_t *fs, - svn_revnum_t rev, - apr_pool_t *scratch_pool) -{ - svn_fs_x__data_t *ffd = fs->fsap_data; - svn_stream_t *manifest_stream; - svn_boolean_t is_cached; - svn_revnum_t shard; - apr_int64_t shard_pos; - apr_array_header_t *manifest; - apr_pool_t *iterpool; - - shard = rev / ffd->max_files_per_dir; - - /* position of the shard within the manifest */ - shard_pos = rev % ffd->max_files_per_dir; - - /* fetch exactly that element into *rev_offset, if the manifest is found - in the cache */ - SVN_ERR(svn_cache__get_partial((void **) rev_offset, &is_cached, - ffd->packed_offset_cache, &shard, - svn_fs_x__get_sharded_offset, &shard_pos, - scratch_pool)); - - if (is_cached) - return SVN_NO_ERROR; - - /* Open the manifest file. */ - SVN_ERR(svn_stream_open_readonly(&manifest_stream, - svn_fs_x__path_rev_packed(fs, rev, PATH_MANIFEST, - scratch_pool), - scratch_pool, scratch_pool)); - - /* While we're here, let's just read the entire manifest file into an array, - so we can cache the entire thing. */ - iterpool = svn_pool_create(scratch_pool); - manifest = apr_array_make(scratch_pool, ffd->max_files_per_dir, - sizeof(apr_off_t)); - while (1) - { - svn_boolean_t eof; - apr_int64_t val; - - svn_pool_clear(iterpool); - SVN_ERR(svn_fs_x__read_number_from_stream(&val, &eof, manifest_stream, - iterpool)); - if (eof) - break; - - APR_ARRAY_PUSH(manifest, apr_off_t) = (apr_off_t)val; - } - svn_pool_destroy(iterpool); - - *rev_offset = APR_ARRAY_IDX(manifest, rev % ffd->max_files_per_dir, - apr_off_t); - - /* Close up shop and cache the array. */ - SVN_ERR(svn_stream_close(manifest_stream)); - return svn_cache__set(ffd->packed_offset_cache, &shard, manifest, - scratch_pool); -} - /* In filesystem FS, pack the revision SHARD containing exactly * MAX_FILES_PER_DIR revisions from SHARD_PATH into the PACK_FILE_DIR, * using SCRATCH_POOL for temporary allocations. Try to limit the amount of @@ -2115,11 +2058,9 @@ pack_rev_shard(svn_fs_t *fs, return SVN_NO_ERROR; } -/* In the file system at FS_PATH, pack the SHARD in REVS_DIR and - * REVPROPS_DIR containing exactly MAX_FILES_PER_DIR revisions, using - * SCRATCH_POOL temporary for allocations. REVPROPS_DIR will be NULL if - * revprop packing is not supported. COMPRESSION_LEVEL and MAX_PACK_SIZE - * will be ignored in that case. +/* In the file system at FS_PATH, pack the SHARD in DIR containing exactly + * MAX_FILES_PER_DIR revisions, using SCRATCH_POOL temporary for allocations. + * COMPRESSION_LEVEL and MAX_PACK_SIZE will be ignored in that case. * * CANCEL_FUNC and CANCEL_BATON are what you think they are; similarly * NOTIFY_FUNC and NOTIFY_BATON. @@ -2128,8 +2069,7 @@ pack_rev_shard(svn_fs_t *fs, * remove the pack file and start again. */ static svn_error_t * -pack_shard(const char *revs_dir, - const char *revsprops_dir, +pack_shard(const char *dir, svn_fs_t *fs, apr_int64_t shard, int max_files_per_dir, @@ -2151,12 +2091,12 @@ pack_shard(const char *revs_dir, scratch_pool)); /* Some useful paths. */ - rev_pack_file_dir = svn_dirent_join(revs_dir, + rev_pack_file_dir = svn_dirent_join(dir, apr_psprintf(scratch_pool, "%" APR_INT64_T_FMT PATH_EXT_PACKED_SHARD, shard), scratch_pool); - rev_shard_path = svn_dirent_join(revs_dir, + rev_shard_path = svn_dirent_join(dir, apr_psprintf(scratch_pool, "%" APR_INT64_T_FMT, shard), scratch_pool); @@ -2165,26 +2105,24 @@ pack_shard(const char *revs_dir, shard, max_files_per_dir, DEFAULT_MAX_MEM, cancel_func, cancel_baton, scratch_pool)); - /* if enabled, pack the revprops in an equivalent way */ - if (revsprops_dir) - { - revprops_pack_file_dir = svn_dirent_join(revsprops_dir, - apr_psprintf(scratch_pool, - "%" APR_INT64_T_FMT PATH_EXT_PACKED_SHARD, - shard), - scratch_pool); - revprops_shard_path = svn_dirent_join(revsprops_dir, - apr_psprintf(scratch_pool, "%" APR_INT64_T_FMT, shard), - scratch_pool); - - SVN_ERR(svn_fs_x__pack_revprops_shard(revprops_pack_file_dir, - revprops_shard_path, - shard, max_files_per_dir, - (int)(0.9 * max_pack_size), - compression_level, - cancel_func, cancel_baton, - scratch_pool)); - } + /* pack the revprops in an equivalent way */ + revprops_pack_file_dir = svn_dirent_join(dir, + apr_psprintf(scratch_pool, + "%" APR_INT64_T_FMT PATH_EXT_PACKED_SHARD, + shard), + scratch_pool); + revprops_shard_path = svn_dirent_join(dir, + apr_psprintf(scratch_pool, "%" APR_INT64_T_FMT, shard), + scratch_pool); + + SVN_ERR(svn_fs_x__pack_revprops_shard(fs, + revprops_pack_file_dir, + revprops_shard_path, + shard, max_files_per_dir, + (int)(0.9 * max_pack_size), + compression_level, + cancel_func, cancel_baton, + scratch_pool)); /* Update the min-unpacked-rev file to reflect our newly packed shard. */ SVN_ERR(svn_fs_x__write_min_unpacked_rev(fs, @@ -2192,35 +2130,9 @@ pack_shard(const char *revs_dir, scratch_pool)); ffd->min_unpacked_rev = (svn_revnum_t)((shard + 1) * max_files_per_dir); - /* Finally, remove the existing shard directories. - * For revprops, clean up older obsolete shards as well as they might - * have been left over from an interrupted FS upgrade. */ + /* Finally, remove the existing shard directories. */ SVN_ERR(svn_io_remove_dir2(rev_shard_path, TRUE, cancel_func, cancel_baton, scratch_pool)); - if (revsprops_dir) - { - svn_node_kind_t kind = svn_node_dir; - apr_int64_t to_cleanup = shard; - do - { - SVN_ERR(svn_fs_x__delete_revprops_shard(revprops_shard_path, - to_cleanup, - max_files_per_dir, - cancel_func, cancel_baton, - scratch_pool)); - - /* If the previous shard exists, clean it up as well. - Don't try to clean up shard 0 as it we can't tell quickly - whether it actually needs cleaning up. */ - revprops_shard_path = svn_dirent_join(revsprops_dir, - apr_psprintf(scratch_pool, - "%" APR_INT64_T_FMT, - --to_cleanup), - scratch_pool); - SVN_ERR(svn_io_check_path(revprops_shard_path, &kind, scratch_pool)); - } - while (kind == svn_node_dir && to_cleanup > 0); - } /* Notify caller we're starting to pack this shard. */ if (notify_func) @@ -2264,8 +2176,7 @@ pack_body(void *baton, apr_int64_t i; svn_revnum_t youngest; apr_pool_t *iterpool; - const char *rev_data_path; - const char *revprops_data_path = NULL; + const char *data_path; /* If we aren't using sharding, we can't do any packing, so quit. */ SVN_ERR(svn_fs_x__read_min_unpacked_rev(&ffd->min_unpacked_rev, pb->fs, @@ -2278,9 +2189,7 @@ pack_body(void *baton, if (ffd->min_unpacked_rev == (completed_shards * ffd->max_files_per_dir)) return SVN_NO_ERROR; - rev_data_path = svn_dirent_join(pb->fs->path, PATH_REVS_DIR, scratch_pool); - revprops_data_path = svn_dirent_join(pb->fs->path, PATH_REVPROPS_DIR, - scratch_pool); + data_path = svn_dirent_join(pb->fs->path, PATH_REVS_DIR, scratch_pool); iterpool = svn_pool_create(scratch_pool); for (i = ffd->min_unpacked_rev / ffd->max_files_per_dir; @@ -2292,7 +2201,7 @@ pack_body(void *baton, if (pb->cancel_func) SVN_ERR(pb->cancel_func(pb->cancel_baton)); - SVN_ERR(pack_shard(rev_data_path, revprops_data_path, + SVN_ERR(pack_shard(data_path, pb->fs, i, ffd->max_files_per_dir, ffd->revprop_pack_size, ffd->compress_packed_revprops Modified: subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/pack.h URL: http://svn.apache.org/viewvc/subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/pack.h?rev=1702504&r1=1702503&r2=1702504&view=diff ============================================================================== --- subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/pack.h (original) +++ subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/pack.h Fri Sep 11 15:51:30 2015 @@ -20,8 +20,8 @@ * ==================================================================== */ -#ifndef SVN_LIBSVN_FS__PACK_H -#define SVN_LIBSVN_FS__PACK_H +#ifndef SVN_LIBSVN_FS_X_PACK_H +#define SVN_LIBSVN_FS_X_PACK_H #include "fs.h" @@ -39,17 +39,6 @@ svn_fs_x__pack(svn_fs_t *fs, void *cancel_baton, apr_pool_t *scratch_pool); -/** - * For the packed revision REV in FS, determine the offset within the - * revision pack file and return it in REV_OFFSET. - * Use SCRATCH_POOL for temporary allocations. - */ -svn_error_t * -svn_fs_x__get_packed_offset(apr_off_t *rev_offset, - svn_fs_t *fs, - svn_revnum_t rev, - apr_pool_t *scratch_pool); - /* Return the svn_dir_entry_t* objects of DIRECTORY in an APR array * allocated in RESULT_POOL with entries added in storage (on-disk) order. * FS' format will be used to pick the optimal ordering strategy. Use Modified: subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/recovery.c URL: http://svn.apache.org/viewvc/subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/recovery.c?rev=1702504&r1=1702503&r2=1702504&view=diff ============================================================================== --- subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/recovery.c (original) +++ subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/recovery.c Fri Sep 11 15:51:30 2015 @@ -38,6 +38,22 @@ #include "svn_private_config.h" +/* Set *EXISTS to TRUE, if the revision / pack file for REV exists in FS. + Use SCRATCH_POOL for temporary allocations. */ +static svn_error_t * +revision_file_exists(svn_boolean_t *exists, + svn_fs_t *fs, + svn_revnum_t rev, + apr_pool_t *scratch_pool) +{ + svn_node_kind_t kind; + const char *path = svn_fs_x__path_rev_absolute(fs, rev, scratch_pool); + SVN_ERR(svn_io_check_path(path, &kind, scratch_pool)); + + *exists = kind == svn_node_file; + return SVN_NO_ERROR; +} + /* Part of the recovery procedure. Return the largest revision *REV in filesystem FS. Use SCRATCH_POOL for temporary allocation. */ static svn_error_t * @@ -56,19 +72,12 @@ recover_get_largest_revision(svn_fs_t *f /* Keep doubling right, until we find a revision that doesn't exist. */ while (1) { - svn_error_t *err; - svn_fs_x__revision_file_t *file; + svn_boolean_t exists; svn_pool_clear(iterpool); - err = svn_fs_x__open_pack_or_rev_file(&file, fs, right, iterpool, - iterpool); - if (err && err->apr_err == SVN_ERR_FS_NO_SUCH_REVISION) - { - svn_error_clear(err); - break; - } - else - SVN_ERR(err); + SVN_ERR(revision_file_exists(&exists, fs, right, iterpool)); + if (!exists) + break; right <<= 1; } @@ -80,22 +89,14 @@ recover_get_largest_revision(svn_fs_t *f while (left + 1 < right) { svn_revnum_t probe = left + ((right - left) / 2); - svn_error_t *err; - svn_fs_x__revision_file_t *file; + svn_boolean_t exists; svn_pool_clear(iterpool); - err = svn_fs_x__open_pack_or_rev_file(&file, fs, probe, iterpool, - iterpool); - if (err && err->apr_err == SVN_ERR_FS_NO_SUCH_REVISION) - { - svn_error_clear(err); - right = probe; - } + SVN_ERR(revision_file_exists(&exists, fs, probe, iterpool)); + if (exists) + left = probe; else - { - SVN_ERR(err); - left = probe; - } + right = probe; } svn_pool_destroy(iterpool); Modified: subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/recovery.h URL: http://svn.apache.org/viewvc/subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/recovery.h?rev=1702504&r1=1702503&r2=1702504&view=diff ============================================================================== --- subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/recovery.h (original) +++ subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/recovery.h Fri Sep 11 15:51:30 2015 @@ -20,8 +20,8 @@ * ==================================================================== */ -#ifndef SVN_LIBSVN_FS__RECOVERY_H -#define SVN_LIBSVN_FS__RECOVERY_H +#ifndef SVN_LIBSVN_FS_X_RECOVERY_H +#define SVN_LIBSVN_FS_X_RECOVERY_H #include "fs.h" Modified: subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/reps.c URL: http://svn.apache.org/viewvc/subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/reps.c?rev=1702504&r1=1702503&r2=1702504&view=diff ============================================================================== --- subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/reps.c (original) +++ subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/reps.c Fri Sep 11 15:51:30 2015 @@ -641,16 +641,17 @@ svn_fs_x__reps_get(svn_fs_x__rep_extract svn_fs_t *fs, const svn_fs_x__reps_t *container, apr_size_t idx, - apr_pool_t *pool) + apr_pool_t *result_pool) { apr_uint32_t first = container->first_instructions[idx]; apr_uint32_t last = container->first_instructions[idx + 1]; /* create the extractor object */ - svn_fs_x__rep_extractor_t *result = apr_pcalloc(pool, sizeof(*result)); + svn_fs_x__rep_extractor_t *result = apr_pcalloc(result_pool, + sizeof(*result)); result->fs = fs; - result->result = svn_stringbuf_create_empty(pool); - result->pool = pool; + result->result = svn_stringbuf_create_empty(result_pool); + result->pool = result_pool; /* fill all the bits of the result that we can, i.e. all but bits coming * from base representations */ @@ -900,7 +901,7 @@ svn_error_t * svn_fs_x__deserialize_reps_container(void **out, void *data, apr_size_t data_len, - apr_pool_t *pool) + apr_pool_t *result_pool) { svn_fs_x__reps_t *reps = (svn_fs_x__reps_t *)data; Modified: subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/reps.h URL: http://svn.apache.org/viewvc/subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/reps.h?rev=1702504&r1=1702503&r2=1702504&view=diff ============================================================================== --- subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/reps.h (original) +++ subversion/branches/reuse-ra-session/subversion/libsvn_fs_x/reps.h Fri Sep 11 15:51:30 2015 @@ -20,8 +20,8 @@ * ==================================================================== */ -#ifndef SVN_LIBSVN_FS__REPS_H -#define SVN_LIBSVN_FS__REPS_H +#ifndef SVN_LIBSVN_FS_X_REPS_H +#define SVN_LIBSVN_FS_X_REPS_H #include "svn_io.h" #include "fs.h" @@ -112,14 +112,14 @@ svn_fs_x__reps_estimate_size(const svn_f /* Read from representation containers. */ /* For fulltext IDX in CONTAINER in filesystem FS, create an extract object - * allocated in POOL and return it in *EXTRACTOR. + * allocated in RESULT_POOL and return it in *EXTRACTOR. */ svn_error_t * svn_fs_x__reps_get(svn_fs_x__rep_extractor_t **extractor, svn_fs_t *fs, const svn_fs_x__reps_t *container, apr_size_t idx, - apr_pool_t *pool); + apr_pool_t *result_pool); /* Let the EXTRACTOR object fetch all parts of the desired fulltext and * return the latter in *CONTENTS. If SIZE is not 0, return SIZE bytes @@ -172,7 +172,7 @@ svn_error_t * svn_fs_x__deserialize_reps_container(void **out, void *data, apr_size_t data_len, - apr_pool_t *pool); + apr_pool_t *result_pool); /* Implements svn_cache__partial_getter_func_t for svn_fs_x__reps_t, * setting *OUT to an svn_fs_x__rep_extractor_t object defined by the
