1
0
Fork 0
mirror of https://github.com/git/git.git synced 2024-05-28 08:06:23 +02:00

fast-import: treat SIGUSR1 as a request to access objects early

It can be tedious to wait for a multi-million-revision import.
Unfortunately it is hard to spy on the import because fast-import
works by continuously streaming out objects, without updating the pack
index or refs until a checkpoint command or the end of the stream.

So allow the impatient operator to request checkpoints by sending a
signal, like so:

	killall -USR1 git-fast-import

When receiving such a signal, fast-import would schedule a checkpoint
to take place after the current top-level command (usually a "commit"
or "blob" request) finishes.

Caveats: just like ordinary checkpoint commands, such requests slow
down the import.  Switching to a new pack at a suboptimal moment is
also likely to result in a less dense initial collection of packs.
That's the price.

Signed-off-by: Jonathan Nieder <jrnieder@gmail.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
This commit is contained in:
Jonathan Nieder 2010-11-22 02:16:02 -06:00 committed by Junio C Hamano
parent 03276d94bc
commit dc01f59d21
2 changed files with 47 additions and 1 deletions

View File

@ -1233,6 +1233,13 @@ and lazy loading of subtrees, allows fast-import to efficiently import
projects with 2,000+ branches and 45,114+ files in a very limited
memory footprint (less than 2.7 MiB per active branch).
Signals
-------
Sending *SIGUSR1* to the 'git fast-import' process ends the current
packfile early, simulating a `checkpoint` command. The impatient
operator can use this facility to peek at the objects and refs from an
import in progress, at the cost of some added running time and worse
compression.
Author
------

View File

@ -361,6 +361,9 @@ static uintmax_t next_mark;
static struct strbuf new_data = STRBUF_INIT;
static int seen_data_command;
/* Signal handling */
static volatile sig_atomic_t checkpoint_requested;
static void parse_argv(void);
static void write_branch_report(FILE *rpt, struct branch *b)
@ -500,6 +503,32 @@ static NORETURN void die_nicely(const char *err, va_list params)
exit(128);
}
#ifndef SIGUSR1 /* Windows, for example */
static void set_checkpoint_signal(void)
{
}
#else
static void checkpoint_signal(int signo)
{
checkpoint_requested = 1;
}
static void set_checkpoint_signal(void)
{
struct sigaction sa;
memset(&sa, 0, sizeof(sa));
sa.sa_handler = checkpoint_signal;
sigemptyset(&sa.sa_mask);
sa.sa_flags = SA_RESTART;
sigaction(SIGUSR1, &sa, NULL);
}
#endif
static void alloc_objects(unsigned int cnt)
{
struct object_entry_pool *b;
@ -2689,14 +2718,20 @@ static void parse_reset_branch(void)
unread_command_buf = 1;
}
static void parse_checkpoint(void)
static void checkpoint(void)
{
checkpoint_requested = 0;
if (object_count) {
cycle_packfile();
dump_branches();
dump_tags();
dump_marks();
}
}
static void parse_checkpoint(void)
{
checkpoint_requested = 1;
skip_optional_lf();
}
@ -2953,6 +2988,7 @@ int main(int argc, const char **argv)
prepare_packed_git();
start_packfile();
set_die_routine(die_nicely);
set_checkpoint_signal();
while (read_next_command() != EOF) {
if (!strcmp("blob", command_buf.buf))
parse_new_blob();
@ -2974,6 +3010,9 @@ int main(int argc, const char **argv)
/* ignore non-git options*/;
else
die("Unsupported command: %s", command_buf.buf);
if (checkpoint_requested)
checkpoint();
}
/* argv hasn't been parsed yet, do so */