"GOT", but the "O" is a cute, smiling pufferfish. Index | Thread | Search

From:
Stefan Sperling <stsp@stsp.name>
Subject:
Re: tog is sluggish with FreeBSD src.git
To:
Christian Weisgerber <naddy@mips.inka.de>
Cc:
gameoftrees@openbsd.org
Date:
Thu, 24 Dec 2020 14:52:14 +0100

Download raw body.

Thread
On Wed, Dec 23, 2020 at 07:42:04PM +0100, Christian Weisgerber wrote:
> "tog log" feels noticeably sluggish with today's version of FreeBSD's
> src.git.  (got clone -a ssh://anongit@git.freebsd.org/src.git)
> 
> I wonder if that is related to...
> 
> $ got ref -l |wc -l
>     3582
> 
> ...?

The patch below shows us where the problem is: Iterating a long SIMPLEQ
relifst in order to decorate commit hashes with branch names is too slow.

This patch makes commits load faster but moving the selection cursor
in the log view is still too slow.

It looks like we'll need to populate a cache of reference names which
is indexed by commit ID, ideally while reading references from the repo?

commit ccf2cdff529609358a59bec3afd73d1b75ae2e76 (tog)
from: Stefan Sperling <stsp@stsp.name>
date: Thu Dec 24 13:42:48 2020 UTC
 
 only update the log view's reference string if really needed
 
diff 2cc8027a71304c327a03e6b915acba067832dca7 c02f1e7f4de0d1b58678c6d56472e306193e2766
blob - d3d4a63398b4c4b05caa731b093b038b0b1d9bee
blob + c118af61c13d785aa29dbf57c12077b6a3f78652
--- tog/tog.c
+++ tog/tog.c
@@ -304,6 +304,8 @@ struct tog_log_view_state {
 	int log_branches;
 	struct got_repository *repo;
 	struct got_reflist_head refs;
+	char *refs_str;
+	int refs_str_is_valid;
 	struct got_object_id *start_id;
 	sig_atomic_t quit;
 	pthread_t thread;
@@ -1552,6 +1554,7 @@ select_commit(struct tog_log_view_state *s)
 		}
 		entry = TAILQ_NEXT(entry, entry);
 		ncommits++;
+		s->refs_str_is_valid = 0;
 	}
 }
 
@@ -1565,7 +1568,6 @@ draw_commits(struct tog_view *view)
 	int width;
 	int ncommits, author_cols = 4;
 	char *id_str = NULL, *header = NULL, *ncommits_str = NULL;
-	char *refs_str = NULL;
 	wchar_t *wline;
 	struct tog_color *tc;
 	static const size_t date_display_cols = 12;
@@ -1575,10 +1577,14 @@ draw_commits(struct tog_view *view)
 		err = got_object_id_str(&id_str, s->selected_entry->id);
 		if (err)
 			return err;
-		err = build_refs_str(&refs_str, &s->refs,
-		    s->selected_entry->id, s->repo);
-		if (err)
-			goto done;
+		if (!s->refs_str_is_valid) {
+			free(s->refs_str);
+			err = build_refs_str(&s->refs_str, &s->refs,
+			    s->selected_entry->id, s->repo);
+			if (err)
+				goto done;
+			s->refs_str_is_valid = 1;
+		}
 	}
 
 	if (s->thread_args.commits_needed == 0)
@@ -1607,7 +1613,7 @@ draw_commits(struct tog_view *view)
 		if (asprintf(&ncommits_str, " [%d/%d] %s",
 		    entry ? entry->idx + 1 : 0, s->commits.ncommits,
 		    search_str ? search_str :
-		    (refs_str ? refs_str : "")) == -1) {
+		    (s->refs_str ? s->refs_str : "")) == -1) {
 			err = got_error_from_errno("asprintf");
 			goto done;
 		}
@@ -1700,7 +1706,6 @@ draw_commits(struct tog_view *view)
 	view_vborder(view);
 done:
 	free(id_str);
-	free(refs_str);
 	free(ncommits_str);
 	free(header);
 	return err;
@@ -2119,6 +2124,8 @@ close_log_view(struct tog_view *view)
 	free(s->head_ref_name);
 	s->head_ref_name = NULL;
 	got_ref_list_free(&s->refs);
+	free(s->refs_str);
+	s->refs_str = NULL;
 	return err;
 }