8 releases

0.1.7 Oct 25, 2024
0.1.6 Aug 13, 2024
0.1.5 Jun 6, 2024
0.1.4 May 28, 2024
0.0.0-unreleased Aug 17, 2023

#149 in Embedded development

Download history 174/week @ 2024-08-12 16/week @ 2024-08-19 19/week @ 2024-08-26 9/week @ 2024-09-02 16/week @ 2024-09-09 39/week @ 2024-09-16 35/week @ 2024-09-23 97/week @ 2024-09-30 108/week @ 2024-10-07 68/week @ 2024-10-14 235/week @ 2024-10-21 57/week @ 2024-10-28 29/week @ 2024-11-04 83/week @ 2024-11-11 86/week @ 2024-11-18 16/week @ 2024-11-25

216 downloads per month

LGPL-3.0-only

335KB
8K SLoC

SE05X driver

This crate contains a Rust driver for the SE05x series of secure elements from NXP. It contains an implementation of the T=1 protocol and the ISO7816-4 APDUs that are used to communicate with the se05x.

use se05x::se05x::commands::*;
use se05x::se05x::policies::*;
use se05x::se05x::*;
let i2c = get_i2c();
let delay = get_delay();
let address = 0x48;
let mut se05x = Se05X::new(i2c, address, delay);
let user_id = ObjectId([0x01, 0x00, 0x00, 0x00]);
let object_id = ObjectId([0x01, 0x02, 0x03, 0x04]);
let buf = &mut [0; 128];

let atr = se05x.enable();

// Running a WriteUserId command:
se05x.run_command(
    &WriteUserId::builder()
        .object_id(user_id)
        .data(b"Some value")
        .build(),
    buf,
)?;

// Creating a file with a policy
let policy = &[Policy {
    object_id: user_id,
    access_rule: ObjectAccessRule::from_flags(ObjectPolicyFlags::ALLOW_READ),
}];

se05x.run_command(
    &WriteBinary::builder()
        .policy(PolicySet(policy))
        .object_id(object_id)
        .file_length(9.into())
        .data(b"Some data")
        .build(),
    buf,
)?;

// Opening a session with teh UserID
let session_id = se05x
    .run_command(&CreateSession { object_id: user_id }, buf)?
    .session_id;

// Verifying the UserId
se05x.run_session_command(
    session_id,
    &VerifySessionUserId {
        user_id: b"Some value",
    },
    buf,
)?;
// Reading the data with the verified session
let data = se05x.run_session_command(
    session_id,
    &ReadObject::builder()
        .object_id(object_id)
        .offset(0.into())
        .length(9.into())
        .build(),
    buf,
)?;

Architecture

T=1

This driver communicates with the se05x over the T=1 protocol over I2C, as described in UM11225.

To do so and be compatible with most embedded controlers, it depends on the I2C Read and Write from embedded-hal. However these traits do not expose the enough, as the T=1 protocol requires detecting I2C NACKs, which are not exposed in this protocol.

Nacks are exposed in the Error types for each HAL crate. As such an extension to the embedded-hal traits is defined as I2CErrorNack, exposing the missing information. It is implemented for the NRF and LPC55 Hals in src/t1/i2cimpl.rs, gated by the features nrf and lpc55 respectively.

This may not be necessary with future releases of embedded-hal, which adds the missing information.

Iso7816

This driver uses the iso7816 crate to implement serialization of APDUs.

Generation of commands

To simplify implementation, all supported se05x APDUs are described in src/se05x/commands.toml. The python script generate_commands.py parses the command.toml file and generates src/se05x/commands.rs, which implements all the APDUs.

Funding

Logo NLnet: abstract logo of four people seen from above Logo NGI Assure: letterlogo shaped like a tag

This project was funded through the NGI Assure Fund, a fund established by NLnet with financial support from the European Commission's Next Generation Internet programme, under the aegis of DG Communications Networks, Content and Technology under grant agreement No 957073.

Dependencies

~1–4MB
~98K SLoC