Git development
 help / color / mirror / Atom feed
* Re: new git-diff switch to eliminate leading "+" and "-" characters
From: Junio C Hamano @ 2017-02-19 18:59 UTC (permalink / raw)
  To: Vanderhoof, Tzadik; +Cc: Duy Nguyen, git@vger.kernel.org
In-Reply-To: <2C8817BDA27E034F8E9A669458E375EF11888CC1@APSWP0428.ms.ds.uhc.com>

"Vanderhoof, Tzadik" <tzadik.vanderhoof@optum360.com> writes:

>> From: Duy Nguyen [mailto:pclouds@gmail.com]
>> 
>> I face this "problem" every day, but most editors nowadays have block-
>> based editing that would allow you to remove a column of "+/-"
>> easily. At least it has not bothered me to think of improving it.
>
> Would a patch be welcome?

I am not enthused for at least two reasons.  

The weaker one is "it would likely to introduce a lot of noise in
the code for a feature of dubious merit".  

The other is a bit more serious.  Cutting and pasting has been a
source of lost or mangled whitespaces.  Tabs get expanded, a wrapped
long single line turns into two lines, an originally indented line
auto-indented when inserted to the receiving editor, etc., etc.,
depending on the pager that the output was passed through for the
terminal, the terminal program itself and the editor.  The "feature"
will encourage cut-and-paste, and I personally would be reluctant to
add things that encourage bad practice to the users.

As Duy said, saving the "diff" output to another file, opening in an
editor that output file and the file the patch targets to modify,
and transferring the lines while dropping unnecessray parts (i.e.
unwanted context lines and preimage lines, and possibly undesired
postimage lines, and also the leading SP/+/- designators) has no
such downside.  It obviously has an added benefit that it makes it
less likely for people to cut and paste a line and then become
unsure if they really cut from the green line or they by mistake
also pasted an adjacent red line.

So, I'd say the answer is "probably not".

^ permalink raw reply

* Re: Git bisect does not find commit introducing the bug
From: Alex Hoffman @ 2017-02-19 19:05 UTC (permalink / raw)
  To: Johannes Sixt; +Cc: Christian Couder, Stephan Beyer, git
In-Reply-To: <d7bb866d-4a50-f75e-ff4c-bcdd54f75459@kdbg.org>

> Then you must adjust your definition of "good": All commits that do not have
> the feature, yet, are "good": since they do not have the feature in the
> first place, they cannot have the breakage that you found in the feature.
>
> That is exactly the situation in your original example! But you constructed
> the condition of goodness in such a simplistic way (depending on the
> presence of a string), that it was impossible to distinguish between "does
> not have the feature at all" and "has the feature, but it is broken".

Johannes, thank you for correctly identifying the error in my logic.
Indeed I was using the term 'bad' also for the commit without the
feature. In order to find the commit introducing the bug in my example
a new state is needed, which would make 'git bisect' a bit more
complicated than the user 'most of the time' probably needs. Or do you
think, it would make sense to ask the user for this state (if e.g 'git
bisect' would be started with a new parameter)?

^ permalink raw reply

* Re: Git bisect does not find commit introducing the bug
From: Jacob Keller @ 2017-02-19 19:25 UTC (permalink / raw)
  To: Alex Hoffman; +Cc: Johannes Sixt, Christian Couder, Stephan Beyer, git
In-Reply-To: <CAMX8fZWRgeK5XjSrFYzZea8YgT9Mqm0XJBxQGt1eqdWZU+DEnA@mail.gmail.com>

On Sun, Feb 19, 2017 at 11:05 AM, Alex Hoffman <spec@gal.ro> wrote:
>> Then you must adjust your definition of "good": All commits that do not have
>> the feature, yet, are "good": since they do not have the feature in the
>> first place, they cannot have the breakage that you found in the feature.
>>
>> That is exactly the situation in your original example! But you constructed
>> the condition of goodness in such a simplistic way (depending on the
>> presence of a string), that it was impossible to distinguish between "does
>> not have the feature at all" and "has the feature, but it is broken".
>
> Johannes, thank you for correctly identifying the error in my logic.
> Indeed I was using the term 'bad' also for the commit without the
> feature. In order to find the commit introducing the bug in my example
> a new state is needed, which would make 'git bisect' a bit more
> complicated than the user 'most of the time' probably needs. Or do you
> think, it would make sense to ask the user for this state (if e.g 'git
> bisect' would be started with a new parameter)?

If a commit doesn't have the feature, then it is by definition, not
containing a broken feature, and you can simply use the "good" state.
There is no need for a different state. If you can't test the commit
because it's broken in some other way, you can use "git bisect skip"
but that isn't what you want in this case.

Thanks,
Jake

^ permalink raw reply

* Draft of Git Rev News edition 24
From: Christian Couder @ 2017-02-19 20:37 UTC (permalink / raw)
  To: git
  Cc: Thomas Ferris Nicolaisen, Jakub Narebski, Markus Jansen,
	Michael J Gruber, Junio C Hamano, Johannes Schindelin, Jeff King,
	Stefan Beller, Jacob Vosmaer,
	Ævar Arnfjörð Bjarmason, Josh Triplett,
	Erik van Zijst, Brendan Forster, Stefan Saasen, David Turner,
	Nguyen Thai Ngoc Duy, Shawn O. Pierce, Carlos Martín Nieto,
	Charles Bailey

Hi,

A draft of a new Git Rev News edition is available here:

  https://github.com/git/git.github.io/blob/master/rev_news/drafts/edition-24.md

Everyone is welcome to contribute in any section either by editing the
above page on GitHub and sending a pull request, or by commenting on
this GitHub issue:

  https://github.com/git/git.github.io/issues/221

You can also reply to this email.

In general all kinds of contribution, for example proofreading,
suggestions for articles or links, help on the issues in GitHub, and
so on, are very much appreciated.

I tried to cc everyone who appears in this edition, but maybe I missed
some people, sorry about that.

Thomas, Jakub, Markus and myself plan to publish this edition on
Wednesday February 22.

Thanks,
Christian.

^ permalink raw reply

* Re: [PATCH] git-check-ref-format: fix typo in man page
From: Philip Oakley @ 2017-02-19 20:40 UTC (permalink / raw)
  To: Jeff King; +Cc: Michael Haggerty, Damien Regad, git
In-Reply-To: <20170219022756.pwxhjluxizuedf46@sigill.intra.peff.net>

From: "Jeff King" <peff@peff.net>
> On Sun, Feb 19, 2017 at 12:20:33AM -0000, Philip Oakley wrote:
>
>> >  Normalize 'refname' by removing any leading slash (`/`)
>> >  characters and collapsing runs of adjacent slashes between
>> > - name components into a single slash.  Iff the normalized
>> > + name components into a single slash.  If the normalized
>> >  refname is valid then print it to standard output and exit
>> >  with a status of 0.  (`--print` is a deprecated way to spell
>> >  `--normalize`.)
>> > -- 
>>
>> Could that be an 'iff' == 'If and only if' (which is common in 
>> mathematics)?
>> Still could be spelling error though.
>
> When we're not sure what the intent of a change is, a good first step is
> to dig up the original commit via `git blame` or similar. In this case,
> it comes from a40e6fb67 (Change check_refname_format() to reject
> unnormalized refnames, 2011-09-15).

Oops, blaming a bit of code feels 'obvious' but I just hadn't thought to 
blame the doc, though it does feel as though code and the docs don't always 
go hand in hand.

>
> The commit message doesn't mention it (not that I really expected it
> to), but it does tell you who the author is. And a good second step is
> to cc them on the patch. :)
>
> I suspect it _was_ intended as "iff" here. In my opinion, we probably
> don't need to be so rigorous in this instance. However, I note that we
> do not describe the "else" half of that "if". So maybe an overall
> improvement would be something like:

I read the commit message the same, that is, only if the given ref name 
normalises to a true (properly formatted) ref will it be printed (sucess).

For those not familiar with 'iff', then a change to the doc is worthwhile.

>
>  If the normalized refname is valid then print it to standard output
>  and exit with a status of 0. Otherwise, exit with a non-zero status.
>
> -Peff
>
Thanks, Philip. 


^ permalink raw reply

* url.<base>.insteadOf vs. submodules
From: Toolforger @ 2017-02-19 21:12 UTC (permalink / raw)
  To: git

Hi all,

I am trying to make url.<base>.insteadOf work on the URLs inside 
.gitmodules, but it won't work (applying it to the repo itself works 
fine, to the config setting seems to be fine).

I do not want to modify .gitmodules: It is maintained upstream.

I cannot simply reconfigure submodule.<module>.url: the Configure script 
(regularly called during each compile) does
   git submodule sync
   git submodule update --init
I could tell upstream to change these commands if I can make a good 
argument; for them, it is relevant that they can change the submodule 
URL inside .gitmodule and have it "just work" for everybody downstream.

My own use case is that I want to be able to work with various 
experimental local clones even if I do not have Internet access.
I'm all ears if there's a way to do this without using insteadOf.


Here are the relevant two lines from the output of "git config -l" 
(after "git submodule init"):

url./home/jo/Projekte/perl6/bare-repos.insteadof=https://github.com
submodule.3rdparty/dynasm.url=https://github.com/MoarVM/dynasm.git


Here is what "git submodule update" does:

Cloning into '3rdparty/dyncall'...
fatal: unable to access 'https://github.com/MoarVM/dyncall.git/': Could 
not resolve host: github.com
fatal: clone of 'https://github.com/MoarVM/dyncall.git' into submodule 
path '3rdparty/dyncall' failed


Any help appreciated!

Regards,
Jo

^ permalink raw reply

* Re: [PATCH v2] l10n: de.po: translate 241 messages
From: Phillip Sz @ 2017-02-19 21:29 UTC (permalink / raw)
  To: Ralf Thielow, git
  Cc: Thomas Rast, Jan Krüger, Christian Stimming,
	Matthias Rüster, Magnus Görlitz
In-Reply-To: <20170219181152.9410-1-ralf.thielow@gmail.com>

Acked-by: Phillip Sz <phillip.szelat@gmail.com>

> Signed-off-by: Ralf Thielow <ralf.thielow@gmail.com>
> ---
>  po/de.po | 750 ++++++++++++++++++++++++++++++++++-----------------------------
>  1 file changed, 409 insertions(+), 341 deletions(-)
> 
> diff --git a/po/de.po b/po/de.po
> index 2326da1fd..e9c86f548 100644
> --- a/po/de.po
> +++ b/po/de.po
> @@ -913,20 +913,20 @@ msgstr ""
>  
>  #: bisect.c:742
>  #, c-format
>  msgid ""
>  "The merge base %s is %s.\n"
>  "This means the first '%s' commit is between %s and [%s].\n"
>  msgstr ""
>  "Die Merge-Basis %s ist %s.\n"
> -"Das bedeutet, der erste '%s' Commit befindet sich zwischen %s und [%s]\n"
> +"Das bedeutet, der erste '%s' Commit befindet sich zwischen %s und [%s].\n"
>  
>  #: bisect.c:750
> -#, fuzzy, c-format
> +#, c-format
>  msgid ""
>  "Some %s revs are not ancestors of the %s rev.\n"
>  "git bisect cannot work properly in this case.\n"
>  "Maybe you mistook %s and %s revs?\n"
>  msgstr ""
>  "Manche %s Commits sind keine Vorgänger des %s Commits.\n"
>  "git bisect kann in diesem Fall nicht richtig arbeiten.\n"
>  "Vielleicht verwechselten Sie %s und %s Commits?\n"
> @@ -1343,19 +1343,19 @@ msgid "bad zlib compression level %d"
>  msgstr "ungültiger zlib Komprimierungsgrad %d"
>  
>  #: config.c:993
>  #, c-format
>  msgid "invalid mode for object creation: %s"
>  msgstr "Ungültiger Modus für Objekterstellung: %s"
>  
>  #: config.c:1149
> -#, fuzzy, c-format
> +#, c-format
>  msgid "bad pack compression level %d"
> -msgstr "Komprimierungsgrad für Paketierung"
> +msgstr "ungültiger Komprimierungsgrad (%d) für Paketierung"
>  
>  #: config.c:1339
>  msgid "unable to parse command-line config"
>  msgstr ""
>  "Konnte die über die Befehlszeile angegebene Konfiguration nicht parsen."
>  
>  #: config.c:1389
>  msgid "unknown error occurred while reading the configuration files"
> @@ -1375,19 +1375,19 @@ msgid "bad config variable '%s' in file '%s' at line %d"
>  msgstr "ungültige Konfigurationsvariable '%s' in Datei '%s' bei Zeile %d"
>  
>  #: config.c:1804
>  #, c-format
>  msgid "%s has multiple values"
>  msgstr "%s hat mehrere Werte"
>  
>  #: config.c:2225 config.c:2450
> -#, fuzzy, c-format
> +#, c-format
>  msgid "fstat on %s failed"
> -msgstr "\"stash\" fehlgeschlagen"
> +msgstr "fstat auf %s fehlgeschlagen"
>  
>  #: config.c:2343
>  #, c-format
>  msgid "could not set '%s' to '%s'"
>  msgstr "Konnte '%s' nicht zu '%s' setzen."
>  
>  #: config.c:2345
>  #, c-format
> @@ -1616,19 +1616,19 @@ msgstr "Fehler beim Sammeln von Namen und Informationen zum Kernel"
>  
>  #: dir.c:1981
>  msgid "Untracked cache is disabled on this system or location."
>  msgstr ""
>  "Cache für unversionierte Dateien ist auf diesem System oder\n"
>  "für dieses Verzeichnis deaktiviert."
>  
>  #: dir.c:2759
> -#, fuzzy, c-format
> +#, c-format
>  msgid "could not migrate git directory from '%s' to '%s'"
> -msgstr "Konnte Verzeichnis '%s' nicht erstellen."
> +msgstr "Konnte Git-Verzeichnis nicht von '%s' nach '%s' migrieren."
>  
>  #: fetch-pack.c:213
>  msgid "git fetch-pack: expected shallow list"
>  msgstr "git fetch-pack: erwartete shallow-Liste"
>  
>  #: fetch-pack.c:225
>  msgid "git fetch-pack: expected ACK/NAK, got EOF"
>  msgstr "git fetch-pack: ACK/NAK erwartet, EOF bekommen"
> @@ -1803,17 +1803,17 @@ msgstr "konnte temporäre Datei nicht erstellen"
>  #: gpg-interface.c:217
>  #, c-format
>  msgid "failed writing detached signature to '%s'"
>  msgstr "Fehler beim Schreiben der losgelösten Signatur nach '%s'"
>  
>  #: graph.c:96
>  #, c-format
>  msgid "ignore invalid color '%.*s' in log.graphColors"
> -msgstr ""
> +msgstr "Ignoriere ungültige Farbe '%.*s' in log.graphColors"
>  
>  #: grep.c:1794
>  #, c-format
>  msgid "'%s': unable to read %s"
>  msgstr "'%s': konnte %s nicht lesen"
>  
>  #: grep.c:1811 builtin/clone.c:381 builtin/diff.c:81 builtin/rm.c:133
>  #, c-format
> @@ -2320,17 +2320,17 @@ msgstr "%s: 'literal' und 'glob' sind inkompatibel"
>  #: pathspec.c:363
>  #, c-format
>  msgid "%s: '%s' is outside repository"
>  msgstr "%s: '%s' liegt außerhalb des Repositories"
>  
>  #: pathspec.c:451
>  #, c-format
>  msgid "'%s' (mnemonic: '%c')"
> -msgstr ""
> +msgstr "'%s' (Kürzel: '%c')"
>  
>  #: pathspec.c:461
>  #, c-format
>  msgid "%s: pathspec magic not supported by this command: %s"
>  msgstr ""
>  "%s: Pfadspezifikationsangabe wird von diesem Befehl nicht unterstützt: %s"
>  
>  #: pathspec.c:511
> @@ -2418,19 +2418,19 @@ msgid "%%(body) does not take arguments"
>  msgstr "%%(body) akzeptiert keine Argumente"
>  
>  #: ref-filter.c:85
>  #, c-format
>  msgid "%%(subject) does not take arguments"
>  msgstr "%%(subject) akzeptiert keine Argumente"
>  
>  #: ref-filter.c:92
> -#, fuzzy, c-format
> +#, c-format
>  msgid "%%(trailers) does not take arguments"
> -msgstr "%%(body) akzeptiert keine Argumente"
> +msgstr "%%(trailers) akzeptiert keine Argumente"
>  
>  #: ref-filter.c:111
>  #, c-format
>  msgid "positive value expected contents:lines=%s"
>  msgstr "Positiver Wert erwartet contents:lines=%s"
>  
>  #: ref-filter.c:113
>  #, c-format
> @@ -2613,32 +2613,30 @@ msgstr "  (benutzen Sie \"git branch --unset-upstream\" zum Beheben)\n"
>  #, c-format
>  msgid "Your branch is up-to-date with '%s'.\n"
>  msgstr "Ihr Branch ist auf dem selben Stand wie '%s'.\n"
>  
>  #: remote.c:2092
>  #, c-format
>  msgid "Your branch is ahead of '%s' by %d commit.\n"
>  msgid_plural "Your branch is ahead of '%s' by %d commits.\n"
> -msgstr[0] "Ihr Branch ist vor '%s' um %d Commit.\n"
> -msgstr[1] "Ihr Branch ist vor '%s' um %d Commits.\n"
> +msgstr[0] "Ihr Branch ist %2$d Commit vor '%1$s'.\n"
> +msgstr[1] "Ihr Branch ist %2$d Commits vor '%1$s'.\n"
>  
>  #: remote.c:2098
>  msgid "  (use \"git push\" to publish your local commits)\n"
>  msgstr "  (benutzen Sie \"git push\", um lokale Commits zu publizieren)\n"
>  
>  #: remote.c:2101
>  #, c-format
>  msgid "Your branch is behind '%s' by %d commit, and can be fast-forwarded.\n"
>  msgid_plural ""
>  "Your branch is behind '%s' by %d commits, and can be fast-forwarded.\n"
> -msgstr[0] ""
> -"Ihr Branch ist zu '%s' um %d Commit hinterher, und kann vorgespult werden.\n"
> -msgstr[1] ""
> -"Ihr Branch ist zu '%s' um %d Commits hinterher, und kann vorgespult werden.\n"
> +msgstr[0] "Ihr Branch ist %2$d Commit hinter '%1$s', und kann vorgespult werden.\n"
> +msgstr[1] "Ihr Branch ist %2$d Commits hinter '%1$s', und kann vorgespult werden.\n"
>  
>  #: remote.c:2109
>  msgid "  (use \"git pull\" to update your local branch)\n"
>  msgstr ""
>  "  (benutzen Sie \"git pull\", um Ihren lokalen Branch zu aktualisieren)\n"
>  
>  #: remote.c:2112
>  #, c-format
> @@ -2712,24 +2710,23 @@ msgstr "die Gegenseite unterstützt keine Push-Optionen"
>  msgid "revert"
>  msgstr "Revert"
>  
>  #: sequencer.c:217
>  msgid "cherry-pick"
>  msgstr "Cherry-Pick"
>  
>  #: sequencer.c:219
> -#, fuzzy
>  msgid "rebase -i"
> -msgstr "Basis-Commit"
> +msgstr "interaktives Rebase"
>  
>  #: sequencer.c:221
> -#, fuzzy, c-format
> +#, c-format
>  msgid "Unknown action: %d"
> -msgstr "Unbekannter Typ: %d"
> +msgstr "Unbekannte Aktion: %d"
>  
>  #: sequencer.c:278
>  msgid ""
>  "after resolving the conflicts, mark the corrected paths\n"
>  "with 'git add <paths>' or 'git rm <paths>'"
>  msgstr ""
>  "nach Auflösung der Konflikte, markieren Sie die korrigierten Pfade\n"
>  "mit 'git add <Pfade>' oder 'git rm <Pfade>'"
> @@ -2844,72 +2841,76 @@ msgstr "Konnte Eltern-Commit %s nicht parsen\n"
>  
>  #: sequencer.c:815
>  #, c-format
>  msgid ""
>  "unexpected 1st line of squash message:\n"
>  "\n"
>  "\t%.*s"
>  msgstr ""
> +"unerwartete erste Zeile der Squash-Beschreibung:\n"
> +"\n"
> +"\t%.*s"
>  
>  #: sequencer.c:821
>  #, c-format
>  msgid ""
>  "invalid 1st line of squash message:\n"
>  "\n"
>  "\t%.*s"
>  msgstr ""
> +"ungültige erste Zeile der Squash-Beschreibung:\n"
> +"\n"
> +"\t%.*s"
>  
>  #: sequencer.c:827 sequencer.c:852
> -#, fuzzy, c-format
> +#, c-format
>  msgid "This is a combination of %d commits."
> -msgstr "Das ist eine Kombination aus 2 Commits."
> +msgstr "Das ist eine Kombination aus %d Commits."
>  
>  #: sequencer.c:836
>  msgid "need a HEAD to fixup"
> -msgstr ""
> +msgstr "benötige HEAD für fixup"
>  
>  #: sequencer.c:838
> -#, fuzzy
>  msgid "could not read HEAD"
> -msgstr "Konnte HEAD nicht loslösen"
> +msgstr "Konnte HEAD nicht lesen"
>  
>  #: sequencer.c:840
> -#, fuzzy
>  msgid "could not read HEAD's commit message"
> -msgstr "Konnte Commit-Beschreibung nicht lesen: %s"
> +msgstr "Konnte Commit-Beschreibung von HEAD nicht lesen"
>  
>  #: sequencer.c:846
> -#, fuzzy, c-format
> +#, c-format
>  msgid "cannot write '%s'"
> -msgstr "kann '%s' nicht erstellen"
> +msgstr "kann '%s' nicht schreiben"
>  
>  #: sequencer.c:855 git-rebase--interactive.sh:445
>  msgid "This is the 1st commit message:"
>  msgstr "Das ist die erste Commit-Beschreibung:"
>  
>  #: sequencer.c:863
> -#, fuzzy, c-format
> +#, c-format
>  msgid "could not read commit message of %s"
> -msgstr "Konnte Commit-Beschreibung nicht lesen: %s"
> +msgstr "Konnte Commit-Beschreibung von %s nicht lesen."
>  
>  #: sequencer.c:870
> -#, fuzzy, c-format
> +#, c-format
>  msgid "This is the commit message #%d:"
> -msgstr "Das ist Commit-Beschreibung #${n}:"
> +msgstr "Das ist Commit-Beschreibung #%d:"
>  
>  #: sequencer.c:875
> -#, fuzzy, c-format
> +#, c-format
>  msgid "The commit message #%d will be skipped:"
> -msgstr "Commit-Beschreibung #${n} wird ausgelassen:"
> +msgstr "Die Commit-Beschreibung #%d wird ausgelassen:"
>  
>  #: sequencer.c:880
> -#, fuzzy, c-format
> +#, c-format
>  msgid "unknown command: %d"
> -msgstr "Unbekannter Unterbefehl: %s"
> +msgstr "Unbekannter Befehl: %d"
>  
>  #: sequencer.c:946
>  msgid "your index file is unmerged."
>  msgstr "Ihre Index-Datei ist nicht zusammengeführt."
>  
>  #: sequencer.c:964
>  #, c-format
>  msgid "commit %s is a merge but no -m option was given."
> @@ -2933,19 +2934,19 @@ msgstr "Kann keine Commit-Beschreibung für %s bekommen."
>  #. TRANSLATORS: The first %s will be a "todo" command like
>  #. "revert" or "pick", the second %s a SHA1.
>  #: sequencer.c:1001
>  #, c-format
>  msgid "%s: cannot parse parent commit %s"
>  msgstr "%s: kann Eltern-Commit %s nicht parsen"
>  
>  #: sequencer.c:1063 sequencer.c:1812
> -#, fuzzy, c-format
> +#, c-format
>  msgid "could not rename '%s' to '%s'"
> -msgstr "Konnte '%s' nicht zu '%s' setzen."
> +msgstr "Konnte '%s' nicht zu '%s' umbenennen."
>  
>  #: sequencer.c:1114
>  #, c-format
>  msgid "could not revert %s... %s"
>  msgstr "Konnte \"revert\" nicht auf %s... (%s) ausführen"
>  
>  #: sequencer.c:1115
>  #, c-format
> @@ -2967,29 +2968,28 @@ msgid "git %s: failed to refresh the index"
>  msgstr "git %s: Fehler beim Aktualisieren des Index"
>  
>  #: sequencer.c:1294
>  #, c-format
>  msgid "invalid line %d: %.*s"
>  msgstr "Ungültige Zeile %d: %.*s"
>  
>  #: sequencer.c:1302
> -#, fuzzy, c-format
> +#, c-format
>  msgid "cannot '%s' without a previous commit"
> -msgstr "Kann nicht '$squash_style' ohne vorherigen Commit"
> +msgstr "Kann '%s' nicht ohne vorherigen Commit ausführen"
>  
>  #: sequencer.c:1334
>  #, c-format
>  msgid "could not read '%s'."
>  msgstr "Konnte '%s' nicht lesen."
>  
>  #: sequencer.c:1341
> -#, fuzzy
>  msgid "please fix this using 'git rebase --edit-todo'."
> -msgstr "Bitte beheben Sie das, indem Sie 'git rebase --edit-todo' ausführen."
> +msgstr "Bitte beheben Sie dieses, indem Sie 'git rebase --edit-todo' ausführen."
>  
>  #: sequencer.c:1343
>  #, c-format
>  msgid "unusable instruction sheet: '%s'"
>  msgstr "Unbenutzbares Instruktionsblatt: '%s'"
>  
>  #: sequencer.c:1348
>  msgid "no commits parsed."
> @@ -3062,166 +3062,155 @@ msgid "unexpected end of file"
>  msgstr "Unerwartetes Dateiende"
>  
>  #: sequencer.c:1629
>  #, c-format
>  msgid "stored pre-cherry-pick HEAD file '%s' is corrupt"
>  msgstr "gespeicherte \"pre-cherry-pick\" HEAD Datei '%s' ist beschädigt"
>  
>  #: sequencer.c:1640
> -#, fuzzy
>  msgid "You seem to have moved HEAD. Not rewinding, check your HEAD!"
> -msgstr ""
> -"Sie scheinen seit dem letzten gescheiterten 'am' HEAD geändert zu haben.\n"
> -"Keine Zurücksetzung zu ORIG_HEAD."
> +msgstr "Sie scheinen HEAD verschoben zu haben. Keine Zurücksetzung, prüfen Sie HEAD."
>  
>  #: sequencer.c:1777 sequencer.c:2049
> -#, fuzzy
>  msgid "cannot read HEAD"
>  msgstr "Kann HEAD nicht lesen"
>  
>  #: sequencer.c:1817 builtin/difftool.c:574
> -#, fuzzy, c-format
> +#, c-format
>  msgid "could not copy '%s' to '%s'"
> -msgstr "Konnte '%s' nicht zu '%s' setzen."
> +msgstr "Konnte '%s' nicht nach '%s' kopieren."
>  
>  #: sequencer.c:1833
> -#, fuzzy
>  msgid "could not read index"
> -msgstr "Konnte den Index nicht lesen"
> +msgstr "Konnte den Index nicht lesen."
>  
>  #: sequencer.c:1838
> -#, fuzzy, c-format
> +#, c-format
>  msgid ""
>  "execution failed: %s\n"
>  "%sYou can fix the problem, and then run\n"
>  "\n"
>  "  git rebase --continue\n"
>  "\n"
>  msgstr ""
> -"Sie können das Problem beheben, und dann\n"
> +"Ausführung fehlgeschlagen: %s\n"
> +"%sSie können das Problem beheben, und dann\n"
>  "\n"
>  "\tgit rebase --continue\n"
>  "\n"
> -"ausführen."
> +"ausführen.\n"
>  
>  #: sequencer.c:1844
> -#, fuzzy
>  msgid "and made changes to the index and/or the working tree\n"
> -msgstr "Der Index und/oder das Arbeitsverzeichnis wurde geändert."
> +msgstr "Der Index und/oder das Arbeitsverzeichnis wurde geändert.\n"
>  
>  #: sequencer.c:1850
> -#, fuzzy, c-format
> +#, c-format
>  msgid ""
>  "execution succeeded: %s\n"
>  "but left changes to the index and/or the working tree\n"
>  "Commit or stash your changes, and then run\n"
>  "\n"
>  "  git rebase --continue\n"
>  "\n"
>  msgstr ""
> -"Ausführung erfolgreich: $rest\n"
> +"Ausführung erfolgreich: %s\n"
>  "Aber Änderungen in Index oder Arbeitsverzeichnis verblieben.\n"
>  "Committen Sie Ihre Änderungen oder benutzen Sie \"stash\".\n"
>  "Führen Sie dann aus:\n"
>  "\n"
> -"\tgit rebase --continue"
> +"  git rebase --continue\n"
> +"\n"
>  
>  #: sequencer.c:1905 git-rebase.sh:168
>  #, c-format
>  msgid "Applied autostash."
>  msgstr "Automatischen Stash angewendet."
>  
>  #: sequencer.c:1917
> -#, fuzzy, c-format
> +#, c-format
>  msgid "cannot store %s"
> -msgstr "kann '%s' nicht öffnen"
> +msgstr "kann %s nicht speichern"
>  
>  #: sequencer.c:1919 git-rebase.sh:172
>  #, c-format
>  msgid ""
>  "Applying autostash resulted in conflicts.\n"
>  "Your changes are safe in the stash.\n"
>  "You can run \"git stash pop\" or \"git stash drop\" at any time.\n"
>  msgstr ""
>  "Anwendung des automatischen Stash resultierte in Konflikten.\n"
>  "Ihre Änderungen sind im Stash sicher.\n"
>  "Sie können jederzeit \"git stash pop\" oder \"git stash drop\" ausführen.\n"
>  
>  #: sequencer.c:2000
> -#, fuzzy, c-format
> +#, c-format
>  msgid "stopped at %s... %.*s"
> -msgstr "Anwendung des Patches fehlgeschlagen bei %s %.*s"
> +msgstr "Angehalten bei %s... %.*s"
>  
>  #: sequencer.c:2027
> -#, fuzzy, c-format
> +#, c-format
>  msgid "unknown command %d"
> -msgstr "Unbekannter Unterbefehl: %s"
> +msgstr "Unbekannter Befehl %d"
>  
>  #: sequencer.c:2057
> -#, fuzzy
>  msgid "could not read orig-head"
> -msgstr "Konnte Referenz %s nicht lesen."
> +msgstr "Konnte orig-head nicht lesen."
>  
>  #: sequencer.c:2061
> -#, fuzzy
>  msgid "could not read 'onto'"
> -msgstr "Konnte '%s' nicht lesen"
> +msgstr "Konnte 'onto' nicht lesen."
>  
>  #: sequencer.c:2068
> -#, fuzzy, c-format
> +#, c-format
>  msgid "could not update %s"
> -msgstr "konnte %s nicht parsen"
> +msgstr "Konnte %s nicht aktualisieren."
>  
>  #: sequencer.c:2075
> -#, fuzzy, c-format
> +#, c-format
>  msgid "could not update HEAD to %s"
> -msgstr "Konnte nicht nach '%s' schreiben."
> +msgstr "Konnte HEAD nicht auf %s aktualisieren."
>  
>  #: sequencer.c:2159
> -#, fuzzy
>  msgid "cannot rebase: You have unstaged changes."
>  msgstr ""
> -"Rebase nicht möglich: Sie haben Änderungen, die nicht zum Commit vorgemerkt "
> -"sind."
> +"Rebase nicht möglich: Sie haben Änderungen, die nicht zum Commit\n"
> +"vorgemerkt sind."
>  
>  #: sequencer.c:2164
> -#, fuzzy
>  msgid "could not remove CHERRY_PICK_HEAD"
> -msgstr "Konnte CHERRY_PICK_HEAD nicht löschen"
> +msgstr "Konnte CHERRY_PICK_HEAD nicht löschen."
>  
>  #: sequencer.c:2173
> -#, fuzzy
>  msgid "cannot amend non-existing commit"
> -msgstr "Kann existierendes Objekt %s nicht lesen."
> +msgstr "Kann nicht existierenden Commit nicht nachbessern."
>  
>  #: sequencer.c:2175
> -#, fuzzy, c-format
> +#, c-format
>  msgid "invalid file: '%s'"
> -msgstr "Ungültiger Schlüssel: %s"
> +msgstr "Ungültige Datei: '%s'"
>  
>  #: sequencer.c:2177
> -#, fuzzy, c-format
> +#, c-format
>  msgid "invalid contents: '%s'"
> -msgstr "Ungültige Option: %s"
> +msgstr "Ungültige Inhalte: '%s'"
>  
>  #: sequencer.c:2180
> -#, fuzzy
>  msgid ""
>  "\n"
>  "You have uncommitted changes in your working tree. Please, commit them\n"
>  "first and then run 'git rebase --continue' again."
>  msgstr ""
> +"\n"
>  "Sie haben nicht committete Änderungen in Ihrem Arbeitsverzeichnis. Bitte\n"
> -"committen Sie diese zuerst und führen Sie dann 'git rebase --continue' "
> -"erneut\n"
> -"aus."
> +"committen Sie diese zuerst und führen Sie dann 'git rebase --continue'\n"
> +"erneut aus."
>  
>  #: sequencer.c:2190
> -#, fuzzy
>  msgid "could not commit staged changes."
>  msgstr "Konnte Änderungen aus der Staging-Area nicht committen."
>  
>  #: sequencer.c:2270
>  #, c-format
>  msgid "%s: can't cherry-pick a %s"
>  msgstr "%s: %s kann nicht in \"cherry-pick\" benutzt werden"
>  
> @@ -3416,54 +3405,59 @@ msgstr "Konnte Eintrag '%s' nicht aus .gitmodules entfernen"
>  msgid "staging updated .gitmodules failed"
>  msgstr "Konnte aktualisierte .gitmodules-Datei nicht zum Commit vormerken"
>  
>  #: submodule.c:159
>  msgid "negative values not allowed for submodule.fetchJobs"
>  msgstr "Negative Werte für submodule.fetchJobs nicht erlaubt"
>  
>  #: submodule.c:1184
> -#, fuzzy, c-format
> +#, c-format
>  msgid "could not start 'git status in submodule '%s'"
> -msgstr "Konnte Submodul-Verzeichnis '%s' nicht finden."
> +msgstr "Konnte 'git status' in Submodul '%s' nicht starten."
>  
>  #: submodule.c:1197
> -#, fuzzy, c-format
> +#, c-format
>  msgid "could not run 'git status in submodule '%s'"
> -msgstr "konnte Datei '%s' nicht erstellen"
> +msgstr "konnte 'git status' in Submodul '%s' nicht ausführen"
>  
>  #: submodule.c:1398
>  #, c-format
>  msgid ""
>  "relocate_gitdir for submodule '%s' with more than one worktree not supported"
>  msgstr ""
> +"relocate_gitdir für Submodul '%s' mit mehr als einem Arbeitsverzeichnis\n"
> +"wird nicht unterstützt"
>  
>  #: submodule.c:1410 submodule.c:1471
> -#, fuzzy, c-format
> +#, c-format
>  msgid "could not lookup name for submodule '%s'"
> -msgstr "konnte '%s' nicht öffnen oder lesen"
> +msgstr "konnte Name für Submodul '%s' nicht nachschlagen"
>  
>  #: submodule.c:1414 submodule.c:1474 builtin/submodule--helper.c:640
>  #: builtin/submodule--helper.c:650
>  #, c-format
>  msgid "could not create directory '%s'"
>  msgstr "Konnte Verzeichnis '%s' nicht erstellen."
>  
>  #: submodule.c:1420
> -#, fuzzy, c-format
> +#, c-format
>  msgid ""
>  "Migrating git directory of '%s%s' from\n"
>  "'%s' to\n"
>  "'%s'\n"
> -msgstr "Fehler beim Kopieren der Notizen von '%s' nach '%s'"
> +msgstr ""
> +"Migriere Git-Verzeichnis von '%s%s' von\n"
> +"'%s' nach\n"
> +"'%s'\n"
>  
>  #: submodule.c:1512
> -#, fuzzy, c-format
> +#, c-format
>  msgid "could not recurse into submodule '%s'"
> -msgstr "Fehler bei Rekursion in Submodul-Pfad '$sm_path'"
> +msgstr "Fehler bei Rekursion in Submodul-Pfad '%s'"
>  
>  #: submodule-config.c:360
>  #, c-format
>  msgid "invalid value for %s"
>  msgstr "Ungültiger Wert für %s"
>  
>  #: trailer.c:240
>  #, c-format
> @@ -3646,17 +3640,17 @@ msgstr ""
>  msgid ""
>  "Your local changes to the following files would be overwritten by %s:\n"
>  "%%s"
>  msgstr ""
>  "Ihre lokalen Änderungen würden durch %s überschrieben werden.\n"
>  "%%s"
>  
>  #: unpack-trees.c:116
> -#, fuzzy, c-format
> +#, c-format
>  msgid ""
>  "Updating the following directories would lose untracked files in them:\n"
>  "%s"
>  msgstr ""
>  "Durch die Aktualisierung der folgenden Verzeichnisse würden unversionierte\n"
>  "Dateien in diesen Verzeichnissen verloren gehen:\n"
>  "%s"
>  
> @@ -4104,17 +4098,17 @@ msgstr "  (benutzen Sie \"git am --skip\", um diesen Patch auszulassen)"
>  #: wt-status.c:1047
>  msgid "  (use \"git am --abort\" to restore the original branch)"
>  msgstr ""
>  "  (benutzen Sie \"git am --abort\", um den ursprünglichen Branch "
>  "wiederherzustellen)"
>  
>  #: wt-status.c:1176
>  msgid "git-rebase-todo is missing."
> -msgstr ""
> +msgstr "git-rebase-todo fehlt."
>  
>  #: wt-status.c:1178
>  msgid "No commands done."
>  msgstr "Keine Befehle ausgeführt."
>  
>  #: wt-status.c:1181
>  #, c-format
>  msgid "Last command done (%d command done):"
> @@ -4343,42 +4337,40 @@ msgid "no changes added to commit\n"
>  msgstr "keine Änderungen zum Commit vorgemerkt\n"
>  
>  #: wt-status.c:1611
>  #, c-format
>  msgid ""
>  "nothing added to commit but untracked files present (use \"git add\" to "
>  "track)\n"
>  msgstr ""
> -"nichts zum Commit vorgemerkt, aber es gibt unversionierte Dateien (benutzen "
> -"Sie \"git add\" zum Versionieren)\n"
> +"nichts zum Commit vorgemerkt, aber es gibt unversionierte Dateien\n"
> +"(benutzen Sie \"git add\" zum Versionieren)\n"
>  
>  #: wt-status.c:1614
>  #, c-format
>  msgid "nothing added to commit but untracked files present\n"
>  msgstr "nichts zum Commit vorgemerkt, aber es gibt unversionierte Dateien\n"
>  
>  #: wt-status.c:1617
>  #, c-format
>  msgid "nothing to commit (create/copy files and use \"git add\" to track)\n"
>  msgstr ""
> -"nichts zu committen (Erstellen/Kopieren Sie Dateien und benutzen Sie \"git "
> -"add\" zum Versionieren)\n"
> +"nichts zu committen (Erstellen/Kopieren Sie Dateien und benutzen\n"
> +"Sie \"git add\" zum Versionieren)\n"
>  
>  #: wt-status.c:1620 wt-status.c:1625
>  #, c-format
>  msgid "nothing to commit\n"
>  msgstr "nichts zu committen\n"
>  
>  #: wt-status.c:1623
>  #, c-format
>  msgid "nothing to commit (use -u to show untracked files)\n"
> -msgstr ""
> -"nichts zu committen (benutzen Sie die Option -u, um unversionierte Dateien "
> -"anzuzeigen)\n"
> +msgstr "nichts zu committen (benutzen Sie die Option -u, um unversionierte Dateien anzuzeigen)\n"
>  
>  #: wt-status.c:1627
>  #, c-format
>  msgid "nothing to commit, working tree clean\n"
>  msgstr "nichts zu committen, Arbeitsverzeichnis unverändert\n"
>  
>  #: wt-status.c:1734
>  msgid "Initial commit on "
> @@ -5086,21 +5078,20 @@ msgid "Show author email instead of name (Default: off)"
>  msgstr ""
>  "Anstatt des Namens die E-Mail-Adresse des Autors anzeigen (Standard: aus)"
>  
>  #: builtin/blame.c:2597
>  msgid "Ignore whitespace differences"
>  msgstr "Unterschiede im Whitespace ignorieren"
>  
>  #: builtin/blame.c:2604
> -#, fuzzy
>  msgid "Use an experimental heuristic to improve diffs"
>  msgstr ""
> -"eine experimentelle, auf Einrückungen basierende Heuristik zur Verbesserung\n"
> -"der Darstellung von Unterschieden verwenden"
> +"eine experimentelle Heuristik zur Verbesserung der Darstellung\n"
> +"von Unterschieden verwenden"
>  
>  #: builtin/blame.c:2606
>  msgid "Spend extra cycles to find better match"
>  msgstr "Länger arbeiten, um bessere Übereinstimmungen zu finden"
>  
>  #: builtin/blame.c:2607
>  msgid "Use revisions from <file> instead of calling git-rev-list"
>  msgstr "Commits von <Datei> benutzen, anstatt \"git-rev-list\" aufzurufen"
> @@ -5520,17 +5511,17 @@ msgid "object"
>  msgstr "Objekt"
>  
>  #: builtin/branch.c:679
>  msgid "print only branches of the object"
>  msgstr "nur Branches von diesem Objekt ausgeben"
>  
>  #: builtin/branch.c:681 builtin/for-each-ref.c:46 builtin/tag.c:388
>  msgid "sorting and filtering are case insensitive"
> -msgstr ""
> +msgstr "Sortierung und Filterung sind unabhängig von Groß- und Kleinschreibung"
>  
>  #: builtin/branch.c:698
>  msgid "Failed to resolve HEAD as a valid ref."
>  msgstr "Konnte HEAD nicht als gültige Referenz auflösen."
>  
>  #: builtin/branch.c:702 builtin/clone.c:706
>  msgid "HEAD not found below refs/heads!"
>  msgstr "HEAD wurde nicht unter \"refs/heads\" gefunden!"
> @@ -6211,30 +6202,30 @@ msgid "Would skip repository %s\n"
>  msgstr "Würde Repository %s überspringen\n"
>  
>  #: builtin/clean.c:33
>  #, c-format
>  msgid "failed to remove %s"
>  msgstr "Fehler beim Löschen von %s"
>  
>  #: builtin/clean.c:291 git-add--interactive.perl:623
> -#, fuzzy, c-format
> +#, c-format
>  msgid ""
>  "Prompt help:\n"
>  "1          - select a numbered item\n"
>  "foo        - select item based on unique prefix\n"
>  "           - (empty) select nothing\n"
>  msgstr ""
>  "Eingabehilfe:\n"
>  "1          - nummeriertes Element auswählen\n"
>  "foo        - Element anhand eines eindeutigen Präfix auswählen\n"
> -"           - (leer) nichts auswählen"
> +"           - (leer) nichts auswählen\n"
>  
>  #: builtin/clean.c:295 git-add--interactive.perl:632
> -#, fuzzy, c-format
> +#, c-format
>  msgid ""
>  "Prompt help:\n"
>  "1          - select a single item\n"
>  "3-5        - select a range of items\n"
>  "2-3,6-9    - select multiple ranges\n"
>  "foo        - select item based on unique prefix\n"
>  "-...       - unselect specified items\n"
>  "*          - choose all items\n"
> @@ -6242,23 +6233,23 @@ msgid ""
>  msgstr ""
>  "Eingabehilfe:\n"
>  "1          - einzelnes Element auswählen\n"
>  "3-5        - Bereich von Elementen auswählen\n"
>  "2-3,6-9    - mehrere Bereiche auswählen\n"
>  "foo        - Element anhand eines eindeutigen Präfix auswählen\n"
>  "-...       - angegebenes Element abwählen\n"
>  "*          - alle Elemente auswählen\n"
> -"           - (leer) Auswahl beenden"
> +"           - (leer) Auswahl beenden\n"
>  
>  #: builtin/clean.c:511 git-add--interactive.perl:598
>  #: git-add--interactive.perl:603
> -#, fuzzy, c-format, perl-format
> +#, c-format, perl-format
>  msgid "Huh (%s)?\n"
> -msgstr "Wie bitte (%s)?"
> +msgstr "Wie bitte (%s)?\n"
>  
>  #: builtin/clean.c:653
>  #, c-format
>  msgid "Input ignore patterns>> "
>  msgstr "Ignorier-Muster eingeben>> "
>  
>  #: builtin/clean.c:690
>  #, c-format
> @@ -6271,19 +6262,19 @@ msgstr "Wählen Sie Einträge zum Löschen"
>  
>  #. TRANSLATORS: Make sure to keep [y/N] as is
>  #: builtin/clean.c:752
>  #, c-format
>  msgid "Remove %s [y/N]? "
>  msgstr "'%s' löschen [y/N]? "
>  
>  #: builtin/clean.c:777 git-add--interactive.perl:1669
> -#, fuzzy, c-format
> +#, c-format
>  msgid "Bye.\n"
> -msgstr "Tschüss."
> +msgstr "Tschüss.\n"
>  
>  #: builtin/clean.c:785
>  msgid ""
>  "clean               - start cleaning\n"
>  "filter by pattern   - exclude items from deletion\n"
>  "select by numbers   - select items to be deleted by numbers\n"
>  "ask each            - confirm each deletion (like \"rm -i\")\n"
>  "quit                - stop cleaning\n"
> @@ -6459,17 +6450,16 @@ msgstr ""
>  "Zeit\n"
>  "erstellen"
>  
>  #: builtin/clone.c:101 builtin/fetch.c:124
>  msgid "revision"
>  msgstr "Commit"
>  
>  #: builtin/clone.c:102 builtin/fetch.c:125
> -#, fuzzy
>  msgid "deepen history of shallow clone, excluding rev"
>  msgstr ""
>  "die Historie eines Klons mit unvollständiger Historie (shallow) mittels\n"
>  "Ausschluss eines Commits vertiefen"
>  
>  #: builtin/clone.c:104
>  msgid "clone only one branch, HEAD or --branch"
>  msgstr "nur einen Branch klonen, HEAD oder --branch"
> @@ -7699,100 +7689,101 @@ msgid "more than two blobs given: '%s'"
>  msgstr "Mehr als zwei Blobs angegeben: '%s'"
>  
>  #: builtin/diff.c:417
>  #, c-format
>  msgid "unhandled object '%s' given."
>  msgstr "unbehandeltes Objekt '%s' angegeben"
>  
>  #: builtin/difftool.c:28
> -#, fuzzy
>  msgid "git difftool [<options>] [<commit> [<commit>]] [--] [<path>...]"
> -msgstr "git log [<Optionen>] [<Commitbereich>] [[--] <Pfad>...]"
> +msgstr "git difftool [<Optionen>] [<Commit> [<Commit>]] [--] [<Pfad>...]"
>  
>  #: builtin/difftool.c:241
> -#, fuzzy, c-format
> +#, c-format
>  msgid "failed: %d"
> -msgstr "Anwendung des Patches fehlgeschlagen: %s:%ld"
> +msgstr "fehlgeschlagen: %d"
>  
>  #: builtin/difftool.c:342
>  msgid ""
>  "combined diff formats('-c' and '--cc') are not supported in\n"
>  "directory diff mode('-d' and '--dir-diff')."
>  msgstr ""
> +"Kombinierte Diff-Formate('-c' und '--cc') werden im Verzeichnis-\n"
> +"Diff-Modus('-d' und '--dir-diff') nicht unterstützt."
>  
>  #: builtin/difftool.c:567
>  #, c-format
>  msgid "both files modified: '%s' and '%s'."
> -msgstr ""
> +msgstr "beide Dateien geändert: '%s' und '%s'."
>  
>  #: builtin/difftool.c:569
> -#, fuzzy
>  msgid "working tree file has been left."
> -msgstr "Arbeitsverzeichnis '%s' existiert bereits."
> +msgstr "Datei im Arbeitsverzeichnis belassen."
>  
>  #: builtin/difftool.c:580
>  #, c-format
>  msgid "temporary files exist in '%s'."
> -msgstr ""
> +msgstr "Es existieren temporäre Dateien in '%s'."
>  
>  #: builtin/difftool.c:581
>  msgid "you may want to cleanup or recover these."
> -msgstr ""
> +msgstr "Sie könnten diese aufräumen oder wiederherstellen."
>  
>  #: builtin/difftool.c:626
>  msgid "use `diff.guitool` instead of `diff.tool`"
> -msgstr ""
> +msgstr "`diff.guitool` anstatt `diff.tool` benutzen"
>  
>  #: builtin/difftool.c:628
>  msgid "perform a full-directory diff"
> -msgstr ""
> +msgstr "Diff über ganzes Verzeichnis ausführen"
>  
>  #: builtin/difftool.c:630
>  msgid "do not prompt before launching a diff tool"
> -msgstr ""
> +msgstr "keine Eingabeaufforderung vor Ausführung eines Diff-Tools"
>  
>  #: builtin/difftool.c:636
>  msgid "use symlinks in dir-diff mode"
> -msgstr ""
> +msgstr "symbolische Verknüpfungen im dir-diff Modus verwenden"
>  
>  #: builtin/difftool.c:637
>  msgid "<tool>"
> -msgstr ""
> +msgstr "<Tool>"
>  
>  #: builtin/difftool.c:638
>  msgid "use the specified diff tool"
> -msgstr ""
> +msgstr "das angegebene Diff-Tool benutzen"
>  
>  #: builtin/difftool.c:640
>  msgid "print a list of diff tools that may be used with `--tool`"
> -msgstr ""
> +msgstr "eine Liste mit Diff-Tools darstellen, die mit `--tool` benutzt werden können"
>  
>  #: builtin/difftool.c:643
>  msgid ""
>  "make 'git-difftool' exit when an invoked diff tool returns a non - zero exit "
>  "code"
>  msgstr ""
> +"'git-difftool' beenden, wenn das aufgerufene Diff-Tool mit einem Rückkehrwert\n"
> +"verschieden 0 ausgeführt wurde"
>  
>  #: builtin/difftool.c:645
> -#, fuzzy
>  msgid "<command>"
> -msgstr "Programm"
> +msgstr "<Programm>"
>  
>  #: builtin/difftool.c:646
>  msgid "specify a custom command for viewing diffs"
> -msgstr ""
> +msgstr "eigenen Befehl zur Anzeige von Unterschieden angeben"
>  
>  #: builtin/difftool.c:670
>  msgid "no <tool> given for --tool=<tool>"
> -msgstr ""
> +msgstr "kein <Tool> für --tool=<Tool> angegeben"
>  
>  #: builtin/difftool.c:677
>  msgid "no <cmd> given for --extcmd=<cmd>"
> -msgstr ""
> +msgstr "kein <Programm> für --extcmd=<Programm> angegeben"
>  
>  #: builtin/fast-export.c:25
>  msgid "git fast-export [rev-list-opts]"
>  msgstr "git fast-export [rev-list-opts]"
>  
>  #: builtin/fast-export.c:980
>  msgid "show progress after <n> objects"
>  msgstr "Fortschritt nach <n> Objekten anzeigen"
> @@ -8399,29 +8390,26 @@ msgstr "auch in Inhalten finden, die nicht von Git verwaltet werden"
>  msgid "search in both tracked and untracked files"
>  msgstr "in versionierten und unversionierten Dateien suchen"
>  
>  #: builtin/grep.c:979
>  msgid "ignore files specified via '.gitignore'"
>  msgstr "Dateien, die über '.gitignore' angegeben sind, ignorieren"
>  
>  #: builtin/grep.c:981
> -#, fuzzy
>  msgid "recursivley search in each submodule"
> -msgstr "rekursive Anforderungen von Submodulen kontrollieren"
> +msgstr "rekursive Suche in jedem Submodul"
>  
>  #: builtin/grep.c:983
> -#, fuzzy
>  msgid "basename"
> -msgstr "umbenennen"
> +msgstr "Basisname"
>  
>  #: builtin/grep.c:984
> -#, fuzzy
>  msgid "prepend parent project's basename to output"
> -msgstr "dies an die Ausgabe der Submodul-Pfade voranstellen"
> +msgstr "Basisname des Elternprojektes an Ausgaben voranstellen"
>  
>  #: builtin/grep.c:987
>  msgid "show non-matching lines"
>  msgstr "Zeilen ohne Übereinstimmungen anzeigen"
>  
>  #: builtin/grep.c:989
>  msgid "case insensitive matching"
>  msgstr "Übereinstimmungen unabhängig von Groß- und Kleinschreibung finden"
> @@ -8590,17 +8578,17 @@ msgstr "ungültige Anzahl von Threads angegeben (%d)"
>  #: builtin/grep.c:1215
>  msgid "--open-files-in-pager only works on the worktree"
>  msgstr ""
>  "Die Option --open-files-in-pager kann nur innerhalb des "
>  "Arbeitsverzeichnisses verwendet werden."
>  
>  #: builtin/grep.c:1238
>  msgid "option not supported with --recurse-submodules."
> -msgstr ""
> +msgstr "Option wird mit --recurse-submodules nicht unterstützt."
>  
>  #: builtin/grep.c:1244
>  msgid "--cached or --untracked cannot be used with --no-index."
>  msgstr ""
>  "Die Optionen --cached und --untracked können nicht mit --no-index verwendet "
>  "werden."
>  
>  #: builtin/grep.c:1249
> @@ -9068,20 +9056,18 @@ msgstr "Name der Paketdatei '%s' endet nicht mit '.pack'"
>  msgid "bad %s"
>  msgstr "%s ist ungültig"
>  
>  #: builtin/index-pack.c:1734
>  msgid "--fix-thin cannot be used without --stdin"
>  msgstr "Die Option --fix-thin kann nicht ohne --stdin verwendet werden."
>  
>  #: builtin/index-pack.c:1736
> -#, fuzzy
>  msgid "--stdin requires a git repository"
> -msgstr ""
> -"Die Option --index kann nicht außerhalb eines Repositories verwendet werden."
> +msgstr "--stdin erfordert ein Git-Repository"
>  
>  #: builtin/index-pack.c:1744
>  msgid "--verify with no packfile name given"
>  msgstr "Die Option --verify wurde ohne Namen der Paketdatei angegeben."
>  
>  #: builtin/init-db.c:54
>  #, c-format
>  msgid "cannot stat '%s'"
> @@ -9762,19 +9748,18 @@ msgstr "git merge [<Optionen>] [<Commit>...]"
>  msgid "git merge [<options>] <msg> HEAD <commit>"
>  msgstr "git merge [<Optionen>] <Beschreibung> HEAD <Commit>"
>  
>  #: builtin/merge.c:48
>  msgid "git merge --abort"
>  msgstr "git merge --abort"
>  
>  #: builtin/merge.c:49
> -#, fuzzy
>  msgid "git merge --continue"
> -msgstr "git merge --abort"
> +msgstr "git merge --continue"
>  
>  #: builtin/merge.c:104
>  msgid "switch `m' requires a value"
>  msgstr "Schalter 'm' erfordert einen Wert."
>  
>  #: builtin/merge.c:141
>  #, c-format
>  msgid "Could not find merge strategy '%s'.\n"
> @@ -9854,19 +9839,18 @@ msgid "merge commit message (for a non-fast-forward merge)"
>  msgstr ""
>  "Commit-Beschreibung zusammenführen (für einen Merge, der kein Vorspulen war)"
>  
>  #: builtin/merge.c:227
>  msgid "abort the current in-progress merge"
>  msgstr "den sich im Gange befindlichen Merge abbrechen"
>  
>  #: builtin/merge.c:229
> -#, fuzzy
>  msgid "continue the current in-progress merge"
> -msgstr "den sich im Gange befindlichen Merge abbrechen"
> +msgstr "den sich im Gange befindlichen Merge fortsetzen"
>  
>  #: builtin/merge.c:231 builtin/pull.c:170
>  msgid "allow merging unrelated histories"
>  msgstr "erlaube das Zusammenführen von nicht zusammenhängenden Historien"
>  
>  #: builtin/merge.c:259
>  msgid "could not run stash."
>  msgstr "Konnte \"stash\" nicht ausführen."
> @@ -10004,32 +9988,30 @@ msgstr "Konnte '%s' nicht schließen"
>  msgid "not something we can merge in %s: %s"
>  msgstr "nichts was wir in %s zusammenführen können: %s"
>  
>  #: builtin/merge.c:1099
>  msgid "not something we can merge"
>  msgstr "nichts was wir zusammenführen können"
>  
>  #: builtin/merge.c:1167
> -#, fuzzy
>  msgid "--abort expects no arguments"
> -msgstr "%%(body) akzeptiert keine Argumente"
> +msgstr "--abort akzeptiert keine Argumente"
>  
>  #: builtin/merge.c:1171
>  msgid "There is no merge to abort (MERGE_HEAD missing)."
>  msgstr "Es gibt keinen Merge zum Abbrechen (MERGE_HEAD fehlt)"
>  
>  #: builtin/merge.c:1183
>  msgid "--continue expects no arguments"
> -msgstr ""
> +msgstr "--continue erwartet keine Argumente"
>  
>  #: builtin/merge.c:1187
> -#, fuzzy
>  msgid "There is no merge in progress (MERGE_HEAD missing)."
> -msgstr "Es gibt keinen Merge zum Abbrechen (MERGE_HEAD fehlt)"
> +msgstr "Es ist keine Merge im Gange (MERGE_HEAD fehlt)."
>  
>  #: builtin/merge.c:1203
>  msgid ""
>  "You have not concluded your merge (MERGE_HEAD exists).\n"
>  "Please, commit your changes before you merge."
>  msgstr ""
>  "Sie haben Ihren Merge nicht abgeschlossen (MERGE_HEAD existiert).\n"
>  "Bitte committen Sie Ihre Änderungen, bevor Sie den Merge ausführen."
> @@ -11641,17 +11623,16 @@ msgstr "Anwendung des Filters für partielles Auschecken überspringen"
>  msgid "debug unpack-trees"
>  msgstr "unpack-trees protokollieren"
>  
>  #: builtin/receive-pack.c:26
>  msgid "git receive-pack <git-dir>"
>  msgstr "git receive-pack <Git-Verzeichnis>"
>  
>  #: builtin/receive-pack.c:793
> -#, fuzzy
>  msgid ""
>  "By default, updating the current branch in a non-bare repository\n"
>  "is denied, because it will make the index and work tree inconsistent\n"
>  "with what you pushed, and will require 'git reset --hard' to match\n"
>  "the work tree to HEAD.\n"
>  "\n"
>  "You can set the 'receive.denyCurrentBranch' configuration variable\n"
>  "to 'ignore' or 'warn' in the remote repository to allow pushing into\n"
> @@ -11664,17 +11645,17 @@ msgid ""
>  msgstr ""
>  "Standardmäßig wird die Aktualisierung des aktuellen Branches in einem\n"
>  "nicht-Bare-Repository zurückgewiesen, da dies den Index und das Arbeits-\n"
>  "verzeichnis inkonsistent zu dem machen würde, was Sie gepushed haben, und\n"
>  "'git reset --hard' erforderlich wäre, damit das Arbeitsverzeichnis HEAD\n"
>  "entspricht.\n"
>  "\n"
>  "Sie könnten die Konfigurationsvariable 'receive.denyCurrentBranch' im\n"
> -"Remote-Repository zu 'ignore' oder 'warn' setzen, um den Push in den\n"
> +"Remote-Repository auf 'ignore' oder 'warn' setzen, um den Push in den\n"
>  "aktuellen Branch zu erlauben; dies wird jedoch nicht empfohlen außer\n"
>  "Sie stellen durch andere Wege die Aktualität des Arbeitsverzeichnisses\n"
>  "gegenüber dem gepushten Stand sicher.\n"
>  "\n"
>  "Um diese Meldung zu unterdrücken und das Standardverhalten zu behalten,\n"
>  "setzen Sie die Konfigurationsvariable 'receive.denyCurrentBranch' auf\n"
>  "'refuse'."
>  
> @@ -12237,16 +12218,19 @@ msgstr "Unbekannter Unterbefehl: %s"
>  msgid "git repack [<options>]"
>  msgstr "git repack [<Optionen>]"
>  
>  #: builtin/repack.c:22
>  msgid ""
>  "Incremental repacks are incompatible with bitmap indexes.  Use\n"
>  "--no-write-bitmap-index or disable the pack.writebitmaps configuration."
>  msgstr ""
> +"Schrittweises Neupacken ist mit Bitmap-Indexen inkompatibel. Benutzen Sie\n"
> +"--no-write-bitmap-index oder deaktivieren Sie die pack.writebitmaps\n"
> +"Konfiguration."
>  
>  #: builtin/repack.c:166
>  msgid "pack everything in a single pack"
>  msgstr "alles in eine einzige Pack-Datei packen"
>  
>  #: builtin/repack.c:168
>  msgid "same as -a, and turn unreachable objects loose"
>  msgstr "genau wie -a, unerreichbare Objekte werden aber nicht gelöscht"
> @@ -12740,19 +12724,19 @@ msgid "not removing '%s' recursively without -r"
>  msgstr "'%s' wird nicht ohne -r rekursiv entfernt"
>  
>  #: builtin/rm.c:347
>  #, c-format
>  msgid "git rm: unable to remove %s"
>  msgstr "git rm: konnte %s nicht löschen"
>  
>  #: builtin/rm.c:370
> -#, fuzzy, c-format
> +#, c-format
>  msgid "could not remove '%s'"
> -msgstr "Konnte Referenz '%s' nicht auflösen"
> +msgstr "Konnte '%s' nicht löschen"
>  
>  #: builtin/send-pack.c:18
>  msgid ""
>  "git send-pack [--all | --mirror] [--dry-run] [--force] [--receive-pack=<git-"
>  "receive-pack>] [--verbose] [--thin] [--atomic] [<host>:]<directory> "
>  "[<ref>...]\n"
>  "  --all and explicit <ref> specification are mutually exclusive."
>  msgstr ""
> @@ -12779,17 +12763,17 @@ msgid "print status from remote helper"
>  msgstr "Status des Remote-Helpers ausgeben"
>  
>  #: builtin/shortlog.c:13
>  msgid "git shortlog [<options>] [<revision-range>] [[--] [<path>...]]"
>  msgstr "git shortlog [<Optionen>] [<Commitbereich>] [[--] [<Pfad>...]]"
>  
>  #: builtin/shortlog.c:249
>  msgid "Group by committer rather than author"
> -msgstr ""
> +msgstr "über Commit-Ersteller anstatt Autor gruppieren"
>  
>  #: builtin/shortlog.c:251
>  msgid "sort output according to the number of commits per author"
>  msgstr "die Ausgabe entsprechend der Anzahl von Commits pro Autor sortieren"
>  
>  #: builtin/shortlog.c:253
>  msgid "Suppress commit descriptions, only provides commit count"
>  msgstr "Commit-Beschreibungen unterdrücken, nur Anzahl der Commits liefern"
> @@ -13217,33 +13201,31 @@ msgstr "Fehlerhafter Wert für --update Parameter"
>  msgid ""
>  "Submodule (%s) branch configured to inherit branch from superproject, but "
>  "the superproject is not on any branch"
>  msgstr ""
>  "Branch von Submodul (%s) ist konfiguriert, den Branch des Hauptprojektes\n"
>  "zu erben, aber das Hauptprojekt befindet sich auf keinem Branch."
>  
>  #: builtin/submodule--helper.c:1106
> -#, fuzzy
>  msgid "recurse into submodules"
> -msgstr "Rekursion in Submodulen durchführen"
> +msgstr "Rekursion in Submodule durchführen"
>  
>  #: builtin/submodule--helper.c:1112
> -#, fuzzy
>  msgid "git submodule--helper embed-git-dir [<path>...]"
> -msgstr "git submodule--helper init [<Pfad>]"
> +msgstr "git submodule--helper embed-git-dir [<Pfad>...]"
>  
>  #: builtin/submodule--helper.c:1157
>  msgid "submodule--helper subcommand must be called with a subcommand"
>  msgstr "submodule--helper muss mit einem Unterbefehl aufgerufen werden"
>  
>  #: builtin/submodule--helper.c:1164
> -#, fuzzy, c-format
> +#, c-format
>  msgid "%s doesn't support --super-prefix"
> -msgstr "Server unterstützt kein --deepen"
> +msgstr "%s unterstützt kein --super-prefix"
>  
>  #: builtin/submodule--helper.c:1170
>  #, c-format
>  msgid "'%s' is not a valid submodule--helper subcommand"
>  msgstr "'%s' ist kein gültiger Unterbefehl von submodule--helper"
>  
>  #: builtin/symbolic-ref.c:7
>  msgid "git symbolic-ref [<options>] <name> [<ref>]"
> @@ -13290,19 +13272,18 @@ msgstr "git tag -d <Tagname>..."
>  msgid ""
>  "git tag -l [-n[<num>]] [--contains <commit>] [--points-at <object>]\n"
>  "\t\t[--format=<format>] [--[no-]merged [<commit>]] [<pattern>...]"
>  msgstr ""
>  "git tag -l [-n[<Nummer>]] [--contains <Commit>] [--points-at <Objekt>]\n"
>  "\t\t[--format=<Muster>] [--[no-]merged [<Commit>]] [<Muster>...]"
>  
>  #: builtin/tag.c:27
> -#, fuzzy
>  msgid "git tag -v [--format=<format>] <tagname>..."
> -msgstr "git tag -v <Tagname>..."
> +msgstr "git tag -v [--format=<Format>] <Tagname>..."
>  
>  #: builtin/tag.c:82
>  #, c-format
>  msgid "tag name too long: %.*s..."
>  msgstr "Tagname zu lang: %.*s..."
>  
>  #: builtin/tag.c:87
>  #, c-format
> @@ -13762,19 +13743,18 @@ msgstr "git verify-pack [-v | --verbose] [-s | --stat-only] <Paket>..."
>  msgid "verbose"
>  msgstr "erweiterte Ausgaben"
>  
>  #: builtin/verify-pack.c:66
>  msgid "show statistics only"
>  msgstr "nur Statistiken anzeigen"
>  
>  #: builtin/verify-tag.c:18
> -#, fuzzy
>  msgid "git verify-tag [-v | --verbose] [--format=<format>] <tag>..."
> -msgstr "git verify-tag [-v | --verbose] <Tag>..."
> +msgstr "git verify-tag [-v | --verbose] [--format=<Format>] <Tag>..."
>  
>  #: builtin/verify-tag.c:36
>  msgid "print tag contents"
>  msgstr "Tag-Inhalte ausgeben"
>  
>  #: builtin/worktree.c:15
>  msgid "git worktree add [<options>] <path> [<branch>]"
>  msgstr "git worktree add [<Optionen>] <Pfad> [<Branch>]"
> @@ -13816,24 +13796,22 @@ msgid "Removing worktrees/%s: invalid gitdir file"
>  msgstr "Lösche worktrees/%s: ungültige gitdir-Datei"
>  
>  #: builtin/worktree.c:80
>  #, c-format
>  msgid "Removing worktrees/%s: gitdir file points to non-existent location"
>  msgstr "Lösche worktrees/%s: gitdir-Datei verweist auf nicht existierenden Ort"
>  
>  #: builtin/worktree.c:128
> -#, fuzzy
>  msgid "report pruned working trees"
> -msgstr "gelöschte Notizen melden"
> +msgstr "entfernte Arbeitsverzeichnisse ausgeben"
>  
>  #: builtin/worktree.c:130
> -#, fuzzy
>  msgid "expire working trees older than <time>"
> -msgstr "Objekte älter als <Zeit> verfallen lassen"
> +msgstr "Arbeitsverzeichnisse älter als <Zeit> verfallen lassen"
>  
>  #: builtin/worktree.c:204
>  #, c-format
>  msgid "'%s' already exists"
>  msgstr "'%s' existiert bereits"
>  
>  #: builtin/worktree.c:236
>  #, c-format
> @@ -13976,21 +13954,24 @@ msgstr ""
>  
>  #: http.c:1713
>  #, c-format
>  msgid ""
>  "unable to update url base from redirection:\n"
>  "  asked for: %s\n"
>  "   redirect: %s"
>  msgstr ""
> +"Konnte Basis-URL nicht durch Umleitung aktualisieren:\n"
> +"  gefragt nach: %s\n"
> +"    umgeleitet: %s"
>  
>  #: remote-curl.c:319
>  #, c-format
>  msgid "redirecting to %s"
> -msgstr ""
> +msgstr "Leite nach %s um"
>  
>  #: common-cmds.h:9
>  msgid "start a working area (see also: git help tutorial)"
>  msgstr "Arbeitsverzeichnis anlegen (siehe auch: git help tutorial)"
>  
>  #: common-cmds.h:10
>  msgid "work on the current change (see also: git help everyday)"
>  msgstr "an aktuellen Änderungen arbeiten (siehe auch: git help everyday)"
> @@ -14685,19 +14666,19 @@ msgid "repo URL: '$repo' must be absolute or begin with ./|../"
>  msgstr "repo URL: '$repo' muss absolut sein oder mit ./|../ beginnen"
>  
>  #: git-submodule.sh:210
>  #, sh-format
>  msgid "'$sm_path' already exists in the index"
>  msgstr "'$sm_path' ist bereits zum Commit vorgemerkt"
>  
>  #: git-submodule.sh:213
> -#, fuzzy, sh-format
> +#, sh-format
>  msgid "'$sm_path' already exists in the index and is not a submodule"
> -msgstr "'$sm_path' ist bereits zum Commit vorgemerkt"
> +msgstr "'$sm_path' ist bereits zum Commit vorgemerkt und ist kein Submodul"
>  
>  #: git-submodule.sh:218
>  #, sh-format
>  msgid ""
>  "The following path is ignored by one of your .gitignore files:\n"
>  "$sm_path\n"
>  "Use -f if you really want to add it."
>  msgstr ""
> @@ -15441,791 +15422,878 @@ msgstr ""
>  #: git-sh-setup.sh:377
>  msgid "Unable to determine absolute path of git directory"
>  msgstr "Konnte absoluten Pfad des Git-Verzeichnisses nicht bestimmen."
>  
>  #. TRANSLATORS: you can adjust this to align "git add -i" status menu
>  #: git-add--interactive.perl:238
>  #, perl-format
>  msgid "%12s %12s %s"
> -msgstr ""
> +msgstr "%28s %25s %s"
>  
>  #: git-add--interactive.perl:239
>  msgid "staged"
> -msgstr ""
> +msgstr "zur Staging-Area hinzugefügt"
>  
>  #: git-add--interactive.perl:239
>  msgid "unstaged"
> -msgstr ""
> +msgstr "aus Staging-Area entfernt"
>  
>  #: git-add--interactive.perl:297 git-add--interactive.perl:322
>  msgid "binary"
> -msgstr ""
> +msgstr "Binär"
>  
>  #: git-add--interactive.perl:306 git-add--interactive.perl:360
>  msgid "nothing"
> -msgstr ""
> +msgstr "Nichts"
>  
>  #: git-add--interactive.perl:342 git-add--interactive.perl:357
> -#, fuzzy
>  msgid "unchanged"
> -msgstr "Keine Änderungen"
> +msgstr "unverändert"
>  
>  #: git-add--interactive.perl:653
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "added %d path\n"
>  msgid_plural "added %d paths\n"
> -msgstr[0] "von denen hinzugefügt:"
> -msgstr[1] "von denen hinzugefügt:"
> +msgstr[0] "%d Pfad hinzugefügt\n"
> +msgstr[1] "%d Pfade hinzugefügt\n"
>  
>  #: git-add--interactive.perl:656
>  #, perl-format
>  msgid "updated %d path\n"
>  msgid_plural "updated %d paths\n"
> -msgstr[0] ""
> -msgstr[1] ""
> +msgstr[0] "%d Pfad aktualisiert\n"
> +msgstr[1] "%d Pfade aktualisiert\n"
>  
>  #: git-add--interactive.perl:659
>  #, perl-format
>  msgid "reverted %d path\n"
>  msgid_plural "reverted %d paths\n"
> -msgstr[0] ""
> -msgstr[1] ""
> +msgstr[0] "%d Pfad wiederhergestellt\n"
> +msgstr[1] "%d Pfade wiederhergestellt\n"
>  
>  #: git-add--interactive.perl:662
>  #, perl-format
>  msgid "touched %d path\n"
>  msgid_plural "touched %d paths\n"
> -msgstr[0] ""
> -msgstr[1] ""
> +msgstr[0] "%d Pfad angefasst\n"
> +msgstr[1] "%d Pfade angefasst\n"
>  
>  #: git-add--interactive.perl:671
> -#, fuzzy
>  msgid "Update"
> -msgstr "Datum"
> +msgstr "Aktualisieren"
>  
>  #: git-add--interactive.perl:683
> -#, fuzzy
>  msgid "Revert"
>  msgstr "Revert"
>  
>  #: git-add--interactive.perl:706
>  #, perl-format
>  msgid "note: %s is untracked now.\n"
> -msgstr ""
> +msgstr "Hinweis: %s ist nun unversioniert.\n"
>  
>  #: git-add--interactive.perl:717
> -#, fuzzy
>  msgid "Add untracked"
> -msgstr " gefolgt"
> +msgstr "unversionierte Dateien hinzufügen"
>  
>  #: git-add--interactive.perl:723
> -#, fuzzy
>  msgid "No untracked files.\n"
> -msgstr "Unversionierte Dateien"
> +msgstr "Keine unversionierten Dateien.\n"
>  
>  #: git-add--interactive.perl:1039
>  msgid ""
>  "If the patch applies cleanly, the edited hunk will immediately be\n"
>  "marked for staging."
>  msgstr ""
> +"Wenn der Patch sauber angewendet werden kann, wird der bearbeitete Patch-Block\n"
> +"direkt als zum Hinzufügen zur Staging-Area markiert."
>  
>  #: git-add--interactive.perl:1042
>  msgid ""
>  "If the patch applies cleanly, the edited hunk will immediately be\n"
>  "marked for stashing."
>  msgstr ""
> +"Wenn der Patch sauber angewendet werden kann, wird der bearbeitete Patch-Block\n"
> +"direkt als zum Hinzufügen zum Stash markiert."
>  
>  #: git-add--interactive.perl:1045
>  msgid ""
>  "If the patch applies cleanly, the edited hunk will immediately be\n"
>  "marked for unstaging."
>  msgstr ""
> +"Wenn der Patch sauber angewendet werden kann, wird der bearbeitete Patch-Block\n"
> +"direkt als zum Entfernen aus der Staging-Area markiert."
>  
>  #: git-add--interactive.perl:1048 git-add--interactive.perl:1057
>  msgid ""
>  "If the patch applies cleanly, the edited hunk will immediately be\n"
>  "marked for applying."
>  msgstr ""
> +"Wenn der Patch sauber angewendet werden kann, wird der bearbeitete Patch-Block\n"
> +"direkt als zum Anwenden markiert."
>  
>  #: git-add--interactive.perl:1051
>  msgid ""
>  "If the patch applies cleanly, the edited hunk will immediately be\n"
>  "marked for discarding"
>  msgstr ""
> +"Wenn der Patch sauber angewendet werden kann, wird der bearbeitete Patch-Block\n"
> +"direkt als zum Verwerfen markiert."
>  
>  #: git-add--interactive.perl:1054
>  msgid ""
>  "If the patch applies cleanly, the edited hunk will immediately be\n"
>  "marked for discarding."
>  msgstr ""
> +"Wenn der Patch sauber angewendet werden kann, wird der bearbeitete Patch-Block\n"
> +"direkt als zum Verwerfen markiert."
>  
>  #: git-add--interactive.perl:1067
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "failed to open hunk edit file for writing: %s"
> -msgstr "Fehler beim Erweitern des Nutzerverzeichnisses in: '%s'"
> +msgstr "Fehler beim Öffnen von Editier-Datei eines Patch-Blocks zum Schreiben: %s"
>  
>  #: git-add--interactive.perl:1068
>  msgid "Manual hunk edit mode -- see bottom for a quick guide.\n"
>  msgstr ""
> +"Manueller Editiermodus für Patch-Blöcke -- siehe nach unten für eine\n"
> +"Kurzanleitung.\n"
>  
>  #: git-add--interactive.perl:1074
>  #, perl-format
>  msgid ""
>  "---\n"
>  "To remove '%s' lines, make them ' ' lines (context).\n"
>  "To remove '%s' lines, delete them.\n"
>  "Lines starting with %s will be removed.\n"
>  msgstr ""
> +"---\n"
> +"Um '%s' Zeilen zu entfernen, machen Sie aus diesen ' ' Zeilen (Kontext).\n"
> +"Um '%s' Zeilen zu entfernen, löschen Sie diese.\n"
> +"Zeilen, die mit %s beginnen, werden entfernt.\n"
>  
>  #. TRANSLATORS: 'it' refers to the patch mentioned in the previous messages.
>  #: git-add--interactive.perl:1082
>  msgid ""
>  "If it does not apply cleanly, you will be given an opportunity to\n"
>  "edit again.  If all lines of the hunk are removed, then the edit is\n"
>  "aborted and the hunk is left unchanged.\n"
>  msgstr ""
> +"Wenn das nicht sauber angewendet werden kann, haben Sie die Möglichkeit\n"
> +"einer erneuten Bearbeitung. Wenn alle Zeilen des Patch-Blocks entfernt werden,\n"
> +"wird die Bearbeitung abgebrochen und der Patch-Block bleibt unverändert.\n"
>  
>  #: git-add--interactive.perl:1096
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "failed to open hunk edit file for reading: %s"
> -msgstr "Fehler beim Erweitern des Nutzerverzeichnisses in: '%s'"
> +msgstr "Fehler beim Öffnen von Editier-Datei eines Patch-Blocks zum Lesen: %s"
>  
>  #. TRANSLATORS: do not translate [y/n]
>  #. The program will only accept that input
>  #. at this point.
>  #. Consider translating (saying "no" discards!) as
>  #. (saying "n" for "no" discards!) if the translation
>  #. of the word "no" does not start with n.
>  #: git-add--interactive.perl:1187
>  msgid ""
>  "Your edited hunk does not apply. Edit again (saying \"no\" discards!) [y/n]? "
>  msgstr ""
> +"Ihr bearbeiteter Patch-Block kann nicht angewendet werden.\n"
> +"Erneut bearbeiten? (\"n\" verwirft Bearbeitung!) [y/n]?"
>  
>  #: git-add--interactive.perl:1196
>  msgid ""
>  "y - stage this hunk\n"
>  "n - do not stage this hunk\n"
>  "q - quit; do not stage this hunk or any of the remaining ones\n"
>  "a - stage this hunk and all later hunks in the file\n"
>  "d - do not stage this hunk or any of the later hunks in the file"
>  msgstr ""
> +"y - diesen Patch-Block zum Commit vormerken\n"
> +"n - diesen Patch-Block nicht zum Commit vormerken\n"
> +"q - Beenden; diesen oder alle verbleibenden Patch-Blöcke nicht zum Commit vormerken\n"
> +"a - diesen und alle weiteren Patch-Blöcke dieser Datei zum Commit vormerken\n"
> +"d - diesen oder alle weiteren Patch-Blöcke in dieser Datei nicht zum Commit vormerken"
>  
>  #: git-add--interactive.perl:1202
>  msgid ""
>  "y - stash this hunk\n"
>  "n - do not stash this hunk\n"
>  "q - quit; do not stash this hunk or any of the remaining ones\n"
>  "a - stash this hunk and all later hunks in the file\n"
>  "d - do not stash this hunk or any of the later hunks in the file"
>  msgstr ""
> +"y - diesen Patch-Block stashen\n"
> +"n - diesen Patch-Block nicht stashen\n"
> +"q - Beenden; diesen oder alle verbleibenden Patch-Blöcke nicht stashen\n"
> +"a - diesen und alle weiteren Patch-Blöcke dieser Datei stashen\n"
> +"d - diesen oder alle weiteren Patch-Blöcke dieser Datei nicht stashen"
>  
>  #: git-add--interactive.perl:1208
>  msgid ""
>  "y - unstage this hunk\n"
>  "n - do not unstage this hunk\n"
>  "q - quit; do not unstage this hunk or any of the remaining ones\n"
>  "a - unstage this hunk and all later hunks in the file\n"
>  "d - do not unstage this hunk or any of the later hunks in the file"
>  msgstr ""
> +"y - diesen Patch-Block unstashen\n"
> +"n - diesen Patch-Block nicht unstashen\n"
> +"q - Beenden; diesen oder alle verbleibenden Patch-Blöcke nicht unstashen\n"
> +"a - diesen und alle weiteren Patch-Blöcke dieser Datei unstashen\n"
> +"d - diesen oder alle weiteren Patch-Blöcke dieser Datei nicht unstashen"
>  
>  #: git-add--interactive.perl:1214
>  msgid ""
>  "y - apply this hunk to index\n"
>  "n - do not apply this hunk to index\n"
>  "q - quit; do not apply this hunk or any of the remaining ones\n"
>  "a - apply this hunk and all later hunks in the file\n"
>  "d - do not apply this hunk or any of the later hunks in the file"
>  msgstr ""
> +"y - diesen Patch-Block auf den Index anwenden\n"
> +"n - diesen Patch-Block nicht auf den Index anwenden\n"
> +"q - Beenden; diesen oder alle verbleibenden Patch-Blöcke nicht auf den Index anwenden\n"
> +"a - diesen und alle weiteren Patch-Blöcke dieser Datei auf den Index anwenden\n"
> +"d - diesen oder alle weiteren Patch-Blöcke dieser Datei nicht auf den Index anwenden"
>  
>  #: git-add--interactive.perl:1220
>  msgid ""
>  "y - discard this hunk from worktree\n"
>  "n - do not discard this hunk from worktree\n"
>  "q - quit; do not discard this hunk or any of the remaining ones\n"
>  "a - discard this hunk and all later hunks in the file\n"
>  "d - do not discard this hunk or any of the later hunks in the file"
>  msgstr ""
> +"y - diesen Patch-Block im Arbeitsverzeichnis verwerfen\n"
> +"n - diesen Patch-Block im Arbeitsverzeichnis nicht verwerfen\n"
> +"q - Beenden; diesen oder alle verbleibenden Patch-Blöcke nicht im Arbeitsverzeichnis verwerfen\n"
> +"a - diesen und alle weiteren Patch-Blöcke dieser Datei im Arbeitsverzeichnis verwerfen\n"
> +"d - diesen oder alle weiteren Patch-Blöcke dieser Datei nicht im Arbeitsverzeichnis verwerfen"
>  
>  #: git-add--interactive.perl:1226
>  msgid ""
>  "y - discard this hunk from index and worktree\n"
>  "n - do not discard this hunk from index and worktree\n"
>  "q - quit; do not discard this hunk or any of the remaining ones\n"
>  "a - discard this hunk and all later hunks in the file\n"
>  "d - do not discard this hunk or any of the later hunks in the file"
>  msgstr ""
> +"y - diesen Patch-Block im Index und Arbeitsverzeichnis verwerfen\n"
> +"n - diesen Patch-Block nicht im Index und Arbeitsverzeichnis verwerfen\n"
> +"q - Beenden; diesen oder alle verbleibenden Patch-Blöcke nicht im Index und Arbeitsverzeichnis verwerfen\n"
> +"a - diesen und alle weiteren Patch-Blöcke in der Datei verwerfen\n"
> +"d - diesen oder alle weiteren Patch-Blöcke in der Datei nicht verwerfen"
>  
>  #: git-add--interactive.perl:1232
>  msgid ""
>  "y - apply this hunk to index and worktree\n"
>  "n - do not apply this hunk to index and worktree\n"
>  "q - quit; do not apply this hunk or any of the remaining ones\n"
>  "a - apply this hunk and all later hunks in the file\n"
>  "d - do not apply this hunk or any of the later hunks in the file"
>  msgstr ""
> +"y - diesen Patch-Block im Index und auf Arbeitsverzeichnis anwenden\n"
> +"n - diesen Patch-Block nicht im Index und auf Arbeitsverzeichnis anwenden\n"
> +"q - Beenden; diesen oder alle verbleibenden Patch-Blöcke nicht anwenden\n"
> +"a - diesen und alle weiteren Patch-Blöcke in der Datei anwenden\n"
> +"d - diesen oder alle weiteren Patch-Blöcke in der Datei nicht anwenden"
>  
>  #: git-add--interactive.perl:1241
>  msgid ""
>  "g - select a hunk to go to\n"
>  "/ - search for a hunk matching the given regex\n"
>  "j - leave this hunk undecided, see next undecided hunk\n"
>  "J - leave this hunk undecided, see next hunk\n"
>  "k - leave this hunk undecided, see previous undecided hunk\n"
>  "K - leave this hunk undecided, see previous hunk\n"
>  "s - split the current hunk into smaller hunks\n"
>  "e - manually edit the current hunk\n"
>  "? - print help\n"
>  msgstr ""
> +"g - Patch-Block zum Hinspringen auswählen\n"
> +"/ - nach Patch-Block suchen der gegebenem regulärem Ausdruck entspricht\n"
> +"j - diesen Patch-Block unbestimmt lassen, nächsten unbestimmten Patch-Block anzeigen\n"
> +"J - diesen Patch-Block unbestimmt lassen, nächsten Patch-Block anzeigen\n"
> +"k - diesen Patch-Block unbestimmt lassen, vorherigen unbestimmten Patch-Block anzeigen\n"
> +"K - diesen Patch-Block unbestimmt lassen, vorherigen Patch-Block anzeigen\n"
> +"s - aktuellen Patch-Block in kleinere Patch-Blöcke aufteilen\n"
> +"e - aktuellen Patch-Block manuell editieren\n"
> +"? - Hilfe anzeigen\n"
>  
>  #: git-add--interactive.perl:1272
> -#, fuzzy
>  msgid "The selected hunks do not apply to the index!\n"
> -msgstr "den angegebenen Eintrag zum Commit vormerken"
> +msgstr "Die ausgewählten Patch-Blöcke können nicht auf den Index angewendet werden!\n"
>  
>  #: git-add--interactive.perl:1273
> -#, fuzzy
>  msgid "Apply them to the worktree anyway? "
> -msgstr "Pfad zum Arbeitsverzeichnis"
> +msgstr "Trotzdem auf Arbeitsverzeichnis anwenden? "
>  
>  #: git-add--interactive.perl:1276
>  msgid "Nothing was applied.\n"
> -msgstr ""
> +msgstr "Nichts angewendet.\n"
>  
>  #: git-add--interactive.perl:1287
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "ignoring unmerged: %s\n"
> -msgstr "Füge zusammengeführte Datei %s hinzu"
> +msgstr "ignoriere nicht zusammengeführte Datei: %s\n"
>  
>  #: git-add--interactive.perl:1296
>  msgid "Only binary files changed.\n"
> -msgstr ""
> +msgstr "Nur Binärdateien geändert.\n"
>  
>  #: git-add--interactive.perl:1298
> -#, fuzzy
>  msgid "No changes.\n"
> -msgstr "Keine Änderungen"
> +msgstr "Keine Änderungen.\n"
>  
>  #: git-add--interactive.perl:1306
> -#, fuzzy
>  msgid "Patch update"
> -msgstr "[Tag Aktualisierung]"
> +msgstr "Patch Aktualisierung"
>  
>  #: git-add--interactive.perl:1358
>  #, perl-format
>  msgid "Stage mode change [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Modusänderung der Staging-Area hinzufügen [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1359
>  #, perl-format
>  msgid "Stage deletion [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Löschung der Staging-Area hinzufügen [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1360
>  #, perl-format
>  msgid "Stage this hunk [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Diesen Patch-Block der Staging-Area hinzufügen [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1363
>  #, perl-format
>  msgid "Stash mode change [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Modusänderung stashen [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1364
>  #, perl-format
>  msgid "Stash deletion [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Löschung stashen [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1365
>  #, perl-format
>  msgid "Stash this hunk [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Diesen Patch-Block stashen [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1368
>  #, perl-format
>  msgid "Unstage mode change [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Modusänderung aus der Staging-Area entfernen [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1369
>  #, perl-format
>  msgid "Unstage deletion [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Löschung aus der Staging-Area entfernen [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1370
>  #, perl-format
>  msgid "Unstage this hunk [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Diesen Patch-Block aus der Staging-Area entfernen [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1373
>  #, perl-format
>  msgid "Apply mode change to index [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Modusänderung auf Index anwenden [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1374
>  #, perl-format
>  msgid "Apply deletion to index [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Löschung auf Index anwenden [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1375
>  #, perl-format
>  msgid "Apply this hunk to index [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Diesen Patch-Block auf Index anwenden [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1378
>  #, perl-format
>  msgid "Discard mode change from worktree [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Modusänderung im Arbeitsverzeichnis verwerfen [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1379
>  #, perl-format
>  msgid "Discard deletion from worktree [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Löschung im Arbeitsverzeichnis verwerfen [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1380
>  #, perl-format
>  msgid "Discard this hunk from worktree [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "diesen Patch-Block im Arbeitsverzeichnis verwerfen [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1383
>  #, perl-format
>  msgid "Discard mode change from index and worktree [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Modusänderung vom Index und Arbeitsverzeichnis verwerfen [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1384
>  #, perl-format
>  msgid "Discard deletion from index and worktree [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Löschung vom Index und Arbeitsverzeichnis verwerfen [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1385
>  #, perl-format
>  msgid "Discard this hunk from index and worktree [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Diesen Patch-Block vom Index und Arbeitsverzeichnis verwerfen [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1388
>  #, perl-format
>  msgid "Apply mode change to index and worktree [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Modusänderung auf Index und Arbeitsverzeichnis anwenden [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1389
>  #, perl-format
>  msgid "Apply deletion to index and worktree [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Löschung auf Index und Arbeitsverzeichnis anwenden [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1390
>  #, perl-format
>  msgid "Apply this hunk to index and worktree [y,n,q,a,d,/%s,?]? "
> -msgstr ""
> +msgstr "Diesen Patch-Block auf Index und Arbeitsverzeichnis anwenden [y,n,q,a,d,/%s,?]? "
>  
>  #: git-add--interactive.perl:1493
>  msgid "go to which hunk (<ret> to see more)? "
> -msgstr ""
> +msgstr "zu welchem Patch-Block springen (<Enter> für mehr Informationen)? "
>  
>  #: git-add--interactive.perl:1495
>  msgid "go to which hunk? "
> -msgstr ""
> +msgstr "zu welchem Patch-Block springen? "
>  
>  #: git-add--interactive.perl:1504
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "Invalid number: '%s'\n"
> -msgstr "Ungültiger %s: '%s'"
> +msgstr "Ungültige Nummer: '%s'\n"
>  
>  #: git-add--interactive.perl:1509
>  #, perl-format
>  msgid "Sorry, only %d hunk available.\n"
>  msgid_plural "Sorry, only %d hunks available.\n"
> -msgstr[0] ""
> -msgstr[1] ""
> +msgstr[0] "Entschuldigung, nur %d Patch-Block verfügbar.\n"
> +msgstr[1] "Entschuldigung, nur %d Patch-Blöcke verfügbar.\n"
>  
>  #: git-add--interactive.perl:1535
>  msgid "search for regex? "
> -msgstr ""
> +msgstr "Suche nach regulärem Ausdruck? "
>  
>  #: git-add--interactive.perl:1548
>  #, perl-format
>  msgid "Malformed search regexp %s: %s\n"
> -msgstr ""
> +msgstr "Fehlerhafter regulärer Ausdruck für Suche %s: %s\n"
>  
>  #: git-add--interactive.perl:1558
> -#, fuzzy
>  msgid "No hunk matches the given pattern\n"
> -msgstr "Änderungen nur im angegebenen Pfad anwenden"
> +msgstr "Kein Patch-Block entspricht dem angegebenen Pattern\n"
>  
>  #: git-add--interactive.perl:1570 git-add--interactive.perl:1592
>  msgid "No previous hunk\n"
> -msgstr ""
> +msgstr "Kein vorheriger Patch-Block\n"
>  
>  #: git-add--interactive.perl:1579 git-add--interactive.perl:1598
>  msgid "No next hunk\n"
> -msgstr ""
> +msgstr "Kein folgender Patch-Block\n"
>  
>  #: git-add--interactive.perl:1606
>  #, perl-format
>  msgid "Split into %d hunk.\n"
>  msgid_plural "Split into %d hunks.\n"
> -msgstr[0] ""
> -msgstr[1] ""
> +msgstr[0] "In %d Patch-Block aufgeteilt.\n"
> +msgstr[1] "In %d Patch-Blöcke aufgeteilt.\n"
>  
>  #: git-add--interactive.perl:1658
>  msgid "Review diff"
> -msgstr ""
> +msgstr "Diff überprüfen"
>  
>  #. TRANSLATORS: please do not translate the command names
>  #. 'status', 'update', 'revert', etc.
>  #: git-add--interactive.perl:1677
>  msgid ""
>  "status        - show paths with changes\n"
>  "update        - add working tree state to the staged set of changes\n"
>  "revert        - revert staged set of changes back to the HEAD version\n"
>  "patch         - pick hunks and update selectively\n"
>  "diff\t      - view diff between HEAD and index\n"
>  "add untracked - add contents of untracked files to the staged set of "
>  "changes\n"
>  msgstr ""
> +"status        - Pfade mit Änderungen anzeigen\n"
> +"update        - Zustand des Arbeitsverzeichnisses den zum Commit vorgemerkten Änderungen hinzufügen\n"
> +"revert        - zum Commit vorgemerkten Änderungen auf HEAD Version zurücksetzen\n"
> +"patch         - Patch-Blöcke auswählen und selektiv aktualisieren\n"
> +"diff\t      - Unterschiede zwischen HEAD und Index anzeigen\n"
> +"add untracked - Inhalte von unversionierten Dateien zum Commit vormerken\n"
>  
>  #: git-add--interactive.perl:1694 git-add--interactive.perl:1699
>  #: git-add--interactive.perl:1702 git-add--interactive.perl:1709
>  #: git-add--interactive.perl:1713 git-add--interactive.perl:1719
>  msgid "missing --"
> -msgstr ""
> +msgstr "-- fehlt"
>  
>  #: git-add--interactive.perl:1715
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "unknown --patch mode: %s"
> -msgstr "Unbekannter Wert für -s/--strategy: %s"
> +msgstr "Unbekannter --patch Modus: %s"
>  
>  #: git-add--interactive.perl:1721 git-add--interactive.perl:1727
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "invalid argument %s, expecting --"
> -msgstr "ungültige Pfadspezifikation"
> +msgstr "ungültiges Argument %s, erwarte --"
>  
>  #: git-send-email.perl:121
>  msgid "local zone differs from GMT by a non-minute interval\n"
> -msgstr ""
> +msgstr "lokale Zeitzone unterscheidet sich von GMT nicht um einen Minutenintervall\n"
>  
>  #: git-send-email.perl:128 git-send-email.perl:134
>  msgid "local time offset greater than or equal to 24 hours\n"
> -msgstr ""
> +msgstr "lokaler Zeit-Offset größer oder gleich 24 Stunden\n"
>  
>  #: git-send-email.perl:202 git-send-email.perl:208
>  msgid "the editor exited uncleanly, aborting everything"
> -msgstr ""
> +msgstr "Der Editor wurde unsauber beendet, breche alles ab."
>  
>  #: git-send-email.perl:282
>  #, perl-format
>  msgid ""
>  "'%s' contains an intermediate version of the email you were composing.\n"
> -msgstr ""
> +msgstr "'%s' enthält eine Zwischenversion der E-Mail, die Sie gerade verfassen.\n"
>  
>  #: git-send-email.perl:287
>  #, perl-format
>  msgid "'%s.final' contains the composed email.\n"
> -msgstr ""
> +msgstr "'%s.final' enthält die verfasste E-Mail.\n"
>  
>  #: git-send-email.perl:305
> -#, fuzzy
>  msgid "--dump-aliases incompatible with other options\n"
> -msgstr "Die Option --dirty kann nicht mit Commits verwendet werden."
> +msgstr "--dump-aliases ist mit anderen Optionen inkompatibel\n"
>  
>  #: git-send-email.perl:368 git-send-email.perl:623
> -#, fuzzy
>  msgid "Cannot run git format-patch from outside a repository\n"
> -msgstr ""
> -"Die Option --cached kann nicht außerhalb eines Repositories verwendet werden."
> +msgstr "Kann 'git format-patch' nicht außerhalb eines Repositories ausführen.\n"
>  
>  #: git-send-email.perl:437
>  #, perl-format
>  msgid "Unknown --suppress-cc field: '%s'\n"
> -msgstr ""
> +msgstr "Unbekanntes --suppress-cc Feld: '%s'\n"
>  
>  #: git-send-email.perl:466
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "Unknown --confirm setting: '%s'\n"
> -msgstr "Unbekannter Commit %s"
> +msgstr "Unbekannte --confirm Einstellung: '%s'\n"
>  
>  #: git-send-email.perl:498
>  #, perl-format
>  msgid "warning: sendmail alias with quotes is not supported: %s\n"
> -msgstr ""
> +msgstr "Warnung: sendemail Alias mit Anführungsstrichen wird nicht unterstützt: %s\n"
>  
>  #: git-send-email.perl:500
>  #, perl-format
>  msgid "warning: `:include:` not supported: %s\n"
> -msgstr ""
> +msgstr "Warnung: `:include:` wird nicht unterstützt: %s\n"
>  
>  #: git-send-email.perl:502
>  #, perl-format
>  msgid "warning: `/file` or `|pipe` redirection not supported: %s\n"
> -msgstr ""
> +msgstr "Warnung: `/file` oder `|pipe` Umleitung wird nicht unterstützt: %s\n"
>  
>  #: git-send-email.perl:507
>  #, perl-format
>  msgid "warning: sendmail line is not recognized: %s\n"
> -msgstr ""
> +msgstr "Warnung: sendmail Zeile wird nicht erkannt: %s\n"
>  
>  #: git-send-email.perl:589
>  #, perl-format
>  msgid ""
>  "File '%s' exists but it could also be the range of commits\n"
>  "to produce patches for.  Please disambiguate by...\n"
>  "\n"
>  "    * Saying \"./%s\" if you mean a file; or\n"
>  "    * Giving --format-patch option if you mean a range.\n"
>  msgstr ""
> +"Datei '%s' existiert, aber es könnte auch der Bereich von Commits sein,\n"
> +"für den Patches erzeugt werden sollen. Bitte machen Sie dies eindeutig\n"
> +"indem Sie ...\n"
> +"\n"
> +"    * \"./%s\" angeben, wenn Sie eine Datei meinen, oder\n"
> +"    * die Option --format-patch angeben, wenn Sie einen Commit-Bereich meinen\n"
>  
>  #: git-send-email.perl:610
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "Failed to opendir %s: %s"
> -msgstr "Fehler beim Öffnen von '%s': %s"
> +msgstr "Fehler beim Öffnen von %s: %s"
>  
>  #: git-send-email.perl:634
>  #, perl-format
>  msgid ""
>  "fatal: %s: %s\n"
>  "warning: no patches were sent\n"
>  msgstr ""
> +"fatal: %s: %s\n"
> +"Warnung: Es wurden keine Patches versendet.\n"
>  
>  #: git-send-email.perl:645
> -#, fuzzy
>  msgid ""
>  "\n"
>  "No patch files specified!\n"
>  "\n"
> -msgstr "kein Pfad angegeben"
> +msgstr "\nkeine Patch-Dateien angegeben!\n\n"
>  
>  #: git-send-email.perl:658
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "No subject line in %s?"
> -msgstr "Objekt nicht gefunden: %s"
> +msgstr "Keine Betreffzeile in %s?"
>  
>  #: git-send-email.perl:668
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "Failed to open for writing %s: %s"
> -msgstr "Fehler beim Öffnen von '%s': %s"
> +msgstr "Fehler beim Öffnen von '%s' zum Schreiben: %s"
>  
>  #: git-send-email.perl:678
>  msgid ""
>  "Lines beginning in \"GIT:\" will be removed.\n"
>  "Consider including an overall diffstat or table of contents\n"
>  "for the patch you are writing.\n"
>  "\n"
>  "Clear the body content if you don't wish to send a summary.\n"
>  msgstr ""
> +"Zeilen, die mit \"GIT:\" beginnen, werden entfernt.\n"
> +"Ziehen Sie in Betracht, einen allgemeinen \"diffstat\" oder ein\n"
> +"Inhaltsverzeichnis, für den Patch den Sie schreiben, hinzuzufügen.\n"
> +"\n"
> +"Leeren Sie den Inhalt des Bodys, wenn Sie keine Zusammenfassung senden möchten.\n"
>  
>  #: git-send-email.perl:701
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "Failed to open %s.final: %s"
> -msgstr "Fehler beim Öffnen von '%s': %s"
> +msgstr "Fehler beim Öffnen von %s.final: %s"
>  
>  #: git-send-email.perl:704
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "Failed to open %s: %s"
> -msgstr "Fehler beim Öffnen von '%s': %s"
> +msgstr "Fehler beim Öffnen von %s: %s"
>  
>  #: git-send-email.perl:739
>  msgid "To/Cc/Bcc fields are not interpreted yet, they have been ignored\n"
> -msgstr ""
> +msgstr "To/Cc/Bcc Felder wurden noch nicht interpretiert, sie wurden ignoriert\n"
>  
>  #: git-send-email.perl:748
>  msgid "Summary email is empty, skipping it\n"
> -msgstr ""
> +msgstr "E-Mail mit Zusammenfassung ist leer, wird ausgelassen\n"
>  
>  #. TRANSLATORS: please keep [y/N] as is.
>  #: git-send-email.perl:780
>  #, perl-format
>  msgid "Are you sure you want to use <%s> [y/N]? "
> -msgstr ""
> +msgstr "Sind Sie sich sicher, <%s> zu benutzen [y/N]? "
>  
>  #: git-send-email.perl:809
>  msgid ""
>  "The following files are 8bit, but do not declare a Content-Transfer-"
>  "Encoding.\n"
>  msgstr ""
> +"Die folgenden Dateien sind 8-Bit, aber deklarieren kein\n"
> +"Content-Transfer-Encoding.\n"
>  
>  #: git-send-email.perl:814
>  msgid "Which 8bit encoding should I declare [UTF-8]? "
> -msgstr ""
> +msgstr "Welches 8-Bit-Encoding soll deklariert werden [UTF-8]? "
>  
>  #: git-send-email.perl:822
>  #, perl-format
>  msgid ""
>  "Refusing to send because the patch\n"
>  "\t%s\n"
>  "has the template subject '*** SUBJECT HERE ***'. Pass --force if you really "
>  "want to send.\n"
>  msgstr ""
> +"Versand zurückgewiesen, weil der Patch\n"
> +"\t%s\n"
> +"die Betreffzeilenvorlage '*** SUBJECT HERE ***' enthält. Geben Sie --force an,\n"
> +"wenn Sie den Patch wirklich versenden wollen.\n"
>  
>  #: git-send-email.perl:841
>  msgid "To whom should the emails be sent (if anyone)?"
> -msgstr ""
> +msgstr "An wen sollen die E-Mails versendet werden (wenn überhaupt jemand)?"
>  
>  #: git-send-email.perl:859
>  #, perl-format
>  msgid "fatal: alias '%s' expands to itself\n"
> -msgstr ""
> +msgstr "fatal: Alias '%s' erweitert sich zu sich selbst\n"
>  
>  #: git-send-email.perl:871
>  msgid "Message-ID to be used as In-Reply-To for the first email (if any)? "
> -msgstr ""
> +msgstr "Message-ID zur Verwendung als In-Reply-To für die erste E-Mail (wenn eine existiert)? "
>  
>  #: git-send-email.perl:921 git-send-email.perl:929
>  #, perl-format
>  msgid "error: unable to extract a valid address from: %s\n"
> -msgstr ""
> +msgstr "Fehler: konnte keine gültige Adresse aus %s extrahieren\n"
>  
>  #. TRANSLATORS: Make sure to include [q] [d] [e] in your
>  #. translation. The program will only accept English input
>  #. at this point.
>  #: git-send-email.perl:933
>  msgid "What to do with this address? ([q]uit|[d]rop|[e]dit): "
> -msgstr ""
> +msgstr "Was soll mit dieser Adresse geschehen? (Beenden [q]|Löschen [d]|Bearbeiten [e]): "
>  
>  #: git-send-email.perl:1234
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "CA path \"%s\" does not exist"
> -msgstr "Pfad '%s' existiert nicht"
> +msgstr "CA Pfad \"%s\" existiert nicht"
>  
>  #: git-send-email.perl:1309
>  msgid ""
>  "    The Cc list above has been expanded by additional\n"
>  "    addresses found in the patch commit message. By default\n"
>  "    send-email prompts before sending whenever this occurs.\n"
>  "    This behavior is controlled by the sendemail.confirm\n"
>  "    configuration setting.\n"
>  "\n"
>  "    For additional information, run 'git send-email --help'.\n"
>  "    To retain the current behavior, but squelch this message,\n"
>  "    run 'git config --global sendemail.confirm auto'.\n"
>  "\n"
>  msgstr ""
> +"    Die Cc-Liste oberhalb wurde um zusätzliche Adressen erweitert, die in der\n"
> +"    Commit-Beschreibung des Patches gefunden wurden. Wenn dies passiert, werden\n"
> +"    Sie von send-email zu einer Eingabe aufgefordert. Dieses Verhalten wird\n"
> +"    durch die Konfigurationseinstellung sendemail.confirm gesteuert.\n"
> +"\n"
> +"    Für weitere Informationen, führen Sie 'git send-email --help' aus.\n"
> +"    Um das aktuelle Verhalten beizubehalten, aber diese Meldung zu unterdrücken,\n"
> +"    führen Sie 'git config --global sendemail.confirm auto' aus.\n"
> +"\n"
>  
>  #. TRANSLATORS: Make sure to include [y] [n] [q] [a] in your
>  #. translation. The program will only accept English input
>  #. at this point.
>  #: git-send-email.perl:1324
>  msgid "Send this email? ([y]es|[n]o|[q]uit|[a]ll): "
> -msgstr ""
> +msgstr "Diese E-Mail versenden? (Ja [y]|Nein [n]|Beenden [q]|Alle [a]): "
>  
>  #: git-send-email.perl:1327
>  msgid "Send this email reply required"
> -msgstr ""
> +msgstr "Zum Versenden dieser E-Mail ist eine Antwort erforderlich."
>  
>  #: git-send-email.perl:1353
>  msgid "The required SMTP server is not properly defined."
> -msgstr ""
> +msgstr "Der erforderliche SMTP-Server ist nicht korrekt definiert."
>  
>  #: git-send-email.perl:1397
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "Server does not support STARTTLS! %s"
> -msgstr "Server unterstützt kein --deepen"
> +msgstr "Server unterstützt kein STARTTLS! %s"
>  
>  #: git-send-email.perl:1403
>  msgid "Unable to initialize SMTP properly. Check config and use --smtp-debug."
>  msgstr ""
> +"Konnte SMTP nicht korrekt initialisieren. Bitte prüfen Sie Ihre Konfiguration\n"
> +"und benutzen Sie --smtp-debug."
>  
>  #: git-send-email.perl:1421
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "Failed to send %s\n"
> -msgstr "Fehler beim Lesen von %s"
> +msgstr "Fehler beim Senden %s\n"
>  
>  #: git-send-email.perl:1424
>  #, perl-format
>  msgid "Dry-Sent %s\n"
> -msgstr ""
> +msgstr "Probeversand %s\n"
>  
>  #: git-send-email.perl:1424
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "Sent %s\n"
> -msgstr "Lösche %s\n"
> +msgstr "%s gesendet\n"
>  
>  #: git-send-email.perl:1426
>  msgid "Dry-OK. Log says:\n"
> -msgstr ""
> +msgstr "Probeversand OK. Log enthält:\n"
>  
>  #: git-send-email.perl:1426
>  msgid "OK. Log says:\n"
> -msgstr ""
> +msgstr "OK. Log enthält:\n"
>  
>  #: git-send-email.perl:1438
>  msgid "Result: "
> -msgstr ""
> +msgstr "Ergebnis: "
>  
>  #: git-send-email.perl:1441
>  msgid "Result: OK\n"
> -msgstr ""
> +msgstr "Ergebnis: OK\n"
>  
>  #: git-send-email.perl:1454
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "can't open file %s"
> -msgstr "Kann Datei '%s' nicht öffnen"
> +msgstr "Kann Datei %s nicht öffnen"
>  
>  #: git-send-email.perl:1501 git-send-email.perl:1521
>  #, perl-format
>  msgid "(mbox) Adding cc: %s from line '%s'\n"
> -msgstr ""
> +msgstr "(mbox) Füge cc: hinzu: %s von Zeile '%s'\n"
>  
>  #: git-send-email.perl:1507
>  #, perl-format
>  msgid "(mbox) Adding to: %s from line '%s'\n"
> -msgstr ""
> +msgstr "(mbox) Füge to: hinzu: %s von Zeile '%s'\n"
>  
>  #: git-send-email.perl:1555
>  #, perl-format
>  msgid "(non-mbox) Adding cc: %s from line '%s'\n"
> -msgstr ""
> +msgstr "(non-mbox) Füge cc: hinzu: %s von Zeile '%s'\n"
>  
>  #: git-send-email.perl:1578
>  #, perl-format
>  msgid "(body) Adding cc: %s from line '%s'\n"
> -msgstr ""
> +msgstr "(body) Füge cc: hinzu: %s von Zeile '%s'\n"
>  
>  #: git-send-email.perl:1676
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "(%s) Could not execute '%s'"
> -msgstr "Konnte %s nicht entfernen"
> +msgstr "(%s) Konnte '%s' nicht ausführen"
>  
>  #: git-send-email.perl:1683
>  #, perl-format
>  msgid "(%s) Adding %s: %s from: '%s'\n"
> -msgstr ""
> +msgstr "(%s) Füge %s: %s hinzu von: '%s'\n"
>  
>  #: git-send-email.perl:1687
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "(%s) failed to close pipe to '%s'"
> -msgstr "Konnte Datei nicht nach '%s' kopieren"
> +msgstr "(%s) Fehler beim Schließen der Pipe nach '%s'"
>  
>  #: git-send-email.perl:1714
> -#, fuzzy
>  msgid "cannot send message as 7bit"
> -msgstr "Kann keine Commit-Beschreibung für %s bekommen."
> +msgstr "Kann Nachricht nicht als 7bit versenden."
>  
>  #: git-send-email.perl:1722
> -#, fuzzy
>  msgid "invalid transfer encoding"
> -msgstr "Ungültige Referenz: %s"
> +msgstr "Ungültiges Transfer-Encoding"
>  
>  #: git-send-email.perl:1741 git-send-email.perl:1792 git-send-email.perl:1802
> -#, fuzzy, perl-format
> +#, perl-format
>  msgid "unable to open %s: %s\n"
> -msgstr "kann %s nicht öffnen"
> +msgstr "konnte %s nicht öffnen: %s\n"
>  
>  #: git-send-email.perl:1744
>  #, perl-format
>  msgid "%s: patch contains a line longer than 998 characters"
> -msgstr ""
> +msgstr "%s: Patch enthält eine Zeile, die länger als 998 Zeichen ist"
>  
>  #: git-send-email.perl:1760
>  #, perl-format
>  msgid "Skipping %s with backup suffix '%s'.\n"
> -msgstr ""
> +msgstr "Lasse %s mit Backup-Suffix '%s' aus.\n"
>  
>  #. TRANSLATORS: please keep "[y|N]" as is.
>  #: git-send-email.perl:1764
>  #, perl-format
>  msgid "Do you really want to send %s? [y|N]: "
> -msgstr ""
> +msgstr "Wollen Sie %s wirklich versenden? [y|N]: "
>  
>  #~ msgid "Use an experimental blank-line-based heuristic to improve diffs"
>  #~ msgstr ""
>  #~ "eine experimentelle, auf Leerzeilen basierende Heuristik zur "
>  #~ "Verbesserung\n"
>  #~ "der Darstellung von Unterschieden verwenden"
>  
>  #~ msgid "Clever... amending the last one with dirty index."
> 


^ permalink raw reply

* Re: [PATCH 0/5] A series of performance enhancements in the memihash and name-cache area
From: Junio C Hamano @ 2017-02-19 21:50 UTC (permalink / raw)
  To: Jeff Hostetler
  Cc: Jeff King, Jeff Hostetler, Johannes Schindelin,
	git@vger.kernel.org
In-Reply-To: <MWHPR03MB2958D975B3B3022D6BC9AFBB8A5C0@MWHPR03MB2958.namprd03.prod.outlook.com>

Jeff Hostetler <Jeff.Hostetler@microsoft.com> writes:

>> But the other Jeff sounded like a follow-up was to follow shortly if
>> not imminent so I decided to allocate my time on other topics still
>> only on the list first while waiting to see what happens.
>
> Sorry, I was out of the office for a family emergency on Thursday
> and Friday.  Add to that the long weekend, and I won't get back around
> to this until Tuesday or Wednesday at the earliest.

The open source process makes progress at the pace of its
participants, and it is expected that some topics come fast while
others don't.

Hope things are all OK for you and your family now.

Thanks.


^ permalink raw reply

* Re: [PATCH 3/5] name-hash: precompute hash values during preload-index
From: Junio C Hamano @ 2017-02-19 21:45 UTC (permalink / raw)
  To: Jeff Hostetler; +Cc: git@vger.kernel.org, Johannes Schindelin
In-Reply-To: <MWHPR03MB295845950BB87BA9479E973E8A5F0@MWHPR03MB2958.namprd03.prod.outlook.com>

Jeff Hostetler <Jeff.Hostetler@microsoft.com> writes:

> I looked at doing this, but I didn't think the complexity and overhead to
> forward search for peers at the current level didn't warrant the limited gains.

It seems that I wasn't clear what I meant.  I didn't mean anything
complex like what you said.

Just something simple, like this on top of yours, that passes and
compares with only the previous one.  I do not know if that gives
any gain, though ;-).

 cache.h         |  2 +-
 name-hash.c     | 11 +++++++++--
 preload-index.c |  4 +++-
 3 files changed, 13 insertions(+), 4 deletions(-)

diff --git a/cache.h b/cache.h
index 390aa803df..bd2980f6e3 100644
--- a/cache.h
+++ b/cache.h
@@ -233,7 +233,7 @@ struct cache_entry {
 #error "CE_EXTENDED_FLAGS out of range"
 #endif
 
-void precompute_istate_hashes(struct cache_entry *ce);
+void precompute_istate_hashes(struct cache_entry *ce, struct cache_entry *prev);
 
 /* Forward structure decls */
 struct pathspec;
diff --git a/name-hash.c b/name-hash.c
index f95054f44c..5e09b79170 100644
--- a/name-hash.c
+++ b/name-hash.c
@@ -300,7 +300,7 @@ void free_name_hash(struct index_state *istate)
  * non-skip-worktree items (since status should not observe skipped items), but
  * because lazy_init_name_hash() hashes everything, we force it here.
  */
-void precompute_istate_hashes(struct cache_entry *ce)
+void precompute_istate_hashes(struct cache_entry *ce, struct cache_entry *prev)
 {
 	int namelen = ce_namelen(ce);
 
@@ -312,7 +312,14 @@ void precompute_istate_hashes(struct cache_entry *ce)
 		ce->precomputed_hash.root_entry = 1;
 	} else {
 		namelen--;
-		ce->precomputed_hash.dir = memihash(ce->name, namelen);
+
+		if (prev && 
+		    prev->precomputed_hash.initialized &&
+		    namelen <= ce_namelen(prev) &&
+		    !memcmp(ce->name, prev->name, namelen))
+			ce->precomputed_hash.dir = prev->precomputed_hash.dir;
+		else
+			ce->precomputed_hash.dir = memihash(ce->name, namelen);
 		ce->precomputed_hash.name = memihash_continue(
 			ce->precomputed_hash.dir, ce->name + namelen,
 			ce_namelen(ce) - namelen);
diff --git a/preload-index.c b/preload-index.c
index 602737f9d0..784378ffac 100644
--- a/preload-index.c
+++ b/preload-index.c
@@ -37,6 +37,7 @@ static void *preload_thread(void *_data)
 	struct thread_data *p = _data;
 	struct index_state *index = p->index;
 	struct cache_entry **cep = index->cache + p->offset;
+	struct cache_entry *previous = NULL;
 	struct cache_def cache = CACHE_DEF_INIT;
 
 	nr = p->nr;
@@ -47,7 +48,8 @@ static void *preload_thread(void *_data)
 		struct cache_entry *ce = *cep++;
 		struct stat st;
 
-		precompute_istate_hashes(ce);
+		precompute_istate_hashes(ce, previous);
+		previous = ce;
 
 		if (ce_stage(ce))
 			continue;




> (I was just looking at the complexity of clear_ce_flags_1() in unpack-trees.c
> and how hard it has to look to find the end of the current directory and the
> effect that that has on the recursion and it felt like too much work for the
> potential gain.)
>
> Whereas remembering the previous one was basically free.  Granted, it only
> helps us for adjacent files in the index, so it's not perfect, but gives us the
> best bang for the buck.
>
> Jeff

^ permalink raw reply related

* [PATCH] Documentation: Link git-ls-files to core.quotePath variable.
From: Andreas Heiduk @ 2017-02-19 22:05 UTC (permalink / raw)
  To: gitster; +Cc: git

Add a hint for script writers where additional quoting can be configured.

Signed-off-by: Andreas Heiduk <asheiduk@gmail.com>
---
 Documentation/git-ls-files.txt | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/Documentation/git-ls-files.txt b/Documentation/git-ls-files.txt
index 446209e..19e0636 100644
--- a/Documentation/git-ls-files.txt
+++ b/Documentation/git-ls-files.txt
@@ -198,7 +198,8 @@ path. (see linkgit:git-read-tree[1] for more information on state)
 
 When `-z` option is not used, TAB, LF, and backslash characters
 in pathnames are represented as `\t`, `\n`, and `\\`,
-respectively.
+respectively. The path is also quoted according to the
+configuration variable `core.quotePath` (see linkgit:git-config[1]).
 
 
 Exclude Patterns
-- 
2.7.4

^ permalink raw reply related

* Re: [PATCH] git-check-ref-format: fix typo in man page
From: Damien Regad @ 2017-02-19 22:13 UTC (permalink / raw)
  To: git
In-Reply-To: <8147218721BE4F239D00CBFAFD9B495D@PhilipOakley>

Thanks all for the feedback.

On 2017-02-19 21:40, Philip Oakley wrote:
> For those not familiar with 'iff', then a change to the doc is worthwhile.

Exactly. Not being a native English speaker, I had never seen 'iff' used
before. Now that you guys have pointed me to its meaning I guess it
makes sense in this context.

That being said, IMHO software documentation is not a mathematics
textbook, and should be written in "plain" English, so

On 2017-02-19 03:27, Jeff King wrote:
> So maybe an overall improvement would be something like:
>
>   If the normalized refname is valid then print it to standard output
>   and exit with a status of 0. Otherwise, exit with a non-zero status.

I'll submit a revised patch shortly, following your suggestion.

Cheers
Damien



^ permalink raw reply

* [PATCH v2] git-check-ref-format: clarify man for --normalize
From: Damien Regad @ 2017-02-19 22:32 UTC (permalink / raw)
  To: git; +Cc: Philip Oakley, Jeff King, Michael Haggerty

Use of 'iff' may be confusing to people not familiar with this term.

Improving the --normalize option's documentation to remove the use of
'iff', and clearly describe what happens when the condition is not met.
---
 Documentation/git-check-ref-format.txt | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/Documentation/git-check-ref-format.txt
b/Documentation/git-check-ref-format.txt
index 8611a99..92777ce 100644
--- a/Documentation/git-check-ref-format.txt
+++ b/Documentation/git-check-ref-format.txt
@@ -100,10 +100,10 @@ OPTIONS
 --normalize::
 	Normalize 'refname' by removing any leading slash (`/`)
 	characters and collapsing runs of adjacent slashes between
-	name components into a single slash.  Iff the normalized
+	name components into a single slash.  If the normalized
 	refname is valid then print it to standard output and exit
-	with a status of 0.  (`--print` is a deprecated way to spell
-	`--normalize`.)
+	with a status of 0, otherwise exit with a non-zero status.
+	(`--print` is a deprecated way to spell `--normalize`.)


 EXAMPLES
-- 
2.7.4


^ permalink raw reply related

* Re: [RFC PATCH] show decorations at the end of the line
From: Linus Torvalds @ 2017-02-19 22:33 UTC (permalink / raw)
  To: Junio C Hamano; +Cc: Git Mailing List, Jeff King
In-Reply-To: <xmqqefywnk5a.fsf@gitster.mtv.corp.google.com>

On Fri, Feb 17, 2017 at 9:27 PM, Junio C Hamano <gitster@pobox.com> wrote:
>
> I just got bitten by a fallout.  I have
>
>     $ git recent --help
>     `git recent' is aliased to `log --oneline --branches --no-merges \
>          --source --since=3.weeks'
>
> but now the branch names are shown at the end, which defeats the
> whole point of the alias.

Yes, your situation actually wants those decorations as primary
things, so having them at the end is indeed pointless.

So I think we should just discard that patch of mine.

                 Linus

^ permalink raw reply

* Re: [RFC PATCH] show decorations at the end of the line
From: Jacob Keller @ 2017-02-19 23:03 UTC (permalink / raw)
  To: Linus Torvalds; +Cc: Junio C Hamano, Git Mailing List, Jeff King
In-Reply-To: <CA+55aFw3ZRtgsLGW-TFqpq-3uCw55L42p7cF=Q-73qM_VPuYsQ@mail.gmail.com>

On Sun, Feb 19, 2017 at 2:33 PM, Linus Torvalds
<torvalds@linux-foundation.org> wrote:
> On Fri, Feb 17, 2017 at 9:27 PM, Junio C Hamano <gitster@pobox.com> wrote:
>>
>> I just got bitten by a fallout.  I have
>>
>>     $ git recent --help
>>     `git recent' is aliased to `log --oneline --branches --no-merges \
>>          --source --since=3.weeks'
>>
>> but now the branch names are shown at the end, which defeats the
>> whole point of the alias.
>
> Yes, your situation actually wants those decorations as primary
> things, so having them at the end is indeed pointless.
>
> So I think we should just discard that patch of mine.
>
>                  Linus

I would think that in general putting them at the end makes more
sense, but we should have the ability to use them in format specifiers
so that users are free to customize it exactly how they want. That is,
I agree with the reasoning presented in the original patch, but think
Junio's case can be solved by strengthening the custom formats.

Thanks,
Jake

^ permalink raw reply

* [PATCH v4 00/19] object_id part 6
From: brian m. carlson @ 2017-02-20  0:10 UTC (permalink / raw)
  To: git; +Cc: Jeff King, Michael Haggerty, Junio C Hamano, Ramsay Jones

This is another series in the continuing conversion to struct object_id.

This series converts more of the builtin directory and some of the refs
code to use struct object_id. Additionally, it implements an
nth_packed_object_oid function which provides a struct object_id version
of the nth_packed_object function, and a parse_oid_hex function that
makes parsing easier.

Changes from v3:
* Move the parse_oid_hex patch earlier in the series.
* Use parse_oid_hex in builtin/diff-tree.c.
* Fix several warts with parse_oid_hex pointed out by Peff.

Changes from v2:
* Fix misnamed function in commit message.
* Improve parameter name of parse_oid_hex.
* Improve docstring of parse_oid_hex.
* Remove needless variable.
* Rebase on master.

Changes from v1:
* Implement parse_oid_hex and use it.
* Make nth_packed_object_oid take a variable into which to store the
  object ID.  This avoids concerns about unsafe casts.
* Rebase on master.

brian m. carlson (19):
  hex: introduce parse_oid_hex
  builtin/commit: convert to struct object_id
  builtin/diff-tree: convert to struct object_id
  builtin/describe: convert to struct object_id
  builtin/fast-export: convert to struct object_id
  builtin/fmt-merge-message: convert to struct object_id
  builtin/grep: convert to struct object_id
  builtin/branch: convert to struct object_id
  builtin/clone: convert to struct object_id
  builtin/merge: convert to struct object_id
  Convert remaining callers of resolve_refdup to object_id
  builtin/replace: convert to struct object_id
  reflog-walk: convert struct reflog_info to struct object_id
  refs: convert each_reflog_ent_fn to struct object_id
  refs: simplify parsing of reflog entries
  sha1_file: introduce an nth_packed_object_oid function
  Convert object iteration callbacks to struct object_id
  builtin/merge-base: convert to struct object_id
  wt-status: convert to struct object_id

 builtin/branch.c        |  26 +++++-----
 builtin/cat-file.c      |   8 +--
 builtin/clone.c         |  10 ++--
 builtin/commit.c        |  46 ++++++++---------
 builtin/count-objects.c |   4 +-
 builtin/describe.c      |  50 +++++++++---------
 builtin/diff-tree.c     |  43 ++++++++--------
 builtin/fast-export.c   |  58 ++++++++++-----------
 builtin/fmt-merge-msg.c |  70 ++++++++++++-------------
 builtin/fsck.c          |  40 +++++++--------
 builtin/grep.c          |  24 ++++-----
 builtin/merge-base.c    |  30 +++++------
 builtin/merge.c         | 134 ++++++++++++++++++++++++------------------------
 builtin/notes.c         |  18 +++----
 builtin/pack-objects.c  |   6 +--
 builtin/prune-packed.c  |   4 +-
 builtin/prune.c         |   8 +--
 builtin/receive-pack.c  |   4 +-
 builtin/reflog.c        |   2 +-
 builtin/replace.c       | 112 ++++++++++++++++++++--------------------
 cache.h                 |  19 ++++++-
 hex.c                   |   8 +++
 reachable.c             |  30 +++++------
 ref-filter.c            |   4 +-
 reflog-walk.c           |  26 +++++-----
 refs.c                  |  24 ++++-----
 refs.h                  |   2 +-
 refs/files-backend.c    |  29 ++++++-----
 revision.c              |  12 ++---
 sha1_file.c             |  27 +++++++---
 sha1_name.c             |   2 +-
 transport.c             |   4 +-
 wt-status.c             |  52 +++++++++----------
 33 files changed, 484 insertions(+), 452 deletions(-)

-- 
2.11.0


^ permalink raw reply

* [PATCH v4 16/19] sha1_file: introduce an nth_packed_object_oid function
From: brian m. carlson @ 2017-02-20  0:10 UTC (permalink / raw)
  To: git; +Cc: Jeff King, Michael Haggerty, Junio C Hamano, Ramsay Jones
In-Reply-To: <20170220001031.559931-1-sandals@crustytoothpaste.net>

There are places in the code where we would like to provide a struct
object_id *, yet read the hash directly from the pack.  Provide an
nth_packed_object_oid function that is similar to the
nth_packed_object_sha1 function.

In order to avoid a potentially invalid cast, nth_packed_object_oid
provides a variable into which to store the value, which it returns on
success; on error, it returns NULL, as nth_packed_object_sha1 does.

Signed-off-by: brian m. carlson <sandals@crustytoothpaste.net>
---
 cache.h     |  6 ++++++
 sha1_file.c | 17 ++++++++++++++---
 2 files changed, 20 insertions(+), 3 deletions(-)

diff --git a/cache.h b/cache.h
index e03a672d15..29e59cbb56 100644
--- a/cache.h
+++ b/cache.h
@@ -1608,6 +1608,12 @@ extern void check_pack_index_ptr(const struct packed_git *p, const void *ptr);
  * error.
  */
 extern const unsigned char *nth_packed_object_sha1(struct packed_git *, uint32_t n);
+/*
+ * Like nth_packed_object_sha1, but write the data into the object specified by
+ * the the first argument.  Returns the first argument on success, and NULL on
+ * error.
+ */
+extern const struct object_id *nth_packed_object_oid(struct object_id *, struct packed_git *, uint32_t n);
 
 /*
  * Return the offset of the nth object within the specified packfile.
diff --git a/sha1_file.c b/sha1_file.c
index ec957db5e1..777b8e8eae 100644
--- a/sha1_file.c
+++ b/sha1_file.c
@@ -2628,6 +2628,17 @@ const unsigned char *nth_packed_object_sha1(struct packed_git *p,
 	}
 }
 
+const struct object_id *nth_packed_object_oid(struct object_id *oid,
+					      struct packed_git *p,
+					      uint32_t n)
+{
+	const unsigned char *hash = nth_packed_object_sha1(p, n);
+	if (!hash)
+		return NULL;
+	hashcpy(oid->hash, hash);
+	return oid;
+}
+
 void check_pack_index_ptr(const struct packed_git *p, const void *vptr)
 {
 	const unsigned char *ptr = vptr;
@@ -3788,13 +3799,13 @@ static int for_each_object_in_pack(struct packed_git *p, each_packed_object_fn c
 	int r = 0;
 
 	for (i = 0; i < p->num_objects; i++) {
-		const unsigned char *sha1 = nth_packed_object_sha1(p, i);
+		struct object_id oid;
 
-		if (!sha1)
+		if (!nth_packed_object_oid(&oid, p, i))
 			return error("unable to get sha1 of object %u in %s",
 				     i, p->pack_name);
 
-		r = cb(sha1, p, i, data);
+		r = cb(oid.hash, p, i, data);
 		if (r)
 			break;
 	}
-- 
2.11.0


^ permalink raw reply related

* [PATCH v4 15/19] refs: simplify parsing of reflog entries
From: brian m. carlson @ 2017-02-20  0:10 UTC (permalink / raw)
  To: git; +Cc: Jeff King, Michael Haggerty, Junio C Hamano, Ramsay Jones
In-Reply-To: <20170220001031.559931-1-sandals@crustytoothpaste.net>

The current code for reflog entries uses a lot of hard-coded constants,
making it hard to read and modify.  Use parse_oid_hex and two temporary
variables to simplify the code and reduce the use of magic constants.

Signed-off-by: brian m. carlson <sandals@crustytoothpaste.net>
---
 refs/files-backend.c | 11 ++++++-----
 1 file changed, 6 insertions(+), 5 deletions(-)

diff --git a/refs/files-backend.c b/refs/files-backend.c
index d7a5fd2a7c..fea20e99fe 100644
--- a/refs/files-backend.c
+++ b/refs/files-backend.c
@@ -3117,12 +3117,13 @@ static int show_one_reflog_ent(struct strbuf *sb, each_reflog_ent_fn fn, void *c
 	char *email_end, *message;
 	unsigned long timestamp;
 	int tz;
+	const char *p = sb->buf;
 
 	/* old SP new SP name <email> SP time TAB msg LF */
-	if (sb->len < 83 || sb->buf[sb->len - 1] != '\n' ||
-	    get_oid_hex(sb->buf, &ooid) || sb->buf[40] != ' ' ||
-	    get_oid_hex(sb->buf + 41, &noid) || sb->buf[81] != ' ' ||
-	    !(email_end = strchr(sb->buf + 82, '>')) ||
+	if (!sb->len || sb->buf[sb->len - 1] != '\n' ||
+	    parse_oid_hex(p, &ooid, &p) || *p++ != ' ' ||
+	    parse_oid_hex(p, &noid, &p) || *p++ != ' ' ||
+	    !(email_end = strchr(p, '>')) ||
 	    email_end[1] != ' ' ||
 	    !(timestamp = strtoul(email_end + 2, &message, 10)) ||
 	    !message || message[0] != ' ' ||
@@ -3136,7 +3137,7 @@ static int show_one_reflog_ent(struct strbuf *sb, each_reflog_ent_fn fn, void *c
 		message += 6;
 	else
 		message += 7;
-	return fn(&ooid, &noid, sb->buf + 82, timestamp, tz, message, cb_data);
+	return fn(&ooid, &noid, p, timestamp, tz, message, cb_data);
 }
 
 static char *find_beginning_of_line(char *bob, char *scan)
-- 
2.11.0


^ permalink raw reply related

* [PATCH v4 05/19] builtin/fast-export: convert to struct object_id
From: brian m. carlson @ 2017-02-20  0:10 UTC (permalink / raw)
  To: git; +Cc: Jeff King, Michael Haggerty, Junio C Hamano, Ramsay Jones
In-Reply-To: <20170220001031.559931-1-sandals@crustytoothpaste.net>

In addition to converting to struct object_id, write some hardcoded
buffer sizes in terms of GIT_SHA1_RAWSZ.

Signed-off-by: brian m. carlson <sandals@crustytoothpaste.net>
---
 builtin/fast-export.c | 58 +++++++++++++++++++++++++--------------------------
 1 file changed, 29 insertions(+), 29 deletions(-)

diff --git a/builtin/fast-export.c b/builtin/fast-export.c
index 1e815b5577..e0220630d0 100644
--- a/builtin/fast-export.c
+++ b/builtin/fast-export.c
@@ -212,7 +212,7 @@ static char *anonymize_blob(unsigned long *size)
 	return strbuf_detach(&out, NULL);
 }
 
-static void export_blob(const unsigned char *sha1)
+static void export_blob(const struct object_id *oid)
 {
 	unsigned long size;
 	enum object_type type;
@@ -223,34 +223,34 @@ static void export_blob(const unsigned char *sha1)
 	if (no_data)
 		return;
 
-	if (is_null_sha1(sha1))
+	if (is_null_oid(oid))
 		return;
 
-	object = lookup_object(sha1);
+	object = lookup_object(oid->hash);
 	if (object && object->flags & SHOWN)
 		return;
 
 	if (anonymize) {
 		buf = anonymize_blob(&size);
-		object = (struct object *)lookup_blob(sha1);
+		object = (struct object *)lookup_blob(oid->hash);
 		eaten = 0;
 	} else {
-		buf = read_sha1_file(sha1, &type, &size);
+		buf = read_sha1_file(oid->hash, &type, &size);
 		if (!buf)
-			die ("Could not read blob %s", sha1_to_hex(sha1));
-		if (check_sha1_signature(sha1, buf, size, typename(type)) < 0)
-			die("sha1 mismatch in blob %s", sha1_to_hex(sha1));
-		object = parse_object_buffer(sha1, type, size, buf, &eaten);
+			die ("Could not read blob %s", oid_to_hex(oid));
+		if (check_sha1_signature(oid->hash, buf, size, typename(type)) < 0)
+			die("sha1 mismatch in blob %s", oid_to_hex(oid));
+		object = parse_object_buffer(oid->hash, type, size, buf, &eaten);
 	}
 
 	if (!object)
-		die("Could not read blob %s", sha1_to_hex(sha1));
+		die("Could not read blob %s", oid_to_hex(oid));
 
 	mark_next_object(object);
 
 	printf("blob\nmark :%"PRIu32"\ndata %lu\n", last_idnum, size);
 	if (size && fwrite(buf, size, 1, stdout) != 1)
-		die_errno ("Could not write blob '%s'", sha1_to_hex(sha1));
+		die_errno ("Could not write blob '%s'", oid_to_hex(oid));
 	printf("\n");
 
 	show_progress();
@@ -323,19 +323,19 @@ static void print_path(const char *path)
 	}
 }
 
-static void *generate_fake_sha1(const void *old, size_t *len)
+static void *generate_fake_oid(const void *old, size_t *len)
 {
 	static uint32_t counter = 1; /* avoid null sha1 */
-	unsigned char *out = xcalloc(20, 1);
-	put_be32(out + 16, counter++);
+	unsigned char *out = xcalloc(GIT_SHA1_RAWSZ, 1);
+	put_be32(out + GIT_SHA1_RAWSZ - 4, counter++);
 	return out;
 }
 
-static const unsigned char *anonymize_sha1(const unsigned char *sha1)
+static const unsigned char *anonymize_sha1(const struct object_id *oid)
 {
 	static struct hashmap sha1s;
-	size_t len = 20;
-	return anonymize_mem(&sha1s, generate_fake_sha1, sha1, &len);
+	size_t len = GIT_SHA1_RAWSZ;
+	return anonymize_mem(&sha1s, generate_fake_oid, oid, &len);
 }
 
 static void show_filemodify(struct diff_queue_struct *q,
@@ -383,7 +383,7 @@ static void show_filemodify(struct diff_queue_struct *q,
 			if (no_data || S_ISGITLINK(spec->mode))
 				printf("M %06o %s ", spec->mode,
 				       sha1_to_hex(anonymize ?
-						   anonymize_sha1(spec->oid.hash) :
+						   anonymize_sha1(&spec->oid) :
 						   spec->oid.hash));
 			else {
 				struct object *object = lookup_object(spec->oid.hash);
@@ -572,7 +572,7 @@ static void handle_commit(struct commit *commit, struct rev_info *rev)
 	/* Export the referenced blobs, and remember the marks. */
 	for (i = 0; i < diff_queued_diff.nr; i++)
 		if (!S_ISGITLINK(diff_queued_diff.queue[i]->two->mode))
-			export_blob(diff_queued_diff.queue[i]->two->oid.hash);
+			export_blob(&diff_queued_diff.queue[i]->two->oid);
 
 	refname = commit->util;
 	if (anonymize) {
@@ -797,14 +797,14 @@ static void get_tags_and_duplicates(struct rev_cmdline_info *info)
 
 	for (i = 0; i < info->nr; i++) {
 		struct rev_cmdline_entry *e = info->rev + i;
-		unsigned char sha1[20];
+		struct object_id oid;
 		struct commit *commit;
 		char *full_name;
 
 		if (e->flags & UNINTERESTING)
 			continue;
 
-		if (dwim_ref(e->name, strlen(e->name), sha1, &full_name) != 1)
+		if (dwim_ref(e->name, strlen(e->name), oid.hash, &full_name) != 1)
 			continue;
 
 		if (refspecs) {
@@ -828,7 +828,7 @@ static void get_tags_and_duplicates(struct rev_cmdline_info *info)
 		case OBJ_COMMIT:
 			break;
 		case OBJ_BLOB:
-			export_blob(commit->object.oid.hash);
+			export_blob(&commit->object.oid);
 			continue;
 		default: /* OBJ_TAG (nested tags) is already handled */
 			warning("Tag points to object of unexpected type %s, skipping.",
@@ -912,7 +912,7 @@ static void import_marks(char *input_file)
 	while (fgets(line, sizeof(line), f)) {
 		uint32_t mark;
 		char *line_end, *mark_end;
-		unsigned char sha1[20];
+		struct object_id oid;
 		struct object *object;
 		struct commit *commit;
 		enum object_type type;
@@ -924,28 +924,28 @@ static void import_marks(char *input_file)
 
 		mark = strtoumax(line + 1, &mark_end, 10);
 		if (!mark || mark_end == line + 1
-			|| *mark_end != ' ' || get_sha1_hex(mark_end + 1, sha1))
+			|| *mark_end != ' ' || get_oid_hex(mark_end + 1, &oid))
 			die("corrupt mark line: %s", line);
 
 		if (last_idnum < mark)
 			last_idnum = mark;
 
-		type = sha1_object_info(sha1, NULL);
+		type = sha1_object_info(oid.hash, NULL);
 		if (type < 0)
-			die("object not found: %s", sha1_to_hex(sha1));
+			die("object not found: %s", oid_to_hex(&oid));
 
 		if (type != OBJ_COMMIT)
 			/* only commits */
 			continue;
 
-		commit = lookup_commit(sha1);
+		commit = lookup_commit(oid.hash);
 		if (!commit)
-			die("not a commit? can't happen: %s", sha1_to_hex(sha1));
+			die("not a commit? can't happen: %s", oid_to_hex(&oid));
 
 		object = &commit->object;
 
 		if (object->flags & SHOWN)
-			error("Object %s already has a mark", sha1_to_hex(sha1));
+			error("Object %s already has a mark", oid_to_hex(&oid));
 
 		mark_object(object, mark);
 
-- 
2.11.0


^ permalink raw reply related

* [PATCH v4 09/19] builtin/clone: convert to struct object_id
From: brian m. carlson @ 2017-02-20  0:10 UTC (permalink / raw)
  To: git; +Cc: Jeff King, Michael Haggerty, Junio C Hamano, Ramsay Jones
In-Reply-To: <20170220001031.559931-1-sandals@crustytoothpaste.net>

Signed-off-by: brian m. carlson <sandals@crustytoothpaste.net>
---
 builtin/clone.c | 10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)

diff --git a/builtin/clone.c b/builtin/clone.c
index 3f63edbbf9..b4c929bb8a 100644
--- a/builtin/clone.c
+++ b/builtin/clone.c
@@ -681,7 +681,7 @@ static void update_head(const struct ref *our, const struct ref *remote,
 
 static int checkout(int submodule_progress)
 {
-	unsigned char sha1[20];
+	struct object_id oid;
 	char *head;
 	struct lock_file *lock_file;
 	struct unpack_trees_options opts;
@@ -692,7 +692,7 @@ static int checkout(int submodule_progress)
 	if (option_no_checkout)
 		return 0;
 
-	head = resolve_refdup("HEAD", RESOLVE_REF_READING, sha1, NULL);
+	head = resolve_refdup("HEAD", RESOLVE_REF_READING, oid.hash, NULL);
 	if (!head) {
 		warning(_("remote HEAD refers to nonexistent ref, "
 			  "unable to checkout.\n"));
@@ -700,7 +700,7 @@ static int checkout(int submodule_progress)
 	}
 	if (!strcmp(head, "HEAD")) {
 		if (advice_detached_head)
-			detach_advice(sha1_to_hex(sha1));
+			detach_advice(oid_to_hex(&oid));
 	} else {
 		if (!starts_with(head, "refs/heads/"))
 			die(_("HEAD not found below refs/heads!"));
@@ -721,7 +721,7 @@ static int checkout(int submodule_progress)
 	opts.src_index = &the_index;
 	opts.dst_index = &the_index;
 
-	tree = parse_tree_indirect(sha1);
+	tree = parse_tree_indirect(oid.hash);
 	parse_tree(tree);
 	init_tree_desc(&t, tree->buffer, tree->size);
 	if (unpack_trees(1, &t, &opts) < 0)
@@ -731,7 +731,7 @@ static int checkout(int submodule_progress)
 		die(_("unable to write new index file"));
 
 	err |= run_hook_le(NULL, "post-checkout", sha1_to_hex(null_sha1),
-			   sha1_to_hex(sha1), "1", NULL);
+			   oid_to_hex(&oid), "1", NULL);
 
 	if (!err && option_recursive) {
 		struct argv_array args = ARGV_ARRAY_INIT;
-- 
2.11.0


^ permalink raw reply related

* [PATCH v4 18/19] builtin/merge-base: convert to struct object_id
From: brian m. carlson @ 2017-02-20  0:10 UTC (permalink / raw)
  To: git; +Cc: Jeff King, Michael Haggerty, Junio C Hamano, Ramsay Jones
In-Reply-To: <20170220001031.559931-1-sandals@crustytoothpaste.net>

Convert the remaining uses of unsigned char [20] to struct object_id.

Signed-off-by: brian m. carlson <sandals@crustytoothpaste.net>
---
 builtin/merge-base.c | 28 ++++++++++++++--------------
 1 file changed, 14 insertions(+), 14 deletions(-)

diff --git a/builtin/merge-base.c b/builtin/merge-base.c
index db95bc29cf..cfe2a796f8 100644
--- a/builtin/merge-base.c
+++ b/builtin/merge-base.c
@@ -36,12 +36,12 @@ static const char * const merge_base_usage[] = {
 
 static struct commit *get_commit_reference(const char *arg)
 {
-	unsigned char revkey[20];
+	struct object_id revkey;
 	struct commit *r;
 
-	if (get_sha1(arg, revkey))
+	if (get_oid(arg, &revkey))
 		die("Not a valid object name %s", arg);
-	r = lookup_commit_reference(revkey);
+	r = lookup_commit_reference(revkey.hash);
 	if (!r)
 		die("Not a valid commit name %s", arg);
 
@@ -113,14 +113,14 @@ struct rev_collect {
 	unsigned int initial : 1;
 };
 
-static void add_one_commit(unsigned char *sha1, struct rev_collect *revs)
+static void add_one_commit(struct object_id *oid, struct rev_collect *revs)
 {
 	struct commit *commit;
 
-	if (is_null_sha1(sha1))
+	if (is_null_oid(oid))
 		return;
 
-	commit = lookup_commit(sha1);
+	commit = lookup_commit(oid->hash);
 	if (!commit ||
 	    (commit->object.flags & TMP_MARK) ||
 	    parse_commit(commit))
@@ -139,15 +139,15 @@ static int collect_one_reflog_ent(struct object_id *ooid, struct object_id *noid
 
 	if (revs->initial) {
 		revs->initial = 0;
-		add_one_commit(ooid->hash, revs);
+		add_one_commit(ooid, revs);
 	}
-	add_one_commit(noid->hash, revs);
+	add_one_commit(noid, revs);
 	return 0;
 }
 
 static int handle_fork_point(int argc, const char **argv)
 {
-	unsigned char sha1[20];
+	struct object_id oid;
 	char *refname;
 	const char *commitname;
 	struct rev_collect revs;
@@ -155,7 +155,7 @@ static int handle_fork_point(int argc, const char **argv)
 	struct commit_list *bases;
 	int i, ret = 0;
 
-	switch (dwim_ref(argv[0], strlen(argv[0]), sha1, &refname)) {
+	switch (dwim_ref(argv[0], strlen(argv[0]), oid.hash, &refname)) {
 	case 0:
 		die("No such ref: '%s'", argv[0]);
 	case 1:
@@ -165,16 +165,16 @@ static int handle_fork_point(int argc, const char **argv)
 	}
 
 	commitname = (argc == 2) ? argv[1] : "HEAD";
-	if (get_sha1(commitname, sha1))
+	if (get_oid(commitname, &oid))
 		die("Not a valid object name: '%s'", commitname);
 
-	derived = lookup_commit_reference(sha1);
+	derived = lookup_commit_reference(oid.hash);
 	memset(&revs, 0, sizeof(revs));
 	revs.initial = 1;
 	for_each_reflog_ent(refname, collect_one_reflog_ent, &revs);
 
-	if (!revs.nr && !get_sha1(refname, sha1))
-		add_one_commit(sha1, &revs);
+	if (!revs.nr && !get_oid(refname, &oid))
+		add_one_commit(&oid, &revs);
 
 	for (i = 0; i < revs.nr; i++)
 		revs.commit[i]->object.flags &= ~TMP_MARK;
-- 
2.11.0


^ permalink raw reply related

* [PATCH v4 01/19] hex: introduce parse_oid_hex
From: brian m. carlson @ 2017-02-20  0:10 UTC (permalink / raw)
  To: git; +Cc: Jeff King, Michael Haggerty, Junio C Hamano, Ramsay Jones
In-Reply-To: <20170220001031.559931-1-sandals@crustytoothpaste.net>

Introduce a function, parse_oid_hex, which parses a hexadecimal object
ID and if successful, sets a pointer to just beyond the last character.
This allows for simpler, more robust parsing without needing to
hard-code integer values throughout the codebase.

Signed-off-by: brian m. carlson <sandals@crustytoothpaste.net>
---
 cache.h | 9 +++++++++
 hex.c   | 8 ++++++++
 2 files changed, 17 insertions(+)

diff --git a/cache.h b/cache.h
index 61fc86e6d7..e03a672d15 100644
--- a/cache.h
+++ b/cache.h
@@ -1319,6 +1319,15 @@ extern char *oid_to_hex_r(char *out, const struct object_id *oid);
 extern char *sha1_to_hex(const unsigned char *sha1);	/* static buffer result! */
 extern char *oid_to_hex(const struct object_id *oid);	/* same static buffer as sha1_to_hex */
 
+/*
+ * Parse a 40-character hexadecimal object ID starting from hex, updating the
+ * pointer specified by end when parsing stops.  The resulting object ID is
+ * stored in oid.  Returns 0 on success.  Parsing will stop on the first NUL or
+ * other invalid character.  end is only updated on success; otherwise, it is
+ * unmodified.
+ */
+extern int parse_oid_hex(const char *hex, struct object_id *oid, const char **end);
+
 extern int interpret_branch_name(const char *str, int len, struct strbuf *);
 extern int get_oid_mb(const char *str, struct object_id *oid);
 
diff --git a/hex.c b/hex.c
index 845b01a874..eab7b626ee 100644
--- a/hex.c
+++ b/hex.c
@@ -53,6 +53,14 @@ int get_oid_hex(const char *hex, struct object_id *oid)
 	return get_sha1_hex(hex, oid->hash);
 }
 
+int parse_oid_hex(const char *hex, struct object_id *oid, const char **end)
+{
+	int ret = get_oid_hex(hex, oid);
+	if (!ret)
+		*end = hex + GIT_SHA1_HEXSZ;
+	return ret;
+}
+
 char *sha1_to_hex_r(char *buffer, const unsigned char *sha1)
 {
 	static const char hex[] = "0123456789abcdef";
-- 
2.11.0


^ permalink raw reply related

* [PATCH v4 12/19] builtin/replace: convert to struct object_id
From: brian m. carlson @ 2017-02-20  0:10 UTC (permalink / raw)
  To: git; +Cc: Jeff King, Michael Haggerty, Junio C Hamano, Ramsay Jones
In-Reply-To: <20170220001031.559931-1-sandals@crustytoothpaste.net>

Convert various uses of unsigned char [20] to struct object_id.  Rename
replace_object_sha1 to replace_object_oid.  Finally, specify a constant
in terms of GIT_SHA1_HEXSZ.

Signed-off-by: brian m. carlson <sandals@crustytoothpaste.net>
---
 builtin/replace.c | 112 +++++++++++++++++++++++++++---------------------------
 1 file changed, 56 insertions(+), 56 deletions(-)

diff --git a/builtin/replace.c b/builtin/replace.c
index b58c714cb8..f7716a5472 100644
--- a/builtin/replace.c
+++ b/builtin/replace.c
@@ -88,78 +88,78 @@ static int list_replace_refs(const char *pattern, const char *format)
 }
 
 typedef int (*each_replace_name_fn)(const char *name, const char *ref,
-				    const unsigned char *sha1);
+				    const struct object_id *oid);
 
 static int for_each_replace_name(const char **argv, each_replace_name_fn fn)
 {
 	const char **p, *full_hex;
 	char ref[PATH_MAX];
 	int had_error = 0;
-	unsigned char sha1[20];
+	struct object_id oid;
 
 	for (p = argv; *p; p++) {
-		if (get_sha1(*p, sha1)) {
+		if (get_oid(*p, &oid)) {
 			error("Failed to resolve '%s' as a valid ref.", *p);
 			had_error = 1;
 			continue;
 		}
-		full_hex = sha1_to_hex(sha1);
+		full_hex = oid_to_hex(&oid);
 		snprintf(ref, sizeof(ref), "%s%s", git_replace_ref_base, full_hex);
 		/* read_ref() may reuse the buffer */
 		full_hex = ref + strlen(git_replace_ref_base);
-		if (read_ref(ref, sha1)) {
+		if (read_ref(ref, oid.hash)) {
 			error("replace ref '%s' not found.", full_hex);
 			had_error = 1;
 			continue;
 		}
-		if (fn(full_hex, ref, sha1))
+		if (fn(full_hex, ref, &oid))
 			had_error = 1;
 	}
 	return had_error;
 }
 
 static int delete_replace_ref(const char *name, const char *ref,
-			      const unsigned char *sha1)
+			      const struct object_id *oid)
 {
-	if (delete_ref(ref, sha1, 0))
+	if (delete_ref(ref, oid->hash, 0))
 		return 1;
 	printf("Deleted replace ref '%s'\n", name);
 	return 0;
 }
 
-static void check_ref_valid(unsigned char object[20],
-			    unsigned char prev[20],
+static void check_ref_valid(struct object_id *object,
+			    struct object_id *prev,
 			    char *ref,
 			    int ref_size,
 			    int force)
 {
 	if (snprintf(ref, ref_size,
 		     "%s%s", git_replace_ref_base,
-		     sha1_to_hex(object)) > ref_size - 1)
+		     oid_to_hex(object)) > ref_size - 1)
 		die("replace ref name too long: %.*s...", 50, ref);
 	if (check_refname_format(ref, 0))
 		die("'%s' is not a valid ref name.", ref);
 
-	if (read_ref(ref, prev))
-		hashclr(prev);
+	if (read_ref(ref, prev->hash))
+		oidclr(prev);
 	else if (!force)
 		die("replace ref '%s' already exists", ref);
 }
 
-static int replace_object_sha1(const char *object_ref,
-			       unsigned char object[20],
+static int replace_object_oid(const char *object_ref,
+			       struct object_id *object,
 			       const char *replace_ref,
-			       unsigned char repl[20],
+			       struct object_id *repl,
 			       int force)
 {
-	unsigned char prev[20];
+	struct object_id prev;
 	enum object_type obj_type, repl_type;
 	char ref[PATH_MAX];
 	struct ref_transaction *transaction;
 	struct strbuf err = STRBUF_INIT;
 
-	obj_type = sha1_object_info(object, NULL);
-	repl_type = sha1_object_info(repl, NULL);
+	obj_type = sha1_object_info(object->hash, NULL);
+	repl_type = sha1_object_info(repl->hash, NULL);
 	if (!force && obj_type != repl_type)
 		die("Objects must be of the same type.\n"
 		    "'%s' points to a replaced object of type '%s'\n"
@@ -167,11 +167,11 @@ static int replace_object_sha1(const char *object_ref,
 		    object_ref, typename(obj_type),
 		    replace_ref, typename(repl_type));
 
-	check_ref_valid(object, prev, ref, sizeof(ref), force);
+	check_ref_valid(object, &prev, ref, sizeof(ref), force);
 
 	transaction = ref_transaction_begin(&err);
 	if (!transaction ||
-	    ref_transaction_update(transaction, ref, repl, prev,
+	    ref_transaction_update(transaction, ref, repl->hash, prev.hash,
 				   0, NULL, &err) ||
 	    ref_transaction_commit(transaction, &err))
 		die("%s", err.buf);
@@ -182,14 +182,14 @@ static int replace_object_sha1(const char *object_ref,
 
 static int replace_object(const char *object_ref, const char *replace_ref, int force)
 {
-	unsigned char object[20], repl[20];
+	struct object_id object, repl;
 
-	if (get_sha1(object_ref, object))
+	if (get_oid(object_ref, &object))
 		die("Failed to resolve '%s' as a valid ref.", object_ref);
-	if (get_sha1(replace_ref, repl))
+	if (get_oid(replace_ref, &repl))
 		die("Failed to resolve '%s' as a valid ref.", replace_ref);
 
-	return replace_object_sha1(object_ref, object, replace_ref, repl, force);
+	return replace_object_oid(object_ref, &object, replace_ref, &repl, force);
 }
 
 /*
@@ -197,7 +197,7 @@ static int replace_object(const char *object_ref, const char *replace_ref, int f
  * If "raw" is true, then the object's raw contents are printed according to
  * "type". Otherwise, we pretty-print the contents for human editing.
  */
-static void export_object(const unsigned char *sha1, enum object_type type,
+static void export_object(const struct object_id *oid, enum object_type type,
 			  int raw, const char *filename)
 {
 	struct child_process cmd = CHILD_PROCESS_INIT;
@@ -213,7 +213,7 @@ static void export_object(const unsigned char *sha1, enum object_type type,
 		argv_array_push(&cmd.args, typename(type));
 	else
 		argv_array_push(&cmd.args, "-p");
-	argv_array_push(&cmd.args, sha1_to_hex(sha1));
+	argv_array_push(&cmd.args, oid_to_hex(oid));
 	cmd.git_cmd = 1;
 	cmd.out = fd;
 
@@ -226,7 +226,7 @@ static void export_object(const unsigned char *sha1, enum object_type type,
  * interpreting it as "type", and writing the result to the object database.
  * The sha1 of the written object is returned via sha1.
  */
-static void import_object(unsigned char *sha1, enum object_type type,
+static void import_object(struct object_id *oid, enum object_type type,
 			  int raw, const char *filename)
 {
 	int fd;
@@ -254,7 +254,7 @@ static void import_object(unsigned char *sha1, enum object_type type,
 
 		if (finish_command(&cmd))
 			die("mktree reported failure");
-		if (get_sha1_hex(result.buf, sha1) < 0)
+		if (get_oid_hex(result.buf, oid) < 0)
 			die("mktree did not return an object name");
 
 		strbuf_release(&result);
@@ -264,7 +264,7 @@ static void import_object(unsigned char *sha1, enum object_type type,
 
 		if (fstat(fd, &st) < 0)
 			die_errno("unable to fstat %s", filename);
-		if (index_fd(sha1, fd, &st, type, NULL, flags) < 0)
+		if (index_fd(oid->hash, fd, &st, type, NULL, flags) < 0)
 			die("unable to write object to database");
 		/* index_fd close()s fd for us */
 	}
@@ -279,29 +279,29 @@ static int edit_and_replace(const char *object_ref, int force, int raw)
 {
 	char *tmpfile = git_pathdup("REPLACE_EDITOBJ");
 	enum object_type type;
-	unsigned char old[20], new[20], prev[20];
+	struct object_id old, new, prev;
 	char ref[PATH_MAX];
 
-	if (get_sha1(object_ref, old) < 0)
+	if (get_oid(object_ref, &old) < 0)
 		die("Not a valid object name: '%s'", object_ref);
 
-	type = sha1_object_info(old, NULL);
+	type = sha1_object_info(old.hash, NULL);
 	if (type < 0)
-		die("unable to get object type for %s", sha1_to_hex(old));
+		die("unable to get object type for %s", oid_to_hex(&old));
 
-	check_ref_valid(old, prev, ref, sizeof(ref), force);
+	check_ref_valid(&old, &prev, ref, sizeof(ref), force);
 
-	export_object(old, type, raw, tmpfile);
+	export_object(&old, type, raw, tmpfile);
 	if (launch_editor(tmpfile, NULL, NULL) < 0)
 		die("editing object file failed");
-	import_object(new, type, raw, tmpfile);
+	import_object(&new, type, raw, tmpfile);
 
 	free(tmpfile);
 
-	if (!hashcmp(old, new))
-		return error("new object is the same as the old one: '%s'", sha1_to_hex(old));
+	if (!oidcmp(&old, &new))
+		return error("new object is the same as the old one: '%s'", oid_to_hex(&old));
 
-	return replace_object_sha1(object_ref, old, "replacement", new, force);
+	return replace_object_oid(object_ref, &old, "replacement", &new, force);
 }
 
 static void replace_parents(struct strbuf *buf, int argc, const char **argv)
@@ -312,7 +312,7 @@ static void replace_parents(struct strbuf *buf, int argc, const char **argv)
 
 	/* find existing parents */
 	parent_start = buf->buf;
-	parent_start += 46; /* "tree " + "hex sha1" + "\n" */
+	parent_start += GIT_SHA1_HEXSZ + 6; /* "tree " + "hex sha1" + "\n" */
 	parent_end = parent_start;
 
 	while (starts_with(parent_end, "parent "))
@@ -320,11 +320,11 @@ static void replace_parents(struct strbuf *buf, int argc, const char **argv)
 
 	/* prepare new parents */
 	for (i = 0; i < argc; i++) {
-		unsigned char sha1[20];
-		if (get_sha1(argv[i], sha1) < 0)
+		struct object_id oid;
+		if (get_oid(argv[i], &oid) < 0)
 			die(_("Not a valid object name: '%s'"), argv[i]);
-		lookup_commit_or_die(sha1, argv[i]);
-		strbuf_addf(&new_parents, "parent %s\n", sha1_to_hex(sha1));
+		lookup_commit_or_die(oid.hash, argv[i]);
+		strbuf_addf(&new_parents, "parent %s\n", oid_to_hex(&oid));
 	}
 
 	/* replace existing parents with new ones */
@@ -345,12 +345,12 @@ static void check_one_mergetag(struct commit *commit,
 {
 	struct check_mergetag_data *mergetag_data = (struct check_mergetag_data *)data;
 	const char *ref = mergetag_data->argv[0];
-	unsigned char tag_sha1[20];
+	struct object_id tag_oid;
 	struct tag *tag;
 	int i;
 
-	hash_sha1_file(extra->value, extra->len, typename(OBJ_TAG), tag_sha1);
-	tag = lookup_tag(tag_sha1);
+	hash_sha1_file(extra->value, extra->len, typename(OBJ_TAG), tag_oid.hash);
+	tag = lookup_tag(tag_oid.hash);
 	if (!tag)
 		die(_("bad mergetag in commit '%s'"), ref);
 	if (parse_tag_buffer(tag, extra->value, extra->len))
@@ -366,7 +366,7 @@ static void check_one_mergetag(struct commit *commit,
 	}
 
 	die(_("original commit '%s' contains mergetag '%s' that is discarded; "
-	      "use --edit instead of --graft"), ref, sha1_to_hex(tag_sha1));
+	      "use --edit instead of --graft"), ref, oid_to_hex(&tag_oid));
 }
 
 static void check_mergetags(struct commit *commit, int argc, const char **argv)
@@ -380,16 +380,16 @@ static void check_mergetags(struct commit *commit, int argc, const char **argv)
 
 static int create_graft(int argc, const char **argv, int force)
 {
-	unsigned char old[20], new[20];
+	struct object_id old, new;
 	const char *old_ref = argv[0];
 	struct commit *commit;
 	struct strbuf buf = STRBUF_INIT;
 	const char *buffer;
 	unsigned long size;
 
-	if (get_sha1(old_ref, old) < 0)
+	if (get_oid(old_ref, &old) < 0)
 		die(_("Not a valid object name: '%s'"), old_ref);
-	commit = lookup_commit_or_die(old, old_ref);
+	commit = lookup_commit_or_die(old.hash, old_ref);
 
 	buffer = get_commit_buffer(commit, &size);
 	strbuf_add(&buf, buffer, size);
@@ -404,15 +404,15 @@ static int create_graft(int argc, const char **argv, int force)
 
 	check_mergetags(commit, argc, argv);
 
-	if (write_sha1_file(buf.buf, buf.len, commit_type, new))
+	if (write_sha1_file(buf.buf, buf.len, commit_type, new.hash))
 		die(_("could not write replacement commit for: '%s'"), old_ref);
 
 	strbuf_release(&buf);
 
-	if (!hashcmp(old, new))
-		return error("new commit is the same as the old one: '%s'", sha1_to_hex(old));
+	if (!oidcmp(&old, &new))
+		return error("new commit is the same as the old one: '%s'", oid_to_hex(&old));
 
-	return replace_object_sha1(old_ref, old, "replacement", new, force);
+	return replace_object_oid(old_ref, &old, "replacement", &new, force);
 }
 
 int cmd_replace(int argc, const char **argv, const char *prefix)
-- 
2.11.0


^ permalink raw reply related

* [PATCH v4 14/19] refs: convert each_reflog_ent_fn to struct object_id
From: brian m. carlson @ 2017-02-20  0:10 UTC (permalink / raw)
  To: git; +Cc: Jeff King, Michael Haggerty, Junio C Hamano, Ramsay Jones
In-Reply-To: <20170220001031.559931-1-sandals@crustytoothpaste.net>

Make each_reflog_ent_fn take two struct object_id pointers instead of
two pointers to unsigned char.  Convert the various callbacks to use
struct object_id as well.  Also, rename fsck_handle_reflog_sha1 to
fsck_handle_reflog_oid.

Signed-off-by: brian m. carlson <sandals@crustytoothpaste.net>
---
 builtin/fsck.c       | 16 ++++++++--------
 builtin/merge-base.c |  6 +++---
 builtin/reflog.c     |  2 +-
 reflog-walk.c        |  6 +++---
 refs.c               | 24 ++++++++++++------------
 refs.h               |  2 +-
 refs/files-backend.c | 24 ++++++++++++------------
 revision.c           | 12 ++++++------
 sha1_name.c          |  2 +-
 wt-status.c          |  6 +++---
 10 files changed, 50 insertions(+), 50 deletions(-)

diff --git a/builtin/fsck.c b/builtin/fsck.c
index 1a5caccd0f..9b37606858 100644
--- a/builtin/fsck.c
+++ b/builtin/fsck.c
@@ -396,13 +396,13 @@ static int fsck_obj_buffer(const unsigned char *sha1, enum object_type type,
 
 static int default_refs;
 
-static void fsck_handle_reflog_sha1(const char *refname, unsigned char *sha1,
+static void fsck_handle_reflog_oid(const char *refname, struct object_id *oid,
 	unsigned long timestamp)
 {
 	struct object *obj;
 
-	if (!is_null_sha1(sha1)) {
-		obj = lookup_object(sha1);
+	if (!is_null_oid(oid)) {
+		obj = lookup_object(oid->hash);
 		if (obj && (obj->flags & HAS_OBJ)) {
 			if (timestamp && name_objects)
 				add_decoration(fsck_walk_options.object_names,
@@ -411,13 +411,13 @@ static void fsck_handle_reflog_sha1(const char *refname, unsigned char *sha1,
 			obj->used = 1;
 			mark_object_reachable(obj);
 		} else {
-			error("%s: invalid reflog entry %s", refname, sha1_to_hex(sha1));
+			error("%s: invalid reflog entry %s", refname, oid_to_hex(oid));
 			errors_found |= ERROR_REACHABLE;
 		}
 	}
 }
 
-static int fsck_handle_reflog_ent(unsigned char *osha1, unsigned char *nsha1,
+static int fsck_handle_reflog_ent(struct object_id *ooid, struct object_id *noid,
 		const char *email, unsigned long timestamp, int tz,
 		const char *message, void *cb_data)
 {
@@ -425,10 +425,10 @@ static int fsck_handle_reflog_ent(unsigned char *osha1, unsigned char *nsha1,
 
 	if (verbose)
 		fprintf(stderr, "Checking reflog %s->%s\n",
-			sha1_to_hex(osha1), sha1_to_hex(nsha1));
+			oid_to_hex(ooid), oid_to_hex(noid));
 
-	fsck_handle_reflog_sha1(refname, osha1, 0);
-	fsck_handle_reflog_sha1(refname, nsha1, timestamp);
+	fsck_handle_reflog_oid(refname, ooid, 0);
+	fsck_handle_reflog_oid(refname, noid, timestamp);
 	return 0;
 }
 
diff --git a/builtin/merge-base.c b/builtin/merge-base.c
index b572a37c26..db95bc29cf 100644
--- a/builtin/merge-base.c
+++ b/builtin/merge-base.c
@@ -131,7 +131,7 @@ static void add_one_commit(unsigned char *sha1, struct rev_collect *revs)
 	commit->object.flags |= TMP_MARK;
 }
 
-static int collect_one_reflog_ent(unsigned char *osha1, unsigned char *nsha1,
+static int collect_one_reflog_ent(struct object_id *ooid, struct object_id *noid,
 				  const char *ident, unsigned long timestamp,
 				  int tz, const char *message, void *cbdata)
 {
@@ -139,9 +139,9 @@ static int collect_one_reflog_ent(unsigned char *osha1, unsigned char *nsha1,
 
 	if (revs->initial) {
 		revs->initial = 0;
-		add_one_commit(osha1, revs);
+		add_one_commit(ooid->hash, revs);
 	}
-	add_one_commit(nsha1, revs);
+	add_one_commit(noid->hash, revs);
 	return 0;
 }
 
diff --git a/builtin/reflog.c b/builtin/reflog.c
index 7a7136e53e..7472775778 100644
--- a/builtin/reflog.c
+++ b/builtin/reflog.c
@@ -615,7 +615,7 @@ static int cmd_reflog_expire(int argc, const char **argv, const char *prefix)
 	return status;
 }
 
-static int count_reflog_ent(unsigned char *osha1, unsigned char *nsha1,
+static int count_reflog_ent(struct object_id *ooid, struct object_id *noid,
 		const char *email, unsigned long timestamp, int tz,
 		const char *message, void *cb_data)
 {
diff --git a/reflog-walk.c b/reflog-walk.c
index fe5be41471..99679f5825 100644
--- a/reflog-walk.c
+++ b/reflog-walk.c
@@ -19,7 +19,7 @@ struct complete_reflogs {
 	int nr, alloc;
 };
 
-static int read_one_reflog(unsigned char *osha1, unsigned char *nsha1,
+static int read_one_reflog(struct object_id *ooid, struct object_id *noid,
 		const char *email, unsigned long timestamp, int tz,
 		const char *message, void *cb_data)
 {
@@ -28,8 +28,8 @@ static int read_one_reflog(unsigned char *osha1, unsigned char *nsha1,
 
 	ALLOC_GROW(array->items, array->nr + 1, array->alloc);
 	item = array->items + array->nr;
-	hashcpy(item->ooid.hash, osha1);
-	hashcpy(item->noid.hash, nsha1);
+	oidcpy(&item->ooid, ooid);
+	oidcpy(&item->noid, noid);
 	item->email = xstrdup(email);
 	item->timestamp = timestamp;
 	item->tz = tz;
diff --git a/refs.c b/refs.c
index cd36b64ed9..b900626d3f 100644
--- a/refs.c
+++ b/refs.c
@@ -674,7 +674,7 @@ struct read_ref_at_cb {
 	int *cutoff_cnt;
 };
 
-static int read_ref_at_ent(unsigned char *osha1, unsigned char *nsha1,
+static int read_ref_at_ent(struct object_id *ooid, struct object_id *noid,
 		const char *email, unsigned long timestamp, int tz,
 		const char *message, void *cb_data)
 {
@@ -698,30 +698,30 @@ static int read_ref_at_ent(unsigned char *osha1, unsigned char *nsha1,
 		 * hold the values for the previous record.
 		 */
 		if (!is_null_sha1(cb->osha1)) {
-			hashcpy(cb->sha1, nsha1);
-			if (hashcmp(cb->osha1, nsha1))
+			hashcpy(cb->sha1, noid->hash);
+			if (hashcmp(cb->osha1, noid->hash))
 				warning("Log for ref %s has gap after %s.",
 					cb->refname, show_date(cb->date, cb->tz, DATE_MODE(RFC2822)));
 		}
 		else if (cb->date == cb->at_time)
-			hashcpy(cb->sha1, nsha1);
-		else if (hashcmp(nsha1, cb->sha1))
+			hashcpy(cb->sha1, noid->hash);
+		else if (hashcmp(noid->hash, cb->sha1))
 			warning("Log for ref %s unexpectedly ended on %s.",
 				cb->refname, show_date(cb->date, cb->tz,
 						       DATE_MODE(RFC2822)));
-		hashcpy(cb->osha1, osha1);
-		hashcpy(cb->nsha1, nsha1);
+		hashcpy(cb->osha1, ooid->hash);
+		hashcpy(cb->nsha1, noid->hash);
 		cb->found_it = 1;
 		return 1;
 	}
-	hashcpy(cb->osha1, osha1);
-	hashcpy(cb->nsha1, nsha1);
+	hashcpy(cb->osha1, ooid->hash);
+	hashcpy(cb->nsha1, noid->hash);
 	if (cb->cnt > 0)
 		cb->cnt--;
 	return 0;
 }
 
-static int read_ref_at_ent_oldest(unsigned char *osha1, unsigned char *nsha1,
+static int read_ref_at_ent_oldest(struct object_id *ooid, struct object_id *noid,
 				  const char *email, unsigned long timestamp,
 				  int tz, const char *message, void *cb_data)
 {
@@ -735,9 +735,9 @@ static int read_ref_at_ent_oldest(unsigned char *osha1, unsigned char *nsha1,
 		*cb->cutoff_tz = tz;
 	if (cb->cutoff_cnt)
 		*cb->cutoff_cnt = cb->reccnt;
-	hashcpy(cb->sha1, osha1);
+	hashcpy(cb->sha1, ooid->hash);
 	if (is_null_sha1(cb->sha1))
-		hashcpy(cb->sha1, nsha1);
+		hashcpy(cb->sha1, noid->hash);
 	/* We just want the first entry */
 	return 1;
 }
diff --git a/refs.h b/refs.h
index 9fbff90e79..a075117a2a 100644
--- a/refs.h
+++ b/refs.h
@@ -292,7 +292,7 @@ int delete_reflog(const char *refname);
 
 /* iterate over reflog entries */
 typedef int each_reflog_ent_fn(
-		unsigned char *old_sha1, unsigned char *new_sha1,
+		struct object_id *old_oid, struct object_id *new_oid,
 		const char *committer, unsigned long timestamp,
 		int tz, const char *msg, void *cb_data);
 
diff --git a/refs/files-backend.c b/refs/files-backend.c
index c041d4ba21..d7a5fd2a7c 100644
--- a/refs/files-backend.c
+++ b/refs/files-backend.c
@@ -3113,15 +3113,15 @@ static int files_delete_reflog(struct ref_store *ref_store,
 
 static int show_one_reflog_ent(struct strbuf *sb, each_reflog_ent_fn fn, void *cb_data)
 {
-	unsigned char osha1[20], nsha1[20];
+	struct object_id ooid, noid;
 	char *email_end, *message;
 	unsigned long timestamp;
 	int tz;
 
 	/* old SP new SP name <email> SP time TAB msg LF */
 	if (sb->len < 83 || sb->buf[sb->len - 1] != '\n' ||
-	    get_sha1_hex(sb->buf, osha1) || sb->buf[40] != ' ' ||
-	    get_sha1_hex(sb->buf + 41, nsha1) || sb->buf[81] != ' ' ||
+	    get_oid_hex(sb->buf, &ooid) || sb->buf[40] != ' ' ||
+	    get_oid_hex(sb->buf + 41, &noid) || sb->buf[81] != ' ' ||
 	    !(email_end = strchr(sb->buf + 82, '>')) ||
 	    email_end[1] != ' ' ||
 	    !(timestamp = strtoul(email_end + 2, &message, 10)) ||
@@ -3136,7 +3136,7 @@ static int show_one_reflog_ent(struct strbuf *sb, each_reflog_ent_fn fn, void *c
 		message += 6;
 	else
 		message += 7;
-	return fn(osha1, nsha1, sb->buf + 82, timestamp, tz, message, cb_data);
+	return fn(&ooid, &noid, sb->buf + 82, timestamp, tz, message, cb_data);
 }
 
 static char *find_beginning_of_line(char *bob, char *scan)
@@ -3936,10 +3936,10 @@ struct expire_reflog_cb {
 	reflog_expiry_should_prune_fn *should_prune_fn;
 	void *policy_cb;
 	FILE *newlog;
-	unsigned char last_kept_sha1[20];
+	struct object_id last_kept_oid;
 };
 
-static int expire_reflog_ent(unsigned char *osha1, unsigned char *nsha1,
+static int expire_reflog_ent(struct object_id *ooid, struct object_id *noid,
 			     const char *email, unsigned long timestamp, int tz,
 			     const char *message, void *cb_data)
 {
@@ -3947,9 +3947,9 @@ static int expire_reflog_ent(unsigned char *osha1, unsigned char *nsha1,
 	struct expire_reflog_policy_cb *policy_cb = cb->policy_cb;
 
 	if (cb->flags & EXPIRE_REFLOGS_REWRITE)
-		osha1 = cb->last_kept_sha1;
+		ooid = &cb->last_kept_oid;
 
-	if ((*cb->should_prune_fn)(osha1, nsha1, email, timestamp, tz,
+	if ((*cb->should_prune_fn)(ooid->hash, noid->hash, email, timestamp, tz,
 				   message, policy_cb)) {
 		if (!cb->newlog)
 			printf("would prune %s", message);
@@ -3958,9 +3958,9 @@ static int expire_reflog_ent(unsigned char *osha1, unsigned char *nsha1,
 	} else {
 		if (cb->newlog) {
 			fprintf(cb->newlog, "%s %s %s %lu %+05d\t%s",
-				sha1_to_hex(osha1), sha1_to_hex(nsha1),
+				oid_to_hex(ooid), oid_to_hex(noid),
 				email, timestamp, tz, message);
-			hashcpy(cb->last_kept_sha1, nsha1);
+			oidcpy(&cb->last_kept_oid, noid);
 		}
 		if (cb->flags & EXPIRE_REFLOGS_VERBOSE)
 			printf("keep %s", message);
@@ -4047,14 +4047,14 @@ static int files_reflog_expire(struct ref_store *ref_store,
 		 */
 		int update = (flags & EXPIRE_REFLOGS_UPDATE_REF) &&
 			!(type & REF_ISSYMREF) &&
-			!is_null_sha1(cb.last_kept_sha1);
+			!is_null_oid(&cb.last_kept_oid);
 
 		if (close_lock_file(&reflog_lock)) {
 			status |= error("couldn't write %s: %s", log_file,
 					strerror(errno));
 		} else if (update &&
 			   (write_in_full(get_lock_file_fd(lock->lk),
-				sha1_to_hex(cb.last_kept_sha1), 40) != 40 ||
+				oid_to_hex(&cb.last_kept_oid), GIT_SHA1_HEXSZ) != GIT_SHA1_HEXSZ ||
 			    write_str_in_full(get_lock_file_fd(lock->lk), "\n") != 1 ||
 			    close_ref(lock) < 0)) {
 			status |= error("couldn't write %s",
diff --git a/revision.c b/revision.c
index b37dbec378..d9fe73318a 100644
--- a/revision.c
+++ b/revision.c
@@ -1196,11 +1196,11 @@ static void handle_refs(const char *submodule, struct rev_info *revs, unsigned f
 	for_each(submodule, handle_one_ref, &cb);
 }
 
-static void handle_one_reflog_commit(unsigned char *sha1, void *cb_data)
+static void handle_one_reflog_commit(struct object_id *oid, void *cb_data)
 {
 	struct all_refs_cb *cb = cb_data;
-	if (!is_null_sha1(sha1)) {
-		struct object *o = parse_object(sha1);
+	if (!is_null_oid(oid)) {
+		struct object *o = parse_object(oid->hash);
 		if (o) {
 			o->flags |= cb->all_flags;
 			/* ??? CMDLINEFLAGS ??? */
@@ -1214,12 +1214,12 @@ static void handle_one_reflog_commit(unsigned char *sha1, void *cb_data)
 	}
 }
 
-static int handle_one_reflog_ent(unsigned char *osha1, unsigned char *nsha1,
+static int handle_one_reflog_ent(struct object_id *ooid, struct object_id *noid,
 		const char *email, unsigned long timestamp, int tz,
 		const char *message, void *cb_data)
 {
-	handle_one_reflog_commit(osha1, cb_data);
-	handle_one_reflog_commit(nsha1, cb_data);
+	handle_one_reflog_commit(ooid, cb_data);
+	handle_one_reflog_commit(noid, cb_data);
 	return 0;
 }
 
diff --git a/sha1_name.c b/sha1_name.c
index 73a915ff1b..744e9f884a 100644
--- a/sha1_name.c
+++ b/sha1_name.c
@@ -1051,7 +1051,7 @@ struct grab_nth_branch_switch_cbdata {
 	struct strbuf buf;
 };
 
-static int grab_nth_branch_switch(unsigned char *osha1, unsigned char *nsha1,
+static int grab_nth_branch_switch(struct object_id *ooid, struct object_id *noid,
 				  const char *email, unsigned long timestamp, int tz,
 				  const char *message, void *cb_data)
 {
diff --git a/wt-status.c b/wt-status.c
index 0ec090a338..5fac8437b0 100644
--- a/wt-status.c
+++ b/wt-status.c
@@ -1373,7 +1373,7 @@ struct grab_1st_switch_cbdata {
 	unsigned char nsha1[20];
 };
 
-static int grab_1st_switch(unsigned char *osha1, unsigned char *nsha1,
+static int grab_1st_switch(struct object_id *ooid, struct object_id *noid,
 			   const char *email, unsigned long timestamp, int tz,
 			   const char *message, void *cb_data)
 {
@@ -1387,13 +1387,13 @@ static int grab_1st_switch(unsigned char *osha1, unsigned char *nsha1,
 		return 0;
 	target += strlen(" to ");
 	strbuf_reset(&cb->buf);
-	hashcpy(cb->nsha1, nsha1);
+	hashcpy(cb->nsha1, noid->hash);
 	end = strchrnul(target, '\n');
 	strbuf_add(&cb->buf, target, end - target);
 	if (!strcmp(cb->buf.buf, "HEAD")) {
 		/* HEAD is relative. Resolve it to the right reflog entry. */
 		strbuf_reset(&cb->buf);
-		strbuf_add_unique_abbrev(&cb->buf, nsha1, DEFAULT_ABBREV);
+		strbuf_add_unique_abbrev(&cb->buf, noid->hash, DEFAULT_ABBREV);
 	}
 	return 1;
 }
-- 
2.11.0


^ permalink raw reply related

* [PATCH v4 19/19] wt-status: convert to struct object_id
From: brian m. carlson @ 2017-02-20  0:10 UTC (permalink / raw)
  To: git; +Cc: Jeff King, Michael Haggerty, Junio C Hamano, Ramsay Jones
In-Reply-To: <20170220001031.559931-1-sandals@crustytoothpaste.net>

Convert the remaining uses of unsigned char [20] to struct object_id.

Signed-off-by: brian m. carlson <sandals@crustytoothpaste.net>
---
 wt-status.c | 44 ++++++++++++++++++++++----------------------
 1 file changed, 22 insertions(+), 22 deletions(-)

diff --git a/wt-status.c b/wt-status.c
index 5fac8437b0..a8d1faf80d 100644
--- a/wt-status.c
+++ b/wt-status.c
@@ -1115,16 +1115,16 @@ static void abbrev_sha1_in_line(struct strbuf *line)
 
 	split = strbuf_split_max(line, ' ', 3);
 	if (split[0] && split[1]) {
-		unsigned char sha1[20];
+		struct object_id oid;
 
 		/*
 		 * strbuf_split_max left a space. Trim it and re-add
 		 * it after abbreviation.
 		 */
 		strbuf_trim(split[1]);
-		if (!get_sha1(split[1]->buf, sha1)) {
+		if (!get_oid(split[1]->buf, &oid)) {
 			strbuf_reset(split[1]);
-			strbuf_add_unique_abbrev(split[1], sha1,
+			strbuf_add_unique_abbrev(split[1], oid.hash,
 						 DEFAULT_ABBREV);
 			strbuf_addch(split[1], ' ');
 			strbuf_reset(line);
@@ -1340,7 +1340,7 @@ static void show_bisect_in_progress(struct wt_status *s,
 static char *get_branch(const struct worktree *wt, const char *path)
 {
 	struct strbuf sb = STRBUF_INIT;
-	unsigned char sha1[20];
+	struct object_id oid;
 	const char *branch_name;
 
 	if (strbuf_read_file(&sb, worktree_git_path(wt, "%s", path), 0) <= 0)
@@ -1354,9 +1354,9 @@ static char *get_branch(const struct worktree *wt, const char *path)
 		strbuf_remove(&sb, 0, branch_name - sb.buf);
 	else if (starts_with(sb.buf, "refs/"))
 		;
-	else if (!get_sha1_hex(sb.buf, sha1)) {
+	else if (!get_oid_hex(sb.buf, &oid)) {
 		strbuf_reset(&sb);
-		strbuf_add_unique_abbrev(&sb, sha1, DEFAULT_ABBREV);
+		strbuf_add_unique_abbrev(&sb, oid.hash, DEFAULT_ABBREV);
 	} else if (!strcmp(sb.buf, "detached HEAD")) /* rebase */
 		goto got_nothing;
 	else			/* bisect */
@@ -1370,7 +1370,7 @@ static char *get_branch(const struct worktree *wt, const char *path)
 
 struct grab_1st_switch_cbdata {
 	struct strbuf buf;
-	unsigned char nsha1[20];
+	struct object_id noid;
 };
 
 static int grab_1st_switch(struct object_id *ooid, struct object_id *noid,
@@ -1387,7 +1387,7 @@ static int grab_1st_switch(struct object_id *ooid, struct object_id *noid,
 		return 0;
 	target += strlen(" to ");
 	strbuf_reset(&cb->buf);
-	hashcpy(cb->nsha1, noid->hash);
+	oidcpy(&cb->noid, noid);
 	end = strchrnul(target, '\n');
 	strbuf_add(&cb->buf, target, end - target);
 	if (!strcmp(cb->buf.buf, "HEAD")) {
@@ -1402,7 +1402,7 @@ static void wt_status_get_detached_from(struct wt_status_state *state)
 {
 	struct grab_1st_switch_cbdata cb;
 	struct commit *commit;
-	unsigned char sha1[20];
+	struct object_id oid;
 	char *ref = NULL;
 
 	strbuf_init(&cb.buf, 0);
@@ -1411,22 +1411,22 @@ static void wt_status_get_detached_from(struct wt_status_state *state)
 		return;
 	}
 
-	if (dwim_ref(cb.buf.buf, cb.buf.len, sha1, &ref) == 1 &&
+	if (dwim_ref(cb.buf.buf, cb.buf.len, oid.hash, &ref) == 1 &&
 	    /* sha1 is a commit? match without further lookup */
-	    (!hashcmp(cb.nsha1, sha1) ||
+	    (!oidcmp(&cb.noid, &oid) ||
 	     /* perhaps sha1 is a tag, try to dereference to a commit */
-	     ((commit = lookup_commit_reference_gently(sha1, 1)) != NULL &&
-	      !hashcmp(cb.nsha1, commit->object.oid.hash)))) {
+	     ((commit = lookup_commit_reference_gently(oid.hash, 1)) != NULL &&
+	      !oidcmp(&cb.noid, &commit->object.oid)))) {
 		const char *from = ref;
 		if (!skip_prefix(from, "refs/tags/", &from))
 			skip_prefix(from, "refs/remotes/", &from);
 		state->detached_from = xstrdup(from);
 	} else
 		state->detached_from =
-			xstrdup(find_unique_abbrev(cb.nsha1, DEFAULT_ABBREV));
-	hashcpy(state->detached_sha1, cb.nsha1);
-	state->detached_at = !get_sha1("HEAD", sha1) &&
-			     !hashcmp(sha1, state->detached_sha1);
+			xstrdup(find_unique_abbrev(cb.noid.hash, DEFAULT_ABBREV));
+	hashcpy(state->detached_sha1, cb.noid.hash);
+	state->detached_at = !get_oid("HEAD", &oid) &&
+			     !hashcmp(oid.hash, state->detached_sha1);
 
 	free(ref);
 	strbuf_release(&cb.buf);
@@ -1476,22 +1476,22 @@ void wt_status_get_state(struct wt_status_state *state,
 			 int get_detached_from)
 {
 	struct stat st;
-	unsigned char sha1[20];
+	struct object_id oid;
 
 	if (!stat(git_path_merge_head(), &st)) {
 		state->merge_in_progress = 1;
 	} else if (wt_status_check_rebase(NULL, state)) {
 		;		/* all set */
 	} else if (!stat(git_path_cherry_pick_head(), &st) &&
-			!get_sha1("CHERRY_PICK_HEAD", sha1)) {
+			!get_oid("CHERRY_PICK_HEAD", &oid)) {
 		state->cherry_pick_in_progress = 1;
-		hashcpy(state->cherry_pick_head_sha1, sha1);
+		hashcpy(state->cherry_pick_head_sha1, oid.hash);
 	}
 	wt_status_check_bisect(NULL, state);
 	if (!stat(git_path_revert_head(), &st) &&
-	    !get_sha1("REVERT_HEAD", sha1)) {
+	    !get_oid("REVERT_HEAD", &oid)) {
 		state->revert_in_progress = 1;
-		hashcpy(state->revert_head_sha1, sha1);
+		hashcpy(state->revert_head_sha1, oid.hash);
 	}
 
 	if (get_detached_from)
-- 
2.11.0


^ permalink raw reply related

* [PATCH v4 08/19] builtin/branch: convert to struct object_id
From: brian m. carlson @ 2017-02-20  0:10 UTC (permalink / raw)
  To: git; +Cc: Jeff King, Michael Haggerty, Junio C Hamano, Ramsay Jones
In-Reply-To: <20170220001031.559931-1-sandals@crustytoothpaste.net>

Signed-off-by: brian m. carlson <sandals@crustytoothpaste.net>
---
 builtin/branch.c | 26 +++++++++++++-------------
 1 file changed, 13 insertions(+), 13 deletions(-)

diff --git a/builtin/branch.c b/builtin/branch.c
index 9d30f55b0b..faf472ff8f 100644
--- a/builtin/branch.c
+++ b/builtin/branch.c
@@ -32,7 +32,7 @@ static const char * const builtin_branch_usage[] = {
 };
 
 static const char *head;
-static unsigned char head_sha1[20];
+static struct object_id head_oid;
 
 static int branch_use_color = -1;
 static char branch_colors[][COLOR_MAXLEN] = {
@@ -117,13 +117,13 @@ static int branch_merged(int kind, const char *name,
 	if (kind == FILTER_REFS_BRANCHES) {
 		struct branch *branch = branch_get(name);
 		const char *upstream = branch_get_upstream(branch, NULL);
-		unsigned char sha1[20];
+		struct object_id oid;
 
 		if (upstream &&
 		    (reference_name = reference_name_to_free =
 		     resolve_refdup(upstream, RESOLVE_REF_READING,
-				    sha1, NULL)) != NULL)
-			reference_rev = lookup_commit_reference(sha1);
+				    oid.hash, NULL)) != NULL)
+			reference_rev = lookup_commit_reference(oid.hash);
 	}
 	if (!reference_rev)
 		reference_rev = head_rev;
@@ -153,10 +153,10 @@ static int branch_merged(int kind, const char *name,
 }
 
 static int check_branch_commit(const char *branchname, const char *refname,
-			       const unsigned char *sha1, struct commit *head_rev,
+			       const struct object_id *oid, struct commit *head_rev,
 			       int kinds, int force)
 {
-	struct commit *rev = lookup_commit_reference(sha1);
+	struct commit *rev = lookup_commit_reference(oid->hash);
 	if (!rev) {
 		error(_("Couldn't look up commit object for '%s'"), refname);
 		return -1;
@@ -183,7 +183,7 @@ static int delete_branches(int argc, const char **argv, int force, int kinds,
 			   int quiet)
 {
 	struct commit *head_rev = NULL;
-	unsigned char sha1[20];
+	struct object_id oid;
 	char *name = NULL;
 	const char *fmt;
 	int i;
@@ -207,7 +207,7 @@ static int delete_branches(int argc, const char **argv, int force, int kinds,
 	}
 
 	if (!force) {
-		head_rev = lookup_commit_reference(head_sha1);
+		head_rev = lookup_commit_reference(head_oid.hash);
 		if (!head_rev)
 			die(_("Couldn't look up commit object for HEAD"));
 	}
@@ -235,7 +235,7 @@ static int delete_branches(int argc, const char **argv, int force, int kinds,
 					RESOLVE_REF_READING
 					| RESOLVE_REF_NO_RECURSE
 					| RESOLVE_REF_ALLOW_BAD_NAME,
-					sha1, &flags);
+					oid.hash, &flags);
 		if (!target) {
 			error(remote_branch
 			      ? _("remote-tracking branch '%s' not found.")
@@ -245,13 +245,13 @@ static int delete_branches(int argc, const char **argv, int force, int kinds,
 		}
 
 		if (!(flags & (REF_ISSYMREF|REF_ISBROKEN)) &&
-		    check_branch_commit(bname.buf, name, sha1, head_rev, kinds,
+		    check_branch_commit(bname.buf, name, &oid, head_rev, kinds,
 					force)) {
 			ret = 1;
 			goto next;
 		}
 
-		if (delete_ref(name, is_null_sha1(sha1) ? NULL : sha1,
+		if (delete_ref(name, is_null_oid(&oid) ? NULL : oid.hash,
 			       REF_NODEREF)) {
 			error(remote_branch
 			      ? _("Error deleting remote-tracking branch '%s'")
@@ -267,7 +267,7 @@ static int delete_branches(int argc, const char **argv, int force, int kinds,
 			       bname.buf,
 			       (flags & REF_ISBROKEN) ? "broken"
 			       : (flags & REF_ISSYMREF) ? target
-			       : find_unique_abbrev(sha1, DEFAULT_ABBREV));
+			       : find_unique_abbrev(oid.hash, DEFAULT_ABBREV));
 		}
 		delete_branch_config(bname.buf);
 
@@ -693,7 +693,7 @@ int cmd_branch(int argc, const char **argv, const char *prefix)
 
 	track = git_branch_track;
 
-	head = resolve_refdup("HEAD", 0, head_sha1, NULL);
+	head = resolve_refdup("HEAD", 0, head_oid.hash, NULL);
 	if (!head)
 		die(_("Failed to resolve HEAD as a valid ref."));
 	if (!strcmp(head, "HEAD"))
-- 
2.11.0


^ permalink raw reply related


This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox