From: Han-Wen Nienhuys via GitGitGadget <hidden> Date: 2021-08-30 14:48:54
From: Han-Wen Nienhuys <redacted>
Follow the reflog format more closely, so it can be used for comparing
reflogs in tests without using inspecting files under .git/logs/
Signed-off-by: Han-Wen Nienhuys <redacted>
---
t/helper/test-ref-store.c | 6 +++---
t/t1405-main-ref-store.sh | 5 +++--
t/t1406-submodule-ref-store.sh | 4 ++--
3 files changed, 8 insertions(+), 7 deletions(-)
@@ -416,8 +416,8 @@ int refs_pack_refs(struct ref_store *refs, unsigned int flags);*Setupreflogbeforeusing.Fillinerrandreturn-1onfailure.*/intrefs_create_reflog(structref_store*refs,constchar*refname,-intforce_create,structstrbuf*err);-intsafe_create_reflog(constchar*refname,intforce_create,structstrbuf*err);+structstrbuf*err);+intsafe_create_reflog(constchar*refname,structstrbuf*err);/** Reads log for the value of ref during at_time. **/intread_ref_at(structref_store*refs,
@@ -1618,8 +1618,7 @@ static int packed_reflog_exists(struct ref_store *ref_store,}staticintpacked_create_reflog(structref_store*ref_store,-constchar*refname,intforce_create,-structstrbuf*err)+constchar*refname,structstrbuf*err){BUG("packed reference store does not support reflogs");}
From: Han-Wen Nienhuys via GitGitGadget <hidden> Date: 2021-08-30 14:49:03
From: Han-Wen Nienhuys <redacted>
Before, if we aren't supposed to update reflogs (eg.
core.logallrefupdates=NONE), we would still write reflog entries if the
reflog file (.git/logs/REFNAME) existed.
The reftable storage backend cannot distinguish between a non-existing
reflog, and an empty one. Therefore it cannot mimick this functionality.
In CAFQ2z_Ps3YxycA+NJ9VKt_PEXb+m83JdNB7ujzWw1fTPKyZ=fg@mail.gmail.com,
we came to the conclusion that this feature is probably a remnant from
the time that reflogs weren't enabled by default, and it does not need
to be kept.
Signed-off-by: Han-Wen Nienhuys <redacted>
---
refs/files-backend.c | 20 +-------------------
t/t1400-update-ref.sh | 7 +++----
2 files changed, 4 insertions(+), 23 deletions(-)
@@ -1551,6 +1551,7 @@ static int log_ref_setup(struct files_ref_store *refs,structstrbuflogfile_sb=STRBUF_INIT;char*logfile;+*logfd=-1;files_reflog_path(refs,&logfile_sb,refname);logfile=strbuf_detach(&logfile_sb,NULL);
@@ -1565,26 +1566,8 @@ static int log_ref_setup(struct files_ref_store *refs,elsestrbuf_addf(err,"unable to append to '%s': %s",logfile,strerror(errno));-gotoerror;}-}else{-*logfd=open(logfile,O_APPEND|O_WRONLY,0666);-if(*logfd<0){-if(errno==ENOENT||errno==EISDIR){-/*-*Thelogfiledoesn'talreadyexist,-*butthatisnotanerror;itonly-*meansthatwewon'twritelog-*entriestoit.-*/-;-}else{-strbuf_addf(err,"unable to append to '%s': %s",-logfile,strerror(errno));-gotoerror;-}-}}if(*logfd>=0)
@@ -1592,7 +1575,6 @@ static int log_ref_setup(struct files_ref_store *refs,free(logfile);return0;-error:free(logfile);return-1;
From: Taylor Blau <hidden> Date: 2021-08-30 20:23:19
On Mon, Aug 30, 2021 at 02:48:45PM +0000, Han-Wen Nienhuys via GitGitGadget wrote:
quoted hunk
From: Han-Wen Nienhuys <redacted>
Follow the reflog format more closely, so it can be used for comparing
reflogs in tests without using inspecting files under .git/logs/
Signed-off-by: Han-Wen Nienhuys <redacted>
---
t/helper/test-ref-store.c | 6 +++---
t/t1405-main-ref-store.sh | 5 +++--
t/t1406-submodule-ref-store.sh | 4 ++--
3 files changed, 8 insertions(+), 7 deletions(-)
Having read the rest of the series, I did scratch my head quite a bit
here, but I think the change is actually quite simple. In the files
backend, show_one_reflog_ent is parsing line-wise, and each line ends
with the LF.
Of course, we don't expect the reflog to have messages that actually
contain a newline because we cleanse them with copy_reflog_message()
before writing.
So really it seems like the files-backend should be calling rstrip on
the message before handing it to the callback. Either that, or we could
call rstrip ourselves (since the generic strchr() makes me think that
the LF could appear anywhere in the string, at least on first read).
Thanks,
Taylor
From: Taylor Blau <hidden> Date: 2021-08-30 21:10:41
On Mon, Aug 30, 2021 at 02:48:48PM +0000, Han-Wen Nienhuys via GitGitGadget wrote:
From: Han-Wen Nienhuys <redacted>
Before, if we aren't supposed to update reflogs (eg.
core.logallrefupdates=NONE), we would still write reflog entries if the
reflog file (.git/logs/REFNAME) existed.
The reftable storage backend cannot distinguish between a non-existing
reflog, and an empty one. Therefore it cannot mimick this functionality.
In CAFQ2z_Ps3YxycA+NJ9VKt_PEXb+m83JdNB7ujzWw1fTPKyZ=fg@mail.gmail.com,
This looks like a faithful implementation of that discussion, so I don't
see any problems with the change.
quoted hunk
we came to the conclusion that this feature is probably a remnant from
the time that reflogs weren't enabled by default, and it does not need
to be kept.
Signed-off-by: Han-Wen Nienhuys <redacted>
---
refs/files-backend.c | 20 +-------------------
t/t1400-update-ref.sh | 7 +++----
2 files changed, 4 insertions(+), 23 deletions(-)
@@ -1551,6 +1551,7 @@ static int log_ref_setup(struct files_ref_store *refs,structstrbuflogfile_sb=STRBUF_INIT;char*logfile;+*logfd=-1;files_reflog_path(refs,&logfile_sb,refname);logfile=strbuf_detach(&logfile_sb,NULL);
@@ -1565,26 +1566,8 @@ static int log_ref_setup(struct files_ref_store *refs,elsestrbuf_addf(err,"unable to append to '%s': %s",logfile,strerror(errno));-gotoerror;}-}else{-*logfd=open(logfile,O_APPEND|O_WRONLY,0666);-if(*logfd<0){-if(errno==ENOENT||errno==EISDIR){-/*-*Thelogfiledoesn'talreadyexist,-*butthatisnotanerror;itonly-*meansthatwewon'twritelog-*entriestoit.-*/-;-}else{-strbuf_addf(err,"unable to append to '%s': %s",-logfile,strerror(errno));-gotoerror;-}-}}if(*logfd>=0)
I'm nit-picking, but I think that this conditional could probably be
moved into the if-statement above, since we no longer set logfd anywhere
else. It might read more clearly, and if you're going to resubmit this
series anyway, it would be helpful to pick that up.
OK, so "Initial Creation" happened in a state where
"core.logAllRefUpdates=false", but we passed "--create-reflog" to force
the behavior anyway.
Then during "Switch", we had a reflog, but again "core.logAllRefUpdates"
is false, and we didn't pass "--create-reflog", so no more updates are
written to the reflog.
That's exactly the test that I would have expected to exist for this
change, and so this LGTM.
Thanks,
Taylor
From: Han-Wen Nienhuys via GitGitGadget <hidden> Date: 2021-09-06 16:52:28
From: Han-Wen Nienhuys <redacted>
Commit 523fa69c ("reflog: cleanse messages in the refs.c layer") standardizes
how write entries into the reflog. This commit standardizes how we get messages
out of the reflog. Before, the files backend implicitly added '\n' to the end of
reflog message on reading, which creates a subtle incompatibility with alternate
ref storage backends, such as reftable.
We address this by stripping LF from the message before we pass it to the
user-provided callback.
Signed-off-by: Han-Wen Nienhuys <redacted>
---
builtin/show-branch.c | 4 +++-
reflog-walk.c | 6 ++----
refs/files-backend.c | 30 +++++++++++++++---------------
t/t1405-main-ref-store.sh | 5 ++---
t/t1406-submodule-ref-store.sh | 4 ++--
5 files changed, 24 insertions(+), 25 deletions(-)
@@ -1897,17 +1897,15 @@ static int show_one_reflog_ent(struct strbuf *sb, each_reflog_ent_fn fn, void *cinttz;constchar*p=sb->buf;-/* old SP new SP name <email> SP time TAB msg LF */-if(!sb->len||sb->buf[sb->len-1]!='\n'||-parse_oid_hex(p,&ooid,&p)||*p++!=' '||+/* old SP new SP name <email> SP time TAB msg */+if(!sb->len||parse_oid_hex(p,&ooid,&p)||*p++!=' '||parse_oid_hex(p,&noid,&p)||*p++!=' '||-!(email_end=strchr(p,'>'))||-email_end[1]!=' '||+!(email_end=strchr(p,'>'))||email_end[1]!=' '||!(timestamp=parse_timestamp(email_end+2,&message,10))||!message||message[0]!=' '||-(message[1]!='+'&&message[1]!='-')||-!isdigit(message[2])||!isdigit(message[3])||-!isdigit(message[4])||!isdigit(message[5]))+(message[1]!='+'&&message[1]!='-')||!isdigit(message[2])||+!isdigit(message[3])||!isdigit(message[4])||+!isdigit(message[5]))return0;/* corrupt? */email_end[1]='\0';tz=strtol(message+1,NULL,10);
@@ -1999,6 +1997,7 @@ static int files_for_each_reflog_ent_reverse(struct ref_store *ref_store,strbuf_splice(&sb,0,0,bp+1,endp-(bp+1));scanp=bp;endp=bp+1;+strbuf_trim_trailing_newline(&sb);ret=show_one_reflog_ent(&sb,fn,cb_data);strbuf_reset(&sb);if(ret)
@@ -2011,6 +2010,7 @@ static int files_for_each_reflog_ent_reverse(struct ref_store *ref_store,*Processit,andwecanendtheloop.*/strbuf_splice(&sb,0,0,buf,endp-buf);+strbuf_trim_trailing_newline(&sb);ret=show_one_reflog_ent(&sb,fn,cb_data);strbuf_reset(&sb);break;
@@ -2060,7 +2060,7 @@ static int files_for_each_reflog_ent(struct ref_store *ref_store,if(!logfp)return-1;-while(!ret&&!strbuf_getwholeline(&sb,logfp,'\n'))+while(!ret&&!strbuf_getline(&sb,logfp))ret=show_one_reflog_ent(&sb,fn,cb_data);fclose(logfp);strbuf_release(&sb);
From: Han-Wen Nienhuys via GitGitGadget <hidden> Date: 2021-09-06 16:52:30
From: Han-Wen Nienhuys <redacted>
Follow the reflog format more closely, so it can be used for comparing
reflogs in tests without using inspecting files under .git/logs/
Signed-off-by: Han-Wen Nienhuys <redacted>
---
t/helper/test-ref-store.c | 5 ++---
t/t1405-main-ref-store.sh | 1 +
2 files changed, 3 insertions(+), 3 deletions(-)
@@ -416,8 +416,8 @@ int refs_pack_refs(struct ref_store *refs, unsigned int flags);*Setupreflogbeforeusing.Fillinerrandreturn-1onfailure.*/intrefs_create_reflog(structref_store*refs,constchar*refname,-intforce_create,structstrbuf*err);-intsafe_create_reflog(constchar*refname,intforce_create,structstrbuf*err);+structstrbuf*err);+intsafe_create_reflog(constchar*refname,structstrbuf*err);/** Reads log for the value of ref during at_time. **/intread_ref_at(structref_store*refs,
@@ -1618,8 +1618,7 @@ static int packed_reflog_exists(struct ref_store *ref_store,}staticintpacked_create_reflog(structref_store*ref_store,-constchar*refname,intforce_create,-structstrbuf*err)+constchar*refname,structstrbuf*err){BUG("packed reference store does not support reflogs");}
From: Han-Wen Nienhuys via GitGitGadget <hidden> Date: 2021-09-06 16:52:34
From: Han-Wen Nienhuys <redacted>
Before, if we aren't supposed to update reflogs (eg.
core.logallrefupdates=NONE), we would still write reflog entries if the
reflog file (.git/logs/REFNAME) existed.
The reftable storage backend cannot distinguish between a non-existing
reflog, and an empty one. Therefore it cannot mimick this functionality.
In CAFQ2z_Ps3YxycA+NJ9VKt_PEXb+m83JdNB7ujzWw1fTPKyZ=fg@mail.gmail.com,
we came to the conclusion that this feature is probably a remnant from
the time that reflogs weren't enabled by default, and it does not need
to be kept.
Signed-off-by: Han-Wen Nienhuys <redacted>
---
refs/files-backend.c | 53 ++++++++++++++-----------------------------
t/t1400-update-ref.sh | 5 ++--
2 files changed, 19 insertions(+), 39 deletions(-)
@@ -1551,51 +1551,32 @@ static int log_ref_setup(struct files_ref_store *refs,structstrbuflogfile_sb=STRBUF_INIT;char*logfile;+*logfd=-1;+if(!force_create&&!should_autocreate_reflog(refname))+return0;+files_reflog_path(refs,&logfile_sb,refname);logfile=strbuf_detach(&logfile_sb,NULL);-if(force_create||should_autocreate_reflog(refname)){-if(raceproof_create_file(logfile,open_or_create_logfile,logfd)){-if(errno==ENOENT)-strbuf_addf(err,"unable to create directory for '%s': "-"%s",logfile,strerror(errno));-elseif(errno==EISDIR)-strbuf_addf(err,"there are still logs under '%s'",-logfile);-else-strbuf_addf(err,"unable to append to '%s': %s",-logfile,strerror(errno));--gotoerror;-}-}else{-*logfd=open(logfile,O_APPEND|O_WRONLY,0666);-if(*logfd<0){-if(errno==ENOENT||errno==EISDIR){-/*-*Thelogfiledoesn'talreadyexist,-*butthatisnotanerror;itonly-*meansthatwewon'twritelog-*entriestoit.-*/-;-}else{-strbuf_addf(err,"unable to append to '%s': %s",-logfile,strerror(errno));-gotoerror;-}-}+if(raceproof_create_file(logfile,open_or_create_logfile,logfd)){+if(errno==ENOENT)+strbuf_addf(err,+"unable to create directory for '%s': "+"%s",+logfile,strerror(errno));+elseif(errno==EISDIR)+strbuf_addf(err,"there are still logs under '%s'",+logfile);+else+strbuf_addf(err,"unable to append to '%s': %s",+logfile,strerror(errno));}if(*logfd>=0)adjust_shared_perm(logfile);free(logfile);-return0;--error:-free(logfile);-return-1;+return(*logfd<0)?-1:0;}staticintfiles_create_reflog(structref_store*ref_store,constchar*refname,
On Mon, Sep 06 2021, Han-Wen Nienhuys via GitGitGadget wrote:
quoted hunk
From: Han-Wen Nienhuys <redacted>
Follow the reflog format more closely, so it can be used for comparing
reflogs in tests without using inspecting files under .git/logs/
Signed-off-by: Han-Wen Nienhuys <redacted>
---
t/helper/test-ref-store.c | 5 ++---
t/t1405-main-ref-store.sh | 1 +
2 files changed, 3 insertions(+), 3 deletions(-)
Nit: Would be a more readable diff if this wasn't a
line-wrap-while-at-it change in addition to changing the format string.
I.e. the last 4x parameters aren't changed, so leaving them on their own
line & just changing the string & the two oid_to_hex()...
On Mon, Sep 06 2021, Han-Wen Nienhuys via GitGitGadget wrote:
From: Han-Wen Nienhuys <redacted>
[...]
- puts(reflog_msg[i]);
+ puts(reflog_msg[i]); /* XXX - this puts a
+ newline. Did we put two
+ newlines beforehand? */
I recently added some tests for show-branch, see the tip of
ab/show-branch-tests. This seems like it would be clearer to both you &
reviewers if we first checked & test_cmp'd the reflog behavior of "git
show-branch" in some "here's how it works now test", then made whatever
non-changes to the format done here.
Presumably this newline mystery would become clear once we'd have
coverage of its reflog codepaths.
On Mon, Sep 06 2021, Han-Wen Nienhuys via GitGitGadget wrote:
From: Han-Wen Nienhuys <redacted>
There is only one caller, builtin/checkout.c, and it hardcodes
force_create=1.
Was it ever needed? A glance at abd0cd3a301 (refs: new public ref
function: safe_create_reflog, 2015-07-21) suggests probably not, but
then there's 0f2a71d9923 (refs: add REF_FORCE_CREATE_REFLOG flag,
2015-07-21) ...
[...]
-static int files_create_reflog(struct ref_store *ref_store,
- const char *refname, int force_create,
+static int files_create_reflog(struct ref_store *ref_store, const char *refname,
struct strbuf *err)
{
struct files_ref_store *refs =
files_downcast(ref_store, REF_STORE_WRITE, "create_reflog");
int fd;
- if (log_ref_setup(refs, refname, force_create, &fd, err))
+ if (log_ref_setup(refs, refname, /*force_create=*/1, &fd, err))
We can lose the inline comment here & let the function definition speak
for itself, we usually don't inline comment boolean flags.
In any case, having not dug (but presumably you have) some overview of
how we ended up having this not-required flag would be nice. I.e. was it
always this dead-end, or did we replace it with REF_FORCE_CREATE_REFLOG
at some point etc?
On Mon, Sep 06 2021, Han-Wen Nienhuys via GitGitGadget wrote:
In CAFQ2z_Ps3YxycA+NJ9VKt_PEXb+m83JdNB7ujzWw1fTPKyZ=fg@mail.gmail.com,
Nit: use <message-id> for quoting, not message-id.
we came to the conclusion that this feature is probably a remnant from
the time that reflogs weren't enabled by default, and it does not need
to be kept.
Maybe some summary of the flexibily either Jeff King or Junio mentioned
we were losing (i.e. we can't selectively enable per-ref now), but that
we think it's OK because...
For the implementation:
+ *logfd = -1;
Weird, more on this later...
+ if (!force_create && !should_autocreate_reflog(refname))
+ return 0;
OK, so we can early abort.
files_reflog_path(refs, &logfile_sb, refname);
logfile = strbuf_detach(&logfile_sb, NULL);
- if (force_create || should_autocreate_reflog(refname)) {
- if (raceproof_create_file(logfile, open_or_create_logfile, logfd)) {
- if (errno == ENOENT)
- strbuf_addf(err, "unable to create directory for '%s': "
- "%s", logfile, strerror(errno));
Here we use one indent/wrapping style...
- else if (errno == EISDIR)
- strbuf_addf(err, "there are still logs under '%s'",
- logfile);
- else
- strbuf_addf(err, "unable to append to '%s': %s",
- logfile, strerror(errno));
-
- goto error;
- }
- } else {
- *logfd = open(logfile, O_APPEND | O_WRONLY, 0666);
- if (*logfd < 0) {
- if (errno == ENOENT || errno == EISDIR) {
- /*
- * The logfile doesn't already exist,
- * but that is not an error; it only
- * means that we won't write log
- * entries to it.
- */
- ;
- } else {
- strbuf_addf(err, "unable to append to '%s': %s",
- logfile, strerror(errno));
- goto error;
- }
- }
+ if (raceproof_create_file(logfile, open_or_create_logfile, logfd)) {
+ if (errno == ENOENT)
+ strbuf_addf(err,
+ "unable to create directory for '%s': "
+ "%s",
+ logfile, strerror(errno));
...but here it's changed while we're at it, this patch would be easier
to follow IMO if we just left the formatting alone (or did it as another
step). I'm aware that it ends us at over 79 columns, but that was the
case before...
+ else if (errno == EISDIR)
+ strbuf_addf(err, "there are still logs under '%s'",
+ logfile);
+ else
+ strbuf_addf(err, "unable to append to '%s': %s",
+ logfile, strerror(errno));
}
if (*logfd >= 0)
adjust_shared_perm(logfile);
free(logfile);
- return 0;
-
-error:
- free(logfile);
- return -1;
+ return (*logfd < 0) ? -1 : 0;
On "more on this later": Since we just return -1, 0 or a valid fd now,
can't we just return the "fd" here and let the callers sort out -1, 0
and >0?
Nit: Would be a more readable diff if this wasn't a
line-wrap-while-at-it change in addition to changing the format string.
I.e. the last 4x parameters aren't changed, so leaving them on their own
line & just changing the string & the two oid_to_hex()...
This is clang-format's output, and the new code takes up less lines vertically.
If you think this is really, really important, I can change it, but I
think it's a better use of everyone's time to leave mechanical tasks
(like formatting) to the machines.
--
Han-Wen Nienhuys - Google Munich
I work 80%. Don't expect answers from me on Fridays.
--
Google Germany GmbH, Erika-Mann-Strasse 33, 80636 Munich
Registergericht und -nummer: Hamburg, HRB 86891
Sitz der Gesellschaft: Hamburg
Geschäftsführer: Paul Manicle, Halimah DeLaine Prado
From: Han-Wen Nienhuys via GitGitGadget <hidden> Date: 2021-09-07 13:37:00
<As discussed in
CAFQ2z_Ps3YxycA+NJ9VKt_PEXb+m83JdNB7ujzWw1fTPKyZ=fg@mail.gmail.com
v3:
* fix show-branch
* add some more context to commit messages
* change calling convention for log_ref_setup; could fold into predecessor
if needed too.
Han-Wen Nienhuys (7):
show-branch: show reflog message
refs: trim newline from reflog message
test-ref-store: tweaks to for-each-reflog-ent format
t1400: use test-helper ref-store to inspect reflog contents
refs: drop force_create argument of create_reflog API
RFC: refs: reflog entries aren't written based on reflog existence.
refs: change log_ref_setup calling convention
builtin/checkout.c | 2 +-
builtin/show-branch.c | 7 +-
reflog-walk.c | 6 +-
refs.c | 9 ++-
refs.h | 4 +-
refs/debug.c | 5 +-
refs/files-backend.c | 128 +++++++++++++--------------------
refs/packed-backend.c | 3 +-
refs/refs-internal.h | 2 +-
t/helper/test-ref-store.c | 8 +--
t/t1400-update-ref.sh | 21 +++---
t/t1405-main-ref-store.sh | 6 +-
t/t1406-submodule-ref-store.sh | 6 +-
t/t3202-show-branch.sh | 15 ++++
14 files changed, 101 insertions(+), 121 deletions(-)
base-commit: e0a2f5cbc585657e757385ad918f167f519cfb96
Published-As: https://github.com/gitgitgadget/git/releases/tag/pr-git-1067%2Fhanwen%2Freflog-touch-v3
Fetch-It-Via: git fetch https://github.com/gitgitgadget/git pr-git-1067/hanwen/reflog-touch-v3
Pull-Request: https://github.com/git/git/pull/1067
Range-diff vs v2:
-: ----------- > 1: e158882812f show-branch: show reflog message
1: 995d450da42 ! 2: d16d94164c1 refs: trim newline from reflog message
@@ Commit message
## builtin/show-branch.c ##
@@ builtin/show-branch.c: int cmd_show_branch(int ac, const char **av, const char *prefix)
- show_one_commit(rev[i], 1);
+ char *logmsg;
+ char *nth_desc;
+ const char *msg;
+- char *end;
+ timestamp_t timestamp;
+ int tz;
+
+@@ builtin/show-branch.c: int cmd_show_branch(int ac, const char **av, const char *prefix)
+ break;
}
- else
-- puts(reflog_msg[i]);
-+ puts(reflog_msg[i]); /* XXX - this puts a
-+ newline. Did we put two
-+ newlines beforehand? */
- if (is_head)
- head_at = i;
+- end = strchr(logmsg, '\n');
+- if (end)
+- *end = '\0';
+-
+ msg = (*logmsg == '\0') ? "(none)" : logmsg;
+ reflog_msg[i] = xstrfmt("(%s) %s",
+ show_date(timestamp, tz,
## reflog-walk.c ##
@@ reflog-walk.c: void get_reflog_message(struct strbuf *sb,
2: 11b296a55e9 = 3: e273963216c test-ref-store: tweaks to for-each-reflog-ent format
3: 9ec09cc64cd = 4: 52093fce57c t1400: use test-helper ref-store to inspect reflog contents
4: aa25fd9b7de ! 5: ce0047028dd refs: drop force_create argument of create_reflog API
@@ Commit message
There is only one caller, builtin/checkout.c, and it hardcodes
force_create=1.
+ This argument was introduced in abd0cd3a301 (refs: new public ref function:
+ safe_create_reflog, 2015-07-21), which promised to immediately use it in a
+ follow-on commit, but that never happened.
+
Signed-off-by: Han-Wen Nienhuys [off-list ref]
## builtin/checkout.c ##
@@ refs/files-backend.c: error:
int fd;
- if (log_ref_setup(refs, refname, force_create, &fd, err))
-+ if (log_ref_setup(refs, refname, /*force_create=*/1, &fd, err))
++ if (log_ref_setup(refs, refname, 1, &fd, err))
return -1;
if (fd >= 0)
5: f6a7c5ad56e ! 6: 7a030cfd3e2 RFC: refs: reflog entries aren't written based on reflog existence.
@@ Commit message
The reftable storage backend cannot distinguish between a non-existing
reflog, and an empty one. Therefore it cannot mimick this functionality.
- In CAFQ2z_Ps3YxycA+NJ9VKt_PEXb+m83JdNB7ujzWw1fTPKyZ=fg@mail.gmail.com,
- we came to the conclusion that this feature is probably a remnant from
- the time that reflogs weren't enabled by default, and it does not need
- to be kept.
+ With this feature, it is possible to mark only specific branches as subject to
+ reflog updates. When introduced, it presumably served as a cheap substitute for
+ introducing branch.$NAME.logRefUpdate configuration setting.
+
+ Reflogs are small and don't impact the runtime of normal operations, so this
+ flexibility is not very useful. Since it incurs complexity for alternate ref
+ backends, we remove it.
+
+ Further background to this change is in
+ [off-list ref].
Signed-off-by: Han-Wen Nienhuys [off-list ref]
-: ----------- > 7: 1124dbad594 refs: change log_ref_setup calling convention
--
gitgitgadget
From: Han-Wen Nienhuys via GitGitGadget <hidden> Date: 2021-09-07 13:37:01
From: Han-Wen Nienhuys <redacted>
Before, --reflog option would look for '\t' in the reflog message. As refs.c
already parses the reflog line, the '\t' was never found, and show-branch
--reflog would always say "(none)" as reflog message
Add test.
Signed-off-by: Han-Wen Nienhuys <redacted>
---
builtin/show-branch.c | 12 +++++++-----
t/t3202-show-branch.sh | 15 +++++++++++++++
2 files changed, 22 insertions(+), 5 deletions(-)
From: Han-Wen Nienhuys via GitGitGadget <hidden> Date: 2021-09-07 13:37:02
From: Han-Wen Nienhuys <redacted>
There is only one caller, builtin/checkout.c, and it hardcodes
force_create=1.
This argument was introduced in abd0cd3a301 (refs: new public ref function:
safe_create_reflog, 2015-07-21), which promised to immediately use it in a
follow-on commit, but that never happened.
Signed-off-by: Han-Wen Nienhuys <redacted>
---
builtin/checkout.c | 2 +-
refs.c | 9 ++++-----
refs.h | 4 ++--
refs/debug.c | 5 ++---
refs/files-backend.c | 5 ++---
refs/packed-backend.c | 3 +--
refs/refs-internal.h | 2 +-
t/helper/test-ref-store.c | 3 +--
t/t1405-main-ref-store.sh | 2 +-
t/t1406-submodule-ref-store.sh | 2 +-
10 files changed, 16 insertions(+), 21 deletions(-)
@@ -416,8 +416,8 @@ int refs_pack_refs(struct ref_store *refs, unsigned int flags);*Setupreflogbeforeusing.Fillinerrandreturn-1onfailure.*/intrefs_create_reflog(structref_store*refs,constchar*refname,-intforce_create,structstrbuf*err);-intsafe_create_reflog(constchar*refname,intforce_create,structstrbuf*err);+structstrbuf*err);+intsafe_create_reflog(constchar*refname,structstrbuf*err);/** Reads log for the value of ref during at_time. **/intread_ref_at(structref_store*refs,
@@ -1618,8 +1618,7 @@ static int packed_reflog_exists(struct ref_store *ref_store,}staticintpacked_create_reflog(structref_store*ref_store,-constchar*refname,intforce_create,-structstrbuf*err)+constchar*refname,structstrbuf*err){BUG("packed reference store does not support reflogs");}
From: Han-Wen Nienhuys via GitGitGadget <hidden> Date: 2021-09-07 13:37:03
From: Han-Wen Nienhuys <redacted>
Commit 523fa69c ("reflog: cleanse messages in the refs.c layer") standardizes
how write entries into the reflog. This commit standardizes how we get messages
out of the reflog. Before, the files backend implicitly added '\n' to the end of
reflog message on reading, which creates a subtle incompatibility with alternate
ref storage backends, such as reftable.
We address this by stripping LF from the message before we pass it to the
user-provided callback.
Signed-off-by: Han-Wen Nienhuys <redacted>
---
builtin/show-branch.c | 5 -----
reflog-walk.c | 6 ++----
refs/files-backend.c | 30 +++++++++++++++---------------
t/t1405-main-ref-store.sh | 5 ++---
t/t1406-submodule-ref-store.sh | 4 ++--
5 files changed, 21 insertions(+), 29 deletions(-)
@@ -1897,17 +1897,15 @@ static int show_one_reflog_ent(struct strbuf *sb, each_reflog_ent_fn fn, void *cinttz;constchar*p=sb->buf;-/* old SP new SP name <email> SP time TAB msg LF */-if(!sb->len||sb->buf[sb->len-1]!='\n'||-parse_oid_hex(p,&ooid,&p)||*p++!=' '||+/* old SP new SP name <email> SP time TAB msg */+if(!sb->len||parse_oid_hex(p,&ooid,&p)||*p++!=' '||parse_oid_hex(p,&noid,&p)||*p++!=' '||-!(email_end=strchr(p,'>'))||-email_end[1]!=' '||+!(email_end=strchr(p,'>'))||email_end[1]!=' '||!(timestamp=parse_timestamp(email_end+2,&message,10))||!message||message[0]!=' '||-(message[1]!='+'&&message[1]!='-')||-!isdigit(message[2])||!isdigit(message[3])||-!isdigit(message[4])||!isdigit(message[5]))+(message[1]!='+'&&message[1]!='-')||!isdigit(message[2])||+!isdigit(message[3])||!isdigit(message[4])||+!isdigit(message[5]))return0;/* corrupt? */email_end[1]='\0';tz=strtol(message+1,NULL,10);
@@ -1999,6 +1997,7 @@ static int files_for_each_reflog_ent_reverse(struct ref_store *ref_store,strbuf_splice(&sb,0,0,bp+1,endp-(bp+1));scanp=bp;endp=bp+1;+strbuf_trim_trailing_newline(&sb);ret=show_one_reflog_ent(&sb,fn,cb_data);strbuf_reset(&sb);if(ret)
@@ -2011,6 +2010,7 @@ static int files_for_each_reflog_ent_reverse(struct ref_store *ref_store,*Processit,andwecanendtheloop.*/strbuf_splice(&sb,0,0,buf,endp-buf);+strbuf_trim_trailing_newline(&sb);ret=show_one_reflog_ent(&sb,fn,cb_data);strbuf_reset(&sb);break;
@@ -2060,7 +2060,7 @@ static int files_for_each_reflog_ent(struct ref_store *ref_store,if(!logfp)return-1;-while(!ret&&!strbuf_getwholeline(&sb,logfp,'\n'))+while(!ret&&!strbuf_getline(&sb,logfp))ret=show_one_reflog_ent(&sb,fn,cb_data);fclose(logfp);strbuf_release(&sb);
From: Han-Wen Nienhuys via GitGitGadget <hidden> Date: 2021-09-07 13:37:04
From: Han-Wen Nienhuys <redacted>
Follow the reflog format more closely, so it can be used for comparing
reflogs in tests without using inspecting files under .git/logs/
Signed-off-by: Han-Wen Nienhuys <redacted>
---
t/helper/test-ref-store.c | 5 ++---
t/t1405-main-ref-store.sh | 1 +
2 files changed, 3 insertions(+), 3 deletions(-)
From: Han-Wen Nienhuys via GitGitGadget <hidden> Date: 2021-09-07 13:37:08
From: Han-Wen Nienhuys <redacted>
Before, if we aren't supposed to update reflogs (eg.
core.logallrefupdates=NONE), we would still write reflog entries if the
reflog file (.git/logs/REFNAME) existed.
The reftable storage backend cannot distinguish between a non-existing
reflog, and an empty one. Therefore it cannot mimick this functionality.
With this feature, it is possible to mark only specific branches as subject to
reflog updates. When introduced, it presumably served as a cheap substitute for
introducing branch.$NAME.logRefUpdate configuration setting.
Reflogs are small and don't impact the runtime of normal operations, so this
flexibility is not very useful. Since it incurs complexity for alternate ref
backends, we remove it.
Further background to this change is in
[off-list ref].
Signed-off-by: Han-Wen Nienhuys <redacted>
---
refs/files-backend.c | 53 ++++++++++++++-----------------------------
t/t1400-update-ref.sh | 5 ++--
2 files changed, 19 insertions(+), 39 deletions(-)
@@ -1551,51 +1551,32 @@ static int log_ref_setup(struct files_ref_store *refs,structstrbuflogfile_sb=STRBUF_INIT;char*logfile;+*logfd=-1;+if(!force_create&&!should_autocreate_reflog(refname))+return0;+files_reflog_path(refs,&logfile_sb,refname);logfile=strbuf_detach(&logfile_sb,NULL);-if(force_create||should_autocreate_reflog(refname)){-if(raceproof_create_file(logfile,open_or_create_logfile,logfd)){-if(errno==ENOENT)-strbuf_addf(err,"unable to create directory for '%s': "-"%s",logfile,strerror(errno));-elseif(errno==EISDIR)-strbuf_addf(err,"there are still logs under '%s'",-logfile);-else-strbuf_addf(err,"unable to append to '%s': %s",-logfile,strerror(errno));--gotoerror;-}-}else{-*logfd=open(logfile,O_APPEND|O_WRONLY,0666);-if(*logfd<0){-if(errno==ENOENT||errno==EISDIR){-/*-*Thelogfiledoesn'talreadyexist,-*butthatisnotanerror;itonly-*meansthatwewon'twritelog-*entriestoit.-*/-;-}else{-strbuf_addf(err,"unable to append to '%s': %s",-logfile,strerror(errno));-gotoerror;-}-}+if(raceproof_create_file(logfile,open_or_create_logfile,logfd)){+if(errno==ENOENT)+strbuf_addf(err,+"unable to create directory for '%s': "+"%s",+logfile,strerror(errno));+elseif(errno==EISDIR)+strbuf_addf(err,"there are still logs under '%s'",+logfile);+else+strbuf_addf(err,"unable to append to '%s': %s",+logfile,strerror(errno));}if(*logfd>=0)adjust_shared_perm(logfile);free(logfile);-return0;--error:-free(logfile);-return-1;+return(*logfd<0)?-1:0;}staticintfiles_create_reflog(structref_store*ref_store,constchar*refname,
Nit: Would be a more readable diff if this wasn't a
line-wrap-while-at-it change in addition to changing the format string.
I.e. the last 4x parameters aren't changed, so leaving them on their own
line & just changing the string & the two oid_to_hex()...
This is clang-format's output, and the new code takes up less lines vertically.
If you think this is really, really important, I can change it, but I
think it's a better use of everyone's time to leave mechanical tasks
(like formatting) to the machines.
It's not "really, really important" or even "really important", just
notes while reading the series.
Patches are read N times, including during review. Since humans read
formatting changes, it's in general are not something we can leave to
machines. We're after all looking at the patch on-list, not diffing two
versions of the generated machine code, or of clang-format's output.
I don't think the intent of the clang-format target is to run it before
patch submission, but to serve as input on suggested formatting changes.
If on master you run:
git ls-files '*.[ch]' -z | xargs -n 1 -0 clang-format -i
You'll get:
631 files changed, 48246 insertions(+), 45061 deletions(-)
Which I think speaks for itself in the likelyhood that
"git-clang-format" is going to inject unnecessary churn into submitted
patches.
I think this case is quite small and not worth a re-roll.
On Tue, Sep 7, 2021 at 3:37 PM Han-Wen Nienhuys via GitGitGadget
[off-list ref] wrote:
<As discussed in
CAFQ2z_Ps3YxycA+NJ9VKt_PEXb+m83JdNB7ujzWw1fTPKyZ=fg@mail.gmail.com
v3:
* fix show-branch
* add some more context to commit messages
* change calling convention for log_ref_setup; could fold into predecessor
if needed too.
Hi Junio,
I had the impression that I addressed all outstanding comments (but
not sure). Are you waiting for me to do something before this can go
into 'seen' ?
There is a merge conflict against master, so I'll send a v4 shortly.
--
Han-Wen Nienhuys - Google Munich
I work 80%. Don't expect answers from me on Fridays.
--
Google Germany GmbH, Erika-Mann-Strasse 33, 80636 Munich
Registergericht und -nummer: Hamburg, HRB 86891
Sitz der Gesellschaft: Hamburg
Geschäftsführer: Paul Manicle, Halimah DeLaine Prado