commit d2cdc63664daa5fa39c9a6398c33f3724650bfe9 from: Stefan Sperling date: Wed Mar 18 16:11:32 2020 UTC send pack file download progress information over imsg commit - a6ee240a22bfd91ad970ed354f494e38d9d4280b commit + d2cdc63664daa5fa39c9a6398c33f3724650bfe9 blob - a3cf2526d4ee1971e59ae8f61e78f60326046405 blob + e4bbfb0c494e0df6e355a7bcc31c0af2d86a4b07 --- got/got.c +++ got/got.c @@ -38,6 +38,7 @@ #include #include #include +#include #include "got_version.h" #include "got_error.h" @@ -969,10 +970,18 @@ done: } static const struct got_error * -fetch_progress(void *arg, const char *message) +fetch_progress(void *arg, const char *message, off_t packfile_size) { - char *servername = arg; - printf("\rserver %s: %s", servername, message); + int *did_something = arg; + char scaled[FMT_SCALED_STRSIZE]; + + if (message) { + printf("\rserver: %s", message); + *did_something = 1; + } else if (packfile_size > 0 && fmt_scaled(packfile_size, scaled) == 0) { + printf("\rfetching... %*s", FMT_SCALED_STRSIZE, scaled); + *did_something = 1; + } fflush(stdout); return NULL; } @@ -990,6 +999,7 @@ cmd_clone(int argc, char *argv[]) struct got_pathlist_entry *pe; struct got_object_id *pack_hash = NULL; int ch, fetchfd = -1; + int did_something = 0; TAILQ_INIT(&refs); TAILQ_INIT(&symrefs); @@ -1045,9 +1055,11 @@ cmd_clone(int argc, char *argv[]) goto done; err = got_fetch_pack(&pack_hash, &refs, &symrefs, fetchfd, - repo, fetch_progress, host); + repo, fetch_progress, &did_something); if (err) goto done; + if (did_something) + printf("\n"); err = got_object_id_str(&id_str, pack_hash); if (err) blob - e3e0144058ef5d5342ddef6dc9a0edd935474201 blob + 773e689afb160f0428740fef229371814d293eb0 --- include/got_fetch.h +++ include/got_fetch.h @@ -40,7 +40,7 @@ const struct got_error *got_fetch_connect(int *, const /* A callback function which gets invoked with progress information to print. */ typedef const struct got_error *(*got_fetch_progress_cb)(void *, - const char *); + const char *, off_t); /* * Attempt to fetch a packfile from a server. This pack file will contain blob - 15ecb2be5c719d2c618a30756def530640a9dad7 blob + 4936c368b72d20f0700da9ef791558f5eeb7ef03 --- lib/fetch.c +++ lib/fetch.c @@ -313,6 +313,7 @@ got_fetch_pack(struct got_object_id **pack_hash, struc const char *repo_path = got_repo_get_path(repo); struct got_pathlist_head have_refs; struct got_pathlist_entry *pe; + off_t packfile_size = 0; char *path; *pack_hash = NULL; @@ -385,13 +386,16 @@ got_fetch_pack(struct got_object_id **pack_hash, struc goto done; } + packfile_size = 0; while (!done) { struct got_object_id *id = NULL; char *refname = NULL; char *server_progress = NULL; + off_t packfile_size_cur; err = got_privsep_recv_fetch_progress(&done, - &id, &refname, symrefs, &server_progress, &ibuf); + &id, &refname, symrefs, &server_progress, + &packfile_size_cur, &ibuf); if (err != NULL) goto done; if (done) @@ -405,13 +409,19 @@ got_fetch_pack(struct got_object_id **pack_hash, struc while ((s = strsep(&s0, "\r")) != NULL) { if (*s == '\0') continue; - err = progress_cb(progress_arg, s); + err = progress_cb(progress_arg, s, 0); if (err) break; } free(server_progress); if (err) goto done; + } else if (packfile_size_cur != packfile_size) { + err = progress_cb(progress_arg, NULL, + packfile_size_cur); + if (err) + break; + packfile_size = packfile_size_cur; } } if (waitpid(pid, &status, 0) == -1) { blob - 5b5d6f6c9f80056a8ccc1e8fdc9b798eff0f2dc8 blob + c557473418f6733044e922f4df08164429fe995f --- lib/got_lib_privsep.h +++ lib/got_lib_privsep.h @@ -113,6 +113,7 @@ enum got_imsg_type { GOT_IMSG_FETCH_SYMREFS, GOT_IMSG_FETCH_REF, GOT_IMSG_FETCH_SERVER_PROGRESS, + GOT_IMSG_FETCH_DOWNLOAD_PROGRESS, GOT_IMSG_FETCH_DONE, GOT_IMSG_IDXPACK_REQUEST, GOT_IMSG_IDXPACK_DONE, @@ -269,6 +270,12 @@ struct got_imsg_fetch_ref { /* Followed by reference name in remaining data of imsg buffer. */ }; +/* Structure for GOT_IMSG_FETCH_DOWNLOAD_PROGRESS data. */ +struct got_imsg_fetch_download_progress { + /* Number of packfile data bytes downloaded so far. */ + off_t packfile_bytes; +}; + /* Structure for GOT_IMSG_PACKIDX. */ struct got_imsg_packidx { size_t len; @@ -359,9 +366,11 @@ const struct got_error *got_privsep_send_fetch_ref(str struct got_object_id *, const char *); const struct got_error *got_privsep_send_fetch_server_progress(struct imsgbuf *, const char *, size_t); +const struct got_error *got_privsep_send_fetch_download_progress(struct imsgbuf *, + off_t); const struct got_error *got_privsep_recv_fetch_progress(int *, struct got_object_id **, char **, struct got_pathlist_head *, - char **, struct imsgbuf *); + char **, off_t *, struct imsgbuf *); const struct got_error *got_privsep_send_fetch_done(struct imsgbuf *, struct got_object_id); const struct got_error *got_privsep_get_imsg_obj(struct got_object **, blob - 6aabc63d20518ccca1b4c176ee56c4af7e7f9adc blob + 96c8759b3613fda441384c283df161cf5059f8fa --- lib/privsep.c +++ lib/privsep.c @@ -583,6 +583,17 @@ got_privsep_send_fetch_server_progress(struct imsgbuf msg, msglen) == -1) return got_error_from_errno( "imsg_compose FETCH_SERVER_PROGRESS"); + + return flush_imsg(ibuf); +} + +const struct got_error * +got_privsep_send_fetch_download_progress(struct imsgbuf *ibuf, off_t bytes) +{ + if (imsg_compose(ibuf, GOT_IMSG_FETCH_DOWNLOAD_PROGRESS, 0, 0, -1, + &bytes, sizeof(bytes)) == -1) + return got_error_from_errno( + "imsg_compose FETCH_DOWNLOAD_PROGRESS"); return flush_imsg(ibuf); } @@ -600,7 +611,7 @@ got_privsep_send_fetch_done(struct imsgbuf *ibuf, stru const struct got_error * got_privsep_recv_fetch_progress(int *done, struct got_object_id **id, char **refname, struct got_pathlist_head *symrefs, char **server_progress, - struct imsgbuf *ibuf) + off_t *packfile_size, struct imsgbuf *ibuf) { const struct got_error *err = NULL; struct imsg imsg; @@ -720,6 +731,13 @@ got_privsep_recv_fetch_progress(int *done, struct got_ } } break; + case GOT_IMSG_FETCH_DOWNLOAD_PROGRESS: + if (datalen < sizeof(*packfile_size)) { + err = got_error(GOT_ERR_PRIVSEP_MSG); + break; + } + memcpy(packfile_size, imsg.data, sizeof(*packfile_size)); + break; case GOT_IMSG_FETCH_DONE: *id = malloc(sizeof(**id)); if (*id == NULL) { blob - 17c615163a853c4b5c228a07100bafca24dce381 blob + 14fb915c5bf3a3ec428cfafcae915f83694cc47b --- libexec/got-fetch-pack/got-fetch-pack.c +++ libexec/got-fetch-pack/got-fetch-pack.c @@ -774,6 +774,9 @@ fetch_pack(int fd, int packfd, struct got_object_id *p goto done; } packsz += w; + err = got_privsep_send_fetch_download_progress(ibuf, packsz); + if (err) + goto done; } if (lseek(packfd, 0, SEEK_SET) == -1) { err = got_error_from_errno("lseek");