There's a mismatch between how the expiration date is represented in gpgme (as seconds since epoch) and gpg (as seconds from now). This leads to keys with expiration dates far in the future
Description
Revisions and Commits
Related Objects
- Mentioned In
- D571: qt: Fix validity for (sub)keys generated using QGpgMEQuickJob
- Mentioned Here
- T6736: Year 2038 issue for key validity date
Event Timeline
In gpg you may also specify the 4xpiarion date in ISO format. afaic, gpgme supports this.
That's both not correct. gpg takes the expiration time in seconds since creation time. For a new key this is close to the corrent time but not really. For an prolonging an expiration, this is of course different - the creation time of the key needs to be taken in account. I recall that we once had a discussion and agreed to keep it at time after the creation of the key. This avoids problems with the expiration going negative.
Recently we fixed some things here in gpg; see the comment for T6736.
My explanation of gpgme's behavior was not quite correct: Specifically in the QGpgMEQuickJobs for creating (sub)keys, the API uses QDateTimes, which are then converted to seconds since epoch.
I did not realize the difference in behavior in gpg; I'll adapt my patch to take that into account.
FWIW, when updating the expiration time gpg does this:
if ( sig->expiredate > sig->timestamp) u = sig->expiredate - sig->timestamp; else u = 1; /* A 1-second expiration time is the shortest one OpenPGP has */
Sorry, I should have been more precise in my description of the problem. Specifically with --quick-addkey, gpg's behavior seems to be that the expiration, when given using seconds=... is treated as seconds from now.
Werner and Tobias are both correct. If a new subkey is generated from scratch then gpg uses the current time as key creation time and sets the expiration date (in the internal in-memory representation of a public key) to the key creation time plus the expiration value.
The expiration value is capped at 2^32-2. There is no check if key_creation_time + expiration_value overflows and the calculations are done with uint32. In other words, if the caller doesn't ensure that the calculation doesn't overflow then adding the subkey will result in an expired key. For example, try gpg --quick-add-key <fingerprint of existing key> - - 83y and then check with gpg -kv <fingerprint>. You'll find a new subkey which has already expired.