{"id":18542718,"url":"https://github.com/coinbase/ledger-plugin-coinbase-staking","last_synced_at":"2025-10-04T19:45:59.563Z","repository":{"id":259039214,"uuid":"860140894","full_name":"coinbase/ledger-plugin-coinbase-staking","owner":"coinbase","description":"Ethereum Ledger App for Coinbase","archived":false,"fork":false,"pushed_at":"2025-06-12T00:01:41.000Z","size":2391,"stargazers_count":5,"open_issues_count":5,"forks_count":4,"subscribers_count":0,"default_branch":"develop","last_synced_at":"2025-06-12T01:18:57.056Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":"","language":"C","has_issues":false,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/coinbase.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE.md","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2024-09-19T22:35:14.000Z","updated_at":"2025-01-14T14:17:56.000Z","dependencies_parsed_at":"2024-12-16T16:26:29.892Z","dependency_job_id":"61170f34-8db5-4aed-a782-ad2f18f3b8a5","html_url":"https://github.com/coinbase/ledger-plugin-coinbase-staking","commit_stats":null,"previous_names":["coinbase/ledger-plugin-coinbase-staking"],"tags_count":14,"template":false,"template_full_name":null,"purl":"pkg:github/coinbase/ledger-plugin-coinbase-staking","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/coinbase%2Fledger-plugin-coinbase-staking","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/coinbase%2Fledger-plugin-coinbase-staking/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/coinbase%2Fledger-plugin-coinbase-staking/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/coinbase%2Fledger-plugin-coinbase-staking/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/coinbase","download_url":"https://codeload.github.com/coinbase/ledger-plugin-coinbase-staking/tar.gz/refs/heads/develop","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/coinbase%2Fledger-plugin-coinbase-staking/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":278366611,"owners_count":25975091,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-10-04T02:00:05.491Z","response_time":63,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-11-06T20:09:53.916Z","updated_at":"2025-10-04T19:45:59.547Z","avatar_url":"https://github.com/coinbase.png","language":"C","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Badges\n\n[![Code style check](https://github.com/LedgerHQ/app-plugin-kiln/actions/workflows/lint-workflow.yml/badge.svg)](https://github.com/LedgerHQ/app-plugin-kiln/actions/workflows/lint-workflow.yml)\n[![Compilation \u0026 tests](https://github.com/LedgerHQ/app-plugin-kiln/actions/workflows/ci-workflow.yml/badge.svg)](https://github.com/LedgerHQ/app-plugin-kiln/actions/workflows/ci-workflow.yml)\n\n# app-plugin-coinbase\n\nThis plug-in is compatible with Nano S / X devices, it enables to interact in a secure way with the Kiln v2 contracts.\n\n## Prerequisite\n\nClone the plugin to a new folder.\n\n```shell\ngit clone https://github.com/coinbase/ledger-plugin-coinbase-staking.git\n```\n\nThen in the same folder clone two more repositories, which is the plugin-tools and app-ethereum.\n\n```shell\ngit clone https://github.com/LedgerHQ/plugin-tools.git                          # plugin-tools\ngit clone --recurse-submodules https://github.com/LedgerHQ/app-ethereum.git     # app-ethereum\n```\n\n## Documentation\n\n### Plugin codebase\n\nThis plugin follows the structure of a Ledger Ethereum app plugin described [here](https://developers.ledger.com/docs/device-app/develop/code/plugin).\n\nIt receives data from the Ethereum app, processes it and displays (ie \"clearsign\") on the device screen.\n\nAll the plugin code is in the `src` folder.\n\nThe plugin codebase follows the 6 steps of the plugin flow:\n\n1. **initialize** (in `src/handle_init_contract.c`): plugin receives the selector to manage, and init the correct parser initial state for the function (`context-\u003enext_param`).\n2. **provide parameter** (in `src/provide_parameter/handle_provide_parameter.c`): selected parser receives parameters 32 bytes by 32 bytes, and parse them to the correct state.\n3. **finalize** (in `src/handle_finalize.c`): plugin returns the number of screens to display\n4. **provide_token** not used here\n5. **query_contract_id** (in `src/handle_query_contract_id.c`): plugin returns the contract name as the first displayed screen on the device\n6. **query_contract_ui** (in `src/query_contract_ui/handle_query_contract_ui.c`): plugin returns the screens to display on the device, each product has its own file.\n\nOther important files:\n\n- `src/contracts.c` holds all the constant representing contract functions, parameters or known contracts mappings.\n- `src/kiln_plugin.h` is where we define all the parser states and the plugin context structure.\n\n### Plugin context\n\nThe plugin context is defined in `src/kiln_plugin.h` and holds the state of the plugin. It is passed to all the plugin functions.\n\nIt is defined using a union of all the possible parser parameters of the plugin, and a `next_param` field to know which parser state to use next.\n\nThe plugin context is memset to 0 everytime init_contract is called (beginning of a clearsigning flow), so we make sure that the plugin context union is in a clean state before using it in the parsers.\n\n### Provide parameter parsers\n\nThe provide parameter parsers are defined in `src/provide_parameter/` and are called by the `handle_provide_parameter` function.\n\nEach parser is a state machine that receives 32 bytes of data at a time (abi format), and updates the plugin context state accordingly.\n\n### Build\n\nGo to the plugin-tools folder and run the \"./start\" script.\n\n```shell\ncd plugin-tools  # go to plugin folder\n./start.sh       # run the script start.sh\n```\n\nThe script will build a docker image and attach a console.\nWhen the docker image is running go to the \"app-plugin-kiln\" folder and build the \".elf\" files.\n\n```shell\ncd app-plugin-kiln/tests        # go to the tests folder in app-plugin-kiln\n./build_local_test_elfs.sh      # run the script build_local_test_elfs.sh\n```\n\n### Tests\n\nThe tests are in the `tests/src` folder. They are written in javascript and use the `@ledgerhq/hw-app-eth` library to simulate the device.\n\nThe tests are run using the `yarn test` command.\n\nThe output of the tests is a series of screenshots stored in the `tests/snapshots-tmp` folder that are compared to the expected screenshots in the `tests/snapshots` folder. The latter are stored in the git repository to make sure we expect the correct outputs.\n\nTo test the plugin go to the tests folder from the \"app-plugin-kiln/tests\" and run the script \"test\"\n\n```shell\ncd app-plugin-kiln/tests        # go to the tests folder in app-plugin-kiln\nyarn                            # install dependencies\nyarn test                       # run the script test\n```\n\n### Continuous Integration\n\nThe flow processed in [GitHub Actions](https://github.com/features/actions) is the following:\n\n- Code formatting with [clang-format](http://clang.llvm.org/docs/ClangFormat.html)\n- Compilation of the application for Ledger Nano S in [ledger-app-builder](https://github.com/LedgerHQ/ledger-app-builder)\n\n### Supported Smart Contracts\n\nSmart contracts covered by this plugin are:\nks\n| Network | Name | Address |\n| ------- | ----------------------------- | -------------------------------------------- |\n| Mainnet | Coinbase On-Chain v2 Native20 | `0x2e3956e1ee8b44ab826556770f69e3b9ca04a2a7` |\n| Mainnet | Coinbase On-Chain v2 ExitQueue | `0x86358f7b33b599c484e0335b8ee4f7f7f92d8b60` |\n\n## Clearsigning\n\n### KILN ON-CHAIN v2 - Stake\n\nFunction: `stake()`\nClearsigned:\n\n- tx.value\n\n![](/tests/snapshots/nanos_stakev2/00000.png) ![](/tests/snapshots/nanos_stakev2/00001.png) ![](/tests/snapshots/nanos_stakev2/00002.png) ![](/tests/snapshots/nanos_stakev2/00003.png) ![](/tests/snapshots/nanos_stakev2/00004.png) ![](/tests/snapshots/nanos_stakev2/00005.png)\n\n![](/tests/snapshots/nanox_stakev2/00000.png) ![](/tests/snapshots/nanox_stakev2/00001.png) ![](/tests/snapshots/nanox_stakev2/00002.png) ![](/tests/snapshots/nanox_stakev2/00003.png) ![](/tests/snapshots/nanox_stakev2/00004.png) ![](/tests/snapshots/nanox_stakev2/00005.png)\n\n### KILN ON-CHAIN v2 - RequestExit\n\nFunction: `requestExit(uint256 shares)`\nClearsigned:\n\n- none as shares is not 1:1 with ETH value, it would confuse users\n\n![](/tests/snapshots/nanos_requestExitv2/00000.png) ![](/tests/snapshots/nanos_requestExitv2/00001.png) ![](/tests/snapshots/nanos_requestExitv2/00002.png) ![](/tests/snapshots/nanos_requestExitv2/00003.png) ![](/tests/snapshots/nanos_requestExitv2/00004.png) ![](/tests/snapshots/nanos_requestExitv2/00005.png)\n\n![](/tests/snapshots/nanox_requestExitv2/00000.png) ![](/tests/snapshots/nanox_requestExitv2/00001.png) ![](/tests/snapshots/nanox_requestExitv2/00002.png) ![](/tests/snapshots/nanox_requestExitv2/00003.png) ![](/tests/snapshots/nanox_requestExitv2/00004.png) ![](/tests/snapshots/nanox_requestExitv2/00005.png)\n\n### KILN ON-CHAIN v2 - MultiClaim\n\nFunction: `multiClaim(address[] exitQueues, uint256[][] ticketIds, uint32[][] casksIds)`\nClearsigned:\n\n- none as shares is not 1:1 with ETH value, it would confuse users\n\n![](/tests/snapshots/nanos_multiClaimv2/00000.png) ![](/tests/snapshots/nanos_multiClaimv2/00001.png) ![](/tests/snapshots/nanos_multiClaimv2/00002.png) ![](/tests/snapshots/nanos_multiClaimv2/00003.png) ![](/tests/snapshots/nanos_multiClaimv2/00004.png) ![](/tests/snapshots/nanos_multiClaimv2/00005.png)\n\n![](/tests/snapshots/nanox_multiClaimv2/00000.png) ![](/tests/snapshots/nanox_multiClaimv2/00001.png) ![](/tests/snapshots/nanox_multiClaimv2/00002.png) ![](/tests/snapshots/nanox_multiClaimv2/00003.png) ![](/tests/snapshots/nanox_multiClaimv2/00004.png) ![](/tests/snapshots/nanox_multiClaimv2/00005.png)\n\n### KILN ON-CHAIN v2 - Claim\n\nFunction: `claim(uint256[] ticketIds, uint32[] caskIds, uint16 maxClaimDepth)`\nClearsigned:\n\n- none as shares is not 1:1 with ETH value, it would confuse users\n\n![](/tests/snapshots/nanos_claimv2/00000.png) ![](/tests/snapshots/nanos_claimv2/00001.png) ![](/tests/snapshots/nanos_claimv2/00002.png) ![](/tests/snapshots/nanos_claimv2/00003.png) ![](/tests/snapshots/nanos_claimv2/00004.png) ![](/tests/snapshots/nanos_claimv2/00005.png)\n\n![](/tests/snapshots/nanox_claimv2/00000.png) ![](/tests/snapshots/nanox_claimv2/00001.png) ![](/tests/snapshots/nanox_claimv2/00002.png) ![](/tests/snapshots/nanox_claimv2/00003.png) ![](/tests/snapshots/nanox_claimv2/00004.png) ![](/tests/snapshots/nanox_claimv2/00005.png)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fcoinbase%2Fledger-plugin-coinbase-staking","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fcoinbase%2Fledger-plugin-coinbase-staking","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fcoinbase%2Fledger-plugin-coinbase-staking/lists"}