git/list[1] front-page[2] threads[3] people[4] search[5] about
 

Re: [PATCH] Port git-tag.sh to C.

From
Kristian Høgsberg <krh@redhat.com>
Date
Jun 9, 2007, 23:27 UTC
Message-ID
<466B376D.8040303@redhat.com>
In-Reply-To
<7v7iqdf0gn.fsf@assigned-by-dhcp.cox.net>
Junio C Hamano wrote:
Show 13 quoted lines
> Kristian Høgsberg <krh@redhat.com> writes:
> 
>> Content-Type: TEXT/PLAIN; charset=ISO-8859-1
>>
>> From: Kristian Høgsberg <krh@redhat.com>
>>
>> A more or less straight-forward port of git-tag.sh to C.
>>
>> Signed-off-by: Kristian Høgsberg <krh@redhat.com>
>> Cc: Johannes Schindelin <Johannes.Schindelin@gmx.de>
> 
> I think your name in your commit message is in UTF-8 but munged your
> mail was mismarked as iso-8859-1.

That's odd both the email I cc'ed to my redhat.com address and the one I got on gmail.com through the list have

   Content-Type: text/plain; charset=utf-8
and saving the raw message and asking /usr/bin/file, it tells me its
   /home/krh/Desktop/hep: UTF-8 Unicode mail text
Show 10 quoted lines
>> +static int launch_editor(const char *path, const char *template,
>> +			  char *buffer, size_t size)
>> +{
> 
> It would have been nicer to have this in editor.c or somesuch,
> as other commands will be redone in C in the future.
> 
> We could do the moving later, but the problem is that later is
> conditional: "if we are lucky enough to remember that we already
> have this function in builtin-tag when doing so".

Yeah, true. I did write it as a generally usable "launch editor" functions, but I didn't want to move it until there was a second user. Is there anything else that git-commit that will use this, btw?

Show 5 quoted lines
>> +	fd = open(path, O_CREAT | O_TRUNC | O_WRONLY, 0644);
> 
> I would understand an argument to use 0666 (honor umask) or 0600
> (this is a temporary file and others have no business looking at
> it while an edit is in progress), but I cannot justify 0644.
Oh hehe, yeah, I didn't think much about the permission bits... 0666 sounds fine.
>> +	fd = open(path, O_RDONLY, 0644);
> 
> Open for reading with mode ;-)?
Even less thinking here :)
Show 34 quoted lines
>> +	if (fd == -1)
>> +		die("could not read %s.", path);
>> +	len = read_in_full(fd, buffer, size);
>> +	if (len < 0)
>> +		die("failed to read '%s', %m", path);
>> +	close(fd);
>> +
>> +	blank_lines = 1;
>> +	for (i = 0, j = 0; i < len; i++) {
>> ...
>> +	}
>> +
>> +	if (buffer[j - 1] != '\n')
>> +		buffer[j++] = '\n';
>> +
>> +	unlink(path);
>> +
>> +	return j;
>> +}
> 
> I really think this function needs to be refactored into three.
> 
>  * A generic "spawn an editor with this initial seed template,
>    return the result of editing in memory and also give exit
>    status of the editor" function that does not take path
>    parameter (instead perhaps mkstemp a temporary file on your
>    own);
> 
>  * A function that does what git-stripspace does in core;
> 
>  * A function for builtin-tag to use, that calls the above two
>    and uses the result (e.g. "did the user kill the editor?
>    does the resulting buffer have any nonempty line?") to decide
>    what it does.

and that last function should be useful for git-commit too, no? The reason I didn't split it up was that I don't see any use for the two parts on their own, and the functions is a total of 70 lines. And wouldn't returning 0 bytes for either an empty buffer or editor quit be sufficient? Do we need to handle the two cases differently?

Show 43 quoted lines
>> +static void create_tag(const unsigned char *object, const char *tag,
>> +		       const char *message, int sign, unsigned char *result)
>> +{
>> +	enum object_type type;
>> +	char buffer[4096];
>> +	int header, body, total;
>> +
>> +	type = sha1_object_info(object, NULL);
>> +	if (type <= 0)
>> +	    die("bad object type.");
>> +
>> +	header = snprintf(buffer, sizeof buffer,
>> +			  "object %s\n"
>> +			  "type %s\n"
>> +			  "tag %s\n"
>> +			  "tagger %s\n\n",
>> +			  sha1_to_hex(object),
>> +			  typename(type),
>> +			  tag,
>> +			  git_committer_info(1));
>> +
>> +	if (message == NULL)
>> +		body = launch_editor(git_path("TAGMSG"), tag_template,
>> +				     buffer + header, sizeof buffer - header);
>> +	else
>> +		body = snprintf(buffer + header, sizeof buffer - header,
>> +				"%s\n", message);
>> +
>> +	if (body == 0)
>> +		die("no tag message?");
>> +
>> +	if (header + body > sizeof buffer)
>> +		die("tag message too big.");
> 
> Two issues:
> 
>  * It used to be a tag had limit of 8kB which was lifted some
>    time ago; now it is limited to 4kB.  Fixing this implies that
>    the "launch editor and get results in core" function I
>    mentioned above may need to realloc, and probably the buffer
>    is better passed as (char *, ulong) pair as done everywhere
>    else (although we know this is text so you can pass only a
>    pointer and have the user run strlen() when needed).

Oh... read_pipe() reallocs... OK. I took the limit from mktag.c and didn't realize that the buffer could get realloced. I did wonder about the xmalloc() for a fixed buffer though...

>  * I do not see any validation on the value of "tag".  Do we want
>    to allow passing "" to it?  What about "my\ntag"?
I do
         if (check_ref_format(ref))
                 die("'%s' is not a valid tag name.", tag);

on the ref, which is what git-tag.sh ends up doing, and it catches the two examples you mention:

[krh@dinky git]$ ./git tag "hello
 > world"
fatal: 'hello
world' is not a valid tag name.
[krh@dinky git]$ ./git tag ""
fatal: '' is not a valid tag name.
so I think it's fine.

But I think I'll leave it to Carlos to finish his builtin-tag work, and he can cherry pick the bits from my patch that work for him. This was more of a friday afternoon hacking sprint, for my part.

cheers, Kristian

Previous: Junio C HamanoNext: Robin Rosenberg
Message 10 of 15 in “Port git-tag.sh to C.”
  1. Port git-tag.sh to C.Kristian Høgsberg, Jun 8, 2007
  2. Carlos RicaJun 9, 2007
  3. Daniel BarkalowJun 12, 2007
  4. git-fetch, was Re: [PATCH] Port git-tag.sh to C.Johannes Schindelin, Jun 12, 2007
  5. Julian PhillipsJun 12, 2007
  6. Daniel BarkalowJun 12, 2007
  7. Daniel BarkalowJun 12, 2007
  8. Johannes SchindelinJun 13, 2007
  9. Junio C HamanoJun 9, 2007
  10. Kristian HøgsbergJun 9, 2007
  11. Robin RosenbergJun 10, 2007
  12. Junio C HamanoJun 10, 2007
  13. Jeff KingJun 10, 2007
  14. Junio C HamanoJun 10, 2007
  15. Jeff KingJun 10, 2007

Read the whole thread, see it on lore, or plain text.

$ cat FOOTERMessages come from the public archive at lore.kernel.org/git, fetched every hour. The front page is chosen and written each morning by an AI editor and can be wrong; the threads themselves are the record. About and API. For agents: an MCP server at https://gitlist.dev/mcp, and any thread, story or person page as Markdown by adding .md to its URL (or sending Accept: text/markdown). Details in /llms.txt.