diff --git a/ledger_secure_sdk_sys/.cargo/config.toml b/.cargo/config.toml similarity index 59% rename from ledger_secure_sdk_sys/.cargo/config.toml rename to .cargo/config.toml index 42dbacd3..1d55c22e 100644 --- a/ledger_secure_sdk_sys/.cargo/config.toml +++ b/.cargo/config.toml @@ -1,6 +1,6 @@ [unstable] -build-std = ["core"] +build-std = ["core", "alloc"] build-std-features = ["compiler-builtins-mem"] [build] -target = "nanosplus" \ No newline at end of file +target = "flex" \ No newline at end of file diff --git a/.github/workflows/build_all_apps.yml b/.github/workflows/build_all_apps.yml deleted file mode 100644 index a03f14dc..00000000 --- a/.github/workflows/build_all_apps.yml +++ /dev/null @@ -1,105 +0,0 @@ -name: Build all Rust apps - -on: - workflow_dispatch: - inputs: - sdk_branch: - type: string - required: false - default: '' - pull_request: - - -jobs: - test-build: - name: Build for all targets - strategy: - fail-fast: false - matrix: - include: - - repo: 'app-radix-babylon' - branch: 'develop' - - repo: 'app-sui' - branch: 'develop' - - repo: 'app-pocket' - branch: 'develop' - - repo: 'app-starknet' - branch: 'develop' - - repo: 'app-alephium' - branch: 'develop' - - repo: 'app-boilerplate-rust' - branch: 'main' - - runs-on: ubuntu-latest - container: - image: ghcr.io/ledgerhq/ledger-app-builder/ledger-app-builder:latest - steps: - - name: Install dependencies - run: pip install ledgered - - - name: Clone SDK - uses: actions/checkout@v4 - with: - path: sdk - - - name: Clone App - uses: actions/checkout@v4 - with: - repository: LedgerHQ/${{ matrix.repo }} - submodules: true - ref: ${{ matrix.branch }} - path: ${{ matrix.repo }}-${{ matrix.branch }} - - - name: Patch Cargo.toml - continue-on-error: false - run: | - cd ${{ matrix.repo }}-${{ matrix.branch }} - build_directory=$(ledger-manifest --output-build-directory ledger_app.toml) - cd $build_directory - - # Determine if the project is a workspace and get the workspace root path - if cargo metadata --no-deps --format-version 1 | jq -e '.workspace_members | length > 0' > /dev/null; then - echo "Workspace detected. Retrieving workspace root path." - workspace_root=$(cargo metadata --no-deps --format-version 1 | jq -r '.workspace_root') - cargo_toml_path="$workspace_root/Cargo.toml" - else - echo "No workspace detected. Using Cargo.toml in the current directory." - cargo_toml_path="$(pwd)/Cargo.toml" - fi - - # Patch ledger_device_sdk - if grep -Fxq "[patch.crates-io.ledger_device_sdk]" $cargo_toml_path; then - echo "The patch already exists in the file." - exit 1 - else - echo "" >> $cargo_toml_path - echo "[patch.crates-io.ledger_device_sdk]" >> $cargo_toml_path - path=\"$GITHUB_WORKSPACE/sdk/ledger_device_sdk\" - echo "path=$path" >> $cargo_toml_path - echo "Patch added to Cargo.toml" - fi - # Patch ledger_secure_sdk_sys - if grep -Fxq "[patch.crates-io.ledger_secure_sdk_sys]" $cargo_toml_path; then - echo "The patch already exists in the file." - exit 1 - else - echo "" >> $cargo_toml_path - echo "[patch.crates-io.ledger_secure_sdk_sys]" >> $cargo_toml_path - path=\"$GITHUB_WORKSPACE/sdk/ledger_secure_sdk_sys\" - echo "path=$path" >> $cargo_toml_path - echo "Patch added to Cargo.toml" - fi - - - name: Build - run: | - cd ${{ matrix.repo }}-${{ matrix.branch }} - build_directory=$(ledger-manifest --output-build-directory ledger_app.toml) - devices="$(ledger-manifest --output-devices ledger_app.toml -j | sed 's/+/plus/' | jq -rc '.devices[]')" - cd $build_directory - for device in $devices; do - # Required as patch has a different version from what is locked in Cargo.lock - cargo +$RUST_NIGHTLY update ledger_device_sdk - cargo +$RUST_NIGHTLY update ledger_secure_sdk_sys - echo "Build for "$device - cargo ledger build $device - done diff --git a/.github/workflows/build_with_current_nightly.yml b/.github/workflows/build_with_current_nightly.yml index 7a829ae5..8d96a86c 100644 --- a/.github/workflows/build_with_current_nightly.yml +++ b/.github/workflows/build_with_current_nightly.yml @@ -32,7 +32,6 @@ jobs: BUILD_DEVICE_NAME="$(echo ${{ matrix.device }})" BIN_DIR_NAME="$(echo ${{ matrix.device }} | sed 's/nanosplus/nanos2/')" cd app-boilerplate - RUST_NIGHTLY=nightly cargo ledger build ${{ matrix.device }} #- name: Upload binary artifacts diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index afba35fe..ccdb7aa0 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -21,31 +21,15 @@ jobs: image: ghcr.io/ledgerhq/ledger-app-builder/ledger-app-dev-tools:latest strategy: matrix: - target: ["nanos", "nanox", "nanosplus", "stax", "flex"] + target: ["nanox", "nanosplus", "stax", "flex"] package: [include_gif, testmacro, ledger_secure_sdk_sys, ledger_device_sdk] steps: - - name: Print Environment variables - run: - echo "The value of RUST_NIGHTLY is $RUST_NIGHTLY" - name: Clone uses: actions/checkout@v4 - name: Cargo clippy working-directory: ${{ matrix.package }} run: | - cargo +$RUST_NIGHTLY clippy --target ${{ matrix.target }} - - clippy-cargo-ledger: - name: Run static analysis for cargo-ledger - runs-on: ubuntu-latest - container: - image: ghcr.io/ledgerhq/ledger-app-builder/ledger-app-dev-tools:latest - steps: - - name: Clone - uses: actions/checkout@v4 - - name: Cargo clippy for cargo-ledger - working-directory: cargo-ledger - run: | - cargo +$RUST_STABLE clippy --no-deps + cargo clippy --target ${{ matrix.target }} format: name: Check code formatting @@ -57,7 +41,7 @@ jobs: uses: actions/checkout@v4 - name: Run cargo fmt run: | - cargo +$RUST_NIGHTLY fmt --all --check + cargo fmt --all --check build: name: Build SDK @@ -66,27 +50,14 @@ jobs: image: ghcr.io/ledgerhq/ledger-app-builder/ledger-app-dev-tools:latest strategy: matrix: - target: ["nanos", "nanox", "nanosplus", "stax", "flex"] + target: ["nanox", "nanosplus", "stax", "flex"] steps: - name: Clone uses: actions/checkout@v4 - name: Cargo build working-directory: ledger_device_sdk run: | - cargo +$RUST_NIGHTLY build --target ${{ matrix.target }} - - build-cargo-ledger: - name: Build SDK - runs-on: ubuntu-latest - container: - image: ghcr.io/ledgerhq/ledger-app-builder/ledger-app-dev-tools:latest - steps: - - name: Clone - uses: actions/checkout@v4 - - name: Cargo build - working-directory: cargo-ledger - run: | - cargo +$RUST_STABLE build + cargo build --target ${{ matrix.target }} test: name: Run unit and integration tests @@ -95,11 +66,11 @@ jobs: image: ghcr.io/ledgerhq/ledger-app-builder/ledger-app-dev-tools:latest strategy: matrix: - target: ["nanos", "nanox", "nanosplus", "stax", "flex"] + target: ["nanox", "nanosplus", "stax", "flex"] steps: - name: Clone uses: actions/checkout@v4 - name: Unit tests working-directory: ledger_device_sdk run: | - cargo +$RUST_NIGHTLY test --target ${{ matrix.target }} --features speculos --tests + cargo test --target ${{ matrix.target }} --features speculos --tests diff --git a/.github/workflows/get_rust_apps.py b/.github/workflows/get_rust_apps.py new file mode 100644 index 00000000..245ceb0a --- /dev/null +++ b/.github/workflows/get_rust_apps.py @@ -0,0 +1,41 @@ +from ledgered.github import GitHubLedgerHQ, NoManifestException, Condition +from github.GithubException import GithubException + +import sys +import json + +if len(sys.argv) != 2: + print("Usage: get_rust_apps.py ") + sys.exit(1) + +# Excluded Rust apps +# app-kadena-legacy: has been replaced by app-kadena +# app-pocket: does not build (Obsidians' Alamgu issue) +# app-age: not maintained anymore +excluded_apps = ["app-kadena-legacy", "app-pocket", "app-age"] + +# Retrieve all public apps on LedgerHQ GitHub organization +token = sys.argv[1] +gh = GitHubLedgerHQ(token) +apps=gh.apps.filter(private=Condition.WITHOUT, archived=Condition.WITHOUT) + +rust_apps = [] +exclude_apps = [] +# loop all apps in gh.apps +for app in apps: + try: + manifest = app.manifest + except NoManifestException as e: + pass + except GithubException as e: + pass + else: + # Filter out apps that are Rust based + if manifest.app.sdk == "rust": + if app.name not in excluded_apps: + for d in manifest.app.devices: + rust_apps.append({"app-name": app.name, "device": d}) + +# save the list of (apps, device) pairs to build in a json format: +with open("rust_apps.json", "w") as f: + f.write(json.dumps(rust_apps)) \ No newline at end of file diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index a0270190..dd9a4728 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -2,12 +2,12 @@ name: Publish to Crates.io on: push: - tags: - - '*@*.*.*' # Match tags like 'package1@1.2.3' + branches: + - master workflow_dispatch: # Allow manual workflow dispatch jobs: - test-dry-run: + dry-run-publish: runs-on: ubuntu-latest if: github.event_name == 'workflow_dispatch' # Only run this job for manual triggers @@ -21,33 +21,31 @@ jobs: profile: minimal toolchain: stable - - name: Retrieve Package Names from workspace root - id: get-root-packages - run: | - # Retrieve package names from the workspace root - PACKAGE_NAMES=$(cargo metadata --format-version=1 --no-deps | jq -r '.packages[].name' | tr '\n' ' ') - - # Set the package names as an output - echo "Package names from root Cargo.toml: $PACKAGE_NAMES" - echo "::set-output name=package-names::$PACKAGE_NAMES" - shell: bash - working-directory: ${{ github.workspace }} - - name: Test Dry-Run Publish for Each Package run: | # Iterate through package names retrieved - PACKAGE_NAMES="${{ steps.get-root-packages.outputs.package-names }}" + PACKAGE_NAMES="testmacro include_gif ledger_secure_sdk_sys ledger_device_sdk" for PACKAGE_NAME in $PACKAGE_NAMES; do - # Test a dry-run publish for each package within the workspace - cargo publish --dry-run --no-verify --token ${{ secrets.CARGO_REGISTRY_TOKEN }} --package "$PACKAGE_NAME" + # Test a dry-run publish for each package within the workspace if required + last_published_version=$(cargo search -q --limit 1 $PACKAGE_NAME | grep -oP '\d+\.\d+\.\d+') + echo "Published version of $PACKAGE_NAME is $version_published" + manifest_version=$(cargo metadata --format-version=1 --no-deps | jq -r --arg PACKAGE_NAME "$PACKAGE_NAME" '.packages[] | select(.name == $PACKAGE_NAME) | .version') + echo "Current version in manifest for $PACKAGE_NAME is $manifest_version" + if [ "$last_published_version" == "$manifest_version" ]; then + echo "Package $PACKAGE_NAME is already published with version $manifest_version." + else + echo "Package $PACKAGE_NAME is not published with version $manifest_version." + echo "Dry-run publishing $PACKAGE_NAME..." + cargo publish --dry-run --no-verify --token ${{ secrets.CARGO_REGISTRY_TOKEN }} --package "$PACKAGE_NAME" + fi done env: CARGO_TERM_COLOR: always working-directory: ${{ github.workspace }} - build-and-publish: + crates-io-publish: runs-on: ubuntu-latest - if: github.event_name == 'push' # Only run this job for tag pushes + if: github.event_name == 'push' # Only run this job for pushes steps: - name: Checkout Code @@ -58,48 +56,25 @@ jobs: with: profile: minimal toolchain: stable - - - name: Determine Package to Publish - id: determine-package - run: | - # Extract package name from the tag name - TAG_NAME="${{ github.ref }}" - PACKAGE_NAME=$(echo "$TAG_NAME" | cut -d'/' -f3 | cut -d'@' -f1) - - PACKAGE_NAMES=$(cargo metadata --format-version=1 --no-deps | jq -r '.packages[].name' | tr '\n' ' ') - - # Check if the extracted package name is a valid package in the workspace root Cargo.toml - if [[ ! " $PACKAGE_NAMES " =~ " $PACKAGE_NAME " ]]; then - echo "Invalid package name: $PACKAGE_NAME" - exit 1 - fi - echo "Package to publish: $PACKAGE_NAME" - echo "::set-output name=package::$PACKAGE_NAME" - shell: bash - working-directory: ${{ github.workspace }} - - - name: Check Package Version - id: check-version - run: | - PACKAGE_NAME="${{ steps.determine-package.outputs.package }}" - TAG_VERSION=$(echo "${{ github.ref }}" | cut -d'@' -f2) - MANIFEST_VERSION=$(cargo metadata --format-version=1 --no-deps | jq -r --arg PACKAGE_NAME "$PACKAGE_NAME" '.packages[] | select(.name == $PACKAGE_NAME) | .version') - - if [ "$TAG_VERSION" != "$MANIFEST_VERSION" ]; then - echo "Package version in manifest $MANIFEST_VERSION does not match tag version $TAG_VERSION." - exit 1 - else - echo "Package version in manifest matches tag version." - fi - shell: bash - working-directory: ${{ github.workspace }} - - - name: Build and Publish + + - name: Publish Package on crates.io if required run: | - PACKAGE_NAME="${{ steps.determine-package.outputs.package }}" - - # Publish the specified package within the workspace to crates.io - cargo publish --no-verify --token ${{ secrets.CARGO_REGISTRY_TOKEN }} --package "$PACKAGE_NAME" + # Iterate through package names retrieved + PACKAGE_NAMES="testmacro include_gif ledger_secure_sdk_sys ledger_device_sdk" + for PACKAGE_NAME in $PACKAGE_NAMES; do + # Publish each package within the workspace if required + last_published_version=$(cargo search -q --limit 1 $PACKAGE_NAME | grep -oP '\d+\.\d+\.\d+') + echo "Published version of $PACKAGE_NAME is $last_published_version" + manifest_version=$(cargo metadata --format-version=1 --no-deps | jq -r --arg PACKAGE_NAME "$PACKAGE_NAME" '.packages[] | select(.name == $PACKAGE_NAME) | .version') + echo "Current version in manifest for $PACKAGE_NAME is $manifest_version" + if [ "$last_published_version" == "$manifest_version" ]; then + echo "Package $PACKAGE_NAME is already published with version $manifest_version." + else + echo "Package $PACKAGE_NAME with version $manifest_version is not published." + echo "Publishing $PACKAGE_NAME..." + cargo publish --no-verify --token ${{ secrets.CARGO_REGISTRY_TOKEN }} --package "$PACKAGE_NAME" + fi + done env: CARGO_TERM_COLOR: always working-directory: ${{ github.workspace }} diff --git a/.github/workflows/reusable_build_all_apps.yml b/.github/workflows/reusable_build_all_apps.yml new file mode 100644 index 00000000..97c240a4 --- /dev/null +++ b/.github/workflows/reusable_build_all_apps.yml @@ -0,0 +1,147 @@ +name: Build all Rust apps + +on: + workflow_call: + inputs: + c_sdk_branch: + required: false + default: '' + type: string + workflow_dispatch: + pull_request: + +env: + C_SDK_URL: 'https://github.com/LedgerHQ/ledger-secure-sdk.git' + +jobs: + how-workflow-is-called: + name: Determine how the workflow is called + runs-on: ubuntu-latest + outputs: + repository: ${{ steps.get_repo_and_branch.outputs.repo }} + branch: ${{ steps.get_repo_and_branch.outputs.branch }} + steps: + - name: Get repository and branch + id: get_repo_and_branch + run: | + if [ -n "${{ inputs.c_sdk_branch }}" ]; then + echo "repo=LedgerHQ/ledger-device-rust-sdk" >> $GITHUB_OUTPUT + echo "branch=master" >> $GITHUB_OUTPUT + else + echo "repo=${{ github.repository}}" >> $GITHUB_OUTPUT + echo "branch=${{ github.ref }}" >> $GITHUB_OUTPUT + fi + retrieve-rust-apps: + name: Retrieve Rust Apps + runs-on: ubuntu-latest + needs: how-workflow-is-called + outputs: + rust_apps: ${{ steps.get_rust_apps.outputs.rust_apps }} + steps: + - name: Checkout repository + uses: actions/checkout@v4 + with: + repository: ${{ needs.how-workflow-is-called.outputs.repository }} + ref: ${{ needs.how-workflow-is-called.outputs.branch }} + - name: Set up Python + uses: actions/setup-python@v4 + with: + python-version: '3.x' + - name: Install ledgered + run: pip install ledgered + - name: Get all rust apps + id: get_rust_apps + run: | + python .github/workflows/get_rust_apps.py ${{ secrets.GITHUB_TOKEN }} + echo "rust_apps=$(cat rust_apps.json)" >> $GITHUB_OUTPUT + + display-rust-apps: + name: Display Rust Apps + runs-on: ubuntu-latest + needs: retrieve-rust-apps + steps: + - name: Display Rust Apps + run: | + echo "Rust apps: ${{ needs.retrieve-rust-apps.outputs.rust_apps }}" + + test-build: + name: Build for all targets + needs: [retrieve-rust-apps, how-workflow-is-called] + strategy: + fail-fast: false + matrix: + app-name: ["app-boilerplate-rust"] + device: ["nanos+", "nanox", "stax", "flex"] + include: ${{ fromJSON(needs.retrieve-rust-apps.outputs.rust_apps) }} + runs-on: ubuntu-latest + container: + image: ghcr.io/ledgerhq/ledger-app-builder/ledger-app-builder:latest + steps: + - name: Install ledgered + run: pip install ledgered --break-system-packages + - name: Clone SDK + uses: actions/checkout@v4 + with: + path: sdk + repository: ${{ needs.how-workflow-is-called.outputs.repository }} + ref: ${{ needs.how-workflow-is-called.outputs.branch }} + - name: Clone App + uses: actions/checkout@v4 + with: + repository: LedgerHQ/${{ matrix.app-name }} + submodules: true + path: ${{ matrix.app-name }} + - name: Patch Cargo.toml + continue-on-error: false + run: | + cd ${{ matrix.app-name }} + build_directory=$(ledger-manifest --output-build-directory ledger_app.toml) + cd $build_directory + workspace_root=$(cargo metadata --no-deps --format-version 1 | jq -r '.workspace_root') + cargo_toml_path="$workspace_root/Cargo.toml" + + # Patch ledger_device_sdk + echo "" >> $cargo_toml_path + echo "[patch.crates-io.ledger_device_sdk]" >> $cargo_toml_path + path=\"$GITHUB_WORKSPACE/sdk/ledger_device_sdk\" + echo "path=$path" >> $cargo_toml_path + echo "Patch added to Cargo.toml" + + # Patch ledger_secure_sdk_sys + echo "" >> $cargo_toml_path + echo "[patch.crates-io.ledger_secure_sdk_sys]" >> $cargo_toml_path + path=\"$GITHUB_WORKSPACE/sdk/ledger_secure_sdk_sys\" + echo "path=$path" >> $cargo_toml_path + echo "Patch added to Cargo.toml" + + # Patch include_gif + echo "" >> $cargo_toml_path + echo "[patch.crates-io.include_gif]" >> $cargo_toml_path + path=\"$GITHUB_WORKSPACE/sdk/include_gif\" + echo "path=$path" >> $cargo_toml_path + echo "Patch added to Cargo.toml" + + # Print Cargo.toml + echo "Cargo.toml:" + cat $cargo_toml_path + + - name: Build + run: | + # Clone C SDK if provided + if [ -n "${{ inputs.c_sdk_branch }}" ]; then + git clone $C_SDK_URL --branch ${{ inputs.c_sdk_branch }} --single-branch c_sdk + echo "setting LEDGER_SDK_PATH to $(realpath c_sdk)" + LEDGER_SDK_PATH=$(realpath c_sdk) + else + echo "using C SDK from ledger-app-builder" + fi + cd ${{ matrix.app-name }} + build_directory=$(ledger-manifest --output-build-directory ledger_app.toml) + cd $build_directory + # Required as patch has a different version from what is locked in Cargo.lock + cargo update include_gif + cargo update ledger_secure_sdk_sys + cargo update ledger_device_sdk + device=$(echo ${{ matrix.device }} | sed 's/+/plus/') + echo "Build for "$device + cargo ledger build $device diff --git a/Cargo.lock b/Cargo.lock index 29ba1cc9..1a176b89 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1,6 +1,6 @@ # This file is automatically @generated by Cargo. # It is not intended for manual editing. -version = 3 +version = 4 [[package]] name = "adler" @@ -17,55 +17,6 @@ dependencies = [ "memchr", ] -[[package]] -name = "anstream" -version = "0.6.14" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "418c75fa768af9c03be99d17643f93f79bbba589895012a80e3452a19ddda15b" -dependencies = [ - "anstyle", - "anstyle-parse", - "anstyle-query", - "anstyle-wincon", - "colorchoice", - "is_terminal_polyfill", - "utf8parse", -] - -[[package]] -name = "anstyle" -version = "1.0.7" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "038dfcf04a5feb68e9c60b21c9625a54c2c0616e79b72b0fd87075a056ae1d1b" - -[[package]] -name = "anstyle-parse" -version = "0.2.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c03a11a9034d92058ceb6ee011ce58af4a9bf61491aa7e1e59ecd24bd40d22d4" -dependencies = [ - "utf8parse", -] - -[[package]] -name = "anstyle-query" -version = "1.0.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a64c907d4e79225ac72e2a354c9ce84d50ebb4586dee56c82b3ee73004f537f5" -dependencies = [ - "windows-sys", -] - -[[package]] -name = "anstyle-wincon" -version = "3.0.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "61a38449feb7068f52bb06c12759005cf459ee52bb4adc1d5a7c4322d716fb19" -dependencies = [ - "anstyle", - "windows-sys", -] - [[package]] name = "autocfg" version = "1.3.0" @@ -125,29 +76,6 @@ version = "1.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1fd0f2584146f6f2ef48085050886acf353beff7305ebd1ae69500e27c67f64b" -[[package]] -name = "cargo-ledger" -version = "1.5.1" -dependencies = [ - "cargo_metadata", - "clap", - "goblin", - "serde", - "serde_derive", - "serde_json", -] - -[[package]] -name = "cargo_metadata" -version = "0.11.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a3a567c24b86754d629addc2db89e340ac9398d07b5875efcff837e3878e17ec" -dependencies = [ - "semver", - "serde", - "serde_json", -] - [[package]] name = "cc" version = "1.0.98" @@ -180,58 +108,12 @@ dependencies = [ "libloading", ] -[[package]] -name = "clap" -version = "4.5.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "90bc066a67923782aa8515dbaea16946c5bcc5addbd668bb80af688e53e548a0" -dependencies = [ - "clap_builder", - "clap_derive", -] - -[[package]] -name = "clap_builder" -version = "4.5.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ae129e2e766ae0ec03484e609954119f123cc1fe650337e155d03b022f24f7b4" -dependencies = [ - "anstream", - "anstyle", - "clap_lex", - "strsim", -] - -[[package]] -name = "clap_derive" -version = "4.5.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "528131438037fd55894f62d6e9f068b8f45ac57ffa77517819645d10aed04f64" -dependencies = [ - "heck", - "proc-macro2", - "quote", - "syn 2.0.66", -] - -[[package]] -name = "clap_lex" -version = "0.7.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "98cc8fbded0c607b7ba9dd60cd98df59af97e84d24e49c8557331cfc26d301ce" - [[package]] name = "color_quant" version = "1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3d7b894f5411737b7867f4827955924d7c254fc9f4d91a6aad6b097804b1018b" -[[package]] -name = "colorchoice" -version = "1.0.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0b6a852b24ab71dffc585bcb46eaf7959d175cb865a7152e35b348d1b2960422" - [[package]] name = "const-zero" version = "0.1.1" @@ -370,17 +252,6 @@ version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d2fabcfbdc87f4758337ca535fb41a6d701b65693ce38287d856d1674551ec9b" -[[package]] -name = "goblin" -version = "0.2.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d20fd25aa456527ce4f544271ae4fea65d2eda4a6561ea56f39fb3ee4f7e3884" -dependencies = [ - "log", - "plain", - "scroll", -] - [[package]] name = "half" version = "2.4.1" @@ -391,12 +262,6 @@ dependencies = [ "crunchy", ] -[[package]] -name = "heck" -version = "0.5.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2304e00983f87ffb38b55b444b5e3b60a884b5d30c0fca7d82fe33449bbe55ea" - [[package]] name = "home" version = "0.5.9" @@ -433,18 +298,6 @@ dependencies = [ "syn 1.0.109", ] -[[package]] -name = "is_terminal_polyfill" -version = "1.70.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f8478577c03552c21db0e2724ffb8986a5ce7af88107e6be5d2ee6e158c12800" - -[[package]] -name = "itoa" -version = "1.0.11" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "49f1f14873335454500d59611f1cf4a4b0f786f9ac11f4312a78e4cf2566695b" - [[package]] name = "jpeg-decoder" version = "0.3.1" @@ -474,7 +327,7 @@ checksum = "03087c2bad5e1034e8cace5926dec053fb3790248370865f5117a7d0213354c8" [[package]] name = "ledger_device_sdk" -version = "1.18.4" +version = "1.22.8" dependencies = [ "const-zero", "include_gif", @@ -489,7 +342,7 @@ dependencies = [ [[package]] name = "ledger_secure_sdk_sys" -version = "1.5.3" +version = "1.8.2" dependencies = [ "bindgen", "cc", @@ -601,12 +454,6 @@ version = "0.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "19b17cddbe7ec3f8bc800887bab5e717348c95ea2ca0b1bf0837fb964dc67099" -[[package]] -name = "plain" -version = "0.2.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b4596b6d070b27117e987119b4dac604f3c58cfb0b191112e24771b2faeac1a6" - [[package]] name = "png" version = "0.17.13" @@ -731,85 +578,12 @@ dependencies = [ "windows-sys", ] -[[package]] -name = "ryu" -version = "1.0.18" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f3cb5ba0dc43242ce17de99c180e96db90b235b8a9fdc9543c96d2209116bd9f" - [[package]] name = "scopeguard" version = "1.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "94143f37725109f92c262ed2cf5e59bce7498c01bcc1502d7b9afe439a4e9f49" -[[package]] -name = "scroll" -version = "0.10.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fda28d4b4830b807a8b43f7b0e6b5df875311b3e7621d84577188c175b6ec1ec" -dependencies = [ - "scroll_derive", -] - -[[package]] -name = "scroll_derive" -version = "0.10.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "aaaae8f38bb311444cfb7f1979af0bc9240d95795f75f9ceddf6a59b79ceffa0" -dependencies = [ - "proc-macro2", - "quote", - "syn 1.0.109", -] - -[[package]] -name = "semver" -version = "0.10.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "394cec28fa623e00903caf7ba4fa6fb9a0e260280bb8cdbbba029611108a0190" -dependencies = [ - "semver-parser", - "serde", -] - -[[package]] -name = "semver-parser" -version = "0.7.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "388a1df253eca08550bef6c72392cfe7c30914bf41df5269b68cbd6ff8f570a3" - -[[package]] -name = "serde" -version = "1.0.203" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7253ab4de971e72fb7be983802300c30b5a7f0c2e56fab8abfc6a214307c0094" -dependencies = [ - "serde_derive", -] - -[[package]] -name = "serde_derive" -version = "1.0.203" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "500cbc0ebeb6f46627f50f3f5811ccf6bf00643be300b4c3eabc0ef55dc5b5ba" -dependencies = [ - "proc-macro2", - "quote", - "syn 2.0.66", -] - -[[package]] -name = "serde_json" -version = "1.0.117" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "455182ea6142b14f93f4bc5320a2b31c1f266b66a4a5c858b013302a5d8cbfc3" -dependencies = [ - "itoa", - "ryu", - "serde", -] - [[package]] name = "shlex" version = "1.3.0" @@ -837,12 +611,6 @@ dependencies = [ "lock_api", ] -[[package]] -name = "strsim" -version = "0.11.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7da8b5736845d9f2fcb837ea5d9e2628564b3b043a70948a3f0b778838c5fb4f" - [[package]] name = "syn" version = "1.0.109" @@ -890,12 +658,6 @@ version = "1.0.12" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3354b9ac3fae1ff6755cb6db53683adb661634f67557942dea4facebec0fee4b" -[[package]] -name = "utf8parse" -version = "0.2.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "711b9620af191e0cdc7468a8d14e709c3dcdb115b36f838e601583af800a370a" - [[package]] name = "weezl" version = "0.1.8" diff --git a/Cargo.toml b/Cargo.toml index 0eb9c9cb..a5006acc 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -3,8 +3,7 @@ members = [ "ledger_device_sdk", "ledger_secure_sdk_sys", "include_gif", - "testmacro", - "cargo-ledger" + "testmacro" ] resolver = "2" diff --git a/README.md b/README.md index f520eff2..0a920c45 100644 --- a/README.md +++ b/README.md @@ -1,8 +1,36 @@ # Ledger Device Rust SDK -This workspace contains the 5 crates members of Ledger Device Rust SDK +[![DEV SUPPORT](https://img.shields.io/badge/Dev_Support-red?logo=discord +)](https://discord.com/channels/885256081289379850/912241185677000704) -* [ledger_device_sdk](./ledger_device_sdk): main Rust SDK crate used to build an application that runs on BOLOS OS, -* [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 -* [testmacro](./testmacro): procedural macro used by unit and integrations tests -* [cargo-ledger](./cargo-ledger): tool to build Ledger device applications developped in Rust +## Crates + +| Crate | Description | Latest Release | +| ------------------------------------------------ | --------------------------------------------------------------- | -------------- | +| [cargo-ledger](./cargo-ledger) | Cargo extension required to build Ledger applications | ![Dynamic TOML Badge](https://img.shields.io/badge/dynamic/toml?url=https%3A%2F%2Fraw.githubusercontent.com%2FLedgerHQ%2Fledger-device-rust-sdk%2Frefs%2Fheads%2Fmaster%2Fcargo-ledger%2FCargo.toml&query=%24.package.version&label=version) | +| [ledger_device_sdk](./ledger_device_sdk) | Rust SDK | ![Dynamic TOML Badge](https://img.shields.io/badge/dynamic/toml?url=https%3A%2F%2Fraw.githubusercontent.com%2FLedgerHQ%2Fledger-device-rust-sdk%2Frefs%2Fheads%2Fmaster%2Fledger_device_sdk%2FCargo.toml&query=%24.package.version&label=version) | +| [ledger_secure_sdk_sys](./ledger_secure_sdk_sys) | [C SDK](https://github.com/LedgerHQ/ledger-secure-sdk) bindings | ![Dynamic TOML Badge](https://img.shields.io/badge/dynamic/toml?url=https%3A%2F%2Fraw.githubusercontent.com%2FLedgerHQ%2Fledger-device-rust-sdk%2Frefs%2Fheads%2Fmaster%2Fledger_secure_sdk_sys%2FCargo.toml&query=%24.package.version&label=version) | +| [include_gif](./include_gif) | Procedural macro to integrate logo in the UI/UX | ![Dynamic TOML Badge](https://img.shields.io/badge/dynamic/toml?url=https%3A%2F%2Fraw.githubusercontent.com%2FLedgerHQ%2Fledger-device-rust-sdk%2Frefs%2Fheads%2Fmaster%2Finclude_gif%2FCargo.toml&query=%24.package.version&label=version) | +| [testmacro](./testmacro) | Procedural macro used by unit and integrations tests | ![Dynamic TOML Badge](https://img.shields.io/badge/dynamic/toml?url=https%3A%2F%2Fraw.githubusercontent.com%2FLedgerHQ%2Fledger-device-rust-sdk%2Frefs%2Fheads%2Fmaster%2Ftestmacro%2FCargo.toml&query=%24.package.version&label=version) | + +## Docker builder + +Docker images are available and shall be used to build and test Rust applications for Ledger devices. + +||`full` | `dev-tools` | +| ---- | ----- | ----------- | +| Rust nightly-2024-12-01 toolchain | :white_check_mark: | :white_check_mark: | +| cargo-ledger | :white_check_mark: | :white_check_mark: | +| Rust Ledger devices custom targets | :white_check_mark: | :white_check_mark: | +| ARM & LLVM toolchains | :white_check_mark: | :white_check_mark: | +| [Speculos](https://github.com/LedgerHQ/speculos) | :x: | :white_check_mark: | +| [Ragger](https://github.com/LedgerHQ/ragger)  | :x: | :white_check_mark: | + +Please check [here](https://github.com/LedgerHQ/ledger-app-builder) for more details. + +## Links + +To learn more about using the SDK and what is required to publish an app on the Ledger Live app store, please don't hesitate to check the following resources: + +- 📚 [Developer's documentation](https://developers.ledger.com/) +- 🗣️ [Ledger's Discord server](https://discord.gg/Ledger) +- 📦 [Fully featured boilerplate app](https://github.com/LedgerHQ/app-boilerplate-rust) \ No newline at end of file diff --git a/cargo-ledger/.rustfmt.toml b/cargo-ledger/.rustfmt.toml deleted file mode 100644 index df99c691..00000000 --- a/cargo-ledger/.rustfmt.toml +++ /dev/null @@ -1 +0,0 @@ -max_width = 80 diff --git a/cargo-ledger/Cargo.toml b/cargo-ledger/Cargo.toml deleted file mode 100644 index 6ab648d0..00000000 --- a/cargo-ledger/Cargo.toml +++ /dev/null @@ -1,18 +0,0 @@ -[package] -name = "cargo-ledger" -version = "1.5.1" -authors = ["yhql", "agrojean-ledger"] -description = "Build and sideload Ledger devices apps" -categories = ["development-tools::cargo-plugins"] -repository = "https://github.com/LedgerHQ/cargo-ledger" -readme = "README.md" -license = "Apache-2.0" -edition = "2018" - -[dependencies] -cargo_metadata = "0.11.0" -clap = { version = "4.1.8", features = ["derive"] } -goblin = "0.2.3" -serde = "1.0" -serde_derive = "1.0" -serde_json = "1.0" diff --git a/cargo-ledger/LICENSE.md b/cargo-ledger/LICENSE.md deleted file mode 100644 index 8dada3ed..00000000 --- a/cargo-ledger/LICENSE.md +++ /dev/null @@ -1,201 +0,0 @@ - Apache License - Version 2.0, January 2004 - http://www.apache.org/licenses/ - - TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION - - 1. Definitions. - - "License" shall mean the terms and conditions for use, reproduction, - and distribution as defined by Sections 1 through 9 of this document. - - "Licensor" shall mean the copyright owner or entity authorized by - the copyright owner that is granting the License. - - "Legal Entity" shall mean the union of the acting entity and all - other entities that control, are controlled by, or are under common - control with that entity. For the purposes of this definition, - "control" means (i) the power, direct or indirect, to cause the - direction or management of such entity, whether by contract or - otherwise, or (ii) ownership of fifty percent (50%) or more of the - outstanding shares, or (iii) beneficial ownership of such entity. - - "You" (or "Your") shall mean an individual or Legal Entity - exercising permissions granted by this License. - - "Source" form shall mean the preferred form for making modifications, - including but not limited to software source code, documentation - source, and configuration files. - - "Object" form shall mean any form resulting from mechanical - transformation or translation of a Source form, including but - not limited to compiled object code, generated documentation, - and conversions to other media types. - - "Work" shall mean the work of authorship, whether in Source or - Object form, made available under the License, as indicated by a - copyright notice that is included in or attached to the work - (an example is provided in the Appendix below). - - "Derivative Works" shall mean any work, whether in Source or Object - form, that is based on (or derived from) the Work and for which the - editorial revisions, annotations, elaborations, or other modifications - represent, as a whole, an original work of authorship. For the purposes - of this License, Derivative Works shall not include works that remain - separable from, or merely link (or bind by name) to the interfaces of, - the Work and Derivative Works thereof. - - "Contribution" shall mean any work of authorship, including - the original version of the Work and any modifications or additions - to that Work or Derivative Works thereof, that is intentionally - submitted to Licensor for inclusion in the Work by the copyright owner - or by an individual or Legal Entity authorized to submit on behalf of - the copyright owner. For the purposes of this definition, "submitted" - means any form of electronic, verbal, or written communication sent - to the Licensor or its representatives, including but not limited to - communication on electronic mailing lists, source code control systems, - and issue tracking systems that are managed by, or on behalf of, the - Licensor for the purpose of discussing and improving the Work, but - excluding communication that is conspicuously marked or otherwise - designated in writing by the copyright owner as "Not a Contribution." - - "Contributor" shall mean Licensor and any individual or Legal Entity - on behalf of whom a Contribution has been received by Licensor and - subsequently incorporated within the Work. - - 2. Grant of Copyright License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - copyright license to reproduce, prepare Derivative Works of, - publicly display, publicly perform, sublicense, and distribute the - Work and such Derivative Works in Source or Object form. - - 3. Grant of Patent License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - (except as stated in this section) patent license to make, have made, - use, offer to sell, sell, import, and otherwise transfer the Work, - where such license applies only to those patent claims licensable - by such Contributor that are necessarily infringed by their - Contribution(s) alone or by combination of their Contribution(s) - with the Work to which such Contribution(s) was submitted. If You - institute patent litigation against any entity (including a - cross-claim or counterclaim in a lawsuit) alleging that the Work - or a Contribution incorporated within the Work constitutes direct - or contributory patent infringement, then any patent licenses - granted to You under this License for that Work shall terminate - as of the date such litigation is filed. - - 4. Redistribution. You may reproduce and distribute copies of the - Work or Derivative Works thereof in any medium, with or without - modifications, and in Source or Object form, provided that You - meet the following conditions: - - (a) You must give any other recipients of the Work or - Derivative Works a copy of this License; and - - (b) You must cause any modified files to carry prominent notices - stating that You changed the files; and - - (c) You must retain, in the Source form of any Derivative Works - that You distribute, all copyright, patent, trademark, and - attribution notices from the Source form of the Work, - excluding those notices that do not pertain to any part of - the Derivative Works; and - - (d) If the Work includes a "NOTICE" text file as part of its - distribution, then any Derivative Works that You distribute must - include a readable copy of the attribution notices contained - within such NOTICE file, excluding those notices that do not - pertain to any part of the Derivative Works, in at least one - of the following places: within a NOTICE text file distributed - as part of the Derivative Works; within the Source form or - documentation, if provided along with the Derivative Works; or, - within a display generated by the Derivative Works, if and - wherever such third-party notices normally appear. The contents - of the NOTICE file are for informational purposes only and - do not modify the License. You may add Your own attribution - notices within Derivative Works that You distribute, alongside - or as an addendum to the NOTICE text from the Work, provided - that such additional attribution notices cannot be construed - as modifying the License. - - You may add Your own copyright statement to Your modifications and - may provide additional or different license terms and conditions - for use, reproduction, or distribution of Your modifications, or - for any such Derivative Works as a whole, provided Your use, - reproduction, and distribution of the Work otherwise complies with - the conditions stated in this License. - - 5. Submission of Contributions. Unless You explicitly state otherwise, - any Contribution intentionally submitted for inclusion in the Work - by You to the Licensor shall be under the terms and conditions of - this License, without any additional terms or conditions. - Notwithstanding the above, nothing herein shall supersede or modify - the terms of any separate license agreement you may have executed - with Licensor regarding such Contributions. - - 6. Trademarks. This License does not grant permission to use the trade - names, trademarks, service marks, or product names of the Licensor, - except as required for reasonable and customary use in describing the - origin of the Work and reproducing the content of the NOTICE file. - - 7. Disclaimer of Warranty. Unless required by applicable law or - agreed to in writing, Licensor provides the Work (and each - Contributor provides its Contributions) on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or - implied, including, without limitation, any warranties or conditions - of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A - PARTICULAR PURPOSE. You are solely responsible for determining the - appropriateness of using or redistributing the Work and assume any - risks associated with Your exercise of permissions under this License. - - 8. Limitation of Liability. In no event and under no legal theory, - whether in tort (including negligence), contract, or otherwise, - unless required by applicable law (such as deliberate and grossly - negligent acts) or agreed to in writing, shall any Contributor be - liable to You for damages, including any direct, indirect, special, - incidental, or consequential damages of any character arising as a - result of this License or out of the use or inability to use the - Work (including but not limited to damages for loss of goodwill, - work stoppage, computer failure or malfunction, or any and all - other commercial damages or losses), even if such Contributor - has been advised of the possibility of such damages. - - 9. Accepting Warranty or Additional Liability. While redistributing - the Work or Derivative Works thereof, You may choose to offer, - and charge a fee for, acceptance of support, warranty, indemnity, - or other liability obligations and/or rights consistent with this - License. However, in accepting such obligations, You may act only - on Your own behalf and on Your sole responsibility, not on behalf - of any other Contributor, and only if You agree to indemnify, - defend, and hold each Contributor harmless for any liability - incurred by, or claims asserted against, such Contributor by reason - of your accepting any such warranty or additional liability. - - END OF TERMS AND CONDITIONS - - APPENDIX: How to apply the Apache License to your work. - - To apply the Apache License to your work, attach the following - boilerplate notice, with the fields enclosed by brackets "{}" - replaced with your own identifying information. (Don't include - the brackets!) The text should be enclosed in the appropriate - comment syntax for the file format. We also recommend that a - file or class name and description of purpose be included on the - same "printed page" as the copyright notice for easier - identification within third-party archives. - - Copyright {yyyy} {name of copyright owner} - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. diff --git a/cargo-ledger/README.md b/cargo-ledger/README.md deleted file mode 100644 index de09b020..00000000 --- a/cargo-ledger/README.md +++ /dev/null @@ -1,57 +0,0 @@ -# Cargo-ledger - -Builds a Nano App and outputs a JSON manifest file that can be used by [ledgerctl](https://github.com/LedgerHQ/ledgerctl) to install an application directly. - -In order to build for Nano S, Nano X, and Nano S Plus, [custom target files](https://docs.rust-embedded.org/embedonomicon/custom-target.html) are used. They can be found at the root of the [Rust SDK](https://github.com/LedgerHQ/ledger-nanos-sdk/) and can be installed automatically with the command `setup`. - -## Installation - -This program requires: - -- `arm-none-eabi-objcopy` -- [`ledgerctl`](https://github.com/LedgerHQ/ledgerctl) - -Install this repo with: - -``` -cargo install --git https://github.com/LedgerHQ/ledger-device-rust-sdk cargo-ledger -``` - -or download it manually and install with: - -``` -cargo install --path cargo-ledger -``` - -Note that `cargo`'s dependency resolver may behave differently when installing, and you may end up with errors. -In order to fix those and force usage of the versions specified in the tagged `Cargo.lock`, append `--locked` to the above commands. - -## Usage - -General usage is displayed when invoking `cargo ledger`. - -### Setup - -This will install custom target files from the SDK directly into your environment. - -``` -cargo ledger setup -``` - -### Building - -``` -cargo ledger build nanos -cargo ledger build nanox -cargo ledger build nanosplus -``` - -Loading on device can optionally be performed by appending `--load` or `-l` to the command. - -By default, this program will attempt to build the current program with in `release` mode (full command: `cargo build --release --target=nanos --message-format=json`) - -Arguments can be passed to modify this behaviour after inserting a `--` like so: - -``` -cargo ledger build nanos --load -- --features one -Z unstable-options --out-dir ./output/ -``` \ No newline at end of file diff --git a/cargo-ledger/src/main.rs b/cargo-ledger/src/main.rs deleted file mode 100644 index b6b97feb..00000000 --- a/cargo-ledger/src/main.rs +++ /dev/null @@ -1,424 +0,0 @@ -use std::fmt::{Display, Formatter}; -use std::fs; -use std::path::PathBuf; -use std::process::Command; -use std::process::Stdio; -use std::str::from_utf8; - -use cargo_metadata::{Message, Package}; -use clap::{Parser, Subcommand, ValueEnum}; -use serde_derive::Deserialize; -use serde_json::json; - -use setup::install_targets; -use utils::*; - -mod setup; -mod utils; - -/// Structure for retrocompatibility, when the cargo manifest file -/// contains a single `[package.metadata.nanos]` section -#[derive(Debug, Deserialize)] -struct NanosMetadata { - curve: Vec, - path: Vec, - flags: String, - icon: String, - icon_small: String, - name: Option, -} - -#[derive(Debug, Deserialize)] -struct LedgerMetadata { - curve: Vec, - path: Vec, - flags: String, - name: Option, -} - -#[derive(Debug, Deserialize)] -struct DeviceMetadata { - icon: String, -} - -#[derive(Parser, Debug)] -#[command(name = "cargo")] -#[command(bin_name = "cargo")] -#[clap(name = "Ledger devices build and load commands")] -#[clap(version = "0.0")] -#[clap(about = "Builds the project and emits a JSON manifest for ledgerctl.")] -enum Cli { - Ledger(CliArgs), -} - -#[derive(clap::Args, Debug)] -struct CliArgs { - #[clap(long)] - #[clap(value_name = "prebuilt ELF exe")] - use_prebuilt: Option, - - #[clap(subcommand)] - command: MainCommand, -} - -#[derive(ValueEnum, Clone, Copy, Debug, PartialEq)] -enum Device { - Nanos, - Nanox, - Nanosplus, - Stax, - Flex, -} - -impl Display for Device { - fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result { - f.write_str(self.as_ref()) - } -} - -impl AsRef for Device { - fn as_ref(&self) -> &str { - match self { - Device::Nanos => "nanos", - Device::Nanox => "nanox", - Device::Nanosplus => "nanosplus", - Device::Stax => "stax", - Device::Flex => "flex", - } - } -} - -#[derive(Subcommand, Debug)] -enum MainCommand { - #[clap(about = "install custom target files")] - Setup, - #[clap(about = "build the project for a given device")] - Build { - #[clap(value_enum)] - #[clap(help = "device to build for")] - device: Device, - #[clap(short, long)] - #[clap(help = "load on a device")] - load: bool, - #[clap(last = true)] - remaining_args: Vec, - }, -} - -fn main() { - let Cli::Ledger(cli) = Cli::parse(); - - match cli.command { - MainCommand::Setup => install_targets(), - MainCommand::Build { - device: d, - load: a, - remaining_args: r, - } => { - build_app(d, a, cli.use_prebuilt, r); - } - } -} - -fn retrieve_metadata( - device: Device, - manifest_path: Option<&str>, -) -> (Package, LedgerMetadata, DeviceMetadata) { - let mut cmd = cargo_metadata::MetadataCommand::new(); - - // Only used during tests - if let Some(manifestpath) = manifest_path { - cmd = cmd.manifest_path(manifestpath).clone(); - } - - let res = cmd - .no_deps() - .exec() - .expect("Could not execute `cargo metadata`"); - - let this_pkg = res.packages.last().unwrap(); - let metadata_section = this_pkg.metadata.get("ledger"); - - if let Some(metadatasection) = metadata_section { - let metadata_device = metadata_section - .unwrap() - .clone() - .get(device.as_ref()) - .unwrap() - .clone(); - - let ledger_metadata: LedgerMetadata = - serde_json::from_value(metadatasection.clone()) - .expect("Could not deserialize medatada.ledger"); - let device_metadata: DeviceMetadata = - serde_json::from_value(metadata_device) - .expect("Could not deserialize device medatada"); - - (this_pkg.clone(), ledger_metadata, device_metadata) - } else { - println!("WARNING: 'package.metadata.ledger' section is missing in Cargo.toml, trying 'package.metadata.nanos'"); - let nanos_section = this_pkg.metadata.get("nanos").expect( - "No appropriate [package.metadata.] section found.", - ); - - let nanos_metadata: NanosMetadata = - serde_json::from_value(nanos_section.clone()) - .expect("Could not deserialize medatada.nanos"); - let ledger_metadata = LedgerMetadata { - curve: nanos_metadata.curve, - path: nanos_metadata.path, - flags: nanos_metadata.flags, - name: nanos_metadata.name, - }; - - let device_metadata = DeviceMetadata { - icon: match device { - Device::Nanos => nanos_metadata.icon, - _ => nanos_metadata.icon_small, - }, - }; - - (this_pkg.clone(), ledger_metadata, device_metadata) - } -} - -fn build_app( - device: Device, - is_load: bool, - use_prebuilt: Option, - remaining_args: Vec, -) { - let exe_path = match use_prebuilt { - None => { - let c_sdk_path = match device { - Device::Nanos => std::env::var("NANOS_SDK"), - Device::Nanosplus => std::env::var("NANOSP_SDK"), - Device::Nanox => std::env::var("NANOX_SDK"), - Device::Stax => std::env::var("STAX_SDK"), - Device::Flex => std::env::var("FLEX_SDK"), - }; - - let mut args: Vec = vec![]; - match std::env::var("RUST_NIGHTLY") { - Ok(version) => { - println!("Use Rust nightly toolchain: {}", version); - args.push(format!("+{}", version)) - } - Err(_) => { - let rustup_cmd = - Command::new("rustup").arg("default").output().unwrap(); - println!( - "Use Rust default toolchain: {}", - from_utf8(rustup_cmd.stdout.as_slice()).unwrap() - ); - } - } - args.push(String::from("build")); - args.push(String::from("--release")); - args.push(format!("--target={}", device.as_ref())); - args.push(String::from( - "--message-format=json-diagnostic-rendered-ansi", - )); - - match std::env::var("LEDGER_SDK_PATH") { - Ok(_) => (), - Err(_) => match c_sdk_path { - Ok(path) => args.push(format!( - "--config=env.LEDGER_SDK_PATH=\"{}\"", - path - )), - Err(_) => println!("C SDK will have to be cloned"), - }, - } - - let mut cargo_cmd = Command::new("cargo") - .args(args) - .args(&remaining_args) - .stdout(Stdio::piped()) - .spawn() - .unwrap(); - - let mut exe_path = PathBuf::new(); - let out = cargo_cmd.stdout.take().unwrap(); - let reader = std::io::BufReader::new(out); - for message in Message::parse_stream(reader) { - match message.as_ref().unwrap() { - Message::CompilerArtifact(artifact) => { - if let Some(n) = &artifact.executable { - exe_path = n.to_path_buf(); - } - } - Message::CompilerMessage(message) => { - println!("{message}"); - } - _ => (), - } - } - - cargo_cmd.wait().expect("Couldn't get cargo's exit status"); - - exe_path - } - Some(prebuilt) => prebuilt.canonicalize().unwrap(), - }; - - let (this_pkg, metadata_ledger, metadata_device) = - retrieve_metadata(device, None); - - let package_path = this_pkg - .manifest_path - .parent() - .expect("Could not find package's parent path"); - - /* exe_path = "exe_parent" + "exe_name" */ - let exe_name = exe_path.file_name().unwrap(); - let exe_parent = exe_path.parent().unwrap(); - - let hex_file_abs = exe_path - .parent() - .unwrap() - .join(exe_name) - .with_extension("hex"); - - let hex_file = hex_file_abs.strip_prefix(exe_parent).unwrap(); - - export_binary(&exe_path, &hex_file_abs); - - // app.json will be placed next to hex file - let app_json_name = format!("app_{}.json", device.as_ref()); - let app_json = exe_parent.join(app_json_name); - - // Retrieve real data size and SDK infos from ELF - let infos = retrieve_infos(&exe_path).unwrap(); - - // Modify flags to enable BLE if targeting Nano X - let flags = match device { - Device::Nanos | Device::Nanosplus => metadata_ledger.flags, - Device::Nanox | Device::Stax | Device::Flex => { - let base = u32::from_str_radix(metadata_ledger.flags.as_str(), 16) - .unwrap_or(0); - format!("0x{:x}", base | 0x200) - } - }; - - // Target ID according to target, in case it - // is not present in the retrieved ELF infos. - let backup_targetid: String = match device { - Device::Nanos => String::from("0x31100004"), - Device::Nanox => String::from("0x33000004"), - Device::Nanosplus => String::from("0x33100004"), - Device::Stax => String::from("0x33200004"), - Device::Flex => String::from("0x33300004"), - }; - - // create manifest - let file = fs::File::create(&app_json).unwrap(); - let mut json = json!({ - "name": metadata_ledger.name.as_ref().unwrap_or(&this_pkg.name), - "version": &this_pkg.version, - "icon": metadata_device.icon, - "targetId": infos.target_id.unwrap_or(backup_targetid), - "flags": flags, - "derivationPath": { - "curves": metadata_ledger.curve, - "paths": metadata_ledger.path - }, - "binary": hex_file, - "dataSize": infos.size - }); - // Ignore apiLevel for Nano S as it is unsupported for now - match device { - Device::Nanos => (), - _ => { - json["apiLevel"] = infos.api_level.into(); - } - } - serde_json::to_writer_pretty(file, &json).unwrap(); - - // Copy icon to the same directory as the app.json - let icon_path = package_path.join(&metadata_device.icon); - let icon_dest = - exe_parent.join(&metadata_device.icon.split('/').last().unwrap()); - - fs::copy(icon_path, icon_dest).unwrap(); - - // Use ledgerctl to dump the APDU installation file. - // Either dump to the location provided by the --out-dir cargo - // argument if provided or use the default binary path. - let output_dir: Option = remaining_args - .iter() - .position(|arg| arg == "--out-dir" || arg.starts_with("--out-dir=")) - .and_then(|index| { - let out_dir_arg = &remaining_args[index]; - // Extracting the value from "--out-dir=" or "--out-dir " - if out_dir_arg.contains('=') { - Some(out_dir_arg.split('=').nth(1).unwrap().to_string()) - } else { - remaining_args - .get(index + 1) - .map(|path_str| path_str.to_string()) - } - }) - .map(PathBuf::from); - let exe_filename = exe_path.file_name().unwrap().to_str(); - let exe_parent = exe_path.parent().unwrap().to_path_buf(); - let apdu_file_path = output_dir - .unwrap_or(exe_parent) - .join(exe_filename.unwrap()) - .with_extension("apdu"); - dump_with_ledgerctl( - package_path, - &app_json, - apdu_file_path.to_str().unwrap(), - ); - - if is_load { - install_with_ledgerctl(package_path, &app_json); - } -} - -#[cfg(test)] -mod tests { - use super::*; - - #[test] - fn valid_metadata() { - let (_, metadata_ledger, metadata_nanos) = - retrieve_metadata(Device::Nanos, Some("./tests/valid/Cargo.toml")); - - assert_eq!(metadata_ledger.name, Some("TestApp".to_string())); - assert_eq!(metadata_ledger.curve, ["secp256k1"]); - assert_eq!(metadata_ledger.flags, "0x38"); - assert_eq!(metadata_ledger.path, ["'44/123"]); - - assert_eq!(metadata_nanos.icon, "./assets/nanos.gif") - } - - #[test] - fn valid_metadata_variant() { - let (_, metadata_ledger, metadata_nanos) = retrieve_metadata( - Device::Nanos, - Some("./tests/valid_variant/Cargo.toml"), - ); - - assert_eq!(metadata_ledger.name, Some("TestApp".to_string())); - assert_eq!(metadata_ledger.curve, ["secp256k1"]); - assert_eq!(metadata_ledger.flags, "0x38"); - assert_eq!(metadata_ledger.path, ["'44/123"]); - assert_eq!(metadata_nanos.icon, "./assets/nanos.gif") - } - - #[test] - fn valid_outdated_metadata() { - let (_, metadata_ledger, metadata_nanos) = retrieve_metadata( - Device::Nanos, - Some("./tests/valid_outdated/Cargo.toml"), - ); - - assert_eq!(metadata_ledger.name, Some("TestApp".to_string())); - assert_eq!(metadata_ledger.curve, ["secp256k1"]); - assert_eq!(metadata_ledger.flags, "0"); - assert_eq!(metadata_ledger.path, ["'44/123"]); - assert_eq!(metadata_nanos.icon, "nanos.gif") - } -} diff --git a/cargo-ledger/src/setup.rs b/cargo-ledger/src/setup.rs deleted file mode 100644 index 822f26d4..00000000 --- a/cargo-ledger/src/setup.rs +++ /dev/null @@ -1,76 +0,0 @@ -use std::path::Path; -use std::process::Command; - -pub fn install_targets() { - println!("[ ] Checking for installed custom targets..."); - // Check if target files are installed - let sysroot_cmd = Command::new("rustc") - .arg("--print") - .arg("sysroot") - .output() - .expect("failed to call rustc") - .stdout; - let sysroot_cmd = std::str::from_utf8(&sysroot_cmd).unwrap().trim(); - - let target_files_url = Path::new( - "https://raw.githubusercontent.com/LedgerHQ/ledger-device-rust-sdk/a7fb841160df34b8de268b136704c8b2ed8f9973/ledger_device_sdk/" - ); - let sysroot = Path::new(sysroot_cmd).join("lib").join("rustlib"); - - // Retrieve each target file independently - // TODO: handle target.json modified upstream - for target in &["nanos", "nanox", "nanosplus", "stax", "flex"] { - let outfilepath = sysroot.join(target).join("target.json"); - let targetpath = - outfilepath.clone().into_os_string().into_string().unwrap(); - println!("* Adding \x1b[1;32m{target}\x1b[0m in \x1b[1;33m{targetpath}\x1b[0m"); - - let target_url = target_files_url.join(format!("{target}.json")); - let cmd = Command::new("curl") - .arg(target_url) - .arg("-o") - .arg(outfilepath) - .arg("--create-dirs") - .output() - .expect("failed to execute 'curl'"); - println!("{}", std::str::from_utf8(&cmd.stderr).unwrap()); - } - - // Install link_wrap.sh script needed for relocation - println!("[ ] Install custom link script..."); - - /* Shall be put at the same place as rust-lld */ - let custom_link_script = "link_wrap.sh"; - - let cmd = Command::new("find") - .arg(sysroot_cmd) - .arg("-name") - .arg("rust-lld") - .output() - .expect("failed to find rust-lld linker") - .stdout; - - let rust_lld_path = std::str::from_utf8(&cmd).unwrap(); - let end = rust_lld_path.rfind('/').unwrap(); - - let outfilepath = - sysroot.join(&rust_lld_path[..end]).join(custom_link_script); - - /* Retrieve the linker script */ - let target_url = target_files_url.join(custom_link_script); - Command::new("curl") - .arg(target_url) - .arg("-o") - .arg(&outfilepath) - .output() - .expect("failed to execute 'curl'"); - - println!("* Custom link script is {}", outfilepath.display()); - - /* Make the linker script executable */ - Command::new("chmod") - .arg("+x") - .arg(outfilepath) - .output() - .expect("failed to execute chmod"); -} diff --git a/cargo-ledger/src/utils.rs b/cargo-ledger/src/utils.rs deleted file mode 100644 index de0f8609..00000000 --- a/cargo-ledger/src/utils.rs +++ /dev/null @@ -1,129 +0,0 @@ -use std::env; -use std::fs; -use std::io; -use std::io::Write; -use std::process::Command; - -#[derive(Default, Debug)] -pub struct LedgerAppInfos { - pub api_level: String, - pub target_id: Option, - pub size: u64, -} - -fn get_string_from_offset(vector: &[u8], offset: &usize) -> String { - // Find the end of the string (search for a line feed character) - let end_index = vector[*offset..] - .iter() - .position(|&x| x == b'\n') - .map(|pos| *offset + pos) - .unwrap_or(*offset); // Use the start offset if the delimiter position is not found - String::from_utf8(vector[*offset..end_index].to_vec()) - .expect("Invalid UTF-8") -} - -pub fn retrieve_infos( - file: &std::path::Path, -) -> Result { - let buffer = fs::read(file)?; - let elf = goblin::elf::Elf::parse(&buffer).unwrap(); - - let mut infos = LedgerAppInfos::default(); - - // All infos coming from the SDK are expected to be regrouped - // in various `.ledger.` (rust SDK <= 1.0.0) or - // `ledger. (rust SDK > 1.0.0) section of the binary. - for section in elf.section_headers.iter() { - if let Some(Ok(name)) = elf.shdr_strtab.get(section.sh_name) { - if name == "ledger.api_level" { - // For rust SDK > 1.0.0, the API level is stored as a string (like C SDK) - infos.api_level = get_string_from_offset( - &buffer, - &(section.sh_offset as usize), - ); - } else if name == ".ledger.api_level" { - // For rust SDK <= 1.0.0, the API level is stored as a byte - infos.api_level = - buffer[section.sh_offset as usize].to_string(); - } else if name == "ledger.target_id" { - infos.target_id = Some(get_string_from_offset( - &buffer, - &(section.sh_offset as usize), - )); - } - } - } - - let mut nvram_data = 0; - let mut envram_data = 0; - for s in elf.syms.iter() { - let symbol_name = elf.strtab.get(s.st_name); - let name = symbol_name.unwrap().unwrap(); - match name { - "_nvram_data" => nvram_data = s.st_value, - "_envram_data" => envram_data = s.st_value, - _ => (), - } - } - infos.size = envram_data - nvram_data; - Ok(infos) -} - -pub fn export_binary(elf_path: &std::path::Path, dest_bin: &std::path::Path) { - let objcopy = env::var_os("CARGO_TARGET_THUMBV6M_NONE_EABI_OBJCOPY") - .unwrap_or_else(|| "arm-none-eabi-objcopy".into()); - - Command::new(objcopy) - .arg(elf_path) - .arg(dest_bin) - .args(["-O", "ihex"]) - .output() - .expect("Objcopy failed"); - - let size = env::var_os("CARGO_TARGET_THUMBV6M_NONE_EABI_SIZE") - .unwrap_or_else(|| "arm-none-eabi-size".into()); - - // print some size info while we're here - let out = Command::new(size) - .arg(elf_path) - .output() - .expect("Size failed"); - - io::stdout().write_all(&out.stdout).unwrap(); - io::stderr().write_all(&out.stderr).unwrap(); -} - -pub fn install_with_ledgerctl( - dir: &std::path::Path, - app_json: &std::path::Path, -) { - let out = Command::new("ledgerctl") - .current_dir(dir) - .args(["install", "-f", app_json.to_str().unwrap()]) - .output() - .expect("fail"); - - io::stdout().write_all(&out.stdout).unwrap(); - io::stderr().write_all(&out.stderr).unwrap(); -} - -pub fn dump_with_ledgerctl( - dir: &std::path::Path, - app_json: &std::path::Path, - out_file_name: &str, -) { - let out = Command::new("ledgerctl") - .current_dir(dir) - .args([ - "install", - app_json.to_str().unwrap(), - "-o", - out_file_name, - "-f", - ]) - .output() - .expect("fail"); - - io::stdout().write_all(&out.stdout).unwrap(); - io::stderr().write_all(&out.stderr).unwrap(); -} diff --git a/cargo-ledger/tests/valid/Cargo.toml b/cargo-ledger/tests/valid/Cargo.toml deleted file mode 100644 index d75f2633..00000000 --- a/cargo-ledger/tests/valid/Cargo.toml +++ /dev/null @@ -1,22 +0,0 @@ -[package] -name = "test" -version = "0.0.0" - -[[bin]] -name = "test" -path = "" - -[package.metadata.ledger] -name = "TestApp" -curve = ["secp256k1"] -flags = "0x38" -path = ["'44/123"] - -[package.metadata.ledger.nanos] -icon = "./assets/nanos.gif" - -[package.metadata.ledger.nanox] -icon = "./assets/nanox.gif" - -[package.metadata.ledger.nanosplus] -icon = "./assets/nanosplus.gif" diff --git a/cargo-ledger/tests/valid_outdated/Cargo.toml b/cargo-ledger/tests/valid_outdated/Cargo.toml deleted file mode 100644 index f661fbb9..00000000 --- a/cargo-ledger/tests/valid_outdated/Cargo.toml +++ /dev/null @@ -1,16 +0,0 @@ -[package] -name = "test" -version = "0.0.0" - -[[bin]] -name = "test" -path = "" - -[package.metadata.nanos] -api_level = "1" -name = "TestApp" -curve = ["secp256k1"] -flags = "0" -icon = "nanos.gif" -icon_small = "nanox.gif" -path = ["'44/123"] diff --git a/cargo-ledger/tests/valid_variant/Cargo.toml b/cargo-ledger/tests/valid_variant/Cargo.toml deleted file mode 100644 index 1c0ff573..00000000 --- a/cargo-ledger/tests/valid_variant/Cargo.toml +++ /dev/null @@ -1,16 +0,0 @@ -[package] -name = "test" -version = "0.0.0" - -[[bin]] -name = "test" -path = "" - -[package.metadata.ledger] -name = "TestApp" -curve = ["secp256k1"] -flags = "0x38" -path = ["'44/123"] -nanos.icon = "./assets/nanos.gif" -nanox.icon = "./assets/nanox.gif" -nanosplus.icon = "./assets/nanosplus.gif" diff --git a/include_gif/README.md b/include_gif/README.md index f114e72a..2bda97f1 100644 --- a/include_gif/README.md +++ b/include_gif/README.md @@ -1,3 +1,4 @@ -# sdk_include_gif +# include_gif +![Dynamic TOML Badge](https://img.shields.io/badge/dynamic/toml?url=https%3A%2F%2Fraw.githubusercontent.com%2FLedgerHQ%2Fledger-device-rust-sdk%2Frefs%2Fheads%2Fmaster%2Finclude_gif%2FCargo.toml&query=%24.package.version&label=version) -This crate provides a macro `include_gif!("path/to/image.gif")` that packs a gif image into a byte representation that can be understood by the [Rust Nano SDK](https://github.com/LedgerHQ/ledger-device-rust-sdk/tree/master/ledger_device_sdk) and included at compile time to produce black-and-white icons. +This crate provides a macro `include_gif!("path/to/image.gif")` that packs a gif image into a byte representation that can be understood by the [Rust SDK](https://github.com/LedgerHQ/ledger-device-rust-sdk/tree/master/ledger_device_sdk) and included at compile time to produce icons. diff --git a/ledger_device_sdk/.cargo/config.toml b/ledger_device_sdk/.cargo/config.toml index bf0bd24b..8e953584 100644 --- a/ledger_device_sdk/.cargo/config.toml +++ b/ledger_device_sdk/.cargo/config.toml @@ -1,6 +1,3 @@ -[target.nanos] -runner = "speculos -m nanos --display=headless" - [target.nanox] runner = "speculos -m nanox --display=headless" @@ -11,11 +8,4 @@ runner = "speculos -m nanosp --display=headless" runner = "speculos --model stax --display=headless" [target.flex] -runner = "speculos --model flex --display=headless" - -[unstable] -build-std = ["core", "alloc"] -build-std-features = ["compiler-builtins-mem"] - -[build] -target = "stax" +runner = "speculos --model flex --display=headless" \ No newline at end of file diff --git a/ledger_device_sdk/Cargo.toml b/ledger_device_sdk/Cargo.toml index 40e04506..8fad5022 100644 --- a/ledger_device_sdk/Cargo.toml +++ b/ledger_device_sdk/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "ledger_device_sdk" -version = "1.18.4" +version = "1.22.8" authors = ["yhql", "yogh333", "agrojean-ledger", "kingofpayne"] edition = "2021" license.workspace = true @@ -21,11 +21,16 @@ rand_core = { version = "0.6.3", default-features = false } zeroize = { version = "1.6.0", default-features = false } numtoa = "0.2.4" const-zero = "0.1.1" -ledger_secure_sdk_sys = { path = "../ledger_secure_sdk_sys", version = "1.5.3" } +ledger_secure_sdk_sys = { path = "../ledger_secure_sdk_sys", version = "1.8.2" } [features] +debug = [] speculos = [] -ccid = [] heap = [ "ledger_secure_sdk_sys/heap" ] +nano_nbgl = [ "ledger_secure_sdk_sys/nano_nbgl" ] default = [ "heap" ] + +[lints.rust.unexpected_cfgs] +level = "warn" +check-cfg = ['cfg(target_os, values("stax", "flex", "nanox", "nanosplus"))'] diff --git a/ledger_device_sdk/README.md b/ledger_device_sdk/README.md index f5077e22..200cacae 100644 --- a/ledger_device_sdk/README.md +++ b/ledger_device_sdk/README.md @@ -1,4 +1,5 @@ -# Ledger wallets SDK for Rust Applications +# Ledger device SDK for Rust Applications +![Dynamic TOML Badge](https://img.shields.io/badge/dynamic/toml?url=https%3A%2F%2Fraw.githubusercontent.com%2FLedgerHQ%2Fledger-device-rust-sdk%2Frefs%2Fheads%2Fmaster%2Fledger_device_sdk%2FCargo.toml&query=%24.package.version&label=version) Crate that allows developing Ledger device apps in Rust with a default configuration. @@ -9,20 +10,11 @@ Contains: - signature abstractions - UI libraries (the `ui` module for Nano (S/SP/X) apps, `nbgl` module for Stax and Flex apps) -## Links - -To learn more about using the SDK and what is required to publish an app on the Ledger Live app store, please don't hesitate to check the following resources : - -- 📚 [Developer's documentation](https://developers.ledger.com/) -- 🗣️ [Ledger's Discord server](https://discord.gg/Ledger) -- 📦 [Fully featured boilerplate app](https://github.com/LedgerHQ/app-boilerplate-rust) -- 📦 [A Password Manager app](https://github.com/LedgerHQ/rust-app-password-manager) - ## Supported devices -| Nano S | Nano X | Nano S Plus | Stax | Flex | -| ------------------ | ------------------ | ------------------ | ------------------ | ------------------ | -| :heavy_check_mark: | :heavy_check_mark: | :heavy_check_mark: | :heavy_check_mark: | :heavy_check_mark: | +| Nano X | Nano S Plus | Stax | Flex | +| ------------------ | ------------------ | ------------------ | ------------------ | +| :white_check_mark: | :white_check_mark: | :white_check_mark: | :white_check_mark: | ## Usage @@ -31,7 +23,7 @@ On Ubuntu, `gcc-multilib` might also be required. Using rustc nightly builds is mandatory as some unstable features are required. -- `rustup default nightly` +- `rustup default nightly-2024-12-01` - `rustup component add rust-src` - install [Clang](http://releases.llvm.org/download.html). - install an [ARM gcc toolchain](https://developer.arm.com/tools-and-software/open-source-software/developer-tools/gnu-toolchain/gnu-rm/downloads) @@ -51,45 +43,33 @@ sudo pacman -S clang arm-none-eabi-gcc arm-none-eabi-newlib This SDK provides [custom target](https://doc.rust-lang.org/rustc/targets/custom.html) files. One for each supported device. -### Building for Nano S - -``` -cargo build --release -Z build-std=core --target=./nanos.json -``` - ### Building for Nano X ``` -cargo build --release -Z build-std=core --target=./nanox.json +cargo build --release --target=nanox ``` ### Building for Nano S+ ``` -cargo build --release -Z build-std=core --target=./nanosplus.json +cargo build --release --target=nanosplus ``` ### Building for Stax ``` -cargo build --release -Z build-std=core --target=./stax.json +cargo build --release --target=stax ``` ### Building for Flex ``` -cargo build --release -Z build-std=core --target=./flex.json +cargo build --release --target=flex ``` -## Building with rustc < 1.54 - -Building before rustc 1.54 should fail with `error[E0635]: unknown feature const_fn_trait_bound`. - -This is solved by activating a specific feature: `cargo build --features pre1_54` - ## Contributing -You can submit an issue or even a pull request if you wish to contribute, we will check what we can do. +You can submit an issue or even a pull request if you wish to contribute. Make sure you've followed the installation steps above. In order for your PR to be accepted, it will have to pass the CI, which performs the following checks: diff --git a/ledger_device_sdk/build.rs b/ledger_device_sdk/build.rs deleted file mode 100644 index 1c4d50d4..00000000 --- a/ledger_device_sdk/build.rs +++ /dev/null @@ -1,43 +0,0 @@ -use std::path::PathBuf; -use std::{env, error::Error}; - -fn main() -> Result<(), Box> { - enum Device { - NanoS, - NanoSPlus, - NanoX, - Stax, - Flex, - } - use Device::*; - - // determine device - let device = match env::var_os("CARGO_CFG_TARGET_OS").unwrap().to_str().unwrap() { - "nanos" => NanoS, - "nanosplus" => NanoSPlus, - "nanox" => NanoX, - "stax" => Stax, - "flex" => Flex, - target_name => panic!( - "invalid target `{target_name}`, expected one of `nanos`, `nanox`, `nanosplus`, `stax` or `flex`. Run with `-Z build-std=core --target=./.json`" - ), - }; - - // Copy this crate's linker script into the working directory of - // the application so that it can be used there for the layout. - // Trick taken from https://docs.rust-embedded.org/embedonomicon/main.html - let out_dir = PathBuf::from(env::var_os("OUT_DIR").unwrap()); - - // extend the library search path - println!("cargo:rustc-link-search={}", out_dir.display()); - // copy - let linkerscript = match device { - NanoS => "nanos_layout.ld", - NanoX => "nanox_layout.ld", - NanoSPlus => "nanosplus_layout.ld", - Stax | Flex => "stax_flex_layout.ld", - }; - std::fs::copy(linkerscript, out_dir.join(linkerscript))?; - std::fs::copy("link.ld", out_dir.join("link.ld"))?; - Ok(()) -} diff --git a/ledger_device_sdk/examples/nbgl_generic_review.rs b/ledger_device_sdk/examples/nbgl_generic_review.rs index 548f96a8..a0ecf8f6 100644 --- a/ledger_device_sdk/examples/nbgl_generic_review.rs +++ b/ledger_device_sdk/examples/nbgl_generic_review.rs @@ -8,11 +8,13 @@ use include_gif::include_gif; use ledger_device_sdk::io::*; use ledger_device_sdk::nbgl::{ init_comm, CenteredInfo, CenteredInfoStyle, Field, InfoButton, InfoLongPress, InfosList, - NbglGenericReview, NbglGlyph, NbglPageContent, NbglStatus, TagValueConfirm, TagValueList, - TuneIndex, + NbglChoice, NbglGenericReview, NbglGlyph, NbglPageContent, NbglStatus, TagValueConfirm, + TagValueList, TuneIndex, }; use ledger_secure_sdk_sys::*; +use core::ops::Not; + #[panic_handler] fn panic(_: &core::panic::PanicInfo) -> ! { exit_app(1); @@ -87,11 +89,33 @@ extern "C" fn sample_main() { .add_content(NbglPageContent::TagValueConfirm(tag_value_confirm)) .add_content(NbglPageContent::InfosList(infos_list)); - let success = review.show("Reject Example"); - let status_text = if success { - "Example confirmed" - } else { - "Example rejected" - }; - NbglStatus::new().text(status_text).show(success); + const IMPORTANT: NbglGlyph = + NbglGlyph::from_include(include_gif!("icons/Important_Circle_64px.png", NBGL)); + + let mut show_tx = true; + let mut status_text = "Example rejected"; + while show_tx { + let confirm = review.show("Reject Example"); + if confirm { + status_text = "Example confirmed"; + show_tx = false; + } else { + show_tx = NbglChoice::new() + .glyph(&IMPORTANT) + .show( + "Reject transaction?", + "", + "Yes, reject", + "Go back to transaction", + ) + // not() is used to invert the boolean value returned + // by the choice (since we want to return to showing the + // transaction if the user selects "Go back to transaction" + // which returns false). + .not(); + } + } + NbglStatus::new() + .text(status_text) + .show(status_text == "Example confirmed"); } diff --git a/ledger_device_sdk/examples/nbgl_spinner.rs b/ledger_device_sdk/examples/nbgl_spinner.rs index d711d77d..568dc180 100644 --- a/ledger_device_sdk/examples/nbgl_spinner.rs +++ b/ledger_device_sdk/examples/nbgl_spinner.rs @@ -49,7 +49,7 @@ extern "C" fn sample_main() { .glyph(&FERRIS) .show(&my_field); - NbglSpinner::new().text("Please wait...").show(); + NbglSpinner::new().show("Please wait..."); // Simulate an idle state of the app where it just // waits for some event to happen (such as APDU reception), going through diff --git a/ledger_device_sdk/icons/Important_Circle_64px.png b/ledger_device_sdk/icons/Important_Circle_64px.png new file mode 100755 index 00000000..40e9c22f Binary files /dev/null and b/ledger_device_sdk/icons/Important_Circle_64px.png differ diff --git a/ledger_device_sdk/nanos.json b/ledger_device_sdk/nanos.json deleted file mode 100644 index 4d893faf..00000000 --- a/ledger_device_sdk/nanos.json +++ /dev/null @@ -1,32 +0,0 @@ -{ - "abi": "eabi", - "arch": "arm", - "atomic-cas": false, - "c-enum-min-bits": 8, - "data-layout": "e-m:e-p:32:32-Fi8-i64:64-v128:64:128-a:0:32-n32-S64", - "emit-debug-gdb-scripts": false, - "executables": true, - "features": "+strict-align", - "frame-pointer": "always", - "linker": "link_wrap.sh", - "linker-flavor": "ld.lld", - "llvm-target": "thumbv6m-none-eabi", - "panic-strategy": "abort", - "pre-link-args": { - "ld.lld": [ - "-Tnanos_layout.ld", - "-Tlink.ld", - "--emit-relocs" - ], - "ld": [ - "-Tnanos_layout.ld", - "-Tlink.ld", - "--emit-relocs" - ] - }, - "relocation-model": "ropi", - "singlethread": true, - "target-pointer-width": "32", - "os": "nanos", - "target-family": [ "bolos" ] -} diff --git a/ledger_device_sdk/nanos_layout.ld b/ledger_device_sdk/nanos_layout.ld deleted file mode 100644 index 129399e6..00000000 --- a/ledger_device_sdk/nanos_layout.ld +++ /dev/null @@ -1,10 +0,0 @@ -MEMORY -{ - FLASH (rx) : ORIGIN = 0xc0d00000, LENGTH = 400K - SRAM (rwx) : ORIGIN = 0x20000200, LENGTH = 4K+512 - CXSRAM (rwx) : ORIGIN = 0x20001400, LENGTH = 1K -} - -PAGE_SIZE = 64; -STACK_SIZE = DEFINED(stack_size) ? stack_size : 1024; -END_STACK = ORIGIN(SRAM) + LENGTH(SRAM); \ No newline at end of file diff --git a/ledger_device_sdk/src/ccid.rs b/ledger_device_sdk/src/ccid.rs deleted file mode 100644 index 0b40b2c6..00000000 --- a/ledger_device_sdk/src/ccid.rs +++ /dev/null @@ -1,11 +0,0 @@ -extern "C" { - pub static mut G_io_apdu_buffer: [u8; 260]; - pub fn io_usb_ccid_reply_bare(length: u16); -} - -pub fn send(buf: &[u8]) { - unsafe { - G_io_apdu_buffer[..buf.len()].copy_from_slice(buf); - io_usb_ccid_reply_bare(buf.len() as u16); - } -} diff --git a/ledger_device_sdk/src/io.rs b/ledger_device_sdk/src/io.rs index eebfded3..071d6084 100644 --- a/ledger_device_sdk/src/io.rs +++ b/ledger_device_sdk/src/io.rs @@ -5,8 +5,6 @@ use ledger_secure_sdk_sys::buttons::{get_button_event, ButtonEvent, ButtonsState use ledger_secure_sdk_sys::seph as sys_seph; use ledger_secure_sdk_sys::*; -#[cfg(feature = "ccid")] -use crate::ccid; use crate::seph; use core::convert::{Infallible, TryFrom}; use core::ops::{Index, IndexMut}; @@ -20,7 +18,7 @@ pub enum StatusWords { BadIns = 0x6e01, BadP1P2 = 0x6e02, BadLen = 0x6e03, - UserCancelled = 0x6e04, + UserCancelled = 0x6985, Unknown = 0x6d00, Panic = 0xe000, DeviceLocked = 0x5515, @@ -170,11 +168,11 @@ impl Comm { /// Send the currently held APDU // This is private. Users should call reply to set the satus word and // transmit the response. - fn apdu_send(&mut self) { + fn apdu_send(&mut self, is_swap: bool) { if !sys_seph::is_status_sent() { sys_seph::send_general_status() } - let mut spi_buffer = [0u8; 128]; + let mut spi_buffer = [0u8; 256]; while sys_seph::is_status_sent() { sys_seph::seph_recv(&mut spi_buffer, 0); seph::handle_event(&mut self.apdu_buffer, &spi_buffer); @@ -193,16 +191,19 @@ impl Comm { sys_seph::seph_send(&[sys_seph::SephTags::RawAPDU as u8, len[0], len[1]]); sys_seph::seph_send(&self.apdu_buffer[..self.tx]); } - #[cfg(feature = "ccid")] - APDU_USB_CCID => { - ccid::send(&self.apdu_buffer[..self.tx]); - } #[cfg(any(target_os = "nanox", target_os = "stax", target_os = "flex"))] APDU_BLE => { ble::send(&self.apdu_buffer[..self.tx]); } _ => (), } + if is_swap { + if !sys_seph::is_status_sent() { + sys_seph::send_general_status() + } + sys_seph::seph_recv(&mut spi_buffer, 0); + seph::handle_event(&mut self.apdu_buffer, &spi_buffer); + } self.tx = 0; self.rx = 0; unsafe { @@ -253,7 +254,7 @@ impl Comm { T: TryFrom, Reply: From<>::Error>, { - let mut spi_buffer = [0u8; 128]; + let mut spi_buffer = [0u8; 256]; unsafe { G_io_app.apdu_state = APDU_IDLE; @@ -282,7 +283,7 @@ impl Comm { T: TryFrom, Reply: From<>::Error>, { - let mut spi_buffer = [0u8; 128]; + let mut spi_buffer = [0u8; 256]; // Signal end of command stream from SE to MCU // And prepare reception @@ -346,7 +347,7 @@ impl Comm { None } - pub fn process_event(&mut self, spi_buffer: &mut [u8; 128]) -> Option> + pub fn process_event(&mut self, spi_buffer: &mut [u8; 256]) -> Option> where T: TryFrom, Reply: From<>::Error>, @@ -371,6 +372,10 @@ impl Comm { match seph::Events::from(tag) { #[cfg(not(any(target_os = "stax", target_os = "flex")))] seph::Events::ButtonPush => { + #[cfg(feature = "nano_nbgl")] + unsafe { + ux_process_button_event(spi_buffer.as_mut_ptr()); + } let button_info = spi_buffer[3] >> 1; if let Some(btn_evt) = get_button_event(&mut self.buttons, button_info) { return Some(Event::Button(btn_evt)); @@ -392,7 +397,7 @@ impl Comm { seph::Events::BleReceive => ble::receive(&mut self.apdu_buffer, spi_buffer), seph::Events::TickerEvent => { - #[cfg(any(target_os = "stax", target_os = "flex"))] + #[cfg(any(target_os = "stax", target_os = "flex", feature = "nano_nbgl"))] unsafe { ux_process_ticker_event(); } @@ -415,7 +420,7 @@ impl Comm { None } - pub fn decode_event(&mut self, spi_buffer: &mut [u8; 128]) -> Option> + pub fn decode_event(&mut self, spi_buffer: &mut [u8; 256]) -> Option> where T: TryFrom, Reply: From<>::Error>, @@ -425,6 +430,14 @@ impl Comm { } if unsafe { G_io_app.apdu_state } != APDU_IDLE && unsafe { G_io_app.apdu_length } > 0 { + unsafe { + if os_perso_is_pin_set() == BOLOS_TRUE.try_into().unwrap() + && os_global_pin_is_validated() != BOLOS_TRUE.try_into().unwrap() + { + self.reply(StatusWords::DeviceLocked); + return None; + } + } self.rx = unsafe { G_io_app.apdu_length as usize }; self.event_pending = true; return self.check_event(); @@ -432,19 +445,19 @@ impl Comm { None } - fn detect_apdu(&mut self, spi_buffer: &mut [u8; 128]) -> bool + fn detect_apdu(&mut self, spi_buffer: &mut [u8; 256]) -> bool where T: TryFrom, Reply: From<>::Error>, { - let _: Option> = self.decode_event(spi_buffer); - - if unsafe { G_io_app.apdu_state } != APDU_IDLE && unsafe { G_io_app.apdu_length } > 0 { - self.rx = unsafe { G_io_app.apdu_length as usize }; - self.event_pending = true; - return true; + match self.decode_event::(spi_buffer) { + Some(Event::Command(_)) => { + self.rx = unsafe { G_io_app.apdu_length as usize }; + self.event_pending = true; + return true; + } + _ => return false, } - false } /// Wait for the next Command event. Discards received button events. @@ -506,7 +519,17 @@ impl Comm { self.apdu_buffer[self.tx + 1] = sw as u8; self.tx += 2; // Transmit the response - self.apdu_send(); + self.apdu_send(false); + } + + pub fn swap_reply>(&mut self, reply: T) { + let sw = reply.into().0; + // Append status word + self.apdu_buffer[self.tx] = (sw >> 8) as u8; + self.apdu_buffer[self.tx + 1] = sw as u8; + self.tx += 2; + // Transmit the response + self.apdu_send(true); } /// Set the Status Word of the response to `StatusWords::OK` (which is equal @@ -515,6 +538,10 @@ impl Comm { self.reply(StatusWords::Ok); } + pub fn swap_reply_ok(&mut self) { + self.swap_reply(StatusWords::Ok); + } + /// Return APDU Metadata pub fn get_apdu_metadata(&self) -> &ApduHeader { assert!(self.apdu_buffer.len() >= 4); @@ -552,10 +579,8 @@ impl Comm { } pub fn append(&mut self, m: &[u8]) { - for c in m.iter() { - self.apdu_buffer[self.tx] = *c; - self.tx += 1; - } + self.apdu_buffer[self.tx..self.tx + m.len()].copy_from_slice(m); + self.tx += m.len(); } } diff --git a/ledger_device_sdk/src/lib.rs b/ledger_device_sdk/src/lib.rs index 2c82630e..63ba76f9 100644 --- a/ledger_device_sdk/src/lib.rs +++ b/ledger_device_sdk/src/lib.rs @@ -10,12 +10,11 @@ #[cfg(any(target_os = "nanox", target_os = "stax", target_os = "flex"))] pub mod ble; -#[cfg(feature = "ccid")] -pub mod ccid; pub mod ecc; pub mod hash; pub mod hmac; pub mod io; +pub mod libcall; pub mod nvm; pub mod random; pub mod screen; @@ -23,9 +22,9 @@ pub mod seph; pub mod testing; -#[cfg(any(target_os = "stax", target_os = "flex"))] +#[cfg(any(target_os = "stax", target_os = "flex", feature = "nano_nbgl"))] pub mod nbgl; -#[cfg(not(any(target_os = "stax", target_os = "flex")))] +#[cfg(not(any(target_os = "stax", target_os = "flex", feature = "nano_nbgl")))] pub mod ui; pub mod uxapp; @@ -124,17 +123,11 @@ impl NVMData { NVMData { data } } - #[cfg(target_os = "nanos")] - pub fn get_mut(&mut self) -> &mut T { - ledger_secure_sdk_sys::pic_rs_mut(&mut self.data) - } - /// This will return a mutable access by casting the pointer /// to the correct offset in `.nvm_data` manually. /// This is necessary when using the `rwpi` relocation model, /// because a static mutable will be assumed to be located in /// RAM, and be accessed through the static base (r9) - #[cfg(not(target_os = "nanos"))] fn get_addr(&self) -> *mut T { use core::arch::asm; unsafe { @@ -149,7 +142,6 @@ impl NVMData { } } - #[cfg(not(target_os = "nanos"))] pub fn get_mut(&mut self) -> &mut T { unsafe { let pic_addr = self.get_addr(); @@ -157,7 +149,6 @@ impl NVMData { } } - #[cfg(not(target_os = "nanos"))] pub fn get_ref(&self) -> &T { unsafe { let pic_addr = self.get_addr(); diff --git a/ledger_device_sdk/src/libcall.rs b/ledger_device_sdk/src/libcall.rs new file mode 100644 index 00000000..b747b412 --- /dev/null +++ b/ledger_device_sdk/src/libcall.rs @@ -0,0 +1,35 @@ +use crate::testing::debug_print; + +use ledger_secure_sdk_sys::{libargs_t, CHECK_ADDRESS, GET_PRINTABLE_AMOUNT, SIGN_TRANSACTION}; + +pub mod string; +pub mod swap; + +pub enum LibCallCommand { + SwapSignTransaction, + SwapGetPrintableAmount, + SwapCheckAddress, +} + +impl From for LibCallCommand { + fn from(command: u32) -> Self { + match command { + SIGN_TRANSACTION => LibCallCommand::SwapSignTransaction, + GET_PRINTABLE_AMOUNT => LibCallCommand::SwapGetPrintableAmount, + CHECK_ADDRESS => LibCallCommand::SwapCheckAddress, + _ => panic!("Unknown command"), + } + } +} + +pub fn get_command(arg0: u32) -> LibCallCommand { + debug_print("GET_CMD\n"); + let mut libarg: libargs_t = libargs_t::default(); + + let arg = arg0 as *const u32; + + libarg.id = unsafe { *arg }; + libarg.command = unsafe { *arg.add(1) }; + libarg.unused = unsafe { *arg.add(2) }; + libarg.command.into() +} diff --git a/ledger_device_sdk/src/libcall/string.rs b/ledger_device_sdk/src/libcall/string.rs new file mode 100644 index 00000000..f65665dd --- /dev/null +++ b/ledger_device_sdk/src/libcall/string.rs @@ -0,0 +1,183 @@ +#[derive(Debug, Copy, Clone)] +pub struct CustomString { + pub arr: [u8; N], + pub capacity: usize, + pub len: usize, +} + +impl Default for CustomString { + fn default() -> Self { + Self { + arr: [b'0'; N], + capacity: N, + len: 0, + } + } +} + +impl CustomString { + pub fn new() -> Self { + Self { + arr: [b'0'; N], + capacity: N, + len: 0, + } + } + + pub fn clear(&mut self) { + self.arr.fill(0); + self.len = 0; + } + + pub fn as_str(&self) -> &str { + core::str::from_utf8(&self.arr[..self.len]).unwrap() + } + + pub fn copy_from(&mut self, s: &CustomString) { + self.arr[..s.len].copy_from_slice(&s.arr[..s.len]); + self.len = s.len; + } +} + +impl From for CustomString<2> { + fn from(val: u8) -> Self { + let mut s = CustomString::<2>::new(); + let mut i: usize = 0; + for c in val.to_be_bytes().into_iter() { + let (c0, c1) = byte_to_hex(c); + s.arr[i] = c0 as u8; + s.arr[i + 1] = c1 as u8; + s.len += 2; + i += 2; + } + s + } +} + +impl From for CustomString<4> { + fn from(val: u16) -> Self { + let mut s = CustomString::<4>::new(); + let mut i: usize = 0; + for c in val.to_be_bytes().into_iter() { + let (c0, c1) = byte_to_hex(c); + s.arr[i] = c0 as u8; + s.arr[i + 1] = c1 as u8; + s.len += 2; + i += 2; + } + s + } +} + +impl From for CustomString<8> { + fn from(val: u32) -> Self { + let mut s = CustomString::<8>::new(); + let mut i: usize = 0; + for c in val.to_be_bytes().into_iter() { + let (c0, c1) = byte_to_hex(c); + s.arr[i] = c0 as u8; + s.arr[i + 1] = c1 as u8; + s.len += 2; + i += 2; + } + s + } +} + +impl From<[u8; 32]> for CustomString<64> { + fn from(arr: [u8; 32]) -> Self { + let mut s = CustomString::<64>::new(); + let mut i: usize = 0; + for c in arr.into_iter() { + let (c0, c1) = byte_to_hex(c); + s.arr[i] = c0 as u8; + s.arr[i + 1] = c1 as u8; + s.len += 2; + i += 2; + } + s + } +} + +impl TryFrom<&str> for CustomString { + type Error = &'static str; + fn try_from(st: &str) -> Result { + if N >= st.len() { + let mut s = CustomString::::new(); + s.arr[..st.len()].copy_from_slice(st.as_bytes()); + s.len = st.len(); + Ok(s) + } else { + Err("CustomString's capacity overflow!") + } + } +} + +/// Output an uint256 as an decimal CustomString +/// For instance: +/// +/// let val: [u8; 32] = token amount (32 bytes / 256 bits); +/// let s: CustomString<79> = uint256_to_integer(&val); // max number of decimal digits for Uint256 = 78 (+ 1 spare for '.') +/// testing::debug_print(s.print().unwrap()); +pub fn uint256_to_integer(value: &[u8; 32]) -> CustomString<79> { + let mut s: CustomString<79> = CustomString::new(); + + // Special case when value is 0 + if *value == [0u8; 32] { + s.arr[0] = b'0'; + s.len = 1; + return s; + } + + let mut n: [u16; 16] = [0u16; 16]; + for idx in 0..16 { + n[idx] = u16::from_be_bytes([value[2 * idx], value[2 * idx + 1]]); + } + + let mut pos: usize = s.capacity; + while n != [0u16; 16] { + if pos == 0 { + return s; + } + pos -= 1; + let mut carry = 0u32; + let mut rem: u32; + for i in 0..16 { + rem = ((carry << 16) | u32::from(n[i])) % 10; + n[i] = (((carry << 16) | u32::from(n[i])) / 10) as u16; + carry = rem; + } + s.arr[pos] = u8::try_from(char::from_digit(carry, 10).unwrap()).unwrap(); + } + s.arr.copy_within(pos.., 0); + s.len = s.capacity - pos; + s +} + +/// Output an uint256 as a float string +pub fn uint256_to_float(value: &[u8; 32], decimals: usize) -> CustomString<79> { + let mut s: CustomString<79> = uint256_to_integer(value); + + if decimals == 0 || s.arr[0] == b'0' { + return s; + } + + if s.len <= decimals { + s.arr.copy_within(0..s.len, 2 + decimals - s.len); + s.arr[0..2 + decimals - s.len].fill(b'0'); + s.arr[1] = b'.'; + s.len += 2 + decimals - s.len; + } else { + s.arr + .copy_within(s.len - decimals..s.len, s.len - decimals + 1); + s.arr[s.len - decimals] = b'.'; + s.len += 1; + } + s +} + +fn byte_to_hex(b: u8) -> (char, char) { + let c0 = char::from_digit((b >> 4).into(), 16).unwrap(); + let c1 = char::from_digit((b & 0xf).into(), 16).unwrap(); + (c0, c1) +} diff --git a/ledger_device_sdk/src/libcall/swap.rs b/ledger_device_sdk/src/libcall/swap.rs new file mode 100644 index 00000000..45a54a5f --- /dev/null +++ b/ledger_device_sdk/src/libcall/swap.rs @@ -0,0 +1,348 @@ +#[cfg(any(target_os = "stax", target_os = "flex"))] +use crate::nbgl::NbglSpinner; +use crate::testing::debug_print; +use ledger_secure_sdk_sys::{ + check_address_parameters_t, create_transaction_parameters_t, get_printable_amount_parameters_t, + libargs_s__bindgen_ty_1, libargs_t, MAX_PRINTABLE_AMOUNT_SIZE, +}; + +pub const DEFAULT_COIN_CONFIG_BUF_SIZE: usize = 16; +pub const DEFAULT_ADDRESS_BUF_SIZE: usize = 64; + +const DPATH_STAGE_SIZE: usize = 16; +const AMOUNT_BUF_SIZE: usize = 16; + +pub struct CheckAddressParams< + const COIN_CONFIG_BUF_SIZE: usize = DEFAULT_COIN_CONFIG_BUF_SIZE, + const ADDRESS_BUF_SIZE: usize = DEFAULT_ADDRESS_BUF_SIZE, +> { + pub coin_config: [u8; COIN_CONFIG_BUF_SIZE], + pub coin_config_len: usize, + pub dpath: [u8; DPATH_STAGE_SIZE * 4], + pub dpath_len: usize, + pub ref_address: [u8; ADDRESS_BUF_SIZE], + pub ref_address_len: usize, + pub result: *mut i32, +} + +impl Default + for CheckAddressParams +{ + fn default() -> Self { + CheckAddressParams { + coin_config: [0; COIN_CONFIG_BUF_SIZE], + coin_config_len: 0, + dpath: [0; DPATH_STAGE_SIZE * 4], + dpath_len: 0, + ref_address: [0; ADDRESS_BUF_SIZE], + ref_address_len: 0, + result: core::ptr::null_mut(), + } + } +} + +pub struct PrintableAmountParams< + const COIN_CONFIG_BUF_SIZE: usize = DEFAULT_COIN_CONFIG_BUF_SIZE, + // Unused const generic paramer here, to allow type inference in `swap_return` fn + const ADDRESS_BUF_SIZE: usize = DEFAULT_ADDRESS_BUF_SIZE, +> { + pub coin_config: [u8; COIN_CONFIG_BUF_SIZE], + pub coin_config_len: usize, + pub amount: [u8; AMOUNT_BUF_SIZE], + pub amount_len: usize, + pub amount_str: *mut i8, + pub is_fee: bool, +} + +impl Default + for PrintableAmountParams +{ + fn default() -> Self { + PrintableAmountParams { + coin_config: [0; COIN_CONFIG_BUF_SIZE], + coin_config_len: 0, + amount: [0; AMOUNT_BUF_SIZE], + amount_len: 0, + amount_str: core::ptr::null_mut(), + is_fee: false, + } + } +} + +pub struct CreateTxParams< + const COIN_CONFIG_BUF_SIZE: usize = DEFAULT_COIN_CONFIG_BUF_SIZE, + const ADDRESS_BUF_SIZE: usize = DEFAULT_ADDRESS_BUF_SIZE, +> { + pub coin_config: [u8; COIN_CONFIG_BUF_SIZE], + pub coin_config_len: usize, + pub amount: [u8; AMOUNT_BUF_SIZE], + pub amount_len: usize, + pub fee_amount: [u8; AMOUNT_BUF_SIZE], + pub fee_amount_len: usize, + pub dest_address: [u8; ADDRESS_BUF_SIZE], + pub dest_address_len: usize, + pub result: *mut u8, +} + +impl Default + for CreateTxParams +{ + fn default() -> Self { + CreateTxParams { + coin_config: [0; COIN_CONFIG_BUF_SIZE], + coin_config_len: 0, + amount: [0; AMOUNT_BUF_SIZE], + amount_len: 0, + fee_amount: [0; AMOUNT_BUF_SIZE], + fee_amount_len: 0, + dest_address: [0; ADDRESS_BUF_SIZE], + dest_address_len: 0, + result: core::ptr::null_mut(), + } + } +} + +pub fn get_check_address_params< + const COIN_CONFIG_BUF_SIZE: usize, + const ADDRESS_BUF_SIZE: usize, +>( + arg0: u32, +) -> CheckAddressParams { + debug_print("=> get_check_address_params\n"); + + let mut libarg: libargs_t = libargs_t::default(); + + let arg = arg0 as *const u32; + + libarg.id = unsafe { *arg }; + libarg.command = unsafe { *arg.add(1) }; + libarg.unused = unsafe { *arg.add(2) }; + + libarg.__bindgen_anon_1 = unsafe { *(arg.add(3) as *const libargs_s__bindgen_ty_1) }; + + let params: check_address_parameters_t = + unsafe { *(libarg.__bindgen_anon_1.check_address as *const check_address_parameters_t) }; + + let mut check_address_params: CheckAddressParams = + Default::default(); + + debug_print("==> GET_COIN_CONFIG_LENGTH\n"); + check_address_params.coin_config_len = params.coin_configuration_length as usize; + + debug_print("==> GET_COIN_CONFIG \n"); + unsafe { + params.coin_configuration.copy_to_nonoverlapping( + check_address_params.coin_config.as_mut_ptr(), + check_address_params + .coin_config_len + .min(COIN_CONFIG_BUF_SIZE), + ); + } + + debug_print("==> GET_DPATH_LENGTH\n"); + check_address_params.dpath_len = + DPATH_STAGE_SIZE.min(unsafe { *(params.address_parameters as *const u8) as usize }); + + debug_print("==> GET_DPATH \n"); + for i in 1..1 + check_address_params.dpath_len * 4 { + check_address_params.dpath[i - 1] = unsafe { *(params.address_parameters.add(i)) }; + } + + debug_print("==> GET_REF_ADDRESS\n"); + let mut address_length = 0usize; + let mut c = unsafe { *(params.address_to_check.add(address_length)) }; + while c != '\0' as i8 && address_length < ADDRESS_BUF_SIZE { + check_address_params.ref_address[address_length] = c as u8; + address_length += 1; + c = unsafe { *(params.address_to_check.add(address_length)) }; + } + check_address_params.ref_address_len = address_length; + + check_address_params.result = unsafe { + &(*(libarg.__bindgen_anon_1.check_address as *mut check_address_parameters_t)).result + as *const i32 as *mut i32 + }; + + check_address_params +} + +pub fn get_printable_amount_params< + const COIN_CONFIG_BUF_SIZE: usize, + const ADDRESS_BUF_SIZE: usize, +>( + arg0: u32, +) -> PrintableAmountParams { + debug_print("=> get_printable_amount_params\n"); + + let mut libarg: libargs_t = libargs_t::default(); + + let arg = arg0 as *const u32; + + libarg.id = unsafe { *arg }; + libarg.command = unsafe { *arg.add(1) }; + libarg.unused = unsafe { *arg.add(2) }; + + libarg.__bindgen_anon_1 = unsafe { *(arg.add(3) as *const libargs_s__bindgen_ty_1) }; + + let params: get_printable_amount_parameters_t = unsafe { + *(libarg.__bindgen_anon_1.get_printable_amount as *const get_printable_amount_parameters_t) + }; + + let mut printable_amount_params: PrintableAmountParams = + Default::default(); + + debug_print("==> GET_COIN_CONFIG_LENGTH\n"); + printable_amount_params.coin_config_len = params.coin_configuration_length as usize; + + debug_print("==> GET_COIN_CONFIG \n"); + unsafe { + params.coin_configuration.copy_to_nonoverlapping( + printable_amount_params.coin_config.as_mut_ptr(), + printable_amount_params + .coin_config_len + .min(COIN_CONFIG_BUF_SIZE), + ); + } + + debug_print("==> GET_IS_FEE\n"); + printable_amount_params.is_fee = params.is_fee == true; + + debug_print("==> GET_AMOUNT_LENGTH\n"); + printable_amount_params.amount_len = AMOUNT_BUF_SIZE.min(params.amount_length as usize); + + debug_print("==> GET_AMOUNT\n"); + for i in 0..printable_amount_params.amount_len { + printable_amount_params.amount[AMOUNT_BUF_SIZE - printable_amount_params.amount_len + i] = + unsafe { *(params.amount.add(i)) }; + } + + debug_print("==> GET_AMOUNT_STR\n"); + printable_amount_params.amount_str = unsafe { + &(*(libarg.__bindgen_anon_1.get_printable_amount as *mut get_printable_amount_parameters_t)) + .printable_amount as *const i8 as *mut i8 + }; + + printable_amount_params +} + +extern "C" { + fn c_reset_bss(); + fn c_boot_std(); +} + +pub fn sign_tx_params( + arg0: u32, +) -> CreateTxParams { + debug_print("=> sign_tx_params\n"); + + let mut libarg: libargs_t = libargs_t::default(); + + let arg = arg0 as *const u32; + + libarg.id = unsafe { *arg }; + libarg.command = unsafe { *arg.add(1) }; + libarg.unused = unsafe { *arg.add(2) }; + + libarg.__bindgen_anon_1 = unsafe { *(arg.add(3) as *const libargs_s__bindgen_ty_1) }; + + let params: create_transaction_parameters_t = unsafe { + *(libarg.__bindgen_anon_1.create_transaction as *const create_transaction_parameters_t) + }; + + let mut create_tx_params: CreateTxParams = + Default::default(); + + debug_print("==> GET_COIN_CONFIG_LENGTH\n"); + create_tx_params.coin_config_len = params.coin_configuration_length as usize; + + debug_print("==> GET_COIN_CONFIG \n"); + unsafe { + params.coin_configuration.copy_to_nonoverlapping( + create_tx_params.coin_config.as_mut_ptr(), + create_tx_params.coin_config_len.min(COIN_CONFIG_BUF_SIZE), + ); + } + + debug_print("==> GET_AMOUNT\n"); + create_tx_params.amount_len = AMOUNT_BUF_SIZE.min(params.amount_length as usize); + for i in 0..create_tx_params.amount_len { + create_tx_params.amount[AMOUNT_BUF_SIZE - create_tx_params.amount_len + i] = + unsafe { *(params.amount.add(i)) }; + } + + debug_print("==> GET_FEE\n"); + create_tx_params.fee_amount_len = AMOUNT_BUF_SIZE.min(params.fee_amount_length as usize); + for i in 0..create_tx_params.fee_amount_len { + create_tx_params.fee_amount[AMOUNT_BUF_SIZE - create_tx_params.fee_amount_len + i] = + unsafe { *(params.fee_amount.add(i)) }; + } + + debug_print("==> GET_DESTINATION_ADDRESS\n"); + let mut dest_address_length = 0usize; + let mut c = unsafe { *params.destination_address.add(dest_address_length) }; + while c != '\0' as i8 && dest_address_length < ADDRESS_BUF_SIZE { + create_tx_params.dest_address[dest_address_length] = c as u8; + dest_address_length += 1; + c = unsafe { *params.destination_address.add(dest_address_length) }; + } + create_tx_params.dest_address_len = dest_address_length; + + create_tx_params.result = unsafe { + &(*(libarg.__bindgen_anon_1.create_transaction as *mut create_transaction_parameters_t)) + .result as *const u8 as *mut u8 + }; + + /* Reset BSS and complete application boot */ + unsafe { + c_reset_bss(); + c_boot_std(); + } + + #[cfg(any(target_os = "stax", target_os = "flex"))] + NbglSpinner::new().show("Signing"); + + create_tx_params +} + +pub enum SwapResult< + 'a, + const COIN_CONFIG_BUF_SIZE: usize = DEFAULT_COIN_CONFIG_BUF_SIZE, + const ADDRESS_BUF_SIZE: usize = DEFAULT_ADDRESS_BUF_SIZE, +> { + CheckAddressResult( + &'a mut CheckAddressParams, + i32, + ), + PrintableAmountResult( + &'a mut PrintableAmountParams, + &'a str, + ), + CreateTxResult( + &'a mut CreateTxParams, + u8, + ), +} + +pub fn swap_return( + res: SwapResult, +) { + match res { + SwapResult::CheckAddressResult(&mut ref p, r) => { + unsafe { *(p.result) = r }; + } + SwapResult::PrintableAmountResult(&mut ref p, s) => { + if s.len() < (MAX_PRINTABLE_AMOUNT_SIZE - 1).try_into().unwrap() { + for (i, c) in s.chars().enumerate() { + unsafe { *(p.amount_str.add(i)) = c as i8 }; + } + unsafe { *(p.amount_str.add(s.len())) = '\0' as i8 }; + } else { + unsafe { *(p.amount_str) = '\0' as i8 }; + } + } + SwapResult::CreateTxResult(&mut ref p, r) => { + unsafe { *(p.result) = r }; + } + } + unsafe { ledger_secure_sdk_sys::os_lib_end() }; +} diff --git a/ledger_device_sdk/src/nbgl.rs b/ledger_device_sdk/src/nbgl.rs index 44451704..dcb86907 100644 --- a/ledger_device_sdk/src/nbgl.rs +++ b/ledger_device_sdk/src/nbgl.rs @@ -8,11 +8,9 @@ use core::ffi::{c_char, c_int}; use core::mem::transmute; use ledger_secure_sdk_sys::*; -#[no_mangle] -static mut G_ux_params: bolos_ux_params_t = unsafe { const_zero!(bolos_ux_params_t) }; - pub mod nbgl_address_review; pub mod nbgl_choice; +#[cfg(any(target_os = "stax", target_os = "flex"))] pub mod nbgl_generic_review; pub mod nbgl_home_and_settings; pub mod nbgl_review; @@ -23,6 +21,7 @@ pub mod nbgl_streaming_review; pub use nbgl_address_review::*; pub use nbgl_choice::*; +#[cfg(any(target_os = "stax", target_os = "flex"))] pub use nbgl_generic_review::*; pub use nbgl_home_and_settings::*; pub use nbgl_review::*; @@ -79,7 +78,7 @@ trait SyncNBGL: Sized { fn ux_sync_wait(&self, exit_on_apdu: bool) -> SyncNbgl { unsafe { - if let Some(comm) = COMM_REF.as_mut() { + if let Some(comm) = (*(&raw mut COMM_REF)).as_mut() { while !G_ENDED { let apdu_received = comm.next_event_ahead::(); if exit_on_apdu && apdu_received { @@ -108,6 +107,7 @@ unsafe extern "C" fn quit_callback() { G_ENDED = true; } +#[cfg(any(target_os = "stax", target_os = "flex"))] unsafe extern "C" fn rejected_callback() { G_RET = SyncNbgl::UxSyncRetRejected.into(); G_ENDED = true; @@ -277,6 +277,7 @@ pub enum TuneIndex { // Direct translation of the C original. This was done to // avoid compiling `os_io_seproxyhal.c` which includes many other things #[no_mangle] +#[cfg(any(target_os = "stax", target_os = "flex"))] extern "C" fn io_seproxyhal_play_tune(tune_index: u8) { let mut buffer = [0u8; 4]; let mut spi_buffer = [0u8; 128]; diff --git a/ledger_device_sdk/src/nbgl/nbgl_address_review.rs b/ledger_device_sdk/src/nbgl/nbgl_address_review.rs index 14b03ac2..3abe7bfc 100644 --- a/ledger_device_sdk/src/nbgl/nbgl_address_review.rs +++ b/ledger_device_sdk/src/nbgl/nbgl_address_review.rs @@ -12,7 +12,7 @@ impl SyncNBGL for NbglAddressReview<'_> {} impl<'a> NbglAddressReview<'a> { pub fn new() -> NbglAddressReview<'a> { NbglAddressReview { - verify_str: CString::new("").unwrap(), + verify_str: CString::default(), glyph: None, } } @@ -45,7 +45,10 @@ impl<'a> NbglAddressReview<'a> { address.as_ptr(), core::ptr::null(), &icon as *const nbgl_icon_details_t, - self.verify_str.as_ptr(), + match self.verify_str.is_empty() { + true => core::ptr::null(), + false => self.verify_str.as_ptr(), + }, core::ptr::null(), Some(choice_callback), ); diff --git a/ledger_device_sdk/src/nbgl/nbgl_home_and_settings.rs b/ledger_device_sdk/src/nbgl/nbgl_home_and_settings.rs index 623217f6..cc4064c6 100644 --- a/ledger_device_sdk/src/nbgl/nbgl_home_and_settings.rs +++ b/ledger_device_sdk/src/nbgl/nbgl_home_and_settings.rs @@ -20,7 +20,7 @@ unsafe extern "C" fn settings_callback(token: c_int, _index: u8, _page: c_int) { _ => panic!("Invalid state."), } - if let Some(data) = NVM_REF.as_mut() { + if let Some(data) = (*(&raw mut NVM_REF)).as_mut() { let mut switch_values: [u8; SETTINGS_SIZE] = *data.get_ref(); if switch_values[setting_idx] == OFF_STATE { switch_values[setting_idx] = ON_STATE; @@ -47,6 +47,7 @@ pub enum PageIndex { /// information fields, and settings switches. pub struct NbglHomeAndSettings { app_name: CString, + tag_line: Option, info_contents: Vec, info_contents_ptr: Vec<*const c_char>, setting_contents: Vec<[CString; 2]>, @@ -74,6 +75,7 @@ impl<'a> NbglHomeAndSettings { pub fn new() -> NbglHomeAndSettings { NbglHomeAndSettings { app_name: CString::new("").unwrap(), + tag_line: None, info_contents: Vec::default(), info_contents_ptr: Vec::default(), setting_contents: Vec::default(), @@ -109,6 +111,13 @@ impl<'a> NbglHomeAndSettings { } } + pub fn tagline(self, tagline: &'a str) -> NbglHomeAndSettings { + NbglHomeAndSettings { + tag_line: Some(CString::new(tagline).unwrap()), + ..self + } + } + pub fn settings( self, nvm_data: &'a mut AtomicStorage<[u8; SETTINGS_SIZE]>, @@ -166,20 +175,23 @@ impl<'a> NbglHomeAndSettings { for (i, setting) in self.setting_contents.iter().enumerate() { SWITCH_ARRAY[i].text = setting[0].as_ptr(); SWITCH_ARRAY[i].subText = setting[1].as_ptr(); - let state = if let Some(data) = NVM_REF.as_mut() { + let state = if let Some(data) = (*(&raw mut NVM_REF)).as_mut() { data.get_ref()[i] } else { OFF_STATE }; SWITCH_ARRAY[i].initState = state; SWITCH_ARRAY[i].token = (FIRST_USER_TOKEN + i as u32) as u8; - SWITCH_ARRAY[i].tuneId = TuneIndex::TapCasual as u8; + #[cfg(any(target_os = "stax", target_os = "flex"))] + { + SWITCH_ARRAY[i].tuneId = TuneIndex::TapCasual as u8; + } } self.content = nbgl_content_t { content: nbgl_content_u { switchesList: nbgl_pageSwitchesList_s { - switches: &SWITCH_ARRAY as *const nbgl_contentSwitch_t, + switches: &raw const SWITCH_ARRAY as *const nbgl_contentSwitch_t, nbSwitches: self.nb_settings, }, }, @@ -192,26 +204,32 @@ impl<'a> NbglHomeAndSettings { __bindgen_anon_1: nbgl_genericContents_t__bindgen_ty_1 { contentsList: &self.content as *const nbgl_content_t, }, - nbContents: if self.nb_settings > 0 { 1 } else { 0 }, + nbContents: self.nb_settings, }; self.ux_sync_init(); nbgl_useCaseHomeAndSettings( self.app_name.as_ptr() as *const c_char, &self.icon as *const nbgl_icon_details_t, - core::ptr::null(), + match self.tag_line { + None => core::ptr::null(), + Some(ref tag) => tag.as_ptr() as *const c_char, + }, match self.start_page { PageIndex::Home => INIT_HOME_PAGE as u8, PageIndex::Settings(idx) => idx, }, - &self.generic_contents as *const nbgl_genericContents_t, + match self.nb_settings { + 0 => core::ptr::null(), + _ => &self.generic_contents as *const nbgl_genericContents_t, + }, &self.info_list as *const nbgl_contentInfoList_t, core::ptr::null(), Some(quit_callback), ); match self.ux_sync_wait(true) { SyncNbgl::UxSyncRetApduReceived => { - if let Some(comm) = COMM_REF.as_mut() { + if let Some(comm) = (*(&raw mut COMM_REF)).as_mut() { if let Some(value) = comm.check_event() { return value; } @@ -250,20 +268,23 @@ impl<'a> NbglHomeAndSettings { for (i, setting) in self.setting_contents.iter().enumerate() { SWITCH_ARRAY[i].text = setting[0].as_ptr(); SWITCH_ARRAY[i].subText = setting[1].as_ptr(); - let state = if let Some(data) = NVM_REF.as_mut() { + let state = if let Some(data) = (*(&raw mut NVM_REF)).as_mut() { data.get_ref()[i] } else { OFF_STATE }; SWITCH_ARRAY[i].initState = state; SWITCH_ARRAY[i].token = (FIRST_USER_TOKEN + i as u32) as u8; - SWITCH_ARRAY[i].tuneId = TuneIndex::TapCasual as u8; + #[cfg(any(target_os = "stax", target_os = "flex"))] + { + SWITCH_ARRAY[i].tuneId = TuneIndex::TapCasual as u8; + } } self.content = nbgl_content_t { content: nbgl_content_u { switchesList: nbgl_pageSwitchesList_s { - switches: &SWITCH_ARRAY as *const nbgl_contentSwitch_t, + switches: &raw const SWITCH_ARRAY as *const nbgl_contentSwitch_t, nbSwitches: self.nb_settings, }, }, @@ -276,18 +297,24 @@ impl<'a> NbglHomeAndSettings { __bindgen_anon_1: nbgl_genericContents_t__bindgen_ty_1 { contentsList: &self.content as *const nbgl_content_t, }, - nbContents: if self.nb_settings > 0 { 1 } else { 0 }, + nbContents: self.nb_settings, }; nbgl_useCaseHomeAndSettings( self.app_name.as_ptr() as *const c_char, &self.icon as *const nbgl_icon_details_t, - core::ptr::null(), + match self.tag_line { + None => core::ptr::null(), + Some(ref tag) => tag.as_ptr() as *const c_char, + }, match self.start_page { PageIndex::Home => INIT_HOME_PAGE as u8, PageIndex::Settings(idx) => idx, }, - &self.generic_contents as *const nbgl_genericContents_t, + match self.nb_settings { + 0 => core::ptr::null(), + _ => &self.generic_contents as *const nbgl_genericContents_t, + }, &self.info_list as *const nbgl_contentInfoList_t, core::ptr::null(), Some(quit_cb), diff --git a/ledger_device_sdk/src/nbgl/nbgl_review.rs b/ledger_device_sdk/src/nbgl/nbgl_review.rs index 8c9567b5..7a5daa1c 100644 --- a/ledger_device_sdk/src/nbgl/nbgl_review.rs +++ b/ledger_device_sdk/src/nbgl/nbgl_review.rs @@ -17,9 +17,9 @@ impl SyncNBGL for NbglReview<'_> {} impl<'a> NbglReview<'a> { pub fn new() -> NbglReview<'a> { NbglReview { - title: CString::new("").unwrap(), - subtitle: CString::new("").unwrap(), - finish_title: CString::new("").unwrap(), + title: CString::default(), + subtitle: CString::default(), + finish_title: CString::default(), glyph: None, tx_type: TransactionType::Transaction, blind: false, @@ -130,9 +130,18 @@ impl<'a> NbglReview<'a> { self.tx_type.to_c_type(false), &tag_value_list as *const nbgl_contentTagValueList_t, &icon as *const nbgl_icon_details_t, - self.title.as_ptr() as *const c_char, - self.subtitle.as_ptr() as *const c_char, - self.finish_title.as_ptr() as *const c_char, + match self.title.is_empty() { + true => core::ptr::null(), + false => self.title.as_ptr() as *const c_char, + }, + match self.subtitle.is_empty() { + true => core::ptr::null(), + false => self.subtitle.as_ptr() as *const c_char, + }, + match self.finish_title.is_empty() { + true => core::ptr::null(), + false => self.finish_title.as_ptr() as *const c_char, + }, Some(choice_callback), ); } diff --git a/ledger_device_sdk/src/nbgl/nbgl_spinner.rs b/ledger_device_sdk/src/nbgl/nbgl_spinner.rs index 83c99368..b13ff56b 100644 --- a/ledger_device_sdk/src/nbgl/nbgl_spinner.rs +++ b/ledger_device_sdk/src/nbgl/nbgl_spinner.rs @@ -1,28 +1,34 @@ use super::*; +extern crate alloc; +use alloc::ffi::CString; /// A wrapper around the asynchronous NBGL nbgl_useCaseSpinner C API binding. /// Draws a spinner page with the given parameters. The spinner will "turn" automatically every /// 800 ms, provided the IO event loop is running to process TickerEvents. +#[derive(Debug, Default)] pub struct NbglSpinner { - text: CString, + text: [CString; 2], + write_idx: usize, + read_idx: usize, } impl NbglSpinner { pub fn new() -> NbglSpinner { NbglSpinner { - text: CString::new("").unwrap(), + text: [CString::default(), CString::default()], + write_idx: 0, + read_idx: 0, } } - pub fn text(self, text: &str) -> NbglSpinner { - NbglSpinner { - text: CString::new(text).unwrap(), - } - } - - pub fn show(&self) { + /// Shows the spinner with the current text. + /// Every call make the spinner "turn" to the next text. + pub fn show(&mut self, text: &str) { + self.text[self.write_idx] = CString::new(text).unwrap(); + self.read_idx = self.write_idx; + self.write_idx = (self.write_idx + 1) % 2; unsafe { - nbgl_useCaseSpinner(self.text.as_ptr() as *const c_char); + nbgl_useCaseSpinner(self.text[self.read_idx].as_ptr() as *const c_char); } } } diff --git a/ledger_device_sdk/src/nvm.rs b/ledger_device_sdk/src/nvm.rs index fe343bf5..de0caa24 100644 --- a/ledger_device_sdk/src/nvm.rs +++ b/ledger_device_sdk/src/nvm.rs @@ -184,8 +184,6 @@ macro_rules! atomic_storage { }; } -#[cfg(target_os = "nanos")] -atomic_storage!(64); #[cfg(target_os = "nanox")] atomic_storage!(256); #[cfg(any(target_os = "nanosplus", target_os = "stax", target_os = "flex"))] diff --git a/ledger_device_sdk/src/seph.rs b/ledger_device_sdk/src/seph.rs index 666776c3..2f902519 100644 --- a/ledger_device_sdk/src/seph.rs +++ b/ledger_device_sdk/src/seph.rs @@ -2,7 +2,7 @@ use ledger_secure_sdk_sys::*; -#[cfg(target_os = "nanox")] +#[cfg(any(target_os = "nanox", target_os = "stax", target_os = "flex"))] use crate::ble; #[repr(u8)] @@ -112,8 +112,8 @@ pub fn handle_usb_event(event: u8) { match Events::from(event) { Events::USBEventReset => { unsafe { - USBD_LL_SetSpeed(&mut USBD_Device, 1 /*USBD_SPEED_FULL*/); - USBD_LL_Reset(&mut USBD_Device); + USBD_LL_SetSpeed(&raw mut USBD_Device, 1 /*USBD_SPEED_FULL*/); + USBD_LL_Reset(&raw mut USBD_Device); if G_io_app.apdu_media != IO_APDU_MEDIA_NONE { return; @@ -124,13 +124,13 @@ pub fn handle_usb_event(event: u8) { } } Events::USBEventSOF => unsafe { - USBD_LL_SOF(&mut USBD_Device); + USBD_LL_SOF(&raw mut USBD_Device); }, Events::USBEventSuspend => unsafe { - USBD_LL_Suspend(&mut USBD_Device); + USBD_LL_Suspend(&raw mut USBD_Device); }, Events::USBEventResume => unsafe { - USBD_LL_Resume(&mut USBD_Device); + USBD_LL_Resume(&raw mut USBD_Device); }, _ => (), } @@ -140,13 +140,13 @@ pub fn handle_usb_ep_xfer_event(apdu_buffer: &mut [u8], buffer: &[u8]) { let endpoint = buffer[3] & 0x7f; match UsbEp::from(buffer[4]) { UsbEp::USBEpXFERSetup => unsafe { - USBD_LL_SetupStage(&mut USBD_Device, &buffer[6]); + USBD_LL_SetupStage(&raw mut USBD_Device, &buffer[6]); }, UsbEp::USBEpXFERIn => { if (endpoint as u32) < IO_USB_MAX_ENDPOINTS { unsafe { G_io_app.usb_ep_timeouts[endpoint as usize].timeout = 0; - USBD_LL_DataInStage(&mut USBD_Device, endpoint, &buffer[6]); + USBD_LL_DataInStage(&raw mut USBD_Device, endpoint, &buffer[6]); } } } @@ -158,7 +158,7 @@ pub fn handle_usb_ep_xfer_event(apdu_buffer: &mut [u8], buffer: &[u8]) { buf: apdu_buffer.as_mut_ptr(), len: 260, }; - USBD_LL_DataOutStage(&mut USBD_Device, endpoint, &buffer[6], &mut apdu_buf); + USBD_LL_DataOutStage(&raw mut USBD_Device, endpoint, &buffer[6], &mut apdu_buf); } } } @@ -167,19 +167,21 @@ pub fn handle_usb_ep_xfer_event(apdu_buffer: &mut [u8], buffer: &[u8]) { } pub fn handle_capdu_event(apdu_buffer: &mut [u8], buffer: &[u8]) { - let io_app = unsafe { &mut G_io_app }; - if io_app.apdu_state == APDU_IDLE { - let max = (apdu_buffer.len() - 3).min(buffer.len() - 3); - let size = u16::from_be_bytes([buffer[1], buffer[2]]) as usize; + let io_app = &raw mut G_io_app; + unsafe { + if (*io_app).apdu_state == APDU_IDLE { + let max = (apdu_buffer.len() - 3).min(buffer.len() - 3); + let size = u16::from_be_bytes([buffer[1], buffer[2]]) as usize; - io_app.apdu_media = IO_APDU_MEDIA_RAW; - io_app.apdu_state = APDU_RAW; + (*io_app).apdu_media = IO_APDU_MEDIA_RAW; + (*io_app).apdu_state = APDU_RAW; - let len = size.min(max); + let len = size.min(max); - io_app.apdu_length = len as u16; + (*io_app).apdu_length = len as u16; - apdu_buffer[..len].copy_from_slice(&buffer[3..len + 3]); + apdu_buffer[..len].copy_from_slice(&buffer[3..len + 3]); + } } } @@ -196,10 +198,15 @@ pub fn handle_event(apdu_buffer: &mut [u8], spi_buffer: &[u8]) { handle_usb_ep_xfer_event(apdu_buffer, spi_buffer); } } - #[cfg(target_os = "nanox")] + #[cfg(any(target_os = "nanox", target_os = "stax", target_os = "flex"))] Events::BleReceive => ble::receive(apdu_buffer, spi_buffer), Events::CAPDUEvent => handle_capdu_event(apdu_buffer, spi_buffer), - Events::TickerEvent => { /* unsafe{ G_io_app.ms += 100; } */ } + Events::TickerEvent => { + #[cfg(any(target_os = "stax", target_os = "flex", feature = "nano_nbgl"))] + unsafe { + ux_process_ticker_event(); + } + } _ => (), } } diff --git a/ledger_device_sdk/src/testing.rs b/ledger_device_sdk/src/testing.rs index 1cebb21c..e80e7f84 100644 --- a/ledger_device_sdk/src/testing.rs +++ b/ledger_device_sdk/src/testing.rs @@ -1,8 +1,11 @@ -use core::arch::asm; use core::panic::PanicInfo; +#[cfg(feature = "debug")] +use core::arch::asm; + /// Debug 'print' function that uses ARM semihosting /// Prints only strings with no formatting +#[cfg(feature = "debug")] pub fn debug_print(s: &str) { let p = s.as_bytes().as_ptr(); for i in 0..s.len() { @@ -16,6 +19,8 @@ pub fn debug_print(s: &str) { } } } +#[cfg(not(feature = "debug"))] +pub fn debug_print(_s: &str) {} pub fn to_hex(m: u32) -> [u8; 8] { let mut hex = [0u8; 8]; diff --git a/ledger_device_sdk/src/ui.rs b/ledger_device_sdk/src/ui.rs index 2b05ba48..6017c03e 100644 --- a/ledger_device_sdk/src/ui.rs +++ b/ledger_device_sdk/src/ui.rs @@ -2,12 +2,8 @@ pub mod bagls; -#[cfg(not(target_os = "nanos"))] pub mod string_se; -#[cfg(target_os = "nanos")] -pub mod string_mcu; - pub mod bitmaps; pub mod fonts; pub mod layout; @@ -19,8 +15,4 @@ pub const PADDING: usize = 2; pub const Y_PADDING: usize = 3; pub const SCREEN_WIDTH: usize = 128; -#[cfg(target_os = "nanos")] -pub const SCREEN_HEIGHT: usize = 32; - -#[cfg(not(target_os = "nanos"))] pub const SCREEN_HEIGHT: usize = 64; diff --git a/ledger_device_sdk/src/ui/bagls.rs b/ledger_device_sdk/src/ui/bagls.rs index b4b4c96b..830f52c2 100644 --- a/ledger_device_sdk/src/ui/bagls.rs +++ b/ledger_device_sdk/src/ui/bagls.rs @@ -1,11 +1,4 @@ -#[cfg(target_os = "nanos")] -pub mod mcu; -#[cfg(target_os = "nanos")] -pub use self::mcu::*; - -#[cfg(not(target_os = "nanos"))] pub mod se; -#[cfg(not(target_os = "nanos"))] pub use self::se::*; use bitmaps::Glyph; diff --git a/ledger_device_sdk/src/ui/bagls/mcu.rs b/ledger_device_sdk/src/ui/bagls/mcu.rs deleted file mode 100644 index c41cbe20..00000000 --- a/ledger_device_sdk/src/ui/bagls/mcu.rs +++ /dev/null @@ -1,451 +0,0 @@ -use super::Icon; -use crate::ui::layout::{Draw, Layout, Location}; -use ledger_secure_sdk_sys; -use ledger_secure_sdk_sys::seph::SephTags; - -#[repr(u8)] -pub enum BaglTypes { - NoneType = 0, - Button = 1, - Label = 2, - Rectangle = 3, - Line = 4, - Icon = 5, - Circle = 6, - LabelLine = 7, -} - -pub const BAGL_FONT_ALIGNMENT_CENTER: u32 = 32768; - -#[repr(C)] -pub struct BaglComponent { - pub type_: u8, - pub userid: u8, - pub x: i16, - pub y: i16, - pub width: u16, - pub height: u16, - pub stroke: u8, - pub radius: u8, - pub fill: u8, - pub fgcolor: u32, - pub bgcolor: u32, - pub font_id: u16, - pub icon_id: u8, -} - -impl BaglComponent { - pub fn paint(&self) { - let bagl_comp = unsafe { - core::slice::from_raw_parts( - self as *const BaglComponent as *const u8, - core::mem::size_of::(), - ) - }; - - ledger_secure_sdk_sys::seph::seph_send(&[ - SephTags::ScreenDisplayStatus as u8, - 0, - bagl_comp.len() as u8, - ]); - ledger_secure_sdk_sys::seph::seph_send(bagl_comp); - } -} - -pub trait SendToDisplay { - fn wait_for_status(&self) { - if ledger_secure_sdk_sys::seph::is_status_sent() { - // TODO: this does not seem like the right way to fix the problem... - let mut spi_buffer = [0u8; 16]; - ledger_secure_sdk_sys::seph::seph_recv(&mut spi_buffer, 0); - } - } - fn paint(&self); - fn send_to_display(&self) { - BLANK.paint(); - self.paint(); - } -} - -pub enum Bagl<'a> { - LABELLINE(Label<'a>), - RECT(Rect), - ICON(Icon<'a>), -} - -impl Bagl<'_> { - /// Erase screen and display the bagl - pub fn display(&self) { - match self { - Bagl::LABELLINE(x) => x.send_to_display(), - Bagl::RECT(x) => x.send_to_display(), - Bagl::ICON(x) => x.send_to_display(), - } - } - - /// Only paint to current screen (draw over) - pub fn paint(&self) { - match self { - Bagl::LABELLINE(x) => x.paint(), - Bagl::RECT(x) => x.paint(), - Bagl::ICON(x) => x.paint(), - } - } -} - -#[repr(C)] -pub struct bagl_element_rs<'a> { - pub component: BaglComponent, - pub text: Option<&'a str>, -} - -impl Draw for Icon<'_> { - fn display(&self) { - self.paint(); - } - fn erase(&self) { - let icon = ledger_secure_sdk_sys::pic_rs(self.icon); - Rect::new() - .pos(self.pos.0, self.pos.1) - .dims(icon.width as u16, icon.height as u16) - .colors(0, 0xffffff) - .fill(true) - .paint(); - } -} - -#[repr(u8)] -pub enum Font { - LucidaConsole8px = 0, - OpenSansLight16_22px, - OpenSansRegular8_11px, - OpenSansRegular10_13px, - OpenSansRegular11_14px, - OpenSansRegular13_18px, - OpenSansRegular22_30px, - OpenSansSemibold8_11px, - OpenSansExtrabold11px, - OpenSansLight16px, - OpenSansRegular11px, - OpenSansSemibold10_13px, - OpenSansSemibold11_16px, - OpenSansSemibold13_18px, - Symbols0, - Symbols1, -} - -#[derive(Clone, Copy)] -pub struct Label<'a> { - pub loc: Location, - pub layout: Layout, - pub dims: (u16, u16), - pub bold: bool, - pub text: &'a str, -} - -impl Default for Label<'_> { - fn default() -> Self { - Label { - text: "", - bold: false, - dims: (128, 11), - loc: Location::Middle, - layout: Layout::Centered, - } - } -} - -impl<'a> Label<'a> { - pub const fn new() -> Self { - Label { - loc: Location::Middle, - layout: Layout::Centered, - dims: (128, 11), - bold: false, - text: "", - } - } - - pub const fn from_const(text: &'static str) -> Self { - Label { - loc: Location::Middle, - layout: Layout::Centered, - dims: (128, 11), - bold: false, - text, - } - } - - pub const fn location(self, loc: Location) -> Self { - Label { loc, ..self } - } - pub const fn layout(self, layout: Layout) -> Self { - Label { layout, ..self } - } - pub const fn dims(self, w: u16, h: u16) -> Self { - Label { - dims: (w, h), - ..self - } - } - pub const fn bold(self) -> Self { - Label { bold: true, ..self } - } - pub fn text(self, text: &'a str) -> Self { - Label { text, ..self } - } -} - -impl<'a> From<&'a str> for Label<'a> { - fn from(text: &'a str) -> Label<'a> { - Label::new().text(text) - } -} - -impl<'a> Draw for Label<'a> { - fn display(&self) { - self.paint(); - } - fn erase(&self) { - let x = self.layout.get_x(self.dims.0 as usize) as i16; - let y = self.loc.get_y(self.dims.1 as usize) as i16; - Rect::new() - .pos(x, y) - .dims(self.dims.0, self.dims.1) - .colors(0, 0xffffff) - .fill(true) - .paint(); - } -} - -pub struct Rect { - pub pos: (i16, i16), - pub dims: (u16, u16), - pub colors: (u32, u32), - pub fill: bool, - pub userid: u8, -} - -impl Rect { - pub const fn new() -> Rect { - Rect { - pos: (32 - 5, 64 - 5), - dims: (10, 10), - colors: (0xffffffu32, 0), - fill: false, - userid: 0, - } - } - pub const fn pos(self, x: i16, y: i16) -> Rect { - Rect { - pos: (x, y), - ..self - } - } - pub const fn colors(self, fg: u32, bg: u32) -> Rect { - Rect { - colors: (fg, bg), - ..self - } - } - pub const fn dims(self, w: u16, h: u16) -> Rect { - Rect { - dims: (w, h), - ..self - } - } - pub const fn fill(self, x: bool) -> Rect { - Rect { fill: x, ..self } - } - pub const fn userid(self, id: u8) -> Rect { - Rect { userid: id, ..self } - } -} - -impl Draw for Rect { - fn display(&self) { - self.paint(); - } - fn erase(&self) { - Rect::new() - .pos(self.pos.0, self.pos.1) - .dims(self.dims.0, self.dims.1) - .colors(0, 0xffffff) - .fill(true) - .paint(); - } -} - -impl Draw for RectFull { - fn display(&self) { - self.paint(); - } - fn erase(&self) { - Rect::new() - .pos(self.pos.0 as i16, self.pos.1 as i16) - .dims(self.width as u16, self.height as u16) - .colors(0, 0xffffff) - .fill(true) - .paint(); - } -} - -impl SendToDisplay for Icon<'_> { - fn paint(&self) { - self.wait_for_status(); - let icon = ledger_secure_sdk_sys::pic_rs(self.icon); - let baglcomp = BaglComponent { - type_: BaglTypes::Icon as u8, - userid: 0, - x: self.pos.0, - y: self.pos.1, - width: icon.width as u16, - height: icon.height as u16, - stroke: 0, - radius: 0, - fill: 0, - fgcolor: 0, - bgcolor: 0, - font_id: 0, - icon_id: 0, - }; - let bagl_comp = unsafe { - core::slice::from_raw_parts( - &baglcomp as *const BaglComponent as *const u8, - core::mem::size_of::(), - ) - }; - let lenbytes = ((bagl_comp.len() + 1 + (2 * 4) + icon.bitmap.len()) as u16).to_be_bytes(); - ledger_secure_sdk_sys::seph::seph_send(&[ - SephTags::ScreenDisplayStatus as u8, - lenbytes[0], - lenbytes[1], - ]); - ledger_secure_sdk_sys::seph::seph_send(bagl_comp); - // bpp (1), 'color_index' (2*4) - ledger_secure_sdk_sys::seph::seph_send(&[1, 0, 0, 0, 0, 0xff, 0xff, 0xff, 0]); - let bmp = unsafe { - core::slice::from_raw_parts( - ledger_secure_sdk_sys::pic(icon.bitmap.as_ptr() as *mut c_void) as *const u8, - icon.bitmap.len(), - ) - }; - ledger_secure_sdk_sys::seph::seph_send(bmp); - } -} - -impl SendToDisplay for Rect { - fn paint(&self) { - self.wait_for_status(); - let baglcomp = BaglComponent { - type_: BaglTypes::Rectangle as u8, - userid: self.userid, - x: self.pos.0, - y: self.pos.1, - width: self.dims.0, - height: self.dims.1, - stroke: 0, - radius: 0, - fill: self.fill as u8, - fgcolor: self.colors.0, - bgcolor: self.colors.1, - font_id: 0, - icon_id: 0, - }; - baglcomp.paint(); - } -} - -use super::RectFull; - -impl SendToDisplay for RectFull { - fn paint(&self) { - self.wait_for_status(); - let baglcomp = BaglComponent { - type_: BaglTypes::Rectangle as u8, - userid: 0, - x: self.pos.0 as i16, - y: self.pos.1 as i16, - width: self.width as u16, - height: self.height as u16, - stroke: 0, - radius: 0, - fill: 1, - fgcolor: 0xffffff, - bgcolor: 0, - font_id: 0, - icon_id: 0, - }; - baglcomp.paint(); - } -} - -use core::ffi::c_void; - -impl<'a> SendToDisplay for Label<'a> { - fn paint(&self) { - self.wait_for_status(); - let font_id = if self.bold { - Font::OpenSansExtrabold11px - } else { - Font::OpenSansRegular11px - }; - let x = match self.layout { - Layout::RightAligned => self.layout.get_x(self.text.len() * 7), - Layout::Custom(x) => x, - _ => 0, - }; - let y = self.loc.get_y(self.dims.1 as usize) as i16; - let width = match self.layout { - Layout::Centered => crate::ui::SCREEN_WIDTH, - _ => self.text.len() * 6, - }; - let alignment = match self.layout { - Layout::LeftAligned => 0_u16, - Layout::Centered => BAGL_FONT_ALIGNMENT_CENTER as u16, - Layout::RightAligned => BAGL_FONT_ALIGNMENT_CENTER as u16, - Layout::Custom(_) => 0_u16, - }; - let baglcomp = BaglComponent { - type_: BaglTypes::LabelLine as u8, - userid: 0, // FIXME - x: x as i16, - y: y - 1 + self.dims.1 as i16, - width: width as u16, //self.dims.0, - height: self.dims.1, - stroke: 0, - radius: 0, - fill: 0, - fgcolor: 0xffffffu32, - bgcolor: 0, - font_id: font_id as u16 | alignment, - icon_id: 0, - }; - - let bagl_comp = unsafe { - core::slice::from_raw_parts( - &baglcomp as *const BaglComponent as *const u8, - core::mem::size_of::(), - ) - }; - let lenbytes = ((bagl_comp.len() + self.text.len()) as u16).to_be_bytes(); - ledger_secure_sdk_sys::seph::seph_send(&[ - SephTags::ScreenDisplayStatus as u8, - lenbytes[0], - lenbytes[1], - ]); - ledger_secure_sdk_sys::seph::seph_send(bagl_comp); - - unsafe { - let pic_text = ledger_secure_sdk_sys::pic(self.text.as_ptr() as *mut u8 as *mut c_void); - ledger_secure_sdk_sys::io_seph_send(pic_text as *mut u8, self.text.len() as u16); - } - } -} - -/// Some common constant Bagls -pub const BLANK: Rect = Rect::new() - .pos(0, 0) - .dims(128, 32) - .colors(0, 0xffffff) - .fill(true); diff --git a/ledger_device_sdk/src/ui/gadgets.rs b/ledger_device_sdk/src/ui/gadgets.rs index f2de19d7..5a1e8066 100644 --- a/ledger_device_sdk/src/ui/gadgets.rs +++ b/ledger_device_sdk/src/ui/gadgets.rs @@ -42,25 +42,19 @@ pub fn get_event(buttons: &mut ButtonsState) -> Option { } pub fn clear_screen() { - #[cfg(not(target_os = "nanos"))] - { - #[cfg(not(feature = "speculos"))] - unsafe { - ledger_secure_sdk_sys::screen_clear(); - } - - #[cfg(feature = "speculos")] - { - // Speculos does not emulate the screen_clear syscall yet - RectFull::new() - .width(crate::ui::SCREEN_WIDTH as u32) - .height(crate::ui::SCREEN_HEIGHT as u32) - .erase(); - } + #[cfg(not(feature = "speculos"))] + unsafe { + ledger_secure_sdk_sys::screen_clear(); } - #[cfg(target_os = "nanos")] - BLANK.paint(); + #[cfg(feature = "speculos")] + { + // Speculos does not emulate the screen_clear syscall yet + RectFull::new() + .width(crate::ui::SCREEN_WIDTH as u32) + .height(crate::ui::SCREEN_HEIGHT as u32) + .erase(); + } } /// Display a developer mode / pending review popup, cleared with user interaction. @@ -89,18 +83,9 @@ pub fn display_pending_review(comm: &mut Comm) { clear_screen(); // Add icon and text to match the C SDK equivalent. - #[cfg(target_os = "nanos")] - { - "Pending".place(Location::Custom(2), Layout::Centered, true); - "Ledger review".place(Location::Custom(14), Layout::Centered, true); - } - - #[cfg(not(target_os = "nanos"))] - { - WARNING.draw(57, 10); - "Pending".place(Location::Custom(28), Layout::Centered, true); - "Ledger review".place(Location::Custom(42), Layout::Centered, true); - } + WARNING.draw(57, 10); + "Pending".place(Location::Custom(28), Layout::Centered, true); + "Ledger review".place(Location::Custom(42), Layout::Centered, true); crate::ui::screen_util::screen_update(); @@ -438,33 +423,20 @@ impl<'a> Page<'a> { self.label.place(Location::Middle, Layout::Centered, true); } PageStyle::PictureNormal => { - let mut icon_x = 16; - let mut icon_y = 8; - if cfg!(target_os = "nanos") { - self.label - .place(Location::Middle, Layout::Custom(41), false); - } else { - icon_x = 57; - icon_y = 10; - self.label - .place(Location::Custom(28), Layout::Centered, false); - } + let icon_x = 57; + let icon_y = 10; + self.label + .place(Location::Custom(28), Layout::Centered, false); if let Some(glyph) = self.glyph { let icon = Icon::from(glyph); icon.set_x(icon_x).set_y(icon_y).display(); } } PageStyle::PictureBold => { - let mut icon_x = 56; - let mut icon_y = 2; - if cfg!(target_os = "nanos") { - self.label[0].place(Location::Bottom, Layout::Centered, true); - } else { - icon_x = 57; - icon_y = 17; - self.label[0].place(Location::Custom(35), Layout::Centered, true); - self.label[1].place(Location::Custom(49), Layout::Centered, true); - } + let icon_x = 57; + let icon_y = 17; + self.label[0].place(Location::Custom(35), Layout::Centered, true); + self.label[1].place(Location::Custom(49), Layout::Centered, true); if let Some(glyph) = self.glyph { let icon = Icon::from(glyph); icon.set_x(icon_x).set_y(icon_y).display(); @@ -472,10 +444,7 @@ impl<'a> Page<'a> { } PageStyle::BoldNormal => { let padding = 1; - let mut max_text_lines = 3; - if cfg!(target_os = "nanos") { - max_text_lines = 1; - } + let max_text_lines = 3; let total_height = (OPEN_SANS[0].height * max_text_lines) as usize + OPEN_SANS[1].height as usize + 2 * padding as usize; @@ -484,29 +453,21 @@ impl<'a> Page<'a> { self.label[0].place(Location::Custom(cur_y), Layout::Centered, true); cur_y += OPEN_SANS[0].height as usize + 2 * padding as usize; - // If the device is a Nano S, display the second label as - // a single line of text - if cfg!(target_os = "nanos") { - self.label[1].place(Location::Custom(cur_y), Layout::Centered, false); - } - // Otherwise, display the second label as up to 3 lines of text - else { - let mut indices = [(0, 0); 3]; - let len = self.label[1].len(); - for (i, indice) in indices.iter_mut().enumerate() { - let start = (i * MAX_CHAR_PER_LINE).min(len); - if start >= len { - break; // Break if we reach the end of the string - } - let end = (start + MAX_CHAR_PER_LINE).min(len); - *indice = (start, end); - (&self.label[1][start..end]).place( - Location::Custom(cur_y), - Layout::Centered, - false, - ); - cur_y += OPEN_SANS[0].height as usize + 2 * padding as usize; + let mut indices = [(0, 0); 3]; + let len = self.label[1].len(); + for (i, indice) in indices.iter_mut().enumerate() { + let start = (i * MAX_CHAR_PER_LINE).min(len); + if start >= len { + break; // Break if we reach the end of the string } + let end = (start + MAX_CHAR_PER_LINE).min(len); + *indice = (start, end); + (&self.label[1][start..end]).place( + Location::Custom(cur_y), + Layout::Centered, + false, + ); + cur_y += OPEN_SANS[0].height as usize + 2 * padding as usize; } } } @@ -577,42 +538,42 @@ impl<'a> MultiPageMenu<'a> { loop { match self.comm.next_event() { - io::Event::Button(button) => match button { - BothButtonsRelease => return EventOrPageIndex::Index(index), - b => { - match b { - LeftButtonRelease => { - if index as i16 - 1 < 0 { - index = self.pages.len() - 1; - } else { - index = index.saturating_sub(1); + io::Event::Button(button) => { + if UxEvent::Event.request() == BOLOS_UX_OK { + match button { + BothButtonsRelease => return EventOrPageIndex::Index(index), + b => { + match b { + LeftButtonRelease => { + if index as i16 - 1 < 0 { + index = self.pages.len() - 1; + } else { + index = index.saturating_sub(1); + } + } + RightButtonRelease => { + if index < self.pages.len() - 1 { + index += 1; + } else { + index = 0; + } + } + _ => (), } + clear_screen(); + self.pages[index].place(); + LEFT_ARROW.display(); + RIGHT_ARROW.display(); + crate::ui::screen_util::screen_update(); } - RightButtonRelease => { - if index < self.pages.len() - 1 { - index += 1; - } else { - index = 0; - } - } - _ => (), } - clear_screen(); - self.pages[index].place(); - LEFT_ARROW.display(); - RIGHT_ARROW.display(); - crate::ui::screen_util::screen_update(); } - }, + } io::Event::Command(ins) => return EventOrPageIndex::Event(io::Event::Command(ins)), io::Event::Ticker => { if UxEvent::Event.request() != BOLOS_UX_OK { // pin lock management - let (_res, ins) = UxEvent::block_and_get_event::(self.comm); - if let Some(_e) = ins { - self.comm - .reply::(io::StatusWords::DeviceLocked); - } + UxEvent::block_and_get_event::(self.comm); // notify Ticker event only when redisplay is required return EventOrPageIndex::Event(io::Event::Ticker); } diff --git a/ledger_device_sdk/src/ui/layout.rs b/ledger_device_sdk/src/ui/layout.rs index f66f87fb..5be999bb 100644 --- a/ledger_device_sdk/src/ui/layout.rs +++ b/ledger_device_sdk/src/ui/layout.rs @@ -36,10 +36,6 @@ impl Location { } } -#[cfg(target_os = "nanos")] -pub const MAX_LINES: usize = 2; - -#[cfg(not(target_os = "nanos"))] pub const MAX_LINES: usize = 4; pub trait Place { diff --git a/ledger_device_sdk/src/ui/screen_util.rs b/ledger_device_sdk/src/ui/screen_util.rs index ce70a544..2fbcd148 100644 --- a/ledger_device_sdk/src/ui/screen_util.rs +++ b/ledger_device_sdk/src/ui/screen_util.rs @@ -24,7 +24,6 @@ pub fn fulldraw(x_pos: i32, y_pos: i32, bmp: &[u8]) { } pub fn screen_update() { - #[cfg(not(target_os = "nanos"))] unsafe { ledger_secure_sdk_sys::screen_update(); } diff --git a/ledger_device_sdk/src/ui/string_mcu.rs b/ledger_device_sdk/src/ui/string_mcu.rs deleted file mode 100644 index 13ea61a9..00000000 --- a/ledger_device_sdk/src/ui/string_mcu.rs +++ /dev/null @@ -1,65 +0,0 @@ -use crate::ui::bagls::*; -use crate::ui::layout::*; - -impl StringPlace for &str { - // unused when using MCU display - fn compute_width(&self, _bold: bool) -> usize { - 0 - } - - fn place(&self, loc: Location, layout: Layout, bold: bool) { - let mut lbl = Label::new() - .dims(128, 11) - .location(loc) - .layout(layout) - .text(self); - if bold { - lbl = lbl.bold(); - } - lbl.paint(); - } -} - -impl StringPlace for [&str] { - // unused when using MCU display - fn compute_width(&self, _bold: bool) -> usize { - 0 - } - - fn place(&self, loc: Location, layout: Layout, bold: bool) { - let c_height = 11; // Default font height - let total_height = self.len() * c_height; - let mut cur_y = loc.get_y(total_height); - for string in self.iter() { - string.place(Location::Custom(cur_y), layout, bold); - cur_y += c_height; - } - } -} - -impl<'a> StringPlace for Label<'a> { - fn compute_width(&self, _bold: bool) -> usize { - self.text.compute_width(self.bold) - } - - fn place(&self, loc: Location, layout: Layout, bold: bool) { - self.text.place(loc, layout, bold); - } -} - -impl<'a> StringPlace for [Label<'a>] { - fn compute_width(&self, bold: bool) -> usize { - self.iter() - .fold(0, |acc, lbl| acc.max(lbl.compute_width(bold))) - } - - fn place(&self, loc: Location, layout: Layout, _bold: bool) { - let padding = if self.len() > 4 { 0 } else { 2 }; - let total_height = self.iter().fold(0, |acc, _| acc + padding + 11); - let mut cur_y = loc.get_y(total_height); - for label in self.iter() { - label.place(Location::Custom(cur_y), layout, label.bold); - cur_y += 11 + padding; - } - } -} diff --git a/ledger_device_sdk/src/uxapp.rs b/ledger_device_sdk/src/uxapp.rs index 5354f27b..27e57a00 100644 --- a/ledger_device_sdk/src/uxapp.rs +++ b/ledger_device_sdk/src/uxapp.rs @@ -11,8 +11,8 @@ pub use ledger_secure_sdk_sys::BOLOS_UX_IGNORE; pub use ledger_secure_sdk_sys::BOLOS_UX_OK; pub use ledger_secure_sdk_sys::BOLOS_UX_REDRAW; -fn os_ux_rs(params: &bolos_ux_params_t) { - unsafe { os_ux(params as *const bolos_ux_params_t as *mut bolos_ux_params_t) }; +unsafe extern "C" { + pub unsafe static mut G_ux_params: bolos_ux_params_t; } #[repr(u8)] @@ -21,31 +21,43 @@ pub enum UxEvent { Keyboard = BOLOS_UX_KEYBOARD, WakeUp = BOLOS_UX_WAKE_UP, ValidatePIN = BOLOS_UX_VALIDATE_PIN, - LastID = BOLOS_UX_LAST_ID, + DelayLock = BOLOS_UX_DELAY_LOCK, + LastID = BOLOS_UX_DELAY_LOCK + 1, } impl UxEvent { + #[allow(unused)] pub fn request(&self) -> u32 { - let mut params = bolos_ux_params_t::default(); - params.ux_id = match self { - Self::Event => Self::Event as u8, - Self::Keyboard => Self::Keyboard as u8, - Self::WakeUp => Self::WakeUp as u8, - Self::ValidatePIN => { - // Perform pre-wake up - params.ux_id = Self::WakeUp as u8; - os_ux_rs(¶ms); + unsafe { + //let mut params = bolos_ux_params_t::default(); + G_ux_params.ux_id = match self { + Self::Event => Self::Event as u8, + Self::Keyboard => Self::Keyboard as u8, + Self::WakeUp => Self::WakeUp as u8, + Self::ValidatePIN => { + // Perform pre-wake up + G_ux_params.ux_id = Self::WakeUp as u8; + os_ux(&raw mut G_ux_params as *mut bolos_ux_params_t); - Self::ValidatePIN as u8 - } - Self::LastID => Self::LastID as u8, - }; + Self::ValidatePIN as u8 + } + Self::DelayLock => { + #[cfg(any(target_os = "stax", target_os = "flex", feature = "nano_nbgl"))] + { + G_ux_params.u.lock_delay.delay_ms = 10000; + } - os_ux_rs(¶ms); + Self::DelayLock as u8 + } + Self::LastID => panic!("Unknown UX Event"), + }; - match self { - Self::ValidatePIN => Self::block(), - _ => unsafe { os_sched_last_status(TASK_BOLOS_UX as u32) as u32 }, + os_ux(&raw mut G_ux_params as *mut bolos_ux_params_t); + + match self { + Self::ValidatePIN => Self::block(), + _ => os_sched_last_status(TASK_BOLOS_UX as u32) as u32, + } } } @@ -55,7 +67,7 @@ impl UxEvent { if unsafe { os_sched_is_running(TASK_SUBTASKS_START as u32) } != BOLOS_TRUE.try_into().unwrap() { - let mut spi_buffer = [0u8; 128]; + let mut spi_buffer = [0u8; 256]; sys_seph::send_general_status(); sys_seph::seph_recv(&mut spi_buffer, 0); UxEvent::Event.request(); @@ -78,7 +90,7 @@ impl UxEvent { if unsafe { os_sched_is_running(TASK_SUBTASKS_START as u32) } != BOLOS_TRUE.try_into().unwrap() { - let mut spi_buffer = [0u8; 128]; + let mut spi_buffer = [0u8; 256]; seph::send_general_status(); seph::seph_recv(&mut spi_buffer, 0); event = comm.decode_event(&mut spi_buffer); diff --git a/ledger_secure_sdk_sys/Cargo.toml b/ledger_secure_sdk_sys/Cargo.toml index 98a4fd0b..ba721419 100644 --- a/ledger_secure_sdk_sys/Cargo.toml +++ b/ledger_secure_sdk_sys/Cargo.toml @@ -1,7 +1,7 @@ [package] name = "ledger_secure_sdk_sys" -version = "1.5.3" -authors = ["yhql", "agrojean-ledger"] +version = "1.8.2" +authors = ["yhql", "agrojean-ledger", "yogh333"] edition = "2021" license.workspace = true repository.workspace = true @@ -18,3 +18,8 @@ critical-section = { version = "1.1.2", optional = true } [features] heap = ["dep:embedded-alloc", "dep:critical-section"] +nano_nbgl = [] + +[lints.rust.unexpected_cfgs] +level = "warn" +check-cfg = ['cfg(target_os, values("stax", "flex", "nanox", "nanosplus"))'] diff --git a/ledger_secure_sdk_sys/README.md b/ledger_secure_sdk_sys/README.md index 201a3584..bb493ba9 100644 --- a/ledger_secure_sdk_sys/README.md +++ b/ledger_secure_sdk_sys/README.md @@ -1,10 +1,11 @@ # Rust Low-level bindings to the Ledger C SDK +![Dynamic TOML Badge](https://img.shields.io/badge/dynamic/toml?url=https%3A%2F%2Fraw.githubusercontent.com%2FLedgerHQ%2Fledger-device-rust-sdk%2Frefs%2Fheads%2Fmaster%2Fledger_secure_sdk_sys%2FCargo.toml&query=%24.package.version&label=version) Provides access to low-level APIs to the operating system of Ledger devices. ## Build -Depending on the target (`--target nanos`, `--target nanox`, ...), this crate will `git clone` the appropriate branch (`API_LEVEL_x`) of the [C SDK](https://github.com/LedgerHQ/ledger-secure-sdk/) and compile the subset of files necessary for the [Rust SDK](https://github.com/LedgerHQ/ledger-nanos-sdk/) to work. +Depending on the target (`--target nanosplus`, `--target nanox`, ...), this crate will `git clone` the appropriate branch (`API_LEVEL_x`) of the [C SDK](https://github.com/LedgerHQ/ledger-secure-sdk/) and compile the subset of files necessary for the [Rust SDK](https://github.com/LedgerHQ/ledger-device-rust-sdk/) to work. To use an already-cloned C SDK, you can pass its path through the environment variable `LEDGER_SDK_PATH=/path/to/c_sdk` or through `cargo`'s `--config` flag: diff --git a/ledger_secure_sdk_sys/build.rs b/ledger_secure_sdk_sys/build.rs index 55ef49d8..4f263a94 100644 --- a/ledger_secure_sdk_sys/build.rs +++ b/ledger_secure_sdk_sys/build.rs @@ -3,15 +3,12 @@ use glob::glob; use std::fs; use std::path::{Path, PathBuf}; use std::process::Command; +use std::time::Instant; use std::{env, fs::File, io::BufRead, io::BufReader, io::Read}; -#[cfg(feature = "ccid")] -const DEFINES_CCID: [(&str, Option<&str>); 2] = - [("HAVE_USB_CLASS_CCID", None), ("HAVE_CCID", None)]; - const AUX_C_FILES: [&str; 2] = ["./src/c/src.c", "./src/c/sjlj.s"]; -const SDK_C_FILES: [&str; 8] = [ +const SDK_C_FILES: [&str; 9] = [ "src/os_io_usb.c", "src/pic.c", "src/checks.c", @@ -20,6 +17,7 @@ const SDK_C_FILES: [&str; 8] = [ "src/svc_call.s", "src/svc_cx_call.s", "src/syscalls.c", + "src/os_printf.c", ]; const SDK_USB_FILES: [&str; 6] = [ @@ -31,43 +29,90 @@ const SDK_USB_FILES: [&str; 6] = [ "lib_stusb/STM32_USB_Device_Library/Class/HID/Src/usbd_hid.c", ]; -#[cfg(feature = "ccid")] -const CCID_FILES: [&str; 9] = [ - "lib_stusb/STM32_USB_Device_Library/Class/CCID/src/usbd_ccid_cmd.c", - "lib_stusb/STM32_USB_Device_Library/Class/CCID/src/usbd_ccid_core.c", - "lib_stusb/STM32_USB_Device_Library/Class/CCID/src/usbd_ccid_if.c", - "lib_stusb/STM32_USB_Device_Library/Class/CCID/src/usbd_ccid_cmd.c", - "lib_stusb/STM32_USB_Device_Library/Class/CCID/src/usbd_ccid_core.c", - "lib_stusb/STM32_USB_Device_Library/Class/CCID/src/usbd_ccid_if.c", - "lib_stusb/STM32_USB_Device_Library/Class/CCID/src/usbd_ccid_cmd.c", - "lib_stusb/STM32_USB_Device_Library/Class/CCID/src/usbd_ccid_core.c", - "lib_stusb/STM32_USB_Device_Library/Class/CCID/src/usbd_ccid_if.c", +const CFLAGS_NANOSPLUS: [&str; 22] = [ + "-Oz", + "-g0", + "-fomit-frame-pointer", + "-momit-leaf-frame-pointer", + "-fno-common", + "-mlittle-endian", + "-std=gnu99", + "-fdata-sections", + "-ffunction-sections", + "-funsigned-char", + "-fshort-enums", + "-mno-unaligned-access", + "-fropi", + "-fno-jump-tables", + "-nostdlib", + "-nodefaultlibs", + "-frwpi", + "--target=armv8m-none-eabi", + "-mcpu=cortex-m35p+nodsp", + "-mthumb", + "-msoft-float", + "-Wno-unused-command-line-argument", +]; +const CFLAGS_STAX: [&str; 22] = CFLAGS_NANOSPLUS; +const CFLAGS_FLEX: [&str; 22] = CFLAGS_NANOSPLUS; +const CFLAGS_NANOX: [&str; 21] = [ + "-Oz", + "-g0", + "-fomit-frame-pointer", + "-momit-leaf-frame-pointer", + "-fno-common", + "-mlittle-endian", + "-std=gnu99", + "-fdata-sections", + "-ffunction-sections", + "-funsigned-char", + "-fshort-enums", + "-mno-unaligned-access", + "-fropi", + "-fno-jump-tables", + "-nostdlib", + "-nodefaultlibs", + "-frwpi", + "-mthumb", + "--target=armv6m-none-eabi", + "-mcpu=cortex-m0plus", + "-Wno-unused-command-line-argument", ]; -#[derive(Debug, PartialEq)] -enum Device { - NanoS, +#[derive(Debug, Default, PartialEq)] +enum DeviceName { + #[default] NanoSPlus, NanoX, Stax, Flex, } -impl std::fmt::Display for Device { +#[derive(Debug, Default)] +struct Device<'a> { + pub name: DeviceName, + pub c_sdk: PathBuf, + pub target: &'a str, + pub defines: Vec<(String, Option)>, + pub cflags: Vec<&'a str>, + pub glyphs_folders: Vec, + pub arm_libs: String, + pub linker_script: &'a str, +} + +impl std::fmt::Display for DeviceName { fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { match self { - Device::NanoS => write!(f, "nanos"), - Device::NanoSPlus => write!(f, "nanos2"), - Device::NanoX => write!(f, "nanox"), - Device::Stax => write!(f, "stax"), - Device::Flex => write!(f, "flex"), + DeviceName::NanoSPlus => write!(f, "nanos2"), + DeviceName::NanoX => write!(f, "nanox"), + DeviceName::Stax => write!(f, "stax"), + DeviceName::Flex => write!(f, "flex"), } } } #[derive(Default)] -struct SDKInfo { - pub bolos_sdk: PathBuf, +struct CSDKInfo { pub api_level: Option, pub target_id: String, pub target_name: String, @@ -76,237 +121,41 @@ struct SDKInfo { pub c_sdk_version: String, } -impl SDKInfo { +impl CSDKInfo { pub fn new() -> Self { - SDKInfo::default() + CSDKInfo::default() } } -fn retrieve_sdk_info(device: &Device, path: &Path) -> Result { - let mut sdk_info = SDKInfo::new(); - sdk_info.bolos_sdk = path.to_path_buf(); - (sdk_info.api_level, sdk_info.c_sdk_name) = retrieve_makefile_infos(&sdk_info.bolos_sdk)?; - (sdk_info.target_id, sdk_info.target_name) = - retrieve_target_file_infos(device, &sdk_info.bolos_sdk)?; - (sdk_info.c_sdk_hash, sdk_info.c_sdk_version) = retrieve_sdk_git_info(&sdk_info.bolos_sdk); - Ok(sdk_info) -} - -fn retrieve_sdk_git_info(bolos_sdk: &Path) -> (String, String) { - let c_sdk_hash = match Command::new("git") - .arg("-C") - .arg(bolos_sdk) - .arg("describe") - .arg("--always") - .arg("--dirty") - .arg("--exclude") - .arg("*") - .arg("--abbrev=40") - .output() - .ok() - { - Some(output) => { - if output.stdout.is_empty() { - "None".to_string() - } else { - String::from_utf8(output.stdout).unwrap_or("None".to_string()) - } - } - None => "None".to_string(), - }; - - let c_sdk_version = match Command::new("git") - .arg("-C") - .arg(bolos_sdk) - .arg("describe") - .arg("--tags") - .arg("--exact-match") - .arg("--match") - .arg("v[0-9]*") - .arg("--dirty") - .output() - .ok() - { - Some(output) => { - if output.stdout.is_empty() { - "None".to_string() - } else { - String::from_utf8(output.stdout).unwrap_or("None".to_string()) - } - } - None => "None".to_string(), - }; - (c_sdk_hash, c_sdk_version) -} - -fn retrieve_makefile_infos(bolos_sdk: &Path) -> Result<(Option, String), SDKBuildError> { - let makefile_defines = - File::open(bolos_sdk.join("Makefile.defines")).expect("Could not find Makefile.defines"); - let mut api_level: Option = None; - let mut sdk_name: Option = None; - for line in BufReader::new(makefile_defines).lines().flatten() { - if let Some(value) = line.split(":=").nth(1).map(str::trim) { - if line.contains("API_LEVEL") && api_level.is_none() { - api_level = Some(value.parse().map_err(|_| SDKBuildError::InvalidAPILevel)?); - } else if line.contains("SDK_NAME") && sdk_name.is_none() { - sdk_name = Some(value.to_string().replace('\"', "")); - } - } - - if api_level.is_some() && sdk_name.is_some() { - // Both keys found, break out of the loop - break; - } - } - let sdk_name = sdk_name.ok_or(SDKBuildError::MissingSDKName)?; - Ok((api_level, sdk_name)) -} - -fn retrieve_target_file_infos( - device: &Device, - bolos_sdk: &Path, -) -> Result<(String, String), SDKBuildError> { - let prefix = if *device == Device::NanoS { - "".to_string() - } else { - format!("target/{}/", device) - }; - let target_file_path = bolos_sdk.join(format!("{}include/bolos_target.h", prefix)); - let target_file = - File::open(target_file_path).map_err(|_| SDKBuildError::TargetFileNotFound)?; - let mut target_id: Option = None; - let mut target_name: Option = None; - - for line in BufReader::new(target_file).lines().flatten() { - if target_id.is_none() && line.contains("#define TARGET_ID") { - target_id = Some( - line.split_whitespace() - .nth(2) - .ok_or("err") - .map_err(|_| SDKBuildError::MissingTargetId)? - .to_string(), - ); - } else if target_name.is_none() && line.contains("TARGET_") { - target_name = Some( - line.split_whitespace() - .nth(1) - .ok_or("err") - .map_err(|_| SDKBuildError::MissingTargetName)? - .to_string(), - ); - } - - if target_id.is_some() && target_name.is_some() { - // Both tokens found, break out of the loop - break; - } - } - - let target_id = target_id.ok_or(SDKBuildError::MissingTargetId)?; - let target_name = target_name.ok_or(SDKBuildError::MissingTargetName)?; - Ok((target_id, target_name)) -} - -/// Fetch the appropriate C SDK to build -fn clone_sdk(device: &Device) -> PathBuf { - let (repo_url, sdk_branch) = match device { - Device::NanoS => ( - Path::new("https://github.com/LedgerHQ/ledger-secure-sdk"), - "API_LEVEL_LNS", - ), - Device::NanoX => ( - Path::new("https://github.com/LedgerHQ/ledger-secure-sdk"), - "API_LEVEL_5", - ), - Device::NanoSPlus => ( - Path::new("https://github.com/LedgerHQ/ledger-secure-sdk"), - "API_LEVEL_5", - ), - Device::Stax => ( - Path::new("https://github.com/LedgerHQ/ledger-secure-sdk"), - "API_LEVEL_21", - ), - Device::Flex => ( - Path::new("https://github.com/LedgerHQ/ledger-secure-sdk"), - "API_LEVEL_21", - ), - }; - - let out_dir = env::var("OUT_DIR").unwrap(); - let bolos_sdk = Path::new(out_dir.as_str()).join("ledger-secure-sdk"); - if !bolos_sdk.exists() { - Command::new("git") - .arg("clone") - .arg(repo_url.to_str().unwrap()) - .arg("-b") - .arg(sdk_branch) - .arg(bolos_sdk.as_path()) - .output() - .ok(); - } - bolos_sdk -} - #[derive(Debug)] enum SDKBuildError { + UnsupportedDevice, InvalidAPILevel, MissingSDKName, + MissingSDKPath, TargetFileNotFound, MissingTargetId, MissingTargetName, } -/// Helper function to concatenate all paths in pathlist to bolos_sdk's path -fn str2path(bolos_sdk: &Path, pathlist: &[&str]) -> Vec { - pathlist - .iter() - .map(|p| bolos_sdk.join(p)) - .collect::>() -} - -/// Get all #define from a header file -fn header2define(headername: &str) -> Vec<(String, Option)> { - let mut headerfile = File::open(headername).unwrap(); - let mut header = String::new(); - headerfile.read_to_string(&mut header).unwrap(); - - header - .lines() - .filter_map(|line| { - if line.trim_start().starts_with("#define") { - let parts: Vec<&str> = line.split_whitespace().collect(); - match parts.len() { - 2 => Some((parts[1].to_string(), None)), - 3 => Some((parts[1].to_string(), Some(parts[2].to_string()))), - _ => None, - } - } else { - None - } - }) - .collect() -} - -struct SDKBuilder { - bolos_sdk: PathBuf, +struct SDKBuilder<'a> { api_level: u32, gcc_toolchain: PathBuf, - device: Device, + device: Device<'a>, cxdefines: Vec, } -impl SDKBuilder { +impl SDKBuilder<'_> { pub fn new() -> Self { SDKBuilder { - bolos_sdk: PathBuf::new(), api_level: 0, gcc_toolchain: PathBuf::new(), - device: Device::NanoS, + device: Device::default(), cxdefines: Vec::new(), } } - pub fn gcc_toolchain(&mut self) { + pub fn gcc_toolchain(&mut self) -> Result<(), SDKBuildError> { // Find out where the arm toolchain is located let output = Command::new("arm-none-eabi-gcc") .arg("-print-sysroot") @@ -319,42 +168,160 @@ impl SDKBuilder { .trim(); let gcc_toolchain = if sysroot.is_empty() { - String::from("/usr") + // path for Debian-based systems + String::from("/usr/lib/arm-none-eabi") } else { format!("{sysroot}") }; self.gcc_toolchain = PathBuf::from(gcc_toolchain); + Ok(()) } - pub fn device(&mut self) { + pub fn device(&mut self) -> Result<(), SDKBuildError> { + println!("cargo:rerun-if-env-changed=LEDGER_SDK_PATH"); // determine device - let device = match env::var_os("CARGO_CFG_TARGET_OS").unwrap().to_str().unwrap() { - "nanos" => Device::NanoS, - "nanosplus" => Device::NanoSPlus, - "nanox" => Device::NanoX, - "stax" => Device::Stax, - "flex" => Device::Flex, - target_name => panic!( - "invalid target `{target_name}`, expected one of `nanos`, `nanox`, `nanosplus`. Run with `-Z build-std=core --target=./.json`" - ), + self.device = match env::var_os("CARGO_CFG_TARGET_OS") + .unwrap() + .to_str() + .unwrap() + { + "nanosplus" => Device { + name: DeviceName::NanoSPlus, + c_sdk: match env::var("LEDGER_SDK_PATH").or_else(|_| env::var("NANOSP_SDK")) { + Ok(path) => PathBuf::from(path), + Err(_) => return Err(SDKBuildError::MissingSDKPath), + }, + target: "thumbv8m.main-none-eabi", + defines: { + let mut v = header2define("csdk_nanos2.h"); + if env::var_os("CARGO_FEATURE_NANO_NBGL").is_some() { + println!("cargo:warning=NBGL is built"); + v.push((String::from("HAVE_NBGL"), None)); + v.push((String::from("NBGL_STEP"), None)); + v.push((String::from("NBGL_USE_CASE"), None)); + } else { + println!("cargo:warning=BAGL is built"); + println!("cargo:rustc-env=C_SDK_GRAPHICS={}", "bagl"); + v.push((String::from("HAVE_BAGL"), None)); + } + v + }, + cflags: Vec::from(CFLAGS_NANOSPLUS), + glyphs_folders: Vec::new(), + arm_libs: Default::default(), + linker_script: "nanosplus_layout.ld", + }, + "nanox" => Device { + name: DeviceName::NanoX, + c_sdk: match env::var("LEDGER_SDK_PATH").or_else(|_| env::var("NANOX_SDK")) { + Ok(path) => PathBuf::from(path), + Err(_) => return Err(SDKBuildError::MissingSDKPath), + }, + target: "thumbv6m-none-eabi", + defines: { + let mut v = header2define("csdk_nanox.h"); + if env::var_os("CARGO_FEATURE_NANO_NBGL").is_some() { + println!("cargo:warning=NBGL is built"); + v.push((String::from("HAVE_NBGL"), None)); + v.push((String::from("NBGL_STEP"), None)); + v.push((String::from("NBGL_USE_CASE"), None)); + } else { + println!("cargo:warning=BAGL is built"); + println!("cargo:rustc-env=C_SDK_GRAPHICS={}", "bagl"); + v.push((String::from("HAVE_BAGL"), None)); + } + v + }, + cflags: Vec::from(CFLAGS_NANOX), + glyphs_folders: Vec::new(), + arm_libs: Default::default(), + linker_script: "nanox_layout.ld", + }, + "stax" => Device { + name: DeviceName::Stax, + c_sdk: match env::var("LEDGER_SDK_PATH").or_else(|_| env::var("STAX_SDK")) { + Ok(path) => PathBuf::from(path), + Err(_) => return Err(SDKBuildError::MissingSDKPath), + }, + target: "thumbv8m.main-none-eabi", + defines: header2define("csdk_stax.h"), + cflags: Vec::from(CFLAGS_STAX), + glyphs_folders: Vec::new(), + arm_libs: Default::default(), + linker_script: "stax_layout.ld", + }, + "flex" => Device { + name: DeviceName::Flex, + c_sdk: match env::var("LEDGER_SDK_PATH").or_else(|_| env::var("FLEX_SDK")) { + Ok(path) => PathBuf::from(path), + Err(_) => return Err(SDKBuildError::MissingSDKPath), + }, + target: "thumbv8m.main-none-eabi", + defines: header2define("csdk_flex.h"), + cflags: Vec::from(CFLAGS_FLEX), + glyphs_folders: Vec::new(), + arm_libs: Default::default(), + linker_script: "flex_layout.ld", + }, + _ => { + return Err(SDKBuildError::UnsupportedDevice); + } }; - self.device = device; - // export TARGET into env for 'infos.rs' - println!("cargo:rustc-env=TARGET={}", self.device); - println!("cargo:warning=Device is {:?}", self.device); - } - pub fn bolos_sdk(&mut self) -> Result<(), SDKBuildError> { - println!("cargo:rerun-if-env-changed=LEDGER_SDK_PATH"); - let sdk_path = match env::var("LEDGER_SDK_PATH") { - Err(_) => clone_sdk(&self.device), - Ok(path) => PathBuf::from(path), - }; + // set glyphs folders + match self.device.name { + DeviceName::Flex => { + self.device + .glyphs_folders + .push(self.device.c_sdk.join("lib_nbgl/glyphs/wallet")); + self.device + .glyphs_folders + .push(self.device.c_sdk.join("lib_nbgl/glyphs/64px")); + self.device + .glyphs_folders + .push(self.device.c_sdk.join("lib_nbgl/glyphs/40px")); + } + DeviceName::Stax => { + self.device + .glyphs_folders + .push(self.device.c_sdk.join("lib_nbgl/glyphs/wallet")); + self.device + .glyphs_folders + .push(self.device.c_sdk.join("lib_nbgl/glyphs/64px")); + self.device + .glyphs_folders + .push(self.device.c_sdk.join("lib_nbgl/glyphs/32px")); + } + _ => { + self.device + .glyphs_folders + .push(self.device.c_sdk.join("lib_nbgl/glyphs/nano")); + } + } - let sdk_info = retrieve_sdk_info(&self.device, &sdk_path)?; + // Set ARM pre-compiled libraries path + self.device.arm_libs = match self.device.name { + DeviceName::NanoX => { + let mut path = self.device.c_sdk.display().to_string(); + path.push_str("/arch/st33/lib"); + path + } + DeviceName::NanoSPlus | DeviceName::Flex | DeviceName::Stax => { + let mut path = self.device.c_sdk.display().to_string(); + path.push_str("/arch/st33k1/lib"); + path + } + }; - self.bolos_sdk = sdk_info.bolos_sdk; + // export TARGET into env for 'infos.rs' + println!("cargo:rustc-env=TARGET={}", self.device.name); + println!("cargo:warning=Device is {:?}", self.device.name); + Ok(()) + } + pub fn get_info(&mut self) -> Result<(), SDKBuildError> { + // Retrieve the C SDK information + let sdk_info = retrieve_csdk_info(&self.device, &self.device.c_sdk)?; match sdk_info.api_level { Some(api_level) => { self.api_level = api_level; @@ -362,12 +329,9 @@ impl SDKBuilder { println!("cargo:rustc-env=API_LEVEL={}", self.api_level); println!("cargo:warning=API_LEVEL is {}", self.api_level); } - None => { - if self.device != Device::NanoS { - return Err(SDKBuildError::InvalidAPILevel); - } - } + None => return Err(SDKBuildError::InvalidAPILevel), } + // Export other SDK infos into env for 'infos.rs' println!("cargo:rustc-env=TARGET_ID={}", sdk_info.target_id); println!("cargo:warning=TARGET_ID is {}", sdk_info.target_id); @@ -382,8 +346,8 @@ impl SDKBuilder { Ok(()) } - fn cxdefines(&mut self) { - let mut makefile = File::open(self.bolos_sdk.join("Makefile.conf.cx")) + fn cxdefines(&mut self) -> Result<(), SDKBuildError> { + let mut makefile = File::open(self.device.c_sdk.join("Makefile.conf.cx")) .expect("Could not find Makefile.conf.cx"); let mut content = String::new(); makefile.read_to_string(&mut content).unwrap(); @@ -398,9 +362,13 @@ impl SDKBuilder { cxdefines.push("NATIVE_LITTLE_ENDIAN".to_string()); self.cxdefines = cxdefines; + Ok(()) } - pub fn build_c_sdk(&self) { + pub fn build_c_sdk(&self) -> Result<(), SDKBuildError> { + // Generate glyphs + generate_glyphs(&self.device); + let mut command = cc::Build::new(); if env::var_os("CC").is_none() { command.compiler("clang"); @@ -408,60 +376,56 @@ impl SDKBuilder { // Let cc::Build determine CC from the environment variable } - // Test if the file lib_cxng/src/cx_exported_functions.c exists - // If it does, add it to the list of files to compile - let cxng_src = self.bolos_sdk.join("lib_cxng/src/cx_exported_functions.c"); - if cxng_src.exists() { - command.file(cxng_src); - } - command .files(&AUX_C_FILES) - .files(str2path(&self.bolos_sdk, &SDK_C_FILES)) - .files(str2path(&self.bolos_sdk, &SDK_USB_FILES)); + .files(str2path(&self.device.c_sdk, &SDK_C_FILES)) + .files(str2path(&self.device.c_sdk, &SDK_USB_FILES)); command = command .include(self.gcc_toolchain.join("include")) - .include(self.bolos_sdk.join("include")) - .include(self.bolos_sdk.join("lib_cxng/include")) - .include(self.bolos_sdk.join("lib_stusb")) - .include(self.bolos_sdk.join("lib_stusb_impl")) + .include(self.device.c_sdk.join("include")) + .include(self.device.c_sdk.join("lib_cxng/include")) + .include(self.device.c_sdk.join("lib_stusb")) + .include(self.device.c_sdk.join("lib_stusb_impl")) .include( - self.bolos_sdk + self.device + .c_sdk .join("lib_stusb/STM32_USB_Device_Library/Core/Inc"), ) .include( - self.bolos_sdk + self.device + .c_sdk .join("lib_stusb/STM32_USB_Device_Library/Class/HID/Inc"), ) .debug(true) - .flag("-Oz") - .flag("-fomit-frame-pointer") - .flag("-fno-common") - .flag("-fdata-sections") - .flag("-ffunction-sections") - .flag("-mthumb") - .flag("-fno-jump-tables") - .flag("-fshort-enums") - .flag("-mno-unaligned-access") - .flag("-Wno-unused-command-line-argument") + .define("main", "_start") .clone(); - // #[cfg(feature = "ccid")] - // { - // for (define, value) in DEFINES_CCID { - // command.define(define, value); - // } - // command.files(str2path(&self.bolos_sdk, &CCID_FILES)); - // } - - match self.device { - Device::NanoS => finalize_nanos_configuration(&mut command, &self.bolos_sdk), - Device::NanoX => finalize_nanox_configuration(&mut command, &self.bolos_sdk), - Device::NanoSPlus => finalize_nanosplus_configuration(&mut command, &self.bolos_sdk), - Device::Stax => finalize_stax_configuration(&mut command, &self.bolos_sdk), - Device::Flex => finalize_flex_configuration(&mut command, &self.bolos_sdk), - }; + // Set the #defines + for (define, value) in &self.device.defines { + command.define(define.as_str(), value.as_deref()); + } + + // Set the CFLAGS + for cflag in &self.device.cflags { + command.flag(cflag); + } + + command.target(self.device.target).include( + self.device + .c_sdk + .join(format!("target/{}/include", self.device.name)), + ); + + // Configure BLE and NBGL + for s in self.device.defines.iter() { + if s.0 == "HAVE_BLE" { + configure_lib_ble(&mut command, &self.device.c_sdk); + } + if s.0 == "HAVE_NBGL" { + configure_lib_nbgl(&mut command, &self.device.c_sdk); + } + } // Add the defines found in the Makefile.conf.cx to our build command. for define in self.cxdefines.iter() { @@ -470,14 +434,18 @@ impl SDKBuilder { command.compile("ledger-secure-sdk"); - /* Link with libc for unresolved symbols */ - let gcc_tc = self.gcc_toolchain.display().to_string(); + /* Link with libc, libm and libgcc */ + let path = self.device.arm_libs.clone(); println!("cargo:rustc-link-lib=c"); - println!("cargo:rustc-link-search={gcc_tc}/lib"); + println!("cargo:rustc-link-lib=m"); + println!("cargo:rustc-link-lib=gcc"); + + println!("cargo:rustc-link-search={path}"); + Ok(()) } - fn generate_bindings(&self) { - let bsdk = self.bolos_sdk.display().to_string(); + fn generate_bindings(&self) -> Result<(), SDKBuildError> { + let bsdk = self.device.c_sdk.display().to_string(); let gcc_tc = self.gcc_toolchain.display().to_string(); let args = [ "--target=thumbv6m-none-eabi".to_string(), // exact target is irrelevant for bindings @@ -488,9 +456,8 @@ impl SDKBuilder { format!("-I{bsdk}/lib_stusb/STM32_USB_Device_Library/Core/Inc/"), format!("-I{bsdk}/lib_stusb/"), ]; - let headers = str2path( - &self.bolos_sdk, + &self.device.c_sdk, &[ "lib_cxng/include/libcxng.h", /* cxlib */ "include/os.h", /* syscalls */ @@ -501,6 +468,7 @@ impl SDKBuilder { "include/ox.h", /* crypto-related syscalls */ "lib_stusb/STM32_USB_Device_Library/Core/Inc/usbd_def.h", "include/os_io_usb.h", + "lib_standard_app/swap_lib_calls.h", ], ); @@ -512,14 +480,10 @@ impl SDKBuilder { .use_core(); // Target specific files - let (include_path, header) = match self.device { - Device::NanoS => ("nanos", "sdk_nanos.h"), - Device::NanoX => ("nanox", "sdk_nanox.h"), - Device::NanoSPlus => ("nanos2", "sdk_nanosp.h"), - Device::Stax => ("stax", "sdk_stax.h"), - Device::Flex => ("flex", "sdk_flex.h"), - }; - bindings = bindings.clang_arg(format!("-I{bsdk}/target/{include_path}/include/")); + let csdk_target_name = self.device.name.to_string(); + let header = format!("csdk_{csdk_target_name}.h"); + + bindings = bindings.clang_arg(format!("-I{bsdk}/target/{csdk_target_name}/include/")); bindings = bindings.header(header); // SDK headers to bind against @@ -527,56 +491,50 @@ impl SDKBuilder { bindings = bindings.header(header); } - match self.device { - Device::NanoS => { - bindings = bindings.header(self.bolos_sdk.join("include/bagl.h").to_str().unwrap()) - } - Device::NanoX => { + // BAGL or NBGL bindings + if ((self.device.name == DeviceName::NanoX || self.device.name == DeviceName::NanoSPlus) + && env::var_os("CARGO_FEATURE_NANO_NBGL").is_some()) + || self.device.name == DeviceName::Stax + || self.device.name == DeviceName::Flex + { + let out_path = PathBuf::from(env::var("OUT_DIR").unwrap()); + let mut include_path = "-I".to_string(); + let glyphs = out_path.join("glyphs"); + include_path += glyphs.to_str().unwrap(); + bindings = bindings.clang_args([include_path.as_str()]); + + bindings = bindings.clang_args([ + format!("-I{bsdk}/lib_nbgl/include/").as_str(), + format!("-I{bsdk}/lib_ux_nbgl/").as_str(), + ]); + bindings = bindings + .header( + self.device + .c_sdk + .join("lib_nbgl/include/nbgl_use_case.h") + .to_str() + .unwrap(), + ) + .header( + self.device + .c_sdk + .join("lib_ux_nbgl/ux_nbgl.h") + .to_str() + .unwrap(), + ); + } + + // BLE bindings + match self.device.name { + DeviceName::NanoX | DeviceName::Flex | DeviceName::Stax => { bindings = bindings.header( - self.bolos_sdk + self.device + .c_sdk .join("lib_blewbxx_impl/include/ledger_ble.h") .to_str() .unwrap(), ) } - Device::Stax | Device::Flex => { - if Device::Stax == self.device { - bindings = bindings.clang_args(["-I./src/c/glyphs_stax"]); - } else { - bindings = bindings.clang_args(["-I./src/c/glyphs_flex"]); - } - - bindings = bindings.clang_args([ - format!("-I{bsdk}/lib_nbgl/include/").as_str(), - format!("-I{bsdk}/lib_ux_sync/include/").as_str(), - format!("-I{bsdk}/lib_ux_nbgl/").as_str(), - ]); - bindings = bindings - .header( - self.bolos_sdk - .join("lib_nbgl/include/nbgl_use_case.h") - .to_str() - .unwrap(), - ) - .header( - self.bolos_sdk - .join("lib_ux_sync/include/ux_sync.h") - .to_str() - .unwrap(), - ) - .header( - self.bolos_sdk - .join("lib_ux_nbgl/ux_nbgl.h") - .to_str() - .unwrap(), - ) - .header( - self.bolos_sdk - .join("lib_blewbxx_impl/include/ledger_ble.h") - .to_str() - .unwrap(), - ) - } _ => (), } @@ -594,9 +552,11 @@ impl SDKBuilder { bindings .write_to_file(out_path.join("bindings.rs")) .expect("Couldn't write bindings"); + + Ok(()) } - fn generate_heap_size(&self) { + fn generate_heap_size(&self) -> Result<(), SDKBuildError> { // Read the HEAP_SIZE environment variable, default to 8192 if not set let heap_size = env::var("HEAP_SIZE").unwrap_or_else(|_| "8192".to_string()); @@ -615,189 +575,310 @@ impl SDKBuilder { format!("pub const HEAP_SIZE: usize = {};", heap_size), ) .expect("Unable to write file"); + Ok(()) + } + + fn copy_linker_script(&self) -> Result<(), SDKBuildError> { + let out_dir = PathBuf::from(env::var_os("OUT_DIR").unwrap()); + // extend the library search path + println!("cargo:rustc-link-search={}", out_dir.display()); + // copy + std::fs::copy( + self.device.linker_script, + out_dir.join(self.device.linker_script), + ) + .unwrap(); + std::fs::copy("link.ld", out_dir.join("link.ld")).unwrap(); + Ok(()) } } fn main() { + let start = Instant::now(); let mut sdk_builder = SDKBuilder::new(); - sdk_builder.gcc_toolchain(); - sdk_builder.device(); - sdk_builder.bolos_sdk().unwrap(); - sdk_builder.cxdefines(); - sdk_builder.build_c_sdk(); - sdk_builder.generate_bindings(); - sdk_builder.generate_heap_size(); + sdk_builder.gcc_toolchain().unwrap(); + sdk_builder.device().unwrap(); + sdk_builder.get_info().unwrap(); + sdk_builder.cxdefines().unwrap(); + sdk_builder.build_c_sdk().unwrap(); + sdk_builder.generate_bindings().unwrap(); + sdk_builder.generate_heap_size().unwrap(); + sdk_builder.copy_linker_script().unwrap(); + let end = start.elapsed(); + println!( + "cargo:warning=Total build.rs time: {} seconds", + end.as_secs() + ); } -fn finalize_nanos_configuration(command: &mut cc::Build, bolos_sdk: &Path) { - let defines = header2define("sdk_nanos.h"); - for (define, value) in defines { - command.define(define.as_str(), value.as_deref()); - } +// -------------------------------------------------- +// Helper functions +// -------------------------------------------------- +fn configure_lib_ble(command: &mut cc::Build, c_sdk: &Path) { command - .target("thumbv6m-none-eabi") - .define("ST31", None) - .define("BAGL_HEIGHT", Some("32")) - .define("BAGL_WIDTH", Some("128")) - .include(bolos_sdk.join("target/nanos/include")) - .flag("-fropi"); + .file(c_sdk.join("src/ledger_protocol.c")) + .file(c_sdk.join("lib_blewbxx/core/auto/ble_gap_aci.c")) + .file(c_sdk.join("lib_blewbxx/core/auto/ble_gatt_aci.c")) + .file(c_sdk.join("lib_blewbxx/core/auto/ble_hal_aci.c")) + .file(c_sdk.join("lib_blewbxx/core/auto/ble_hci_le.c")) + .file(c_sdk.join("lib_blewbxx/core/auto/ble_l2cap_aci.c")) + .file(c_sdk.join("lib_blewbxx/core/template/osal.c")) + .file(c_sdk.join("lib_blewbxx_impl/src/ledger_ble.c")) + .include(c_sdk.join("lib_blewbxx/include")) + .include(c_sdk.join("lib_blewbxx/core")) + .include(c_sdk.join("lib_blewbxx/core/auto")) + .include(c_sdk.join("lib_blewbxx/core/template")) + .include(c_sdk.join("lib_blewbxx_impl/include")); } -fn finalize_nanox_configuration(command: &mut cc::Build, bolos_sdk: &Path) { - let defines = header2define("sdk_nanox.h"); - for (define, value) in defines { - command.define(define.as_str(), value.as_deref()); - } +fn configure_lib_nbgl(command: &mut cc::Build, c_sdk: &Path) { + println!("cargo:rustc-env=C_SDK_GRAPHICS={}", "nbgl"); + let glyphs_path = PathBuf::from(env::var("OUT_DIR").unwrap()).join("glyphs"); command - .target("thumbv6m-none-eabi") - .define("ST33", None) - .define("BAGL_HEIGHT", Some("64")) - .define("BAGL_WIDTH", Some("128")) - .file(bolos_sdk.join("src/ledger_protocol.c")) - .file(bolos_sdk.join("lib_blewbxx/core/auto/ble_gap_aci.c")) - .file(bolos_sdk.join("lib_blewbxx/core/auto/ble_gatt_aci.c")) - .file(bolos_sdk.join("lib_blewbxx/core/auto/ble_hal_aci.c")) - .file(bolos_sdk.join("lib_blewbxx/core/auto/ble_hci_le.c")) - .file(bolos_sdk.join("lib_blewbxx/core/auto/ble_l2cap_aci.c")) - .file(bolos_sdk.join("lib_blewbxx/core/template/osal.c")) - .file(bolos_sdk.join("lib_blewbxx_impl/src/ledger_ble.c")) - .include(bolos_sdk.join("lib_blewbxx/include")) - .include(bolos_sdk.join("lib_blewbxx/core")) - .include(bolos_sdk.join("lib_blewbxx/core/auto")) - .include(bolos_sdk.join("lib_blewbxx/core/template")) - .include(bolos_sdk.join("lib_blewbxx_impl/include")) - .include(bolos_sdk.join("target/nanox/include")) - .flag("-mno-movt") - .flag("-ffixed-r9") - .flag("-fropi") - .flag("-frwpi"); - configure_lib_bagl(command, bolos_sdk); + .include(c_sdk.join("lib_nbgl/include/")) + .include(c_sdk.join("lib_nbgl/include/fonts/")) + .include(c_sdk.join("lib_ux_nbgl/")) + .include(c_sdk.join("qrcode/include/")) + .include(c_sdk.join("lib_bagl/include/")) + .file(c_sdk.join("lib_ux_nbgl/ux.c")) + .file(c_sdk.join("qrcode/src/qrcodegen.c")) + .files( + glob(c_sdk.join("lib_nbgl/src/*.c").to_str().unwrap()) + .unwrap() + .map(|x| x.unwrap()) + .collect::>(), + ) + .include(&glyphs_path) + .file(glyphs_path.join("glyphs.c")); } -fn finalize_nanosplus_configuration(command: &mut cc::Build, bolos_sdk: &Path) { - let defines = header2define("sdk_nanosp.h"); - for (define, value) in defines { - command.define(define.as_str(), value.as_deref()); - } +fn retrieve_csdk_info(device: &Device, path: &PathBuf) -> Result { + let mut csdk_info = CSDKInfo::new(); + (csdk_info.api_level, csdk_info.c_sdk_name) = retrieve_makefile_infos(path)?; + (csdk_info.target_id, csdk_info.target_name) = retrieve_target_file_infos(device, path)?; + (csdk_info.c_sdk_hash, csdk_info.c_sdk_version) = retrieve_csdk_git_info(path); + Ok(csdk_info) +} - command - .target("thumbv8m.main-none-eabi") - .define("ST33K1M5", None) - .define("BAGL_HEIGHT", Some("64")) - .define("BAGL_WIDTH", Some("128")) - .include(bolos_sdk.join("target/nanos2/include")) - .flag("-fropi") - .flag("-frwpi"); - configure_lib_bagl(command, bolos_sdk); +fn retrieve_csdk_git_info(c_sdk: &Path) -> (String, String) { + let c_sdk_hash = match Command::new("git") + .arg("-C") + .arg(c_sdk) + .arg("describe") + .arg("--always") + .arg("--dirty") + .arg("--exclude") + .arg("*") + .arg("--abbrev=40") + .output() + .ok() + { + Some(output) => { + if output.stdout.is_empty() { + "None".to_string() + } else { + String::from_utf8(output.stdout).unwrap_or("None".to_string()) + } + } + None => "None".to_string(), + }; + + let c_sdk_version = match Command::new("git") + .arg("-C") + .arg(c_sdk) + .arg("describe") + .arg("--tags") + .arg("--match") + .arg("v[0-9]*") + .arg("--dirty") + .output() + .ok() + { + Some(output) => { + if output.status.success() { + String::from_utf8(output.stdout).unwrap_or("None".to_string()) + } else { + String::from_utf8(output.stderr).unwrap_or("None".to_string()) + } + } + None => "None".to_string(), + }; + (c_sdk_hash, c_sdk_version) } -fn configure_lib_bagl(command: &mut cc::Build, bolos_sdk: &Path) { - if env::var_os("CARGO_FEATURE_LIB_BAGL").is_some() { - command - .define("HAVE_BAGL", None) - // Just include all the fonts for now; we can shrink the X and S+ images later. - .define("HAVE_BAGL_FONT_LUCIDA_CONSOLE_8PX", None) - .define("HAVE_BAGL_FONT_OPEN_SANS_LIGHT_16_22PX", None) - .define("HAVE_BAGL_FONT_OPEN_SANS_REGULAR_8_11PX", None) - .define("HAVE_BAGL_FONT_OPEN_SANS_REGULAR_10_13PX", None) - .define("HAVE_BAGL_FONT_OPEN_SANS_REGULAR_11_14PX", None) - .define("HAVE_BAGL_FONT_OPEN_SANS_REGULAR_13_18PX", None) - .define("HAVE_BAGL_FONT_OPEN_SANS_REGULAR_22_30PX", None) - .define("HAVE_BAGL_FONT_OPEN_SANS_SEMIBOLD_8_11PX", None) - .define("HAVE_BAGL_FONT_OPEN_SANS_EXTRABOLD_11PX", None) - .define("HAVE_BAGL_FONT_OPEN_SANS_LIGHT_16PX", None) - .define("HAVE_BAGL_FONT_OPEN_SANS_REGULAR_11PX", None) - .define("HAVE_BAGL_FONT_OPEN_SANS_SEMIBOLD_10_13PX", None) - .define("HAVE_BAGL_FONT_OPEN_SANS_SEMIBOLD_11_16PX", None) - .define("HAVE_BAGL_FONT_OPEN_SANS_SEMIBOLD_13_18PX", None) - .define("HAVE_BAGL_FONT_SYMBOLS_0", None) - .define("HAVE_BAGL_FONT_SYMBOLS_1", None) - .include(bolos_sdk.join("lib_bagl/src/")) - .file(bolos_sdk.join("lib_bagl/src/bagl.c")) - .file(bolos_sdk.join("lib_bagl/src/bagl_fonts.c")) - .file(bolos_sdk.join("lib_bagl/src/bagl_glyphs.c")); +fn retrieve_makefile_infos(c_sdk: &Path) -> Result<(Option, String), SDKBuildError> { + let makefile = + File::open(c_sdk.join("Makefile.defines")).expect("Could not find Makefile.defines"); + let mut api_level: Option = None; + for line in BufReader::new(makefile).lines().flatten() { + if let Some(value) = line.split(":=").nth(1).map(str::trim) { + if line.contains("API_LEVEL") && api_level.is_none() { + api_level = Some(value.parse().map_err(|_| SDKBuildError::InvalidAPILevel)?); + } + } + if api_level.is_some() { + // Key found, break out of the loop + break; + } } + let makefile = + File::open(c_sdk.join("Makefile.target")).expect("Could not find Makefile.defines"); + let mut sdk_name: Option = None; + for line in BufReader::new(makefile).lines().flatten() { + if let Some(value) = line.split(":=").nth(1).map(str::trim) { + if line.contains("SDK_NAME") && sdk_name.is_none() { + sdk_name = Some(value.to_string().replace('\"', "")); + } + } + if sdk_name.is_some() { + // Key found, break out of the loop + break; + } + } + + let sdk_name = sdk_name.ok_or(SDKBuildError::MissingSDKName)?; + Ok((api_level, sdk_name)) } -fn finalize_stax_configuration(command: &mut cc::Build, bolos_sdk: &Path) { - let defines = header2define("sdk_stax.h"); - for (define, value) in defines { - command.define(define.as_str(), value.as_deref()); +fn retrieve_target_file_infos( + device: &Device, + c_sdk: &Path, +) -> Result<(String, String), SDKBuildError> { + let prefix = format!("target/{}/", device.name); + let target_file_path = c_sdk.join(format!("{}include/bolos_target.h", prefix)); + let target_file = + File::open(target_file_path).map_err(|_| SDKBuildError::TargetFileNotFound)?; + let mut target_id: Option = None; + let mut target_name: Option = None; + + for line in BufReader::new(target_file).lines().flatten() { + if target_id.is_none() && line.contains("#define TARGET_ID") { + target_id = Some( + line.split_whitespace() + .nth(2) + .ok_or("err") + .map_err(|_| SDKBuildError::MissingTargetId)? + .to_string(), + ); + } else if target_name.is_none() + && line.contains("#define TARGET_") + && !line.contains("#define TARGET_ID") + { + target_name = Some( + line.split_whitespace() + .nth(1) + .ok_or("err") + .map_err(|_| SDKBuildError::MissingTargetName)? + .to_string(), + ); + } + + if target_id.is_some() && target_name.is_some() { + // Both tokens found, break out of the loop + break; + } } - command - .target("thumbv8m.main-none-eabi") - .file(bolos_sdk.join("src/ledger_protocol.c")) - .file(bolos_sdk.join("lib_blewbxx/core/auto/ble_gap_aci.c")) - .file(bolos_sdk.join("lib_blewbxx/core/auto/ble_gatt_aci.c")) - .file(bolos_sdk.join("lib_blewbxx/core/auto/ble_hal_aci.c")) - .file(bolos_sdk.join("lib_blewbxx/core/auto/ble_hci_le.c")) - .file(bolos_sdk.join("lib_blewbxx/core/auto/ble_l2cap_aci.c")) - .file(bolos_sdk.join("lib_blewbxx/core/template/osal.c")) - .file(bolos_sdk.join("lib_blewbxx_impl/src/ledger_ble.c")) - .include(bolos_sdk.join("lib_blewbxx/include")) - .include(bolos_sdk.join("lib_blewbxx/core")) - .include(bolos_sdk.join("lib_blewbxx/core/auto")) - .include(bolos_sdk.join("lib_blewbxx/core/template")) - .include(bolos_sdk.join("lib_blewbxx_impl/include")) - .include(bolos_sdk.join("target/stax/include/")) - .flag("-fropi") - .flag("-frwpi") - .include("./src/c/glyphs_stax/") - .file("./src/c/glyphs_stax/glyphs.c"); - configure_lib_nbgl(command, bolos_sdk); + let target_id = target_id.ok_or(SDKBuildError::MissingTargetId)?; + let target_name = target_name.ok_or(SDKBuildError::MissingTargetName)?; + Ok((target_id, target_name)) +} + +/// Fetch the appropriate C SDK to build +#[allow(dead_code)] +fn clone_sdk(devicename: &DeviceName) -> PathBuf { + let (repo_url, sdk_branch) = match devicename { + DeviceName::NanoX => ( + Path::new("https://github.com/LedgerHQ/ledger-secure-sdk"), + "API_LEVEL_22", + ), + DeviceName::NanoSPlus => ( + Path::new("https://github.com/LedgerHQ/ledger-secure-sdk"), + "API_LEVEL_22", + ), + DeviceName::Stax => ( + Path::new("https://github.com/LedgerHQ/ledger-secure-sdk"), + "API_LEVEL_22", + ), + DeviceName::Flex => ( + Path::new("https://github.com/LedgerHQ/ledger-secure-sdk"), + "API_LEVEL_22", + ), + }; + + let out_dir = env::var("OUT_DIR").unwrap(); + let c_sdk = Path::new(out_dir.as_str()).join("ledger-secure-sdk"); + if !c_sdk.exists() { + Command::new("git") + .arg("clone") + .arg(repo_url.to_str().unwrap()) + .arg("-b") + .arg(sdk_branch) + .arg(c_sdk.as_path()) + .output() + .ok(); + } + c_sdk } -fn finalize_flex_configuration(command: &mut cc::Build, bolos_sdk: &Path) { - let defines = header2define("sdk_flex.h"); - for (define, value) in defines { - command.define(define.as_str(), value.as_deref()); +fn generate_glyphs(device: &Device) { + let icon2glyph = device.c_sdk.join("lib_nbgl/tools/icon2glyph.py"); + + let out_path = PathBuf::from(env::var("OUT_DIR").unwrap()); + let dest_path = out_path.join("glyphs"); + if !dest_path.exists() { + fs::create_dir_all(&dest_path).ok(); } - command - .target("thumbv8m.main-none-eabi") - .file(bolos_sdk.join("src/ledger_protocol.c")) - .file(bolos_sdk.join("lib_blewbxx/core/auto/ble_gap_aci.c")) - .file(bolos_sdk.join("lib_blewbxx/core/auto/ble_gatt_aci.c")) - .file(bolos_sdk.join("lib_blewbxx/core/auto/ble_hal_aci.c")) - .file(bolos_sdk.join("lib_blewbxx/core/auto/ble_hci_le.c")) - .file(bolos_sdk.join("lib_blewbxx/core/auto/ble_l2cap_aci.c")) - .file(bolos_sdk.join("lib_blewbxx/core/template/osal.c")) - .file(bolos_sdk.join("lib_blewbxx_impl/src/ledger_ble.c")) - .include(bolos_sdk.join("lib_blewbxx/include")) - .include(bolos_sdk.join("lib_blewbxx/core")) - .include(bolos_sdk.join("lib_blewbxx/core/auto")) - .include(bolos_sdk.join("lib_blewbxx/core/template")) - .include(bolos_sdk.join("lib_blewbxx_impl/include")) - .include(bolos_sdk.join("target/flex/include/")) - .flag("-fropi") - .flag("-frwpi") - .include("./src/c/glyphs_flex/") - .file("./src/c/glyphs_flex/glyphs.c"); - configure_lib_nbgl(command, bolos_sdk); + let mut cmd = Command::new(icon2glyph.as_os_str()); + cmd.arg("--glyphcheader") + .arg(dest_path.join("glyphs.h").as_os_str()) + .arg("--glyphcfile") + .arg(dest_path.join("glyphs.c").as_os_str()); + + if device.name == DeviceName::NanoSPlus || device.name == DeviceName::NanoX { + cmd.arg("--reverse"); + } + + for folder in device.glyphs_folders.iter() { + for file in std::fs::read_dir(folder).unwrap() { + let path = file.unwrap().path(); + let path_str = path.to_str().unwrap().to_string(); + cmd.arg(path_str); + } + } + let _ = cmd.output(); } -fn configure_lib_nbgl(command: &mut cc::Build, bolos_sdk: &Path) { - command - .flag("-Wno-microsoft-anon-tag") - .flag("-fms-extensions") - .include(bolos_sdk.join("lib_nbgl/include/")) - .include(bolos_sdk.join("lib_nbgl/include/fonts/")) - .include(bolos_sdk.join("lib_ux_sync/include/")) - .include(bolos_sdk.join("lib_ux_nbgl/")) - .include(bolos_sdk.join("qrcode/include/")) - .include(bolos_sdk.join("lib_bagl/include/")) - .file(bolos_sdk.join("lib_ux_nbgl/ux.c")) - .file(bolos_sdk.join("lib_ux_sync/src/ux_sync.c")) - .file(bolos_sdk.join("lib_bagl/src/bagl_fonts.c")) - .file(bolos_sdk.join("src/os_printf.c")) - .file(bolos_sdk.join("qrcode/src/qrcodegen.c")) - .files( - glob(bolos_sdk.join("lib_nbgl/src/*.c").to_str().unwrap()) - .unwrap() - .map(|x| x.unwrap()) - .collect::>(), - ); +/// Helper function to concatenate all paths in pathlist to c_sdk's path +fn str2path(c_sdk: &Path, pathlist: &[&str]) -> Vec { + pathlist + .iter() + .map(|p| c_sdk.join(p)) + .collect::>() +} + +/// Get all #define from a header file +fn header2define(headername: &str) -> Vec<(String, Option)> { + let mut headerfile = File::open(headername).unwrap(); + let mut header = String::new(); + headerfile.read_to_string(&mut header).unwrap(); + + header + .lines() + .filter_map(|line| { + if line.trim_start().starts_with("#define") { + let parts: Vec<&str> = line.split_whitespace().collect(); + match parts.len() { + 2 => Some((parts[1].to_string(), None)), + 3 => Some((parts[1].to_string(), Some(parts[2].to_string()))), + _ => None, + } + } else { + None + } + }) + .collect() } diff --git a/ledger_secure_sdk_sys/c_sdk_build_flex.cflags b/ledger_secure_sdk_sys/c_sdk_build_flex.cflags new file mode 100644 index 00000000..519cb514 --- /dev/null +++ b/ledger_secure_sdk_sys/c_sdk_build_flex.cflags @@ -0,0 +1,34 @@ +--sysroot="/usr/arm-none-eabi" +-Oz +-g0 +-fomit-frame-pointer +-momit-leaf-frame-pointer +-fno-common +-mlittle-endian +-std=gnu99 +-Wall +-Wextra +-Wno-main +-Werror=int-to-pointer-cast +-Wno-error=int-conversion +-Wimplicit-fallthrough +-Wvla +-Wundef +-Wshadow +-Wformat=2 +-Wformat-security +-Wwrite-strings +-fdata-sections +-ffunction-sections +-funsigned-char +-fshort-enums +-mno-unaligned-access +-fropi +-fno-jump-tables +-nostdlib +-nodefaultlibs +-frwpi +-mthumb +--target=armv8m-none-eabi +-mcpu=cortex-m35p+nodsp +-msoft-float \ No newline at end of file diff --git a/ledger_secure_sdk_sys/c_sdk_build_nanosplus.cflags b/ledger_secure_sdk_sys/c_sdk_build_nanosplus.cflags new file mode 100644 index 00000000..519cb514 --- /dev/null +++ b/ledger_secure_sdk_sys/c_sdk_build_nanosplus.cflags @@ -0,0 +1,34 @@ +--sysroot="/usr/arm-none-eabi" +-Oz +-g0 +-fomit-frame-pointer +-momit-leaf-frame-pointer +-fno-common +-mlittle-endian +-std=gnu99 +-Wall +-Wextra +-Wno-main +-Werror=int-to-pointer-cast +-Wno-error=int-conversion +-Wimplicit-fallthrough +-Wvla +-Wundef +-Wshadow +-Wformat=2 +-Wformat-security +-Wwrite-strings +-fdata-sections +-ffunction-sections +-funsigned-char +-fshort-enums +-mno-unaligned-access +-fropi +-fno-jump-tables +-nostdlib +-nodefaultlibs +-frwpi +-mthumb +--target=armv8m-none-eabi +-mcpu=cortex-m35p+nodsp +-msoft-float \ No newline at end of file diff --git a/ledger_secure_sdk_sys/c_sdk_build_nanox.cflags b/ledger_secure_sdk_sys/c_sdk_build_nanox.cflags new file mode 100644 index 00000000..db9a2818 --- /dev/null +++ b/ledger_secure_sdk_sys/c_sdk_build_nanox.cflags @@ -0,0 +1,34 @@ +--sysroot="/usr/arm-none-eabi" +-Oz +-g0 +-fomit-frame-pointer +-momit-leaf-frame-pointer +-fno-common +-mlittle-endian +-std=gnu99 +-Wall +-Wextra +-Wno-main +-Werror=int-to-pointer-cast +-Wno-error=int-conversion +-Wimplicit-fallthrough +-Wvla +-Wundef +-Wshadow +-Wformat=2 +-Wformat-security +-Wwrite-strings +-fdata-sections +-ffunction-sections +-funsigned-char +-fshort-enums +-mno-unaligned-access +-fropi +-fno-jump-tables +-nostdlib +-nodefaultlibs +-frwpi +-mthumb +--target=armv6m-none-eabi +-mcpu=cortex-m0plus + diff --git a/ledger_secure_sdk_sys/c_sdk_build_stax.cflags b/ledger_secure_sdk_sys/c_sdk_build_stax.cflags new file mode 100644 index 00000000..519cb514 --- /dev/null +++ b/ledger_secure_sdk_sys/c_sdk_build_stax.cflags @@ -0,0 +1,34 @@ +--sysroot="/usr/arm-none-eabi" +-Oz +-g0 +-fomit-frame-pointer +-momit-leaf-frame-pointer +-fno-common +-mlittle-endian +-std=gnu99 +-Wall +-Wextra +-Wno-main +-Werror=int-to-pointer-cast +-Wno-error=int-conversion +-Wimplicit-fallthrough +-Wvla +-Wundef +-Wshadow +-Wformat=2 +-Wformat-security +-Wwrite-strings +-fdata-sections +-ffunction-sections +-funsigned-char +-fshort-enums +-mno-unaligned-access +-fropi +-fno-jump-tables +-nostdlib +-nodefaultlibs +-frwpi +-mthumb +--target=armv8m-none-eabi +-mcpu=cortex-m35p+nodsp +-msoft-float \ No newline at end of file diff --git a/ledger_secure_sdk_sys/csdk_flex.h b/ledger_secure_sdk_sys/csdk_flex.h new file mode 100644 index 00000000..b878a6ab --- /dev/null +++ b/ledger_secure_sdk_sys/csdk_flex.h @@ -0,0 +1,66 @@ +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// Makefile.standard_app +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// BLUETOOTH +#define HAVE_BLE +#define HAVE_BLE_APDU +#define BLE_COMMAND_TIMEOUT_MS 2000 +#define BLE_SEGMENT_SIZE 32 +// NFC SUPPORT (feature dependent) +//#define HAVE_NFC +//#define HAVE_NFC_READER +// APP STORAGE (feature dependent) +//#define HAVE_APP_STORAGE +// IO SEPROXY BUFFER SIZE +#define IO_SEPROXYHAL_BUFFER_SIZE_B 300 +// NBGL QRCODE (feature dependent) +#define NBGL_QRCODE +// NBGL KEYBOARD (feature dependent) +//#define NBGL_KEYBOARD +// NBGL KEYPAD (feature dependent) +//#define NBGL_KEYPAD +// STANDARD DEFINES +#define IO_HID_EP_LENGTH 64 +#define HAVE_SPRINTF +#define HAVE_SNPRINTF_FORMAT_U +#define HAVE_IO_USB +#define HAVE_L4_USBLIB +#define IO_USB_MAX_ENDPOINTS 4 +#define HAVE_USB_APDU +#define USB_SEGMENT_SIZE 64 +//#define HAVE_WEBUSB +//#define WEBUSB_URL_SIZE_B +//#define WEBUSB_URL +#define OS_IO_SEPROXYHAL +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// Makefile.defines +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +#define gcc +#define __IO volatile +// Flex +#define HAVE_BAGL_FONT_INTER_REGULAR_28PX +#define HAVE_BAGL_FONT_INTER_SEMIBOLD_28PX +#define HAVE_BAGL_FONT_INTER_MEDIUM_36PX +#define HAVE_INAPP_BLE_PAIRING +#define HAVE_NBGL +#define HAVE_PIEZO_SOUND +#define HAVE_SE_TOUCH +#define HAVE_SE_EINK_DISPLAY +//#define HAVE_HW_TOUCH_SWIPE +#define NBGL_PAGE +#define NBGL_USE_CASE +#define SCREEN_SIZE_WALLET +#define HAVE_FAST_HOLD_TO_APPROVE + +#define HAVE_LEDGER_PKI + +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// Misc +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +#define HAVE_LOCAL_APDU_BUFFER + +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// DEBUG C SDK +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +//#define HAVE_PRINTF +//#define PRINTF mcu_usb_printf \ No newline at end of file diff --git a/ledger_secure_sdk_sys/csdk_nanos2.h b/ledger_secure_sdk_sys/csdk_nanos2.h new file mode 100644 index 00000000..126ba21f --- /dev/null +++ b/ledger_secure_sdk_sys/csdk_nanos2.h @@ -0,0 +1,56 @@ +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// Makefile.standard_app +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// APP STORAGE (feature dependent) +//#define HAVE_APP_STORAGE +// IO SEPROXY BUFFER SIZE +#define IO_SEPROXYHAL_BUFFER_SIZE_B 300 +// NBGL KEYBOARD (feature dependent) +//#define NBGL_KEYBOARD +// NBGL KEYPAD (feature dependent) +//#define NBGL_KEYPAD +// STANDARD DEFINES +#define IO_HID_EP_LENGTH 64 +#define HAVE_SPRINTF +#define HAVE_SNPRINTF_FORMAT_U +#define HAVE_IO_USB +#define HAVE_L4_USBLIB +#define IO_USB_MAX_ENDPOINTS 4 +#define HAVE_USB_APDU +#define USB_SEGMENT_SIZE 64 +//#define HAVE_WEBUSB +//#define WEBUSB_URL_SIZE_B +//#define WEBUSB_URL +#define OS_IO_SEPROXYHAL +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// Makefile.defines +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +#define gcc +#define __IO volatile + +#define BAGL_HEIGHT 64 +#define BAGL_WIDTH 128 +#define HAVE_BAGL_ELLIPSIS +#define HAVE_BAGL_FONT_OPEN_SANS_REGULAR_11PX +#define HAVE_BAGL_FONT_OPEN_SANS_EXTRABOLD_11PX +#define HAVE_BAGL_FONT_OPEN_SANS_LIGHT_16PX +#define SCREEN_SIZE_NANO + +#define HAVE_SE_BUTTON +#define HAVE_SE_SCREEN +#define HAVE_FONTS +#define HAVE_INAPP_BLE_PAIRING +#define HAVE_BATTERY + +#define HAVE_LEDGER_PKI + +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// Misc +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +#define HAVE_LOCAL_APDU_BUFFER + +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// DEBUG C SDK +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +//#define HAVE_PRINTF +//#define PRINTF mcu_usb_printf diff --git a/ledger_secure_sdk_sys/csdk_nanox.h b/ledger_secure_sdk_sys/csdk_nanox.h new file mode 100644 index 00000000..c6f69c1d --- /dev/null +++ b/ledger_secure_sdk_sys/csdk_nanox.h @@ -0,0 +1,63 @@ +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// Makefile.standard_app +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// BLUETOOTH +#define HAVE_BLE +#define HAVE_BLE_APDU +#define BLE_COMMAND_TIMEOUT_MS 2000 +#define BLE_SEGMENT_SIZE 32 +// APP STORAGE (feature dependent) +//#define HAVE_APP_STORAGE +// IO SEPROXY BUFFER SIZE +#define IO_SEPROXYHAL_BUFFER_SIZE_B 300 +// NBGL KEYBOARD (feature dependent) +//#define NBGL_KEYBOARD +// NBGL KEYPAD (feature dependent) +//#define NBGL_KEYPAD +// STANDARD DEFINES +#define IO_HID_EP_LENGTH 64 +#define HAVE_SPRINTF +#define HAVE_SNPRINTF_FORMAT_U +#define HAVE_IO_USB +#define HAVE_L4_USBLIB +#define IO_USB_MAX_ENDPOINTS 4 +#define HAVE_USB_APDU +#define USB_SEGMENT_SIZE 64 +//#define HAVE_WEBUSB +//#define WEBUSB_URL_SIZE_B +//#define WEBUSB_URL +#define OS_IO_SEPROXYHAL +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// Makefile.defines +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +#define gcc +#define __IO volatile + +#define BAGL_HEIGHT 64 +#define BAGL_WIDTH 128 +#define HAVE_BAGL_ELLIPSIS +#define HAVE_BAGL_FONT_OPEN_SANS_REGULAR_11PX +#define HAVE_BAGL_FONT_OPEN_SANS_EXTRABOLD_11PX +#define HAVE_BAGL_FONT_OPEN_SANS_LIGHT_16PX +#define SCREEN_SIZE_NANO + +#define HAVE_SE_BUTTON +#define HAVE_SE_SCREEN +#define HAVE_FONTS +#define HAVE_INAPP_BLE_PAIRING +#define HAVE_BATTERY + +#define HAVE_LEDGER_PKI + +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// Misc +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +#define HAVE_LOCAL_APDU_BUFFER +#define HAVE_SEPROXYHAL_MCU +#define HAVE_MCU_PROTECT + +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// DEBUG C SDK +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +//#define HAVE_PRINTF +//#define PRINTF mcu_usb_printf \ No newline at end of file diff --git a/ledger_secure_sdk_sys/csdk_stax.h b/ledger_secure_sdk_sys/csdk_stax.h new file mode 100644 index 00000000..bfb3d7fa --- /dev/null +++ b/ledger_secure_sdk_sys/csdk_stax.h @@ -0,0 +1,64 @@ +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// Makefile.standard_app +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// BLUETOOTH +#define HAVE_BLE +#define HAVE_BLE_APDU +#define BLE_COMMAND_TIMEOUT_MS 2000 +#define BLE_SEGMENT_SIZE 32 +// NFC SUPPORT (feature dependent) +//#define HAVE_NFC +//#define HAVE_NFC_READER +// APP STORAGE (feature dependent) +//#define HAVE_APP_STORAGE +// IO SEPROXY BUFFER SIZE +#define IO_SEPROXYHAL_BUFFER_SIZE_B 300 +// NBGL QRCODE (feature dependent) +#define NBGL_QRCODE +// NBGL KEYBOARD (feature dependent) +//#define NBGL_KEYBOARD +// NBGL KEYPAD (feature dependent) +//#define NBGL_KEYPAD +// STANDARD DEFINES +#define IO_HID_EP_LENGTH 64 +#define HAVE_SPRINTF +#define HAVE_SNPRINTF_FORMAT_U +#define HAVE_IO_USB +#define HAVE_L4_USBLIB +#define IO_USB_MAX_ENDPOINTS 4 +#define HAVE_USB_APDU +#define USB_SEGMENT_SIZE 64 +//#define HAVE_WEBUSB +//#define WEBUSB_URL_SIZE_B +//#define WEBUSB_URL +#define OS_IO_SEPROXYHAL +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// Makefile.defines +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +#define gcc +#define __IO volatile +// Stax +#define HAVE_BAGL_FONT_INTER_REGULAR_24PX +#define HAVE_BAGL_FONT_INTER_SEMIBOLD_24PX +#define HAVE_BAGL_FONT_INTER_MEDIUM_32PX +#define HAVE_INAPP_BLE_PAIRING +#define HAVE_NBGL +#define HAVE_PIEZO_SOUND +#define HAVE_SE_TOUCH +#define HAVE_SE_EINK_DISPLAY +#define NBGL_PAGE +#define NBGL_USE_CASE +#define SCREEN_SIZE_WALLET + +#define HAVE_LEDGER_PKI + +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// Misc +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +#define HAVE_LOCAL_APDU_BUFFER + +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// DEBUG C SDK +//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +//#define HAVE_PRINTF +//#define PRINTF mcu_usb_printf \ No newline at end of file diff --git a/ledger_device_sdk/flex.json b/ledger_secure_sdk_sys/flex.json similarity index 90% rename from ledger_device_sdk/flex.json rename to ledger_secure_sdk_sys/flex.json index af01a46e..e4039ab9 100644 --- a/ledger_device_sdk/flex.json +++ b/ledger_secure_sdk_sys/flex.json @@ -13,11 +13,11 @@ "panic-strategy": "abort", "pre-link-args": { "ld.lld": [ - "-Tstax_flex_layout.ld", + "-Tflex_layout.ld", "-Tlink.ld" ], "ld": [ - "-Tstax_flex_layout.ld", + "-Tflex_layout.ld", "-Tlink.ld" ] }, diff --git a/ledger_device_sdk/stax_flex_layout.ld b/ledger_secure_sdk_sys/flex_layout.ld similarity index 100% rename from ledger_device_sdk/stax_flex_layout.ld rename to ledger_secure_sdk_sys/flex_layout.ld diff --git a/ledger_device_sdk/link.ld b/ledger_secure_sdk_sys/link.ld similarity index 98% rename from ledger_device_sdk/link.ld rename to ledger_secure_sdk_sys/link.ld index 4d5fd241..5736654c 100644 --- a/ledger_device_sdk/link.ld +++ b/ledger_secure_sdk_sys/link.ld @@ -141,6 +141,7 @@ SECTIONS ledger.rust_sdk_name (INFO): { KEEP(*(ledger.rust_sdk_name)) } ledger.sdk_name (INFO): { KEEP(*(ledger.sdk_name)) } ledger.sdk_hash (INFO): { KEEP(*(ledger.sdk_hash)) } + ledger.sdk_graphics (INFO): { KEEP(*(ledger.sdk_graphics)) } } PROVIDE(_nvram = ABSOLUTE(_nvram_start)); diff --git a/ledger_device_sdk/link_wrap.sh b/ledger_secure_sdk_sys/link_wrap.sh similarity index 96% rename from ledger_device_sdk/link_wrap.sh rename to ledger_secure_sdk_sys/link_wrap.sh index 31f6cb7e..7decd9e3 100755 --- a/ledger_device_sdk/link_wrap.sh +++ b/ledger_secure_sdk_sys/link_wrap.sh @@ -28,7 +28,7 @@ llvm-objcopy --dump-section .rel.nvm_data=$OUT-nvm-reloc $OUT /dev/null || true cat $OUT-rodata-reloc $OUT-nvm-reloc $OUT-data-reloc > $OUT-relocs || true reloc_allocated_size="$((0x$(llvm-nm $OUT | grep _reloc_size | cut -d' ' -f1)))" -reloc_real_size="$(stat -c %s $OUT-relocs)" +reloc_real_size="$(wc -c < "$OUT-relocs")" # Check that our relocations _actually_ fit. if [ "$reloc_real_size" -gt "$reloc_allocated_size" ] then diff --git a/ledger_device_sdk/nanosplus.json b/ledger_secure_sdk_sys/nanosplus.json similarity index 100% rename from ledger_device_sdk/nanosplus.json rename to ledger_secure_sdk_sys/nanosplus.json diff --git a/ledger_device_sdk/nanosplus_layout.ld b/ledger_secure_sdk_sys/nanosplus_layout.ld similarity index 79% rename from ledger_device_sdk/nanosplus_layout.ld rename to ledger_secure_sdk_sys/nanosplus_layout.ld index 8456e07d..9418ef65 100644 --- a/ledger_device_sdk/nanosplus_layout.ld +++ b/ledger_secure_sdk_sys/nanosplus_layout.ld @@ -2,7 +2,7 @@ MEMORY { FLASH (rx) : ORIGIN = 0xc0de0000, LENGTH = 400K DATA (r) : ORIGIN = 0xc0de0000, LENGTH = 400K - SRAM (rwx) : ORIGIN = 0xda7a0000, LENGTH = 30K + SRAM (rwx) : ORIGIN = 0xda7a0000, LENGTH = 44K } PAGE_SIZE = 512; diff --git a/ledger_device_sdk/nanox.json b/ledger_secure_sdk_sys/nanox.json similarity index 100% rename from ledger_device_sdk/nanox.json rename to ledger_secure_sdk_sys/nanox.json diff --git a/ledger_device_sdk/nanox_layout.ld b/ledger_secure_sdk_sys/nanox_layout.ld similarity index 79% rename from ledger_device_sdk/nanox_layout.ld rename to ledger_secure_sdk_sys/nanox_layout.ld index 88856e92..c708fdf8 100644 --- a/ledger_device_sdk/nanox_layout.ld +++ b/ledger_secure_sdk_sys/nanox_layout.ld @@ -2,7 +2,7 @@ MEMORY { FLASH (rx) : ORIGIN = 0xc0de0000, LENGTH = 400K DATA (r) : ORIGIN = 0xc0de0000, LENGTH = 400K - SRAM (rwx) : ORIGIN = 0xda7a0000, LENGTH = 30K + SRAM (rwx) : ORIGIN = 0xda7a0000, LENGTH = 28K } PAGE_SIZE = 256; diff --git a/ledger_secure_sdk_sys/sdk_flex.h b/ledger_secure_sdk_sys/sdk_flex.h deleted file mode 100644 index b3350ab9..00000000 --- a/ledger_secure_sdk_sys/sdk_flex.h +++ /dev/null @@ -1,33 +0,0 @@ -#define HAVE_SPRINTF -#define HAVE_LOCAL_APDU_BUFFER -#define IO_HID_EP_LENGTH 64 -#define USB_SEGMENT_SIZE 64 -#define OS_IO_SEPROXYHAL -#define HAVE_IO_USB -#define HAVE_L4_USBLIB -#define HAVE_USB_APDU -#define __IO volatile -#define IO_USB_MAX_ENDPOINTS 6 -#define IO_SEPROXYHAL_BUFFER_SIZE_B 300 -#define main _start - -#define NBGL_QRCODE - -// from Makefile.defines -#define HAVE_BAGL_FONT_INTER_REGULAR_28PX -#define HAVE_BAGL_FONT_INTER_SEMIBOLD_28PX -#define HAVE_BAGL_FONT_INTER_MEDIUM_36PX -#define HAVE_INAPP_BLE_PAIRING -#define HAVE_NBGL -#define HAVE_PIEZO_SOUND -#define HAVE_SE_TOUCH -#define HAVE_SE_EINK_DISPLAY -#define NBGL_PAGE -#define NBGL_USE_CASE -#define SCREEN_SIZE_WALLET -#define HAVE_FAST_HOLD_TO_APPROVE - -#define HAVE_BLE -#define HAVE_BLE_APDU -#define BLE_COMMAND_TIMEOUT_MS 2000 -#define BLE_SEGMENT_SIZE 32 \ No newline at end of file diff --git a/ledger_secure_sdk_sys/sdk_nanos.h b/ledger_secure_sdk_sys/sdk_nanos.h deleted file mode 100644 index 7d665ec9..00000000 --- a/ledger_secure_sdk_sys/sdk_nanos.h +++ /dev/null @@ -1,11 +0,0 @@ -#define HAVE_LOCAL_APDU_BUFFER -#define IO_HID_EP_LENGTH 64 -#define USB_SEGMENT_SIZE 64 -#define OS_IO_SEPROXYHAL -#define HAVE_IO_USB -#define HAVE_L4_USBLIB -#define HAVE_USB_APDU -#define __IO volatile -#define IO_USB_MAX_ENDPOINTS 6 -#define IO_SEPROXYHAL_BUFFER_SIZE_B 128 -#define main _start \ No newline at end of file diff --git a/ledger_secure_sdk_sys/sdk_nanosp.h b/ledger_secure_sdk_sys/sdk_nanosp.h deleted file mode 100644 index ce099221..00000000 --- a/ledger_secure_sdk_sys/sdk_nanosp.h +++ /dev/null @@ -1,19 +0,0 @@ -#define HAVE_LOCAL_APDU_BUFFER -#define IO_HID_EP_LENGTH 64 -#define USB_SEGMENT_SIZE 64 -#define OS_IO_SEPROXYHAL -#define HAVE_IO_USB -#define HAVE_L4_USBLIB -#define HAVE_USB_APDU -#define __IO volatile -#define IO_USB_MAX_ENDPOINTS 6 -#define IO_SEPROXYHAL_BUFFER_SIZE_B 128 -#define main _start - -#define HAVE_SEPROXYHAL_MCU -#define HAVE_MCU_PROTECT -#define HAVE_MCU_SEPROXYHAL -#define HAVE_MCU_SERIAL_STORAGE -#define HAVE_SE_BUTTON -#define HAVE_BAGL -#define HAVE_SE_SCREEN \ No newline at end of file diff --git a/ledger_secure_sdk_sys/sdk_nanox.h b/ledger_secure_sdk_sys/sdk_nanox.h deleted file mode 100644 index aa4c956a..00000000 --- a/ledger_secure_sdk_sys/sdk_nanox.h +++ /dev/null @@ -1,22 +0,0 @@ -#define HAVE_LOCAL_APDU_BUFFER -#define IO_HID_EP_LENGTH 64 -#define USB_SEGMENT_SIZE 64 -#define OS_IO_SEPROXYHAL -#define HAVE_IO_USB -#define HAVE_L4_USBLIB -#define HAVE_USB_APDU -#define __IO volatile -#define IO_USB_MAX_ENDPOINTS 6 -#define IO_SEPROXYHAL_BUFFER_SIZE_B 128 -#define main _start - -#define HAVE_SEPROXYHAL_MCU -#define HAVE_MCU_PROTECT -#define HAVE_MCU_SEPROXYHAL -#define HAVE_MCU_SERIAL_STORAGE -#define HAVE_SE_BUTTON -#define HAVE_BAGL -#define HAVE_SE_SCREEN - -#define HAVE_BLE -#define HAVE_BLE_APDU \ No newline at end of file diff --git a/ledger_secure_sdk_sys/sdk_stax.h b/ledger_secure_sdk_sys/sdk_stax.h deleted file mode 100644 index ace4a4b5..00000000 --- a/ledger_secure_sdk_sys/sdk_stax.h +++ /dev/null @@ -1,32 +0,0 @@ -#define HAVE_SPRINTF -#define HAVE_LOCAL_APDU_BUFFER -#define IO_HID_EP_LENGTH 64 -#define USB_SEGMENT_SIZE 64 -#define OS_IO_SEPROXYHAL -#define HAVE_IO_USB -#define HAVE_L4_USBLIB -#define HAVE_USB_APDU -#define __IO volatile -#define IO_USB_MAX_ENDPOINTS 6 -#define IO_SEPROXYHAL_BUFFER_SIZE_B 300 -#define main _start - -#define NBGL_QRCODE - -// from Makefile.defines -#define HAVE_BAGL_FONT_INTER_REGULAR_24PX -#define HAVE_BAGL_FONT_INTER_SEMIBOLD_24PX -#define HAVE_BAGL_FONT_INTER_MEDIUM_32PX -#define HAVE_INAPP_BLE_PAIRING -#define HAVE_NBGL -#define HAVE_PIEZO_SOUND -#define HAVE_SE_TOUCH -#define HAVE_SE_EINK_DISPLAY -#define NBGL_PAGE -#define NBGL_USE_CASE -#define SCREEN_SIZE_WALLET - -#define HAVE_BLE -#define HAVE_BLE_APDU -#define BLE_COMMAND_TIMEOUT_MS 2000 -#define BLE_SEGMENT_SIZE 32 \ No newline at end of file diff --git a/ledger_secure_sdk_sys/src/c/glyphs_flex/glyphs.c b/ledger_secure_sdk_sys/src/c/glyphs_flex/glyphs.c deleted file mode 100644 index 1324f214..00000000 --- a/ledger_secure_sdk_sys/src/c/glyphs_flex/glyphs.c +++ /dev/null @@ -1,813 +0,0 @@ -/* Automatically generated by icon2glyph.py */ - -#include "glyphs.h" - -uint8_t const C_app_boilerplate_16px_bitmap[] = { - 0x10, 0x00, 0x10, 0x00, 0x02, 0x15, 0x00, 0x00, 0xf0, 0x71, 0xf1, 0xf2, 0x42, 0x83, 0x14, 0x87, - 0x78, 0x69, 0x79, 0x98, 0xa7, 0x93, 0x14, 0x82, 0x42, 0x81, 0xf1, 0xf0, 0xa0, -}; -const nbgl_icon_details_t C_app_boilerplate_16px = { 16, 16, NBGL_BPP_1, true, C_app_boilerplate_16px_bitmap }; - -uint8_t const C_app_boilerplate_64px_bitmap[] = { - 0x40, 0x00, 0x40, 0x00, 0x01, 0xb3, 0x00, 0x00, 0xb1, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x75, 0xd1, 0xbb, 0x0d, 0x03, 0x21, 0x0c, 0x06, 0x60, 0x9f, 0x22, 0x85, - 0x92, 0x11, 0x6e, 0x85, 0x6c, 0x70, 0xa3, 0x1d, 0xa3, 0x79, 0x14, 0xa4, 0x14, 0x69, 0x29, 0x29, - 0x2c, 0x1c, 0x83, 0xff, 0x44, 0x04, 0xe5, 0xdc, 0x7c, 0x12, 0x0f, 0x1b, 0x1b, 0xa2, 0xab, 0xb8, - 0xc3, 0xf0, 0x31, 0x2d, 0x32, 0xcc, 0xb0, 0xc0, 0x3a, 0xf9, 0x30, 0x85, 0x68, 0xb3, 0xbd, 0xd0, - 0x88, 0xa2, 0x9d, 0x0d, 0x4a, 0x74, 0xf2, 0xf0, 0xa6, 0xc3, 0xb4, 0x6b, 0xea, 0xb2, 0x6a, 0xbf, - 0xa7, 0x2f, 0x6d, 0x43, 0xfd, 0x2a, 0xb0, 0xc2, 0x32, 0xb9, 0x9b, 0xfd, 0x09, 0x86, 0xa7, 0xb3, - 0xb0, 0x74, 0x47, 0xd7, 0x2a, 0xab, 0x1b, 0xd5, 0xd3, 0x8d, 0x65, 0x81, 0x15, 0xeb, 0x82, 0x73, - 0xbd, 0xdc, 0x01, 0xa3, 0xdf, 0xf3, 0x8d, 0x84, 0x0d, 0x46, 0xdd, 0xbc, 0x58, 0x96, 0xf7, 0xc9, - 0x8f, 0x4f, 0xf4, 0x91, 0x4f, 0xef, 0x8f, 0xa3, 0xf7, 0x9b, 0x36, 0x7f, 0xb0, 0xe5, 0xe6, 0x69, - 0x3e, 0x0d, 0xf3, 0x12, 0xcc, 0xaf, 0x2e, 0xf3, 0x2d, 0xcb, 0xdc, 0xf9, 0xe2, 0x7f, 0x96, 0x7f, - 0xfc, 0x1f, 0x6f, 0xe5, 0xd1, 0xa9, 0x21, 0x00, 0x02, 0x00, 0x00, -}; -const nbgl_icon_details_t C_app_boilerplate_64px = { 64, 64, NBGL_BPP_1, true, C_app_boilerplate_64px_bitmap }; - -uint8_t const C_pin_24_bitmap[] = { - 0x18, 0x00, 0x18, 0x00, 0x02, 0x29, 0x00, 0x00, 0x96, 0xfc, 0xbe, 0x9f, 0x01, 0x7f, 0x03, 0x5f, - 0x05, 0x3f, 0x07, 0x2f, 0x07, 0x2f, 0x07, 0x1f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, - 0x09, 0x1f, 0x07, 0x2f, 0x07, 0x2f, 0x07, 0x3f, 0x05, 0x5f, 0x03, 0x7f, 0x01, 0x9e, 0xbc, 0xf6, - 0x90, -}; -const nbgl_icon_details_t C_pin_24 = { 24, 24, NBGL_BPP_1, true, C_pin_24_bitmap }; - -uint8_t const C_quarter_circle_bottom_left_32px_1bpp_bitmap[] = { - 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, - 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x06, - 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x0c, - 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x38, 0x00, 0x00, 0x00, 0x30, - 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x01, 0x80, - 0x00, 0x00, 0x03, 0x80, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x0e, 0x00, 0x00, 0x00, 0x1c, 0x00, - 0x00, 0x00, 0x38, 0x00, 0x00, 0x00, 0xe0, 0x00, 0x00, 0x03, 0xc0, 0x00, 0x00, 0x0f, 0x00, 0x00, - 0x00, 0x3e, 0x00, 0x00, 0x03, 0xf0, 0x00, 0x00, 0xff, 0xc0, 0x00, 0x00, 0xfc, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_quarter_circle_bottom_left_32px_1bpp = { 32, 32, NBGL_BPP_1, false, C_quarter_circle_bottom_left_32px_1bpp_bitmap }; - -uint8_t const C_quarter_circle_bottom_left_40px_1bpp_bitmap[] = { - 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, - 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, - 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, - 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, - 0x0c, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x18, - 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, - 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, - 0x00, 0x01, 0x80, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x00, - 0x06, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x30, - 0x00, 0x00, 0x00, 0x00, 0xe0, 0x00, 0x00, 0x00, 0x01, 0xc0, 0x00, 0x00, 0x00, 0x03, 0x80, 0x00, - 0x00, 0x00, 0x0e, 0x00, 0x00, 0x00, 0x00, 0x3c, 0x00, 0x00, 0x00, 0x00, 0xf0, 0x00, 0x00, 0x00, - 0x03, 0xc0, 0x00, 0x00, 0x00, 0x1f, 0x00, 0x00, 0x00, 0x03, 0xfc, 0x00, 0x00, 0x00, 0xff, 0xe0, - 0x00, 0x00, 0x00, 0xfc, 0x00, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_quarter_circle_bottom_left_40px_1bpp = { 40, 40, NBGL_BPP_1, false, C_quarter_circle_bottom_left_40px_1bpp_bitmap }; - -uint8_t const C_quarter_circle_bottom_left_44px_1bpp_bitmap[] = { - 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x30, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, - 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, - 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, - 0x00, 0x01, 0x80, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x01, 0x80, 0x00, 0x00, - 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, - 0x00, 0x00, 0x0e, 0x00, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x1c, 0x00, 0x00, - 0x00, 0x00, 0x01, 0x80, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, - 0x00, 0x00, 0x00, 0xe0, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x01, 0x80, 0x00, - 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, - 0x00, 0x00, 0x00, 0x38, 0x00, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0xe0, 0x00, - 0x00, 0x00, 0x00, 0x3c, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00, 0x00, 0x01, 0xe0, 0x00, - 0x00, 0x00, 0x00, 0x78, 0x00, 0x00, 0x00, 0x00, 0x3e, 0x00, 0x00, 0x00, 0x00, 0x1f, 0x80, 0x00, - 0x00, 0x00, 0x3f, 0xc0, 0x00, 0x00, 0x00, 0xff, 0xe0, 0x00, 0x00, 0x00, 0x0f, 0xc0, 0x00, 0x00, - 0x00, 0x00, -}; -const nbgl_icon_details_t C_quarter_circle_bottom_left_44px_1bpp = { 44, 44, NBGL_BPP_1, false, C_quarter_circle_bottom_left_44px_1bpp_bitmap }; - -uint8_t const C_quarter_circle_top_left_32px_1bpp_bitmap[] = { - 0xc0, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, - 0xc0, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, - 0x60, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, - 0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x1c, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, - 0x06, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x01, 0x80, 0x00, 0x00, - 0x01, 0xc0, 0x00, 0x00, 0x00, 0xe0, 0x00, 0x00, 0x00, 0x70, 0x00, 0x00, 0x00, 0x38, 0x00, 0x00, - 0x00, 0x1c, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x03, 0xc0, 0x00, 0x00, 0x00, 0xf0, 0x00, - 0x00, 0x00, 0x7c, 0x00, 0x00, 0x00, 0x0f, 0xc0, 0x00, 0x00, 0x03, 0xff, 0x00, 0x00, 0x00, 0x3f, -}; -const nbgl_icon_details_t C_quarter_circle_top_left_32px_1bpp = { 32, 32, NBGL_BPP_1, false, C_quarter_circle_top_left_32px_1bpp_bitmap }; - -uint8_t const C_quarter_circle_top_left_40px_1bpp_bitmap[] = { - 0xc0, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0xc0, - 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, - 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, - 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, - 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, - 0x0c, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x06, - 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x01, 0x80, - 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0xe0, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, - 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, - 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x00, 0x03, 0x80, 0x00, 0x00, 0x00, 0x01, 0xc0, 0x00, 0x00, - 0x00, 0x00, 0x70, 0x00, 0x00, 0x00, 0x00, 0x3c, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00, - 0x00, 0x03, 0xc0, 0x00, 0x00, 0x00, 0x00, 0xf8, 0x00, 0x00, 0x00, 0x00, 0x3f, 0xc0, 0x00, 0x00, - 0x00, 0x07, 0xff, 0x00, 0x00, 0x00, 0x00, 0x3f, -}; -const nbgl_icon_details_t C_quarter_circle_top_left_40px_1bpp = { 40, 40, NBGL_BPP_1, false, C_quarter_circle_top_left_40px_1bpp_bitmap }; - -uint8_t const C_quarter_circle_top_left_44px_1bpp_bitmap[] = { - 0xc0, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, - 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, - 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, - 0x00, 0x00, 0x01, 0x80, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, - 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x07, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x03, 0x80, 0x00, 0x00, 0x00, 0x00, 0x18, - 0x00, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x0e, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x70, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, - 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, - 0x00, 0x01, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x0e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x70, 0x00, 0x00, - 0x00, 0x00, 0x03, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x78, 0x00, - 0x00, 0x00, 0x00, 0x01, 0xe0, 0x00, 0x00, 0x00, 0x00, 0x07, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x1f, - 0x80, 0x00, 0x00, 0x00, 0x00, 0x3f, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x7f, 0xf0, 0x00, 0x00, 0x00, - 0x00, 0x3f, -}; -const nbgl_icon_details_t C_quarter_circle_top_left_44px_1bpp = { 44, 44, NBGL_BPP_1, false, C_quarter_circle_top_left_44px_1bpp_bitmap }; - -uint8_t const C_quarter_disc_bottom_left_32px_1bpp_bitmap[] = { - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xfe, - 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xfc, 0xff, 0xff, 0xff, 0xfc, - 0xff, 0xff, 0xff, 0xf8, 0xff, 0xff, 0xff, 0xf8, 0xff, 0xff, 0xff, 0xf8, 0xff, 0xff, 0xff, 0xf0, - 0xff, 0xff, 0xff, 0xe0, 0xff, 0xff, 0xff, 0xe0, 0xff, 0xff, 0xff, 0xc0, 0xff, 0xff, 0xff, 0x80, - 0xff, 0xff, 0xff, 0x80, 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, 0xfe, 0x00, 0xff, 0xff, 0xfc, 0x00, - 0xff, 0xff, 0xf8, 0x00, 0xff, 0xff, 0xe0, 0x00, 0xff, 0xff, 0xc0, 0x00, 0xff, 0xff, 0x00, 0x00, - 0xff, 0xfe, 0x00, 0x00, 0xff, 0xf0, 0x00, 0x00, 0xff, 0xc0, 0x00, 0x00, 0xfc, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_quarter_disc_bottom_left_32px_1bpp = { 32, 32, NBGL_BPP_1, false, C_quarter_disc_bottom_left_32px_1bpp_bitmap }; - -uint8_t const C_quarter_disc_bottom_left_40px_1bpp_bitmap[] = { - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, - 0xff, 0xfe, 0xff, 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xff, 0xfc, 0xff, 0xff, 0xff, 0xff, - 0xfc, 0xff, 0xff, 0xff, 0xff, 0xfc, 0xff, 0xff, 0xff, 0xff, 0xf8, 0xff, 0xff, 0xff, 0xff, 0xf8, - 0xff, 0xff, 0xff, 0xff, 0xf0, 0xff, 0xff, 0xff, 0xff, 0xf0, 0xff, 0xff, 0xff, 0xff, 0xe0, 0xff, - 0xff, 0xff, 0xff, 0xe0, 0xff, 0xff, 0xff, 0xff, 0xc0, 0xff, 0xff, 0xff, 0xff, 0xc0, 0xff, 0xff, - 0xff, 0xff, 0x80, 0xff, 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, 0xff, - 0xfe, 0x00, 0xff, 0xff, 0xff, 0xfc, 0x00, 0xff, 0xff, 0xff, 0xf8, 0x00, 0xff, 0xff, 0xff, 0xf0, - 0x00, 0xff, 0xff, 0xff, 0xe0, 0x00, 0xff, 0xff, 0xff, 0xc0, 0x00, 0xff, 0xff, 0xff, 0x80, 0x00, - 0xff, 0xff, 0xfe, 0x00, 0x00, 0xff, 0xff, 0xfc, 0x00, 0x00, 0xff, 0xff, 0xf0, 0x00, 0x00, 0xff, - 0xff, 0xc0, 0x00, 0x00, 0xff, 0xff, 0x00, 0x00, 0x00, 0xff, 0xfc, 0x00, 0x00, 0x00, 0xff, 0xe0, - 0x00, 0x00, 0x00, 0xfc, 0x00, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_quarter_disc_bottom_left_40px_1bpp = { 40, 40, NBGL_BPP_1, false, C_quarter_disc_bottom_left_40px_1bpp_bitmap }; - -uint8_t const C_quarter_disc_bottom_left_44px_1bpp_bitmap[] = { - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xef, 0xff, 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xef, 0xff, 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xff, 0xff, 0xef, 0xff, 0xff, 0xff, - 0xff, 0xfc, 0xff, 0xff, 0xff, 0xff, 0xff, 0xcf, 0xff, 0xff, 0xff, 0xff, 0xfc, 0xff, 0xff, 0xff, - 0xff, 0xff, 0x8f, 0xff, 0xff, 0xff, 0xff, 0xf8, 0xff, 0xff, 0xff, 0xff, 0xff, 0x8f, 0xff, 0xff, - 0xff, 0xff, 0xf0, 0xff, 0xff, 0xff, 0xff, 0xff, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xe0, 0xff, 0xff, - 0xff, 0xff, 0xfe, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xc0, 0xff, 0xff, 0xff, 0xff, 0xfc, 0x0f, 0xff, - 0xff, 0xff, 0xff, 0x80, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x0f, 0xff, 0xff, 0xff, 0xff, 0x00, 0xff, - 0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff, 0xfc, 0x00, 0xff, 0xff, 0xff, 0xff, 0x80, 0x0f, - 0xff, 0xff, 0xff, 0xf0, 0x00, 0xff, 0xff, 0xff, 0xfe, 0x00, 0x0f, 0xff, 0xff, 0xff, 0xc0, 0x00, - 0xff, 0xff, 0xff, 0xf8, 0x00, 0x0f, 0xff, 0xff, 0xff, 0x00, 0x00, 0xff, 0xff, 0xff, 0xe0, 0x00, - 0x0f, 0xff, 0xff, 0xfc, 0x00, 0x00, 0xff, 0xff, 0xff, 0x00, 0x00, 0x0f, 0xff, 0xff, 0xe0, 0x00, - 0x00, 0xff, 0xff, 0xf8, 0x00, 0x00, 0x0f, 0xff, 0xfe, 0x00, 0x00, 0x00, 0xff, 0xff, 0x80, 0x00, - 0x00, 0x0f, 0xff, 0xc0, 0x00, 0x00, 0x00, 0xff, 0xe0, 0x00, 0x00, 0x00, 0x0f, 0xc0, 0x00, 0x00, - 0x00, 0x00, -}; -const nbgl_icon_details_t C_quarter_disc_bottom_left_44px_1bpp = { 44, 44, NBGL_BPP_1, false, C_quarter_disc_bottom_left_44px_1bpp_bitmap }; - -uint8_t const C_quarter_disc_top_left_32px_1bpp_bitmap[] = { - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, - 0x7f, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, 0x3f, 0xff, 0xff, 0xff, 0x3f, 0xff, 0xff, 0xff, - 0x1f, 0xff, 0xff, 0xff, 0x1f, 0xff, 0xff, 0xff, 0x1f, 0xff, 0xff, 0xff, 0x0f, 0xff, 0xff, 0xff, - 0x07, 0xff, 0xff, 0xff, 0x07, 0xff, 0xff, 0xff, 0x03, 0xff, 0xff, 0xff, 0x01, 0xff, 0xff, 0xff, - 0x01, 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, 0xff, 0x00, 0x7f, 0xff, 0xff, 0x00, 0x3f, 0xff, 0xff, - 0x00, 0x1f, 0xff, 0xff, 0x00, 0x07, 0xff, 0xff, 0x00, 0x03, 0xff, 0xff, 0x00, 0x00, 0xff, 0xff, - 0x00, 0x00, 0x7f, 0xff, 0x00, 0x00, 0x0f, 0xff, 0x00, 0x00, 0x03, 0xff, 0x00, 0x00, 0x00, 0x3f, -}; -const nbgl_icon_details_t C_quarter_disc_top_left_32px_1bpp = { 32, 32, NBGL_BPP_1, false, C_quarter_disc_top_left_32px_1bpp_bitmap }; - -uint8_t const C_quarter_disc_top_left_40px_1bpp_bitmap[] = { - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x7f, 0xff, - 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, - 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, 0xff, 0x3f, 0xff, 0xff, 0xff, 0xff, 0x3f, 0xff, 0xff, 0xff, - 0xff, 0x3f, 0xff, 0xff, 0xff, 0xff, 0x1f, 0xff, 0xff, 0xff, 0xff, 0x1f, 0xff, 0xff, 0xff, 0xff, - 0x0f, 0xff, 0xff, 0xff, 0xff, 0x0f, 0xff, 0xff, 0xff, 0xff, 0x07, 0xff, 0xff, 0xff, 0xff, 0x07, - 0xff, 0xff, 0xff, 0xff, 0x03, 0xff, 0xff, 0xff, 0xff, 0x03, 0xff, 0xff, 0xff, 0xff, 0x01, 0xff, - 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x7f, 0xff, - 0xff, 0xff, 0x00, 0x3f, 0xff, 0xff, 0xff, 0x00, 0x1f, 0xff, 0xff, 0xff, 0x00, 0x0f, 0xff, 0xff, - 0xff, 0x00, 0x07, 0xff, 0xff, 0xff, 0x00, 0x03, 0xff, 0xff, 0xff, 0x00, 0x01, 0xff, 0xff, 0xff, - 0x00, 0x00, 0x7f, 0xff, 0xff, 0x00, 0x00, 0x3f, 0xff, 0xff, 0x00, 0x00, 0x0f, 0xff, 0xff, 0x00, - 0x00, 0x03, 0xff, 0xff, 0x00, 0x00, 0x00, 0xff, 0xff, 0x00, 0x00, 0x00, 0x3f, 0xff, 0x00, 0x00, - 0x00, 0x07, 0xff, 0x00, 0x00, 0x00, 0x00, 0x3f, -}; -const nbgl_icon_details_t C_quarter_disc_top_left_40px_1bpp = { 40, 40, NBGL_BPP_1, false, C_quarter_disc_top_left_40px_1bpp_bitmap }; - -uint8_t const C_quarter_disc_top_left_44px_1bpp_bitmap[] = { - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xf7, 0xff, 0xff, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, - 0xff, 0xf7, 0xff, 0xff, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xf3, 0xff, 0xff, 0xff, - 0xff, 0xff, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xf3, 0xff, 0xff, 0xff, 0xff, 0xff, 0x1f, 0xff, 0xff, - 0xff, 0xff, 0xf1, 0xff, 0xff, 0xff, 0xff, 0xff, 0x1f, 0xff, 0xff, 0xff, 0xff, 0xf0, 0xff, 0xff, - 0xff, 0xff, 0xff, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x7f, 0xff, 0xff, 0xff, 0xff, 0x07, 0xff, - 0xff, 0xff, 0xff, 0xf0, 0x3f, 0xff, 0xff, 0xff, 0xff, 0x03, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x1f, - 0xff, 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x0f, 0xff, 0xff, 0xff, 0xff, 0x00, - 0x7f, 0xff, 0xff, 0xff, 0xf0, 0x03, 0xff, 0xff, 0xff, 0xff, 0x00, 0x1f, 0xff, 0xff, 0xff, 0xf0, - 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x07, 0xff, 0xff, 0xff, 0xf0, 0x00, 0x3f, 0xff, 0xff, 0xff, - 0x00, 0x01, 0xff, 0xff, 0xff, 0xf0, 0x00, 0x0f, 0xff, 0xff, 0xff, 0x00, 0x00, 0x7f, 0xff, 0xff, - 0xf0, 0x00, 0x03, 0xff, 0xff, 0xff, 0x00, 0x00, 0x0f, 0xff, 0xff, 0xf0, 0x00, 0x00, 0x7f, 0xff, - 0xff, 0x00, 0x00, 0x01, 0xff, 0xff, 0xf0, 0x00, 0x00, 0x07, 0xff, 0xff, 0x00, 0x00, 0x00, 0x1f, - 0xff, 0xf0, 0x00, 0x00, 0x00, 0x3f, 0xff, 0x00, 0x00, 0x00, 0x00, 0x7f, 0xf0, 0x00, 0x00, 0x00, - 0x00, 0x3f, -}; -const nbgl_icon_details_t C_quarter_disc_top_left_44px_1bpp = { 44, 44, NBGL_BPP_1, false, C_quarter_disc_top_left_44px_1bpp_bitmap }; - -uint8_t const C_round_24px_bitmap[] = { - 0x18, 0x00, 0x18, 0x00, 0x02, 0x27, 0x00, 0x00, 0xf0, 0xf0, 0xf0, 0xf0, 0xf0, 0x74, 0xf0, 0x38, - 0xec, 0xbe, 0xae, 0x9f, 0x01, 0x8f, 0x01, 0x7f, 0x03, 0x6f, 0x03, 0x6f, 0x03, 0x6f, 0x03, 0x7f, - 0x01, 0x8f, 0x01, 0x9e, 0xae, 0xbc, 0xe8, 0xf0, 0x34, 0xf0, 0xf0, 0xf0, 0xf0, 0xf0, 0x70, -}; -const nbgl_icon_details_t C_round_24px = { 24, 24, NBGL_BPP_1, true, C_round_24px_bitmap }; - -uint8_t const C_switch_60_40_bitmap[] = { - 0x00, 0x00, 0xff, 0x00, 0x00, 0x00, 0x07, 0xff, 0xe0, 0x00, 0x00, 0x1f, 0xff, 0xf8, 0x00, 0x00, - 0x3f, 0xff, 0xfc, 0x00, 0x00, 0xff, 0xff, 0xff, 0x00, 0x01, 0xff, 0xff, 0xff, 0x80, 0x03, 0xff, - 0xff, 0xff, 0xc0, 0x03, 0xff, 0xff, 0xff, 0xc0, 0x07, 0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, - 0xff, 0xf0, 0x0f, 0xff, 0xff, 0xff, 0xf0, 0x1f, 0xff, 0xff, 0xff, 0xf8, 0x1f, 0xff, 0xff, 0xff, - 0xf8, 0x1f, 0xff, 0xff, 0xff, 0xf8, 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xfc, - 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, - 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, - 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, - 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0x00, 0xff, 0xfc, 0x3f, 0xf8, 0x00, 0x1f, - 0xfc, 0x3f, 0xf0, 0x00, 0x0f, 0xfc, 0x3f, 0xc0, 0x00, 0x03, 0xfc, 0x3f, 0x80, 0x00, 0x01, 0xfc, - 0x3f, 0x00, 0x00, 0x00, 0xfc, 0x3f, 0x00, 0x00, 0x00, 0xfc, 0x3e, 0x00, 0x00, 0x00, 0x7c, 0x3c, - 0x00, 0x00, 0x00, 0x3c, 0x3c, 0x00, 0x00, 0x00, 0x3c, 0x3c, 0x00, 0x00, 0x00, 0x3c, 0x38, 0x00, - 0x00, 0x00, 0x1c, 0x38, 0x00, 0x00, 0x00, 0x1c, 0x38, 0x00, 0x00, 0x00, 0x1c, 0x38, 0x00, 0x00, - 0x00, 0x1c, 0x38, 0x00, 0x00, 0x00, 0x1c, 0x38, 0x00, 0x00, 0x00, 0x1c, 0x38, 0x00, 0x00, 0x00, - 0x1c, 0x38, 0x00, 0x00, 0x00, 0x1c, 0x1c, 0x00, 0x00, 0x00, 0x38, 0x1c, 0x00, 0x00, 0x00, 0x38, - 0x1c, 0x00, 0x00, 0x00, 0x38, 0x0e, 0x00, 0x00, 0x00, 0x70, 0x0f, 0x00, 0x00, 0x00, 0xf0, 0x07, - 0x00, 0x00, 0x00, 0xe0, 0x03, 0x80, 0x00, 0x01, 0xc0, 0x03, 0xc0, 0x00, 0x03, 0xc0, 0x01, 0xf0, - 0x00, 0x0f, 0x80, 0x00, 0xf8, 0x00, 0x1f, 0x00, 0x00, 0x3f, 0x00, 0xfc, 0x00, 0x00, 0x1f, 0xff, - 0xf8, 0x00, 0x00, 0x07, 0xff, 0xe0, 0x00, 0x00, 0x00, 0xff, 0x00, 0x00, -}; -const nbgl_icon_details_t C_switch_60_40 = { 60, 40, NBGL_BPP_1, false, C_switch_60_40_bitmap }; - -uint8_t const C_Check_Circle_64px_bitmap[] = { - 0x40, 0x00, 0x40, 0x00, 0x21, 0x33, 0x02, 0x00, 0x31, 0x02, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xad, 0x55, 0x39, 0x4e, 0x03, 0x31, 0x14, 0xfd, 0x24, 0x61, 0x5f, 0x4b, - 0x28, 0x80, 0x91, 0xa0, 0x01, 0x24, 0x88, 0xb8, 0x40, 0x46, 0x54, 0x20, 0x21, 0x41, 0x49, 0x39, - 0x2d, 0x15, 0xdc, 0x00, 0x90, 0xa0, 0x66, 0x11, 0xa2, 0x05, 0x71, 0x01, 0x10, 0x17, 0x48, 0x0a, - 0x6a, 0x02, 0x17, 0x60, 0xab, 0x41, 0x61, 0x89, 0x04, 0x24, 0x21, 0x9f, 0xef, 0x65, 0x66, 0xbe, - 0x3d, 0x0e, 0x8b, 0xc4, 0x14, 0x99, 0xb1, 0x9f, 0xfd, 0xfc, 0xfc, 0xfc, 0xf3, 0x8c, 0xf8, 0x7f, - 0x4f, 0xf5, 0x60, 0x1a, 0x60, 0x74, 0xa9, 0xd8, 0x00, 0xde, 0x04, 0xfd, 0xcc, 0x95, 0x1c, 0x68, - 0xcd, 0x87, 0xe8, 0xc9, 0x14, 0xbf, 0x85, 0x01, 0x52, 0x79, 0x0b, 0xae, 0x1b, 0x30, 0x40, 0x8b, - 0xb5, 0xc4, 0xae, 0x9c, 0xb5, 0x7c, 0x8d, 0xf8, 0x70, 0xe0, 0x89, 0xef, 0x71, 0x03, 0x7e, 0x13, - 0x5d, 0xfd, 0x7a, 0x4e, 0x7d, 0x4f, 0xb4, 0xd6, 0x38, 0x9e, 0xa5, 0x8e, 0xf9, 0xb8, 0x79, 0x4c, - 0xcd, 0x34, 0x5b, 0xe1, 0x9e, 0xda, 0x13, 0x7c, 0xbc, 0x18, 0x30, 0x19, 0x8b, 0xa3, 0x15, 0x5b, - 0x4d, 0xb9, 0x01, 0xa9, 0x89, 0x5a, 0xaf, 0x34, 0xfa, 0xd0, 0xd4, 0xfb, 0x41, 0x5d, 0xb9, 0xb0, - 0xb1, 0x0a, 0x30, 0x68, 0xfb, 0x71, 0x15, 0x53, 0x56, 0x00, 0x9a, 0x6e, 0x6c, 0xfc, 0xb3, 0x2f, - 0xe2, 0x24, 0x75, 0xdd, 0x49, 0xbf, 0x2f, 0x01, 0x86, 0xd4, 0x57, 0x10, 0x8e, 0xac, 0x5a, 0x0a, - 0x32, 0xaa, 0x97, 0xdc, 0x54, 0x5d, 0x47, 0x39, 0x3e, 0x80, 0x54, 0xc9, 0x63, 0x7a, 0x09, 0xb7, - 0x5a, 0x81, 0x34, 0xc7, 0xa9, 0x7f, 0x41, 0xbc, 0x0b, 0x00, 0x27, 0x6a, 0x3a, 0xdb, 0x92, 0xe2, - 0xed, 0x12, 0x6f, 0x3f, 0x74, 0x82, 0xb6, 0x64, 0x10, 0xf8, 0x52, 0x40, 0x1d, 0xa0, 0x23, 0xde, - 0x12, 0x27, 0x20, 0x62, 0xa5, 0x73, 0x0a, 0x9d, 0x04, 0xcf, 0x00, 0xdb, 0x88, 0xe5, 0xd8, 0x5b, - 0x8b, 0xe0, 0x5d, 0x0a, 0x7c, 0x02, 0x28, 0xa1, 0x93, 0x80, 0x56, 0xee, 0x15, 0xab, 0xa4, 0x0c, - 0x53, 0x19, 0x81, 0x07, 0x9d, 0x88, 0xeb, 0xa1, 0x3b, 0x49, 0x82, 0x00, 0xda, 0x11, 0x17, 0xc5, - 0x8f, 0x9b, 0x60, 0x47, 0x4c, 0xf5, 0x95, 0x0b, 0x2e, 0x82, 0x4b, 0xf1, 0xed, 0x41, 0x0f, 0x36, - 0x20, 0xb8, 0x15, 0xd2, 0xa4, 0x48, 0x37, 0xc1, 0x93, 0x30, 0xc8, 0xc2, 0x39, 0x81, 0x0b, 0xe7, - 0x04, 0x4e, 0x5c, 0x10, 0xac, 0x30, 0xdc, 0xd4, 0xa7, 0x08, 0x56, 0x98, 0xbe, 0xac, 0x5d, 0x7c, - 0x31, 0x5e, 0x10, 0x07, 0x1c, 0x70, 0x7f, 0x34, 0xff, 0x5a, 0xe8, 0x4f, 0xb3, 0x36, 0xc9, 0xad, - 0x2f, 0x80, 0x36, 0xc4, 0x53, 0x76, 0x3e, 0xd6, 0xfe, 0x3c, 0x61, 0x2d, 0x3f, 0x5f, 0x73, 0xba, - 0x3a, 0xdf, 0xb2, 0xac, 0x12, 0xd7, 0xf4, 0x0f, 0x59, 0x1f, 0x54, 0x25, 0xc3, 0x6e, 0x7b, 0x5f, - 0x54, 0x65, 0x01, 0x3b, 0x40, 0xe3, 0x78, 0x8e, 0xd4, 0xca, 0xbe, 0xfe, 0x1f, 0xe9, 0x92, 0x4c, - 0xb3, 0xf2, 0xc9, 0xe8, 0x32, 0xce, 0xb3, 0x92, 0x8c, 0xa6, 0x57, 0x34, 0x71, 0x39, 0x2e, 0x70, - 0xaa, 0xb6, 0x34, 0x0f, 0x1d, 0xd9, 0x5f, 0xe3, 0xe1, 0xf2, 0x9e, 0x63, 0xd5, 0xa7, 0x79, 0xfd, - 0x44, 0xba, 0xe8, 0xdd, 0x69, 0x63, 0xef, 0x1a, 0xe5, 0xc3, 0x64, 0x34, 0xd2, 0x9d, 0x2f, 0x27, - 0xbf, 0xcb, 0xa7, 0x1f, 0xf3, 0x8d, 0x9c, 0xb0, 0x03, 0x9b, 0x28, 0x53, 0x25, 0x23, 0x5f, 0x8d, - 0xc0, 0x3e, 0x33, 0xf2, 0x15, 0xeb, 0x59, 0x73, 0xc0, 0x39, 0x58, 0x51, 0x22, 0xf3, 0x7d, 0x2c, - 0xcc, 0xf7, 0x8d, 0x44, 0xbe, 0xcb, 0xc0, 0xa6, 0xfb, 0xe1, 0x02, 0xf1, 0x51, 0xdd, 0x0f, 0x03, - 0x98, 0x08, 0x6c, 0xfe, 0x64, 0xec, 0x2b, 0xac, 0xea, 0x19, 0x70, 0xf1, 0xaf, 0xf7, 0x1b, 0x2d, - 0xb1, 0x1f, 0xc2, 0xb3, 0x0d, 0x2e, 0xd0, 0xda, 0xd6, 0x0c, 0xc0, 0xc8, 0x72, 0xfe, 0x1f, 0xaf, - 0x6c, 0xfc, 0x02, 0x24, 0x14, 0x5a, 0xc5, 0x00, 0x08, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Check_Circle_64px = { 64, 64, NBGL_BPP_4, true, C_Check_Circle_64px_bitmap }; - -uint8_t const C_Denied_Circle_64px_bitmap[] = { - 0x40, 0x00, 0x40, 0x00, 0x21, 0x30, 0x02, 0x00, 0x2e, 0x02, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xad, 0x55, 0x4b, 0x2f, 0x04, 0x41, 0x10, 0x2e, 0x6b, 0xbd, 0x9f, 0x47, - 0x0e, 0xd8, 0x84, 0x48, 0x90, 0xac, 0x8d, 0x3f, 0x60, 0xe2, 0x44, 0x22, 0xe1, 0xe8, 0xb8, 0x71, - 0x73, 0xe2, 0x1f, 0x20, 0xe1, 0xec, 0x11, 0x71, 0x25, 0xfe, 0x00, 0xf1, 0x07, 0xd6, 0xc1, 0xd9, - 0xf2, 0x07, 0x3c, 0xe6, 0x4c, 0xd6, 0x63, 0xe3, 0xb9, 0xa6, 0x54, 0xf5, 0x63, 0xa6, 0xa7, 0x67, - 0x66, 0x97, 0x44, 0x1f, 0x76, 0xb6, 0xbb, 0xba, 0xaa, 0xbe, 0xfe, 0xea, 0xeb, 0x6a, 0xc4, 0xff, - 0x1b, 0x5f, 0xfb, 0x13, 0x00, 0x43, 0x0b, 0xc5, 0x04, 0xf3, 0x06, 0xa8, 0x31, 0x53, 0x8a, 0xb1, - 0x56, 0x1c, 0xf0, 0x47, 0xba, 0x58, 0xd5, 0x0c, 0x90, 0x2a, 0x58, 0x66, 0x2f, 0x64, 0x06, 0x68, - 0xb4, 0x52, 0xec, 0x08, 0xaf, 0xa5, 0x6b, 0xc4, 0xfb, 0xfd, 0x0c, 0xff, 0x1f, 0x0d, 0x99, 0xdf, - 0x78, 0xa9, 0x47, 0xf9, 0x78, 0xbb, 0x3c, 0x5b, 0x35, 0xed, 0x39, 0x5a, 0x98, 0x0d, 0xa6, 0x47, - 0x34, 0xad, 0x37, 0x32, 0xb8, 0x34, 0x1f, 0x33, 0xf7, 0xf3, 0x86, 0x6c, 0x00, 0x8e, 0x32, 0x36, - 0x85, 0xe1, 0xe6, 0x09, 0x8d, 0x3f, 0x7b, 0xa1, 0xdd, 0x07, 0x61, 0xbc, 0x1f, 0xb4, 0x34, 0xa9, - 0x27, 0x2b, 0x00, 0x7d, 0x36, 0x1f, 0x57, 0x41, 0xc8, 0x4f, 0x80, 0xba, 0x1b, 0xdb, 0xfe, 0xdd, - 0xed, 0xc7, 0x24, 0x74, 0x1d, 0x51, 0xbe, 0x2f, 0x01, 0xfa, 0xe5, 0xbf, 0x7c, 0x24, 0xbb, 0x42, - 0x90, 0x96, 0x55, 0x25, 0x36, 0xe3, 0xca, 0x49, 0xa8, 0x44, 0x99, 0x9e, 0xcd, 0xa3, 0x1a, 0x83, - 0xd6, 0xe7, 0xf8, 0x7b, 0x06, 0x70, 0x2c, 0x0f, 0x6d, 0xa9, 0x05, 0xa0, 0x9d, 0xbf, 0x8e, 0x66, - 0x62, 0x51, 0xf3, 0x3f, 0x2c, 0xbf, 0x8e, 0x00, 0xe0, 0x01, 0xb4, 0x8a, 0xe9, 0xab, 0x4e, 0xe3, - 0xc2, 0x32, 0xaa, 0xc0, 0x12, 0xe7, 0xb8, 0x3a, 0x46, 0xaa, 0xa4, 0xd8, 0x96, 0x78, 0x9f, 0x00, - 0xb6, 0x10, 0xcb, 0xfa, 0x74, 0x19, 0x85, 0x93, 0xe8, 0x90, 0x1b, 0xdf, 0x05, 0xc0, 0x47, 0x80, - 0x12, 0x1a, 0xeb, 0x9e, 0xde, 0xc7, 0x99, 0xbb, 0x38, 0x4b, 0x2a, 0xa8, 0x62, 0xd6, 0x70, 0xe7, - 0x88, 0x6d, 0x88, 0x6b, 0x3e, 0x3b, 0xc2, 0x12, 0xb8, 0x33, 0xa2, 0x16, 0xc4, 0x79, 0xfe, 0x09, - 0x02, 0x18, 0xee, 0xb8, 0xcd, 0xae, 0x8e, 0x64, 0x41, 0x07, 0x30, 0xdc, 0xa9, 0x44, 0xf5, 0x9c, - 0xa4, 0xd3, 0xd4, 0x91, 0xe1, 0x8e, 0xb7, 0x0c, 0x4d, 0x80, 0x34, 0x74, 0x68, 0x14, 0xe3, 0x91, - 0x09, 0x32, 0xed, 0x1c, 0x20, 0x70, 0xff, 0xbb, 0x3d, 0x2e, 0x7e, 0x2d, 0x7c, 0xb9, 0x40, 0x7c, - 0xf6, 0xf9, 0xce, 0xb8, 0xc0, 0xf9, 0x6a, 0xfc, 0x34, 0x28, 0x92, 0x92, 0xf8, 0x6d, 0x46, 0x3c, - 0xa9, 0x56, 0x9f, 0xf6, 0xda, 0xf5, 0x2d, 0x0b, 0x95, 0x18, 0xeb, 0xae, 0xbe, 0x9a, 0x1f, 0x42, - 0x1f, 0xa4, 0x92, 0x81, 0x78, 0x7d, 0x3d, 0x4b, 0x65, 0x29, 0x19, 0x47, 0xf5, 0x79, 0x28, 0x33, - 0x3b, 0xea, 0x1e, 0x45, 0xf4, 0x9d, 0x91, 0x06, 0x92, 0xb1, 0xd5, 0xcd, 0x4a, 0xfa, 0x5a, 0x8b, - 0xc0, 0x65, 0x2d, 0x70, 0x6b, 0xb8, 0x6a, 0xbd, 0x62, 0x37, 0x17, 0x9f, 0x1d, 0x15, 0xd7, 0x49, - 0xba, 0xdf, 0x8a, 0xd8, 0xbb, 0xa4, 0xfe, 0x90, 0xf5, 0x77, 0xc6, 0xf7, 0x97, 0xe3, 0xdf, 0xf5, - 0xa7, 0x9a, 0xfd, 0x8d, 0xaf, 0xa6, 0xd5, 0xb0, 0x57, 0x42, 0x42, 0x74, 0xed, 0x86, 0x7d, 0x1a, - 0xd2, 0x21, 0x7a, 0xb9, 0xf0, 0x86, 0x73, 0xee, 0xcf, 0x91, 0xfe, 0x3e, 0xa2, 0xf9, 0x5f, 0x8f, - 0xf4, 0x77, 0xd1, 0xb0, 0xe9, 0x7d, 0xb8, 0x40, 0x7c, 0x90, 0xef, 0x43, 0x2f, 0x46, 0x1a, 0xb6, - 0x39, 0xd2, 0xf6, 0x13, 0xf6, 0x95, 0x09, 0x99, 0x8b, 0x7f, 0x7d, 0xdf, 0x28, 0xc5, 0x9e, 0x36, - 0x4f, 0x27, 0x3c, 0xa0, 0x95, 0xcd, 0x29, 0x80, 0xc1, 0xa5, 0xc2, 0x3f, 0x3e, 0xd9, 0xf8, 0x03, - 0x70, 0xa7, 0x85, 0x84, 0x00, 0x08, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Denied_Circle_64px = { 64, 64, NBGL_BPP_4, true, C_Denied_Circle_64px_bitmap }; - -uint8_t const C_Important_Circle_64px_bitmap[] = { - 0x40, 0x00, 0x40, 0x00, 0x21, 0xfa, 0x01, 0x00, 0xf8, 0x01, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xb5, 0x55, 0xcd, 0x4e, 0xc2, 0x40, 0x10, 0x1e, 0xa1, 0xfe, 0xe3, 0xcf, - 0x51, 0x0f, 0x2a, 0x89, 0x5e, 0xd4, 0x04, 0x89, 0x2f, 0x60, 0xe3, 0x49, 0x13, 0x13, 0x3c, 0x7a, - 0xe4, 0xca, 0xcd, 0x37, 0x50, 0x13, 0x3d, 0xa3, 0xc6, 0x70, 0xd5, 0xf8, 0x02, 0x18, 0x5f, 0x00, - 0x0f, 0x9e, 0x05, 0x5f, 0xc0, 0x1f, 0xce, 0x1a, 0x10, 0x49, 0x54, 0xc0, 0x8e, 0xb3, 0xed, 0xb6, - 0x74, 0xdb, 0x59, 0xd0, 0x04, 0xe7, 0xd0, 0x76, 0xf6, 0xdb, 0xee, 0x7c, 0xfd, 0x76, 0xfa, 0x2d, - 0x62, 0xef, 0xa2, 0x99, 0x5b, 0x05, 0x58, 0xd8, 0x29, 0x6a, 0xe0, 0x43, 0x90, 0xb1, 0x59, 0x61, - 0xd0, 0x96, 0x09, 0x5e, 0x18, 0xc5, 0x8e, 0x30, 0x40, 0xa4, 0x10, 0x80, 0x2d, 0x05, 0x06, 0x18, - 0x08, 0x94, 0x38, 0xb1, 0xdf, 0xca, 0x3c, 0x20, 0xbe, 0xe4, 0xe2, 0xe2, 0x79, 0x49, 0x81, 0x3f, - 0xc4, 0xd0, 0x94, 0x7c, 0xc7, 0x3a, 0x15, 0xd9, 0x9e, 0x1f, 0x4f, 0xd2, 0xc0, 0x56, 0x3b, 0xbd, - 0xa4, 0x34, 0xea, 0xab, 0x50, 0xa6, 0x7c, 0xd9, 0x3f, 0x5f, 0x4c, 0x48, 0xb4, 0xc9, 0x51, 0xc5, - 0x41, 0x95, 0x6e, 0x9a, 0xd8, 0x78, 0xd9, 0x3b, 0xcd, 0x3e, 0x57, 0xf9, 0x7e, 0xd1, 0xd0, 0x9a, - 0x9b, 0xec, 0x02, 0xcc, 0x04, 0xf5, 0xb8, 0x6f, 0x2f, 0xd9, 0x00, 0xe8, 0x7b, 0x0c, 0xe2, 0xdf, - 0x93, 0xde, 0x9a, 0xc4, 0x6e, 0x2c, 0xac, 0x77, 0x09, 0x60, 0xd6, 0x79, 0x4a, 0x87, 0xaa, 0x4b, - 0x06, 0x86, 0xb3, 0xab, 0xa4, 0x26, 0xb7, 0x9d, 0xc4, 0xca, 0xde, 0xa6, 0x9a, 0xff, 0x53, 0x7d, - 0x41, 0xe3, 0x29, 0x71, 0xbf, 0x01, 0xc8, 0xb3, 0xdd, 0x02, 0x10, 0x13, 0x77, 0xd3, 0xa7, 0x84, - 0x12, 0xa6, 0x4d, 0xc0, 0x02, 0x18, 0xe1, 0x71, 0x5a, 0xd8, 0xe1, 0xb9, 0xc2, 0xe3, 0x6f, 0x00, - 0x59, 0xc4, 0x3a, 0xfb, 0x75, 0x22, 0x3e, 0x6d, 0x82, 0x55, 0x80, 0x0a, 0x8f, 0x53, 0xe5, 0x09, - 0x51, 0x25, 0xa2, 0xeb, 0xf7, 0x38, 0x8c, 0x22, 0xee, 0xf3, 0xea, 0x38, 0xc2, 0x0e, 0x23, 0x6e, - 0x8b, 0x0b, 0x1f, 0xc7, 0xe2, 0x55, 0xd3, 0x51, 0x81, 0x8b, 0x12, 0x44, 0x45, 0x91, 0x71, 0x3b, - 0x69, 0xf7, 0xb6, 0x20, 0x9e, 0x15, 0x43, 0x4f, 0x82, 0x9a, 0x4d, 0x92, 0xc7, 0xab, 0x42, 0xa0, - 0xff, 0xc6, 0xbb, 0xf1, 0x4b, 0x72, 0xcd, 0xe7, 0x6e, 0xa0, 0x21, 0x45, 0xd2, 0xe9, 0xd3, 0x2f, - 0x45, 0xd2, 0xe9, 0x3b, 0x84, 0x78, 0xd5, 0x69, 0x7f, 0x62, 0xdd, 0xf7, 0xb7, 0x2e, 0xc9, 0xb2, - 0x7f, 0x40, 0xca, 0xee, 0x92, 0x39, 0x1e, 0xaf, 0x39, 0x9d, 0x05, 0xba, 0x0d, 0xbc, 0x70, 0x2a, - 0x9b, 0xf2, 0x3f, 0x62, 0xe8, 0x19, 0xb2, 0x8d, 0x0b, 0x1c, 0xdc, 0x90, 0x0b, 0xd7, 0x35, 0x0d, - 0x5e, 0x96, 0xe3, 0xad, 0xa0, 0xb9, 0x78, 0xea, 0xc8, 0x75, 0x4d, 0xdd, 0xff, 0x2d, 0x85, 0x7d, - 0xd6, 0xf9, 0x43, 0xc2, 0x9b, 0xc9, 0xfb, 0x4b, 0xfe, 0x77, 0xfe, 0xd4, 0xd5, 0xdf, 0x48, 0x89, - 0xa0, 0x61, 0xd3, 0x92, 0x91, 0x8a, 0xe2, 0xaf, 0x8a, 0x61, 0x5f, 0x2b, 0xfe, 0x8a, 0x56, 0x52, - 0x9d, 0x70, 0x2b, 0xfc, 0x39, 0xe4, 0xef, 0x8b, 0xae, 0xbf, 0x1f, 0x84, 0xfc, 0xdd, 0x36, 0x6c, - 0x3a, 0x1f, 0xee, 0x10, 0x5f, 0x9d, 0xf3, 0x61, 0x1a, 0x43, 0x86, 0xed, 0x0f, 0x23, 0xd8, 0x53, - 0xcd, 0xb8, 0x02, 0x17, 0xff, 0x7a, 0xbe, 0x51, 0x89, 0x33, 0x17, 0xde, 0xd0, 0xf4, 0x73, 0xeb, - 0x68, 0x1d, 0x60, 0x3e, 0x53, 0xe8, 0xe1, 0x91, 0x8d, 0x3f, 0x0e, 0xc1, 0x39, 0xe4, 0x00, 0x08, - 0x00, 0x00, -}; -const nbgl_icon_details_t C_Important_Circle_64px = { 64, 64, NBGL_BPP_4, true, C_Important_Circle_64px_bitmap }; - -uint8_t const C_Review_64px_bitmap[] = { - 0x40, 0x00, 0x40, 0x00, 0x21, 0xd3, 0x00, 0x00, 0xd1, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xed, 0xd5, 0x3b, 0x0e, 0xc2, 0x30, 0x0c, 0x06, 0x60, 0xab, 0xea, 0x90, - 0x8d, 0x2b, 0xf4, 0x04, 0x39, 0x07, 0xc7, 0xe0, 0x28, 0x11, 0x62, 0xc8, 0x04, 0x77, 0x64, 0xea, - 0xd6, 0x95, 0xa9, 0xc1, 0x29, 0x24, 0xa6, 0xf8, 0x01, 0x43, 0x87, 0x0e, 0xf1, 0x52, 0xa1, 0xaf, - 0xb8, 0x4e, 0xa5, 0xfe, 0x4e, 0x69, 0x93, 0x9a, 0xa3, 0x50, 0x13, 0xf9, 0x1d, 0x84, 0xf2, 0xf4, - 0xf7, 0x41, 0xf2, 0xae, 0x36, 0x78, 0x00, 0x98, 0x0d, 0x14, 0xaf, 0x0d, 0xd0, 0x8f, 0x6c, 0xbc, - 0x81, 0x1a, 0xa0, 0xdf, 0xd8, 0x99, 0x70, 0x66, 0x87, 0x97, 0x11, 0x6f, 0xbd, 0x48, 0x8e, 0x43, - 0x3b, 0x1a, 0x9d, 0x7b, 0x0a, 0xd9, 0xcb, 0xc9, 0x35, 0x0f, 0xff, 0xfb, 0xf2, 0x1b, 0xe0, 0xf0, - 0xe5, 0x7d, 0x99, 0x4f, 0x71, 0x57, 0xce, 0xd7, 0xbc, 0x79, 0x73, 0xdd, 0x95, 0xef, 0x6f, 0x1f, - 0xce, 0xf2, 0xeb, 0xba, 0x76, 0x21, 0xfc, 0x6c, 0x07, 0x4f, 0x2e, 0xe6, 0x6f, 0x77, 0xaa, 0x2e, - 0xe7, 0x37, 0x90, 0xf3, 0xfc, 0x3f, 0xaf, 0x3c, 0x49, 0xe9, 0x69, 0xfa, 0xf2, 0x48, 0xcb, 0x73, - 0x03, 0xcb, 0xdf, 0xf9, 0xfd, 0xdb, 0xfb, 0x28, 0xd7, 0x6b, 0x3f, 0x04, 0xd0, 0x2b, 0xef, 0x17, - 0xcb, 0xbd, 0xfe, 0xe6, 0xea, 0x7a, 0x92, 0x57, 0xdf, 0xc7, 0x7a, 0x1b, 0xa3, 0x56, 0xd3, 0x06, - 0x8b, 0xfb, 0x09, 0xaa, 0x24, 0xa5, 0x2a, 0x00, 0x08, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Review_64px = { 64, 64, NBGL_BPP_4, true, C_Review_64px_bitmap }; - -uint8_t const C_SecurityShield_64px_bitmap[] = { - 0x40, 0x00, 0x40, 0x00, 0x21, 0x5a, 0x02, 0x00, 0x58, 0x02, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xad, 0x95, 0xbf, 0x53, 0x13, 0x41, 0x14, 0xc7, 0xbf, 0x97, 0x1c, 0xbf, - 0x14, 0xf1, 0x2a, 0x3a, 0xf0, 0x26, 0xb6, 0x8e, 0xc6, 0x86, 0x52, 0xd3, 0xd0, 0xd0, 0xc0, 0x7f, - 0x00, 0xa2, 0x85, 0x9d, 0x69, 0x1d, 0x2d, 0x62, 0xc1, 0x4c, 0xba, 0x60, 0x6d, 0x01, 0x63, 0x63, - 0xe3, 0x8c, 0xb4, 0x56, 0xde, 0x28, 0x43, 0xc3, 0x00, 0xf6, 0x16, 0x41, 0x0a, 0xad, 0x0c, 0xc2, - 0x80, 0x06, 0x48, 0x38, 0xf7, 0xed, 0xde, 0xed, 0xef, 0x8b, 0x33, 0x8e, 0xdb, 0x24, 0xbb, 0x9f, - 0xbd, 0xb7, 0xef, 0x7d, 0xdf, 0xbe, 0xb7, 0x69, 0xfa, 0x3f, 0x46, 0xef, 0xcd, 0xa3, 0x4a, 0xe5, - 0xe6, 0xec, 0xd3, 0x3d, 0x3f, 0x7e, 0x81, 0x7c, 0xcc, 0x7c, 0xf0, 0xe0, 0x4b, 0x68, 0x63, 0xce, - 0xe5, 0xa7, 0x3a, 0xc7, 0xf0, 0xa1, 0xcd, 0xd7, 0x0d, 0x8e, 0xd0, 0xf6, 0x22, 0x46, 0xf0, 0xf8, - 0x6d, 0xa7, 0xf3, 0x63, 0x7b, 0xa5, 0xea, 0xb3, 0x70, 0x0e, 0x5c, 0xc9, 0xff, 0x6f, 0xc5, 0xb4, - 0x61, 0xd4, 0xe0, 0xc7, 0xc0, 0xbc, 0x9c, 0xf4, 0x97, 0x69, 0xc3, 0x2d, 0xeb, 0x78, 0xdd, 0xe0, - 0x6b, 0xda, 0xd0, 0xd2, 0x16, 0x6a, 0x18, 0x32, 0xec, 0xd1, 0x86, 0xb2, 0xfa, 0xa2, 0x0f, 0x8c, - 0x9b, 0xfe, 0x36, 0xd8, 0x86, 0xdb, 0x72, 0xf6, 0x0b, 0xb8, 0x6f, 0xe9, 0x55, 0x03, 0x4a, 0x6d, - 0xcd, 0xbd, 0x77, 0x56, 0xc0, 0x5d, 0x66, 0x60, 0x2a, 0x9f, 0x6c, 0x20, 0x70, 0x14, 0xfd, 0x08, - 0x04, 0xb9, 0x81, 0x25, 0x0c, 0xbb, 0x19, 0x61, 0x32, 0x4c, 0x4b, 0xf5, 0xae, 0xba, 0x29, 0x39, - 0x60, 0x1e, 0x88, 0x10, 0x7a, 0xc0, 0x0d, 0x75, 0x2a, 0x72, 0xf9, 0xaa, 0xb9, 0x68, 0x67, 0xc0, - 0xa2, 0x0a, 0x4b, 0x8c, 0x16, 0x37, 0x30, 0xc2, 0x57, 0x4f, 0x80, 0x35, 0xc1, 0x55, 0x06, 0xaf, - 0x0b, 0x0f, 0x78, 0x1e, 0x8f, 0x80, 0xb6, 0x87, 0xa7, 0x09, 0x70, 0x87, 0x56, 0x3f, 0xcb, 0xf0, - 0x00, 0xf1, 0xfb, 0x93, 0xf3, 0xb3, 0xec, 0x80, 0x04, 0x21, 0xe5, 0xb8, 0xd9, 0x6c, 0x9a, 0x9c, - 0xa5, 0x85, 0x1b, 0x5e, 0xe5, 0xdb, 0x84, 0x6f, 0x06, 0xff, 0x2a, 0x22, 0xa8, 0x63, 0x8c, 0x5f, - 0x11, 0x87, 0x77, 0x45, 0xde, 0x6a, 0x24, 0x4f, 0xd7, 0xc3, 0x99, 0x70, 0x21, 0xe7, 0xe3, 0xc4, - 0x43, 0xe7, 0x7c, 0x96, 0x18, 0x8a, 0x30, 0xc6, 0x04, 0xf1, 0x51, 0xdb, 0x7f, 0xae, 0xcc, 0x93, - 0x34, 0x8d, 0x68, 0x96, 0xf3, 0xfe, 0x8e, 0xc6, 0xcf, 0xb9, 0xf2, 0xd0, 0xf9, 0x7a, 0x79, 0x47, - 0x71, 0xf6, 0xe9, 0x98, 0xc5, 0x1b, 0xe4, 0x92, 0xe4, 0x7c, 0x36, 0x80, 0xd7, 0x1d, 0x6e, 0xda, - 0x8f, 0xa9, 0x6e, 0x0c, 0xff, 0x7a, 0x96, 0x7f, 0x13, 0x7f, 0x8f, 0xaf, 0x8a, 0x6b, 0x05, 0xfa, - 0x24, 0x5c, 0x9f, 0x05, 0x3a, 0xc4, 0xab, 0x6f, 0x15, 0x25, 0x7e, 0x7d, 0x0b, 0xf2, 0x93, 0x95, - 0xf5, 0x2a, 0xbf, 0xde, 0x9e, 0xfc, 0x1e, 0x8b, 0x0b, 0xb4, 0x81, 0xb2, 0xff, 0x7e, 0xd4, 0x45, - 0x5d, 0xed, 0x17, 0xdc, 0xaf, 0x0b, 0x88, 0xba, 0x29, 0xba, 0x9f, 0x07, 0x59, 0x05, 0x9d, 0xfa, - 0xef, 0x37, 0x15, 0xc8, 0x5a, 0x56, 0x1f, 0xf3, 0x9e, 0xfa, 0x60, 0x55, 0x3f, 0x34, 0xa8, 0xbe, - 0x1a, 0xb2, 0x45, 0x44, 0x76, 0xfb, 0xc8, 0xf7, 0xb6, 0x8b, 0xeb, 0x9b, 0x2d, 0x92, 0x6c, 0x99, - 0xcc, 0x6e, 0x7f, 0x38, 0xd1, 0x5a, 0xd8, 0x91, 0x0c, 0x40, 0xb5, 0xac, 0x58, 0xeb, 0x91, 0xbf, - 0xf5, 0xf6, 0xa8, 0x22, 0x91, 0x1d, 0xb0, 0xe7, 0xf4, 0xb7, 0x4f, 0x50, 0xa7, 0xf3, 0x0a, 0x09, - 0x0d, 0xfc, 0x8d, 0xe1, 0x40, 0xeb, 0xe1, 0x49, 0xd6, 0x09, 0xb2, 0xf1, 0x3d, 0x62, 0xfc, 0x5e, - 0x51, 0x7f, 0x4e, 0x37, 0x49, 0xa1, 0x11, 0xab, 0xbf, 0x4b, 0x07, 0x2e, 0x1e, 0x10, 0x2e, 0xef, - 0x59, 0xef, 0x43, 0xe9, 0xd9, 0x2e, 0x75, 0xbd, 0xf7, 0x0f, 0xb9, 0xbe, 0x81, 0x15, 0x6f, 0xc2, - 0x57, 0x2b, 0x51, 0x26, 0x7f, 0xd0, 0xf2, 0xa8, 0xa5, 0x86, 0x83, 0xd3, 0xcb, 0x48, 0xc3, 0x93, - 0x9e, 0x37, 0xf2, 0xa5, 0xa4, 0xa5, 0xe7, 0xde, 0x07, 0xf4, 0xcb, 0xca, 0x5d, 0x82, 0x33, 0xaf, - 0x06, 0xbc, 0xc1, 0x9d, 0xc3, 0x7f, 0x79, 0xb9, 0xff, 0x00, 0xb6, 0x83, 0x9c, 0x31, 0x00, 0x08, - 0x00, 0x00, -}; -const nbgl_icon_details_t C_SecurityShield_64px = { 64, 64, NBGL_BPP_4, true, C_SecurityShield_64px_bitmap }; - -uint8_t const C_Warning_64px_bitmap[] = { - 0x40, 0x00, 0x40, 0x00, 0x21, 0x5f, 0x01, 0x00, 0x5d, 0x01, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x85, 0xd5, 0x31, 0x4e, 0xc3, 0x40, 0x10, 0x05, 0xd0, 0x8d, 0x85, 0x08, - 0x4a, 0x45, 0x49, 0x91, 0xc2, 0x25, 0xb2, 0x52, 0xe4, 0x08, 0x39, 0x40, 0xc4, 0x19, 0x72, 0x82, - 0x5c, 0x81, 0x84, 0x03, 0x80, 0xb8, 0x41, 0xc4, 0x05, 0x72, 0x04, 0x0a, 0xd2, 0xe7, 0x08, 0x69, - 0x02, 0xa2, 0x0b, 0xa5, 0x13, 0xa1, 0x1d, 0xec, 0x99, 0x5d, 0xb3, 0xf6, 0xee, 0x1f, 0x6f, 0xfb, - 0xc6, 0x96, 0xbc, 0xfe, 0x33, 0x43, 0x84, 0x4f, 0xb9, 0x27, 0xed, 0x5c, 0xf2, 0xeb, 0x93, 0xc2, - 0xbf, 0x53, 0x63, 0x26, 0x0a, 0xcf, 0x8c, 0x31, 0x23, 0x9d, 0xb1, 0x5b, 0x66, 0xe8, 0x76, 0x51, - 0xe1, 0x60, 0x06, 0x7d, 0x5d, 0x3f, 0xfc, 0xb8, 0x41, 0xce, 0xbc, 0x24, 0xe4, 0xcc, 0x73, 0x42, - 0xfe, 0xea, 0x18, 0xf8, 0x9b, 0xe7, 0xb4, 0xef, 0x6a, 0x96, 0x7b, 0x4b, 0x39, 0x73, 0x41, 0xc8, - 0x99, 0xef, 0x08, 0xf9, 0x31, 0xe4, 0xd8, 0xbf, 0x5a, 0x1c, 0x79, 0x79, 0x5b, 0xf1, 0x90, 0x90, - 0x33, 0x87, 0x91, 0x68, 0x3b, 0xf3, 0x55, 0x18, 0xa9, 0x96, 0x9f, 0x23, 0x6e, 0xf9, 0x25, 0x8f, - 0x38, 0x74, 0x8e, 0x4b, 0xd6, 0xc9, 0xeb, 0xbf, 0x0b, 0x6f, 0x09, 0x38, 0xf3, 0xe0, 0x85, 0x80, - 0xdb, 0x34, 0x7b, 0x97, 0xb0, 0xc5, 0xec, 0x5d, 0xc2, 0x46, 0xc8, 0x5d, 0xd8, 0x90, 0xaf, 0x9b, - 0xb8, 0x94, 0xc6, 0x9f, 0x1b, 0xfa, 0x31, 0x46, 0xdc, 0x36, 0x8c, 0x7d, 0x4e, 0xba, 0x17, 0x3d, - 0xae, 0xbd, 0x5f, 0xe2, 0xbc, 0xc4, 0x6e, 0x9f, 0xf4, 0xef, 0x93, 0xeb, 0x4b, 0x16, 0x84, 0xf7, - 0x9b, 0x2a, 0x68, 0xfe, 0x4f, 0x5d, 0x90, 0x3d, 0x43, 0x77, 0x05, 0x5b, 0xe8, 0x7d, 0xf9, 0x70, - 0xf1, 0xeb, 0x16, 0x44, 0xf9, 0xcc, 0xde, 0xa1, 0xbb, 0x00, 0x1f, 0xa0, 0xd3, 0x39, 0xef, 0xb4, - 0x4f, 0xb7, 0xbf, 0xbe, 0xf5, 0xfe, 0x72, 0xed, 0x1b, 0x14, 0xa4, 0xfb, 0x7b, 0x78, 0x82, 0x2e, - 0x05, 0xf7, 0xd8, 0xe9, 0x33, 0x18, 0x3f, 0xc9, 0xf9, 0xf4, 0xa1, 0xcf, 0x27, 0x97, 0x97, 0x02, - 0xbb, 0x14, 0x4c, 0xb0, 0x4b, 0xc1, 0x03, 0x76, 0xf2, 0x89, 0x43, 0x6e, 0x57, 0xfa, 0x7c, 0xf7, - 0x89, 0xdb, 0xe8, 0xfb, 0xc5, 0x4c, 0x95, 0xfd, 0xb4, 0x50, 0xf7, 0x93, 0x5f, 0x60, 0x23, 0x65, - 0x3f, 0xe6, 0xba, 0x73, 0xa0, 0xc6, 0x3d, 0xfb, 0x99, 0xf4, 0x05, 0x5e, 0xcd, 0xcb, 0x3f, 0xe4, - 0x2a, 0x7b, 0x24, 0x00, 0x08, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Warning_64px = { 64, 64, NBGL_BPP_4, true, C_Warning_64px_bitmap }; - -uint8_t const C_left_half_64px_bitmap[] = { - 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, - 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, - 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf8, 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf8, - 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf8, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf0, - 0x07, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x07, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe0, - 0x03, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x80, - 0x01, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x80, 0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x00, - 0x00, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xfe, 0x00, 0x00, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xfc, 0x00, - 0x00, 0x1f, 0xff, 0xff, 0xff, 0xff, 0xf8, 0x00, 0x00, 0x07, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x00, - 0x00, 0x03, 0xff, 0xff, 0xff, 0xff, 0xc0, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, - 0x00, 0x00, 0x7f, 0xff, 0xff, 0xfe, 0x00, 0x00, 0x00, 0x00, 0x0f, 0xff, 0xff, 0xf0, 0x00, 0x00, - 0x00, 0x00, 0x03, 0xff, 0xff, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3f, 0xfc, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_left_half_64px = { 24, 64, NBGL_BPP_1, false, C_left_half_64px_bitmap }; - -uint8_t const C_Back_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x21, 0x8c, 0x00, 0x00, 0x8a, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xed, 0xd3, 0xcd, 0x09, 0xc0, 0x20, 0x0c, 0x80, 0xd1, 0xd0, 0x53, 0x0e, - 0x1d, 0xa2, 0xa3, 0x39, 0x4a, 0x36, 0x70, 0x95, 0x6e, 0xd2, 0x6d, 0xc4, 0x43, 0xc1, 0xe6, 0xc7, - 0xd6, 0xa8, 0xd0, 0x73, 0x0f, 0xf5, 0x10, 0xe1, 0xe3, 0x81, 0x10, 0xb0, 0x94, 0x97, 0x43, 0xf8, - 0xb7, 0xef, 0xb6, 0xc3, 0xb7, 0x53, 0x67, 0x46, 0xdf, 0x28, 0xca, 0xdc, 0x21, 0xb6, 0x96, 0x61, - 0x95, 0x2b, 0x01, 0xb6, 0x46, 0x06, 0x4a, 0xd0, 0x5b, 0x5b, 0x86, 0xfa, 0x92, 0x41, 0x6d, 0x37, - 0xab, 0x50, 0xda, 0xc3, 0x2a, 0x94, 0xd6, 0x98, 0x41, 0x6e, 0x8e, 0x19, 0xe4, 0xe6, 0x99, 0x42, - 0xc2, 0x8e, 0x29, 0x24, 0xec, 0x99, 0xc0, 0x6d, 0x81, 0x61, 0x33, 0x09, 0xf8, 0xc4, 0x61, 0x55, - 0x01, 0x60, 0x5a, 0x60, 0x9a, 0x19, 0x43, 0x7c, 0xfb, 0x01, 0xe5, 0x02, 0xe6, 0x04, 0x3a, 0xe4, - 0x20, 0x03, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Back_40px = { 40, 40, NBGL_BPP_4, true, C_Back_40px_bitmap }; - -uint8_t const C_Check_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x01, 0x54, 0x00, 0x00, 0x52, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x63, 0x60, 0xc0, 0x05, 0x78, 0x40, 0x84, 0x1c, 0x88, 0x90, 0x07, 0x13, - 0x0d, 0x40, 0x82, 0xff, 0x00, 0x90, 0x60, 0x7f, 0x00, 0x24, 0x98, 0x3f, 0x00, 0x09, 0xc6, 0x1f, - 0x20, 0x99, 0x3f, 0x20, 0xa2, 0x0e, 0x44, 0xd8, 0xe3, 0x57, 0x08, 0x26, 0x2a, 0x60, 0x2c, 0xb0, - 0x18, 0x58, 0x16, 0xac, 0x0e, 0xac, 0x03, 0xac, 0xd7, 0x1e, 0x6e, 0x5e, 0x0d, 0x5c, 0x83, 0x01, - 0x03, 0x01, 0x00, 0x00, 0x63, 0x83, 0xdc, 0x77, 0xc8, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Check_40px = { 40, 40, NBGL_BPP_1, true, C_Check_40px_bitmap }; - -uint8_t const C_Check_Circle_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x21, 0x4b, 0x01, 0x00, 0x49, 0x01, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x75, 0x53, 0x3b, 0x52, 0xc3, 0x30, 0x10, 0x7d, 0x16, 0x0d, 0x50, 0x04, - 0x57, 0x0c, 0x34, 0x58, 0x4d, 0x66, 0x20, 0x05, 0xd0, 0xd0, 0x86, 0x3b, 0xc0, 0x01, 0x18, 0x4e, - 0xc0, 0x15, 0x0c, 0x17, 0xe0, 0x53, 0xc3, 0x84, 0x49, 0xcf, 0xe4, 0x08, 0xa9, 0xa9, 0xa8, 0xa1, - 0x61, 0x12, 0x0e, 0x00, 0xe6, 0x37, 0xb6, 0x83, 0xb3, 0x48, 0x96, 0x56, 0x96, 0x32, 0xe3, 0x2d, - 0xa4, 0x9d, 0xe7, 0xb7, 0xbb, 0x4f, 0xbb, 0x6b, 0xa2, 0x56, 0x7b, 0x3c, 0x8a, 0xa3, 0x83, 0xbb, - 0x00, 0xba, 0x40, 0x6d, 0xbd, 0xf7, 0x06, 0x3a, 0x87, 0xb5, 0x6d, 0x07, 0xbd, 0x01, 0xeb, 0x0f, - 0x44, 0x2f, 0xa7, 0xc0, 0xae, 0x85, 0xca, 0x18, 0x3b, 0xc6, 0x1b, 0x22, 0x1a, 0x1b, 0xef, 0x1e, - 0x9b, 0x1c, 0x71, 0x8d, 0xd5, 0xfa, 0x9e, 0x41, 0xb8, 0xd4, 0x73, 0x89, 0x91, 0xbe, 0x27, 0xe8, - 0x93, 0x97, 0x7a, 0x4b, 0x5f, 0x52, 0x78, 0x0a, 0xe6, 0x72, 0x49, 0x9d, 0x39, 0x3a, 0xfa, 0xbc, - 0xb4, 0xe0, 0x04, 0xca, 0x9b, 0x62, 0xa0, 0xdc, 0x74, 0xd9, 0x62, 0x05, 0x12, 0x55, 0x55, 0x68, - 0x37, 0x05, 0x13, 0xa5, 0xfa, 0x2a, 0xeb, 0xea, 0x39, 0x98, 0x78, 0x25, 0xa8, 0xd2, 0x5c, 0x9f, - 0x98, 0xe1, 0xa9, 0xc0, 0x19, 0x05, 0xc4, 0x5f, 0x0c, 0x7e, 0x8c, 0xc8, 0x86, 0x58, 0xe2, 0xe4, - 0x0b, 0xaf, 0x14, 0x10, 0x2b, 0xec, 0x65, 0x60, 0xb9, 0x4c, 0x44, 0xf2, 0xe1, 0x30, 0x26, 0x62, - 0xad, 0xc1, 0x14, 0x71, 0x64, 0xb0, 0x26, 0x96, 0xbe, 0x4d, 0x30, 0x92, 0x4f, 0xae, 0xc1, 0xbc, - 0x0a, 0x87, 0x4e, 0x0b, 0xe7, 0x53, 0x5a, 0x58, 0xb3, 0xab, 0xab, 0x34, 0xff, 0xd9, 0xb7, 0xb9, - 0xb2, 0x99, 0x4a, 0x26, 0x57, 0x42, 0x79, 0xba, 0x4f, 0xa9, 0xb0, 0x98, 0x7d, 0xaf, 0xee, 0x53, - 0x56, 0xf7, 0xd4, 0x75, 0xba, 0xd0, 0x23, 0xce, 0xcd, 0x54, 0xc8, 0xef, 0x3d, 0xed, 0x87, 0x33, - 0x12, 0x6d, 0xb3, 0x2c, 0xc3, 0x99, 0x8f, 0xdb, 0x76, 0x83, 0x66, 0x31, 0x7a, 0xc6, 0xbb, 0x41, - 0xc4, 0x2f, 0x9d, 0x36, 0xbb, 0xd6, 0x5f, 0x5c, 0x53, 0x60, 0xc3, 0x53, 0x30, 0x5c, 0x5c, 0x53, - 0x6d, 0xcf, 0xc7, 0x71, 0xd4, 0xbd, 0x6d, 0xff, 0x07, 0xe8, 0x1f, 0xf5, 0xf4, 0xf5, 0xf3, 0x20, - 0x03, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Check_Circle_40px = { 40, 40, NBGL_BPP_4, true, C_Check_Circle_40px_bitmap }; - -uint8_t const C_Chevron_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x22, 0x5c, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xda, 0x1c, 0xe4, 0x03, 0x10, 0x03, 0xe2, 0x03, 0x30, 0x03, 0xe0, 0x03, 0x50, 0x03, 0xde, 0x03, - 0x20, 0x18, 0x20, 0x03, 0xdc, 0x03, 0x20, 0x08, 0xc1, 0x08, 0x20, 0x03, 0xda, 0x03, 0x20, 0x08, - 0xc3, 0x08, 0x20, 0x03, 0xd8, 0x03, 0x20, 0x08, 0xc5, 0x08, 0x20, 0x03, 0xd6, 0x03, 0x20, 0x08, - 0xc7, 0x08, 0x20, 0x03, 0xd4, 0x05, 0x20, 0x08, 0xc9, 0x08, 0x20, 0x05, 0xd3, 0x9e, 0x20, 0x80, - 0xcb, 0x98, 0x02, 0xe0, 0xd4, 0x0e, 0x09, 0xcd, 0x09, 0x0e, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xe2, -}; -const nbgl_icon_details_t C_Chevron_40px = { 40, 40, NBGL_BPP_4, true, C_Chevron_40px_bitmap }; - -uint8_t const C_Chevron_Back_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x21, 0x76, 0x00, 0x00, 0x74, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xed, 0xd2, 0xc1, 0x0d, 0x80, 0x30, 0x08, 0x05, 0x50, 0x8e, 0x3d, 0x38, - 0xa4, 0xa3, 0xb0, 0x41, 0x57, 0x71, 0x93, 0x6e, 0x63, 0x38, 0x98, 0xd4, 0x42, 0x10, 0x7e, 0xeb, - 0x06, 0x46, 0x0e, 0x34, 0xe5, 0xbf, 0x84, 0x0b, 0xbd, 0xff, 0x35, 0xaa, 0xe1, 0xe7, 0xb2, 0x2e, - 0x05, 0x67, 0x5c, 0xb5, 0x1f, 0x54, 0x73, 0x24, 0xb4, 0xe9, 0x73, 0x12, 0x40, 0x76, 0xb0, 0x27, - 0x94, 0x27, 0x07, 0xc8, 0x11, 0x07, 0x94, 0x4c, 0x03, 0x32, 0xac, 0x73, 0x28, 0xb8, 0xcd, 0x21, - 0x32, 0x87, 0x13, 0x73, 0x38, 0x33, 0x83, 0x0b, 0x33, 0xb8, 0x32, 0x85, 0x2b, 0x53, 0xf8, 0x62, - 0x03, 0x96, 0xcf, 0x1d, 0xc6, 0x0d, 0xf2, 0x8e, 0x43, 0x73, 0x20, 0x03, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Chevron_Back_40px = { 40, 40, NBGL_BPP_4, true, C_Chevron_Back_40px_bitmap }; - -uint8_t const C_Chevron_Next_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x21, 0x71, 0x00, 0x00, 0x6f, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xed, 0xce, 0xbb, 0x0d, 0x80, 0x30, 0x0c, 0x45, 0x51, 0x57, 0x51, 0x0a, - 0x86, 0xcc, 0x06, 0xac, 0x90, 0x0d, 0x18, 0x09, 0xa6, 0x42, 0x48, 0x14, 0x8f, 0xc4, 0x44, 0x8e, - 0x3f, 0x1b, 0x20, 0x6e, 0xf9, 0x74, 0x64, 0x19, 0xf8, 0x58, 0x35, 0x87, 0xe9, 0x22, 0xda, 0x02, - 0x23, 0xca, 0x81, 0xa5, 0xe2, 0x61, 0xa5, 0xf5, 0x74, 0xb0, 0x31, 0xc0, 0xc1, 0xc6, 0x00, 0x0b, - 0x99, 0x39, 0xc8, 0xcc, 0xc2, 0xc1, 0x0c, 0x1c, 0x4c, 0x43, 0x61, 0x0a, 0x0a, 0x9b, 0x50, 0x31, - 0x81, 0xc7, 0x64, 0x1d, 0x2e, 0xec, 0x92, 0xfe, 0xbe, 0xbc, 0x07, 0x77, 0xbd, 0xdd, 0xf8, 0xeb, - 0x3d, 0x38, 0x09, 0xbe, 0x9b, 0x20, 0x03, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Chevron_Next_40px = { 40, 40, NBGL_BPP_4, true, C_Chevron_Next_40px_bitmap }; - -uint8_t const C_Close_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x21, 0x85, 0x00, 0x00, 0x83, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xfb, 0xff, 0x7f, 0xc0, 0xc0, 0xbf, 0xf9, 0x08, 0xf6, 0xcf, 0xf7, 0x10, - 0xfa, 0x11, 0x07, 0x42, 0xac, 0x41, 0x0f, 0x42, 0x4f, 0x60, 0xe8, 0x87, 0x09, 0xfd, 0x60, 0xe0, - 0x84, 0x31, 0xe0, 0x0a, 0x1b, 0xe0, 0xd2, 0x70, 0x16, 0x92, 0x2c, 0x9c, 0x89, 0x50, 0x06, 0x67, - 0x23, 0x29, 0x83, 0x73, 0x90, 0x95, 0x41, 0x79, 0x28, 0xca, 0xa0, 0x5c, 0x54, 0x65, 0x60, 0x3e, - 0x9a, 0x32, 0xb0, 0x42, 0x74, 0x65, 0x20, 0x85, 0xe8, 0xca, 0x40, 0x0a, 0x31, 0x94, 0x61, 0x15, - 0xc3, 0xa2, 0x17, 0x9b, 0x1d, 0x58, 0xdc, 0x82, 0xcd, 0xcd, 0x58, 0xfc, 0x86, 0x2d, 0x0c, 0xb0, - 0x84, 0x15, 0xb6, 0x30, 0xc5, 0x12, 0xf6, 0xd8, 0xe2, 0x08, 0x5b, 0x5c, 0x62, 0x8b, 0x73, 0x6c, - 0x69, 0x63, 0x40, 0x00, 0x00, 0xb4, 0x0b, 0xb4, 0x14, 0x20, 0x03, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Close_40px = { 40, 40, NBGL_BPP_4, true, C_Close_40px_bitmap }; - -uint8_t const C_Denied_Circle_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x21, 0x3e, 0x01, 0x00, 0x3c, 0x01, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x75, 0x53, 0x3b, 0x4e, 0x03, 0x31, 0x10, 0x7d, 0x6b, 0x9a, 0x90, 0x02, - 0xb6, 0x42, 0xd0, 0x24, 0x6e, 0x90, 0x20, 0x45, 0xa0, 0xa1, 0x0d, 0x77, 0x80, 0x03, 0x20, 0x4e, - 0xc0, 0x15, 0x16, 0x2e, 0x10, 0xa0, 0x06, 0x05, 0xa5, 0x47, 0x39, 0x42, 0x6a, 0x2a, 0x6a, 0x68, - 0xa2, 0x84, 0x03, 0x40, 0x40, 0xa0, 0xcd, 0x06, 0xf2, 0xf0, 0xac, 0x77, 0x13, 0xef, 0x6f, 0xa4, - 0xb5, 0xc7, 0xcf, 0xcf, 0x33, 0x6f, 0xc7, 0x63, 0xb2, 0xd2, 0x9e, 0x4e, 0x7c, 0xef, 0xe8, 0x3e, - 0x03, 0x5d, 0x21, 0xb6, 0xd6, 0xfb, 0x0a, 0xba, 0x44, 0x62, 0x7b, 0x4b, 0xe8, 0x0d, 0xd8, 0x7a, - 0x24, 0x5f, 0xcf, 0x81, 0x76, 0x02, 0x45, 0x3e, 0xf6, 0xad, 0xd7, 0x87, 0x37, 0xb4, 0xde, 0x03, - 0x76, 0xd2, 0x13, 0x37, 0xa8, 0xc7, 0xf3, 0x1c, 0x6a, 0x19, 0x7a, 0xa1, 0x31, 0x90, 0x79, 0x8c, - 0x0e, 0x9d, 0xd0, 0x0d, 0x99, 0xb4, 0x72, 0x14, 0x2c, 0xf4, 0x9a, 0x19, 0x43, 0x6c, 0xb8, 0x4a, - 0xc7, 0xe8, 0x92, 0x13, 0xf4, 0x5c, 0x6c, 0x86, 0xa6, 0xc9, 0xaa, 0x84, 0xdc, 0x65, 0x3a, 0xea, - 0x9a, 0xf9, 0x24, 0x7b, 0x50, 0x63, 0x3a, 0x5e, 0x2b, 0xfe, 0x09, 0x97, 0x81, 0x44, 0x09, 0x21, - 0xd8, 0x14, 0xcf, 0x33, 0x5c, 0x30, 0x59, 0xc6, 0x1b, 0xfc, 0x41, 0xef, 0xdb, 0x8a, 0x34, 0x6b, - 0x4b, 0x63, 0x84, 0xb3, 0x2f, 0x8c, 0x68, 0x89, 0x96, 0x66, 0x82, 0x1d, 0x4c, 0x61, 0x35, 0x04, - 0xb0, 0x34, 0x12, 0xcd, 0x8f, 0x04, 0x0b, 0x61, 0x69, 0x06, 0xdb, 0x2c, 0xc3, 0xca, 0xce, 0x7e, - 0x16, 0x73, 0x1c, 0x97, 0x69, 0x29, 0xd3, 0xfc, 0x5b, 0xfc, 0xb7, 0x11, 0xf5, 0x7a, 0xb6, 0x06, - 0x52, 0xa7, 0x20, 0x5f, 0xab, 0xba, 0x70, 0x73, 0x35, 0x6d, 0x4b, 0x94, 0x46, 0xa1, 0xf6, 0x3c, - 0xcc, 0xde, 0x91, 0xaa, 0xba, 0xcb, 0x28, 0x7b, 0xe7, 0xc3, 0xaa, 0xde, 0xe0, 0xdc, 0x47, 0xcb, - 0x7a, 0xb7, 0xf0, 0x06, 0xc9, 0xee, 0x64, 0xd5, 0x6b, 0x9d, 0x7c, 0x9b, 0x02, 0xdb, 0x8e, 0x82, - 0x7e, 0xbe, 0x4d, 0xc5, 0x5e, 0x4e, 0x7d, 0x6f, 0xf7, 0xae, 0xfa, 0x0d, 0xf0, 0x1f, 0x93, 0x8f, - 0x11, 0x3f, 0x20, 0x03, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Denied_Circle_40px = { 40, 40, NBGL_BPP_4, true, C_Denied_Circle_40px_bitmap }; - -uint8_t const C_Erase_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x01, 0x70, 0x00, 0x00, 0x6e, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x63, 0x60, 0x80, 0x03, 0xfb, 0xff, 0x7f, 0x18, 0x18, 0xea, 0xff, 0xff, - 0xc3, 0x43, 0xd4, 0xfd, 0xaf, 0x63, 0x60, 0xa8, 0xa9, 0xb3, 0x03, 0xb2, 0x6c, 0x80, 0xac, 0x7a, - 0x09, 0x90, 0x44, 0x23, 0x88, 0x38, 0x0c, 0x27, 0xc0, 0x5c, 0x90, 0x04, 0x58, 0x09, 0x44, 0x31, - 0x48, 0x1b, 0x7e, 0x93, 0xc1, 0x04, 0xd8, 0x05, 0xf2, 0xff, 0x7f, 0x30, 0x30, 0xf0, 0xff, 0xff, - 0xc0, 0xc0, 0xc0, 0xfe, 0xff, 0x01, 0x03, 0x03, 0xf3, 0xff, 0x03, 0x0c, 0x0c, 0x8c, 0xff, 0x1b, - 0x80, 0x0e, 0xfc, 0x0f, 0x72, 0x65, 0x1d, 0x88, 0xb0, 0x01, 0x11, 0x12, 0x0c, 0x48, 0x00, 0x00, - 0xd0, 0xf4, 0xce, 0x34, 0xc8, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Erase_40px = { 40, 40, NBGL_BPP_1, true, C_Erase_40px_bitmap }; - -uint8_t const C_Info_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x21, 0x31, 0x00, 0x00, 0x2f, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xfb, 0xff, 0x7f, 0x14, 0xd0, 0x0b, 0x30, 0xf0, 0xff, 0x67, 0x80, 0x01, - 0x7e, 0x2a, 0x89, 0x71, 0x60, 0x5a, 0xd3, 0x80, 0x45, 0xec, 0x57, 0xcf, 0x68, 0xf0, 0x93, 0x05, - 0x00, 0xd9, 0x9e, 0xc9, 0x19, 0x20, 0x03, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Info_40px = { 40, 40, NBGL_BPP_4, true, C_Info_40px_bitmap }; - -uint8_t const C_Maj_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x01, 0x51, 0x00, 0x00, 0x4f, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x63, 0x60, 0x20, 0x09, 0x58, 0x80, 0x88, 0x0a, 0x10, 0xf1, 0x03, 0x88, - 0x19, 0x41, 0x04, 0x33, 0x88, 0x60, 0x07, 0x11, 0xfc, 0xff, 0xff, 0x33, 0x30, 0xc8, 0xff, 0xff, - 0xdf, 0xc0, 0x60, 0x0f, 0x22, 0xea, 0x41, 0xc4, 0x7f, 0x38, 0x51, 0x0f, 0x97, 0x00, 0x2b, 0x01, - 0x2b, 0x66, 0x87, 0x1b, 0x00, 0x36, 0x0a, 0x6c, 0x28, 0xc4, 0x78, 0x0b, 0xd2, 0xdc, 0xc5, 0x00, - 0x00, 0x96, 0xe8, 0xea, 0xc6, 0xc8, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Maj_40px = { 40, 40, NBGL_BPP_1, true, C_Maj_40px_bitmap }; - -uint8_t const C_Maj_Lock_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x01, 0x4d, 0x00, 0x00, 0x4b, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x63, 0x60, 0x20, 0x09, 0x3c, 0x00, 0x62, 0x46, 0x10, 0xc1, 0x0c, 0x22, - 0xd8, 0x41, 0x04, 0x3f, 0x88, 0x90, 0x07, 0x11, 0xf6, 0xff, 0x7f, 0x3c, 0x60, 0xa8, 0x07, 0x11, - 0xff, 0x81, 0x04, 0x23, 0x88, 0x60, 0x86, 0x13, 0x60, 0x2e, 0x58, 0x02, 0xa2, 0x04, 0xac, 0x58, - 0x1e, 0x6e, 0x00, 0x3b, 0xdc, 0x50, 0xb0, 0xf1, 0x60, 0x8b, 0x48, 0x01, 0x00, 0xac, 0x36, 0x99, - 0x6b, 0xc8, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Maj_Lock_40px = { 40, 40, NBGL_BPP_1, true, C_Maj_Lock_40px_bitmap }; - -uint8_t const C_Mini_Push_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x21, 0xce, 0x00, 0x00, 0xcc, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x6d, 0x93, 0xcd, 0x0d, 0xc2, 0x30, 0x0c, 0x46, 0x23, 0x21, 0xa4, 0x4e, - 0x83, 0xba, 0x01, 0x2b, 0x30, 0x52, 0x37, 0x60, 0x04, 0x46, 0x62, 0x07, 0x06, 0xb0, 0x0f, 0x5c, - 0x40, 0x42, 0x36, 0x49, 0x9c, 0x2f, 0xbf, 0xf6, 0xa5, 0xc9, 0xd3, 0xb3, 0x13, 0x39, 0xae, 0xaa, - 0x85, 0x10, 0xb1, 0x0e, 0x11, 0x49, 0x0a, 0x1e, 0x10, 0x77, 0x9f, 0x82, 0xb0, 0x6a, 0x90, 0x5a, - 0x06, 0x96, 0xc2, 0x3a, 0xa7, 0x08, 0xf5, 0xa7, 0xd1, 0xa2, 0x61, 0x47, 0xe3, 0xb5, 0x68, 0xd1, - 0x6c, 0x2f, 0x3a, 0x05, 0x2f, 0xa9, 0x19, 0xf0, 0xcc, 0xa4, 0x95, 0xfb, 0x3d, 0x6b, 0xc1, 0xca, - 0xf6, 0x53, 0x63, 0x65, 0xf5, 0x0e, 0xe1, 0x8a, 0x43, 0xc0, 0xf6, 0x10, 0x20, 0x32, 0x41, 0xdb, - 0x0e, 0x88, 0x44, 0xd0, 0xee, 0x1f, 0x88, 0x85, 0x45, 0x4d, 0x15, 0x62, 0x61, 0x51, 0x53, 0x85, - 0x68, 0x2c, 0x6b, 0x55, 0x34, 0x76, 0x4b, 0x5a, 0x12, 0xcf, 0x99, 0xe5, 0xbb, 0xbc, 0x36, 0xab, - 0x7e, 0x5c, 0xda, 0xfd, 0xe4, 0x61, 0xec, 0xcb, 0xc6, 0xd6, 0x1e, 0xb8, 0xcc, 0xeb, 0x95, 0xdb, - 0x53, 0xaf, 0xf7, 0xde, 0x1b, 0x79, 0x6f, 0xe9, 0xbe, 0xf9, 0x28, 0x96, 0xc9, 0xea, 0x47, 0xb1, - 0x26, 0x39, 0xb3, 0xe6, 0xce, 0xa4, 0x37, 0xbb, 0xee, 0x8c, 0x4f, 0xff, 0xc2, 0x1f, 0x64, 0x87, - 0x98, 0x9d, 0x20, 0x03, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Mini_Push_40px = { 40, 40, NBGL_BPP_4, true, C_Mini_Push_40px_bitmap }; - -uint8_t const C_Next_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x21, 0x86, 0x00, 0x00, 0x84, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xed, 0xd0, 0x31, 0x0e, 0x80, 0x30, 0x08, 0x40, 0x51, 0x5c, 0x1a, 0x06, - 0x07, 0x8f, 0xe8, 0x0d, 0xbc, 0x02, 0x37, 0xf0, 0x48, 0x7a, 0xaa, 0xa6, 0x89, 0x43, 0x2d, 0x50, - 0x95, 0x4a, 0xa2, 0xab, 0x83, 0x8c, 0x3f, 0x2f, 0x0d, 0x25, 0xe7, 0x87, 0x21, 0x74, 0x29, 0x01, - 0xcc, 0x8e, 0x01, 0xa0, 0x67, 0x0e, 0x12, 0x0c, 0xdd, 0x0d, 0x26, 0x08, 0x84, 0x63, 0x0b, 0x09, - 0x26, 0xc2, 0xd8, 0xc0, 0xc2, 0x78, 0x97, 0x06, 0x16, 0xc6, 0xcd, 0x42, 0x66, 0xb2, 0xb3, 0x81, - 0xcc, 0xa4, 0x5d, 0x50, 0x98, 0xfe, 0xed, 0x84, 0xc2, 0xb4, 0x1d, 0x50, 0x59, 0xbd, 0x41, 0x85, - 0xab, 0xb0, 0xda, 0x22, 0xf4, 0xe2, 0x82, 0xbd, 0xd5, 0xa8, 0x0f, 0x2e, 0xb6, 0x6d, 0x2f, 0x37, - 0xfd, 0xdb, 0xc7, 0x9a, 0x99, 0x1d, 0xa6, 0xf9, 0xc2, 0x38, 0x20, 0x03, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Next_40px = { 40, 40, NBGL_BPP_4, true, C_Next_40px_bitmap }; - -uint8_t const C_Plus_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x21, 0x36, 0x00, 0x00, 0x34, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xfb, 0xff, 0x9f, 0x46, 0xa0, 0x81, 0x63, 0x54, 0x0c, 0x45, 0xac, 0x03, - 0x02, 0x1c, 0x58, 0xa0, 0x0c, 0x90, 0x18, 0x03, 0x1a, 0xc0, 0x25, 0x86, 0x4d, 0xef, 0x68, 0x98, - 0xe2, 0x15, 0xa3, 0x12, 0x00, 0x00, 0x63, 0x2f, 0x8b, 0x12, 0x20, 0x03, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Plus_40px = { 40, 40, NBGL_BPP_4, true, C_Plus_40px_bitmap }; - -uint8_t const C_QRCode_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x21, 0x99, 0x00, 0x00, 0x97, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xfb, 0xff, 0x9f, 0xda, 0xe0, 0x11, 0x03, 0x08, 0x30, 0xbd, 0xff, 0x00, - 0xa2, 0xfe, 0x7f, 0x60, 0x00, 0x89, 0x29, 0x80, 0xc5, 0x18, 0xf4, 0x91, 0xc5, 0x20, 0x42, 0x0c, - 0xfc, 0x28, 0x62, 0xfc, 0x30, 0x12, 0xc2, 0xc2, 0x2d, 0xf6, 0xa7, 0xa3, 0x07, 0x43, 0xec, 0x07, - 0x03, 0x07, 0x84, 0xff, 0x01, 0x61, 0x1e, 0xb1, 0x62, 0x10, 0xf3, 0xc0, 0x3c, 0x90, 0x73, 0x90, - 0xec, 0x25, 0x28, 0x86, 0xf0, 0x07, 0x3f, 0xcc, 0x39, 0x48, 0xfe, 0x85, 0x8b, 0x21, 0x85, 0x0b, - 0x3f, 0x92, 0xb3, 0x49, 0x0a, 0xd3, 0x7f, 0x10, 0x83, 0xf5, 0x90, 0xed, 0xf8, 0x04, 0xa1, 0x99, - 0x30, 0xc2, 0x14, 0x9b, 0x9b, 0xd1, 0xc2, 0x19, 0x55, 0x0c, 0x1e, 0x06, 0x27, 0x3a, 0xce, 0xa3, - 0x86, 0x15, 0x90, 0xd7, 0xc0, 0xd0, 0x4f, 0xaa, 0x18, 0x36, 0xf3, 0x88, 0x74, 0x0b, 0x16, 0x7f, - 0x60, 0xf3, 0x2f, 0xb6, 0x70, 0xa1, 0x2e, 0x00, 0x00, 0x5b, 0xb2, 0x1e, 0xfb, 0x20, 0x03, 0x00, - 0x00, -}; -const nbgl_icon_details_t C_QRCode_40px = { 40, 40, NBGL_BPP_4, true, C_QRCode_40px_bitmap }; - -uint8_t const C_Settings_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x21, 0x93, 0x01, 0x00, 0x91, 0x01, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x75, 0x52, 0xb1, 0x52, 0xc2, 0x40, 0x10, 0x7d, 0xc9, 0x88, 0x41, 0x98, - 0x91, 0x8c, 0x56, 0x8e, 0xce, 0x10, 0x87, 0x5e, 0x46, 0x3e, 0x40, 0xec, 0xb0, 0x93, 0x8e, 0x4e, - 0xfd, 0x03, 0x53, 0x40, 0x0d, 0x85, 0x95, 0x16, 0x62, 0x9d, 0x42, 0x4a, 0x3b, 0xb0, 0x93, 0x8a, - 0xf1, 0x0b, 0xfc, 0x04, 0x1c, 0x1c, 0xeb, 0x40, 0x02, 0xa2, 0x20, 0x39, 0x77, 0x2f, 0x38, 0x17, - 0x18, 0xd8, 0x62, 0x6f, 0xef, 0xe5, 0xf2, 0xee, 0xed, 0xbb, 0x15, 0x62, 0x7d, 0x8c, 0x4d, 0xad, - 0xba, 0x8c, 0xd5, 0x81, 0xad, 0x25, 0x28, 0x80, 0x61, 0x6b, 0xdd, 0x45, 0xac, 0x87, 0xac, 0x8f, - 0xac, 0xda, 0x4f, 0x76, 0x0b, 0x4e, 0x51, 0x77, 0x03, 0x33, 0xd6, 0xae, 0x1c, 0x76, 0x42, 0xac, - 0x01, 0x8a, 0x84, 0x10, 0xad, 0xf9, 0x4a, 0x31, 0xe5, 0x12, 0xf7, 0x74, 0xb5, 0x2c, 0x9a, 0x8c, - 0x0d, 0x30, 0x6b, 0x97, 0x73, 0x5c, 0xe5, 0x4a, 0x8e, 0x8b, 0x34, 0x57, 0x1e, 0x5c, 0xc5, 0x3d, - 0x43, 0x9e, 0x97, 0x11, 0x3a, 0x0a, 0x9b, 0xe2, 0x5c, 0x76, 0x80, 0x47, 0x85, 0xfd, 0xa0, 0x1a, - 0x59, 0x9e, 0xee, 0x5c, 0x75, 0x60, 0x8a, 0x4b, 0xca, 0x57, 0xc0, 0x26, 0x81, 0xc3, 0x90, 0x68, - 0xc4, 0xfa, 0x7b, 0x2c, 0xe3, 0x48, 0x08, 0x1f, 0x17, 0x7c, 0x93, 0x45, 0x57, 0x05, 0x16, 0x0a, - 0x37, 0xd0, 0x59, 0x84, 0x4e, 0xa7, 0x1f, 0x60, 0x08, 0xf1, 0x85, 0x03, 0x21, 0x9e, 0x71, 0x2d, - 0x44, 0x8d, 0xec, 0x19, 0x43, 0x23, 0x86, 0x77, 0xa6, 0xf9, 0x45, 0x8a, 0x9a, 0xb7, 0x50, 0x1d, - 0xe0, 0x84, 0x08, 0x5a, 0x1b, 0xcc, 0x7c, 0x9a, 0x90, 0x0e, 0xa5, 0xfb, 0x06, 0xef, 0x6a, 0x71, - 0xce, 0x76, 0x98, 0x53, 0x73, 0x2c, 0xfa, 0x25, 0x35, 0x60, 0x05, 0xa2, 0x11, 0xfe, 0x9b, 0xa4, - 0xf4, 0x81, 0xf4, 0x18, 0x3a, 0xb9, 0xd3, 0xc7, 0x1b, 0x8b, 0xdf, 0xa6, 0x64, 0x52, 0x5b, 0x75, - 0xc4, 0x59, 0xcb, 0xbe, 0x10, 0xaf, 0xac, 0xc5, 0xc6, 0x9e, 0x60, 0xb9, 0xd4, 0x87, 0x85, 0xb3, - 0x32, 0xcb, 0xf5, 0xa1, 0xf3, 0x4b, 0x7d, 0xb2, 0x65, 0xff, 0xbd, 0x79, 0xb2, 0xf9, 0xd0, 0xb2, - 0x80, 0x3d, 0x50, 0x66, 0x86, 0x5e, 0x05, 0x2f, 0xb7, 0x11, 0x33, 0x57, 0x79, 0x3a, 0x5c, 0xf4, - 0x5e, 0xf2, 0xf9, 0xe8, 0x46, 0x67, 0x24, 0x1b, 0xbe, 0x65, 0xd0, 0xae, 0x64, 0xb8, 0xca, 0x14, - 0x9c, 0x6e, 0xf8, 0x96, 0x13, 0xf9, 0xd4, 0x44, 0xf3, 0x2d, 0x8b, 0x8e, 0x9a, 0x8d, 0xa4, 0x9a, - 0x11, 0xc9, 0xbb, 0x53, 0x72, 0x8a, 0x9a, 0x1b, 0x58, 0xb1, 0x76, 0xf9, 0xb8, 0xa9, 0xb8, 0x3d, - 0xe4, 0x3d, 0xe9, 0x50, 0x24, 0x66, 0xa6, 0x61, 0x47, 0x67, 0x64, 0xdd, 0xec, 0xae, 0x9c, 0xf1, - 0x68, 0xfc, 0x01, 0x47, 0x1a, 0xf5, 0x7f, 0x20, 0x03, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Settings_40px = { 40, 40, NBGL_BPP_4, true, C_Settings_40px_bitmap }; - -uint8_t const C_Space_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x01, 0x24, 0x00, 0x00, 0x22, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x63, 0x60, 0xe0, 0xff, 0xc0, 0xc0, 0x80, 0x44, 0x30, 0x14, 0x0c, 0x15, - 0x02, 0xc5, 0xe1, 0x00, 0xfa, 0x92, 0x85, 0x5f, 0xc8, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Space_40px = { 40, 40, NBGL_BPP_1, true, C_Space_40px_bitmap }; - -uint8_t const C_Warning_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x21, 0xe7, 0x00, 0x00, 0xe5, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x6d, 0xd3, 0xb1, 0x0d, 0xc2, 0x40, 0x0c, 0x85, 0xe1, 0x47, 0x84, 0x22, - 0x3a, 0x28, 0x11, 0xd5, 0xd5, 0x88, 0x82, 0x11, 0x32, 0x00, 0x62, 0x86, 0x4c, 0x90, 0x15, 0x08, - 0x13, 0x30, 0x03, 0x2c, 0xc0, 0x0e, 0x88, 0x9e, 0x25, 0x10, 0x6d, 0x52, 0x50, 0x84, 0x10, 0x9d, - 0xb9, 0x73, 0x42, 0x88, 0x7d, 0xb8, 0xfc, 0xaa, 0x5f, 0x67, 0x1f, 0x91, 0x1c, 0x4b, 0xc1, 0x34, - 0x26, 0x0b, 0x28, 0xc1, 0x44, 0x5b, 0x8a, 0xc0, 0xf6, 0xc0, 0x5a, 0xd9, 0x11, 0xd8, 0xe6, 0xd2, - 0xae, 0xc0, 0x86, 0xa4, 0xdd, 0x81, 0x05, 0x49, 0xab, 0x80, 0x39, 0x49, 0xab, 0x66, 0x88, 0x49, - 0x5a, 0x63, 0x30, 0xbe, 0x49, 0x73, 0xad, 0x11, 0xd3, 0xc0, 0x52, 0x8c, 0x0e, 0x24, 0xcd, 0xb5, - 0x76, 0xd4, 0x9b, 0x6f, 0x25, 0x69, 0xdc, 0x2a, 0xad, 0x6d, 0x15, 0xd6, 0xb5, 0x0e, 0xed, 0xc5, - 0xad, 0x25, 0xfc, 0x4c, 0x4b, 0xb0, 0x3d, 0xb9, 0x35, 0xb0, 0x42, 0xdb, 0xdb, 0x20, 0x2e, 0x94, - 0xd1, 0x43, 0x3e, 0x77, 0xdb, 0xe2, 0x70, 0xa9, 0x8d, 0x2e, 0xc0, 0x4a, 0x1b, 0x9d, 0x80, 0x4c, - 0x1b, 0xe5, 0x3f, 0xec, 0xcd, 0xa6, 0x88, 0xce, 0xca, 0xc8, 0x26, 0x5f, 0x1c, 0xbc, 0x7d, 0x6d, - 0xb8, 0x5d, 0xee, 0xa8, 0xe6, 0x76, 0xb5, 0xcb, 0xae, 0x5d, 0xee, 0xbc, 0x6d, 0x57, 0xb7, 0xc1, - 0xed, 0xca, 0xb8, 0x5d, 0x9b, 0x6f, 0x37, 0xda, 0xec, 0x9f, 0x9b, 0xf4, 0xed, 0x81, 0xb9, 0xcc, - 0x5d, 0x78, 0xf8, 0xfe, 0x2f, 0x7c, 0x00, 0x13, 0xd8, 0xb8, 0x06, 0x20, 0x03, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Warning_40px = { 40, 40, NBGL_BPP_4, true, C_Warning_40px_bitmap }; - -uint8_t const C_radio_active_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x22, 0x1f, 0x01, 0x00, 0xff, 0xff, 0xff, 0xfe, 0x9c, 0x73, 0x10, 0x10, - 0x91, 0x47, 0xc0, 0xdb, 0x0a, 0x02, 0x70, 0x10, 0x02, 0x0a, 0xd7, 0x0e, 0x03, 0x70, 0x50, 0x02, - 0x0e, 0xd4, 0x0a, 0x01, 0x70, 0x70, 0x01, 0x0b, 0xd2, 0x0b, 0x40, 0x91, 0x7b, 0xe0, 0xc1, 0x8d, - 0xb6, 0x50, 0x0a, 0xd0, 0x0e, 0x01, 0x30, 0x05, 0xc8, 0x0e, 0x06, 0x30, 0x01, 0x0e, 0xcf, 0x02, - 0x30, 0x09, 0xcb, 0x08, 0x30, 0x03, 0xce, 0x0a, 0x30, 0x08, 0xcd, 0x09, 0x30, 0x0a, 0xcd, 0x02, - 0x20, 0x06, 0xc4, 0x08, 0x04, 0x10, 0x03, 0x0a, 0xc4, 0x05, 0x20, 0x02, 0xcc, 0x0c, 0x30, 0x0e, - 0xc2, 0x0e, 0x02, 0x50, 0x02, 0x0e, 0xc3, 0x01, 0x20, 0x0c, 0xcb, 0x07, 0x20, 0x06, 0xc3, 0x02, - 0x70, 0x02, 0xc3, 0x07, 0x20, 0x07, 0xcb, 0x04, 0x20, 0x0b, 0xc2, 0x0a, 0x70, 0x10, 0x08, 0xc2, - 0x0b, 0x20, 0x03, 0xcb, 0x01, 0x20, 0x0d, 0xc2, 0x03, 0x70, 0x10, 0x04, 0xc2, 0x0e, 0x20, 0x01, - 0xcb, 0x30, 0xc3, 0x70, 0x30, 0xc3, 0x30, 0xcb, 0x30, 0xc3, 0x70, 0x30, 0xc3, 0x30, 0xcb, 0x01, - 0x20, 0x0e, 0xc2, 0x04, 0x70, 0x10, 0x03, 0xc2, 0x0d, 0x20, 0x01, 0xcb, 0x03, 0x20, 0x0b, 0xc2, - 0x08, 0x70, 0x10, 0x0a, 0xc2, 0x0b, 0x20, 0x04, 0xcb, 0x07, 0x20, 0x07, 0xc3, 0x02, 0x70, 0x02, - 0xc3, 0x06, 0x20, 0x07, 0xcb, 0x0c, 0x20, 0x01, 0xc3, 0x0e, 0x02, 0x50, 0x02, 0x0e, 0xc2, 0x0e, - 0x30, 0x0c, 0xcc, 0x02, 0x20, 0x05, 0xc4, 0x0a, 0x03, 0x10, 0x04, 0x08, 0xc4, 0x06, 0x20, 0x02, - 0xcd, 0x0a, 0x30, 0x09, 0xcd, 0x08, 0x30, 0x0a, 0xce, 0x03, 0x30, 0x08, 0xcb, 0x09, 0x30, 0x02, - 0xcf, 0x0e, 0x01, 0x30, 0x06, 0x0e, 0xc8, 0x05, 0x30, 0x01, 0x0e, 0xd0, 0x0a, 0x50, 0x86, 0xbd, - 0xc1, 0x9e, 0xb7, 0x10, 0x40, 0x0b, 0xd2, 0x0b, 0x01, 0x70, 0x70, 0x01, 0x0a, 0xd4, 0x0e, 0x02, - 0x70, 0x50, 0x03, 0x0e, 0xd7, 0x0a, 0x02, 0x70, 0x10, 0x02, 0x0a, 0xdb, 0x9c, 0x74, 0x10, 0x10, - 0x91, 0x37, 0xc0, 0xff, 0xff, 0xff, 0xfe, -}; -const nbgl_icon_details_t C_radio_active_40px = { 40, 40, NBGL_BPP_4, true, C_radio_active_40px_bitmap }; - -uint8_t const C_radio_inactive_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x21, 0xc5, 0x00, 0x00, 0xc3, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xc5, 0x52, 0xbb, 0x0e, 0xc2, 0x30, 0x10, 0xfb, 0xff, 0x4f, 0x70, 0xc2, - 0x63, 0xce, 0x00, 0x9d, 0x2b, 0x21, 0x31, 0x23, 0x24, 0x98, 0x99, 0x32, 0x17, 0x21, 0x65, 0xa6, - 0xb4, 0x84, 0x6b, 0x93, 0xeb, 0x5d, 0x51, 0x10, 0x1b, 0x78, 0xe9, 0xc9, 0xaa, 0x6b, 0x9f, 0xaf, - 0x31, 0xfe, 0x15, 0xcf, 0xa3, 0x33, 0xbb, 0x30, 0xa7, 0x1c, 0x08, 0x66, 0x46, 0xd6, 0x18, 0x61, - 0x14, 0x75, 0x45, 0xc6, 0x56, 0x94, 0xf4, 0xc6, 0x29, 0xc6, 0x1b, 0x91, 0x9e, 0xb9, 0x16, 0xd8, - 0x0f, 0xcf, 0x0e, 0xa8, 0x98, 0x73, 0x58, 0xa6, 0xe1, 0x02, 0x2b, 0xd2, 0x2c, 0xe9, 0x81, 0xc0, - 0xd2, 0x85, 0xf8, 0x67, 0x71, 0x83, 0xb5, 0x7c, 0x79, 0x95, 0x86, 0x03, 0xce, 0xcc, 0x75, 0x2c, - 0xa9, 0x11, 0x24, 0x95, 0x65, 0x5b, 0x49, 0xcf, 0xab, 0x40, 0x73, 0xf8, 0xcc, 0x95, 0xb4, 0x25, - 0x8f, 0x52, 0x96, 0x46, 0x36, 0xbf, 0x73, 0xe6, 0x76, 0xda, 0x9c, 0x24, 0xd5, 0xb4, 0xb9, 0x7f, - 0x9f, 0xc8, 0x64, 0xea, 0xca, 0xa8, 0x4e, 0x47, 0x97, 0x87, 0xea, 0x94, 0x0a, 0xc4, 0xd0, 0xbd, - 0x83, 0xa4, 0x92, 0x1b, 0x6d, 0xd4, 0xe1, 0x5c, 0xa2, 0xac, 0xbe, 0x6f, 0x9f, 0x6e, 0xee, 0xbf, - 0xfd, 0x1b, 0xbf, 0xc7, 0x0b, 0x8b, 0x9c, 0x75, 0x0e, 0x20, 0x03, 0x00, 0x00, -}; -const nbgl_icon_details_t C_radio_inactive_40px = { 40, 40, NBGL_BPP_4, true, C_radio_inactive_40px_bitmap }; - -uint8_t const C_app_boilerplate_40px_bitmap[] = { - 0x28, 0x00, 0x28, 0x00, 0x21, 0xe4, 0x00, 0x00, 0xe2, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x9d, 0x92, 0xbd, 0x0d, 0x83, 0x30, 0x10, 0x85, 0xcf, 0x72, 0x81, 0xe4, - 0x26, 0x66, 0x00, 0x94, 0x15, 0x88, 0x32, 0x00, 0x33, 0x21, 0x06, 0xc8, 0x2c, 0x51, 0x3a, 0x1a, - 0x86, 0xa1, 0x40, 0x4a, 0x93, 0x31, 0x2c, 0x59, 0x3a, 0x5d, 0x62, 0x88, 0xed, 0xb3, 0x4d, 0x41, - 0x72, 0x05, 0x32, 0x8f, 0xc7, 0x7d, 0xf7, 0x63, 0xa2, 0x5f, 0x02, 0x5f, 0xa5, 0x66, 0x9a, 0x52, - 0xb3, 0x72, 0xc7, 0x07, 0xd3, 0x8e, 0xa6, 0xca, 0x7f, 0x01, 0x3c, 0xc5, 0x4e, 0xc1, 0x07, 0xdd, - 0x76, 0x1a, 0xeb, 0x5b, 0xd4, 0x56, 0x0a, 0x0e, 0xba, 0x8a, 0xf9, 0xc0, 0x51, 0x96, 0x56, 0xe8, - 0x86, 0x6b, 0xca, 0xde, 0x35, 0x80, 0x08, 0xd5, 0x1b, 0xf7, 0xd6, 0x7e, 0x3e, 0x40, 0x45, 0xdc, - 0x07, 0xda, 0x3d, 0x3a, 0x5e, 0xcb, 0x16, 0x22, 0x8e, 0xa0, 0xf7, 0x5a, 0x28, 0x7d, 0x69, 0xbd, - 0xe4, 0x5b, 0x5c, 0x71, 0xdf, 0xa8, 0x0a, 0x53, 0x20, 0x70, 0xc9, 0x13, 0x6c, 0x2f, 0x20, 0x4f, - 0x47, 0x38, 0x47, 0xed, 0x1c, 0x4a, 0x19, 0x03, 0x84, 0x8d, 0x1b, 0x87, 0x0c, 0x92, 0xf4, 0xa1, - 0x28, 0xed, 0x37, 0xa1, 0x30, 0x1f, 0x9c, 0x12, 0x9f, 0x7c, 0x5e, 0x74, 0x3e, 0x2b, 0x45, 0xf8, - 0xa8, 0x41, 0x74, 0x7c, 0xa6, 0x2e, 0x93, 0xe9, 0x23, 0xc5, 0x08, 0xb1, 0x9d, 0xf1, 0x1a, 0x96, - 0x1a, 0x77, 0x49, 0x73, 0xdc, 0xa5, 0xdc, 0xb9, 0x07, 0xea, 0xd8, 0x1d, 0x92, 0xc7, 0xee, 0x24, - 0xd2, 0x3f, 0xf1, 0x06, 0x29, 0x24, 0x97, 0x3f, 0x20, 0x03, 0x00, 0x00, -}; -const nbgl_icon_details_t C_app_boilerplate_40px = { 40, 40, NBGL_BPP_4, true, C_app_boilerplate_40px_bitmap }; - diff --git a/ledger_secure_sdk_sys/src/c/glyphs_flex/glyphs.h b/ledger_secure_sdk_sys/src/c/glyphs_flex/glyphs.h deleted file mode 100644 index 7fe841f1..00000000 --- a/ledger_secure_sdk_sys/src/c/glyphs_flex/glyphs.h +++ /dev/null @@ -1,145 +0,0 @@ -/* Automatically generated by icon2glyph.py */ - -#pragma once - -#include "app_config.h" -#include "nbgl_types.h" - -extern uint8_t const C_app_boilerplate_16px_bitmap[29]; -extern const nbgl_icon_details_t C_app_boilerplate_16px; - -extern uint8_t const C_app_boilerplate_64px_bitmap[187]; -extern const nbgl_icon_details_t C_app_boilerplate_64px; - -extern uint8_t const C_pin_24_bitmap[49]; -extern const nbgl_icon_details_t C_pin_24; - -extern uint8_t const C_quarter_circle_bottom_left_32px_1bpp_bitmap[128]; -extern const nbgl_icon_details_t C_quarter_circle_bottom_left_32px_1bpp; - -extern uint8_t const C_quarter_circle_bottom_left_40px_1bpp_bitmap[200]; -extern const nbgl_icon_details_t C_quarter_circle_bottom_left_40px_1bpp; - -extern uint8_t const C_quarter_circle_bottom_left_44px_1bpp_bitmap[242]; -extern const nbgl_icon_details_t C_quarter_circle_bottom_left_44px_1bpp; - -extern uint8_t const C_quarter_circle_top_left_32px_1bpp_bitmap[128]; -extern const nbgl_icon_details_t C_quarter_circle_top_left_32px_1bpp; - -extern uint8_t const C_quarter_circle_top_left_40px_1bpp_bitmap[200]; -extern const nbgl_icon_details_t C_quarter_circle_top_left_40px_1bpp; - -extern uint8_t const C_quarter_circle_top_left_44px_1bpp_bitmap[242]; -extern const nbgl_icon_details_t C_quarter_circle_top_left_44px_1bpp; - -extern uint8_t const C_quarter_disc_bottom_left_32px_1bpp_bitmap[128]; -extern const nbgl_icon_details_t C_quarter_disc_bottom_left_32px_1bpp; - -extern uint8_t const C_quarter_disc_bottom_left_40px_1bpp_bitmap[200]; -extern const nbgl_icon_details_t C_quarter_disc_bottom_left_40px_1bpp; - -extern uint8_t const C_quarter_disc_bottom_left_44px_1bpp_bitmap[242]; -extern const nbgl_icon_details_t C_quarter_disc_bottom_left_44px_1bpp; - -extern uint8_t const C_quarter_disc_top_left_32px_1bpp_bitmap[128]; -extern const nbgl_icon_details_t C_quarter_disc_top_left_32px_1bpp; - -extern uint8_t const C_quarter_disc_top_left_40px_1bpp_bitmap[200]; -extern const nbgl_icon_details_t C_quarter_disc_top_left_40px_1bpp; - -extern uint8_t const C_quarter_disc_top_left_44px_1bpp_bitmap[242]; -extern const nbgl_icon_details_t C_quarter_disc_top_left_44px_1bpp; - -extern uint8_t const C_round_24px_bitmap[47]; -extern const nbgl_icon_details_t C_round_24px; - -extern uint8_t const C_switch_60_40_bitmap[300]; -extern const nbgl_icon_details_t C_switch_60_40; - -extern uint8_t const C_Check_Circle_64px_bitmap[571]; -extern const nbgl_icon_details_t C_Check_Circle_64px; - -extern uint8_t const C_Denied_Circle_64px_bitmap[568]; -extern const nbgl_icon_details_t C_Denied_Circle_64px; - -extern uint8_t const C_Important_Circle_64px_bitmap[514]; -extern const nbgl_icon_details_t C_Important_Circle_64px; - -extern uint8_t const C_Review_64px_bitmap[219]; -extern const nbgl_icon_details_t C_Review_64px; - -extern uint8_t const C_SecurityShield_64px_bitmap[610]; -extern const nbgl_icon_details_t C_SecurityShield_64px; - -extern uint8_t const C_Warning_64px_bitmap[359]; -extern const nbgl_icon_details_t C_Warning_64px; - -extern uint8_t const C_left_half_64px_bitmap[192]; -extern const nbgl_icon_details_t C_left_half_64px; - -extern uint8_t const C_Back_40px_bitmap[148]; -extern const nbgl_icon_details_t C_Back_40px; - -extern uint8_t const C_Check_40px_bitmap[92]; -extern const nbgl_icon_details_t C_Check_40px; - -extern uint8_t const C_Check_Circle_40px_bitmap[339]; -extern const nbgl_icon_details_t C_Check_Circle_40px; - -extern uint8_t const C_Chevron_40px_bitmap[100]; -extern const nbgl_icon_details_t C_Chevron_40px; - -extern uint8_t const C_Chevron_Back_40px_bitmap[126]; -extern const nbgl_icon_details_t C_Chevron_Back_40px; - -extern uint8_t const C_Chevron_Next_40px_bitmap[121]; -extern const nbgl_icon_details_t C_Chevron_Next_40px; - -extern uint8_t const C_Close_40px_bitmap[141]; -extern const nbgl_icon_details_t C_Close_40px; - -extern uint8_t const C_Denied_Circle_40px_bitmap[326]; -extern const nbgl_icon_details_t C_Denied_Circle_40px; - -extern uint8_t const C_Erase_40px_bitmap[120]; -extern const nbgl_icon_details_t C_Erase_40px; - -extern uint8_t const C_Info_40px_bitmap[57]; -extern const nbgl_icon_details_t C_Info_40px; - -extern uint8_t const C_Maj_40px_bitmap[89]; -extern const nbgl_icon_details_t C_Maj_40px; - -extern uint8_t const C_Maj_Lock_40px_bitmap[85]; -extern const nbgl_icon_details_t C_Maj_Lock_40px; - -extern uint8_t const C_Mini_Push_40px_bitmap[214]; -extern const nbgl_icon_details_t C_Mini_Push_40px; - -extern uint8_t const C_Next_40px_bitmap[142]; -extern const nbgl_icon_details_t C_Next_40px; - -extern uint8_t const C_Plus_40px_bitmap[62]; -extern const nbgl_icon_details_t C_Plus_40px; - -extern uint8_t const C_QRCode_40px_bitmap[161]; -extern const nbgl_icon_details_t C_QRCode_40px; - -extern uint8_t const C_Settings_40px_bitmap[411]; -extern const nbgl_icon_details_t C_Settings_40px; - -extern uint8_t const C_Space_40px_bitmap[44]; -extern const nbgl_icon_details_t C_Space_40px; - -extern uint8_t const C_Warning_40px_bitmap[239]; -extern const nbgl_icon_details_t C_Warning_40px; - -extern uint8_t const C_radio_active_40px_bitmap[295]; -extern const nbgl_icon_details_t C_radio_active_40px; - -extern uint8_t const C_radio_inactive_40px_bitmap[205]; -extern const nbgl_icon_details_t C_radio_inactive_40px; - -extern uint8_t const C_app_boilerplate_40px_bitmap[236]; -extern const nbgl_icon_details_t C_app_boilerplate_40px; - diff --git a/ledger_secure_sdk_sys/src/c/glyphs_stax/glyphs.c b/ledger_secure_sdk_sys/src/c/glyphs_stax/glyphs.c deleted file mode 100644 index 2e99cac2..00000000 --- a/ledger_secure_sdk_sys/src/c/glyphs_stax/glyphs.c +++ /dev/null @@ -1,784 +0,0 @@ -/* Automatically generated by icon2glyph.py */ - -#include "glyphs.h" - -uint8_t const C_app_boilerplate_16px_bitmap[] = { - 0x10, 0x00, 0x10, 0x00, 0x02, 0x15, 0x00, 0x00, 0xf0, 0x71, 0xf1, 0xf2, 0x42, 0x83, 0x14, 0x87, - 0x78, 0x69, 0x79, 0x98, 0xa7, 0x93, 0x14, 0x82, 0x42, 0x81, 0xf1, 0xf0, 0xa0, -}; -const nbgl_icon_details_t C_app_boilerplate_16px = { 16, 16, NBGL_BPP_1, true, C_app_boilerplate_16px_bitmap }; - -uint8_t const C_app_boilerplate_64px_bitmap[] = { - 0x40, 0x00, 0x40, 0x00, 0x01, 0xb3, 0x00, 0x00, 0xb1, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x75, 0xd1, 0xbb, 0x0d, 0x03, 0x21, 0x0c, 0x06, 0x60, 0x9f, 0x22, 0x85, - 0x92, 0x11, 0x6e, 0x85, 0x6c, 0x70, 0xa3, 0x1d, 0xa3, 0x79, 0x14, 0xa4, 0x14, 0x69, 0x29, 0x29, - 0x2c, 0x1c, 0x83, 0xff, 0x44, 0x04, 0xe5, 0xdc, 0x7c, 0x12, 0x0f, 0x1b, 0x1b, 0xa2, 0xab, 0xb8, - 0xc3, 0xf0, 0x31, 0x2d, 0x32, 0xcc, 0xb0, 0xc0, 0x3a, 0xf9, 0x30, 0x85, 0x68, 0xb3, 0xbd, 0xd0, - 0x88, 0xa2, 0x9d, 0x0d, 0x4a, 0x74, 0xf2, 0xf0, 0xa6, 0xc3, 0xb4, 0x6b, 0xea, 0xb2, 0x6a, 0xbf, - 0xa7, 0x2f, 0x6d, 0x43, 0xfd, 0x2a, 0xb0, 0xc2, 0x32, 0xb9, 0x9b, 0xfd, 0x09, 0x86, 0xa7, 0xb3, - 0xb0, 0x74, 0x47, 0xd7, 0x2a, 0xab, 0x1b, 0xd5, 0xd3, 0x8d, 0x65, 0x81, 0x15, 0xeb, 0x82, 0x73, - 0xbd, 0xdc, 0x01, 0xa3, 0xdf, 0xf3, 0x8d, 0x84, 0x0d, 0x46, 0xdd, 0xbc, 0x58, 0x96, 0xf7, 0xc9, - 0x8f, 0x4f, 0xf4, 0x91, 0x4f, 0xef, 0x8f, 0xa3, 0xf7, 0x9b, 0x36, 0x7f, 0xb0, 0xe5, 0xe6, 0x69, - 0x3e, 0x0d, 0xf3, 0x12, 0xcc, 0xaf, 0x2e, 0xf3, 0x2d, 0xcb, 0xdc, 0xf9, 0xe2, 0x7f, 0x96, 0x7f, - 0xfc, 0x1f, 0x6f, 0xe5, 0xd1, 0xa9, 0x21, 0x00, 0x02, 0x00, 0x00, -}; -const nbgl_icon_details_t C_app_boilerplate_64px = { 64, 64, NBGL_BPP_1, true, C_app_boilerplate_64px_bitmap }; - -uint8_t const C_pin_24_bitmap[] = { - 0x18, 0x00, 0x18, 0x00, 0x02, 0x29, 0x00, 0x00, 0x96, 0xfc, 0xbe, 0x9f, 0x01, 0x7f, 0x03, 0x5f, - 0x05, 0x3f, 0x07, 0x2f, 0x07, 0x2f, 0x07, 0x1f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, 0x0f, - 0x09, 0x1f, 0x07, 0x2f, 0x07, 0x2f, 0x07, 0x3f, 0x05, 0x5f, 0x03, 0x7f, 0x01, 0x9e, 0xbc, 0xf6, - 0x90, -}; -const nbgl_icon_details_t C_pin_24 = { 24, 24, NBGL_BPP_1, true, C_pin_24_bitmap }; - -uint8_t const C_quarter_circle_bottom_left_32px_1bpp_bitmap[] = { - 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, - 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x06, - 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x0c, - 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x38, 0x00, 0x00, 0x00, 0x30, - 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x01, 0x80, - 0x00, 0x00, 0x03, 0x80, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x0e, 0x00, 0x00, 0x00, 0x1c, 0x00, - 0x00, 0x00, 0x38, 0x00, 0x00, 0x00, 0xe0, 0x00, 0x00, 0x03, 0xc0, 0x00, 0x00, 0x0f, 0x00, 0x00, - 0x00, 0x3e, 0x00, 0x00, 0x03, 0xf0, 0x00, 0x00, 0xff, 0xc0, 0x00, 0x00, 0xfc, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_quarter_circle_bottom_left_32px_1bpp = { 32, 32, NBGL_BPP_1, false, C_quarter_circle_bottom_left_32px_1bpp_bitmap }; - -uint8_t const C_quarter_circle_bottom_left_40px_1bpp_bitmap[] = { - 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, - 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, - 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, - 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, - 0x0c, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x18, - 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, - 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, - 0x00, 0x01, 0x80, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x00, - 0x06, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x30, - 0x00, 0x00, 0x00, 0x00, 0xe0, 0x00, 0x00, 0x00, 0x01, 0xc0, 0x00, 0x00, 0x00, 0x03, 0x80, 0x00, - 0x00, 0x00, 0x0e, 0x00, 0x00, 0x00, 0x00, 0x3c, 0x00, 0x00, 0x00, 0x00, 0xf0, 0x00, 0x00, 0x00, - 0x03, 0xc0, 0x00, 0x00, 0x00, 0x1f, 0x00, 0x00, 0x00, 0x03, 0xfc, 0x00, 0x00, 0x00, 0xff, 0xe0, - 0x00, 0x00, 0x00, 0xfc, 0x00, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_quarter_circle_bottom_left_40px_1bpp = { 40, 40, NBGL_BPP_1, false, C_quarter_circle_bottom_left_40px_1bpp_bitmap }; - -uint8_t const C_quarter_circle_bottom_left_44px_1bpp_bitmap[] = { - 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x30, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, - 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, - 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, - 0x00, 0x01, 0x80, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x01, 0x80, 0x00, 0x00, - 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, - 0x00, 0x00, 0x0e, 0x00, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x1c, 0x00, 0x00, - 0x00, 0x00, 0x01, 0x80, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, - 0x00, 0x00, 0x00, 0xe0, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x01, 0x80, 0x00, - 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, - 0x00, 0x00, 0x00, 0x38, 0x00, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0xe0, 0x00, - 0x00, 0x00, 0x00, 0x3c, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00, 0x00, 0x01, 0xe0, 0x00, - 0x00, 0x00, 0x00, 0x78, 0x00, 0x00, 0x00, 0x00, 0x3e, 0x00, 0x00, 0x00, 0x00, 0x1f, 0x80, 0x00, - 0x00, 0x00, 0x3f, 0xc0, 0x00, 0x00, 0x00, 0xff, 0xe0, 0x00, 0x00, 0x00, 0x0f, 0xc0, 0x00, 0x00, - 0x00, 0x00, -}; -const nbgl_icon_details_t C_quarter_circle_bottom_left_44px_1bpp = { 44, 44, NBGL_BPP_1, false, C_quarter_circle_bottom_left_44px_1bpp_bitmap }; - -uint8_t const C_quarter_circle_top_left_32px_1bpp_bitmap[] = { - 0xc0, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, - 0xc0, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, - 0x60, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, - 0x18, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x1c, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, - 0x06, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x01, 0x80, 0x00, 0x00, - 0x01, 0xc0, 0x00, 0x00, 0x00, 0xe0, 0x00, 0x00, 0x00, 0x70, 0x00, 0x00, 0x00, 0x38, 0x00, 0x00, - 0x00, 0x1c, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x03, 0xc0, 0x00, 0x00, 0x00, 0xf0, 0x00, - 0x00, 0x00, 0x7c, 0x00, 0x00, 0x00, 0x0f, 0xc0, 0x00, 0x00, 0x03, 0xff, 0x00, 0x00, 0x00, 0x3f, -}; -const nbgl_icon_details_t C_quarter_circle_top_left_32px_1bpp = { 32, 32, NBGL_BPP_1, false, C_quarter_circle_top_left_32px_1bpp_bitmap }; - -uint8_t const C_quarter_circle_top_left_40px_1bpp_bitmap[] = { - 0xc0, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0xc0, - 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, - 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, - 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, - 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, - 0x0c, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x06, - 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x01, 0x80, - 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0xe0, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, - 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, - 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x00, 0x03, 0x80, 0x00, 0x00, 0x00, 0x01, 0xc0, 0x00, 0x00, - 0x00, 0x00, 0x70, 0x00, 0x00, 0x00, 0x00, 0x3c, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00, - 0x00, 0x03, 0xc0, 0x00, 0x00, 0x00, 0x00, 0xf8, 0x00, 0x00, 0x00, 0x00, 0x3f, 0xc0, 0x00, 0x00, - 0x00, 0x07, 0xff, 0x00, 0x00, 0x00, 0x00, 0x3f, -}; -const nbgl_icon_details_t C_quarter_circle_top_left_40px_1bpp = { 40, 40, NBGL_BPP_1, false, C_quarter_circle_top_left_40px_1bpp_bitmap }; - -uint8_t const C_quarter_circle_top_left_44px_1bpp_bitmap[] = { - 0xc0, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, - 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, - 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, - 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, - 0x00, 0x00, 0x01, 0x80, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, - 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x60, 0x00, 0x00, 0x00, 0x00, 0x07, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00, 0x03, 0x80, 0x00, 0x00, 0x00, 0x00, 0x18, - 0x00, 0x00, 0x00, 0x00, 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x0e, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x70, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x00, - 0x00, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, - 0x00, 0x01, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x0e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x70, 0x00, 0x00, - 0x00, 0x00, 0x03, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x78, 0x00, - 0x00, 0x00, 0x00, 0x01, 0xe0, 0x00, 0x00, 0x00, 0x00, 0x07, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x1f, - 0x80, 0x00, 0x00, 0x00, 0x00, 0x3f, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x7f, 0xf0, 0x00, 0x00, 0x00, - 0x00, 0x3f, -}; -const nbgl_icon_details_t C_quarter_circle_top_left_44px_1bpp = { 44, 44, NBGL_BPP_1, false, C_quarter_circle_top_left_44px_1bpp_bitmap }; - -uint8_t const C_quarter_disc_bottom_left_32px_1bpp_bitmap[] = { - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xfe, - 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xfc, 0xff, 0xff, 0xff, 0xfc, - 0xff, 0xff, 0xff, 0xf8, 0xff, 0xff, 0xff, 0xf8, 0xff, 0xff, 0xff, 0xf8, 0xff, 0xff, 0xff, 0xf0, - 0xff, 0xff, 0xff, 0xe0, 0xff, 0xff, 0xff, 0xe0, 0xff, 0xff, 0xff, 0xc0, 0xff, 0xff, 0xff, 0x80, - 0xff, 0xff, 0xff, 0x80, 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, 0xfe, 0x00, 0xff, 0xff, 0xfc, 0x00, - 0xff, 0xff, 0xf8, 0x00, 0xff, 0xff, 0xe0, 0x00, 0xff, 0xff, 0xc0, 0x00, 0xff, 0xff, 0x00, 0x00, - 0xff, 0xfe, 0x00, 0x00, 0xff, 0xf0, 0x00, 0x00, 0xff, 0xc0, 0x00, 0x00, 0xfc, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_quarter_disc_bottom_left_32px_1bpp = { 32, 32, NBGL_BPP_1, false, C_quarter_disc_bottom_left_32px_1bpp_bitmap }; - -uint8_t const C_quarter_disc_bottom_left_40px_1bpp_bitmap[] = { - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, - 0xff, 0xfe, 0xff, 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xff, 0xfc, 0xff, 0xff, 0xff, 0xff, - 0xfc, 0xff, 0xff, 0xff, 0xff, 0xfc, 0xff, 0xff, 0xff, 0xff, 0xf8, 0xff, 0xff, 0xff, 0xff, 0xf8, - 0xff, 0xff, 0xff, 0xff, 0xf0, 0xff, 0xff, 0xff, 0xff, 0xf0, 0xff, 0xff, 0xff, 0xff, 0xe0, 0xff, - 0xff, 0xff, 0xff, 0xe0, 0xff, 0xff, 0xff, 0xff, 0xc0, 0xff, 0xff, 0xff, 0xff, 0xc0, 0xff, 0xff, - 0xff, 0xff, 0x80, 0xff, 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, 0xff, - 0xfe, 0x00, 0xff, 0xff, 0xff, 0xfc, 0x00, 0xff, 0xff, 0xff, 0xf8, 0x00, 0xff, 0xff, 0xff, 0xf0, - 0x00, 0xff, 0xff, 0xff, 0xe0, 0x00, 0xff, 0xff, 0xff, 0xc0, 0x00, 0xff, 0xff, 0xff, 0x80, 0x00, - 0xff, 0xff, 0xfe, 0x00, 0x00, 0xff, 0xff, 0xfc, 0x00, 0x00, 0xff, 0xff, 0xf0, 0x00, 0x00, 0xff, - 0xff, 0xc0, 0x00, 0x00, 0xff, 0xff, 0x00, 0x00, 0x00, 0xff, 0xfc, 0x00, 0x00, 0x00, 0xff, 0xe0, - 0x00, 0x00, 0x00, 0xfc, 0x00, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_quarter_disc_bottom_left_40px_1bpp = { 40, 40, NBGL_BPP_1, false, C_quarter_disc_bottom_left_40px_1bpp_bitmap }; - -uint8_t const C_quarter_disc_bottom_left_44px_1bpp_bitmap[] = { - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xef, 0xff, 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xef, 0xff, 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xff, 0xff, 0xef, 0xff, 0xff, 0xff, - 0xff, 0xfc, 0xff, 0xff, 0xff, 0xff, 0xff, 0xcf, 0xff, 0xff, 0xff, 0xff, 0xfc, 0xff, 0xff, 0xff, - 0xff, 0xff, 0x8f, 0xff, 0xff, 0xff, 0xff, 0xf8, 0xff, 0xff, 0xff, 0xff, 0xff, 0x8f, 0xff, 0xff, - 0xff, 0xff, 0xf0, 0xff, 0xff, 0xff, 0xff, 0xff, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xe0, 0xff, 0xff, - 0xff, 0xff, 0xfe, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xc0, 0xff, 0xff, 0xff, 0xff, 0xfc, 0x0f, 0xff, - 0xff, 0xff, 0xff, 0x80, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x0f, 0xff, 0xff, 0xff, 0xff, 0x00, 0xff, - 0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff, 0xfc, 0x00, 0xff, 0xff, 0xff, 0xff, 0x80, 0x0f, - 0xff, 0xff, 0xff, 0xf0, 0x00, 0xff, 0xff, 0xff, 0xfe, 0x00, 0x0f, 0xff, 0xff, 0xff, 0xc0, 0x00, - 0xff, 0xff, 0xff, 0xf8, 0x00, 0x0f, 0xff, 0xff, 0xff, 0x00, 0x00, 0xff, 0xff, 0xff, 0xe0, 0x00, - 0x0f, 0xff, 0xff, 0xfc, 0x00, 0x00, 0xff, 0xff, 0xff, 0x00, 0x00, 0x0f, 0xff, 0xff, 0xe0, 0x00, - 0x00, 0xff, 0xff, 0xf8, 0x00, 0x00, 0x0f, 0xff, 0xfe, 0x00, 0x00, 0x00, 0xff, 0xff, 0x80, 0x00, - 0x00, 0x0f, 0xff, 0xc0, 0x00, 0x00, 0x00, 0xff, 0xe0, 0x00, 0x00, 0x00, 0x0f, 0xc0, 0x00, 0x00, - 0x00, 0x00, -}; -const nbgl_icon_details_t C_quarter_disc_bottom_left_44px_1bpp = { 44, 44, NBGL_BPP_1, false, C_quarter_disc_bottom_left_44px_1bpp_bitmap }; - -uint8_t const C_quarter_disc_top_left_32px_1bpp_bitmap[] = { - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, - 0x7f, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, 0x3f, 0xff, 0xff, 0xff, 0x3f, 0xff, 0xff, 0xff, - 0x1f, 0xff, 0xff, 0xff, 0x1f, 0xff, 0xff, 0xff, 0x1f, 0xff, 0xff, 0xff, 0x0f, 0xff, 0xff, 0xff, - 0x07, 0xff, 0xff, 0xff, 0x07, 0xff, 0xff, 0xff, 0x03, 0xff, 0xff, 0xff, 0x01, 0xff, 0xff, 0xff, - 0x01, 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, 0xff, 0x00, 0x7f, 0xff, 0xff, 0x00, 0x3f, 0xff, 0xff, - 0x00, 0x1f, 0xff, 0xff, 0x00, 0x07, 0xff, 0xff, 0x00, 0x03, 0xff, 0xff, 0x00, 0x00, 0xff, 0xff, - 0x00, 0x00, 0x7f, 0xff, 0x00, 0x00, 0x0f, 0xff, 0x00, 0x00, 0x03, 0xff, 0x00, 0x00, 0x00, 0x3f, -}; -const nbgl_icon_details_t C_quarter_disc_top_left_32px_1bpp = { 32, 32, NBGL_BPP_1, false, C_quarter_disc_top_left_32px_1bpp_bitmap }; - -uint8_t const C_quarter_disc_top_left_40px_1bpp_bitmap[] = { - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x7f, 0xff, - 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, - 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, 0xff, 0x3f, 0xff, 0xff, 0xff, 0xff, 0x3f, 0xff, 0xff, 0xff, - 0xff, 0x3f, 0xff, 0xff, 0xff, 0xff, 0x1f, 0xff, 0xff, 0xff, 0xff, 0x1f, 0xff, 0xff, 0xff, 0xff, - 0x0f, 0xff, 0xff, 0xff, 0xff, 0x0f, 0xff, 0xff, 0xff, 0xff, 0x07, 0xff, 0xff, 0xff, 0xff, 0x07, - 0xff, 0xff, 0xff, 0xff, 0x03, 0xff, 0xff, 0xff, 0xff, 0x03, 0xff, 0xff, 0xff, 0xff, 0x01, 0xff, - 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x7f, 0xff, - 0xff, 0xff, 0x00, 0x3f, 0xff, 0xff, 0xff, 0x00, 0x1f, 0xff, 0xff, 0xff, 0x00, 0x0f, 0xff, 0xff, - 0xff, 0x00, 0x07, 0xff, 0xff, 0xff, 0x00, 0x03, 0xff, 0xff, 0xff, 0x00, 0x01, 0xff, 0xff, 0xff, - 0x00, 0x00, 0x7f, 0xff, 0xff, 0x00, 0x00, 0x3f, 0xff, 0xff, 0x00, 0x00, 0x0f, 0xff, 0xff, 0x00, - 0x00, 0x03, 0xff, 0xff, 0x00, 0x00, 0x00, 0xff, 0xff, 0x00, 0x00, 0x00, 0x3f, 0xff, 0x00, 0x00, - 0x00, 0x07, 0xff, 0x00, 0x00, 0x00, 0x00, 0x3f, -}; -const nbgl_icon_details_t C_quarter_disc_top_left_40px_1bpp = { 40, 40, NBGL_BPP_1, false, C_quarter_disc_top_left_40px_1bpp_bitmap }; - -uint8_t const C_quarter_disc_top_left_44px_1bpp_bitmap[] = { - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, - 0xff, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xf7, 0xff, 0xff, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, - 0xff, 0xf7, 0xff, 0xff, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xf3, 0xff, 0xff, 0xff, - 0xff, 0xff, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xf3, 0xff, 0xff, 0xff, 0xff, 0xff, 0x1f, 0xff, 0xff, - 0xff, 0xff, 0xf1, 0xff, 0xff, 0xff, 0xff, 0xff, 0x1f, 0xff, 0xff, 0xff, 0xff, 0xf0, 0xff, 0xff, - 0xff, 0xff, 0xff, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x7f, 0xff, 0xff, 0xff, 0xff, 0x07, 0xff, - 0xff, 0xff, 0xff, 0xf0, 0x3f, 0xff, 0xff, 0xff, 0xff, 0x03, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x1f, - 0xff, 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x0f, 0xff, 0xff, 0xff, 0xff, 0x00, - 0x7f, 0xff, 0xff, 0xff, 0xf0, 0x03, 0xff, 0xff, 0xff, 0xff, 0x00, 0x1f, 0xff, 0xff, 0xff, 0xf0, - 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x07, 0xff, 0xff, 0xff, 0xf0, 0x00, 0x3f, 0xff, 0xff, 0xff, - 0x00, 0x01, 0xff, 0xff, 0xff, 0xf0, 0x00, 0x0f, 0xff, 0xff, 0xff, 0x00, 0x00, 0x7f, 0xff, 0xff, - 0xf0, 0x00, 0x03, 0xff, 0xff, 0xff, 0x00, 0x00, 0x0f, 0xff, 0xff, 0xf0, 0x00, 0x00, 0x7f, 0xff, - 0xff, 0x00, 0x00, 0x01, 0xff, 0xff, 0xf0, 0x00, 0x00, 0x07, 0xff, 0xff, 0x00, 0x00, 0x00, 0x1f, - 0xff, 0xf0, 0x00, 0x00, 0x00, 0x3f, 0xff, 0x00, 0x00, 0x00, 0x00, 0x7f, 0xf0, 0x00, 0x00, 0x00, - 0x00, 0x3f, -}; -const nbgl_icon_details_t C_quarter_disc_top_left_44px_1bpp = { 44, 44, NBGL_BPP_1, false, C_quarter_disc_top_left_44px_1bpp_bitmap }; - -uint8_t const C_round_24px_bitmap[] = { - 0x18, 0x00, 0x18, 0x00, 0x02, 0x27, 0x00, 0x00, 0xf0, 0xf0, 0xf0, 0xf0, 0xf0, 0x74, 0xf0, 0x38, - 0xec, 0xbe, 0xae, 0x9f, 0x01, 0x8f, 0x01, 0x7f, 0x03, 0x6f, 0x03, 0x6f, 0x03, 0x6f, 0x03, 0x7f, - 0x01, 0x8f, 0x01, 0x9e, 0xae, 0xbc, 0xe8, 0xf0, 0x34, 0xf0, 0xf0, 0xf0, 0xf0, 0xf0, 0x70, -}; -const nbgl_icon_details_t C_round_24px = { 24, 24, NBGL_BPP_1, true, C_round_24px_bitmap }; - -uint8_t const C_switch_60_40_bitmap[] = { - 0x00, 0x00, 0xff, 0x00, 0x00, 0x00, 0x07, 0xff, 0xe0, 0x00, 0x00, 0x1f, 0xff, 0xf8, 0x00, 0x00, - 0x3f, 0xff, 0xfc, 0x00, 0x00, 0xff, 0xff, 0xff, 0x00, 0x01, 0xff, 0xff, 0xff, 0x80, 0x03, 0xff, - 0xff, 0xff, 0xc0, 0x03, 0xff, 0xff, 0xff, 0xc0, 0x07, 0xff, 0xff, 0xff, 0xe0, 0x0f, 0xff, 0xff, - 0xff, 0xf0, 0x0f, 0xff, 0xff, 0xff, 0xf0, 0x1f, 0xff, 0xff, 0xff, 0xf8, 0x1f, 0xff, 0xff, 0xff, - 0xf8, 0x1f, 0xff, 0xff, 0xff, 0xf8, 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xfc, - 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, - 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, - 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, - 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0x00, 0xff, 0xfc, 0x3f, 0xf8, 0x00, 0x1f, - 0xfc, 0x3f, 0xf0, 0x00, 0x0f, 0xfc, 0x3f, 0xc0, 0x00, 0x03, 0xfc, 0x3f, 0x80, 0x00, 0x01, 0xfc, - 0x3f, 0x00, 0x00, 0x00, 0xfc, 0x3f, 0x00, 0x00, 0x00, 0xfc, 0x3e, 0x00, 0x00, 0x00, 0x7c, 0x3c, - 0x00, 0x00, 0x00, 0x3c, 0x3c, 0x00, 0x00, 0x00, 0x3c, 0x3c, 0x00, 0x00, 0x00, 0x3c, 0x38, 0x00, - 0x00, 0x00, 0x1c, 0x38, 0x00, 0x00, 0x00, 0x1c, 0x38, 0x00, 0x00, 0x00, 0x1c, 0x38, 0x00, 0x00, - 0x00, 0x1c, 0x38, 0x00, 0x00, 0x00, 0x1c, 0x38, 0x00, 0x00, 0x00, 0x1c, 0x38, 0x00, 0x00, 0x00, - 0x1c, 0x38, 0x00, 0x00, 0x00, 0x1c, 0x1c, 0x00, 0x00, 0x00, 0x38, 0x1c, 0x00, 0x00, 0x00, 0x38, - 0x1c, 0x00, 0x00, 0x00, 0x38, 0x0e, 0x00, 0x00, 0x00, 0x70, 0x0f, 0x00, 0x00, 0x00, 0xf0, 0x07, - 0x00, 0x00, 0x00, 0xe0, 0x03, 0x80, 0x00, 0x01, 0xc0, 0x03, 0xc0, 0x00, 0x03, 0xc0, 0x01, 0xf0, - 0x00, 0x0f, 0x80, 0x00, 0xf8, 0x00, 0x1f, 0x00, 0x00, 0x3f, 0x00, 0xfc, 0x00, 0x00, 0x1f, 0xff, - 0xf8, 0x00, 0x00, 0x07, 0xff, 0xe0, 0x00, 0x00, 0x00, 0xff, 0x00, 0x00, -}; -const nbgl_icon_details_t C_switch_60_40 = { 60, 40, NBGL_BPP_1, false, C_switch_60_40_bitmap }; - -uint8_t const C_Check_Circle_64px_bitmap[] = { - 0x40, 0x00, 0x40, 0x00, 0x21, 0x33, 0x02, 0x00, 0x31, 0x02, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xad, 0x55, 0x39, 0x4e, 0x03, 0x31, 0x14, 0xfd, 0x24, 0x61, 0x5f, 0x4b, - 0x28, 0x80, 0x91, 0xa0, 0x01, 0x24, 0x88, 0xb8, 0x40, 0x46, 0x54, 0x20, 0x21, 0x41, 0x49, 0x39, - 0x2d, 0x15, 0xdc, 0x00, 0x90, 0xa0, 0x66, 0x11, 0xa2, 0x05, 0x71, 0x01, 0x10, 0x17, 0x48, 0x0a, - 0x6a, 0x02, 0x17, 0x60, 0xab, 0x41, 0x61, 0x89, 0x04, 0x24, 0x21, 0x9f, 0xef, 0x65, 0x66, 0xbe, - 0x3d, 0x0e, 0x8b, 0xc4, 0x14, 0x99, 0xb1, 0x9f, 0xfd, 0xfc, 0xfc, 0xfc, 0xf3, 0x8c, 0xf8, 0x7f, - 0x4f, 0xf5, 0x60, 0x1a, 0x60, 0x74, 0xa9, 0xd8, 0x00, 0xde, 0x04, 0xfd, 0xcc, 0x95, 0x1c, 0x68, - 0xcd, 0x87, 0xe8, 0xc9, 0x14, 0xbf, 0x85, 0x01, 0x52, 0x79, 0x0b, 0xae, 0x1b, 0x30, 0x40, 0x8b, - 0xb5, 0xc4, 0xae, 0x9c, 0xb5, 0x7c, 0x8d, 0xf8, 0x70, 0xe0, 0x89, 0xef, 0x71, 0x03, 0x7e, 0x13, - 0x5d, 0xfd, 0x7a, 0x4e, 0x7d, 0x4f, 0xb4, 0xd6, 0x38, 0x9e, 0xa5, 0x8e, 0xf9, 0xb8, 0x79, 0x4c, - 0xcd, 0x34, 0x5b, 0xe1, 0x9e, 0xda, 0x13, 0x7c, 0xbc, 0x18, 0x30, 0x19, 0x8b, 0xa3, 0x15, 0x5b, - 0x4d, 0xb9, 0x01, 0xa9, 0x89, 0x5a, 0xaf, 0x34, 0xfa, 0xd0, 0xd4, 0xfb, 0x41, 0x5d, 0xb9, 0xb0, - 0xb1, 0x0a, 0x30, 0x68, 0xfb, 0x71, 0x15, 0x53, 0x56, 0x00, 0x9a, 0x6e, 0x6c, 0xfc, 0xb3, 0x2f, - 0xe2, 0x24, 0x75, 0xdd, 0x49, 0xbf, 0x2f, 0x01, 0x86, 0xd4, 0x57, 0x10, 0x8e, 0xac, 0x5a, 0x0a, - 0x32, 0xaa, 0x97, 0xdc, 0x54, 0x5d, 0x47, 0x39, 0x3e, 0x80, 0x54, 0xc9, 0x63, 0x7a, 0x09, 0xb7, - 0x5a, 0x81, 0x34, 0xc7, 0xa9, 0x7f, 0x41, 0xbc, 0x0b, 0x00, 0x27, 0x6a, 0x3a, 0xdb, 0x92, 0xe2, - 0xed, 0x12, 0x6f, 0x3f, 0x74, 0x82, 0xb6, 0x64, 0x10, 0xf8, 0x52, 0x40, 0x1d, 0xa0, 0x23, 0xde, - 0x12, 0x27, 0x20, 0x62, 0xa5, 0x73, 0x0a, 0x9d, 0x04, 0xcf, 0x00, 0xdb, 0x88, 0xe5, 0xd8, 0x5b, - 0x8b, 0xe0, 0x5d, 0x0a, 0x7c, 0x02, 0x28, 0xa1, 0x93, 0x80, 0x56, 0xee, 0x15, 0xab, 0xa4, 0x0c, - 0x53, 0x19, 0x81, 0x07, 0x9d, 0x88, 0xeb, 0xa1, 0x3b, 0x49, 0x82, 0x00, 0xda, 0x11, 0x17, 0xc5, - 0x8f, 0x9b, 0x60, 0x47, 0x4c, 0xf5, 0x95, 0x0b, 0x2e, 0x82, 0x4b, 0xf1, 0xed, 0x41, 0x0f, 0x36, - 0x20, 0xb8, 0x15, 0xd2, 0xa4, 0x48, 0x37, 0xc1, 0x93, 0x30, 0xc8, 0xc2, 0x39, 0x81, 0x0b, 0xe7, - 0x04, 0x4e, 0x5c, 0x10, 0xac, 0x30, 0xdc, 0xd4, 0xa7, 0x08, 0x56, 0x98, 0xbe, 0xac, 0x5d, 0x7c, - 0x31, 0x5e, 0x10, 0x07, 0x1c, 0x70, 0x7f, 0x34, 0xff, 0x5a, 0xe8, 0x4f, 0xb3, 0x36, 0xc9, 0xad, - 0x2f, 0x80, 0x36, 0xc4, 0x53, 0x76, 0x3e, 0xd6, 0xfe, 0x3c, 0x61, 0x2d, 0x3f, 0x5f, 0x73, 0xba, - 0x3a, 0xdf, 0xb2, 0xac, 0x12, 0xd7, 0xf4, 0x0f, 0x59, 0x1f, 0x54, 0x25, 0xc3, 0x6e, 0x7b, 0x5f, - 0x54, 0x65, 0x01, 0x3b, 0x40, 0xe3, 0x78, 0x8e, 0xd4, 0xca, 0xbe, 0xfe, 0x1f, 0xe9, 0x92, 0x4c, - 0xb3, 0xf2, 0xc9, 0xe8, 0x32, 0xce, 0xb3, 0x92, 0x8c, 0xa6, 0x57, 0x34, 0x71, 0x39, 0x2e, 0x70, - 0xaa, 0xb6, 0x34, 0x0f, 0x1d, 0xd9, 0x5f, 0xe3, 0xe1, 0xf2, 0x9e, 0x63, 0xd5, 0xa7, 0x79, 0xfd, - 0x44, 0xba, 0xe8, 0xdd, 0x69, 0x63, 0xef, 0x1a, 0xe5, 0xc3, 0x64, 0x34, 0xd2, 0x9d, 0x2f, 0x27, - 0xbf, 0xcb, 0xa7, 0x1f, 0xf3, 0x8d, 0x9c, 0xb0, 0x03, 0x9b, 0x28, 0x53, 0x25, 0x23, 0x5f, 0x8d, - 0xc0, 0x3e, 0x33, 0xf2, 0x15, 0xeb, 0x59, 0x73, 0xc0, 0x39, 0x58, 0x51, 0x22, 0xf3, 0x7d, 0x2c, - 0xcc, 0xf7, 0x8d, 0x44, 0xbe, 0xcb, 0xc0, 0xa6, 0xfb, 0xe1, 0x02, 0xf1, 0x51, 0xdd, 0x0f, 0x03, - 0x98, 0x08, 0x6c, 0xfe, 0x64, 0xec, 0x2b, 0xac, 0xea, 0x19, 0x70, 0xf1, 0xaf, 0xf7, 0x1b, 0x2d, - 0xb1, 0x1f, 0xc2, 0xb3, 0x0d, 0x2e, 0xd0, 0xda, 0xd6, 0x0c, 0xc0, 0xc8, 0x72, 0xfe, 0x1f, 0xaf, - 0x6c, 0xfc, 0x02, 0x24, 0x14, 0x5a, 0xc5, 0x00, 0x08, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Check_Circle_64px = { 64, 64, NBGL_BPP_4, true, C_Check_Circle_64px_bitmap }; - -uint8_t const C_Denied_Circle_64px_bitmap[] = { - 0x40, 0x00, 0x40, 0x00, 0x21, 0x30, 0x02, 0x00, 0x2e, 0x02, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xad, 0x55, 0x4b, 0x2f, 0x04, 0x41, 0x10, 0x2e, 0x6b, 0xbd, 0x9f, 0x47, - 0x0e, 0xd8, 0x84, 0x48, 0x90, 0xac, 0x8d, 0x3f, 0x60, 0xe2, 0x44, 0x22, 0xe1, 0xe8, 0xb8, 0x71, - 0x73, 0xe2, 0x1f, 0x20, 0xe1, 0xec, 0x11, 0x71, 0x25, 0xfe, 0x00, 0xf1, 0x07, 0xd6, 0xc1, 0xd9, - 0xf2, 0x07, 0x3c, 0xe6, 0x4c, 0xd6, 0x63, 0xe3, 0xb9, 0xa6, 0x54, 0xf5, 0x63, 0xa6, 0xa7, 0x67, - 0x66, 0x97, 0x44, 0x1f, 0x76, 0xb6, 0xbb, 0xba, 0xaa, 0xbe, 0xfe, 0xea, 0xeb, 0x6a, 0xc4, 0xff, - 0x1b, 0x5f, 0xfb, 0x13, 0x00, 0x43, 0x0b, 0xc5, 0x04, 0xf3, 0x06, 0xa8, 0x31, 0x53, 0x8a, 0xb1, - 0x56, 0x1c, 0xf0, 0x47, 0xba, 0x58, 0xd5, 0x0c, 0x90, 0x2a, 0x58, 0x66, 0x2f, 0x64, 0x06, 0x68, - 0xb4, 0x52, 0xec, 0x08, 0xaf, 0xa5, 0x6b, 0xc4, 0xfb, 0xfd, 0x0c, 0xff, 0x1f, 0x0d, 0x99, 0xdf, - 0x78, 0xa9, 0x47, 0xf9, 0x78, 0xbb, 0x3c, 0x5b, 0x35, 0xed, 0x39, 0x5a, 0x98, 0x0d, 0xa6, 0x47, - 0x34, 0xad, 0x37, 0x32, 0xb8, 0x34, 0x1f, 0x33, 0xf7, 0xf3, 0x86, 0x6c, 0x00, 0x8e, 0x32, 0x36, - 0x85, 0xe1, 0xe6, 0x09, 0x8d, 0x3f, 0x7b, 0xa1, 0xdd, 0x07, 0x61, 0xbc, 0x1f, 0xb4, 0x34, 0xa9, - 0x27, 0x2b, 0x00, 0x7d, 0x36, 0x1f, 0x57, 0x41, 0xc8, 0x4f, 0x80, 0xba, 0x1b, 0xdb, 0xfe, 0xdd, - 0xed, 0xc7, 0x24, 0x74, 0x1d, 0x51, 0xbe, 0x2f, 0x01, 0xfa, 0xe5, 0xbf, 0x7c, 0x24, 0xbb, 0x42, - 0x90, 0x96, 0x55, 0x25, 0x36, 0xe3, 0xca, 0x49, 0xa8, 0x44, 0x99, 0x9e, 0xcd, 0xa3, 0x1a, 0x83, - 0xd6, 0xe7, 0xf8, 0x7b, 0x06, 0x70, 0x2c, 0x0f, 0x6d, 0xa9, 0x05, 0xa0, 0x9d, 0xbf, 0x8e, 0x66, - 0x62, 0x51, 0xf3, 0x3f, 0x2c, 0xbf, 0x8e, 0x00, 0xe0, 0x01, 0xb4, 0x8a, 0xe9, 0xab, 0x4e, 0xe3, - 0xc2, 0x32, 0xaa, 0xc0, 0x12, 0xe7, 0xb8, 0x3a, 0x46, 0xaa, 0xa4, 0xd8, 0x96, 0x78, 0x9f, 0x00, - 0xb6, 0x10, 0xcb, 0xfa, 0x74, 0x19, 0x85, 0x93, 0xe8, 0x90, 0x1b, 0xdf, 0x05, 0xc0, 0x47, 0x80, - 0x12, 0x1a, 0xeb, 0x9e, 0xde, 0xc7, 0x99, 0xbb, 0x38, 0x4b, 0x2a, 0xa8, 0x62, 0xd6, 0x70, 0xe7, - 0x88, 0x6d, 0x88, 0x6b, 0x3e, 0x3b, 0xc2, 0x12, 0xb8, 0x33, 0xa2, 0x16, 0xc4, 0x79, 0xfe, 0x09, - 0x02, 0x18, 0xee, 0xb8, 0xcd, 0xae, 0x8e, 0x64, 0x41, 0x07, 0x30, 0xdc, 0xa9, 0x44, 0xf5, 0x9c, - 0xa4, 0xd3, 0xd4, 0x91, 0xe1, 0x8e, 0xb7, 0x0c, 0x4d, 0x80, 0x34, 0x74, 0x68, 0x14, 0xe3, 0x91, - 0x09, 0x32, 0xed, 0x1c, 0x20, 0x70, 0xff, 0xbb, 0x3d, 0x2e, 0x7e, 0x2d, 0x7c, 0xb9, 0x40, 0x7c, - 0xf6, 0xf9, 0xce, 0xb8, 0xc0, 0xf9, 0x6a, 0xfc, 0x34, 0x28, 0x92, 0x92, 0xf8, 0x6d, 0x46, 0x3c, - 0xa9, 0x56, 0x9f, 0xf6, 0xda, 0xf5, 0x2d, 0x0b, 0x95, 0x18, 0xeb, 0xae, 0xbe, 0x9a, 0x1f, 0x42, - 0x1f, 0xa4, 0x92, 0x81, 0x78, 0x7d, 0x3d, 0x4b, 0x65, 0x29, 0x19, 0x47, 0xf5, 0x79, 0x28, 0x33, - 0x3b, 0xea, 0x1e, 0x45, 0xf4, 0x9d, 0x91, 0x06, 0x92, 0xb1, 0xd5, 0xcd, 0x4a, 0xfa, 0x5a, 0x8b, - 0xc0, 0x65, 0x2d, 0x70, 0x6b, 0xb8, 0x6a, 0xbd, 0x62, 0x37, 0x17, 0x9f, 0x1d, 0x15, 0xd7, 0x49, - 0xba, 0xdf, 0x8a, 0xd8, 0xbb, 0xa4, 0xfe, 0x90, 0xf5, 0x77, 0xc6, 0xf7, 0x97, 0xe3, 0xdf, 0xf5, - 0xa7, 0x9a, 0xfd, 0x8d, 0xaf, 0xa6, 0xd5, 0xb0, 0x57, 0x42, 0x42, 0x74, 0xed, 0x86, 0x7d, 0x1a, - 0xd2, 0x21, 0x7a, 0xb9, 0xf0, 0x86, 0x73, 0xee, 0xcf, 0x91, 0xfe, 0x3e, 0xa2, 0xf9, 0x5f, 0x8f, - 0xf4, 0x77, 0xd1, 0xb0, 0xe9, 0x7d, 0xb8, 0x40, 0x7c, 0x90, 0xef, 0x43, 0x2f, 0x46, 0x1a, 0xb6, - 0x39, 0xd2, 0xf6, 0x13, 0xf6, 0x95, 0x09, 0x99, 0x8b, 0x7f, 0x7d, 0xdf, 0x28, 0xc5, 0x9e, 0x36, - 0x4f, 0x27, 0x3c, 0xa0, 0x95, 0xcd, 0x29, 0x80, 0xc1, 0xa5, 0xc2, 0x3f, 0x3e, 0xd9, 0xf8, 0x03, - 0x70, 0xa7, 0x85, 0x84, 0x00, 0x08, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Denied_Circle_64px = { 64, 64, NBGL_BPP_4, true, C_Denied_Circle_64px_bitmap }; - -uint8_t const C_Important_Circle_64px_bitmap[] = { - 0x40, 0x00, 0x40, 0x00, 0x21, 0xfa, 0x01, 0x00, 0xf8, 0x01, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xb5, 0x55, 0xcd, 0x4e, 0xc2, 0x40, 0x10, 0x1e, 0xa1, 0xfe, 0xe3, 0xcf, - 0x51, 0x0f, 0x2a, 0x89, 0x5e, 0xd4, 0x04, 0x89, 0x2f, 0x60, 0xe3, 0x49, 0x13, 0x13, 0x3c, 0x7a, - 0xe4, 0xca, 0xcd, 0x37, 0x50, 0x13, 0x3d, 0xa3, 0xc6, 0x70, 0xd5, 0xf8, 0x02, 0x18, 0x5f, 0x00, - 0x0f, 0x9e, 0x05, 0x5f, 0xc0, 0x1f, 0xce, 0x1a, 0x10, 0x49, 0x54, 0xc0, 0x8e, 0xb3, 0xed, 0xb6, - 0x74, 0xdb, 0x59, 0xd0, 0x04, 0xe7, 0xd0, 0x76, 0xf6, 0xdb, 0xee, 0x7c, 0xfd, 0x76, 0xfa, 0x2d, - 0x62, 0xef, 0xa2, 0x99, 0x5b, 0x05, 0x58, 0xd8, 0x29, 0x6a, 0xe0, 0x43, 0x90, 0xb1, 0x59, 0x61, - 0xd0, 0x96, 0x09, 0x5e, 0x18, 0xc5, 0x8e, 0x30, 0x40, 0xa4, 0x10, 0x80, 0x2d, 0x05, 0x06, 0x18, - 0x08, 0x94, 0x38, 0xb1, 0xdf, 0xca, 0x3c, 0x20, 0xbe, 0xe4, 0xe2, 0xe2, 0x79, 0x49, 0x81, 0x3f, - 0xc4, 0xd0, 0x94, 0x7c, 0xc7, 0x3a, 0x15, 0xd9, 0x9e, 0x1f, 0x4f, 0xd2, 0xc0, 0x56, 0x3b, 0xbd, - 0xa4, 0x34, 0xea, 0xab, 0x50, 0xa6, 0x7c, 0xd9, 0x3f, 0x5f, 0x4c, 0x48, 0xb4, 0xc9, 0x51, 0xc5, - 0x41, 0x95, 0x6e, 0x9a, 0xd8, 0x78, 0xd9, 0x3b, 0xcd, 0x3e, 0x57, 0xf9, 0x7e, 0xd1, 0xd0, 0x9a, - 0x9b, 0xec, 0x02, 0xcc, 0x04, 0xf5, 0xb8, 0x6f, 0x2f, 0xd9, 0x00, 0xe8, 0x7b, 0x0c, 0xe2, 0xdf, - 0x93, 0xde, 0x9a, 0xc4, 0x6e, 0x2c, 0xac, 0x77, 0x09, 0x60, 0xd6, 0x79, 0x4a, 0x87, 0xaa, 0x4b, - 0x06, 0x86, 0xb3, 0xab, 0xa4, 0x26, 0xb7, 0x9d, 0xc4, 0xca, 0xde, 0xa6, 0x9a, 0xff, 0x53, 0x7d, - 0x41, 0xe3, 0x29, 0x71, 0xbf, 0x01, 0xc8, 0xb3, 0xdd, 0x02, 0x10, 0x13, 0x77, 0xd3, 0xa7, 0x84, - 0x12, 0xa6, 0x4d, 0xc0, 0x02, 0x18, 0xe1, 0x71, 0x5a, 0xd8, 0xe1, 0xb9, 0xc2, 0xe3, 0x6f, 0x00, - 0x59, 0xc4, 0x3a, 0xfb, 0x75, 0x22, 0x3e, 0x6d, 0x82, 0x55, 0x80, 0x0a, 0x8f, 0x53, 0xe5, 0x09, - 0x51, 0x25, 0xa2, 0xeb, 0xf7, 0x38, 0x8c, 0x22, 0xee, 0xf3, 0xea, 0x38, 0xc2, 0x0e, 0x23, 0x6e, - 0x8b, 0x0b, 0x1f, 0xc7, 0xe2, 0x55, 0xd3, 0x51, 0x81, 0x8b, 0x12, 0x44, 0x45, 0x91, 0x71, 0x3b, - 0x69, 0xf7, 0xb6, 0x20, 0x9e, 0x15, 0x43, 0x4f, 0x82, 0x9a, 0x4d, 0x92, 0xc7, 0xab, 0x42, 0xa0, - 0xff, 0xc6, 0xbb, 0xf1, 0x4b, 0x72, 0xcd, 0xe7, 0x6e, 0xa0, 0x21, 0x45, 0xd2, 0xe9, 0xd3, 0x2f, - 0x45, 0xd2, 0xe9, 0x3b, 0x84, 0x78, 0xd5, 0x69, 0x7f, 0x62, 0xdd, 0xf7, 0xb7, 0x2e, 0xc9, 0xb2, - 0x7f, 0x40, 0xca, 0xee, 0x92, 0x39, 0x1e, 0xaf, 0x39, 0x9d, 0x05, 0xba, 0x0d, 0xbc, 0x70, 0x2a, - 0x9b, 0xf2, 0x3f, 0x62, 0xe8, 0x19, 0xb2, 0x8d, 0x0b, 0x1c, 0xdc, 0x90, 0x0b, 0xd7, 0x35, 0x0d, - 0x5e, 0x96, 0xe3, 0xad, 0xa0, 0xb9, 0x78, 0xea, 0xc8, 0x75, 0x4d, 0xdd, 0xff, 0x2d, 0x85, 0x7d, - 0xd6, 0xf9, 0x43, 0xc2, 0x9b, 0xc9, 0xfb, 0x4b, 0xfe, 0x77, 0xfe, 0xd4, 0xd5, 0xdf, 0x48, 0x89, - 0xa0, 0x61, 0xd3, 0x92, 0x91, 0x8a, 0xe2, 0xaf, 0x8a, 0x61, 0x5f, 0x2b, 0xfe, 0x8a, 0x56, 0x52, - 0x9d, 0x70, 0x2b, 0xfc, 0x39, 0xe4, 0xef, 0x8b, 0xae, 0xbf, 0x1f, 0x84, 0xfc, 0xdd, 0x36, 0x6c, - 0x3a, 0x1f, 0xee, 0x10, 0x5f, 0x9d, 0xf3, 0x61, 0x1a, 0x43, 0x86, 0xed, 0x0f, 0x23, 0xd8, 0x53, - 0xcd, 0xb8, 0x02, 0x17, 0xff, 0x7a, 0xbe, 0x51, 0x89, 0x33, 0x17, 0xde, 0xd0, 0xf4, 0x73, 0xeb, - 0x68, 0x1d, 0x60, 0x3e, 0x53, 0xe8, 0xe1, 0x91, 0x8d, 0x3f, 0x0e, 0xc1, 0x39, 0xe4, 0x00, 0x08, - 0x00, 0x00, -}; -const nbgl_icon_details_t C_Important_Circle_64px = { 64, 64, NBGL_BPP_4, true, C_Important_Circle_64px_bitmap }; - -uint8_t const C_Review_64px_bitmap[] = { - 0x40, 0x00, 0x40, 0x00, 0x21, 0xd3, 0x00, 0x00, 0xd1, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xed, 0xd5, 0x3b, 0x0e, 0xc2, 0x30, 0x0c, 0x06, 0x60, 0xab, 0xea, 0x90, - 0x8d, 0x2b, 0xf4, 0x04, 0x39, 0x07, 0xc7, 0xe0, 0x28, 0x11, 0x62, 0xc8, 0x04, 0x77, 0x64, 0xea, - 0xd6, 0x95, 0xa9, 0xc1, 0x29, 0x24, 0xa6, 0xf8, 0x01, 0x43, 0x87, 0x0e, 0xf1, 0x52, 0xa1, 0xaf, - 0xb8, 0x4e, 0xa5, 0xfe, 0x4e, 0x69, 0x93, 0x9a, 0xa3, 0x50, 0x13, 0xf9, 0x1d, 0x84, 0xf2, 0xf4, - 0xf7, 0x41, 0xf2, 0xae, 0x36, 0x78, 0x00, 0x98, 0x0d, 0x14, 0xaf, 0x0d, 0xd0, 0x8f, 0x6c, 0xbc, - 0x81, 0x1a, 0xa0, 0xdf, 0xd8, 0x99, 0x70, 0x66, 0x87, 0x97, 0x11, 0x6f, 0xbd, 0x48, 0x8e, 0x43, - 0x3b, 0x1a, 0x9d, 0x7b, 0x0a, 0xd9, 0xcb, 0xc9, 0x35, 0x0f, 0xff, 0xfb, 0xf2, 0x1b, 0xe0, 0xf0, - 0xe5, 0x7d, 0x99, 0x4f, 0x71, 0x57, 0xce, 0xd7, 0xbc, 0x79, 0x73, 0xdd, 0x95, 0xef, 0x6f, 0x1f, - 0xce, 0xf2, 0xeb, 0xba, 0x76, 0x21, 0xfc, 0x6c, 0x07, 0x4f, 0x2e, 0xe6, 0x6f, 0x77, 0xaa, 0x2e, - 0xe7, 0x37, 0x90, 0xf3, 0xfc, 0x3f, 0xaf, 0x3c, 0x49, 0xe9, 0x69, 0xfa, 0xf2, 0x48, 0xcb, 0x73, - 0x03, 0xcb, 0xdf, 0xf9, 0xfd, 0xdb, 0xfb, 0x28, 0xd7, 0x6b, 0x3f, 0x04, 0xd0, 0x2b, 0xef, 0x17, - 0xcb, 0xbd, 0xfe, 0xe6, 0xea, 0x7a, 0x92, 0x57, 0xdf, 0xc7, 0x7a, 0x1b, 0xa3, 0x56, 0xd3, 0x06, - 0x8b, 0xfb, 0x09, 0xaa, 0x24, 0xa5, 0x2a, 0x00, 0x08, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Review_64px = { 64, 64, NBGL_BPP_4, true, C_Review_64px_bitmap }; - -uint8_t const C_SecurityShield_64px_bitmap[] = { - 0x40, 0x00, 0x40, 0x00, 0x21, 0x5a, 0x02, 0x00, 0x58, 0x02, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xad, 0x95, 0xbf, 0x53, 0x13, 0x41, 0x14, 0xc7, 0xbf, 0x97, 0x1c, 0xbf, - 0x14, 0xf1, 0x2a, 0x3a, 0xf0, 0x26, 0xb6, 0x8e, 0xc6, 0x86, 0x52, 0xd3, 0xd0, 0xd0, 0xc0, 0x7f, - 0x00, 0xa2, 0x85, 0x9d, 0x69, 0x1d, 0x2d, 0x62, 0xc1, 0x4c, 0xba, 0x60, 0x6d, 0x01, 0x63, 0x63, - 0xe3, 0x8c, 0xb4, 0x56, 0xde, 0x28, 0x43, 0xc3, 0x00, 0xf6, 0x16, 0x41, 0x0a, 0xad, 0x0c, 0xc2, - 0x80, 0x06, 0x48, 0x38, 0xf7, 0xed, 0xde, 0xed, 0xef, 0x8b, 0x33, 0x8e, 0xdb, 0x24, 0xbb, 0x9f, - 0xbd, 0xb7, 0xef, 0x7d, 0xdf, 0xbe, 0xb7, 0x69, 0xfa, 0x3f, 0x46, 0xef, 0xcd, 0xa3, 0x4a, 0xe5, - 0xe6, 0xec, 0xd3, 0x3d, 0x3f, 0x7e, 0x81, 0x7c, 0xcc, 0x7c, 0xf0, 0xe0, 0x4b, 0x68, 0x63, 0xce, - 0xe5, 0xa7, 0x3a, 0xc7, 0xf0, 0xa1, 0xcd, 0xd7, 0x0d, 0x8e, 0xd0, 0xf6, 0x22, 0x46, 0xf0, 0xf8, - 0x6d, 0xa7, 0xf3, 0x63, 0x7b, 0xa5, 0xea, 0xb3, 0x70, 0x0e, 0x5c, 0xc9, 0xff, 0x6f, 0xc5, 0xb4, - 0x61, 0xd4, 0xe0, 0xc7, 0xc0, 0xbc, 0x9c, 0xf4, 0x97, 0x69, 0xc3, 0x2d, 0xeb, 0x78, 0xdd, 0xe0, - 0x6b, 0xda, 0xd0, 0xd2, 0x16, 0x6a, 0x18, 0x32, 0xec, 0xd1, 0x86, 0xb2, 0xfa, 0xa2, 0x0f, 0x8c, - 0x9b, 0xfe, 0x36, 0xd8, 0x86, 0xdb, 0x72, 0xf6, 0x0b, 0xb8, 0x6f, 0xe9, 0x55, 0x03, 0x4a, 0x6d, - 0xcd, 0xbd, 0x77, 0x56, 0xc0, 0x5d, 0x66, 0x60, 0x2a, 0x9f, 0x6c, 0x20, 0x70, 0x14, 0xfd, 0x08, - 0x04, 0xb9, 0x81, 0x25, 0x0c, 0xbb, 0x19, 0x61, 0x32, 0x4c, 0x4b, 0xf5, 0xae, 0xba, 0x29, 0x39, - 0x60, 0x1e, 0x88, 0x10, 0x7a, 0xc0, 0x0d, 0x75, 0x2a, 0x72, 0xf9, 0xaa, 0xb9, 0x68, 0x67, 0xc0, - 0xa2, 0x0a, 0x4b, 0x8c, 0x16, 0x37, 0x30, 0xc2, 0x57, 0x4f, 0x80, 0x35, 0xc1, 0x55, 0x06, 0xaf, - 0x0b, 0x0f, 0x78, 0x1e, 0x8f, 0x80, 0xb6, 0x87, 0xa7, 0x09, 0x70, 0x87, 0x56, 0x3f, 0xcb, 0xf0, - 0x00, 0xf1, 0xfb, 0x93, 0xf3, 0xb3, 0xec, 0x80, 0x04, 0x21, 0xe5, 0xb8, 0xd9, 0x6c, 0x9a, 0x9c, - 0xa5, 0x85, 0x1b, 0x5e, 0xe5, 0xdb, 0x84, 0x6f, 0x06, 0xff, 0x2a, 0x22, 0xa8, 0x63, 0x8c, 0x5f, - 0x11, 0x87, 0x77, 0x45, 0xde, 0x6a, 0x24, 0x4f, 0xd7, 0xc3, 0x99, 0x70, 0x21, 0xe7, 0xe3, 0xc4, - 0x43, 0xe7, 0x7c, 0x96, 0x18, 0x8a, 0x30, 0xc6, 0x04, 0xf1, 0x51, 0xdb, 0x7f, 0xae, 0xcc, 0x93, - 0x34, 0x8d, 0x68, 0x96, 0xf3, 0xfe, 0x8e, 0xc6, 0xcf, 0xb9, 0xf2, 0xd0, 0xf9, 0x7a, 0x79, 0x47, - 0x71, 0xf6, 0xe9, 0x98, 0xc5, 0x1b, 0xe4, 0x92, 0xe4, 0x7c, 0x36, 0x80, 0xd7, 0x1d, 0x6e, 0xda, - 0x8f, 0xa9, 0x6e, 0x0c, 0xff, 0x7a, 0x96, 0x7f, 0x13, 0x7f, 0x8f, 0xaf, 0x8a, 0x6b, 0x05, 0xfa, - 0x24, 0x5c, 0x9f, 0x05, 0x3a, 0xc4, 0xab, 0x6f, 0x15, 0x25, 0x7e, 0x7d, 0x0b, 0xf2, 0x93, 0x95, - 0xf5, 0x2a, 0xbf, 0xde, 0x9e, 0xfc, 0x1e, 0x8b, 0x0b, 0xb4, 0x81, 0xb2, 0xff, 0x7e, 0xd4, 0x45, - 0x5d, 0xed, 0x17, 0xdc, 0xaf, 0x0b, 0x88, 0xba, 0x29, 0xba, 0x9f, 0x07, 0x59, 0x05, 0x9d, 0xfa, - 0xef, 0x37, 0x15, 0xc8, 0x5a, 0x56, 0x1f, 0xf3, 0x9e, 0xfa, 0x60, 0x55, 0x3f, 0x34, 0xa8, 0xbe, - 0x1a, 0xb2, 0x45, 0x44, 0x76, 0xfb, 0xc8, 0xf7, 0xb6, 0x8b, 0xeb, 0x9b, 0x2d, 0x92, 0x6c, 0x99, - 0xcc, 0x6e, 0x7f, 0x38, 0xd1, 0x5a, 0xd8, 0x91, 0x0c, 0x40, 0xb5, 0xac, 0x58, 0xeb, 0x91, 0xbf, - 0xf5, 0xf6, 0xa8, 0x22, 0x91, 0x1d, 0xb0, 0xe7, 0xf4, 0xb7, 0x4f, 0x50, 0xa7, 0xf3, 0x0a, 0x09, - 0x0d, 0xfc, 0x8d, 0xe1, 0x40, 0xeb, 0xe1, 0x49, 0xd6, 0x09, 0xb2, 0xf1, 0x3d, 0x62, 0xfc, 0x5e, - 0x51, 0x7f, 0x4e, 0x37, 0x49, 0xa1, 0x11, 0xab, 0xbf, 0x4b, 0x07, 0x2e, 0x1e, 0x10, 0x2e, 0xef, - 0x59, 0xef, 0x43, 0xe9, 0xd9, 0x2e, 0x75, 0xbd, 0xf7, 0x0f, 0xb9, 0xbe, 0x81, 0x15, 0x6f, 0xc2, - 0x57, 0x2b, 0x51, 0x26, 0x7f, 0xd0, 0xf2, 0xa8, 0xa5, 0x86, 0x83, 0xd3, 0xcb, 0x48, 0xc3, 0x93, - 0x9e, 0x37, 0xf2, 0xa5, 0xa4, 0xa5, 0xe7, 0xde, 0x07, 0xf4, 0xcb, 0xca, 0x5d, 0x82, 0x33, 0xaf, - 0x06, 0xbc, 0xc1, 0x9d, 0xc3, 0x7f, 0x79, 0xb9, 0xff, 0x00, 0xb6, 0x83, 0x9c, 0x31, 0x00, 0x08, - 0x00, 0x00, -}; -const nbgl_icon_details_t C_SecurityShield_64px = { 64, 64, NBGL_BPP_4, true, C_SecurityShield_64px_bitmap }; - -uint8_t const C_Warning_64px_bitmap[] = { - 0x40, 0x00, 0x40, 0x00, 0x21, 0x5f, 0x01, 0x00, 0x5d, 0x01, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x85, 0xd5, 0x31, 0x4e, 0xc3, 0x40, 0x10, 0x05, 0xd0, 0x8d, 0x85, 0x08, - 0x4a, 0x45, 0x49, 0x91, 0xc2, 0x25, 0xb2, 0x52, 0xe4, 0x08, 0x39, 0x40, 0xc4, 0x19, 0x72, 0x82, - 0x5c, 0x81, 0x84, 0x03, 0x80, 0xb8, 0x41, 0xc4, 0x05, 0x72, 0x04, 0x0a, 0xd2, 0xe7, 0x08, 0x69, - 0x02, 0xa2, 0x0b, 0xa5, 0x13, 0xa1, 0x1d, 0xec, 0x99, 0x5d, 0xb3, 0xf6, 0xee, 0x1f, 0x6f, 0xfb, - 0xc6, 0x96, 0xbc, 0xfe, 0x33, 0x43, 0x84, 0x4f, 0xb9, 0x27, 0xed, 0x5c, 0xf2, 0xeb, 0x93, 0xc2, - 0xbf, 0x53, 0x63, 0x26, 0x0a, 0xcf, 0x8c, 0x31, 0x23, 0x9d, 0xb1, 0x5b, 0x66, 0xe8, 0x76, 0x51, - 0xe1, 0x60, 0x06, 0x7d, 0x5d, 0x3f, 0xfc, 0xb8, 0x41, 0xce, 0xbc, 0x24, 0xe4, 0xcc, 0x73, 0x42, - 0xfe, 0xea, 0x18, 0xf8, 0x9b, 0xe7, 0xb4, 0xef, 0x6a, 0x96, 0x7b, 0x4b, 0x39, 0x73, 0x41, 0xc8, - 0x99, 0xef, 0x08, 0xf9, 0x31, 0xe4, 0xd8, 0xbf, 0x5a, 0x1c, 0x79, 0x79, 0x5b, 0xf1, 0x90, 0x90, - 0x33, 0x87, 0x91, 0x68, 0x3b, 0xf3, 0x55, 0x18, 0xa9, 0x96, 0x9f, 0x23, 0x6e, 0xf9, 0x25, 0x8f, - 0x38, 0x74, 0x8e, 0x4b, 0xd6, 0xc9, 0xeb, 0xbf, 0x0b, 0x6f, 0x09, 0x38, 0xf3, 0xe0, 0x85, 0x80, - 0xdb, 0x34, 0x7b, 0x97, 0xb0, 0xc5, 0xec, 0x5d, 0xc2, 0x46, 0xc8, 0x5d, 0xd8, 0x90, 0xaf, 0x9b, - 0xb8, 0x94, 0xc6, 0x9f, 0x1b, 0xfa, 0x31, 0x46, 0xdc, 0x36, 0x8c, 0x7d, 0x4e, 0xba, 0x17, 0x3d, - 0xae, 0xbd, 0x5f, 0xe2, 0xbc, 0xc4, 0x6e, 0x9f, 0xf4, 0xef, 0x93, 0xeb, 0x4b, 0x16, 0x84, 0xf7, - 0x9b, 0x2a, 0x68, 0xfe, 0x4f, 0x5d, 0x90, 0x3d, 0x43, 0x77, 0x05, 0x5b, 0xe8, 0x7d, 0xf9, 0x70, - 0xf1, 0xeb, 0x16, 0x44, 0xf9, 0xcc, 0xde, 0xa1, 0xbb, 0x00, 0x1f, 0xa0, 0xd3, 0x39, 0xef, 0xb4, - 0x4f, 0xb7, 0xbf, 0xbe, 0xf5, 0xfe, 0x72, 0xed, 0x1b, 0x14, 0xa4, 0xfb, 0x7b, 0x78, 0x82, 0x2e, - 0x05, 0xf7, 0xd8, 0xe9, 0x33, 0x18, 0x3f, 0xc9, 0xf9, 0xf4, 0xa1, 0xcf, 0x27, 0x97, 0x97, 0x02, - 0xbb, 0x14, 0x4c, 0xb0, 0x4b, 0xc1, 0x03, 0x76, 0xf2, 0x89, 0x43, 0x6e, 0x57, 0xfa, 0x7c, 0xf7, - 0x89, 0xdb, 0xe8, 0xfb, 0xc5, 0x4c, 0x95, 0xfd, 0xb4, 0x50, 0xf7, 0x93, 0x5f, 0x60, 0x23, 0x65, - 0x3f, 0xe6, 0xba, 0x73, 0xa0, 0xc6, 0x3d, 0xfb, 0x99, 0xf4, 0x05, 0x5e, 0xcd, 0xcb, 0x3f, 0xe4, - 0x2a, 0x7b, 0x24, 0x00, 0x08, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Warning_64px = { 64, 64, NBGL_BPP_4, true, C_Warning_64px_bitmap }; - -uint8_t const C_left_half_64px_bitmap[] = { - 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe, - 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfc, - 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf8, 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf8, - 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf8, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf0, - 0x07, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x07, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe0, - 0x03, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xc0, 0x01, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x80, - 0x01, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x80, 0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x00, - 0x00, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xfe, 0x00, 0x00, 0x3f, 0xff, 0xff, 0xff, 0xff, 0xfc, 0x00, - 0x00, 0x1f, 0xff, 0xff, 0xff, 0xff, 0xf8, 0x00, 0x00, 0x07, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x00, - 0x00, 0x03, 0xff, 0xff, 0xff, 0xff, 0xc0, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, - 0x00, 0x00, 0x7f, 0xff, 0xff, 0xfe, 0x00, 0x00, 0x00, 0x00, 0x0f, 0xff, 0xff, 0xf0, 0x00, 0x00, - 0x00, 0x00, 0x03, 0xff, 0xff, 0xc0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3f, 0xfc, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_left_half_64px = { 24, 64, NBGL_BPP_1, false, C_left_half_64px_bitmap }; - -uint8_t const C_Back_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x21, 0x85, 0x00, 0x00, 0x83, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xfb, 0xff, 0x1f, 0x0c, 0xde, 0x9c, 0xfb, 0x8f, 0x02, 0x1a, 0x38, 0x46, - 0xf9, 0x50, 0xb0, 0xf0, 0x3e, 0x8c, 0xff, 0x57, 0x0a, 0x48, 0xfc, 0x66, 0x90, 0x85, 0xf1, 0x2f, - 0x32, 0xac, 0xff, 0xff, 0xff, 0x9f, 0x02, 0xe3, 0x7d, 0x08, 0xff, 0xaf, 0x00, 0xd3, 0x7b, 0xa0, - 0xe8, 0x23, 0x90, 0x02, 0x10, 0xff, 0x22, 0x83, 0x1e, 0x48, 0x3f, 0x58, 0x01, 0x90, 0x0f, 0x95, - 0x86, 0x28, 0x00, 0xf2, 0xa1, 0xd2, 0x10, 0x05, 0x0d, 0x1c, 0x70, 0x69, 0xb0, 0x82, 0x06, 0x0e, - 0xb8, 0x34, 0x58, 0x41, 0x00, 0x2b, 0x42, 0x1a, 0xa4, 0x00, 0x08, 0xf4, 0x10, 0xae, 0xfd, 0xa7, - 0xc0, 0xc0, 0x80, 0x24, 0x0d, 0x56, 0xa0, 0x87, 0xec, 0x9d, 0x7f, 0x0a, 0x28, 0xd2, 0xff, 0xff, - 0xbf, 0xe8, 0x83, 0x32, 0x00, 0x80, 0x9b, 0xa4, 0x4d, 0x00, 0x02, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Back_32px = { 32, 32, NBGL_BPP_4, true, C_Back_32px_bitmap }; - -uint8_t const C_Check_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x02, 0x42, 0x00, 0x00, 0xf0, 0xf0, 0xf0, 0xf0, 0xf0, 0xf0, 0xf0, 0xf0, - 0xf0, 0x32, 0xf0, 0xe4, 0xf0, 0xc6, 0xf0, 0xc6, 0xf0, 0xc6, 0xf0, 0xc6, 0xf0, 0xc6, 0xf0, 0xc6, - 0xf0, 0xc6, 0xf0, 0xc6, 0xf0, 0xc6, 0xf0, 0xc6, 0xf0, 0xc6, 0xf0, 0xc5, 0xf0, 0xc5, 0xf0, 0xb6, - 0xf0, 0xa6, 0xf0, 0xa6, 0xf0, 0xa6, 0xf0, 0xa6, 0xf0, 0xa6, 0xf0, 0xb5, 0xf0, 0xd3, 0xf0, 0xf0, - 0xf0, 0xf0, 0xf0, 0xf0, 0xf0, 0xf0, 0xf0, 0xf0, 0xf0, 0xa0, -}; -const nbgl_icon_details_t C_Check_32px = { 32, 32, NBGL_BPP_1, true, C_Check_32px_bitmap }; - -uint8_t const C_Check_Circle_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x21, 0x16, 0x01, 0x00, 0x14, 0x01, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x6d, 0x91, 0x3d, 0x4e, 0xc3, 0x40, 0x10, 0x85, 0xdf, 0x2e, 0x48, 0x44, - 0x16, 0x52, 0xf6, 0x06, 0xf6, 0x09, 0x48, 0x3a, 0xca, 0x94, 0x94, 0x70, 0x13, 0x90, 0xa0, 0x44, - 0x0a, 0x15, 0x55, 0x94, 0x1c, 0x21, 0xb9, 0x41, 0x8e, 0x60, 0x3a, 0xe8, 0x7c, 0x07, 0x2a, 0xba, - 0x60, 0x12, 0xc5, 0x26, 0xb1, 0x32, 0xcc, 0xcf, 0xda, 0x42, 0x4a, 0xb6, 0x59, 0x7d, 0x33, 0x6f, - 0xe7, 0xe7, 0x2d, 0xd1, 0x89, 0xd3, 0x3c, 0x06, 0x77, 0x93, 0x77, 0x58, 0x07, 0xf0, 0xf1, 0xd3, - 0x88, 0xbf, 0x8a, 0x1c, 0x58, 0x1a, 0x3f, 0xc0, 0x4d, 0x56, 0xf4, 0x9e, 0xe1, 0x42, 0x71, 0x0b, - 0x5f, 0xc8, 0xbd, 0xcb, 0x70, 0x6f, 0xe9, 0xb1, 0xe9, 0x2a, 0x15, 0xec, 0xd0, 0x6b, 0xeb, 0xbe, - 0x60, 0x4e, 0xf4, 0x29, 0xe9, 0xd7, 0x28, 0x48, 0x39, 0xe8, 0xb9, 0xa1, 0xbd, 0xa4, 0x8c, 0xa5, - 0x59, 0x22, 0x7c, 0xae, 0xfc, 0xe6, 0x68, 0x8f, 0x81, 0xbe, 0x1c, 0x09, 0x97, 0x28, 0x2a, 0xad, - 0x5e, 0xe3, 0x4c, 0x07, 0xc5, 0x78, 0x83, 0x82, 0x3a, 0x41, 0x83, 0x51, 0x09, 0x5b, 0x41, 0x05, - 0x07, 0xa4, 0xdf, 0x68, 0x7b, 0x8b, 0x00, 0xfd, 0x96, 0x6b, 0x1d, 0x0b, 0xfd, 0x12, 0x2b, 0x0b, - 0x04, 0xe5, 0x74, 0x6d, 0xf5, 0x68, 0x8d, 0x44, 0xea, 0xdd, 0x56, 0x98, 0x29, 0x0f, 0xe5, 0xe6, - 0xe6, 0x8d, 0xcc, 0x2c, 0x69, 0x91, 0xff, 0x20, 0xa7, 0x70, 0x29, 0x7c, 0xa7, 0xb2, 0x85, 0xb7, - 0x7d, 0x38, 0x9f, 0xb4, 0xfb, 0x94, 0x66, 0x47, 0xae, 0xfb, 0x5e, 0xb1, 0x9b, 0xff, 0xfd, 0x58, - 0x1e, 0xfb, 0x25, 0x7e, 0xaa, 0xd1, 0x4d, 0xf4, 0x93, 0x05, 0xfe, 0x99, 0x0e, 0x1f, 0x21, 0xfa, - 0x2d, 0x46, 0xeb, 0x71, 0xf3, 0x58, 0xe7, 0x4b, 0x03, 0x6e, 0xd6, 0x7d, 0xe0, 0xfe, 0x29, 0xb8, - 0xeb, 0xe2, 0xd4, 0x4f, 0xd3, 0x1f, 0x10, 0xc6, 0xaf, 0x18, 0x00, 0x02, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Check_Circle_32px = { 32, 32, NBGL_BPP_4, true, C_Check_Circle_32px_bitmap }; - -uint8_t const C_Chevron_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x22, 0x50, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xcd, 0x0a, 0x14, - 0x0a, 0xda, 0x0a, 0x30, 0x0a, 0xd8, 0x0a, 0x50, 0x0a, 0xd6, 0x0a, 0x20, 0x12, 0x20, 0x0a, 0xd4, - 0x0a, 0x20, 0x02, 0x1e, 0x02, 0x20, 0x0a, 0xd2, 0x0a, 0x20, 0x02, 0x0e, 0xc1, 0x0e, 0x02, 0x20, - 0x0a, 0xd0, 0x0a, 0x20, 0x02, 0x0e, 0xc3, 0x0e, 0x02, 0x20, 0x0a, 0xcf, 0x02, 0x10, 0x02, 0x0e, - 0xc5, 0x0e, 0x02, 0x10, 0x02, 0xcf, 0x0e, 0x12, 0x0e, 0xc7, 0x0e, 0x12, 0x0e, 0xd0, 0x1e, 0xc9, - 0x1e, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xc8, -}; -const nbgl_icon_details_t C_Chevron_32px = { 32, 32, NBGL_BPP_4, true, C_Chevron_32px_bitmap }; - -uint8_t const C_Chevron_Back_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x21, 0x69, 0x00, 0x00, 0x67, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xfb, 0xff, 0x7f, 0xb0, 0x83, 0x27, 0xef, 0x61, 0xac, 0x7f, 0x7e, 0x20, - 0x42, 0x41, 0x0f, 0xc6, 0x7f, 0xc4, 0x04, 0x94, 0xfa, 0x2b, 0xc0, 0x04, 0x55, 0xf0, 0x4f, 0x81, - 0xf1, 0x3e, 0x90, 0xba, 0xc8, 0x00, 0x55, 0xf0, 0x88, 0x41, 0x16, 0x44, 0xc1, 0x14, 0x40, 0xa5, - 0xe1, 0x0a, 0xa0, 0xd2, 0x30, 0x05, 0x70, 0x69, 0xa8, 0x02, 0xb8, 0x34, 0x44, 0x01, 0x92, 0x34, - 0x58, 0x01, 0x92, 0x34, 0x58, 0x01, 0xb2, 0x34, 0x48, 0x01, 0xb2, 0x34, 0x48, 0x01, 0x8a, 0xf4, - 0xff, 0xff, 0xd7, 0x72, 0x07, 0x49, 0xe8, 0x02, 0x00, 0x69, 0xf0, 0x4c, 0x8b, 0x00, 0x02, 0x00, - 0x00, -}; -const nbgl_icon_details_t C_Chevron_Back_32px = { 32, 32, NBGL_BPP_4, true, C_Chevron_Back_32px_bitmap }; - -uint8_t const C_Chevron_Next_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x21, 0x69, 0x00, 0x00, 0x67, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xfb, 0xff, 0x7f, 0x50, 0x80, 0x6b, 0xb9, 0x28, 0xdc, 0xbf, 0x02, 0x8c, - 0xf7, 0x91, 0xf9, 0x17, 0x19, 0x18, 0x64, 0x51, 0xa4, 0x99, 0x14, 0x90, 0x15, 0x5c, 0x64, 0xd0, - 0x7b, 0x84, 0xa4, 0x00, 0x28, 0xfd, 0xfe, 0x1f, 0x92, 0x02, 0xa0, 0xf4, 0xff, 0xff, 0x08, 0x05, - 0x20, 0xe9, 0xff, 0xff, 0x11, 0x0a, 0xc0, 0xd2, 0x08, 0x05, 0x10, 0x69, 0x84, 0x02, 0xa8, 0x34, - 0x4c, 0x01, 0x4c, 0x1a, 0xa6, 0xe0, 0x9f, 0x82, 0x1e, 0xcc, 0x9e, 0x47, 0x60, 0x99, 0x27, 0xef, - 0x61, 0xfc, 0x7f, 0x7e, 0xff, 0x07, 0x3d, 0x00, 0x00, 0xb4, 0x0a, 0xa5, 0xcb, 0x00, 0x02, 0x00, - 0x00, -}; -const nbgl_icon_details_t C_Chevron_Next_32px = { 32, 32, NBGL_BPP_4, true, C_Chevron_Next_32px_bitmap }; - -uint8_t const C_Close_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x21, 0x68, 0x00, 0x00, 0x66, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xfb, 0xff, 0x9f, 0xea, 0x60, 0x05, 0x8c, 0xd1, 0x05, 0x26, 0x7f, 0x31, - 0xf4, 0x43, 0xb8, 0x3f, 0x18, 0xd6, 0x43, 0x28, 0x0e, 0x08, 0xbf, 0x01, 0x2a, 0x01, 0xa5, 0xe1, - 0xe2, 0x50, 0x06, 0x4c, 0x1a, 0xca, 0x82, 0x4b, 0x43, 0x99, 0x08, 0x69, 0x30, 0x1b, 0x49, 0x1a, - 0xac, 0x00, 0x59, 0x1a, 0xa4, 0x00, 0x59, 0x1a, 0xa4, 0x00, 0x45, 0x1a, 0x83, 0x8f, 0xa6, 0x1e, - 0xdd, 0x3c, 0x34, 0xfb, 0xd0, 0xdd, 0x83, 0xe6, 0x5e, 0x74, 0xff, 0xa0, 0xf9, 0x17, 0x3d, 0x3c, - 0xd0, 0xc3, 0x0b, 0x3d, 0x3c, 0xa9, 0x0b, 0x00, 0x26, 0xb1, 0x3a, 0x4e, 0x00, 0x02, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Close_32px = { 32, 32, NBGL_BPP_4, true, C_Close_32px_bitmap }; - -uint8_t const C_Denied_Circle_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x21, 0x10, 0x01, 0x00, 0x0e, 0x01, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x6d, 0x51, 0x31, 0x4e, 0xc3, 0x40, 0x10, 0x9c, 0x3b, 0x0a, 0x22, 0x14, - 0x89, 0xfb, 0x81, 0xfd, 0x02, 0xa0, 0xa3, 0x4c, 0x49, 0xc9, 0x53, 0x40, 0x82, 0x12, 0x29, 0x79, - 0x00, 0xc2, 0x4f, 0x30, 0x3f, 0xf0, 0x13, 0x42, 0x07, 0x9d, 0xff, 0x40, 0x45, 0x17, 0x0c, 0x08, - 0x3b, 0x8e, 0x95, 0x61, 0xf7, 0xd6, 0x4e, 0x08, 0xe4, 0x9a, 0xd5, 0xec, 0xce, 0xce, 0xee, 0xce, - 0x91, 0x7b, 0x5e, 0x77, 0x13, 0xdc, 0xc5, 0x7c, 0x03, 0x9b, 0x00, 0x79, 0xfe, 0xa1, 0x87, 0xcb, - 0x08, 0x25, 0x51, 0x18, 0xbe, 0x86, 0xbb, 0x5f, 0xf0, 0x39, 0xc5, 0x61, 0x84, 0xdf, 0xf0, 0xa5, - 0xc6, 0x36, 0xc5, 0x95, 0x95, 0xa7, 0xc6, 0xab, 0x23, 0xa1, 0xc5, 0x68, 0xd0, 0x9d, 0x21, 0x27, - 0x5f, 0x87, 0xb2, 0x12, 0x12, 0x49, 0x7a, 0x99, 0xa0, 0x48, 0xd4, 0x53, 0xa1, 0xa6, 0x47, 0xe4, - 0x59, 0x26, 0x4b, 0x1c, 0x90, 0x4f, 0x8e, 0x2b, 0x9c, 0x9a, 0x84, 0x36, 0x57, 0x28, 0x6b, 0x6d, - 0x9f, 0x21, 0x6b, 0x34, 0xd7, 0x60, 0xfa, 0x85, 0x52, 0xe3, 0x48, 0x52, 0x72, 0x07, 0x26, 0x15, - 0x6c, 0x52, 0x9c, 0xba, 0x46, 0xf2, 0x1e, 0x71, 0x03, 0x2d, 0x93, 0x38, 0xfe, 0x8b, 0x2b, 0x2c, - 0xb6, 0x7c, 0x22, 0xf9, 0xdc, 0xd5, 0xbb, 0xac, 0x35, 0x0e, 0xf3, 0x64, 0x78, 0x27, 0x3b, 0x2f, - 0x6d, 0x9f, 0x82, 0x1f, 0x98, 0x33, 0x8c, 0xb7, 0xfb, 0x3e, 0x7a, 0xbb, 0xa7, 0x55, 0xad, 0xdc, - 0xee, 0xa9, 0x7e, 0xdf, 0x7b, 0x42, 0x6b, 0x1e, 0xfc, 0x28, 0xfe, 0xfb, 0xa5, 0x7e, 0x46, 0xa3, - 0xbb, 0xde, 0x4f, 0x21, 0xf8, 0x3b, 0xae, 0x5f, 0x42, 0xef, 0xb7, 0x1a, 0x1d, 0x9f, 0xcb, 0x7b, - 0x9d, 0xb7, 0x98, 0x70, 0xd9, 0xe6, 0x03, 0x57, 0xb7, 0xc1, 0x9d, 0x97, 0xfb, 0x7e, 0x9a, 0x3f, - 0xba, 0x87, 0x04, 0xa2, 0x00, 0x02, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Denied_Circle_32px = { 32, 32, NBGL_BPP_4, true, C_Denied_Circle_32px_bitmap }; - -uint8_t const C_Erase_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x02, 0x48, 0x00, 0x00, 0xf0, 0xf0, 0xaf, 0x01, 0xff, 0x03, 0xef, 0x03, - 0xef, 0x03, 0xef, 0x03, 0xef, 0x03, 0xe5, 0x16, 0x15, 0xe4, 0x34, 0x34, 0xe5, 0x32, 0x35, 0xe6, - 0x66, 0xe7, 0x47, 0xe7, 0x47, 0xe6, 0x66, 0xe5, 0x32, 0x35, 0xe4, 0x34, 0x34, 0xe5, 0x16, 0x15, - 0xef, 0x03, 0xef, 0x03, 0xef, 0x03, 0xef, 0x03, 0xef, 0x03, 0xef, 0x03, 0xff, 0x01, 0xf0, 0x2e, - 0xf0, 0x4c, 0xf0, 0x6a, 0xf0, 0x88, 0xf0, 0xa6, 0xf0, 0xc4, 0xf0, 0xe2, 0xf0, 0xf0, 0xf0, 0x20, -}; -const nbgl_icon_details_t C_Erase_32px = { 32, 32, NBGL_BPP_1, true, C_Erase_32px_bitmap }; - -uint8_t const C_Important_Circle_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x21, 0xf9, 0x00, 0x00, 0xf7, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x6d, 0x91, 0x3f, 0x12, 0xc1, 0x40, 0x14, 0xc6, 0xbf, 0xdd, 0x86, 0x31, - 0x66, 0xec, 0x0d, 0x92, 0x13, 0x50, 0x2a, 0x95, 0x4a, 0xb7, 0xd0, 0x32, 0x43, 0x69, 0x86, 0x52, - 0x61, 0xe4, 0x08, 0xdc, 0xc0, 0x11, 0xa2, 0xa3, 0xcb, 0x1d, 0x54, 0x3a, 0x82, 0x11, 0x24, 0xe3, - 0x79, 0xbb, 0x49, 0x6c, 0xfc, 0xf9, 0x9a, 0xcc, 0xef, 0xed, 0xb7, 0x2f, 0xef, 0x7d, 0x4b, 0xf4, - 0x47, 0xc9, 0x40, 0x89, 0xb6, 0xff, 0xc6, 0x9b, 0x02, 0x4b, 0xce, 0x33, 0xbc, 0x1b, 0xe4, 0xc2, - 0x2a, 0xe5, 0x3e, 0xc4, 0xec, 0x40, 0x1b, 0x17, 0x25, 0x83, 0x57, 0xc8, 0x40, 0x7f, 0x1f, 0x2e, - 0x7a, 0xe9, 0xf1, 0x38, 0xf5, 0x45, 0xc6, 0xf0, 0x40, 0x39, 0xef, 0x3b, 0xc1, 0x82, 0x68, 0x97, - 0x1f, 0x6b, 0x83, 0xc3, 0x45, 0x69, 0xe7, 0x70, 0xd9, 0xea, 0x56, 0x2c, 0xaf, 0x05, 0xc5, 0x68, - 0x58, 0x0e, 0x11, 0x44, 0xf6, 0x3a, 0x0f, 0x8a, 0xf1, 0x05, 0x41, 0x61, 0x0f, 0xb4, 0x42, 0x10, - 0xc5, 0x5d, 0x96, 0x3f, 0xf5, 0xe8, 0x09, 0xe7, 0x08, 0x6d, 0x63, 0x79, 0xa8, 0x11, 0xa1, 0xf6, - 0xcd, 0x21, 0x0e, 0xd6, 0x4f, 0x70, 0xce, 0x9f, 0xfd, 0x3a, 0x11, 0x3c, 0xcb, 0xfc, 0xf3, 0x44, - 0xcf, 0x9c, 0xeb, 0x04, 0x9f, 0x54, 0xd5, 0xf2, 0x52, 0xfe, 0xee, 0x13, 0x16, 0xf7, 0xad, 0x73, - 0x9a, 0xc5, 0x3c, 0x56, 0xbf, 0x79, 0xe9, 0x3c, 0x4d, 0xd0, 0x49, 0x96, 0x27, 0x1b, 0xe4, 0x88, - 0x9e, 0x5b, 0x95, 0xe5, 0xad, 0x83, 0x36, 0x12, 0x8b, 0xac, 0xcf, 0xde, 0x14, 0x84, 0x1d, 0x34, - 0x1e, 0x2a, 0xd1, 0x0c, 0xfe, 0xbd, 0x34, 0xbd, 0x00, 0xf4, 0xd3, 0x6c, 0x41, 0x00, 0x02, 0x00, - 0x00, -}; -const nbgl_icon_details_t C_Important_Circle_32px = { 32, 32, NBGL_BPP_4, true, C_Important_Circle_32px_bitmap }; - -uint8_t const C_Info_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x22, 0x2d, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xc5, - 0x20, 0xc1, 0x70, 0x60, 0x0a, 0xca, 0x20, 0xc1, 0x70, 0x60, 0x0a, 0xca, 0x20, 0xc1, 0x70, 0x60, - 0x0a, 0xca, 0x20, 0xc1, 0x70, 0x60, 0x0a, 0xcf, 0x08, 0x10, 0x08, 0xdc, 0x8a, 0x8c, 0xff, 0xff, - 0xff, 0xff, 0xff, 0xff, 0xd0, -}; -const nbgl_icon_details_t C_Info_32px = { 32, 32, NBGL_BPP_4, true, C_Info_32px_bitmap }; - -uint8_t const C_Maj_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x01, 0x43, 0x00, 0x00, 0x41, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x63, 0x60, 0xc0, 0x03, 0x98, 0x1b, 0x18, 0x18, 0xd8, 0x81, 0x98, 0x1f, - 0x88, 0xe5, 0x81, 0xd8, 0x1e, 0x88, 0xeb, 0xff, 0x1f, 0x60, 0xf8, 0xff, 0xff, 0x01, 0x23, 0x10, - 0x33, 0x43, 0x31, 0x88, 0x0d, 0x12, 0x03, 0xcb, 0xd9, 0x43, 0xd5, 0xf2, 0x43, 0xf5, 0x82, 0xcc, - 0xc0, 0x03, 0x00, 0x1d, 0xbe, 0x6b, 0xd4, 0x80, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Maj_32px = { 32, 32, NBGL_BPP_1, true, C_Maj_32px_bitmap }; - -uint8_t const C_Maj_Lock_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x01, 0x3f, 0x00, 0x00, 0x3d, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x63, 0x60, 0xc0, 0x03, 0xd8, 0x80, 0x98, 0x1f, 0x88, 0xe5, 0x81, 0xd8, - 0x1e, 0x88, 0xeb, 0x81, 0xf8, 0xff, 0xff, 0x02, 0x46, 0x20, 0x66, 0x06, 0x62, 0x76, 0x28, 0x66, - 0x86, 0x8a, 0x81, 0xe4, 0xc0, 0x6a, 0xec, 0xa1, 0x7a, 0xf8, 0xa1, 0x66, 0xe0, 0x01, 0x00, 0x80, - 0xa1, 0x95, 0x6d, 0x80, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Maj_Lock_32px = { 32, 32, NBGL_BPP_1, true, C_Maj_Lock_32px_bitmap }; - -uint8_t const C_Mini_Push_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x22, 0xb4, 0x00, 0x00, 0xcc, 0x5e, 0xd6, 0x2e, 0xc5, 0x2e, 0xd1, 0x1e, - 0xcb, 0x1e, 0xcd, 0x2e, 0xce, 0x1e, 0xca, 0x1e, 0xd1, 0x1e, 0xc8, 0x1e, 0xd4, 0x0e, 0xc6, 0x1e, - 0xd5, 0x1e, 0xc5, 0x0e, 0xd7, 0x1e, 0xc3, 0x0e, 0xd9, 0x0e, 0xc3, 0x0e, 0xd9, 0x0e, 0xc2, 0x0e, - 0xcc, 0x1d, 0xcc, 0x0e, 0xc1, 0x0e, 0xcb, 0x99, 0x10, 0x60, 0xcb, 0x0e, 0xc1, 0x0e, 0xca, 0x0a, - 0x01, 0x10, 0x01, 0x07, 0xca, 0x0e, 0xc1, 0x0e, 0xc9, 0xb9, 0x10, 0x34, 0x00, 0x01, 0x07, 0xca, - 0x2e, 0xc8, 0xb8, 0x10, 0x3c, 0xe0, 0x95, 0x01, 0x60, 0xc9, 0x2e, 0xc7, 0xa9, 0x10, 0x2c, 0xc1, - 0x0e, 0x04, 0x10, 0x06, 0xc8, 0x2e, 0xc6, 0xaa, 0x10, 0x2b, 0xc3, 0xad, 0x40, 0x17, 0xc7, 0x2e, - 0xc5, 0xaa, 0x10, 0x3c, 0xc5, 0xad, 0x40, 0x18, 0xc6, 0x8e, 0xfe, 0xc5, 0x9c, 0x13, 0xc0, 0xc7, - 0x9e, 0x51, 0x90, 0xc6, 0x8e, 0xfe, 0xc6, 0x0d, 0x0c, 0xc9, 0x0e, 0x0b, 0xc6, 0x0e, 0xc1, 0x0e, - 0xdb, 0x0e, 0xc1, 0x0e, 0xdb, 0x0e, 0xc2, 0x0e, 0xd9, 0x0e, 0xc3, 0x1e, 0xd8, 0x0e, 0xc4, 0x0e, - 0xd7, 0x0e, 0xc6, 0x0e, 0xd5, 0x1e, 0xc6, 0x1e, 0xd3, 0x1e, 0xc8, 0x1e, 0xd1, 0x1e, 0xcb, 0x0e, - 0xcf, 0x1e, 0xcd, 0x1e, 0xcb, 0x1e, 0xd1, 0x7e, 0x3e, 0xd7, 0x4e, 0xcc, -}; -const nbgl_icon_details_t C_Mini_Push_32px = { 32, 32, NBGL_BPP_4, true, C_Mini_Push_32px_bitmap }; - -uint8_t const C_Next_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x21, 0x81, 0x00, 0x00, 0x7f, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xe5, 0x8e, 0xbb, 0x0d, 0x80, 0x30, 0x0c, 0x05, 0x2d, 0x68, 0xa2, 0x4c, - 0xc1, 0x04, 0x88, 0x11, 0x33, 0x0a, 0x13, 0x90, 0x11, 0xd8, 0x80, 0x21, 0x28, 0x11, 0x12, 0x7d, - 0x0a, 0x1e, 0xb6, 0xf3, 0xc1, 0xcc, 0x80, 0x8b, 0xc8, 0xa7, 0x3b, 0x59, 0x01, 0x74, 0x8e, 0x05, - 0x76, 0xee, 0xa1, 0xbb, 0x2c, 0xef, 0x44, 0xe3, 0x47, 0x13, 0xd9, 0x80, 0xb5, 0x0d, 0x58, 0x4f, - 0xbd, 0x09, 0x76, 0xf2, 0xc1, 0xcd, 0x2d, 0x60, 0x1d, 0x83, 0x4b, 0x2d, 0x60, 0x8d, 0xe0, 0x50, - 0x03, 0xd1, 0xc2, 0x35, 0x10, 0x2d, 0x5c, 0x02, 0xd5, 0xca, 0x39, 0x48, 0xa2, 0x95, 0x39, 0x58, - 0xe5, 0x8d, 0x95, 0x93, 0xd7, 0x7b, 0xa8, 0x8c, 0xf7, 0xcb, 0x99, 0xf1, 0x5b, 0x3e, 0xb7, 0xb2, - 0x3c, 0xa9, 0x70, 0x9b, 0xe5, 0x00, 0x02, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Next_32px = { 32, 32, NBGL_BPP_4, true, C_Next_32px_bitmap }; - -uint8_t const C_QRCode_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x21, 0x87, 0x00, 0x00, 0x85, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x95, 0x8f, 0xc1, 0x0d, 0x80, 0x20, 0x0c, 0x45, 0x7f, 0x5c, 0x80, 0x15, - 0xdc, 0xc0, 0x35, 0xbd, 0x39, 0x9a, 0xa3, 0x40, 0x3c, 0x79, 0x30, 0x96, 0x02, 0x05, 0x4b, 0xb9, - 0x48, 0x43, 0x52, 0x1e, 0xa1, 0xbf, 0xff, 0x13, 0x4d, 0xd6, 0xbb, 0x02, 0x58, 0x7c, 0x00, 0x1c, - 0xf1, 0xa1, 0x0b, 0xa9, 0xb6, 0xc6, 0x21, 0xb3, 0x53, 0xcc, 0x43, 0xe9, 0xc2, 0xaf, 0x69, 0x3e, - 0xe0, 0xd9, 0xcf, 0x8e, 0x6f, 0x1c, 0x23, 0xf3, 0x58, 0x96, 0xa8, 0xff, 0x15, 0x67, 0x3d, 0xc5, - 0x75, 0x9f, 0x37, 0x7e, 0x0a, 0x7f, 0x7e, 0x0b, 0xff, 0xcc, 0x27, 0xad, 0xe9, 0x49, 0xd3, 0xfb, - 0x60, 0xfc, 0x10, 0x75, 0x7e, 0x25, 0x66, 0xcb, 0x23, 0x31, 0x47, 0xb6, 0xff, 0xad, 0x5e, 0xbf, - 0xcf, 0xfa, 0xb1, 0x7e, 0x27, 0x2b, 0x02, 0x01, 0x38, 0xc0, 0x97, 0x00, 0x02, 0x00, 0x00, -}; -const nbgl_icon_details_t C_QRCode_32px = { 32, 32, NBGL_BPP_4, true, C_QRCode_32px_bitmap }; - -uint8_t const C_Settings_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x21, 0x11, 0x01, 0x00, 0x0f, 0x01, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0xfb, 0xff, 0x1f, 0x0c, 0xde, 0x9e, 0xfb, 0x8f, 0x0c, 0x7e, 0x31, 0x30, - 0xac, 0x47, 0xe6, 0x3f, 0x64, 0x60, 0x90, 0x43, 0xe6, 0x2b, 0x30, 0x29, 0x30, 0xc1, 0xd8, 0xff, - 0x14, 0x5d, 0xdb, 0x18, 0xe4, 0x1e, 0x32, 0x64, 0x24, 0x2b, 0xbd, 0x07, 0xf1, 0x1f, 0x31, 0x00, - 0xc1, 0xfc, 0x9f, 0x20, 0x52, 0x0f, 0xac, 0x16, 0xc8, 0x60, 0xff, 0xff, 0xbf, 0x00, 0x48, 0x81, - 0xf5, 0x28, 0xf0, 0x9c, 0x2c, 0xf5, 0xff, 0xff, 0xff, 0x4b, 0xfa, 0xea, 0x03, 0x8c, 0x20, 0xbe, - 0x01, 0x37, 0xcc, 0xa4, 0x03, 0x2c, 0x20, 0x32, 0x81, 0x0b, 0xc6, 0x9f, 0xc0, 0x0a, 0x22, 0x1b, - 0x80, 0x9a, 0xff, 0x9f, 0xe8, 0x01, 0x12, 0x05, 0x1c, 0x60, 0x79, 0xb6, 0xff, 0xff, 0x0f, 0x31, - 0x30, 0xe8, 0xfc, 0xff, 0x1f, 0xc0, 0x06, 0xb6, 0x8e, 0xe5, 0xff, 0x1f, 0x90, 0x65, 0xe7, 0xff, - 0x3b, 0x00, 0x2d, 0xfc, 0x25, 0xc0, 0x50, 0xff, 0xff, 0x13, 0x83, 0x78, 0x11, 0x83, 0xfe, 0xff, - 0xef, 0x0c, 0x8c, 0xeb, 0x1f, 0x30, 0x48, 0x02, 0x0d, 0x66, 0x7a, 0xff, 0x4f, 0x80, 0xe7, 0xff, - 0xff, 0x89, 0x0c, 0x7c, 0x40, 0x26, 0xc4, 0x48, 0x90, 0x61, 0xff, 0x14, 0x78, 0x2f, 0xa0, 0xf2, - 0x79, 0x20, 0xea, 0x19, 0xdf, 0x03, 0x99, 0x60, 0xf5, 0x50, 0xf3, 0xd4, 0x0b, 0xa1, 0xe6, 0xa1, - 0xdb, 0x07, 0x74, 0x0f, 0x2b, 0xcc, 0x3d, 0x20, 0x97, 0x61, 0xba, 0x37, 0x80, 0x13, 0xe6, 0x9f, - 0x05, 0x60, 0x79, 0x07, 0x1e, 0x18, 0x7f, 0x03, 0x33, 0x88, 0x14, 0xe0, 0xd9, 0x55, 0x06, 0x0a, - 0x8f, 0xf0, 0x39, 0x07, 0x98, 0xb0, 0x85, 0x17, 0x7a, 0x78, 0xfe, 0x53, 0x32, 0x83, 0x84, 0x77, - 0x88, 0xd0, 0x7b, 0x6c, 0xf1, 0x81, 0x2d, 0xbe, 0xd0, 0xe3, 0xf3, 0xff, 0x9b, 0x7b, 0x50, 0x06, - 0x00, 0x17, 0x13, 0x23, 0x7a, 0x00, 0x02, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Settings_32px = { 32, 32, NBGL_BPP_4, true, C_Settings_32px_bitmap }; - -uint8_t const C_Space_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x01, 0x21, 0x00, 0x00, 0x1f, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x63, 0x60, 0xf8, 0xc7, 0xc0, 0x00, 0xc7, 0x7c, 0x74, 0xc2, 0x08, 0x3b, - 0x01, 0xfa, 0xbb, 0x7f, 0xea, 0x80, 0x00, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Space_32px = { 32, 32, NBGL_BPP_1, true, C_Space_32px_bitmap }; - -uint8_t const C_Warning_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x21, 0xc1, 0x00, 0x00, 0xbf, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x65, 0xd1, 0xbd, 0x0a, 0xc2, 0x30, 0x14, 0x05, 0xe0, 0x83, 0x96, 0x1a, - 0x9c, 0x3a, 0x0a, 0x2e, 0x1d, 0x7d, 0x2c, 0x27, 0x67, 0x1f, 0xa1, 0xa3, 0x83, 0xe0, 0xe6, 0x03, - 0x08, 0xce, 0x82, 0x2f, 0x20, 0x88, 0x7b, 0xdf, 0x42, 0xbb, 0x65, 0x71, 0x88, 0x54, 0x38, 0x26, - 0x2d, 0x69, 0xee, 0xb5, 0xd9, 0xbe, 0x43, 0x48, 0xee, 0x0f, 0x29, 0xcf, 0xd1, 0x2a, 0x9e, 0x30, - 0x97, 0xbc, 0x02, 0x46, 0xf0, 0x01, 0x65, 0xcf, 0xc5, 0xd6, 0x28, 0xb2, 0x32, 0x8a, 0xc9, 0x9e, - 0x33, 0x26, 0x3f, 0x81, 0xdc, 0x26, 0x7b, 0x66, 0x5d, 0x25, 0xbd, 0x5d, 0x81, 0xac, 0xe6, 0xe0, - 0xc4, 0xce, 0x82, 0xc1, 0x92, 0xde, 0x9f, 0x02, 0xd3, 0xfa, 0xbb, 0xf3, 0x67, 0xdf, 0x6e, 0x6e, - 0x95, 0x79, 0x63, 0x72, 0xa1, 0x43, 0x28, 0xdd, 0xe1, 0x30, 0x76, 0x5b, 0xfa, 0x40, 0xdc, 0xa7, - 0x0b, 0x41, 0x7a, 0x8f, 0x6c, 0x4a, 0xf5, 0x1f, 0xf9, 0x8a, 0xd5, 0xc6, 0x7a, 0x63, 0x37, 0xb2, - 0x9f, 0x5c, 0xf4, 0x33, 0xea, 0x77, 0x08, 0xd2, 0xbc, 0xfa, 0xa0, 0xd2, 0xf3, 0xb4, 0xc2, 0xbc, - 0x03, 0xab, 0xb5, 0x51, 0xdb, 0xd2, 0xfb, 0x09, 0x81, 0xf9, 0xdb, 0xe7, 0x52, 0x99, 0x67, 0xfb, - 0x03, 0xe2, 0x51, 0xe0, 0xb9, 0x00, 0x02, 0x00, 0x00, -}; -const nbgl_icon_details_t C_Warning_32px = { 32, 32, NBGL_BPP_4, true, C_Warning_32px_bitmap }; - -uint8_t const C_radio_active_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x21, 0x18, 0x01, 0x00, 0x16, 0x01, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x8d, 0x51, 0x3b, 0x4e, 0x03, 0x31, 0x14, 0x9c, 0xfd, 0x90, 0x10, 0x84, - 0x90, 0xeb, 0x20, 0xc1, 0xde, 0x20, 0xdb, 0xd1, 0xa6, 0xa3, 0xe5, 0x06, 0xd0, 0x23, 0x01, 0x12, - 0x74, 0x14, 0xe4, 0x06, 0xe1, 0x06, 0xc0, 0x09, 0x50, 0x1a, 0x28, 0xc9, 0x0d, 0x72, 0x84, 0x40, - 0x43, 0xbb, 0x22, 0x12, 0x10, 0x3e, 0xd9, 0x61, 0x9e, 0xed, 0x45, 0x42, 0xa2, 0xc8, 0x48, 0xd6, - 0xf3, 0x58, 0x7e, 0x33, 0xef, 0x43, 0x2e, 0x81, 0xef, 0x53, 0x97, 0xec, 0x4e, 0x7e, 0xe9, 0x67, - 0x01, 0x21, 0xbd, 0x8d, 0xb4, 0x2e, 0xe1, 0x91, 0x56, 0x81, 0xdf, 0x20, 0x62, 0xd3, 0xd3, 0x2f, - 0x20, 0x39, 0xaf, 0x16, 0x77, 0x7a, 0xf0, 0x19, 0x4f, 0xc0, 0xbe, 0xc5, 0x67, 0x60, 0xcb, 0x62, - 0x81, 0x4e, 0xc8, 0x1b, 0x20, 0x33, 0x71, 0x60, 0x18, 0xf8, 0x87, 0x4f, 0x98, 0xa1, 0x45, 0xce, - 0xfb, 0x99, 0xae, 0x7b, 0xe8, 0x91, 0x63, 0x6c, 0xb0, 0x2e, 0xbc, 0xdb, 0x0b, 0xd6, 0xc9, 0x13, - 0x1c, 0xeb, 0x8f, 0xd0, 0xe3, 0x3b, 0xda, 0x64, 0x1f, 0x0f, 0xbc, 0x36, 0xbe, 0x2a, 0x67, 0x09, - 0x3a, 0x4c, 0xe9, 0x0b, 0xcc, 0x59, 0x23, 0x21, 0x01, 0x3b, 0x86, 0xe6, 0xfe, 0x97, 0x3b, 0x54, - 0xd2, 0x10, 0x32, 0x2e, 0xec, 0x7f, 0x29, 0xbd, 0x81, 0xf1, 0x35, 0xe9, 0xe5, 0xe6, 0x77, 0xd1, - 0xf8, 0xbd, 0x99, 0xdf, 0x18, 0xdb, 0x4d, 0x3d, 0x8f, 0x56, 0xcf, 0x0c, 0x2b, 0x6a, 0xa2, 0xcc, - 0xd5, 0xc4, 0x81, 0xd5, 0xab, 0x7e, 0xae, 0x42, 0x3f, 0xf3, 0x30, 0x80, 0x52, 0x95, 0x79, 0x5c, - 0x22, 0x8d, 0xf3, 0x38, 0xb2, 0xf8, 0x1a, 0xe7, 0xa1, 0x04, 0x1c, 0x4e, 0xeb, 0x7b, 0x07, 0x39, - 0x1b, 0x46, 0xcd, 0x3c, 0xbb, 0x71, 0xde, 0x45, 0xa0, 0x59, 0xf5, 0xff, 0x3e, 0xb4, 0xaf, 0x33, - 0x97, 0xec, 0x4c, 0x96, 0xd9, 0x2c, 0x7f, 0x00, 0xda, 0xde, 0xe9, 0x38, 0x00, 0x02, 0x00, 0x00, -}; -const nbgl_icon_details_t C_radio_active_32px = { 32, 32, NBGL_BPP_4, true, C_radio_active_32px_bitmap }; - -uint8_t const C_radio_inactive_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x21, 0xc1, 0x00, 0x00, 0xbf, 0x00, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x02, 0xff, 0x8d, 0x51, 0xbb, 0x0e, 0xc2, 0x30, 0x0c, 0xfc, 0xff, 0x4f, 0xb8, 0xf0, - 0x9a, 0x33, 0x00, 0x73, 0x25, 0x24, 0xe6, 0x0a, 0x09, 0x66, 0xa6, 0xcc, 0x45, 0x48, 0x9d, 0x09, - 0x4d, 0xdd, 0x38, 0x76, 0x93, 0x2a, 0x08, 0xc4, 0x2d, 0xd1, 0x39, 0x17, 0xdb, 0x77, 0x21, 0xfa, - 0x03, 0xe3, 0xc5, 0x9a, 0x53, 0x5f, 0xa8, 0x45, 0x84, 0xc9, 0x85, 0x06, 0x09, 0x46, 0xe9, 0x03, - 0x8a, 0x83, 0xa8, 0xe3, 0xcd, 0x95, 0xe8, 0x19, 0x0b, 0x8e, 0xb9, 0x07, 0xce, 0x7c, 0x0e, 0xc0, - 0x91, 0x4f, 0x8b, 0x8d, 0xbc, 0xbb, 0x63, 0x25, 0x72, 0x27, 0x3c, 0x00, 0x3d, 0xcb, 0xd7, 0x65, - 0x4e, 0x7c, 0xd0, 0x61, 0x37, 0x73, 0x8f, 0x2d, 0x51, 0x8b, 0xdb, 0xcc, 0x07, 0x96, 0x36, 0xc8, - 0x7b, 0x8d, 0xdc, 0xd0, 0xa2, 0xf8, 0xe0, 0x15, 0xb1, 0xe4, 0xf8, 0xe4, 0xb5, 0xbe, 0xee, 0x57, - 0xcf, 0xeb, 0xc4, 0x05, 0xe3, 0xc5, 0xfb, 0xf8, 0xe4, 0x22, 0xa1, 0xe5, 0xab, 0xb0, 0xf4, 0xe3, - 0x92, 0x8b, 0xec, 0xd7, 0x68, 0x1e, 0xa9, 0xe3, 0x5b, 0xf3, 0x88, 0x01, 0x80, 0xf3, 0xb2, 0xd0, - 0xc9, 0x39, 0xcf, 0xbd, 0xf6, 0xb5, 0x42, 0xf3, 0x9c, 0x20, 0xff, 0xe1, 0xbe, 0xfd, 0xd7, 0x2f, - 0x4c, 0x5a, 0x1c, 0xe5, 0x46, 0x00, 0x02, 0x00, 0x00, -}; -const nbgl_icon_details_t C_radio_inactive_32px = { 32, 32, NBGL_BPP_4, true, C_radio_inactive_32px_bitmap }; - -uint8_t const C_app_boilerplate_32px_bitmap[] = { - 0x20, 0x00, 0x20, 0x00, 0x02, 0x45, 0x00, 0x00, 0xf0, 0xf0, 0xd1, 0xf0, 0xf0, 0x12, 0xf0, 0xf3, - 0xf0, 0xe3, 0xf0, 0xe4, 0xf0, 0xd5, 0xc2, 0xd6, 0x84, 0xe6, 0x56, 0xf7, 0x19, 0xff, 0x01, 0xf0, - 0x1f, 0xff, 0x01, 0xdf, 0x04, 0xaf, 0x06, 0x9f, 0x07, 0xaf, 0x07, 0xcf, 0x06, 0xef, 0x04, 0xf0, - 0x1f, 0x02, 0xf0, 0x2f, 0xf0, 0x2f, 0x01, 0xf0, 0x17, 0x19, 0xf6, 0x57, 0xe5, 0x94, 0xe5, 0xc2, - 0xd4, 0xf0, 0xd3, 0xf0, 0xe2, 0xf0, 0xf2, 0xf0, 0xf1, 0xf0, 0xf0, 0xf0, 0x70, -}; -const nbgl_icon_details_t C_app_boilerplate_32px = { 32, 32, NBGL_BPP_1, true, C_app_boilerplate_32px_bitmap }; - diff --git a/ledger_secure_sdk_sys/src/c/glyphs_stax/glyphs.h b/ledger_secure_sdk_sys/src/c/glyphs_stax/glyphs.h deleted file mode 100644 index 50e28aaa..00000000 --- a/ledger_secure_sdk_sys/src/c/glyphs_stax/glyphs.h +++ /dev/null @@ -1,145 +0,0 @@ -/* Automatically generated by icon2glyph.py */ - -#pragma once - -#include "app_config.h" -#include "nbgl_types.h" - -extern uint8_t const C_app_boilerplate_16px_bitmap[29]; -extern const nbgl_icon_details_t C_app_boilerplate_16px; - -extern uint8_t const C_app_boilerplate_64px_bitmap[187]; -extern const nbgl_icon_details_t C_app_boilerplate_64px; - -extern uint8_t const C_pin_24_bitmap[49]; -extern const nbgl_icon_details_t C_pin_24; - -extern uint8_t const C_quarter_circle_bottom_left_32px_1bpp_bitmap[128]; -extern const nbgl_icon_details_t C_quarter_circle_bottom_left_32px_1bpp; - -extern uint8_t const C_quarter_circle_bottom_left_40px_1bpp_bitmap[200]; -extern const nbgl_icon_details_t C_quarter_circle_bottom_left_40px_1bpp; - -extern uint8_t const C_quarter_circle_bottom_left_44px_1bpp_bitmap[242]; -extern const nbgl_icon_details_t C_quarter_circle_bottom_left_44px_1bpp; - -extern uint8_t const C_quarter_circle_top_left_32px_1bpp_bitmap[128]; -extern const nbgl_icon_details_t C_quarter_circle_top_left_32px_1bpp; - -extern uint8_t const C_quarter_circle_top_left_40px_1bpp_bitmap[200]; -extern const nbgl_icon_details_t C_quarter_circle_top_left_40px_1bpp; - -extern uint8_t const C_quarter_circle_top_left_44px_1bpp_bitmap[242]; -extern const nbgl_icon_details_t C_quarter_circle_top_left_44px_1bpp; - -extern uint8_t const C_quarter_disc_bottom_left_32px_1bpp_bitmap[128]; -extern const nbgl_icon_details_t C_quarter_disc_bottom_left_32px_1bpp; - -extern uint8_t const C_quarter_disc_bottom_left_40px_1bpp_bitmap[200]; -extern const nbgl_icon_details_t C_quarter_disc_bottom_left_40px_1bpp; - -extern uint8_t const C_quarter_disc_bottom_left_44px_1bpp_bitmap[242]; -extern const nbgl_icon_details_t C_quarter_disc_bottom_left_44px_1bpp; - -extern uint8_t const C_quarter_disc_top_left_32px_1bpp_bitmap[128]; -extern const nbgl_icon_details_t C_quarter_disc_top_left_32px_1bpp; - -extern uint8_t const C_quarter_disc_top_left_40px_1bpp_bitmap[200]; -extern const nbgl_icon_details_t C_quarter_disc_top_left_40px_1bpp; - -extern uint8_t const C_quarter_disc_top_left_44px_1bpp_bitmap[242]; -extern const nbgl_icon_details_t C_quarter_disc_top_left_44px_1bpp; - -extern uint8_t const C_round_24px_bitmap[47]; -extern const nbgl_icon_details_t C_round_24px; - -extern uint8_t const C_switch_60_40_bitmap[300]; -extern const nbgl_icon_details_t C_switch_60_40; - -extern uint8_t const C_Check_Circle_64px_bitmap[571]; -extern const nbgl_icon_details_t C_Check_Circle_64px; - -extern uint8_t const C_Denied_Circle_64px_bitmap[568]; -extern const nbgl_icon_details_t C_Denied_Circle_64px; - -extern uint8_t const C_Important_Circle_64px_bitmap[514]; -extern const nbgl_icon_details_t C_Important_Circle_64px; - -extern uint8_t const C_Review_64px_bitmap[219]; -extern const nbgl_icon_details_t C_Review_64px; - -extern uint8_t const C_SecurityShield_64px_bitmap[610]; -extern const nbgl_icon_details_t C_SecurityShield_64px; - -extern uint8_t const C_Warning_64px_bitmap[359]; -extern const nbgl_icon_details_t C_Warning_64px; - -extern uint8_t const C_left_half_64px_bitmap[192]; -extern const nbgl_icon_details_t C_left_half_64px; - -extern uint8_t const C_Back_32px_bitmap[141]; -extern const nbgl_icon_details_t C_Back_32px; - -extern uint8_t const C_Check_32px_bitmap[74]; -extern const nbgl_icon_details_t C_Check_32px; - -extern uint8_t const C_Check_Circle_32px_bitmap[286]; -extern const nbgl_icon_details_t C_Check_Circle_32px; - -extern uint8_t const C_Chevron_32px_bitmap[88]; -extern const nbgl_icon_details_t C_Chevron_32px; - -extern uint8_t const C_Chevron_Back_32px_bitmap[113]; -extern const nbgl_icon_details_t C_Chevron_Back_32px; - -extern uint8_t const C_Chevron_Next_32px_bitmap[113]; -extern const nbgl_icon_details_t C_Chevron_Next_32px; - -extern uint8_t const C_Close_32px_bitmap[112]; -extern const nbgl_icon_details_t C_Close_32px; - -extern uint8_t const C_Denied_Circle_32px_bitmap[280]; -extern const nbgl_icon_details_t C_Denied_Circle_32px; - -extern uint8_t const C_Erase_32px_bitmap[80]; -extern const nbgl_icon_details_t C_Erase_32px; - -extern uint8_t const C_Important_Circle_32px_bitmap[257]; -extern const nbgl_icon_details_t C_Important_Circle_32px; - -extern uint8_t const C_Info_32px_bitmap[53]; -extern const nbgl_icon_details_t C_Info_32px; - -extern uint8_t const C_Maj_32px_bitmap[75]; -extern const nbgl_icon_details_t C_Maj_32px; - -extern uint8_t const C_Maj_Lock_32px_bitmap[71]; -extern const nbgl_icon_details_t C_Maj_Lock_32px; - -extern uint8_t const C_Mini_Push_32px_bitmap[188]; -extern const nbgl_icon_details_t C_Mini_Push_32px; - -extern uint8_t const C_Next_32px_bitmap[137]; -extern const nbgl_icon_details_t C_Next_32px; - -extern uint8_t const C_QRCode_32px_bitmap[143]; -extern const nbgl_icon_details_t C_QRCode_32px; - -extern uint8_t const C_Settings_32px_bitmap[281]; -extern const nbgl_icon_details_t C_Settings_32px; - -extern uint8_t const C_Space_32px_bitmap[41]; -extern const nbgl_icon_details_t C_Space_32px; - -extern uint8_t const C_Warning_32px_bitmap[201]; -extern const nbgl_icon_details_t C_Warning_32px; - -extern uint8_t const C_radio_active_32px_bitmap[288]; -extern const nbgl_icon_details_t C_radio_active_32px; - -extern uint8_t const C_radio_inactive_32px_bitmap[201]; -extern const nbgl_icon_details_t C_radio_inactive_32px; - -extern uint8_t const C_app_boilerplate_32px_bitmap[77]; -extern const nbgl_icon_details_t C_app_boilerplate_32px; - diff --git a/ledger_secure_sdk_sys/src/c/src.c b/ledger_secure_sdk_sys/src/c/src.c index 5542e4d1..5b7c94d0 100644 --- a/ledger_secure_sdk_sys/src/c/src.c +++ b/ledger_secure_sdk_sys/src/c/src.c @@ -14,7 +14,7 @@ bolos_ux_asynch_callback_t G_io_asynch_ux_callback; #endif -extern void sample_main(); +extern void sample_main(int arg0); extern void heap_init(); struct SectionSrc; @@ -62,9 +62,6 @@ void printhex_c(char* str, uint32_t m); "ldr %[result], =" #SYM "(sbrel)\n\t" \ "add %[result], r9, %[result]" \ : [result] "=r" (DST)) -#elif defined(TARGET_NANOS) -# define SYMBOL_SBREL_ADDRESS(DST, SYM) \ - SYMBOL_ABSOLUTE_VALUE(DST, SYM) #else # error "unknown machine" #endif @@ -78,11 +75,7 @@ void link_pass( void* envram_prev, int dst_ram) { -#ifdef TARGET_NANOS - uint32_t buf[16]; -#else uint32_t buf[128]; -#endif typedef typeof(*buf) link_addr_t; @@ -173,10 +166,7 @@ void get_link_time_nvram_values( void** nvram_ptr_p, void** envram_ptr_p) { -#if defined(ST31) - SYMBOL_ABSOLUTE_VALUE(*nvram_ptr_p, _nvram); - SYMBOL_ABSOLUTE_VALUE(*envram_ptr_p, _envram); -#elif defined(ST33) || defined(ST33K1M5) +#if defined(ST33) || defined(ST33K1M5) __asm volatile("ldr %0, =_nvram":"=r"(*nvram_ptr_p)); __asm volatile("ldr %0, =_envram":"=r"(*envram_ptr_p)); #else @@ -253,12 +243,71 @@ void link_pass_nvram( nvm_write(nvram_prev_val_ptr, &nvram_current, sizeof(void*)); } -#ifdef HAVE_CCID - #include "usbd_ccid_if.h" -uint8_t G_io_apdu_buffer[260]; +void c_reset_bss() { + size_t bss_len; + SYMBOL_ABSOLUTE_VALUE(bss_len, _bss_len); + struct SectionDst* bss; + SYMBOL_SBREL_ADDRESS(bss, _bss); + memset(bss, 0, bss_len); +} + +bolos_ux_params_t G_ux_params = {0}; + +void c_boot_std() { + // below is a 'manual' implementation of `io_seproxyhal_init` +#ifdef HAVE_MCU_PROTECT + unsigned char c[4]; + c[0] = SEPROXYHAL_TAG_MCU; + c[1] = 0; + c[2] = 1; + c[3] = SEPROXYHAL_TAG_MCU_TYPE_PROTECT; + io_seproxyhal_spi_send(c, 4); +#endif + + // Warn UX layer of io reset to avoid unwanted pin lock + memset(&G_ux_params, 0, sizeof(G_ux_params)); + G_ux_params.ux_id = BOLOS_UX_IO_RESET; + + // If the app has just been booted from the UX, multiple os_ux calls may be necessary + // to ensure UX layer has take the BOLOS_UX_IO_RESET instruction into account. + for (uint8_t i = 0; i < 2; i++) { + os_ux(&G_ux_params); + if (os_sched_last_status(TASK_BOLOS_UX) == BOLOS_UX_OK) { + break; + } + } + +#ifdef HAVE_BLE + unsigned int plane = G_io_app.plane_mode; +#endif + + memset(&G_io_app, 0, sizeof(G_io_app)); + +#ifdef HAVE_BLE + G_io_app.plane_mode = plane; #endif + G_io_app.apdu_state = APDU_IDLE; + G_io_app.apdu_length = 0; + G_io_app.apdu_media = IO_APDU_MEDIA_NONE; + + G_io_app.ms = 0; + io_usb_hid_init(); + + USB_power(0); + USB_power(1); + +#ifdef HAVE_BLE + memset(&G_io_asynch_ux_callback, 0, sizeof(G_io_asynch_ux_callback)); + BLE_power(1, NULL); +#endif + +#if !defined(HAVE_BOLOS) && defined(HAVE_PENDING_REVIEW_SCREEN) + check_audited_app(); +#endif // !defined(HAVE_BOLOS) && defined(HAVE_PENDING_REVIEW_SCREEN) + heap_init(); +} -int c_main(void) { +int c_main(int arg0) { __asm volatile("cpsie i"); // Update pointers for pic(), only issuing nvm_write() if we actually changed a pointer in the block. @@ -280,12 +329,10 @@ int c_main(void) { __asm volatile("mov %[result],r9" : [result] "=r" (data)); link_pass_ram(data_len, sidata_src, data); - - size_t bss_len; - SYMBOL_ABSOLUTE_VALUE(bss_len, _bss_len); - struct SectionDst* bss; - SYMBOL_SBREL_ADDRESS(bss, _bss); - memset(bss, 0, bss_len); + + // if libcall, does not reset bss as it is shared with the calling app + if (arg0 == 0) + c_reset_bss(); // formerly known as 'os_boot()' try_context_set(NULL); @@ -293,49 +340,10 @@ int c_main(void) { for(;;) { BEGIN_TRY { TRY { - // below is a 'manual' implementation of `io_seproxyhal_init` - #ifdef HAVE_MCU_PROTECT - unsigned char c[4]; - c[0] = SEPROXYHAL_TAG_MCU; - c[1] = 0; - c[2] = 1; - c[3] = SEPROXYHAL_TAG_MCU_TYPE_PROTECT; - io_seproxyhal_spi_send(c, 4); - #endif - - #ifdef HAVE_BLE - unsigned int plane = G_io_app.plane_mode; - #endif - - memset(&G_io_app, 0, sizeof(G_io_app)); - - #ifdef HAVE_BLE - G_io_app.plane_mode = plane; - #endif - G_io_app.apdu_state = APDU_IDLE; - G_io_app.apdu_length = 0; - G_io_app.apdu_media = IO_APDU_MEDIA_NONE; - - G_io_app.ms = 0; - io_usb_hid_init(); - - USB_power(0); - USB_power(1); - #ifdef HAVE_CCID - io_usb_ccid_set_card_inserted(1); - #endif - - #ifdef HAVE_BLE - memset(&G_io_asynch_ux_callback, 0, sizeof(G_io_asynch_ux_callback)); - BLE_power(1, NULL); - #endif - - #if !defined(HAVE_BOLOS) && defined(HAVE_PENDING_REVIEW_SCREEN) - check_audited_app(); - #endif // !defined(HAVE_BOLOS) && defined(HAVE_PENDING_REVIEW_SCREEN) - - heap_init(); - sample_main(); + // if libcall, does not start io and memory allocator + if (arg0 == 0) + c_boot_std(); + sample_main(arg0); } CATCH(EXCEPTION_IO_RESET) { continue; @@ -350,3 +358,15 @@ int c_main(void) { } return 0; } + +#ifdef HAVE_PRINTF +void mcu_usb_prints(const char *str, unsigned int charcount) +{ + unsigned char buf[4]; + buf[0] = SEPROXYHAL_TAG_PRINTF; + buf[1] = charcount >> 8; + buf[2] = charcount; + io_seproxyhal_spi_send(buf, 3); + io_seproxyhal_spi_send((const uint8_t *) str, charcount); +} +#endif \ No newline at end of file diff --git a/ledger_secure_sdk_sys/src/infos.rs b/ledger_secure_sdk_sys/src/infos.rs index 70013478..b327cc3e 100644 --- a/ledger_secure_sdk_sys/src/infos.rs +++ b/ledger_secure_sdk_sys/src/infos.rs @@ -17,7 +17,6 @@ macro_rules! const_cstr { }; } -#[cfg(not(target_os = "nanos"))] const fn const_parse_api_level(x: &str) -> u8 { let a = x.as_bytes(); let mut res = a[0] - b'0'; @@ -32,11 +31,9 @@ const fn const_parse_api_level(x: &str) -> u8 { /// Expose the API_LEVEL #[used] -#[cfg(not(target_os = "nanos"))] static API_LEVEL: u8 = const_parse_api_level(env!("API_LEVEL")); // Store metadata in the ELF file -#[cfg(not(target_os = "nanos"))] const_cstr!(ELF_API_LEVEL, "ledger.api_level", env!("API_LEVEL")); const_cstr!(ELF_TARGET, "ledger.target", env!("TARGET")); @@ -59,3 +56,8 @@ const_cstr!( "ledger.sdk_version", env!("C_SDK_VERSION") ); +const_cstr!( + ELF_C_SDK_GRAPHICS, + "ledger.sdk_graphics", + env!("C_SDK_GRAPHICS") +); diff --git a/ledger_secure_sdk_sys/src/lib.rs b/ledger_secure_sdk_sys/src/lib.rs index 3039f88c..0759acae 100644 --- a/ledger_secure_sdk_sys/src/lib.rs +++ b/ledger_secure_sdk_sys/src/lib.rs @@ -4,7 +4,7 @@ #![allow(non_snake_case)] use core::ffi::c_void; -#[cfg(all(feature = "heap", not(target_os = "nanos")))] +#[cfg(all(feature = "heap"))] use core::mem::MaybeUninit; pub mod buttons; @@ -35,22 +35,22 @@ pub fn pic_rs_mut(x: &mut T) -> &mut T { unsafe { &mut *ptr } } -#[cfg(all(feature = "heap", not(target_os = "nanos")))] +#[cfg(all(feature = "heap"))] use critical_section::RawRestoreState; -#[cfg(all(feature = "heap", not(target_os = "nanos")))] +#[cfg(all(feature = "heap"))] use embedded_alloc::Heap; -#[cfg(all(feature = "heap", not(target_os = "nanos")))] +#[cfg(all(feature = "heap"))] #[global_allocator] static HEAP: Heap = Heap::empty(); -#[cfg(all(feature = "heap", not(target_os = "nanos")))] +#[cfg(all(feature = "heap"))] struct CriticalSection; -#[cfg(all(feature = "heap", not(target_os = "nanos")))] +#[cfg(all(feature = "heap"))] critical_section::set_impl!(CriticalSection); /// Default empty implementation as we don't have concurrency. -#[cfg(all(feature = "heap", not(target_os = "nanos")))] +#[cfg(all(feature = "heap"))] unsafe impl critical_section::Impl for CriticalSection { unsafe fn acquire() -> RawRestoreState {} unsafe fn release(_restore_state: RawRestoreState) {} @@ -61,15 +61,15 @@ unsafe impl critical_section::Impl for CriticalSection { /// The heap is stored in the stack, and has a fixed size. /// This method is called just before [sample_main]. #[no_mangle] -#[cfg(all(feature = "heap", not(target_os = "nanos")))] +#[cfg(all(feature = "heap"))] extern "C" fn heap_init() { // HEAP_SIZE comes from heap_size.rs, which is defined via env var and build.rs static mut HEAP_MEM: [MaybeUninit; HEAP_SIZE] = [MaybeUninit::uninit(); HEAP_SIZE]; - unsafe { HEAP.init(HEAP_MEM.as_ptr() as usize, HEAP_SIZE) } + unsafe { HEAP.init(&raw mut HEAP_MEM as usize, HEAP_SIZE) } } #[no_mangle] -#[cfg(any(not(feature = "heap"), target_os = "nanos"))] +#[cfg(any(not(feature = "heap")))] extern "C" fn heap_init() {} include!(concat!(env!("OUT_DIR"), "/bindings.rs")); diff --git a/ledger_secure_sdk_sys/src/seph.rs b/ledger_secure_sdk_sys/src/seph.rs index b6ed8e75..0a83fcb1 100644 --- a/ledger_secure_sdk_sys/src/seph.rs +++ b/ledger_secure_sdk_sys/src/seph.rs @@ -34,6 +34,17 @@ pub fn send_general_status() { } } +/// Function to ensure a I/O channel is not timeouting waiting +/// for operations after a long time without SEPH packet exchanges +pub fn heartbeat() { + send_general_status(); + let mut spi_buffer = [0u8; 128]; + seph_recv(&mut spi_buffer, 0); + while is_status_sent() { + seph_recv(&mut spi_buffer, 0); + } +} + #[repr(u8)] pub enum SephTags { ScreenDisplayStatus = SEPROXYHAL_TAG_SCREEN_DISPLAY_STATUS as u8, diff --git a/ledger_device_sdk/stax.json b/ledger_secure_sdk_sys/stax.json similarity index 90% rename from ledger_device_sdk/stax.json rename to ledger_secure_sdk_sys/stax.json index c39cd3d0..035c1e11 100644 --- a/ledger_device_sdk/stax.json +++ b/ledger_secure_sdk_sys/stax.json @@ -13,11 +13,11 @@ "panic-strategy": "abort", "pre-link-args": { "ld.lld": [ - "-Tstax_flex_layout.ld", + "-Tstax_layout.ld", "-Tlink.ld" ], "ld": [ - "-Tstax_flex_layout.ld", + "-Tstax_layout.ld", "-Tlink.ld" ] }, diff --git a/ledger_secure_sdk_sys/stax_layout.ld b/ledger_secure_sdk_sys/stax_layout.ld new file mode 100644 index 00000000..9418ef65 --- /dev/null +++ b/ledger_secure_sdk_sys/stax_layout.ld @@ -0,0 +1,10 @@ +MEMORY +{ + FLASH (rx) : ORIGIN = 0xc0de0000, LENGTH = 400K + DATA (r) : ORIGIN = 0xc0de0000, LENGTH = 400K + SRAM (rwx) : ORIGIN = 0xda7a0000, LENGTH = 44K +} + +PAGE_SIZE = 512; +STACK_SIZE = 1500; +END_STACK = ORIGIN(SRAM) + LENGTH(SRAM); \ No newline at end of file diff --git a/rust-toolchain.toml b/rust-toolchain.toml new file mode 100644 index 00000000..a9c14142 --- /dev/null +++ b/rust-toolchain.toml @@ -0,0 +1,2 @@ +[toolchain] +channel = "nightly-2024-12-01" \ No newline at end of file diff --git a/testmacro/README.md b/testmacro/README.md index cc7c0d93..6fd8a94b 100644 --- a/testmacro/README.md +++ b/testmacro/README.md @@ -1,3 +1,4 @@ # testmacro +![Dynamic TOML Badge](https://img.shields.io/badge/dynamic/toml?url=https%3A%2F%2Fraw.githubusercontent.com%2FLedgerHQ%2Fledger-device-rust-sdk%2Frefs%2Fheads%2Fmaster%2Ftestmacro%2FCargo.toml&query=%24.package.version&label=version) A macro inspired from [Writing an OS in Rust](https://os.phil-opp.com/testing/) and [Rust Raspberry OS tutorials](https://github.com/rust-embedded/rust-raspberrypi-OS-tutorials/tree/master/13_integrated_testing) that helps building `#![no_std]` tests in some other projects.