Skip to content
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

Certificate Key Usage Attributes - S/MIME signing is needed for bundle creation #1124

Open
Drotak opened this issue May 11, 2023 · 3 comments
Labels
Milestone

Comments

@Drotak
Copy link

Drotak commented May 11, 2023

Describe the bug
I use smallstep as CA and for creating my certificates. Like mentioned in the documentation I created my leaf certificate with the needed X509 keyUsage and extendedKeyUsage parameters. (keyUsage = "digitalSignature" and extendetKeyUsage = "codeSigning").
The bundle creation worked fine with the demo certificate mentioned in the documentation, but when I tried to use my self signed certificate it failed with the error message:

405A1CF6FB7F0000:error:17000064:CMS routines:cms_signerinfo_verify_cert:certificate verify error:../crypto/cms/cms_smime.c:289:Verify error: unsupported certificate purpose
Failed to resign bundle: failed to sign manifest: signature verification failed: error:1700006B:CMS routines::content type not enveloped data

Background information
RAUC version: rauc 1.9.96-973ae
System:
I'm running a ubuntu server 22.04.2 LTS version in a qemu virtualization

root@secc04:~# hostnamectl
 Static hostname: my_comp
       Icon name: computer-vm
         Chassis: vm
      Machine ID: bae476e4d484402eae8536cd64b293ec
         Boot ID: cc401e676ee44947bced60480c38d611
  Virtualization: kvm
Operating System: Ubuntu 22.04.2 LTS              
          Kernel: Linux 5.19.0-41-generic
    Architecture: x86-64
 Hardware Vendor: QEMU
  Hardware Model: Standard PC _Q35 + ICH9, 2009_
root@secc04:~#

To Reproduce
Steps to reproduce the behavior:

  1. Create leaf certificate 'my_leaf.pem' with smallstep (step ca certificate). Chain: "root -> intermediate -> leaf"
    1.1 My provisioner config was updated with this template:
{
  "subject": {{ toJson .Subject }},
  "sans": {{ toJson .SANs }},
  "keyUsage": ["digitalSignature"],
  "extKeyUsage": ["codeSigning"],
  "basicConstraints": {
    "isCA": false
  }
}
  1. Create keyring file cat root.crt intermediate.crt > keyring.pem
  2. execute rauc --cert=/data/update/certs/my_leaf.pem --key=/data/update/certs/my_leaf.key --keyring=/data/update/certs/keyring.pem bundle rauc-bundle/ update-2023.05-1.raucb

Expected behavior
Bundle creation without error

Logs

402AEF40DF7F0000:error:17000064:CMS routines:cms_signerinfo_verify_cert:certificate verify error:../crypto/cms/cms_smime.c:289:Verify error: unsupported certificate purpose
Failed to resign bundle: failed to sign manifest: signature verification failed: error:1700006B:CMS routines::content type not enveloped data

Additional context
After a view hours of trying to find the problem and even changing my intermediate certificate to include the extendetKeyUsage = "codeSigning" parameter without luck, I found the problem!
The leaf certificate also needed the S/MIME signing parameter!
With the updated template, everything worked as expected:

{
  "subject": {{ toJson .Subject }},
  "sans": {{ toJson .SANs }},
  "keyUsage": ["digitalSignature"],
  "extKeyUsage": ["codeSigning", "emailProtection"],
  "basicConstraints": {
    "isCA": false
  }
}

Before including the "emailProtection" in the extKeyUsage Field, I also tried to include the "check-purpose=codesign" inside the config file, but it didn't change anything.

My config file now:

[system]
compatible=MyOwnDefinedName
bootloader=grub
bundle-formats=-plain
data-directory=/data/rauc-status
grubenv=/mnt/boot/grub/grubenv

[keyring]
path=/data/update/certs/keyring.pem
check-purpose=codesign

[slot.rootfs.0]
device=/dev/sda3
type=ext4
bootname=A

[slot.rootfs.1]
device=/dev/sda4
type=ext4
bootname=B

Therefore either the documentation is incomplete or the implementation is wrong.

Just wanted to let you know that I had huge problems with this. :)

Kind regards
Michael

@Drotak Drotak added the bug label May 11, 2023
@jluebbe
Copy link
Member

jluebbe commented Oct 24, 2023

When you pass a keyring to rauc bundle, it will try to verify the generated signature against that keyring (which helps catching inconsistencies or expired certs). Currently, it's not possible to set the certificate purpose for that check without passing a config file. So for bundle either pass a config file or don't pass --keyring.

Your output also mentions Failed to resign bundle, is that part of your workflow? As resign currently requires --keyring even with --no-verify, you have to pass a config file to set the purpose and use the same purpose for both the old certificate (input signature check) and the new one (generated signature check).

Together this should be a workaround for your case. To fix this properly, we'd have to:

  • split config file parsing from config consistency check (to require [system] only on the target)
  • allow passing config file key/values from the command line (perhaps something like -C keyring.check-purpose=codesign)
  • support different verification settings for the consistency check of the generated signature
  • add CLI tests of the check-purpose functionality

@jluebbe
Copy link
Member

jluebbe commented Oct 24, 2023

When #1268 is merged, you should be able to use rauc resign --no-verify without --keyring to disable signature checks completely. You should probably automate those a different way, in that case. :)

@jluebbe jluebbe assigned jluebbe and unassigned jluebbe Oct 24, 2023
@jluebbe jluebbe added this to the Unplanned milestone Oct 24, 2023
@jluebbe
Copy link
Member

jluebbe commented Oct 24, 2023

#1268 is merged now, so you should be able to use rauc resign --no-verify.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

2 participants