Page MenuHome GnuPG

Print diagnostics to explain certain expiration cases
Open, LowPublic

Description

It seems to be impossible to change the expiration date of *some* keys, such as the one attached (not in use by a human and part of a test suite, safe to publish).

[luca3@moore ~]$ rm -rf .gnupg
[luca3@moore ~]$ gpg --import linda.asc
gpg: directory '/home/luca3/.gnupg' created
gpg: keybox '/home/luca3/.gnupg/pubring.kbx' created
gpg: /home/luca3/.gnupg/trustdb.gpg: trustdb created
gpg: key 6A48221A903A158B: public key "Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>" imported
gpg: key 6A48221A903A158B: secret key imported
gpg: Total number processed: 1
gpg:               imported: 1
gpg:       secret keys read: 1
gpg:   secret keys imported: 1
[luca3@moore ~]$ gpg --list-keys
/home/luca3/.gnupg/pubring.kbx
------------------------------
pub   rsa3072 2019-05-09 [C] [expired: 2022-05-05]
      ABC96B3B4BAFB57DC45D81B56A48221A903A158B
uid           [ expired] Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>

Everything is correct up to this point. Now let us try to unexpire the key.

[luca3@moore ~]$ gpg --edit-key 6A48221A903A158B
gpg (GnuPG) 2.2.40; Copyright (C) 2022 g10 Code GmbH
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

Secret key is available.

sec  rsa3072/6A48221A903A158B
     created: 2019-05-09  expired: 2022-05-05  usage: C   
     trust: unknown       validity: expired
ssb  rsa3072/713A187451941578
     created: 2019-05-09  expired: 2022-05-05  usage: E   
ssb  rsa3072/DCD555B6055ADE22
     created: 2019-05-09  expired: 2022-05-05  usage: S   
[ expired] (1). Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>

gpg> expire
Changing expiration time for the primary key.
Please specify how long the key should be valid.
         0 = key does not expire
      <n>  = key expires in n days
      <n>w = key expires in n weeks
      <n>m = key expires in n months
      <n>y = key expires in n years
Key is valid for? (0) 0
Key does not expire at all
Is this correct? (y/N) y

sec  rsa3072/6A48221A903A158B
     created: 2019-05-09  expired: 2022-05-05  usage: C     <<<<<<<<<<<<<<<< WRONG
     trust: unknown       validity: expired
ssb  rsa3072/713A187451941578
     created: 2019-05-09  expired: 2022-05-05  usage: E   
ssb  rsa3072/DCD555B6055ADE22
     created: 2019-05-09  expired: 2022-05-05  usage: S   
[ expired] (1). Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>

gpg: WARNING: Your encryption subkey expires soon.
gpg: You may want to change its expiration date too.
gpg> save
[luca3@moore ~]$ gpg --list-keys
gpg: checking the trustdb
gpg: no ultimately trusted keys found
/home/luca3/.gnupg/pubring.kbx
------------------------------
pub   rsa3072 2019-05-09 [C] [expired: 2022-05-05]
      ABC96B3B4BAFB57DC45D81B56A48221A903A158B
uid           [ expired] Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>

The same happens if I try to keep an actual expiration date:

[luca3@moore ~]$ gpg --edit-key 6A48221A903A158B
gpg (GnuPG) 2.2.40; Copyright (C) 2022 g10 Code GmbH
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

Secret key is available.

sec  rsa3072/6A48221A903A158B
     created: 2019-05-09  expired: 2022-05-05  usage: C   
     trust: unknown       validity: expired
ssb  rsa3072/713A187451941578
     created: 2019-05-09  expired: 2022-05-05  usage: E   
ssb  rsa3072/DCD555B6055ADE22
     created: 2019-05-09  expired: 2022-05-05  usage: S   
[ expired] (1). Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>

gpg> expire
Changing expiration time for the primary key.
Please specify how long the key should be valid.
         0 = key does not expire
      <n>  = key expires in n days
      <n>w = key expires in n weeks
      <n>m = key expires in n months
      <n>y = key expires in n years
Key is valid for? (0) 2y
Key expires at Wed 12 Feb 2025 11:50:25 AM CET   <<<<<<<<<< CORRECT: TWO YEARS FROM NOW
Is this correct? (y/N) y

sec  rsa3072/6A48221A903A158B
     created: 2019-05-09  expired: 2022-05-05  usage: C   <<<<<<<<<<<<<<<<< WRONG
     trust: unknown       validity: expired
ssb  rsa3072/713A187451941578
     created: 2019-05-09  expired: 2022-05-05  usage: E   
ssb  rsa3072/DCD555B6055ADE22
     created: 2019-05-09  expired: 2022-05-05  usage: S   
[ expired] (1). Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>

gpg: WARNING: Your encryption subkey expires soon.
gpg: You may want to change its expiration date too.
gpg> save
[luca3@moore ~]$ gpg --list-keys
gpg: checking the trustdb
gpg: no ultimately trusted keys found
/home/luca3/.gnupg/pubring.kbx
------------------------------
pub   rsa3072 2019-05-09 [C] [expired: 2022-05-05]
      ABC96B3B4BAFB57DC45D81B56A48221A903A158B
uid           [ expired] Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>

Exactly the same happens if I use --quick-set-expire:
[luca3@moore ~]$ gpg --quick-set-expire ABC96B3B4BAFB57DC45D81B56A48221A903A158B 0 
[luca3@moore ~]$ gpg --list-keys
gpg: checking the trustdb
gpg: no ultimately trusted keys found
/home/luca3/.gnupg/pubring.kbx
------------------------------
pub   rsa3072 2019-05-09 [C] [expired: 2022-05-05]
      ABC96B3B4BAFB57DC45D81B56A48221A903A158B
uid           [ expired] Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>

(Here I am not using a SUBFPRS argument, in order to avoid the issue of already expired subkeys:)

'--quick-set-expire FPR EXPIRE [*|SUBFPRS]'
     With two arguments given, directly set the expiration time of the
     primary key identified by FPR to EXPIRE.  To remove the expiration
     time '0' can be used.  With three arguments and the third given as
     an asterisk, the expiration time of all non-revoked and not yet
     expired subkeys are set to EXPIRE.  With more than two arguments
     and a list of fingerprints given for SUBFPRS, all non-revoked
     subkeys matching these fingerprints are set to EXPIRE.

I tried cheating with the system clock by using the faketime utility and gpg's
option --faked-system-time along with --ignore-time-conflict and
--ignore-valid-from. But even by operating on a freshly emptied .gnupg/
directory and at a time where the key is not yet expired I found no way of
changing the expiration date.

I can unexpire the two subkeys:

[luca3@moore ~]$ gpg --edit-key ABC96B3B4BAFB57DC45D81B56A48221A903A158B
gpg (GnuPG) 2.2.40; Copyright (C) 2022 g10 Code GmbH
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

Secret key is available.

sec  rsa3072/6A48221A903A158B
     created: 2019-05-09  expired: 2022-05-05  usage: C   
     trust: unknown       validity: expired
ssb  rsa3072/713A187451941578
     created: 2019-05-09  expired: 2022-05-05  usage: E   
ssb  rsa3072/DCD555B6055ADE22
     created: 2019-05-09  expired: 2022-05-05  usage: S   
[ expired] (1). Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>

gpg> key -1

sec  rsa3072/6A48221A903A158B
     created: 2019-05-09  expired: 2022-05-05  usage: C   
     trust: unknown       validity: expired
ssb* rsa3072/713A187451941578
     created: 2019-05-09  expired: 2022-05-05  usage: E   
ssb* rsa3072/DCD555B6055ADE22
     created: 2019-05-09  expired: 2022-05-05  usage: S   
[ expired] (1). Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>

gpg> expire
Are you sure you want to change the expiration time for multiple subkeys? (y/N) y
Please specify how long the key should be valid.
         0 = key does not expire
      <n>  = key expires in n days
      <n>w = key expires in n weeks
      <n>m = key expires in n months
      <n>y = key expires in n years
Key is valid for? (0) 0
Key does not expire at all
Is this correct? (y/N) y

sec  rsa3072/6A48221A903A158B
     created: 2019-05-09  expired: 2022-05-05  usage: C   
     trust: unknown       validity: expired
ssb* rsa3072/713A187451941578
     created: 2019-05-09  expired: never       usage: E   
ssb* rsa3072/DCD555B6055ADE22
     created: 2019-05-09  expired: never       usage: S   
[ expired] (1). Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>

gpg> save
[luca3@moore ~]$

But the main key remains unusable.

This is the main version I was using while I discovered the problem:

[luca3@moore ~]$ gpg --version
gpg (GnuPG) 2.2.40
libgcrypt 1.10.1
Copyright (C) 2022 g10 Code GmbH
License GNU GPL-3.0-or-later <https://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

Home: /home/luca3/.gnupg
Supported algorithms:
Pubkey: RSA, ELG, DSA, ECDH, ECDSA, EDDSA
Cipher: IDEA, 3DES, CAST5, BLOWFISH, AES, AES192, AES256, TWOFISH,
        CAMELLIA128, CAMELLIA192, CAMELLIA256
Hash: SHA1, RIPEMD160, SHA256, SHA384, SHA512, SHA224
Compression: Uncompressed, ZIP, ZLIB, BZIP2

But then I have also compiled the latest GPG release from source and tried with that, to no avail:

[luca3@moore ~]$ gpg --version
gpg (GnuPG) 2.4.0
libgcrypt 1.10.1
Copyright (C) 2021 Free Software Foundation, Inc.
License GNU GPL-3.0-or-later <https://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

Home: /home/luca3/.gnupg
Supported algorithms:
Pubkey: RSA, ELG, DSA, ECDH, ECDSA, EDDSA
Cipher: IDEA, 3DES, CAST5, BLOWFISH, AES, AES192, AES256, TWOFISH,
        CAMELLIA128, CAMELLIA192, CAMELLIA256
Hash: SHA1, RIPEMD160, SHA256, SHA384, SHA512, SHA224
Compression: Uncompressed, ZIP, ZLIB, BZIP2

This might be more remarkable. I can reproduce the issue with gpg 1.4.23 as well:

[luca3@moore ~]$ rm -rf .gnupg/
[luca3@moore ~]$ faketime '2022-05-01' gpg1 --import linda.asc
gpg: directory `/home/luca3/.gnupg' created
gpg: new configuration file `/home/luca3/.gnupg/gpg.conf' created
gpg: WARNING: options in `/home/luca3/.gnupg/gpg.conf' are not yet active during this run
gpg: keyring `/home/luca3/.gnupg/secring.gpg' created
gpg: keyring `/home/luca3/.gnupg/pubring.gpg' created
gpg: key 903A158B: secret key imported
gpg: /home/luca3/.gnupg/trustdb.gpg: trustdb created
gpg: key 903A158B: public key "Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>" imported
gpg: Total number processed: 1
gpg:               imported: 1  (RSA: 1)
gpg:       secret keys read: 1
gpg:   secret keys imported: 1
[luca3@moore ~]$ faketime '2022-05-01' gpg1 --list-keys
/home/luca3/.gnupg/pubring.gpg
------------------------------
pub   3072R/903A158B 2019-05-09 [expires: 2022-05-05]
uid                  Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>
sub   3072R/51941578 2019-05-09 [expires: 2022-05-05]
sub   3072R/055ADE22 2019-05-09 [expires: 2022-05-05]

[luca3@moore ~]$ faketime '2022-05-01' gpg1 --edit-key 903A158B
gpg (GnuPG) 1.4.23; Copyright (C) 2015 Free Software Foundation, Inc.
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

Secret key is available.

pub  3072R/903A158B  created: 2019-05-09  expires: 2022-05-05  usage: C   
                     trust: unknown       validity: unknown
sub  3072R/51941578  created: 2019-05-09  expires: 2022-05-05  usage: E   
sub  3072R/055ADE22  created: 2019-05-09  expires: 2022-05-05  usage: S   
[ unknown] (1). Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>

gpg> expire
Changing expiration time for the primary key.
Please specify how long the key should be valid.
         0 = key does not expire
      <n>  = key expires in n days
      <n>w = key expires in n weeks
      <n>m = key expires in n months
      <n>y = key expires in n years
Key is valid for? (0) 0
Key does not expire at all
Is this correct? (y/N) y

pub  3072R/903A158B  created: 2019-05-09  expires: 2022-05-05  usage: C   <<<<<<<< WRONG
                     trust: unknown       validity: unknown
sub  3072R/51941578  created: 2019-05-09  expires: 2022-05-05  usage: E   
sub  3072R/055ADE22  created: 2019-05-09  expires: 2022-05-05  usage: S   
[ unknown] (1). Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>

gpg: WARNING: Your encryption subkey expires soon.
gpg: You may want to change its expiration date too.
gpg> {F4571283}

I am running a recent GNU/Linux system on x86_64; a customised debian with nothing that should affect GPG at all. I do in fact use GPG every day for my email on this machine (Gnus, EasyPG) with no trouble.

Am I missing something obvious? Thanks in advance.

Details

Version
GPG 2.4.0, GPG 2.2.40, GPG 1.4.23

Event Timeline

{F4571289}linda.asc

This is the file I am repeatedly importing in the sessions from my report. It is one of the keys that seem impossible to unexpire for me.
There is no privacy issue: this belongs to a published test suite and is not used by any human.

With the current development version I get

$ gpg --version
gpg (GnuPG) 2.4.1-beta21
libgcrypt 1.11.0

$ $ GNUPGHOME=~/dev/g10/T6370 gpg --check-sigs --with-colons
tru::1:1676361640:0:3:1:5
pub:e:3072:1:6A48221A903A158B:1557403701:1651752501::-:::c::::::23::0:
fpr:::::::::ABC96B3B4BAFB57DC45D81B56A48221A903A158B:
sig:!::1:6A48221A903A158B:1557403701::::Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>:1fx::ABC96B3B4BAFB57DC45D81B56A48221A903A158B:::10:
uid:e::::1557403701::AE213441C7BB1CDC493FFC6FEBDA1C1D3F1D485E::Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>::::::::::0:
sig:!::1:6A48221A903A158B:1557403701::::Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>:13x::ABC96B3B4BAFB57DC45D81B56A48221A903A158B:::10:
sub:e:3072:1:713A187451941578:1557403701:1651752501:::::e::::::23:
fpr:::::::::ED4DFA33D55BA026B5FEEBE1713A187451941578:
sig:!::1:6A48221A903A158B:1557403701::::Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>:18x::ABC96B3B4BAFB57DC45D81B56A48221A903A158B:::10:
sub:e:3072:1:DCD555B6055ADE22:1557403701:1651752501:::::s::::::23:
fpr:::::::::33F10399FEF8BD5B7AAFA594DCD555B6055ADE22:
sig:!::1:6A48221A903A158B:1557403701::::Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>:18x::ABC96B3B4BAFB57DC45D81B56A48221A903A158B:::10:

$ GNUPGHOME=~/dev/g10/T6370 gpg --quick-set-expire ABC96B3B4BAFB57DC45D81B56A48221A903A158B 0
gpg: signing failed: Bad secret key
gpg: make_keysig_packet failed: Bad secret key

In another test with Kleopatra and a new GNUPGHOME with fresh imported key I get the following result when changing the end of the validity period of the primary key:

$ GNUPGHOME=~/dev/g10/T6370 gpg --check-sigs --with-colons
tru::1:1676361732:0:3:1:5
pub:e:3072:1:6A48221A903A158B:1557403701:1651752501::-:::c::::::23::0:
fpr:::::::::ABC96B3B4BAFB57DC45D81B56A48221A903A158B:
sig:!::1:6A48221A903A158B:1557403701::::Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>:1fx::ABC96B3B4BAFB57DC45D81B56A48221A903A158B:::10:
uid:e::::1676361730::AE213441C7BB1CDC493FFC6FEBDA1C1D3F1D485E::Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>::::::::::0:
sig:!::1:6A48221A903A158B:1676361730::::Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>:13x::ABC96B3B4BAFB57DC45D81B56A48221A903A158B:::10:
sub:e:3072:1:713A187451941578:1557403701:1651752501:::::e::::::23:
fpr:::::::::ED4DFA33D55BA026B5FEEBE1713A187451941578:
sig:!::1:6A48221A903A158B:1557403701::::Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>:18x::ABC96B3B4BAFB57DC45D81B56A48221A903A158B:::10:
sub:e:3072:1:DCD555B6055ADE22:1557403701:1651752501:::::s::::::23:
fpr:::::::::33F10399FEF8BD5B7AAFA594DCD555B6055ADE22:
sig:!::1:6A48221A903A158B:1557403701::::Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>:18x::ABC96B3B4BAFB57DC45D81B56A48221A903A158B:::10:

Kleopatra reports success. Note that the signature of the user ID changed/was updated and that the creation (!) timestamp of the user ID changed.

Here is the output of gpg --full-timestrings --check-sigs:

pub   rsa3072 2019-05-09 12:08:21 [C] [expired: 2022-05-05 12:08:21]
      ABC96B3B4BAFB57DC45D81B56A48221A903A158B
sig!         6A48221A903A158B 2019-05-09 12:08:21  [self-signature]
uid           [ expired] Linda Mary Patricia Deborah Barbara Susan Maria Nancy <linda@example.org>
sig!3        6A48221A903A158B 2019-05-09 12:08:21  [self-signature]
sub   rsa3072 2019-05-09 12:08:21 [E] [expired: 2022-05-05 12:08:21]
sig!         6A48221A903A158B 2019-05-09 12:08:21  [self-signature]
sub   rsa3072 2019-05-09 12:08:21 [S] [expired: 2022-05-05 12:08:21]
sig!         6A48221A903A158B 2019-05-09 12:08:21  [self-signature]

The first signature is a direct key signature (class 0x1f) and this determines the expiration time. The usual case is to have the expiration time in the user id signatures. Our code does not allow to chnage the expiration time of direct key signature. This is because direct key signature are used by PGP and GnuPG only to add designated revokers. Gpg has no means to create a direct key signature like you have in your key.

For reference, here is the direct key signature packet which is legal but missing its only useful part, the revocation key (subpkt 12):

# off=400 ctb=89 tag=2 hlen=3 plen=450
:signature packet: algo 1, keyid 6A48221A903A158B
        version 4, created 1557403701, md5len 0, sigclass 0x1f
        digest algo 10, begin of digest 66 81
        hashed subpkt 30 len 1 (features: 03)
        critical hashed subpkt 27 len 1 (key flags: 01)
        critical hashed subpkt 2 len 4 (sig created 2019-05-09)
        critical hashed subpkt 9 len 4 (key expires after 2y362d0h0m)
        hashed subpkt 33 len 21 (issuer fpr v4 ABC96B3B4BAFB57DC45D81B56A48221A903A158B)
        hashed subpkt 16 len 8 (issuer key ID 6A48221A903A158B)
        hashed subpkt 21 len 1 (pref-hash-algos: 10)
        data: [3072 bits]

The first signature is a direct key signature (class 0x1f) and this determines the expiration time. The usual case is to have the expiration time in the user id signatures. Our code does not allow to chnage the expiration time of direct key signature. This is because direct key signature are used by PGP and GnuPG only to add designated revokers. Gpg has no means to create a direct key signature like you have in your key.

I was assuming that this key had been generated by GPG or even by something simpler like netpgp, because of its age. I cannot know exactly because this was done some years back before I came into the project, by somebody who has since left.

Thanks.

(I would suggest printing a warning message when GPG sees a direct key signature expiration time and the user is trying to change expirations.)

I guess this is the first time such a key was reported. Printing diagnostics would be a bit of work because the code to compute th. expiration time is deep in gpg's guts.

werner renamed this task from Impossible to change expiration date for some keys to Print diagnostics to explain certain expiration cases.Feb 14 2023, 5:20 PM
werner triaged this task as Low priority.
werner edited projects, added Feature Request; removed Not A Bug.

Understood. I appreciate the time you took to analyse the issue. Thanks.