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

Re: Git ransom campaign incident report - May 2019

From
Jeff King <peff@peff.net>
Date
May 17, 2019, 22:20 UTC
Message-ID
<20190517222031.GA17966@sigill.intra.peff.net>
In-Reply-To
<nycvar.QRO.7.76.6.1905172121130.46@tvgsbejvaqbjf.bet>
On Fri, May 17, 2019 at 09:39:55PM +0200, Johannes Schindelin wrote:
Show 11 quoted lines
> > Of course I suspect there are many cases where people _do_ need to store
> > the password in plaintext, because an automated system needs to fetch
> > with it. They can use the plaintext git-credential-store, but it's
> > slightly more hassle. And it doesn't really _solve_ the problem (though
> > perhaps it would be harder to accidentally expose it with your web
> > server!).
> 
> One thing that we actually *could* do here is to anonymize the URLs stored
> under remote.origin.url when cloning. In no other circumstance that I can
> think of do we take an URL from some command-line parameter that is not
> *explicitly* intended for storing in the config.

Good point. That's a plausible way that these end up in config even when they're not needed and it wasn't intended by the user.

Show 5 quoted lines
> Combined with that warning "You cloned via a URL that contains
> credentials; for security reasons, the credentials were scrubbed before
> storing this in your Git config. Please consider using a credential
> manager instead of storing secrets in your Git config." this should
> provide a reasonable compromise.

Yeah, we'd definitely want to warn the user. Some people might find it irritating because a follow-up fetch would require an interactive password. We might need to make sure the escape hatch is pretty turnkey. The simplest thing is just a "--save-password" option to override this, but it would be nice if there's an out-of-the-box solution with a credential helper.

We can use credential-store as a general solution. That's still sticking the password in the filesystem in plaintext, but the file is 0700 by default, and it's not in the repo directory).

Unfortunately converting:
  git clone https://user@pass:example.com/repo.git

into a safer use of credential-store is a little tricky, because seeding the store is generally only done interactively. What if we did this:

  1. Do not ever write the password part of a URL into config.
  2. When we extract the user/pass out of a URL, put them into the
     credential struct, so that when we successfully authenticate, we
     trigger storage. This _might_ actually happen already, but we
     should definitely confirm it.
  3. If the user has no credential helper defined, then do one of:
     a. Warn them that the credential was not recorded, but that they
        can use "git clone -c credential.helper=store" as a fallback
	(but probably worded in a way to recommend using something
	stronger if possible).
	This is slightly annoying because following the advice requires
	re-cloning. Fixing it up from there is more like:
	  git config credential.helper store
	  git fetch
	  [interactively input password]
     b. Just use credential-store. Optionally notify them of what
         happened (and that they might want to choose a better helper).

I hate the magical-ness of 3b, because credential-store really _isn't_ the best choice. It's just better than the current behavior. At the same time, by doing it automatically, the existing flow they were using just works, and is moderately better.

> Judging from looking at my own automated jobs, it does not appear that you
> would *ever* need to store such credentials in the Git config, anyway. If
> you need to, say, push to a repository, you can always store the full URL
> (or the credentials) in a secret variable.

Yes, that's definitely the way you _should_ do it. I think the problem is that handling secret storage is tricky and system-specific, and the people who are affected here are ones who just didn't think about it. If we can make even a moderate improvement without the user having to do anything differently, it's worth considering.

-Peff
Previous: Johannes SchindelinNext: Martin Langhoff
Message 5 of 23 in “Git ransom campaign incident report - May 2019”
  1. Martin LanghoffMay 15, 2019
  2. Ævar Arnfjörð BjarmasonMay 15, 2019
  3. Jeff KingMay 16, 2019
  4. Johannes SchindelinMay 17, 2019
  5. Jeff KingMay 17, 2019
  6. Martin LanghoffMay 17, 2019
  7. Jeff KingMay 19, 2019
  8. 1/3 transport_anonymize_url(): support retaining usernameJeff King, May 19, 2019
  9. Eric SunshineMay 19, 2019
  10. René ScharfeMay 20, 2019
  11. Johannes SchindelinMay 20, 2019
  12. Johannes SchindelinMay 20, 2019
  13. 2/3 clone: avoid storing URL passwords in configJeff King, May 19, 2019
  14. 3/3 clone: auto-enable git-credential-store when necessaryJeff King, May 19, 2019
  15. Eric SunshineMay 20, 2019
  16. Jeff KingMay 20, 2019
  17. Johannes SchindelinMay 20, 2019
  18. Ævar Arnfjörð BjarmasonMay 20, 2019
  19. Jeff KingMay 20, 2019
  20. Ævar Arnfjörð BjarmasonMay 20, 2019
  21. Jeff KingMay 20, 2019
  22. Ævar Arnfjörð BjarmasonMay 20, 2019
  23. Johannes SchindelinMay 20, 2019

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

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