-
Notifications
You must be signed in to change notification settings - Fork 65
IoT Edge 1.5 (Scarthgap) on STM32MP1 - inconsistent certificate timestamp conversion / check #187
Description
Hi!
I am currently trying to get meta-iotedge running on an STM32MP1 platform. I already have a working iotedge setup for my hardware using a Debian image with the matching derivate of iotedge. However, we are planning to switch long-term to Yocto for flexibility and OS customization possibilities.
For testing I am using a very basic poky-altcfg distro (due to the systemd requirement) with a custom image based on core-image-minimal. The image compiles without errors and iotedge is available in my distro, there are no iotedge related errors printed in dmesg or journalctl.
However, when I try to configure iotedge with my (know working) config.toml, I run into the issue that my aziot-edged-ca certificate instantly expires upon creation:
Jan 14 13:58:17 my-client aziot-edged[1478]: 2026-01-14T13:58:17Z [INFO] - Edge CA was renewed
Jan 14 13:58:17 my-client aziot-edged[1478]: 2026-01-14T13:58:17Z [ERR!] - Cert aziot-edged-ca is expired and could not be renewed.
Jan 14 13:58:17 my-client aziot-edged[1478]: 2026-01-14T13:58:17Z [ERR!] - failed to configure Edge CA auto renew: Cert aziot-edged-ca is expired and could not be renewed
Using Yocto patches, I have been trying to track down the issue and found that function get_cert_chain() in cert-renewal/src/engine.rs actually reports a date expiration of the certificate! However, after trying to debug the code for a bit I have seen that the certificate timestamp conversion performed by crate::Time::from() seems to be inconsistent and produces bogus dates on the first call?
I added some lines to get_cert_chain() (engine.rs line 343ff):
let not_after = cert_chain[0].not_after();
// First conversion
let expiry1 = crate::Time::from(not_after);
log::error!("First conversion: {}", expiry1);
// Immediate second conversion with same reference
let expiry2 = crate::Time::from(not_after);
log::error!("Second conversion (same ref): {}", expiry2);
// Third conversion with fresh call
let expiry3 = crate::Time::from(cert_chain[0].not_after());
log::error!("Third conversion (fresh call): {}", expiry3);
// Fourth - repeat fresh call
let expiry4 = crate::Time::from(cert_chain[0].not_after());
log::error!("Fourth conversion (fresh call): {}", expiry4);
The resolut is an inconstant timestamp conversion:
Jan 14 14:34:20 my-client aziot-edged[1170]: 2026-01-14T14:34:20Z [INFO] - Edge CA was renewed
Jan 14 14:34:20 my-client aziot-edged[1170]: 2026-01-14T14:34:20Z [ERR!] - First conversion: -2330-08-31T06:03:56+00:00
Jan 14 14:34:20 my-client aziot-edged[1170]: 2026-01-14T14:34:20Z [ERR!] - Second conversion (same ref): 2026-04-14T14:34:19+00:00
Jan 14 14:34:20 my-client aziot-edged[1170]: 2026-01-14T14:34:20Z [ERR!] - Third conversion (fresh call): 2026-04-14T14:34:19+00:00
Jan 14 14:34:20 my-client aziot-edged[1170]: 2026-01-14T14:34:20Z [ERR!] - Fourth conversion (fresh call): 2026-04-14T14:34:19+00:00
Jan 14 14:34:20 my-client aziot-edged[1170]: 2026-01-14T14:34:20Z [ERR!] - Failed to calculate time difference.
With my debug code, the time conversion works from the second call on but then iotedge fails at a later point in time, probably also related to time conversion. I am not quite sure how to further debug this issue, maybe a specific flag is needed for the Rust compiler to properly support my platform?