]> git.ipfire.org Git - thirdparty/git.git/log
thirdparty/git.git
4 years agopath: also guard `.gitmodules` against NTFS Alternate Data Streams
Johannes Schindelin [Wed, 28 Aug 2019 10:22:17 +0000 (12:22 +0200)] 
path: also guard `.gitmodules` against NTFS Alternate Data Streams

We just safe-guarded `.git` against NTFS Alternate Data Stream-related
attack vectors, and now it is time to do the same for `.gitmodules`.

Note: In the added regression test, we refrain from verifying all kinds
of variations between short names and NTFS Alternate Data Streams: as
the new code disallows _all_ Alternate Data Streams of `.gitmodules`, it
is enough to test one in order to know that all of them are guarded
against.

Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
4 years agopath: safeguard `.git` against NTFS Alternate Streams Accesses
Johannes Schindelin [Wed, 28 Aug 2019 10:22:17 +0000 (12:22 +0200)] 
path: safeguard `.git` against NTFS Alternate Streams Accesses

Probably inspired by HFS' resource streams, NTFS supports "Alternate
Data Streams": by appending `:<stream-name>` to the file name,
information in addition to the file contents can be written and read,
information that is copied together with the file (unless copied to a
non-NTFS location).

These Alternate Data Streams are typically used for things like marking
an executable as having just been downloaded from the internet (and
hence not necessarily being trustworthy).

In addition to a stream name, a stream type can be appended, like so:
`:<stream-name>:<stream-type>`. Unless specified, the default stream
type is `$DATA` for files and `$INDEX_ALLOCATION` for directories. In
other words, `.git::$INDEX_ALLOCATION` is a valid way to reference the
`.git` directory!

In our work in Git v2.2.1 to protect Git on NTFS drives under
`core.protectNTFS`, we focused exclusively on NTFS short names, unaware
of the fact that NTFS Alternate Data Streams offer a similar attack
vector.

Let's fix this.

Seeing as it is better to be safe than sorry, we simply disallow paths
referring to *any* NTFS Alternate Data Stream of `.git`, not just
`::$INDEX_ALLOCATION`. This also simplifies the implementation.

This closes CVE-2019-1352.

Further reading about NTFS Alternate Data Streams:
https://docs.microsoft.com/en-us/openspecs/windows_protocols/ms-fscc/c54dec26-1551-4d3a-a0ea-4fa40f848eb3

Reported-by: Nicolas Joly <Nicolas.Joly@microsoft.com>
Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
4 years agois_ntfs_dotgit(): only verify the leading segment
Johannes Schindelin [Mon, 23 Sep 2019 06:58:11 +0000 (08:58 +0200)] 
is_ntfs_dotgit(): only verify the leading segment

The config setting `core.protectNTFS` is specifically designed to work
not only on Windows, but anywhere, to allow for repositories hosted on,
say, Linux servers to be protected against NTFS-specific attack vectors.

As a consequence, `is_ntfs_dotgit()` manually splits backslash-separated
paths (but does not do the same for paths separated by forward slashes),
under the assumption that the backslash might not be a valid directory
separator on the _current_ Operating System.

However, the two callers, `verify_path()` and `fsck_tree()`, are
supposed to feed only individual path segments to the `is_ntfs_dotgit()`
function.

This causes a lot of duplicate scanning (and very inefficient scanning,
too, as the inner loop of `is_ntfs_dotgit()` was optimized for
readability rather than for speed.

Let's simplify the design of `is_ntfs_dotgit()` by putting the burden of
splitting the paths by backslashes as directory separators on the
callers of said function.

Consequently, the `verify_path()` function, which already splits the
path by directory separators, now treats backslashes as directory
separators _explicitly_ when `core.protectNTFS` is turned on, even on
platforms where the backslash is _not_ a directory separator.

Note that we have to repeat some code in `verify_path()`: if the
backslash is not a directory separator on the current Operating System,
we want to allow file names like `\`, but we _do_ want to disallow paths
that are clearly intended to cause harm when the repository is cloned on
Windows.

The `fsck_tree()` function (the other caller of `is_ntfs_dotgit()`) now
needs to look for backslashes in tree entries' names specifically when
`core.protectNTFS` is turned on. While it would be tempting to
completely disallow backslashes in that case (much like `fsck` reports
names containing forward slashes as "full paths"), this would be
overzealous: when `core.protectNTFS` is turned on in a non-Windows
setup, backslashes are perfectly valid characters in file names while we
_still_ want to disallow tree entries that are clearly designed to
exploit NTFS-specific behavior.

This simplification will make subsequent changes easier to implement,
such as turning `core.protectNTFS` on by default (not only on Windows)
or protecting against attack vectors involving NTFS Alternate Data
Streams.

Incidentally, this change allows for catching malicious repositories
that contain tree entries of the form `dir\.gitmodules` already on the
server side rather than only on the client side (and previously only on
Windows): in contrast to `is_ntfs_dotgit()`, the
`is_ntfs_dotgitmodules()` function already expects the caller to split
the paths by directory separators.

Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
4 years agotest-path-utils: offer to run a protectNTFS/protectHFS benchmark
Garima Singh [Wed, 4 Sep 2019 17:36:39 +0000 (13:36 -0400)] 
test-path-utils: offer to run a protectNTFS/protectHFS benchmark

In preparation to flipping the default on `core.protectNTFS`, let's have
some way to measure the speed impact of this config setting reliably
(and for comparison, the `core.protectHFS` config setting).

For now, this is a manual performance benchmark:

./t/helper/test-path-utils protect_ntfs_hfs [arguments...]

where the arguments are an optional number of file names to test with,
optionally followed by minimum and maximum length of the random file
names. The default values are one million, 3 and 20, respectively.

Just like `sqrti()` in `bisect.c`, we introduce a very simple function
to approximation the square root of a given value, in order to avoid
having to introduce the first user of `<math.h>` in Git's source code.

Note: this is _not_ implemented as a Unix shell script in t/perf/
because we really care about _very_ precise timings here, and Unix shell
scripts are simply unsuited for precise and consistent benchmarking.

Signed-off-by: Garima Singh <garima.singh@microsoft.com>
Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
4 years agopath.c: document the purpose of `is_ntfs_dotgit()`
Johannes Schindelin [Mon, 16 Sep 2019 18:44:31 +0000 (20:44 +0200)] 
path.c: document the purpose of `is_ntfs_dotgit()`

Previously, this function was completely undocumented. It is worth,
though, to explain what is going on, as it is not really obvious at all.

Suggested-by: Garima Singh <garima.singh@microsoft.com>
Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
4 years agomingw: disallow backslash characters in tree objects' file names
Johannes Schindelin [Thu, 12 Sep 2019 12:54:05 +0000 (14:54 +0200)] 
mingw: disallow backslash characters in tree objects' file names

The backslash character is not a valid part of a file name on Windows.
Hence it is dangerous to allow writing files that were unpacked from
tree objects, when the stored file name contains a backslash character:
it will be misinterpreted as directory separator.

This not only causes ambiguity when a tree contains a blob `a\b` and a
tree `a` that contains a blob `b`, but it also can be used as part of an
attack vector to side-step the careful protections against writing into
the `.git/` directory during a clone of a maliciously-crafted
repository.

Let's prevent that, addressing CVE-2019-1354.

Note: we guard against backslash characters in tree objects' file names
_only_ on Windows (because on other platforms, even on those where NTFS
volumes can be mounted, the backslash character is _not_ a directory
separator), and _only_ when `core.protectNTFS = true` (because users
might need to generate tree objects for other platforms, of course
without touching the worktree, e.g. using `git update-index
--cacheinfo`).

Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
4 years agoclone --recurse-submodules: prevent name squatting on Windows
Johannes Schindelin [Thu, 12 Sep 2019 12:20:39 +0000 (14:20 +0200)] 
clone --recurse-submodules: prevent name squatting on Windows

In addition to preventing `.git` from being tracked by Git, on Windows
we also have to prevent `git~1` from being tracked, as the default NTFS
short name (also known as the "8.3 filename") for the file name `.git`
is `git~1`, otherwise it would be possible for malicious repositories to
write directly into the `.git/` directory, e.g. a `post-checkout` hook
that would then be executed _during_ a recursive clone.

When we implemented appropriate protections in 2b4c6efc821 (read-cache:
optionally disallow NTFS .git variants, 2014-12-16), we had analyzed
carefully that the `.git` directory or file would be guaranteed to be
the first directory entry to be written. Otherwise it would be possible
e.g. for a file named `..git` to be assigned the short name `git~1` and
subsequently, the short name generated for `.git` would be `git~2`. Or
`git~3`. Or even `~9999999` (for a detailed explanation of the lengths
we have to go to protect `.gitmodules`, see the commit message of
e7cb0b4455c (is_ntfs_dotgit: match other .git files, 2018-05-11)).

However, by exploiting two issues (that will be addressed in a related
patch series close by), it is currently possible to clone a submodule
into a non-empty directory:

- On Windows, file names cannot end in a space or a period (for
  historical reasons: the period separating the base name from the file
  extension was not actually written to disk, and the base name/file
  extension was space-padded to the full 8/3 characters, respectively).
  Helpfully, when creating a directory under the name, say, `sub.`, that
  trailing period is trimmed automatically and the actual name on disk
  is `sub`.

  This means that while Git thinks that the submodule names `sub` and
  `sub.` are different, they both access `.git/modules/sub/`.

- While the backslash character is a valid file name character on Linux,
  it is not so on Windows. As Git tries to be cross-platform, it
  therefore allows backslash characters in the file names stored in tree
  objects.

  Which means that it is totally possible that a submodule `c` sits next
  to a file `c\..git`, and on Windows, during recursive clone a file
  called `..git` will be written into `c/`, of course _before_ the
  submodule is cloned.

Note that the actual exploit is not quite as simple as having a
submodule `c` next to a file `c\..git`, as we have to make sure that the
directory `.git/modules/b` already exists when the submodule is checked
out, otherwise a different code path is taken in `module_clone()` that
does _not_ allow a non-empty submodule directory to exist already.

Even if we will address both issues nearby (the next commit will
disallow backslash characters in tree entries' file names on Windows,
and another patch will disallow creating directories/files with trailing
spaces or periods), it is a wise idea to defend in depth against this
sort of attack vector: when submodules are cloned recursively, we now
_require_ the directory to be empty, addressing CVE-2019-1349.

Note: the code path we patch is shared with the code path of `git
submodule update --init`, which must not expect, in general, that the
directory is empty. Hence we have to introduce the new option
`--force-init` and hand it all the way down from `git submodule` to the
actual `git submodule--helper` process that performs the initial clone.

Reported-by: Nicolas Joly <Nicolas.Joly@microsoft.com>
Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
4 years agofast-import: disallow "feature import-marks" by default
Jeff King [Thu, 29 Aug 2019 19:08:42 +0000 (15:08 -0400)] 
fast-import: disallow "feature import-marks" by default

As with export-marks in the previous commit, import-marks can access the
filesystem. This is significantly less dangerous than export-marks
because it only involves reading from arbitrary paths, rather than
writing them. However, it could still be surprising and have security
implications (e.g., exfiltrating data from a service that accepts
fast-import streams).

Let's lump it (and its "if-exists" counterpart) in with export-marks,
and enable the in-stream version only if --allow-unsafe-features is set.

Signed-off-by: Jeff King <peff@peff.net>
4 years agofast-import: disallow "feature export-marks" by default
Jeff King [Thu, 29 Aug 2019 18:37:26 +0000 (14:37 -0400)] 
fast-import: disallow "feature export-marks" by default

The fast-import stream command "feature export-marks=<path>" lets the
stream write marks to an arbitrary path. This may be surprising if you
are running fast-import against an untrusted input (which otherwise
cannot do anything except update Git objects and refs).

Let's disallow the use of this feature by default, and provide a
command-line option to re-enable it (you can always just use the
command-line --export-marks as well, but the in-stream version provides
an easy way for exporters to control the process).

This is a backwards-incompatible change, since the default is flipping
to the new, safer behavior. However, since the main users of the
in-stream versions would be import/export-based remote helpers, and
since we trust remote helpers already (which are already running
arbitrary code), we'll pass the new option by default when reading a
remote helper's stream. This should minimize the impact.

Note that the implementation isn't totally simple, as we have to work
around the fact that fast-import doesn't parse its command-line options
until after it has read any "feature" lines from the stream. This is how
it lets command-line options override in-stream. But in our case, it's
important to parse the new --allow-unsafe-features first.

There are three options for resolving this:

  1. Do a separate "early" pass over the options. This is easy for us to
     do because there are no command-line options that allow the
     "unstuck" form (so there's no chance of us mistaking an argument
     for an option), though it does introduce a risk of incorrect
     parsing later (e.g,. if we convert to parse-options).

  2. Move the option parsing phase back to the start of the program, but
     teach the stream-reading code never to override an existing value.
     This is tricky, because stream "feature" lines override each other
     (meaning we'd have to start tracking the source for every option).

  3. Accept that we might parse a "feature export-marks" line that is
     forbidden, as long we don't _act_ on it until after we've parsed
     the command line options.

     This would, in fact, work with the current code, but only because
     the previous patch fixed the export-marks parser to avoid touching
     the filesystem.

     So while it works, it does carry risk of somebody getting it wrong
     in the future in a rather subtle and unsafe way.

I've gone with option (1) here as simple, safe, and unlikely to cause
regressions.

This fixes CVE-2019-1348.

Signed-off-by: Jeff King <peff@peff.net>
4 years agofast-import: delay creating leading directories for export-marks
Jeff King [Thu, 29 Aug 2019 17:33:48 +0000 (13:33 -0400)] 
fast-import: delay creating leading directories for export-marks

When we parse the --export-marks option, we don't immediately open the
file, but we do create any leading directories. This can be especially
confusing when a command-line option overrides an in-stream one, in
which case we'd create the leading directory for the in-stream file,
even though we never actually write the file.

Let's instead create the directories just before opening the file, which
means we'll create only useful directories. Note that this could change
the handling of relative paths if we chdir() in between, but we don't
actually do so; the only permanent chdir is from setup_git_directory()
which runs before either code path (potentially we should take the
pre-setup dir into account to avoid surprising the user, but that's an
orthogonal change).

The test just adapts the existing "override" test to use paths with
leading directories. This checks both that the correct directory is
created (which worked before but was not tested), and that the
overridden one is not (our new fix here).

While we're here, let's also check the error result of
safe_create_leading_directories(). We'd presumably notice any failure
immediately after when we try to open the file itself, but we can give a
more specific error message in this case.

Signed-off-by: Jeff King <peff@peff.net>
4 years agofast-import: stop creating leading directories for import-marks
Jeff King [Thu, 29 Aug 2019 17:07:04 +0000 (13:07 -0400)] 
fast-import: stop creating leading directories for import-marks

When asked to import marks from "subdir/file.marks", we create the
leading directory "subdir" if it doesn't exist. This makes no sense for
importing marks, where we only ever open the path for reading.

Most of the time this would be a noop, since if the marks file exists,
then the leading directories exist, too. But if it doesn't (e.g.,
because --import-marks-if-exists was used), then we'd create the useless
directory.

This dates back to 580d5f83e7 (fast-import: always create marks_file
directories, 2010-03-29). Even then it was useless, so it seems to have
been added in error alongside the --export-marks case (which _is_
helpful).

Signed-off-by: Jeff King <peff@peff.net>
4 years agofast-import: tighten parsing of boolean command line options
Jeff King [Thu, 29 Aug 2019 15:25:45 +0000 (11:25 -0400)] 
fast-import: tighten parsing of boolean command line options

We parse options like "--max-pack-size=" using skip_prefix(), which
makes sense to get at the bytes after the "=". However, we also parse
"--quiet" and "--stats" with skip_prefix(), which allows things like
"--quiet-nonsense" to behave like "--quiet".

This was a mistaken conversion in 0f6927c229 (fast-import: put option
parsing code in separate functions, 2009-12-04). Let's tighten this to
an exact match, which was the original intent.

Signed-off-by: Jeff King <peff@peff.net>
4 years agot9300: create marks files for double-import-marks test
Jeff King [Thu, 29 Aug 2019 17:43:23 +0000 (13:43 -0400)] 
t9300: create marks files for double-import-marks test

Our tests confirm that providing two "import-marks" options in a
fast-import stream is an error. However, the invoked command would fail
even without covering this case, because the marks files themselves do
not actually exist.  Let's create the files to make sure we fail for the
right reason (we actually do, because the option parsing happens before
we open anything, but this future-proofs our test).

Signed-off-by: Jeff King <peff@peff.net>
4 years agot9300: drop some useless uses of cat
Jeff King [Thu, 29 Aug 2019 15:19:18 +0000 (11:19 -0400)] 
t9300: drop some useless uses of cat

These waste a process, and make the line longer than it needs to be.

Signed-off-by: Jeff King <peff@peff.net>
5 years agoGit 2.14.5 v2.14.5
Junio C Hamano [Thu, 27 Sep 2018 18:19:11 +0000 (11:19 -0700)] 
Git 2.14.5

Signed-off-by: Junio C Hamano <gitster@pobox.com>
5 years agosubmodule-config: ban submodule paths that start with a dash
Jeff King [Mon, 24 Sep 2018 08:39:55 +0000 (04:39 -0400)] 
submodule-config: ban submodule paths that start with a dash

We recently banned submodule urls that look like
command-line options. This is the matching change to ban
leading-dash paths.

As with the urls, this should not break any use cases that
currently work. Even with our "--" separator passed to
git-clone, git-submodule.sh gets confused. Without the code
portion of this patch, the clone of "-sub" added in t7417
would yield results like:

    /path/to/git-submodule: 410: cd: Illegal option -s
    /path/to/git-submodule: 417: cd: Illegal option -s
    /path/to/git-submodule: 410: cd: Illegal option -s
    /path/to/git-submodule: 417: cd: Illegal option -s
    Fetched in submodule path '-sub', but it did not contain b56243f8f4eb91b2f1f8109452e659f14dd3fbe4. Direct fetching of that commit failed.

Moreover, naively adding such a submodule doesn't work:

  $ git submodule add $url -sub
  The following path is ignored by one of your .gitignore files:
  -sub

even though there is no such ignore pattern (the test script
hacks around this with a well-placed "git mv").

Unlike leading-dash urls, though, it's possible that such a
path _could_ be useful if we eventually made it work. So
this commit should be seen not as recommending a particular
policy, but rather temporarily closing off a broken and
possibly dangerous code-path. We may revisit this decision
later.

There are two minor differences to the tests in t7416 (that
covered urls):

  1. We don't have a "./-sub" escape hatch to make this
     work, since the submodule code expects to be able to
     match canonical index names to the path field (so you
     are free to add submodule config with that path, but we
     would never actually use it, since an index entry would
     never start with "./").

  2. After this patch, cloning actually succeeds. Since we
     ignore the submodule.*.path value, we fail to find a
     config stanza for our submodule at all, and simply
     treat it as inactive. We still check for the "ignoring"
     message.

Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
5 years agosubmodule-config: ban submodule urls that start with dash
Jeff King [Mon, 24 Sep 2018 08:36:30 +0000 (04:36 -0400)] 
submodule-config: ban submodule urls that start with dash

The previous commit taught the submodule code to invoke our
"git clone $url $path" with a "--" separator so that we
aren't confused by urls or paths that start with dashes.

However, that's just one code path. It's not clear if there
are others, and it would be an easy mistake to add one in
the future. Moreover, even with the fix in the previous
commit, it's quite hard to actually do anything useful with
such an entry. Any url starting with a dash must fall into
one of three categories:

 - it's meant as a file url, like "-path". But then any
   clone is not going to have the matching path, since it's
   by definition relative inside the newly created clone. If
   you spell it as "./-path", the submodule code sees the
   "/" and translates this to an absolute path, so it at
   least works (assuming the receiver has the same
   filesystem layout as you). But that trick does not apply
   for a bare "-path".

 - it's meant as an ssh url, like "-host:path". But this
   already doesn't work, as we explicitly disallow ssh
   hostnames that begin with a dash (to avoid option
   injection against ssh).

 - it's a remote-helper scheme, like "-scheme::data". This
   _could_ work if the receiver bends over backwards and
   creates a funny-named helper like "git-remote--scheme".
   But normally there would not be any helper that matches.

Since such a url does not work today and is not likely to do
anything useful in the future, let's simply disallow them
entirely. That protects the existing "git clone" path (in a
belt-and-suspenders way), along with any others that might
exist.

Our tests cover two cases:

  1. A file url with "./" continues to work, showing that
     there's an escape hatch for people with truly silly
     repo names.

  2. A url starting with "-" is rejected.

Note that we expect case (2) to fail, but it would have done
so even without this commit, for the reasons given above.
So instead of just expecting failure, let's also check for
the magic word "ignoring" on stderr. That lets us know that
we failed for the right reason.

Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
5 years agosubmodule--helper: use "--" to signal end of clone options
Jeff King [Mon, 24 Sep 2018 08:32:15 +0000 (04:32 -0400)] 
submodule--helper: use "--" to signal end of clone options

When we clone a submodule, we call "git clone $url $path".
But there's nothing to say that those components can't begin
with a dash themselves, confusing git-clone into thinking
they're options. Let's pass "--" to make it clear what we
expect.

There's no test here, because it's actually quite hard to
make these names work, even with "git clone" parsing them
correctly. And we're going to restrict these cases even
further in future commits. So we'll leave off testing until
then; this is just the minimal fix to prevent us from doing
something stupid with a badly formed entry.

Reported-by: joernchen <joernchen@phenoelit.de>
Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
5 years agoGit 2.14.4 v2.14.4
Junio C Hamano [Tue, 22 May 2018 05:12:02 +0000 (14:12 +0900)] 
Git 2.14.4

Signed-off-by: Junio C Hamano <gitster@pobox.com>
5 years agoSync with Git 2.13.7
Junio C Hamano [Tue, 22 May 2018 05:10:49 +0000 (14:10 +0900)] 
Sync with Git 2.13.7

* maint-2.13:
  Git 2.13.7
  verify_path: disallow symlinks in .gitmodules
  update-index: stat updated files earlier
  verify_dotfile: mention case-insensitivity in comment
  verify_path: drop clever fallthrough
  skip_prefix: add case-insensitive variant
  is_{hfs,ntfs}_dotgitmodules: add tests
  is_ntfs_dotgit: match other .git files
  is_hfs_dotgit: match other .git files
  is_ntfs_dotgit: use a size_t for traversing string
  submodule-config: verify submodule names as paths

5 years agoGit 2.13.7 v2.13.7
Junio C Hamano [Tue, 22 May 2018 04:50:36 +0000 (13:50 +0900)] 
Git 2.13.7

Signed-off-by: Junio C Hamano <gitster@pobox.com>
5 years agoMerge branch 'jk/submodule-fix-loose' into maint-2.13
Junio C Hamano [Tue, 22 May 2018 04:48:26 +0000 (13:48 +0900)] 
Merge branch 'jk/submodule-fix-loose' into maint-2.13

* jk/submodule-fix-loose:
  verify_path: disallow symlinks in .gitmodules
  update-index: stat updated files earlier
  verify_dotfile: mention case-insensitivity in comment
  verify_path: drop clever fallthrough
  skip_prefix: add case-insensitive variant
  is_{hfs,ntfs}_dotgitmodules: add tests
  is_ntfs_dotgit: match other .git files
  is_hfs_dotgit: match other .git files
  is_ntfs_dotgit: use a size_t for traversing string
  submodule-config: verify submodule names as paths

5 years agoverify_path: disallow symlinks in .gitmodules
Jeff King [Sat, 5 May 2018 00:03:35 +0000 (20:03 -0400)] 
verify_path: disallow symlinks in .gitmodules

There are a few reasons it's not a good idea to make
.gitmodules a symlink, including:

  1. It won't be portable to systems without symlinks.

  2. It may behave inconsistently, since Git may look at
     this file in the index or a tree without bothering to
     resolve any symbolic links. We don't do this _yet_, but
     the config infrastructure is there and it's planned for
     the future.

With some clever code, we could make (2) work. And some
people may not care about (1) if they only work on one
platform. But there are a few security reasons to simply
disallow it:

  a. A symlinked .gitmodules file may circumvent any fsck
     checks of the content.

  b. Git may read and write from the on-disk file without
     sanity checking the symlink target. So for example, if
     you link ".gitmodules" to "../oops" and run "git
     submodule add", we'll write to the file "oops" outside
     the repository.

Again, both of those are problems that _could_ be solved
with sufficient code, but given the complications in (1) and
(2), we're better off just outlawing it explicitly.

Note the slightly tricky call to verify_path() in
update-index's update_one(). There we may not have a mode if
we're not updating from the filesystem (e.g., we might just
be removing the file). Passing "0" as the mode there works
fine; since it's not a symlink, we'll just skip the extra
checks.

Signed-off-by: Jeff King <peff@peff.net>
5 years agoupdate-index: stat updated files earlier
Jeff King [Mon, 14 May 2018 15:00:56 +0000 (11:00 -0400)] 
update-index: stat updated files earlier

In the update_one(), we check verify_path() on the proposed
path before doing anything else. In preparation for having
verify_path() look at the file mode, let's stat the file
earlier, so we can check the mode accurately.

This is made a bit trickier by the fact that this function
only does an lstat in a few code paths (the ones that flow
down through process_path()). So we can speculatively do the
lstat() here and pass the results down, and just use a dummy
mode for cases where we won't actually be updating the index
from the filesystem.

Signed-off-by: Jeff King <peff@peff.net>
5 years agoverify_dotfile: mention case-insensitivity in comment
Jeff King [Tue, 15 May 2018 13:56:50 +0000 (09:56 -0400)] 
verify_dotfile: mention case-insensitivity in comment

We're more restrictive than we need to be in matching ".GIT"
on case-sensitive filesystems; let's make a note that this
is intentional.

Signed-off-by: Jeff King <peff@peff.net>
5 years agoverify_path: drop clever fallthrough
Jeff King [Sun, 13 May 2018 17:00:23 +0000 (13:00 -0400)] 
verify_path: drop clever fallthrough

We check ".git" and ".." in the same switch statement, and
fall through the cases to share the end-of-component check.
While this saves us a line or two, it makes modifying the
function much harder. Let's just write it out.

Signed-off-by: Jeff King <peff@peff.net>
5 years agoskip_prefix: add case-insensitive variant
Jeff King [Sun, 13 May 2018 16:57:14 +0000 (12:57 -0400)] 
skip_prefix: add case-insensitive variant

We have the convenient skip_prefix() helper, but if you want
to do case-insensitive matching, you're stuck doing it by
hand. We could add an extra parameter to the function to
let callers ask for this, but the function is small and
somewhat performance-critical. Let's just re-implement it
for the case-insensitive version.

Signed-off-by: Jeff King <peff@peff.net>
5 years agois_{hfs,ntfs}_dotgitmodules: add tests
Johannes Schindelin [Sat, 12 May 2018 20:16:51 +0000 (22:16 +0200)] 
is_{hfs,ntfs}_dotgitmodules: add tests

This tests primarily for NTFS issues, but also adds one example of an
HFS+ issue.

Thanks go to Congyi Wu for coming up with the list of examples where
NTFS would possibly equate the filename with `.gitmodules`.

Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
Signed-off-by: Jeff King <peff@peff.net>
5 years agois_ntfs_dotgit: match other .git files
Johannes Schindelin [Fri, 11 May 2018 14:03:54 +0000 (16:03 +0200)] 
is_ntfs_dotgit: match other .git files

When we started to catch NTFS short names that clash with .git, we only
looked for GIT~1. This is sufficient because we only ever clone into an
empty directory, so .git is guaranteed to be the first subdirectory or
file in that directory.

However, even with a fresh clone, .gitmodules is *not* necessarily the
first file to be written that would want the NTFS short name GITMOD~1: a
malicious repository can add .gitmodul0000 and friends, which sorts
before `.gitmodules` and is therefore checked out *first*. For that
reason, we have to test not only for ~1 short names, but for others,
too.

It's hard to just adapt the existing checks in is_ntfs_dotgit(): since
Windows 2000 (i.e., in all Windows versions still supported by Git),
NTFS short names are only generated in the <prefix>~<number> form up to
number 4. After that, a *different* prefix is used, calculated from the
long file name using an undocumented, but stable algorithm.

For example, the short name of .gitmodules would be GITMOD~1, but if it
is taken, and all of ~2, ~3 and ~4 are taken, too, the short name
GI7EBA~1 will be used. From there, collisions are handled by
incrementing the number, shortening the prefix as needed (until ~9999999
is reached, in which case NTFS will not allow the file to be created).

We'd also want to handle .gitignore and .gitattributes, which suffer
from a similar problem, using the fall-back short names GI250A~1 and
GI7D29~1, respectively.

To accommodate for that, we could reimplement the hashing algorithm, but
it is just safer and simpler to provide the known prefixes. This
algorithm has been reverse-engineered and described at
https://usn.pw/blog/gen/2015/06/09/filenames/, which is defunct but
still available via https://web.archive.org/.

These can be recomputed by running the following Perl script:

-- snip --
use warnings;
use strict;

sub compute_short_name_hash ($) {
        my $checksum = 0;
        foreach (split('', $_[0])) {
                $checksum = ($checksum * 0x25 + ord($_)) & 0xffff;
        }

        $checksum = ($checksum * 314159269) & 0xffffffff;
        $checksum = 1 + (~$checksum & 0x7fffffff) if ($checksum & 0x80000000);
        $checksum -= (($checksum * 1152921497) >> 60) * 1000000007;

        return scalar reverse sprintf("%x", $checksum & 0xffff);
}

print compute_short_name_hash($ARGV[0]);
-- snap --

E.g., running that with the argument ".gitignore" will
result in "250a" (which then becomes "gi250a" in the code).

Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
Signed-off-by: Jeff King <peff@peff.net>
5 years agois_hfs_dotgit: match other .git files
Jeff King [Wed, 2 May 2018 19:23:45 +0000 (15:23 -0400)] 
is_hfs_dotgit: match other .git files

Both verify_path() and fsck match ".git", ".GIT", and other
variants specific to HFS+. Let's allow matching other
special files like ".gitmodules", which we'll later use to
enforce extra restrictions via verify_path() and fsck.

Signed-off-by: Jeff King <peff@peff.net>
5 years agois_ntfs_dotgit: use a size_t for traversing string
Jeff King [Sun, 13 May 2018 16:09:42 +0000 (12:09 -0400)] 
is_ntfs_dotgit: use a size_t for traversing string

We walk through the "name" string using an int, which can
wrap to a negative value and cause us to read random memory
before our array (e.g., by creating a tree with a name >2GB,
since "int" is still 32 bits even on most 64-bit platforms).
Worse, this is easy to trigger during the fsck_tree() check,
which is supposed to be protecting us from malicious
garbage.

Note one bit of trickiness in the existing code: we
sometimes assign -1 to "len" at the end of the loop, and
then rely on the "len++" in the for-loop's increment to take
it back to 0. This is still legal with a size_t, since
assigning -1 will turn into SIZE_MAX, which then wraps
around to 0 on increment.

Signed-off-by: Jeff King <peff@peff.net>
5 years agosubmodule-config: verify submodule names as paths
Jeff King [Mon, 30 Apr 2018 07:25:25 +0000 (03:25 -0400)] 
submodule-config: verify submodule names as paths

Submodule "names" come from the untrusted .gitmodules file,
but we blindly append them to $GIT_DIR/modules to create our
on-disk repo paths. This means you can do bad things by
putting "../" into the name (among other things).

Let's sanity-check these names to avoid building a path that
can be exploited. There are two main decisions:

  1. What should the allowed syntax be?

     It's tempting to reuse verify_path(), since submodule
     names typically come from in-repo paths. But there are
     two reasons not to:

       a. It's technically more strict than what we need, as
          we really care only about breaking out of the
          $GIT_DIR/modules/ hierarchy.  E.g., having a
          submodule named "foo/.git" isn't actually
          dangerous, and it's possible that somebody has
          manually given such a funny name.

       b. Since we'll eventually use this checking logic in
          fsck to prevent downstream repositories, it should
          be consistent across platforms. Because
          verify_path() relies on is_dir_sep(), it wouldn't
          block "foo\..\bar" on a non-Windows machine.

  2. Where should we enforce it? These days most of the
     .gitmodules reads go through submodule-config.c, so
     I've put it there in the reading step. That should
     cover all of the C code.

     We also construct the name for "git submodule add"
     inside the git-submodule.sh script. This is probably
     not a big deal for security since the name is coming
     from the user anyway, but it would be polite to remind
     them if the name they pick is invalid (and we need to
     expose the name-checker to the shell anyway for our
     test scripts).

     This patch issues a warning when reading .gitmodules
     and just ignores the related config entry completely.
     This will generally end up producing a sensible error,
     as it works the same as a .gitmodules file which is
     missing a submodule entry (so "submodule update" will
     barf, but "git clone --recurse-submodules" will print
     an error but not abort the clone.

     There is one minor oddity, which is that we print the
     warning once per malformed config key (since that's how
     the config subsystem gives us the entries). So in the
     new test, for example, the user would see three
     warnings. That's OK, since the intent is that this case
     should never come up outside of malicious repositories
     (and then it might even benefit the user to see the
     message multiple times).

Credit for finding this vulnerability and the proof of
concept from which the test script was adapted goes to
Etienne Stalmans.

Signed-off-by: Jeff King <peff@peff.net>
6 years agoGit 2.14.3 v2.14.3
Junio C Hamano [Mon, 23 Oct 2017 05:44:17 +0000 (14:44 +0900)] 
Git 2.14.3

Signed-off-by: Junio C Hamano <gitster@pobox.com>
6 years agoMerge branch 'jk/info-alternates-fix' into maint
Junio C Hamano [Mon, 23 Oct 2017 05:40:00 +0000 (14:40 +0900)] 
Merge branch 'jk/info-alternates-fix' into maint

A regression fix for 2.11 that made the code to read the list of
alternate object stores overrun the end of the string.

* jk/info-alternates-fix:
  read_info_alternates: warn on non-trivial errors
  read_info_alternates: read contents into strbuf

6 years agoMerge branch 'jc/fetch-refspec-doc-update' into maint
Junio C Hamano [Mon, 23 Oct 2017 05:39:08 +0000 (14:39 +0900)] 
Merge branch 'jc/fetch-refspec-doc-update' into maint

"git fetch <there> <src>:<dst>" allows an object name on the <src>
side when the other side accepts such a request since Git v2.5, but
the documentation was left stale.

* jc/fetch-refspec-doc-update:
  fetch doc: src side of refspec could be full SHA-1

6 years agoMerge branch 'jk/write-in-full-fix' into maint
Junio C Hamano [Mon, 23 Oct 2017 05:37:21 +0000 (14:37 +0900)] 
Merge branch 'jk/write-in-full-fix' into maint

Many codepaths did not diagnose write failures correctly when disks
go full, due to their misuse of write_in_full() helper function,
which have been corrected.

* jk/write-in-full-fix:
  read_pack_header: handle signed/unsigned comparison in read result
  config: flip return value of store_write_*()
  notes-merge: use ssize_t for write_in_full() return value
  pkt-line: check write_in_full() errors against "< 0"
  convert less-trivial versions of "write_in_full() != len"
  avoid "write_in_full(fd, buf, len) != len" pattern
  get-tar-commit-id: check write_in_full() return against 0
  config: avoid "write_in_full(fd, buf, len) < len" pattern

6 years agoMerge branch 'rj/no-sign-compare' into maint
Junio C Hamano [Mon, 23 Oct 2017 05:20:18 +0000 (14:20 +0900)] 
Merge branch 'rj/no-sign-compare' into maint

Many codepaths have been updated to squelch -Wsign-compare
warnings.

* rj/no-sign-compare:
  ALLOC_GROW: avoid -Wsign-compare warnings
  cache.h: hex2chr() - avoid -Wsign-compare warnings
  commit-slab.h: avoid -Wsign-compare warnings
  git-compat-util.h: xsize_t() - avoid -Wsign-compare warnings

6 years agoMerge branch 'ma/ts-cleanups' into maint
Junio C Hamano [Mon, 23 Oct 2017 05:19:02 +0000 (14:19 +0900)] 
Merge branch 'ma/ts-cleanups' into maint

Assorted bugfixes and clean-ups.

* ma/ts-cleanups:
  ThreadSanitizer: add suppressions
  strbuf_setlen: don't write to strbuf_slopbuf
  pack-objects: take lock before accessing `remaining`
  convert: always initialize attr_action in convert_attrs

6 years agoMerge branch 'ls/travis-scriptify' into maint
Junio C Hamano [Mon, 23 Oct 2017 05:17:53 +0000 (14:17 +0900)] 
Merge branch 'ls/travis-scriptify' into maint

The scripts to drive TravisCI has been reorganized and then an
optimization to avoid spending cycles on a branch whose tip is
tagged has been implemented.

* ls/travis-scriptify:
  travis-ci: fix "skip_branch_tip_with_tag()" string comparison
  travis: dedent a few scripts that are indented overly deeply
  travis-ci: skip a branch build if equal tag is present
  travis-ci: move Travis CI code into dedicated scripts

6 years agoMerge branch 'er/fast-import-dump-refs-on-checkpoint' into maint
Junio C Hamano [Mon, 23 Oct 2017 05:17:27 +0000 (14:17 +0900)] 
Merge branch 'er/fast-import-dump-refs-on-checkpoint' into maint

The checkpoint command "git fast-import" did not flush updates to
refs and marks unless at least one object was created since the
last checkpoint, which has been corrected, as these things can
happen without any new object getting created.

* er/fast-import-dump-refs-on-checkpoint:
  fast-import: checkpoint: dump branches/tags/marks even if object_count==0

6 years agoMerge branch 'jt/fast-export-copy-modify-fix' into maint
Junio C Hamano [Mon, 23 Oct 2017 05:14:51 +0000 (14:14 +0900)] 
Merge branch 'jt/fast-export-copy-modify-fix' into maint

"git fast-export" with -M/-C option issued "copy" instruction on a
path that is simultaneously modified, which was incorrect.

* jt/fast-export-copy-modify-fix:
  fast-export: do not copy from modified file

6 years agoMerge branch 'nd/worktree-kill-parse-ref' into maint
Junio C Hamano [Mon, 23 Oct 2017 05:14:16 +0000 (14:14 +0900)] 
Merge branch 'nd/worktree-kill-parse-ref' into maint

"git branch -M a b" while on a branch that is completely unrelated
to either branch a or branch b misbehaved when multiple worktree
was in use.  This has been fixed.

* nd/worktree-kill-parse-ref:
  branch: fix branch renaming not updating HEADs correctly

6 years agoPrepare for 2.14.3
Junio C Hamano [Wed, 18 Oct 2017 05:24:09 +0000 (14:24 +0900)] 
Prepare for 2.14.3

Signed-off-by: Junio C Hamano <gitster@pobox.com>
6 years agoMerge branch 'jk/ref-filter-colors-fix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:20:43 +0000 (14:20 +0900)] 
Merge branch 'jk/ref-filter-colors-fix' into maint

This is the "theoretically more correct" approach of simply
stepping back to the state before plumbing commands started paying
attention to "color.ui" configuration variable.

* jk/ref-filter-colors-fix:
  tag: respect color.ui config
  Revert "color: check color.ui in git_default_config()"
  Revert "t6006: drop "always" color config tests"
  Revert "color: make "always" the same as "auto" in config"
  color: make "always" the same as "auto" in config
  provide --color option for all ref-filter users
  t3205: use --color instead of color.branch=always
  t3203: drop "always" color test
  t6006: drop "always" color config tests
  t7502: use diff.noprefix for --verbose test
  t7508: use test_terminal for color output
  t3701: use test-terminal to collect color output
  t4015: prefer --color to -c color.diff=always
  test-terminal: set TERM=vt100

6 years agoMerge branch 'jc/doc-checkout' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:14 +0000 (14:19 +0900)] 
Merge branch 'jc/doc-checkout' into maint

Doc update.

* jc/doc-checkout:
  checkout doc: clarify command line args for "checkout paths" mode

6 years agoMerge branch 'tb/complete-describe' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:14 +0000 (14:19 +0900)] 
Merge branch 'tb/complete-describe' into maint

Docfix.

* tb/complete-describe:
  completion: add --broken and --dirty to describe

6 years agoMerge branch 'rs/rs-mailmap' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:14 +0000 (14:19 +0900)] 
Merge branch 'rs/rs-mailmap' into maint

* rs/rs-mailmap:
  .mailmap: normalize name for René Scharfe

6 years agoMerge branch 'rs/fsck-null-return-from-lookup' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:14 +0000 (14:19 +0900)] 
Merge branch 'rs/fsck-null-return-from-lookup' into maint

Improve behaviour of "git fsck" upon finding a missing object.

* rs/fsck-null-return-from-lookup:
  fsck: handle NULL return of lookup_blob() and lookup_tree()

6 years agoMerge branch 'jk/sha1-loose-object-info-fix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:14 +0000 (14:19 +0900)] 
Merge branch 'jk/sha1-loose-object-info-fix' into maint

Leakfix and futureproofing.

* jk/sha1-loose-object-info-fix:
  sha1_loose_object_info: handle errors from unpack_sha1_rest

6 years agoMerge branch 'sb/branch-avoid-repeated-strbuf-release' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:14 +0000 (14:19 +0900)] 
Merge branch 'sb/branch-avoid-repeated-strbuf-release' into maint

* sb/branch-avoid-repeated-strbuf-release:
  branch: reset instead of release a strbuf

6 years agoMerge branch 'rs/qsort-s' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:14 +0000 (14:19 +0900)] 
Merge branch 'rs/qsort-s' into maint

* rs/qsort-s:
  test-stringlist: avoid buffer underrun when sorting nothing

6 years agoMerge branch 'jn/strbuf-doc-re-reuse' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:13 +0000 (14:19 +0900)] 
Merge branch 'jn/strbuf-doc-re-reuse' into maint

* jn/strbuf-doc-re-reuse:
  strbuf doc: reuse after strbuf_release is fine

6 years agoMerge branch 'rs/run-command-use-alloc-array' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:13 +0000 (14:19 +0900)] 
Merge branch 'rs/run-command-use-alloc-array' into maint

Code clean-up.

* rs/run-command-use-alloc-array:
  run-command: use ALLOC_ARRAY

6 years agoMerge branch 'rs/tag-null-pointer-arith-fix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:12 +0000 (14:19 +0900)] 
Merge branch 'rs/tag-null-pointer-arith-fix' into maint

Code clean-up.

* rs/tag-null-pointer-arith-fix:
  tag: avoid NULL pointer arithmetic

6 years agoMerge branch 'rs/cocci-de-paren-call-params' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:12 +0000 (14:19 +0900)] 
Merge branch 'rs/cocci-de-paren-call-params' into maint

Code clean-up.

* rs/cocci-de-paren-call-params:
  coccinelle: remove parentheses that become unnecessary

6 years agoMerge branch 'ad/doc-markup-fix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:12 +0000 (14:19 +0900)] 
Merge branch 'ad/doc-markup-fix' into maint

Docfix.

* ad/doc-markup-fix:
  doc: correct command formatting

6 years agoMerge branch 'mr/doc-negative-pathspec' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:12 +0000 (14:19 +0900)] 
Merge branch 'mr/doc-negative-pathspec' into maint

Doc updates.

* mr/doc-negative-pathspec:
  docs: improve discoverability of exclude pathspec

6 years agoMerge branch 'jk/validate-headref-fix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:12 +0000 (14:19 +0900)] 
Merge branch 'jk/validate-headref-fix' into maint

Code clean-up.

* jk/validate-headref-fix:
  validate_headref: use get_oid_hex for detached HEADs
  validate_headref: use skip_prefix for symref parsing
  validate_headref: NUL-terminate HEAD buffer

6 years agoMerge branch 'ks/doc-use-camelcase-for-config-name' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:12 +0000 (14:19 +0900)] 
Merge branch 'ks/doc-use-camelcase-for-config-name' into maint

Doc update.

* ks/doc-use-camelcase-for-config-name:
  doc: camelCase the config variables to improve readability

6 years agoMerge branch 'jk/doc-read-tree-table-asciidoctor-fix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:11 +0000 (14:19 +0900)] 
Merge branch 'jk/doc-read-tree-table-asciidoctor-fix' into maint

A docfix.

* jk/doc-read-tree-table-asciidoctor-fix:
  doc: put literal block delimiter around table

6 years agoMerge branch 'hn/typofix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:11 +0000 (14:19 +0900)] 
Merge branch 'hn/typofix' into maint

* hn/typofix:
  submodule.h: typofix

6 years agoMerge branch 'ks/test-readme-phrasofix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:10 +0000 (14:19 +0900)] 
Merge branch 'ks/test-readme-phrasofix' into maint

Doc updates.

* ks/test-readme-phrasofix:
  t/README: fix typo and grammatically improve a sentence

6 years agoMerge branch 'ez/doc-duplicated-words-fix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:10 +0000 (14:19 +0900)] 
Merge branch 'ez/doc-duplicated-words-fix' into maint

Typofix.

* ez/doc-duplicated-words-fix:
  doc: fix minor typos (extra/duplicated words)

6 years agoMerge branch 'kd/doc-for-each-ref' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:10 +0000 (14:19 +0900)] 
Merge branch 'kd/doc-for-each-ref' into maint

Doc update.

* kd/doc-for-each-ref:
  doc/for-each-ref: explicitly specify option names
  doc/for-each-ref: consistently use '=' to between argument names and values

6 years agoMerge branch 'cc/subprocess-handshake-missing-capabilities' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:10 +0000 (14:19 +0900)] 
Merge branch 'cc/subprocess-handshake-missing-capabilities' into maint

Finishing touches to a topic already in 'master'.

* cc/subprocess-handshake-missing-capabilities:
  subprocess: loudly die when subprocess asks for an unsupported capability

6 years agoMerge branch 'jk/system-path-cleanup' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:10 +0000 (14:19 +0900)] 
Merge branch 'jk/system-path-cleanup' into maint

Code clean-up.

* jk/system-path-cleanup:
  git_extract_argv0_path: do nothing without RUNTIME_PREFIX
  system_path: move RUNTIME_PREFIX to a sub-function

6 years agoMerge branch 'bb/doc-eol-dirty' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:09 +0000 (14:19 +0900)] 
Merge branch 'bb/doc-eol-dirty' into maint

Doc update.

* bb/doc-eol-dirty:
  Documentation: mention that `eol` can change the dirty status of paths

6 years agoMerge branch 'mg/timestamp-t-fix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:09 +0000 (14:19 +0900)] 
Merge branch 'mg/timestamp-t-fix' into maint

A mismerge fix.

* mg/timestamp-t-fix:
  name-rev: change ULONG_MAX to TIME_MAX

6 years agoMerge branch 'ma/pkt-line-leakfix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:08 +0000 (14:19 +0900)] 
Merge branch 'ma/pkt-line-leakfix' into maint

A leakfix.

* ma/pkt-line-leakfix:
  pkt-line: re-'static'-ify buffer in packet_write_fmt_1()

6 years agoMerge branch 'jk/config-lockfile-leak-fix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:07 +0000 (14:19 +0900)] 
Merge branch 'jk/config-lockfile-leak-fix' into maint

A leakfix.

* jk/config-lockfile-leak-fix:
  config: use a static lock_file struct

6 years agoMerge branch 'dw/diff-highlight-makefile-fix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:07 +0000 (14:19 +0900)] 
Merge branch 'dw/diff-highlight-makefile-fix' into maint

Build clean-up.

* dw/diff-highlight-makefile-fix:
  diff-highlight: add clean target to Makefile

6 years agoMerge branch 'jk/drop-sha1-entry-pos' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:06 +0000 (14:19 +0900)] 
Merge branch 'jk/drop-sha1-entry-pos' into maint

Code clean-up.

* jk/drop-sha1-entry-pos:
  sha1-lookup: remove sha1_entry_pos() from header file
  sha1_file: drop experimental GIT_USE_LOOKUP search

6 years agoMerge branch 'tb/ref-filter-empty-modifier' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:06 +0000 (14:19 +0900)] 
Merge branch 'tb/ref-filter-empty-modifier' into maint

In the "--format=..." option of the "git for-each-ref" command (and
its friends, i.e. the listing mode of "git branch/tag"), "%(atom:)"
(e.g. "%(refname:)", "%(body:)" used to error out.  Instead, treat
them as if the colon and an empty string that follows it were not
there.

* tb/ref-filter-empty-modifier:
  ref-filter.c: pass empty-string as NULL to atom parsers

6 years agoMerge branch 'rb/compat-poll-fix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:05 +0000 (14:19 +0900)] 
Merge branch 'rb/compat-poll-fix' into maint

Backports a moral equivalent of 2015 fix to the poll emulation from
the upstream gnulib to fix occasional breakages on HPE NonStop.

* rb/compat-poll-fix:
  poll.c: always set revents, even if to zero

6 years agoMerge branch 'tg/memfixes' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:04 +0000 (14:19 +0900)] 
Merge branch 'tg/memfixes' into maint

Fixes for a handful memory access issues identified by valgrind.

* tg/memfixes:
  sub-process: use child_process.args instead of child_process.argv
  http-push: fix construction of hex value from path
  path.c: fix uninitialized memory access

6 years agoMerge branch 'ar/request-pull-phrasofix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:04 +0000 (14:19 +0900)] 
Merge branch 'ar/request-pull-phrasofix' into maint

Spell the name of our system as "Git" in the output from
request-pull script.

* ar/request-pull-phrasofix:
  request-pull: capitalise "Git" to make it a proper noun

6 years agoMerge branch 'jc/merge-x-theirs-docfix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:03 +0000 (14:19 +0900)] 
Merge branch 'jc/merge-x-theirs-docfix' into maint

The documentation for '-X<option>' for merges was misleadingly
written to suggest that "-s theirs" exists, which is not the case.

* jc/merge-x-theirs-docfix:
  merge-strategies: avoid implying that "-s theirs" exists

6 years agoMerge branch 'rs/mailinfo-qp-decode-fix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:03 +0000 (14:19 +0900)] 
Merge branch 'rs/mailinfo-qp-decode-fix' into maint

"git mailinfo" was loose in decoding quoted printable and produced
garbage when the two letters after the equal sign are not
hexadecimal.  This has been fixed.

* rs/mailinfo-qp-decode-fix:
  mailinfo: don't decode invalid =XY quoted-printable sequences

6 years agoMerge branch 'ik/userdiff-html-h-element-fix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:02 +0000 (14:19 +0900)] 
Merge branch 'ik/userdiff-html-h-element-fix' into maint

The built-in pattern to detect the "function header" for HTML did
not match <H1>..<H6> elements without any attributes, which has
been fixed.

* ik/userdiff-html-h-element-fix:
  userdiff: fix HTML hunk header regexp

6 years agoMerge branch 'jk/diff-blob' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:01 +0000 (14:19 +0900)] 
Merge branch 'jk/diff-blob' into maint

"git cat-file --textconv" started segfaulting recently, which
has been corrected.

* jk/diff-blob:
  cat-file: handle NULL object_context.path

6 years agoMerge branch 'jk/describe-omit-some-refs' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:01 +0000 (14:19 +0900)] 
Merge branch 'jk/describe-omit-some-refs' into maint

"git describe --match" learned to take multiple patterns in v2.13
series, but the feature ignored the patterns after the first one
and did not work at all.  This has been fixed.

* jk/describe-omit-some-refs:
  describe: fix matching to actually match all patterns

6 years agoMerge branch 'mh/for-each-string-list-item-empty-fix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:19:00 +0000 (14:19 +0900)] 
Merge branch 'mh/for-each-string-list-item-empty-fix' into maint

Code cmp.std.c nitpick.

* mh/for-each-string-list-item-empty-fix:
  for_each_string_list_item: avoid undefined behavior for empty list

6 years agoMerge branch 'tb/test-lint-echo-e' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:18:59 +0000 (14:18 +0900)] 
Merge branch 'tb/test-lint-echo-e' into maint

The test linter has been taught that we do not like "echo -e".

* tb/test-lint-echo-e:
  test-lint: echo -e (or -E) is not portable

6 years agoMerge branch 'aw/gc-lockfile-fscanf-fix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:18:59 +0000 (14:18 +0900)] 
Merge branch 'aw/gc-lockfile-fscanf-fix' into maint

"git gc" tries to avoid running two instances at the same time by
reading and writing pid/host from and to a lock file; it used to
use an incorrect fscanf() format when reading, which has been
corrected.

* aw/gc-lockfile-fscanf-fix:
  gc: call fscanf() with %<len>s, not %<len>c, when reading hostname

6 years agoMerge branch 'tg/refs-allowed-flags' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:18:58 +0000 (14:18 +0900)] 
Merge branch 'tg/refs-allowed-flags' into maint

API error-proofing which happens to also squelch warnings from GCC.

* tg/refs-allowed-flags:
  refs: strip out not allowed flags from ref_transaction_update

6 years agoMerge branch 'rs/archive-excluded-directory' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:18:58 +0000 (14:18 +0900)] 
Merge branch 'rs/archive-excluded-directory' into maint

"git archive", especially when used with pathspec, stored an empty
directory in its output, even though Git itself never does so.
This has been fixed.

* rs/archive-excluded-directory:
  archive: don't add empty directories to archives

6 years agoMerge branch 'rk/commit-tree-make-F-verbatim' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:18:58 +0000 (14:18 +0900)] 
Merge branch 'rk/commit-tree-make-F-verbatim' into maint

Unlike "git commit-tree < file", "git commit-tree -F file" did not
pass the contents of the file verbatim and instead completed an
incomplete line at the end, if exists.  The latter has been updated
to match the behaviour of the former.

* rk/commit-tree-make-F-verbatim:
  commit-tree: do not complete line in -F input

6 years agoMerge branch 'mh/packed-ref-store-prep' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:18:58 +0000 (14:18 +0900)] 
Merge branch 'mh/packed-ref-store-prep' into maint

Fix regression to "gitk --bisect" by a recent update.

* mh/packed-ref-store-prep:
  rev-parse: don't trim bisect refnames

6 years agoMerge branch 'mm/send-email-cc-cruft' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:18:58 +0000 (14:18 +0900)] 
Merge branch 'mm/send-email-cc-cruft' into maint

In addition to "cc: <a@dd.re.ss> # cruft", "cc: a@dd.re.ss # cruft"
was taught to "git send-email" as a valid way to tell it that it
needs to also send a carbon copy to <a@dd.re.ss> in the trailer
section.

* mm/send-email-cc-cruft:
  send-email: don't use Mail::Address, even if available
  send-email: fix garbage removal after address

6 years agoMerge branch 'rs/strbuf-getwholeline-fix' into maint
Junio C Hamano [Wed, 18 Oct 2017 05:18:57 +0000 (14:18 +0900)] 
Merge branch 'rs/strbuf-getwholeline-fix' into maint

A helper function to read a single whole line into strbuf
mistakenly triggered OOM error at EOF under certain conditions,
which has been fixed.

* rs/strbuf-getwholeline-fix:
  strbuf: clear errno before calling getdelim(3)

6 years agofetch doc: src side of refspec could be full SHA-1
Junio C Hamano [Tue, 17 Oct 2017 02:31:06 +0000 (11:31 +0900)] 
fetch doc: src side of refspec could be full SHA-1

Since a9d34933 ("Merge branch 'fm/fetch-raw-sha1'", 2015-06-01) we
allow to fetch by an object name when the other side accepts such a
request, but we never updated the documentation to match.

Signed-off-by: Junio C Hamano <gitster@pobox.com>
Reviewed-by: Jonathan Nieder <jrnieder@gmail.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
6 years agotag: respect color.ui config
Jeff King [Fri, 13 Oct 2017 17:26:02 +0000 (13:26 -0400)] 
tag: respect color.ui config

Since 11b087adfd (ref-filter: consult want_color() before
emitting colors, 2017-07-13), we expect that setting
"color.ui" to "always" will enable color tag formats even
without a tty.  As that commit was built on top of
136c8c8b8f (color: check color.ui in git_default_config(),
2017-07-13) from the same series, we didn't need to touch
tag's config parsing at all.

However, since we reverted 136c8c8b8f, we now need to
explicitly call git_color_default_config() to make this
work.

Let's do so, and also restore the test dropped in 0c88bf5050
(provide --color option for all ref-filter users,
2017-10-03). That commit swapped out our "color.ui=always"
test for "--color" in preparation for "always" going away.
But since it is here to stay, we should test both cases.

Note that for-each-ref also lost its color.ui support as
part of reverting 136c8c8b8f. But as a plumbing command, it
should _not_ respect the color.ui config. Since it also
gained a --color option in 0c88bf5050, that's the correct
way to ask it for color. We'll continue to test that, and
confirm that "color.ui" is not respected.

Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
6 years agoRevert "color: check color.ui in git_default_config()"
Jeff King [Fri, 13 Oct 2017 17:24:31 +0000 (13:24 -0400)] 
Revert "color: check color.ui in git_default_config()"

This reverts commit 136c8c8b8fa39f1315713248473dececf20f8fe7.

That commit was trying to address a bug caused by 4c7f1819b3
(make color.ui default to 'auto', 2013-06-10), in which
plumbing like diff-tree defaulted to "auto" color, but did
not respect a "color.ui" directive to disable it.

But it also meant that we started respecting "color.ui" set
to "always". This was a known problem, but 4c7f1819b3 argued
that nobody ought to be doing that. However, that turned out
to be wrong, and we got a number of bug reports related to
"add -p" regressing in v2.14.2.

Let's revert 136c8c8b8, fixing the regression to "add -p".
This leaves the problem from 4c7f1819b3 unfixed, but:

  1. It's a pretty obscure problem in the first place. I
     only noticed it while working on the color code, and we
     haven't got a single bug report or complaint about it.

  2. We can make a more moderate fix on top by respecting
     "never" but not "always" for plumbing commands. This
     is just the minimal fix to go back to the working state
     we had before v2.14.2.

Note that this isn't a pure revert. We now have a test in
t3701 which shows off the "add -p" regression. This can be
flipped to success.

Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
6 years agoRevert "t6006: drop "always" color config tests"
Jeff King [Fri, 13 Oct 2017 17:23:41 +0000 (13:23 -0400)] 
Revert "t6006: drop "always" color config tests"

This reverts commit c5bdfe677cfab5b2e87771c35565d44d3198efda.

That commit was done primarily to prepare for the weakening
of "always" in 6be4595edb (color: make "always" the same as
"auto" in config, 2017-10-03). But since we've now reverted
6be4595edb, there's no need for us to remove "-c
color.ui=always" from the tests. And in fact it's a good
idea to restore these tests, to make sure that "always"
continues to work.

Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
6 years agoRevert "color: make "always" the same as "auto" in config"
Jeff King [Fri, 13 Oct 2017 17:23:24 +0000 (13:23 -0400)] 
Revert "color: make "always" the same as "auto" in config"

This reverts commit 6be4595edb8e5b616c6e8b9fbc78b0f831fa2a87.

That commit weakened the "always" setting of color config so
that it acted as "auto". This was meant to solve regressions
in v2.14.2 in which setting "color.ui=always" in the on-disk
config broke scripts like add--interactive, because the
plumbing diff commands began to generate color output.

This was due to 136c8c8b8f (color: check color.ui in
git_default_config(), 2017-07-13), which was in turn trying
to fix issues caused by 4c7f1819b3 (make color.ui default to
'auto', 2013-06-10). But in weakening "always", we created
even more problems, as people expect to be able to use "git
-c color.ui=always" to force color (especially because some
commands don't have their own --color flag). We can fix that
by special-casing the command-line "-c", but now things are
getting pretty confusing.

Instead of piling hacks upon hacks, let's start peeling off
the hacks. The first step is dropping the weakening of
"always", which this revert does.

Note that we could actually revert the whole series merged
in by da15b78e52642bd45fd5513ab0000fdf2e58a6f4. Most of that
series consists of preparations to the tests to handle the
weakening of "-c color.ui=always". But it's worth keeping
for a few reasons:

  - there are some other preparatory cleanups, like
    e433749d86 (test-terminal: set TERM=vt100, 2017-10-03)

  - it adds "--color" options more consistently in
    0c88bf5050 (provide --color option for all ref-filter
    users, 2017-10-03)

  - some of the cases dropping "-c" end up being more robust
    and realistic tests, as in 01c94e9001 (t7508: use
    test_terminal for color output, 2017-10-03)

  - the preferred tool for overriding config is "--color",
    and we should be modeling that consistently

We can individually revert the few commits necessary to
restore some useful tests (which will be done on top of this
patch).

Note that this isn't a pure revert; we'll keep the test
added in t3701, but mark it as failure for now.

Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
6 years agoMerge branch 'jk/ui-color-always-to-auto-maint' (early part) into jk/ref-filter-color...
Junio C Hamano [Tue, 17 Oct 2017 06:08:31 +0000 (15:08 +0900)] 
Merge branch 'jk/ui-color-always-to-auto-maint' (early part) into jk/ref-filter-colors-fix-maint

* 'jk/ui-color-always-to-auto-maint' (early part):
  color: make "always" the same as "auto" in config
  provide --color option for all ref-filter users
  t3205: use --color instead of color.branch=always
  t3203: drop "always" color test
  t6006: drop "always" color config tests
  t7502: use diff.noprefix for --verbose test
  t7508: use test_terminal for color output
  t3701: use test-terminal to collect color output
  t4015: prefer --color to -c color.diff=always
  test-terminal: set TERM=vt100

6 years agocheckout doc: clarify command line args for "checkout paths" mode
Junio C Hamano [Wed, 11 Oct 2017 02:21:03 +0000 (11:21 +0900)] 
checkout doc: clarify command line args for "checkout paths" mode

There are "git checkout [-p][<tree-ish>][--][<paths>...]" in the
SYNOPSIS section, and "git checkout [-p][<tree-ish>][--]<paths>..."
as the header for the section that explains the "check out paths
from index/tree-ish" mode.  It is unclear if we require at least one
path, or it is entirely optional.

Actually, both are wrong.  Without the "-p(atch)" option, you must
have <pathspec> (otherwise, with a commit that is a <tree-ish>, you
would be checking out that commit to build a new history on top of
it).  With it, it is already clear that you are checking out paths,
it is optional.  In other words, you cannot omit both.

The source of the confusion is that -p(atch) is described as if it
is just another "optional" part and its description is lumped
together with the non patch mode, even though the actual end user
experience is vastly different.

Let's split the entry into two, and describe the regular mode and
the patch mode separately.  This allows us to make it clear that the
regular mode MUST be given at least one pathspec, that the patch
mode can be invoked with either '-p' or '--patch' but one of these
must be given, and that the pathspec is entirely optional in the
patch mode.

Also, revamp the explanation of "checkout paths" by removing
extraneous description at the beginning, that says "checking out
paths is not checking out a branch".  Explaining what it is for and
when the user wants to use it upfront is the most direct way to help
the readers.

Noticed-by: Robert P J Day
Helped-by: Jonathan Nieder <jrnieder@gmail.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
6 years agocompletion: add --broken and --dirty to describe
Thomas Braun [Fri, 6 Oct 2017 18:02:47 +0000 (20:02 +0200)] 
completion: add --broken and --dirty to describe

When the flags for broken and dirty were implemented in
b0176ce6b5 (builtin/describe: introduce --broken flag, 2017-03-21)
and 9f67d2e827 (Teach "git describe" --dirty option, 2009-10-21)
the completion was not updated, although these flags are useful
completions. Add them.

Signed-off-by: Thomas Braun <thomas.braun@virtuell-zuhause.de>
Helped-by: Stefan Beller <sbeller@google.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
6 years agosha1_loose_object_info: handle errors from unpack_sha1_rest
Jeff King [Thu, 5 Oct 2017 05:59:52 +0000 (01:59 -0400)] 
sha1_loose_object_info: handle errors from unpack_sha1_rest

When a caller of sha1_object_info_extended() sets the
"contentp" field in object_info, we call unpack_sha1_rest()
but do not check whether it signaled an error.

This causes two problems:

  1. We pass back NULL to the caller via the contentp field,
     but the function returns "0" for success. A caller
     might reasonably expect after a successful return that
     it can access contentp without a NULL check and
     segfault.

     As it happens, this is impossible to trigger in the
     current code. There is exactly one caller which uses
     contentp, read_object(). And the only thing it does
     after a successful call is to return the content
     pointer to its caller, using NULL as a sentinel for
     errors. So in effect it converts the success code from
     sha1_object_info_extended() back into an error!

     But this is still worth addressing avoid problems for
     future users of "contentp".

  2. Callers of unpack_sha1_rest() are expected to close the
     zlib stream themselves on error. Which means that we're
     leaking the stream.

The problem in (1) comes from from c84a1f3ed4 (sha1_file:
refactor read_object, 2017-06-21), which added the contentp
field.  Before that, we called unpack_sha1_rest() via
unpack_sha1_file(), which directly used the NULL to signal
an error.

But note that the leak in (2) is actually older than that.
The original unpack_sha1_file() directly returned the result
of unpack_sha1_rest() to its caller, when it should have
been closing the zlib stream itself on error.

Signed-off-by: Jeff King <peff@peff.net>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
6 years ago.mailmap: normalize name for René Scharfe
René Scharfe [Thu, 5 Oct 2017 19:41:31 +0000 (21:41 +0200)] 
.mailmap: normalize name for René Scharfe

Reported-by: Johannes Schindelin <johannes.schindelin@gmx.de>
Reported-by: Stefan Beller <sbeller@google.com>
Signed-off-by: Rene Scharfe <l.s.r@web.de>
Reviewed-by: Jonathan Nieder <jrnieder@gmail.com>
Signed-off-by: Junio C Hamano <gitster@pobox.com>