Skip to content

Commit 1946eb5

Browse files
committed
Merge 'create-empty-bundle'
This was pull request #797 from glhez/master `git bundle create <bundle>` leaks handle the revlist is empty. Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
2 parents 61cbaa3 + bcccbe6 commit 1946eb5

File tree

2 files changed

+24
-21
lines changed

2 files changed

+24
-21
lines changed

bundle.c

Lines changed: 18 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -243,7 +243,7 @@ static int is_tag_in_date_range(struct object *tag, struct rev_info *revs)
243243
}
244244

245245

246-
/* Write the pack data to bundle_fd, then close it if it is > 1. */
246+
/* Write the pack data to bundle_fd */
247247
static int write_pack_data(int bundle_fd, struct rev_info *revs)
248248
{
249249
struct child_process pack_objects = CHILD_PROCESS_INIT;
@@ -256,6 +256,20 @@ static int write_pack_data(int bundle_fd, struct rev_info *revs)
256256
pack_objects.in = -1;
257257
pack_objects.out = bundle_fd;
258258
pack_objects.git_cmd = 1;
259+
260+
/*
261+
* start_command() will close our descriptor if it's >1. Duplicate it
262+
* to avoid surprising the caller.
263+
*/
264+
if (pack_objects.out > 1) {
265+
pack_objects.out = dup(pack_objects.out);
266+
if (pack_objects.out < 0) {
267+
error_errno(_("unable to dup bundle descriptor"));
268+
child_process_clear(&pack_objects);
269+
return -1;
270+
}
271+
}
272+
259273
if (start_command(&pack_objects))
260274
return error(_("Could not spawn pack-objects"));
261275

@@ -421,21 +435,10 @@ int create_bundle(struct bundle_header *header, const char *path,
421435
bundle_to_stdout = !strcmp(path, "-");
422436
if (bundle_to_stdout)
423437
bundle_fd = 1;
424-
else {
438+
else
425439
bundle_fd = hold_lock_file_for_update(&lock, path,
426440
LOCK_DIE_ON_ERROR);
427441

428-
/*
429-
* write_pack_data() will close the fd passed to it,
430-
* but commit_lock_file() will also try to close the
431-
* lockfile's fd. So make a copy of the file
432-
* descriptor to avoid trying to close it twice.
433-
*/
434-
bundle_fd = dup(bundle_fd);
435-
if (bundle_fd < 0)
436-
die_errno("unable to dup file descriptor");
437-
}
438-
439442
/* write signature */
440443
write_or_die(bundle_fd, bundle_signature, strlen(bundle_signature));
441444

@@ -463,22 +466,16 @@ int create_bundle(struct bundle_header *header, const char *path,
463466
goto err;
464467

465468
/* write pack */
466-
if (write_pack_data(bundle_fd, &revs)) {
467-
bundle_fd = -1; /* already closed by the above call */
469+
if (write_pack_data(bundle_fd, &revs))
468470
goto err;
469-
}
470471

471472
if (!bundle_to_stdout) {
472473
if (commit_lock_file(&lock))
473474
die_errno(_("cannot create '%s'"), path);
474475
}
475476
return 0;
476477
err:
477-
if (!bundle_to_stdout) {
478-
if (0 <= bundle_fd)
479-
close(bundle_fd);
480-
rollback_lock_file(&lock);
481-
}
478+
rollback_lock_file(&lock);
482479
return -1;
483480
}
484481

t/t5607-clone-bundle.sh

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -71,4 +71,10 @@ test_expect_success 'prerequisites with an empty commit message' '
7171
git bundle verify bundle
7272
'
7373

74+
test_expect_success 'failed bundle creation does not leave cruft' '
75+
# This fails because the bundle would be empty.
76+
test_must_fail git bundle create fail.bundle master..master &&
77+
test_path_is_missing fail.bundle.lock
78+
'
79+
7480
test_done

0 commit comments

Comments
 (0)