Skip to content

SmartCard/PIV authentication support #2269

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
danizen opened this issue Jul 22, 2019 · 17 comments
Closed

SmartCard/PIV authentication support #2269

danizen opened this issue Jul 22, 2019 · 17 comments

Comments

@danizen
Copy link

danizen commented Jul 22, 2019

Feature Request

Please add support for SmartCard/PIV login using Windows certificate and cryptography APIs. The benefit is that federal agencies can login to Github securely, and to SSH bastions that require this capability.

Motivation

My federal institute has an ATO for use of AWS that we must only use our SmartCard/PIV login to access the Cloud, and many federal developers have only Windows, rather than a PowerBook. I'm looking to enhance their login process so that they can use ssh from a windows or bash command-line.

My federal institute is happy to use this with VanDyke SecureCRT on Windows and MacOS, but this displeases me as a developer/architect, because it always opens a window. I wish this feature were part of "Git for Windows".

Previous Issues

I did searches on SmartCard and PIV, and then looked through the related issues displayed when entering the title. Nothing seemed right.

Setup

  • Which version of Git for Windows are you using?

2.2.0.windows.1

  • Is it 32-bit or 64-bit?

64 bit

$ git --version --build-options
git version 2.22.0.windows.1
cpu: x86_64
built from commit: d003d728ffa6c0006da875ec6318d3f6b28a4ddb
sizeof-long: 4
sizeof-size_t: 8
  • Which version of Windows are you running? Vista, 7, 8, 10? Is it 32-bit or 64-bit?
$ cmd.exe /c ver

Microsoft Windows [Version 10.0.17134.885]
  • What options did you set as part of the installation? Or did you choose the
    defaults?
# One of the following:
$ cat $HOME/Tools/Git/etc/install-options.txt
Editor Option: SublimeText
Custom Editor Path:
Path Option: Cmd
SSH Option: OpenSSH
CURL Option: OpenSSL
CRLF Option: LFOnly
Bash Terminal Option: ConHost
Performance Tweaks FSCache: Enabled
Use Credential Manager: Enabled
Enable Symlinks: Disabled
Enable Builtin Interactive Add: Disabled

*NOTE: * This implies it may work if I install OpenSC, and I will try it. However, half the advantages of PIV integration will be using the cached credentials that the Windows service already has.

Details

This is a feature request, rather than a big report, and so I will dispense with the questions about reproducing the issue to the extent possible.

There are workarounds for OpenSSH on MacOS that involve the use of OpenSC. These may or may not work with git for windows. If they do work, that is a work-around, but it will be most ideal to use the Windows Cryptography API or the New cryptography API to obtain the private key, because that will allow a password already authenticated recently to work out of the box.

I cannot advise on how to setup Windows 10 to require smart card authentication - I think NIST and SmartCard vendors provide a lot of that intelligence. I can provide wisdom on getting the public key from Active Directory or related tools.

Software that does it

  • VanDyke SecureCRT supports SmartCard/PIV login, as does Chrome.
  • Firefox supports PIV login only through OpenSC.
  • Using VanDyke SecureCRT, I export my authentication certificate as an SSH public key,
    and register it with Github.com under SSH keys.

PublicKey via Python from Active Directory

I can also export my public key from Active Directory. To maximize the likelihood this feature can be added, I provide some python for this:

import ldap3 as ldap
from ldap3.core.exceptions import LDAPExceptionError
from cryptography.hazmat.primitives.serialization import Encoding, PublicFormat
from OpenSSL.crypto import load_certificate, FILETYPE_ASN1

## The following are assumed to be provided
# hostname
# bind_dn - equivalent of username
# password
# base-dn - where to start search from
# username - the user whose public key you wish to search on

server = ldap.Server(hostname, use_ssl=True)
connection = ldap.Connection(server, bind_dn, password, auto_bind=ldap.AUTO_BIND_TLS_BEFORE_BIND, read_only=True)

query = '(&(objectclass=user)(sAMAccountName=%s))' % username
connection.search(base_dn, query, attributes=['sAMAccountName', 'userCertificate'])

# now we assume it worked and we got a single response
certificate_bytes = connection.entries[0].userCertificate.values[0]
x509 = load_certificate(FILETYPE_ASN1, certificate_bytes)
public_key = x509.get_pubkey().to_cryptography_key()
public_key = public_key.public_bytes(Encoding.OpenSSH, PublicFormat.OpenSSH).decode('utf-8')
suffix = username + '@some-domain.com'

# now finally, the SSH public key
print(public_key+' '+suffix)
@danizen
Copy link
Author

danizen commented Jul 22, 2019

One place where to start:

https://github.com/OpenSC/OpenSC/wiki/Windows-Quick-Start

@danizen
Copy link
Author

danizen commented Jul 22, 2019

Found it:

https://github.com/OpenSC/OpenSC/wiki/Example-to-use-OpenSC-with-Microsoft-CNG-and-CryptoAPI

After I get this to work with my python tool, I may provide a pull request.

@dscho
Copy link
Member

dscho commented Jul 23, 2019

I would have expected smartcards to be supported via Secure Channel right out of the box. So when your Git for Windows installer asks you to choose the HTTPS backend, and you choose Secure Channel, I could imagine that it already works.

Not for OpenSSH, though, that would require a ton more work.

@danizen
Copy link
Author

danizen commented Jul 25, 2019

So when your Git for Windows installer asks you to choose ...

I will certainly try that, as I'm trying to craft a solution for multiple developers, but I think my desire to use PIV and also $HOME/.ssh/id_rsa.pub when appropriate would be normal for many users.

Since opening this, I did try a variant of https://github.com/OpenSC/OpenSC/wiki/OpenSSH-and-smart-cards-PKCS%2311, where I installed OpenSC on my Windows server, identified the PKCS#11 DLL they describe, and then gave it as a an option.

With C:\Windows\System32\OpenSSL\ssh.exe, I was just informed that PKCS#11 was not supported by their ssh, and it continued to try other certificates and password, which would not work. With C:\Users\davisda4\Tools\Git\usr\bin\ssh.exe, it simply was not able to load the OpenSC DLL properly OpenSC was not a mingw64 build. Custom builds I can do ... but I'm better on Linux than Windows.

@dscho
Copy link
Member

dscho commented Jul 25, 2019

With C:\Users\davisda4\Tools\Git\usr\bin\ssh.exe, it simply was not able to load the OpenSC DLL properly OpenSC was not a mingw64 build.

That should not matter. MINGW64 builds can call LoadLibraryW() with any DLL quite easily.

But you tickled my curiosity, being so short on details as to how this fails. I would be eager to learn the full details, if only because I have no experience with PKCS#11 whatsoever. Remember: there is usually a million ways code can fail to do what you want, and only one way it can succeed to do so. Therefore, when saying "it does not work", that single bit of information belies the entropy of the problem space at hand.

@dscho
Copy link
Member

dscho commented Aug 23, 2019

I would be eager to learn the full details

I still would be.

@WSLUser
Copy link

WSLUser commented Sep 5, 2019

Please bear in mind we do have PKCS#11 support in the win32-openssh project in the latest release. While mostly there, it isn't 100% complete. See PowerShell/openssh-portable#362 for the rest (if you require the ssh agent).

I honestly don't know why at this point, this project doesn't use win32-openssh by default. Yes you can set the GIT_SSH env variable but seems to me to be ignored unless you call the binaries directly in the directory they are installed to (C:/Program Files/OpenSSH-Win32). At least that has been my experience.

@rimrul
Copy link
Member

rimrul commented Sep 5, 2019

I honestly don't know why at this point, this project doesn't use win32-openssh by default.

Windows versions <10.

@WSLUser
Copy link

WSLUser commented Sep 5, 2019

Works on win7. I use it there with git bash (mintty) as it provides the xterm features needed. Nobody should be using Vista, XP or older.

@rimrul
Copy link
Member

rimrul commented Sep 6, 2019

Oh. I Didn't know that. Microsoft seems to communicate it as a pure windows 10 feature. Does it work on Vista, too?

@WSLUser
Copy link

WSLUser commented Sep 6, 2019

No. Support only goes to Win7. It is in their Wiki. There's an open issue for XP support that will never get resolved and they are barely active. It appears they contribute more towards the upstream to make it easier for Windows.

Microsoft seems to communicate it as a pure windows 10 feature.

This is due to making it a optional feature built into Windows 10. But the OS updates less frequently than the project most of the time. The maintainers come out of the blue and throw a bunch of changes into the project and then call it a release.

@danizen
Copy link
Author

danizen commented Sep 9, 2019

I would have expected smartcards to be supported via Secure Channel right out of the box.
So when your Git for Windows installer asks you to choose the HTTPS backend, and
you choose Secure Channel, I could imagine that it already works.

Not for OpenSSH, though, that would require a ton more work.

That's interesting, and before I provide "full details", I'd like to explore it. There doesn't seem to be a documented way to change to secure channel, but this stackoverflow provides guidance. I will try this and get back to you.

@danizen
Copy link
Author

danizen commented Sep 9, 2019

Details

So, I did try again with schannel enabled, and my conclusion is that this only affects whether the Windows or openssl libraries are used for SSL/TLS. With schannel enabled, username/password authentication is still used.

As a federal government user (who is sophisticated), I will prefer SSH as the communication channel every time so that my password is not cached on disk and I do not have to enter it again and again.

My request is not for a different mechanisms of secure communications, but for a method of authentication tied to the PIV key. It is a fairly clear process extracting an OpenSSH key pair from a certificate pair; the question is how to do this on the fly using Microsoft CNG or older CAPI to obtain the OpenSSH key pair from the PIV/SmartCard.

Thanks.

@WSLUser
Copy link

WSLUser commented Sep 9, 2019

the question is how to do this on the fly using Microsoft CNG or older CAPI to obtain the OpenSSH key pair from the PIV/SmartCard

You need PKCS11 support. OpenSSH does so with .so files. Windows uses dll to get to the hardware. So the functionality is there but not exposed. The win32-openssh project exposes it.

So if you set GIT_SSH (which as stated above doesn't seem to really matter) or navigate to the ssh path and execute ssh.exe there, you should be able to use your smart card. But without the agent, there are limitations. If you can, build/compile the project with the PR I referenced above with VS2017 or VS2015 (2019 doesn't work unfortunately). Then test if it works. As the PKCS11 portion provided by ssh will be completely covered, it will then be up to this project to ensure git works with it.

@dscho
Copy link
Member

dscho commented Sep 9, 2019

I honestly don't know why at this point, this project doesn't use win32-openssh by default.

But you do! As you commented yourself in #1981, you don't have time to take care of it. And neither did anybody else so far.

Besides, you probably missed the rather important bug reported in PowerShell/Win32-OpenSSH#1322. That's a show-stopper.

@dscho
Copy link
Member

dscho commented Mar 7, 2020

I suspect that the latest OpenSSH version, as shipped in https://github.com/git-for-windows/git/releases/tag/v2.26.0-rc0.windows.1, and together with its libfido2 support offers an extension API, might make support for Smartcard authentication more feasible now.

@dscho
Copy link
Member

dscho commented Oct 15, 2021

Closing this stale ticket.

@dscho dscho closed this as completed Oct 15, 2021
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants