Skip to content

Commit

Permalink
Merge pull request #95 from LedgerHQ/add-ui-gadgets
Browse files Browse the repository at this point in the history
Add new UI gadgets
  • Loading branch information
agrojean-ledger authored Nov 16, 2023
2 parents 894b445 + 05355eb commit cee5644
Show file tree
Hide file tree
Showing 17 changed files with 538 additions and 108 deletions.
9 changes: 9 additions & 0 deletions .cargo/config.toml
Original file line number Diff line number Diff line change
@@ -1,3 +1,12 @@
[target.nanos]
runner = "speculos -m nanos --display=headless"

[target.nanox]
runner = "speculos -m nanox -a 5 --display=headless"

[target.nanosplus]
runner = "speculos -m nanosp -a 1 --display=headless"

[unstable]
build-std = ["core"]
build-std-features = ["compiler-builtins-mem"]
84 changes: 27 additions & 57 deletions .github/workflows/rust.yml
Original file line number Diff line number Diff line change
Expand Up @@ -15,96 +15,66 @@ env:

jobs:
clippy:
name: Run static analysis
runs-on: ubuntu-latest

container:
image: ghcr.io/ledgerhq/ledger-app-builder/ledger-app-dev-tools:latest
strategy:
matrix:
target: ["nanos", "nanox", "nanosplus"]

steps:
- name: arm-none-eabi-gcc
uses: fiam/[email protected]
with:
release: '9-2019-q4'
- name: Install toolchains
uses: actions-rs/toolchain@v1
with:
toolchain: nightly
override: true
components: rust-src, clippy
- uses: actions/checkout@v2
- name: Clone
uses: actions/checkout@v2
- name: Cargo clippy
uses: actions-rs/cargo@v1
with:
command: clippy
args: -p ledger_device_rust_sdk --target ledger_device_rust_sdk/${{ matrix.target }}.json
fmt:
args: -p ledger_device_sdk --target ledger_device_sdk/${{ matrix.target }}.json

format:
name: Check code formatting
runs-on: ubuntu-latest
container:
image: ghcr.io/ledgerhq/ledger-app-builder/ledger-app-dev-tools:latest
steps:
- name: Install toolchains
uses: actions-rs/toolchain@v1
with:
toolchain: nightly
override: true
components: rust-src, rustfmt
- uses: actions/checkout@v2
- name: Cargo fmt
- name: Clone
uses: actions/checkout@v2
- name: Run cargo fmt
uses: actions-rs/cargo@v1
with:
command: fmt
args: -p ledger_device_rust_sdk --all -- --check
args: -p ledger_device_sdk --all -- --check

build:
name: Build SDK
runs-on: ubuntu-latest
container:
image: ghcr.io/ledgerhq/ledger-app-builder/ledger-app-dev-tools:latest
strategy:
matrix:
target: ["nanos", "nanox", "nanosplus"]

steps:
- name: arm-none-eabi-gcc
uses: fiam/[email protected]
with:
release: '9-2019-q4'
- name: Install clang
run: sudo apt-get update && sudo apt install -y clang
- name: Install toolchains
uses: actions-rs/toolchain@v1
with:
toolchain: nightly
override: true
components: rust-src
- uses: actions/checkout@v2
- name: Clone
uses: actions/checkout@v2
- name: Cargo build
uses: actions-rs/cargo@v1
with:
command: build
args: -p ledger_device_rust_sdk --target ledger_device_rust_sdk/${{ matrix.target }}.json
args: -p ledger_device_sdk --target ledger_device_sdk/${{ matrix.target }}.json

test:
name: Run unit tests
runs-on: ubuntu-latest
container:
image: ghcr.io/ledgerhq/ledger-app-builder/ledger-app-dev-tools:latest
strategy:
matrix:
target: ["nanos", "nanox", "nanosplus"]

steps:
- name: arm-none-eabi-gcc
uses: fiam/[email protected]
with:
release: '9-2019-q4'
- name: Install clang
run: sudo apt-get update && sudo apt install -y clang
- uses: actions-rs/toolchain@v1
with:
toolchain: nightly
override: true
components: rust-src
- name: Install dependencies
run: |
sudo apt-get update && sudo apt-get install -y qemu-user-static
pip install speculos --extra-index-url https://test.pypi.org/simple/
- uses: actions/checkout@v2
- name: Clone
uses: actions/checkout@v2
- name: Unit tests
uses: actions-rs/cargo@v1
with:
command: test
args: -p ledger_device_rust_sdk --target ledger_device_rust_sdk/${{ matrix.target }}.json --features speculos
args: -p ledger_device_sdk --target ledger_device_sdk/${{ matrix.target }}.json --features speculos
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
# Ledger Device Rust SDK
This workspace contains the 4 crates members of Ledger Device Rust SDK

* [ledger_device_rust_sdk](./ledger_device_rust_sdk): main Rust SDK crate used to build an application that runs on BOLOS OS,
* [ledger_device_sdk](./ledger_device_sdk): main Rust SDK crate used to build an application that runs on BOLOS OS,
* [ledger_device_ui_sdk](./ledger_device_ui_sdk): UI SDK used by application to get access to UI gadgets,
* [ledger_secure_sdk_sys](./ledger_secure_sdk_sys): bindings to [ledger_secure_sdk](https://github.com/LedgerHQ/ledger-secure-sdk)
* [include_gif](./include_gif): procedural macro used to manage GIF.
12 changes: 6 additions & 6 deletions include_gif/src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
extern crate proc_macro;

use proc_macro::TokenStream;
use syn;
use std;
use std::fs::File;
use std::io::Write;
use syn;

#[proc_macro]
pub fn include_gif(input: TokenStream) -> TokenStream {
Expand All @@ -18,19 +18,19 @@ pub fn include_gif(input: TokenStream) -> TokenStream {
let palette = decoder.palette().unwrap();
let dimensions = frame.width * frame.height;
let (size, remainder) = ((dimensions / 8) as usize, (dimensions % 8) as usize);

let mut packed = Vec::new();
for i in 0..size {
let mut byte = 0;
for j in 0..8 {
let color = (palette[frame.buffer[8*i + j] as usize * 3] != 0) as u8;
let color = (palette[frame.buffer[8 * i + j] as usize * 3] != 0) as u8;
byte |= color << j;
}
packed.push(byte);
}
let mut byte = 0;
let mut byte = 0;
for j in 0..remainder {
let color = (palette[frame.buffer[8*size + j] as usize * 3] != 0) as u8;
let color = (palette[frame.buffer[8 * size + j] as usize * 3] != 0) as u8;
byte |= color << j;
}
packed.push(byte);
Expand All @@ -40,4 +40,4 @@ pub fn include_gif(input: TokenStream) -> TokenStream {
let a = std::str::from_utf8(&b).unwrap();

a.parse().unwrap()
}
}
2 changes: 1 addition & 1 deletion ledger_device_sdk/examples/signature.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ fn panic(_info: &PanicInfo) -> ! {
loop {}
}

use ledger_device_rust_sdk::ecc::{make_bip32_path, Secp256r1, SeedDerive};
use ledger_device_sdk::ecc::{make_bip32_path, Secp256r1, SeedDerive};

const PATH: [u32; 5] = make_bip32_path(b"m/44'/123'/0'/0/0");

Expand Down
3 changes: 2 additions & 1 deletion ledger_device_sdk/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -137,7 +137,8 @@ impl<T> NVMData<T> {
asm!( "mov {}, r9", out(reg) static_base);
let offset = (addr - static_base) as isize;
let data_addr = (_nvram_data as *const u8).offset(offset);
let pic_addr = ledger_secure_sdk_sys::pic(data_addr as *mut core::ffi::c_void) as *mut T;
let pic_addr =
ledger_secure_sdk_sys::pic(data_addr as *mut core::ffi::c_void) as *mut T;
&mut *pic_addr.cast()
}
}
Expand Down
4 changes: 2 additions & 2 deletions ledger_device_sdk/src/nvm.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,8 @@
//! update:
//!
//! ```
//! use ledger_device_rust_sdk::PIC;
//! use ledger_device_rust_sdk::nvm::AtomicStorage;
//! use ledger_device_sdk::PIC;
//! use ledger_device_sdk::nvm::AtomicStorage;
//!
//! // This is necessary to store the object in NVM and not in RAM
//! #[link_section=".nvm_data"]
Expand Down
4 changes: 3 additions & 1 deletion ledger_device_ui_sdk/Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,14 +1,16 @@
[package]
name = "ledger_device_ui_sdk"
version = "1.0.0"
version = "1.1.0"
authors = ["yhql"]
edition = "2021"
license.workspace = true
description = "Ledger devices abstractions for displaying text, icons, menus and other common gadgets to the screen"

[dependencies]
ledger_device_sdk = "1.0.0"
ledger_secure_sdk_sys = "1.0.0"
include_gif = "1.0.0"
numtoa = "0.2.4"

[features]
speculos = []
Expand Down
13 changes: 9 additions & 4 deletions ledger_device_ui_sdk/examples/gadgets.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ fn panic(_: &PanicInfo) -> ! {
loop {}
}

use ledger_device_rust_sdk::buttons::*;
use ledger_device_sdk::buttons::*;
use ledger_device_ui_sdk::layout::{Layout, Location, StringPlace};
use ledger_device_ui_sdk::ui;

Expand Down Expand Up @@ -118,16 +118,21 @@ extern "C" fn sample_main() {

ui::clear_screen();

let checkmark = ledger_device_ui_sdk::bagls::CHECKMARK_ICON.set_x(0).set_y(4);
let checkmark = ledger_device_ui_sdk::bagls::CHECKMARK_ICON
.set_x(0)
.set_y(4);
checkmark.instant_display();
ledger_device_ui_sdk::bagls::CROSS_ICON
.set_x(20)
.set_y(4)
.instant_display();
ledger_device_ui_sdk::bagls::COGGLE.set_x(40).set_y(4).instant_display();
ledger_device_ui_sdk::bagls::COGGLE
.set_x(40)
.set_y(4)
.instant_display();
wait_any();
checkmark.instant_erase();
wait_any();

ledger_device_rust_sdk::exit_app(0);
ledger_device_sdk::exit_app(0);
}
9 changes: 8 additions & 1 deletion ledger_device_ui_sdk/src/bagls/mcu.rs
Original file line number Diff line number Diff line change
Expand Up @@ -379,13 +379,20 @@ impl<'a> SendToDisplay for Label<'a> {
};
let x = match self.layout {
Layout::RightAligned => self.layout.get_x(self.text.len() * 7),
Layout::Custom(x) => x as usize,
_ => 0,
};
let y = self.loc.get_y(self.dims.1 as usize) as i16;
let width = match self.layout {
Layout::Centered => crate::SCREEN_WIDTH,
_ => self.text.len() * 6,
};
let alignment = match self.layout {
Layout::LeftAligned => 0 as u16,
Layout::Centered => BAGL_FONT_ALIGNMENT_CENTER as u16,
Layout::RightAligned => BAGL_FONT_ALIGNMENT_CENTER as u16,
Layout::Custom(_) => 0 as u16,
};
let baglcomp = BaglComponent {
type_: BaglTypes::LabelLine as u8,
userid: 0, // FIXME
Expand All @@ -398,7 +405,7 @@ impl<'a> SendToDisplay for Label<'a> {
fill: 0,
fgcolor: 0xffffffu32,
bgcolor: 0,
font_id: font_id as u16 | BAGL_FONT_ALIGNMENT_CENTER as u16,
font_id: font_id as u16 | alignment,
icon_id: 0,
};

Expand Down
3 changes: 1 addition & 2 deletions ledger_device_ui_sdk/src/bagls/se.rs
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,7 @@ use crate::bagls::RectFull;

impl Draw for RectFull {
fn display(&self) {
unsafe {
unsafe {
ledger_secure_sdk_sys::bagl_hal_draw_rect(
1,
self.pos.0,
Expand All @@ -97,7 +97,6 @@ impl Draw for RectFull {
}
}


use core::ffi::c_void;

#[inline(never)]
Expand Down
18 changes: 9 additions & 9 deletions ledger_device_ui_sdk/src/bitmaps.rs
Original file line number Diff line number Diff line change
Expand Up @@ -40,15 +40,15 @@ pub fn manual_screen_clear() {
let inverted = [0u32, 1u32];
unsafe {
ledger_secure_sdk_sys::bagl_hal_draw_bitmap_within_rect(
0,
0,
128,
64,
2,
inverted.as_ptr(),
1,
BLANK.as_ptr(),
128 * 64
0,
0,
128,
64,
2,
inverted.as_ptr(),
1,
BLANK.as_ptr(),
128 * 64,
);
}
}
Expand Down
6 changes: 4 additions & 2 deletions ledger_device_ui_sdk/src/layout.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ pub enum Layout {
LeftAligned,
RightAligned,
Centered,
Custom(usize),
}

impl Layout {
Expand All @@ -11,6 +12,7 @@ impl Layout {
Layout::LeftAligned => crate::PADDING,
Layout::Centered => (crate::SCREEN_WIDTH - width) / 2,
Layout::RightAligned => crate::SCREEN_WIDTH - crate::PADDING - width,
Layout::Custom(x) => *x,
}
}
}
Expand All @@ -26,9 +28,9 @@ pub enum Location {
impl Location {
pub fn get_y(&self, height: usize) -> usize {
match self {
Location::Top => 0,
Location::Top => crate::Y_PADDING,
Location::Middle => (crate::SCREEN_HEIGHT - height) / 2,
Location::Bottom => crate::SCREEN_HEIGHT - height,
Location::Bottom => crate::SCREEN_HEIGHT - height - crate::Y_PADDING,
Location::Custom(y) => *y,
}
}
Expand Down
1 change: 1 addition & 0 deletions ledger_device_ui_sdk/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ pub mod screen_util;
pub mod ui;

pub const PADDING: usize = 2;
pub const Y_PADDING: usize = 3;
pub const SCREEN_WIDTH: usize = 128;

#[cfg(target_os = "nanos")]
Expand Down
Loading

0 comments on commit cee5644

Please sign in to comment.