Signing pkg repos with a YubiKey — security feedback welcome

Hi,

I've written an article on signing FreeBSD pkg repositories with a GPG key on a YubiKey. The approach uses gpg-connect-agent PKSIGN for raw RSA signatures (since gpg --sign produces OpenPGP format instead of the PKCS#1 v1.5 that pkg expects) and SSH remote forwarding ( ssh -R) to keep the YubiKey on a local workstation while pkg repo runs on a remote FreeBSD build host.

The article also documents parts of pkg's signing protocol that I had to piece together from the source code — the double-hash verification scheme in libpkg/pkgsign_ossl.c, the stdin behavior in libpkg/pkg_repo_create.c, and the fingerprint computation in libpkg/pkg_repo.c.

I'd appreciate feedback on whether there are any security concerns with this approach — particularly around the GPG agent forwarding and the way the signing script interacts with gpg-agent.

Full article: Signing FreeBSD pkg Repositories with a YubiKey
Signing script (Python): sign-repo.py

Full disclosure: I came up with the idea to use gpg-connect-agent for the raw RSA signatures, and Claude Code did the rest — writing the signing script, the article, and verifying claims against the pkg source code. I use Claude Code extensively in my professional and private life. If you'd like to discuss that, feel free to connect with me on LinkedIn — happy to chat there.

Best,

-Brendan
 
So that is you as the maintainer of the repo signing with your private key via yubikey on the repo.
Someone downloading from your repo needs to verify your signature on the repo.

If you sign with yubikey, is your pub key available for someone to verify your signature?
 
Yes, that's correct — I'm the maintainer and sign the repo with my YubiKey.

The public key is in the GitHub repo at Keys/repo.pub. Clients verify signatures using pkg's fingerprint mechanism. The setup comes down to installing the fingerprint on the client:

Code:
mkdir -p /usr/local/etc/pkg/fingerprints/banzai-plugins/trusted
mkdir -p /usr/local/etc/pkg/fingerprints/banzai-plugins/revoked

cat > /usr/local/etc/pkg/fingerprints/banzai-plugins/trusted/repo.fingerprint <<'EOF'
function: sha256
fingerprint: 7ae0ef1e50a0658802b01291be9de188c184a2d64310ac84efc81a31ca1e7681
EOF

Then add the repo config:

Code:
cat > /usr/local/etc/pkg/repos/banzai-plugins.conf <<'EOF'
banzai-plugins: {
  url: "https://brendanbank.github.io/banzai-plugins/${ABI}/26.1/repo",
  signature_type: "fingerprints",
  fingerprints: "/usr/local/etc/pkg/fingerprints/banzai-plugins",
  enabled: yes
}
EOF

The fingerprint is SHA256 of the PEM file. Once both are in place, pkg update -r banzai-plugins verifies every repo catalogue download against it.
 
Ok so the biggest difference between "normal" is you sign with private key that happens to live on yubikey instead of manually entering. Cool/interesting.
As a consumer all that matters is "I can access the pub key that corresponds to your priv key". How you utilize priv key shouldn't matter to the pub key side.
 
I no longer use GPG for anything. I sign my commits with the SSH key I use for git.

Thanks for bringing that up. I don't want to get into a debate about GPG itself, the issues you mention maybe real, I have not looked into them, but they're outside the scope of what I was trying to solve here.

That said, based on your feedback I've moved away from the GPG agent forwarding approach entirely. The article has been updated to use the YubiKey's PIV applet via PKCS#11 instead. With PIV you achieve the same goals: a) private key never leaves the hardware token b) PIN and touch required for every signature, while avoiding the GPG ecosystem altogether. No gpg-agent, no Assuan protocol, no socket forwarding conflicts. Just a standard PKCS#11 interface with a simple custom socket protocol.

Updated article: Signing FreeBSD pkg Repositories with a YubiKey
 
I no longer use GPG for anything. I sign my commits with the SSH key I use for git.
How can be signed and checked signatures of SSH public keys? Without key hierarchy or other organisation, the SSH signature is only for you (or for web site integrated with SSH keys).

About topic - I don't understand why it is signed with Yubikey and not with PGP key in file?
 
How can be signed and checked signatures of SSH public keys? Without key hierarchy or other organisation, the SSH signature is only for you (or for web site integrated with SSH keys).

There's no hierarchy with PGP which relies more on the decentralized Web of Trust model.

OpenSSH public keys can be used for authentication and signing. These can be trusted on first use (TOFU) or they can be signed by a CA with PKI giving you a real hierarchy.
 
Back
Top