Merge branch 'master' into lp-0005-private-balance-attestation-submission

Bring the branch up to date with the fixed validate-submission workflow.
This commit is contained in:
edenbd1
2026-07-31 23:24:09 +02:00
24 changed files with 847 additions and 273 deletions
+17 -5
View File
@@ -4,8 +4,11 @@
#
# Runtime contract (from validate-submission.yml):
# - Runs on ubuntu-latest (GNU grep / sed / coreutils assumed).
# - `base/` contains the trusted base-branch checkout.
# - `pr/` contains the PR-head checkout, treated as untrusted data only.
# - `base/` contains the trusted base-branch checkout, and is the only
# source for repo-owned files such as the prize specs.
# - `pr/solutions/` contains just the submission markdown the PR changed,
# fetched by path from the API and treated as untrusted data only. The
# fork's working tree is never checked out.
# - Env: PR_TITLE, PR_REPO, BASE_REPO, CHANGED_FILES.
set -euo pipefail
@@ -230,7 +233,9 @@ if $IS_SOLUTION; then
# -------------------------------------------------------------------------
# 3h. Prize exists and is open
# -------------------------------------------------------------------------
PRIZE_FILE="pr/prizes/${PRIZE_ID}.md"
# Read from base/: the prize spec is repo-owned, so the authoritative copy
# is the base branch's, not whatever stale revision the fork branched from.
PRIZE_FILE="base/prizes/${PRIZE_ID}.md"
if [[ ! -f "$PRIZE_FILE" ]]; then
err "Prize \`${PRIZE_ID}\` not found in \`prizes/\`. Check the ID."
else
@@ -261,7 +266,12 @@ if $IS_SOLUTION; then
CLONE_DIR="/tmp/submission-repo"
rm -rf "$CLONE_DIR"
if git clone --depth=1 "$REPO_URL" "$CLONE_DIR" 2>/dev/null; then
# `REPO_URL` is submitter-controlled, so the clone is bounded: no auth
# prompts, no submodules, one shallow branch, and a wall-clock ceiling so
# an oversized or slow repo cannot consume the whole job.
if GIT_TERMINAL_PROMPT=0 timeout "${LP_CLONE_TIMEOUT:-300}" \
git clone --depth=1 --single-branch --no-tags \
--no-recurse-submodules "$REPO_URL" "$CLONE_DIR" 2>/dev/null; then
# 4a. AI workspace artifacts in the external repo
AI_ARTIFACTS=()
@@ -336,7 +346,9 @@ if $IS_SOLUTION; then
# Logos Messaging / Waku integration
if echo "$PRIZE_CONTENT" | grep -qi 'Logos Messaging\|Logos Chat\|Waku'; then
waku_ref=$(grep -ril 'waku\|logos.messaging\|logos.chat' "$CLONE_DIR" \
# Time-bounded: this is the one full-content scan of the clone.
waku_ref=$(timeout "${LP_SCAN_TIMEOUT:-60}" \
grep -ril 'waku\|logos.messaging\|logos.chat' "$CLONE_DIR" \
--include='*.rs' --include='*.go' --include='*.ts' --include='*.js' \
--include='*.toml' --include='*.json' 2>/dev/null | head -1 || true)
if [[ -z "$waku_ref" ]]; then
+29 -9
View File
@@ -2,8 +2,8 @@ name: Validate Submission
# `pull_request_target` is used so the workflow can comment on PRs from forks
# (which is how solutions are submitted). It runs on the base branch with
# write perms; the PR-head checkout is treated as untrusted data only and
# never executed.
# write perms, so the fork's tree is never checked out here: the only
# submission content the validator reads is fetched by path as data.
on:
pull_request_target:
types: [opened, synchronize, reopened, edited]
@@ -26,13 +26,8 @@ jobs:
with:
ref: ${{ github.event.pull_request.base.sha }}
path: base
- name: Checkout PR head (untrusted data, never executed)
uses: actions/checkout@v4
with:
ref: ${{ github.event.pull_request.head.sha }}
repository: ${{ github.event.pull_request.head.repo.full_name }}
path: pr
# Nothing in this job pushes, so the token has no reason to sit in
# base/.git/config for the life of the run.
persist-credentials: false
- name: Get changed files
@@ -52,6 +47,31 @@ jobs:
echo "__LP_EOF__"
} >> "$GITHUB_OUTPUT"
- name: Fetch changed solution files (untrusted data, never executed)
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
REPO: ${{ github.repository }}
HEAD_SHA: ${{ github.event.pull_request.head.sha }}
CHANGED_FILES: ${{ steps.changed.outputs.files }}
run: |
# The validator reads exactly one thing from the PR: the submission
# markdown. Fetching those blobs by path keeps the fork's working
# tree off the runner entirely, so there is nothing here to execute
# and no `allow-unsafe-pr-checkout` opt-in to carry. Paths come from
# the PR files API and are constrained to a single markdown file
# directly under `solutions/`.
mkdir -p pr/solutions
solution_files=$(printf '%s\n' "$CHANGED_FILES" \
| grep -E '^solutions/[A-Za-z0-9._-]+\.md$' || true)
# Unquoted on purpose: the pattern above admits no spaces or globs.
for f in $solution_files; do
if ! gh api -H "Accept: application/vnd.github.raw" \
"/repos/${REPO}/contents/${f}?ref=${HEAD_SHA}" > "pr/${f}"; then
rm -f "pr/${f}"
echo "::warning::Could not fetch ${f} at ${HEAD_SHA}."
fi
done
- name: Run validation
id: validate
env:
+8 -9
View File
@@ -30,17 +30,16 @@ All prizes live in the `[prizes/](prizes/)` directory. Each prize is a markdown
| [LP-0003](prizes/LP-0003.md) | Private Allowlist / Airdrop Distributor | Medium | Open |
| [LP-0004](prizes/LP-0004.md) | Sealed-Bid Auction Using Shielded Balances | Large | Draft |
| [LP-0005](prizes/LP-0005.md) | Private Token Balance Attestation | Large | Open |
| [LP-0006](prizes/LP-0006.md) | Atomic Swap with LEZ (BTC, XMR, ETH) | XL | Draft |
| [LP-0008](prizes/LP-0008.md) | Autonomous AI Module with Wallet, Storage, and Messaging | Large | Open |
| [LP-0009](prizes/LP-0009.md) | Keycard NIP-46 Nostr Signer Proxy | Small | Closed |
| [LP-0010](prizes/LP-0010.md) | Shell dApp Integration Proof of Concept | Small | Closed |
| [LP-0009](prizes/LP-0009.md) | Keycard NIP-46 Nostr Signer Proxy | Small | Closed ([Solution](solutions/LP-0009.md)) |
| [LP-0010](prizes/LP-0010.md) | Shell dApp Integration Proof of Concept | Small | Closed ([Solution](solutions/LP-0010.md)) |
| [LP-0011](prizes/LP-0011.md) | Program development tooling: Rust SDK | Medium | Draft |
| [LP-0012](prizes/LP-0012.md) | Event/Log mechanism | Large | Closed |
| [LP-0013](prizes/LP-0013.md) | Token program improvements (authorities) | Medium | Open |
| [LP-0014](prizes/LP-0014.md) | Token program improvements (ATAs + wallet tooling) | Medium | Closed |
| [LP-0015](prizes/LP-0015.md) | General cross-program calls via tail calls | Large | Closed |
| [LP-0016](prizes/LP-0016.md) | Anonymous Forum with Threshold Moderation | Large | Open |
| [LP-0017](prizes/LP-0017.md) | Whistleblower: document upload and indexing Basecamp app | Medium | Open |
| [LP-0012](prizes/LP-0012.md) | Event/Log mechanism | Large | Closed ([Solution](solutions/LP-0012.md)) |
| [LP-0013](prizes/LP-0013.md) | Token program improvements (authorities) | Medium | Closed ([Solution](solutions/LP-0013.md)) |
| [LP-0014](prizes/LP-0014.md) | Token program improvements (ATAs + wallet tooling) | Medium | Closed |
| [LP-0015](prizes/LP-0015.md) | General cross-program calls via tail calls | Large | Closed |
| [LP-0016](prizes/LP-0016.md) | Anonymous Forum with Threshold Moderation | Large | Closed ([Solution](solutions/LP-0016.md)) |
| [LP-0017](prizes/LP-0017.md) | Whistleblower: document upload and indexing Basecamp app | Medium | Closed ([Solution](solutions/LP-0017.md)) |
### Proposing a New Prize
+12 -11
View File
@@ -1,18 +1,18 @@
# Logos Lambda Prize Program Terms & Conditions
*Last updated: 2 March 2026*
*Last updated: 17 July 2026*
These Terms and Conditions ("Terms") are entered into by and between Logos Collective Association, Baarerstrasse 10, 6300 Zug, Switzerland ("Logos", "we", "us") and any individual or legal entity participating in the λPrize Program, including by submitting any solution or pull request ("Submission") to the λPrize GitHub repository ("you", "Participant") (each a "Party" and together the "Parties").
These Terms and Conditions ("Terms") are entered into by and between Logos Collective Association, Baarerstrasse 10, 6300 Zug, Switzerland ("Logos", "we", "us") and any individual or legal entity participating in the λ Prize Program, including by submitting any solution or pull request ("Submission") to the λ Prize GitHub repository ("you", "Participant") (each a "Party" and together the "Parties").
By making a Submission to λPrize through the relevant λPrize GitHub repositories or relevant platform (and for the purposes of these Terms, it'll be referred to as λPrize Github repository), you acknowledge that you have read, understood, and agree to be bound by these Terms and any applicable Prize specifications.
By making a Submission to λ Prize through the relevant λ Prize GitHub repositories or relevant platform (and for the purposes of these Terms, it'll be referred to as λ Prize Github repository), you acknowledge that you have read, understood, and agree to be bound by these Terms and any applicable Prize specifications.
You can contact us about these Terms in case you have any questions: [legal@free.technology](mailto:legal@free.technology).
## 1. Lambda Prize Overview
Logos supports the development and adoption of decentralised technologies and applications around the Logos technology stack and related ecosystem components through the λPrize Program ("Program" or "λPrize").
Logos supports the development and adoption of decentralised technologies and applications around the Logos technology stack and related ecosystem components through the λ Prize Program ("Program" or "λ Prize").
The Program comprises multiple prizes (each a "Prize"), including but not limited to prizes described in the λPrize GitHub repository. Each Prize is governed by a separate prize specification, which sets out the scope, requirements, success criteria, and prize amount applicable to that Prize.
The Program comprises multiple prizes (each a "Prize"), including but not limited to prizes described in the λ Prize GitHub repository. Each Prize is governed by a separate prize specification, which sets out the scope, requirements, success criteria, and prize amount applicable to that Prize.
The Program is discretionary in nature. Logos retains sole and absolute discretion over the design of the Program, the content and nature of any prize specifications, the evaluation of submissions, the selection (or nonselection) of winners, and the award or nonaward of any Prize. No Participant will have any entitlement to receive a Prize.
@@ -60,7 +60,7 @@ Each Submission shall target only one Prize as defined in the relevant Prize spe
### 5.2 Manner of submissions and deadline
Submissions must be made through λPrize GitHub repository workflow, as indicated in the applicable Prize specification or an alternative platform as communicated by Logos.
Submissions must be made through λ Prize GitHub repository workflow, as indicated in the applicable Prize specification or an alternative platform as communicated by Logos.
Unless stated otherwise, Submissions for the Parallel Society event must be received before the deadline specified in the relevant platform (e.g. Saturday 7 March 2026, 23:59 UTC). Late Submissions will not be considered.
@@ -70,8 +70,9 @@ A valid Submission must satisfy all of Logos' requirements set out in the releva
1. source code hosted in a public repository;
2. a working demo or deployable artefact;
3. adequate technical documentation and any other specified documentation indicated; and
4. any other requirements indicated by Logos.
3. a recorded demo or walkthrough video of the Submission;
4. adequate technical documentation and any other specified documentation indicated; and
5. any other requirements indicated by Logos.
Logos reserves the right to not review any incomplete or partial Submissions or Submissions which do not meet all mandatory requirements in the applicable Prize specification.
@@ -91,7 +92,7 @@ Subject to the licences granted below, Participants retain ownership of the inte
### 6.2 Licence to Logos
By making a Submission, Participants grant Logos and its Affiliates a worldwide, perpetual, irrevocable, nonexclusive, royaltyfree licence (with the right to sublicense) to use, reproduce, display, perform, distribute, adapt, modify, and create derivative works from Participant's Submission and related materials for purposes connected with the Program, the Logos technology stack, and the broader Logos ecosystem, including without limitation for testing, evaluation, promotion, documentation, and demonstration.
By making a Submission, Participants grant Logos and its Affiliates a worldwide, perpetual, irrevocable, nonexclusive, royaltyfree licence (with the right to sublicense) to use, reproduce, display, perform, distribute, adapt, modify, and create derivative works from Participant's Submission and related materials (including any video and audiovisual materials) for purposes connected with the Program, the Logos technology stack, and the broader Logos ecosystem, including without limitation for testing, evaluation, promotion, documentation, demonstration and as the case may be, publishing on any of Logos' or Affiliates' websites, social media profiles or other public channels.
## 7. Evaluation and judging
@@ -127,7 +128,7 @@ Winners are solely responsible for any tax obligations, reporting, or filings ar
## 9. Post-Event continuation
Following the conclusion of any associated hackathon or live event (including the Parallel Society Congress), the λPrize GitHub repository may remain open or be opened for further Submissions from a specified date.
Following the conclusion of any associated hackathon or live event (including the Parallel Society Congress), the λ Prize GitHub repository may remain open or be opened for further Submissions from a specified date.
Unless otherwise specified:
@@ -164,7 +165,7 @@ Logos reserves the right, at any time and in its sole discretion, to:
4. cancel individual Prizes; or
5. cancel, suspend, or modify the Program or any associated event in whole or in part.
Logos will communicate material changes to the Program through the λPrize GitHub repository, or other official channels designated by Logos. Your continued participation in the Program after publication of updated Terms or rules constitutes your acceptance of such updates.
Logos will communicate material changes to the Program through the λ Prize GitHub repository, or other official channels designated by Logos. Your continued participation in the Program after publication of updated Terms or rules constitutes your acceptance of such updates.
All decisions by Logos regarding eligibility, evaluation, and winner selection are final and binding.
+18 -1
View File
@@ -1,5 +1,22 @@
<!-- Don't forget to add/update this prize in the table in README.md -->
---
# Always declare `dependencies:` — use `[]` if there are none.
# A missing field signals the author has not considered deps yet
# (lintable); `[]` signals considered and none. Replace `[]` with
# a list of `{ id, reason }` objects for prizes with hard deps on
# other L-Prizes, RFPs, R&D items, or sample apps, using canonical
# IDs (LP-XXXX, RFP-XXX). This field is parsed by downstream tooling
# (e.g. flywheels.logos.co). Example:
#
# dependencies:
# - id: LP-XXXX
# reason: short reason this prize depends on it
# - id: RFP-XXX
# reason: short reason this prize depends on it
dependencies: []
---
# LP-XXXX: <Title> [status]
**`Status`**:
@@ -96,6 +113,6 @@ The following policies apply to all prizes (see [evaluation policies](../README.
> Links to relevant specs, documentation, APIs, or prior work that participants should know about.
## Potential for Subsequent λPrizes
## Potential for Subsequent λ Prizes
> If this prize targets a specific testnet, codebase version, or external dependency that is expected to change, note here whether a follow-up prize may be opened to cover adaptation to future versions.
+7 -2
View File
@@ -1,3 +1,7 @@
---
dependencies: []
---
# LP-0001: Private NFT Ownership Proof [DRAFT]
**`Status: draft - pending NFT Program readiness`**
@@ -23,7 +27,7 @@ A competitive prize is the right mechanism here because the problem is well-spec
- [ ] The proof can be verified on LEZ without revealing the token ID or the holder's wallet address to the verifier.
- [ ] The system is resistant to proof reuse across contexts — a nullifier or domain-separation mechanism prevents the same proof from being replayed in a different gating context.
- [ ] A reference integration is delivered: a working demo of at least one token-gated action (e.g., allowlist registration or an on-chain vote) using the proof system.
- [ ] At least 5 independent NFT collections are deployed on LEZ testnet with the proof system integrated, each by a distinct team or community outside the submitting team.
- [ ] At least 5 independent NFT collections are deployed on LEZ testnet with the proof system integrated; the deployments must be reproducible and evidence must be provided.
- [ ] Full documentation and a clean public repository are delivered.
### Usability
@@ -80,6 +84,7 @@ Open to any individual or team. Submissions must be original work. Teams must ho
- Public repository containing all circuit code, LEZ program code, and client-side tooling, licensed under MIT or Apache-2.0.
- Deployment of the verifier program on LEZ testnet, with a verified program ID.
- End-to-end demo video in which the builder narrates what they built and why, walks through the architecture and key implementation decisions, and demonstrates proof generation and on-chain verification for at least one token-gating use case. A silent screencast is not sufficient (see [demo requirements](../README.md#evaluation-policies)).
- Reproducible deployment steps and evidence for at least 5 NFT collection deployments on LEZ testnet with the proof system integrated.
- A write-up covering: cryptographic approach, proving system used, Merkle tree construction, nullifier/domain-separation scheme, security assumptions, known limitations, and integration instructions.
- Gas cost benchmarks for on-chain verification.
- GitHub issues open for any problem encountered with Logos technology.
@@ -99,6 +104,6 @@ The following policies apply to all prizes (see [evaluation policies](../README.
- [LEZ Github repository](https://github.com/logos-blockchain/logos-execution-zone)
## Potential for Subsequent λPrizes
## Potential for Subsequent λ Prizes
TBD
+8 -3
View File
@@ -1,3 +1,7 @@
---
dependencies: []
---
# LP-0002: Private M-of-N Multisig [OPEN]
**`Logos Circle: N/A`**
@@ -25,7 +29,7 @@ A competitive prize is the right mechanism because the design space is large: ch
- [ ] A completed execution is unlinkable to any individual member's shielded account.
- [ ] Proof generation runs client-side on a standard laptop.
- [ ] A reference integration is delivered: a working demo of a threshold-gated action (e.g., treasury transfer or parameter change) on LEZ testnet using shielded member accounts.
- [ ] At least 5 distinct multisig instances are created on LEZ testnet by parties outside the submitting team, with at least one proposal submitted, approved by threshold, and executed in each.
- [ ] At least 1 multisig instance is created on LEZ testnet, with at least one proposal submitted, approved by threshold, and executed; the deployment must be reproducible and evidence must be provided.
- [ ] Full documentation and a clean public repository are delivered.
### Usability
@@ -84,6 +88,7 @@ Open to any individual or team. Submissions must be original work. Teams must ho
- Public repository with all circuit code, LEZ program code, and client-side tooling under MIT or Apache-2.0.
- Verifier program deployed on LEZ testnet with a verified program ID.
- End-to-end demo video in which the builder narrates what they built and why, walks through the architecture and key implementation decisions, and demonstrates M-of-N approval and execution using shielded member accounts. A silent screencast is not sufficient (see [demo requirements](../README.md#evaluation-policies)).
- Reproducible deployment steps and evidence for at least 1 multisig instance on LEZ testnet, with at least one proposal submitted, approved by threshold, and executed.
- Write-up covering: threshold proof scheme, nullifier design, LEZ account model compatibility (specifically how the nonce and `program_owner` constraints are handled), security assumptions, known limitations, and integration instructions.
- Proof generation time and on-chain verification gas cost benchmarks.
@@ -107,6 +112,6 @@ The following policies apply to all prizes (see [evaluation policies](../README.
- [MACI — Minimum Anti-Collusion Infrastructure](https://privacy-scaling-explorations.github.io/maci/)
- [Threshold signature schemes (FROST)](https://eprint.iacr.org/2020/852)
## Potential for Subsequent λPrizes
## Potential for Subsequent λ Prizes
This prize targets the current LEZ testnet. Should a future testnet version introduce breaking changes, a subsequent λPrize may be opened to cover the necessary adaptation and redeployment.
This prize targets the current LEZ testnet. Should a future testnet version introduce breaking changes, a subsequent λ Prize may be opened to cover the necessary adaptation and redeployment.
+7 -2
View File
@@ -1,3 +1,7 @@
---
dependencies: []
---
# LP-0003: Private Allowlist / Airdrop Distributor [OPEN]
**`Status: Open`**
@@ -27,7 +31,7 @@ Logos' shielded account model offers a richer design surface than standard EVM e
- [ ] An on-chain observer cannot link a completed claim to any specific address in the eligibility set.
- [ ] The submission documents its full privacy model: what on-chain observers learn, what the distributor learns, at which points in the claim flow identity information is revealed or withheld, and where trade-offs or residual leakage remain. Claims of privacy must be precise — "unlinkable" must be defined relative to a stated threat model.
- [ ] A reference integration is delivered: a working demo of a private airdrop or allowlist gate on LEZ testnet.
- [ ] At least 3 distinct distributions are deployed on LEZ testnet by parties outside the submitting team, with a combined total of at least 30 unique claims completed across them.
- [ ] At least 2 distinct distributions are deployed on LEZ testnet, with a combined total of at least 20 unique claims completed across them; the distributions must be reproducible and evidence must be provided.
- [ ] Full documentation and a clean public repository are delivered.
### Usability
@@ -85,6 +89,7 @@ Open to any individual or team. Submissions must be original work. Teams must ho
- Public repository with all circuit code, LEZ program code, and client-side tooling under MIT or Apache-2.0.
- Program deployed on LEZ testnet with a verified program ID.
- End-to-end demo video in which the builder narrates what they built and why, walks through the architecture and key implementation decisions, and demonstrates a private claim from a shielded account. A silent screencast is not sufficient (see [demo requirements](../README.md#evaluation-policies)).
- Reproducible deployment steps and evidence for at least 2 distinct distributions on LEZ testnet, with a combined total of at least 20 unique claims completed across them.
- Write-up covering: commitment scheme, claim-uniqueness mechanism, privacy model (what on-chain observers and the distributor learn at each stage, stated threat model, and any residual leakage or limitations), LEZ account model compatibility, security assumptions, known limitations, and integration instructions.
- Proof generation time and on-chain verification compute unit benchmarks.
- GitHub issues open for any problem encountered with Logos technology.
@@ -109,6 +114,6 @@ The following policies apply to all prizes (see [evaluation policies](../README.
- [Merkle airdrop reference (public baseline)](https://github.com/Uniswap/merkle-distributor)
- [zk-kit — Merkle tree and nullifier primitives](https://github.com/privacy-scaling-explorations/zk-kit)
## Potential for Subsequent λPrizes
## Potential for Subsequent λ Prizes
Testnet 0.3/0.4 compatibility, mainnet deployment and adoption.
+7 -2
View File
@@ -1,3 +1,7 @@
---
dependencies: []
---
# LP-0004: Sealed-Bid Auction Using Shielded Balances [DRAFT]
**`Status: Draft - pending LEZ timelock feature`**
@@ -25,7 +29,7 @@ A competitive prize is the right mechanism because the design space is large: au
- [ ] Losing bidders receive full refunds to their shielded accounts without the refund amount being linkable to their original bid.
- [ ] At no point during or after the auction can a passive observer determine any losing bidder's maximum offer.
- [ ] A reference integration is delivered: a working demo of a complete auction lifecycle (open → bid → close → winner determined → refunds issued) on LEZ testnet.
- [ ] At least 5 complete auction cycles are run on LEZ testnet, each with a minimum of 3 distinct bidders, at least 3 of those auctions organised by parties outside the submitting team.
- [ ] At least 5 complete auction cycles are run on LEZ testnet, each with a minimum of 3 distinct bidders; the cycles must be reproducible and evidence must be provided.
- [ ] Full documentation and a clean public repository are delivered.
### Usability
@@ -85,6 +89,7 @@ Open to any individual or team. Submissions must be original work. Teams must ho
- Public repository with LEZ program code and client-side tooling under MIT or Apache-2.0.
- Program deployed on LEZ testnet with a verified program ID.
- End-to-end demo video in which the builder narrates what they built and why, walks through the architecture and key implementation decisions, and demonstrates a full auction lifecycle with at least three bidders using shielded accounts. A silent screencast is not sufficient (see [demo requirements](../README.md#evaluation-policies)).
- Reproducible steps and evidence for at least 5 complete auction cycles on LEZ testnet, each with a minimum of 3 distinct bidders.
- Write-up covering: auction format and rationale, how shielded balances are used for escrow, winner determination and refund mechanics, security assumptions (e.g. miner/sequencer front-running), known limitations, and integration instructions.
- Gas cost benchmarks for bid submission, winner determination, and refund issuance.
@@ -107,6 +112,6 @@ The following policies apply to all prizes (see [evaluation policies](../README.
- [Sealed-bid auctions on blockchains — survey](https://eprint.iacr.org/2021/1113)
- [Penumbra DEX — sealed-bid batch auction design](https://protocol.penumbra.zone/main/dex.html)
## Potential for Subsequent λPrizes
## Potential for Subsequent λ Prizes
TBD
+8 -3
View File
@@ -1,3 +1,7 @@
---
dependencies: []
---
# LP-0005: Private Token Balance Attestation [OPEN]
**`Logos Circle: N/A`**
@@ -31,7 +35,7 @@ A competitive prize is the right mechanism because the proving strategy, nullifi
- [ ] The circuit correctly targets the existing LEZ private account commitment format: `SHA256(npk || program_owner || balance || nonce || SHA256(data))`.
- [ ] **On-chain path**: A LEZ verifier program accepts and verifies the proof, gating at least one on-chain action.
- [ ] **Off-chain path**: The proof can be transmitted over Logos Messaging and verified locally by a recipient, demonstrated by a token-gated access flow (e.g., admission to a chat group).
- [ ] At least 3 distinct applications integrate the attestation primitive on LEZ testnet (e.g., a governance gate, a token-gated Logos Messaging group, and a third use case), with at least one built by a party outside the submitting team.
- [ ] A standalone consumer integration demo is included in the submission repository. Any demonstrated, testable path that exercises the attestation primitive is acceptable (e.g., on-chain gating, off-chain verification via Logos Messaging, or another integration the submitter can run and verify).
- [ ] Full documentation and a clean public repository are delivered.
### Usability
@@ -96,6 +100,7 @@ Open to any individual or team. Submissions must be original work. Teams must ho
- Public repository with all circuit code, LEZ verifier program, off-chain verifier library, and client-side tooling under MIT or Apache-2.0.
- Verifier program deployed on LEZ testnet with a verified program ID.
- End-to-end demo video in which the builder narrates what they built and why, walks through the architecture and key implementation decisions, and demonstrates both verification paths. The demo must cover the on-chain path (proof generation and on-chain verification against a threshold) and the off-chain path (proof transmitted over Logos Messaging and verified locally to gate access, e.g., chat group admission). A silent screencast is not sufficient (see [demo requirements](../README.md#evaluation-policies)).
- Standalone consumer integration demo with instructions to run and test the integration.
- Write-up covering: circuit design, commitment format targeting, context-binding approach, both verification paths, privacy guarantees (including what is and is not hidden), security assumptions, known limitations, and integration instructions.
- Proof generation time and on-chain verification gas cost benchmarks.
@@ -119,6 +124,6 @@ The following policies apply to all prizes (see [evaluation policies](../README.
- [Range proofs in ZK circuits](https://docs.circom.io/more-circuits/more-basic-circuits/#range-proof) — background on proving `balance >= N`
- [zk-kit — Merkle tree primitives](https://github.com/privacy-scaling-explorations/zk-kit)
## Potential for Subsequent λPrizes
## Potential for Subsequent λ Prizes
This prize targets the current LEZ testnet. Should a future testnet version introduce breaking changes, a subsequent λPrize may be opened to cover the necessary adaptation and redeployment.
This prize targets the current LEZ testnet. Should a future testnet version introduce breaking changes, a subsequent λ Prize may be opened to cover the necessary adaptation and redeployment.
-202
View File
@@ -1,202 +0,0 @@
<!-- Don't forget to add/update this prize in the table in README.md -->
# LP-0006: Atomic Swap with LEZ [DRAFT]
**`Status: Draft - pending LEZ timelock feature, Logos Delivery module, and Logos Chat module`**
**`Logos Circle: N/A`**
## Overview
The Logos ecosystem already has a working ETHLEZ atomic swap using Hash Time-Locked Contracts ([eth-lez-atomic-swaps](https://github.com/logos-blockchain/eth-lez-atomic-swaps)). This prize is for a unified atomic swap application that supports trustless swaps between LEZ and **all three** of the following chains:
- **Bitcoin** — using Schnorr adaptor signatures and Taproot key-path spends (no custom scripts, swap indistinguishable from a normal payment).
- **Monero** — using Ed25519 adaptor signatures with cross-curve Discrete Log Equality (DLEQ) proofs (the h4sh3d/COMIT protocol, proven on BitcoinMonero mainnet).
- **Ethereum** — using HTLCs or adaptor signatures against an Ethereum RPC endpoint.
The LEZ side is implemented as a Risc0 guest program (Rust) that locks funds contingent on revealing a secret (adaptor secret, hash preimage, or DLEQ proof, depending on the protocol).
The application follows a **maker/taker model**: the maker acts as a liquidity provider, configuring which trading pairs and prices they support. The maker advertises prices over **Logos Delivery**, and maker-taker negotiation happens over **Logos Chat** — no central infrastructure is used. The maker software must support pricing from both a local configuration (e.g., static prices for testing) and an external source (e.g., a REST API), with the specific external integration left to the developer.
> **Note:** This prize is currently in **Draft** status because the following dependencies are not yet available:
> - **LEZ timelock**: LEZ does not yet support on-chain timelocks.
> - **Logos Delivery module**: Required for makers to advertise prices and trading pairs.
> - **Logos Chat module**: Required for maker-taker negotiation and swap coordination.
>
> The prize will open once all three are available.
## Motivation
Enabling trustless swaps between LEZ and widely-held digital assets — without custodians, bridges, or wrapped tokens — is a prerequisite for meaningful DeFi liquidity in the Logos ecosystem. Different chains present different cryptographic challenges:
- **Bitcoin**: HTLCs work but have drawbacks (non-standard script, on-chain preimage links the swap legs, identifiable as an atomic swap). Adaptor signatures solve all three — the Bitcoin transaction is a plain Taproot spend, no preimage appears on-chain, and the two legs are cryptographically unlinked.
- **Monero**: No scripting system, so neither HTLCs nor standard adaptor signatures apply directly. The established solution combines Ed25519 adaptor signatures with cross-curve DLEQ proofs to atomically transfer a Monero spend key share.
- **Ethereum**: The existing ETHLEZ HTLC swap provides a reference, but participants may propose improved approaches (e.g., adaptor signatures, more efficient gas usage).
A competitive prize is the right mechanism because the protocol design, LEZ escrow construction, and cross-chain coordination all admit multiple valid approaches with meaningful trade-offs.
## Security & Reliability Assumptions
The following assumptions underpin the security and reliability of the atomic swap protocol. Submissions must clearly document how their implementation relies on each assumption and what happens if an assumption is violated.
### Security Assumptions
- **Trustlessness**: Neither party trusts the other. The protocol must guarantee that a rational adversary cannot steal funds — either both legs of the swap complete, or both are refunded.
- **No centralised intermediaries**: No trusted third party, relay, or centralised service is involved in swap execution, price discovery, or coordination. All communication uses Logos Delivery and Logos Chat.
- **Cryptographic hardness**: The security of adaptor signatures (Bitcoin), cross-curve DLEQ proofs (Monero), and hash-lock constructions (Ethereum) relies on the hardness of the discrete logarithm problem on secp256k1 and Ed25519. Submissions must state which cryptographic assumptions they depend on.
- **On-chain finality**: Each chain's finality model is assumed to hold. Submissions must document the number of confirmations required on each chain before a swap leg is considered final, and the risk of chain reorganisations.
- **Timelock safety margin**: Timelocks must be set with sufficient margin to account for block time variance, network congestion, and clock drift. Submissions must document their timelock parameter choices and the rationale.
- **Key management**: Private keys and adaptor secrets are assumed to be stored securely on each party's local machine. The protocol's security does not extend to compromised keys.
### Reliability Assumptions
- **Network availability**: Both parties must be online during the active swap window. Submissions must document what happens if a party goes offline mid-swap (expected behaviour: the counterparty can reclaim funds after the timelock expires).
- **Node liveness**: Each party is assumed to have access to a functioning node for each relevant chain (Bitcoin, Monero, Ethereum, LEZ). Submissions must document graceful degradation if a node becomes temporarily unreachable (e.g., retry logic, swap state persistence).
- **Swap state persistence**: The swap coordinator must persist swap state locally so that incomplete swaps can be resumed after a crash or restart. Loss of swap state before the timelock expires must not lead to loss of funds.
- **Concurrent swap isolation**: Multiple in-flight swaps must not interfere with each other. Each swap must maintain independent state, escrow, and timelock tracking.
- **Logos Delivery & Chat availability**: Price advertisements and negotiation messages depend on the Logos Delivery and Logos Chat modules being available. Submissions must document behaviour when these services are temporarily unreachable (e.g., retry, buffering, degraded mode).
## Success Criteria
### Functionality
- [ ] **No central infrastructure**: The application must not depend on any centralised server or service to operate. All communication between maker and taker uses the Logos stack (see below).
- [ ] Trustless swaps between LEZ and **all three chains** (Bitcoin, Monero, Ethereum) can be completed without custodians, bridges, or wrapped tokens. The Ethereum side must use the **Logos Ethereum module** for Ethereum interactions.
- [ ] The swap protocol is appropriate for each chain's capabilities (adaptor signatures for Bitcoin/Taproot, DLEQ proofs for Monero, HTLCs or adaptor signatures for Ethereum).
- [ ] The LEZ escrow program correctly enforces release of funds upon the required proof (adaptor secret, DLEQ proof, or hash preimage) and supports refund after timelock expiry (see [Security & Reliability Assumptions](#security--reliability-assumptions) for timelock details).
- [ ] The two legs of each swap are atomic: either both complete or both refund. There is no state where one party receives funds and the other does not.
- [ ] **Token support on LEZ**: Swaps support both the native LEZ token and custom tokens issued via the LEZ token program, using Associated Token Accounts (ATAs).
- [ ] **Token support on Ethereum**: Swaps support both native ETH and ERC-20 tokens.
- [ ] **Maker/taker model**: The maker operates as a liquidity provider. The maker software allows configuration of supported trading pairs and prices. The maker advertises available pairs and prices over **Logos Delivery** (the Logos storage/data availability layer). Maker-taker negotiation and swap coordination messages are exchanged over **Logos Chat** (the Logos messaging layer).
- [ ] **Maker pricing**: The maker software supports two pricing modes: (1) **local configuration** (static prices set via config file or CLI, useful for testing) and (2) **external price feed** (fetching prices from an external service, e.g., a REST API). The specific external integration is left to the developer, but the architecture must support pluggable price sources.
- [ ] The **maker** is deployable as a **headless service** with all necessary functionality (pair/price configuration, external price feed, liquidity management, swap execution, monitoring) — no GUI required for operation.
- [ ] At least 5 complete swaps are executed per chain on testnets, involving at least 3 distinct counterparty pairs outside the submitting team.
### Usability
- [ ] A **CLI** is provided for both maker and taker roles. The maker CLI covers the full swap lifecycle. The taker CLI may have limited functionality if a GUI is the primary taker interface.
- [ ] A **GUI** (Logos Basecamp app) is provided for both maker and taker roles, with local build instructions, downloadable assets, and loadable in Logos app (Basecamp).
- [ ] A **module/SDK** is provided that can be used to build Logos modules for interacting with the swap system.
- [ ] An **IDL** is provided for the LEZ escrow program(s), using the [SPEL framework](https://github.com/logos-co/spel).
### Reliability
- [ ] **Graceful degradation**: If a chain-specific dependency is unavailable (e.g., no Monero node running, no Ethereum RPC configured), the application must still start and enable functionality for the remaining chains. Unavailable chains are clearly reported to the user.
- [ ] Swap state is persisted locally so that incomplete swaps can be resumed after a crash or restart without loss of funds.
- [ ] Multiple in-flight swaps do not interfere with each other — each swap maintains independent state, escrow, and timelock tracking.
### Performance
- [ ] Document the compute unit (CU) cost of each LEZ escrow operation (lock, release, refund) on LEZ devnet/testnet. Note: LEZ's per-transaction compute budget may change during testnet.
### Supportability
- [ ] The program is deployed and tested on LEZ testnet 0.2.
- [ ] End-to-end integration tests run against a LEZ sequencer (standalone mode) and are included in CI.
- [ ] CI must be green on the default branch.
- [ ] A reference integration is delivered for each chain: working demos of complete swaps on Bitcoin testnet, Monero stagenet, Ethereum Sepolia, and LEZ testnet 0.2.
- [ ] Full documentation and a clean public repository are delivered, including deployment steps, program addresses, and step-by-step instructions for interacting with the program via CLI and Basecamp app. Documentation must include clear **prerequisites for each chain** (e.g., Bitcoin Core node URL, Monero node + wallet RPC URLs, Ethereum Web3 RPC URL, LEZ testnet access) and step-by-step setup instructions for both maker and taker sides.
- [ ] A reproducible end-to-end demo script is provided for each supported chain and works against a real local sequencer with `RISC0_DEV_MODE=0`.
- [ ] Recorded video demos are included in the submission; each recording must show terminal output (including proof generation) to confirm `RISC0_DEV_MODE=0` was active.
## Scope
### In Scope
- Bitcoin-side implementation: adaptor signatures using Schnorr/BIP-340 and Taproot key-path spends, including pre-signing and signature completion logic.
- Monero-side implementation: key share generation, XMR locking to a combined address, spend key reconstruction, wallet sweep, and cross-curve DLEQ proof construction.
- Ethereum-side implementation: HTLC or adaptor signature contracts for ETH↔LEZ and ERC-20↔LEZ swaps, using the **Logos Ethereum module** for Ethereum interactions.
- LEZ escrow program(s) (Rust, Risc0) that lock funds (native token or custom tokens via ATA) contingent on the appropriate cryptographic proof for each chain, with timelock-based refund.
- Maker software: headless-deployable service with pair/price configuration, external price feed integration, liquidity advertisement, and full swap execution.
- Taker software: discovery of maker offers, swap initiation, monitoring, and claim/refund.
- CLI (full functionality for maker, may be limited for taker), GUI (both roles), and module/SDK for programmatic integration.
- Reference integrations on Bitcoin testnet, Monero stagenet, Ethereum Sepolia, and LEZ testnet 0.2, demonstrating complete swaps.
- Documentation covering: protocol design for each chain, LEZ escrow design, cross-chain atomicity argument, timelock handling, security assumptions, and known limitations.
### Out of Scope
- Lightning Network integration or multi-hop/routed swaps.
- Ongoing maintenance or security audits beyond initial delivery. Follow-up prizes may cover testnet 0.3 compatibility, mainnet deployment, and ongoing maintenance — see [Potential for Subsequent λPrizes](#potential-for-subsequent-λprizes).
## Infrastructure & Dependencies
Participants must run or have access to the following infrastructure for all three target chains:
### Bitcoin
- A **Bitcoin Core** full node or access to a Bitcoin testnet node (e.g., running `bitcoind` locally with `testnet=1`).
- A Bitcoin wallet capable of creating and signing Taproot (P2TR) transactions (e.g., Bitcoin Core 22+, or a library like `rust-bitcoin` with Taproot support).
- Familiarity with BIP-340 (Schnorr) and BIP-341 (Taproot).
### Monero
- A **Monero** full node running on stagenet (`monerod --stagenet`), or access to a public stagenet node.
- A **Monero wallet RPC** instance (`monero-wallet-rpc --stagenet`) for programmatic wallet operations.
- Stagenet XMR (available from Monero stagenet faucets).
- Familiarity with Monero's key structure (spend key, view key) and transaction construction.
### Ethereum
- Access to an **Ethereum RPC endpoint** (e.g., a local node via `geth` or `reth`, or a provider such as Infura, Alchemy, or a public Sepolia RPC).
- Sepolia ETH for testnet deployment (available from Sepolia faucets).
- Familiarity with Solidity smart contracts and tooling (Foundry, Hardhat, or similar).
### LEZ (all targets)
- The application must work with **LEZ testnet 0.2**.
- Access to the LEZ testnet and LEZ CLI tooling.
- Rust toolchain and [Risc0](https://dev.risczero.com/) development environment for building LEZ programs.
- Familiarity with the [Logos Execution Zone](https://github.com/logos-blockchain/logos-execution-zone/) architecture and the [eth-lez-atomic-swaps](https://github.com/logos-blockchain/eth-lez-atomic-swaps) reference implementation.
## Prize Structure
- **Total Prize:** $TBD
- **Effort:** XL
## Eligibility
Open to any individual or team. Submissions must be original work. Teams must hold the rights to all submitted code and agree to license it under MIT and Apache-2.0.
## Submission Requirements
- Public repository with Bitcoin, Monero, and Ethereum swap implementations, LEZ escrow program(s), and coordination tooling under MIT or Apache-2.0.
- LEZ escrow program deployed on LEZ testnet 0.2 with a verified program ID.
- **Demo videos** — for **each supported chain** (Bitcoin, Monero, Ethereum), three separate narrated recordings in which the builder explains what they built and why, walks through the architecture and key implementation decisions, and demonstrates a complete end-to-end swap with LEZ. A silent screencast is not sufficient (see [demo requirements](../README.md#evaluation-policies)). Each chain must show:
1. A **happy path** swap: both parties complete the protocol successfully.
2. A **refund/timeout path** swap: one party abandons the protocol and the other recovers their funds via the timelock refund.
3. A **concurrent swap** demo: two or more swaps executing in parallel, demonstrating that the system handles multiple in-flight swaps correctly.
- Write-up covering: protocol design for each chain, LEZ escrow design, cross-chain atomicity argument, timelock handling, security assumptions, known limitations, and integration instructions.
- **FURPS self-assessment** as part of the solution (see [solution template](../solutions/LP-0000.md)).
## Evaluation Process
Submissions are evaluated first-come-first-served against the success criteria. The first submission that satisfies all criteria wins.
Evaluators will independently clone the repository and run the demo script from a clean environment; the script must succeed without modification. Evaluators may also ask technical follow-up questions to verify authorship and understanding of the implementation.
The following policies apply to all prizes (see [evaluation policies](../README.md#evaluation-policies)):
- **Submissions:** each builder (or team) is allowed a maximum of **3 submissions** per prize, with at most **one submission/review per week**.
- **Feedback:** initial evaluation feedback is limited to a pass/fail indication against the success criteria.
## Resources
### General
- [eth-lez-atomic-swaps](https://github.com/logos-blockchain/eth-lez-atomic-swaps) — ETHLEZ HTLC-based swap (reference implementation and LEZ program structure)
- [Logos Execution Zone repo](https://github.com/logos-blockchain/logos-execution-zone/)
- [Risc0 proving system](https://dev.risczero.com/)
### Bitcoin
- [BIP-340: Schnorr signatures for secp256k1](https://github.com/bitcoin/bips/blob/master/bip-0340.mediawiki)
- [BIP-341: Taproot](https://github.com/bitcoin/bips/blob/master/bip-0341.mediawiki)
- [Adaptor signatures — Lloyd Fournier](https://github.com/LLFourn/one-time-vrf/blob/master/main.pdf)
- [Scriptless Scripts — Andrew Poelstra](https://github.com/apoelstra/scriptless-scripts)
- [rust-bitcoin](https://github.com/rust-bitcoin/rust-bitcoin)
- [secp256k1-zkp (adaptor sig support)](https://github.com/BlockstreamResearch/secp256k1-zkp)
### Monero
- [BitcoinMonero Cross-chain Atomic Swap — h4sh3d paper](https://eprint.iacr.org/2020/1126.pdf)
- [comit-network/xmr-btc-swap](https://github.com/comit-network/xmr-btc-swap) — production Monero-Bitcoin implementation
- [comit-network/cross-curve-dleq](https://github.com/comit-network/cross-curve-dleq) — cross-group DLEQ proof library (secp256k1 ↔ Ed25519)
- [Monero-Starknet atomic swap PoC](https://github.com/omarespejel/monero-starknet-atomic-swap) — adapting the protocol to a non-Bitcoin chain
- [curve25519-dalek](https://github.com/dalek-cryptography/curve25519-dalek)
- [secp256kFUN!](https://github.com/LLFourn/secp256kfun)
## Potential for Subsequent λPrizes
- **Testnet 0.3 compatibility**: If LEZ testnet 0.3 introduces breaking changes, a follow-up prize may be opened to update the atomic swap implementation for compatibility.
- **Mainnet deployment**: A subsequent prize may target mainnet deployment of the atomic swap application, with adoption-related success criteria (e.g., volume, number of unique users, liquidity thresholds).
+8 -4
View File
@@ -1,3 +1,7 @@
---
dependencies: []
---
# LP-0008: Autonomous AI Module with Wallet, Storage, and Messaging [OPEN]
**`Logos Circle: N/A`**
@@ -98,7 +102,7 @@ Submissions are not required to implement all of these, but the default skills a
- [ ] Agent-to-agent coordination is A2A-compatible: Agent Cards follow the A2A schema, task interactions follow the A2A task lifecycle, and the implementation is documented as an A2A transport binding over Logos Messaging.
- [ ] Two or more agents can discover each other via Agent Cards, execute a task following the A2A lifecycle, and transfer LEZ payment autonomously, without owner intervention.
- [ ] At least 3 of the illustrative use cases above are demonstrated end-to-end on LEZ testnet.
- [ ] At least 5 agents are deployed on LEZ testnet by parties outside the submitting team, each demonstrating at least one skill autonomously.
- [ ] Three separate agents are deployed on LEZ testnet — one per default skill category (Storage, Messaging, and Blockchain) — each with a demonstrated, reproducible deployment and evidence provided.
- [ ] Full documentation — including the skill interface spec, deployment guide, and owner interaction guide — and a clean public repository are delivered.
### Usability
@@ -156,7 +160,7 @@ Open to any individual or team. Submissions must be original work. Teams must ho
- Public repository with the Logos Core module, CLI, and all default skill implementations under MIT or Apache-2.0.
- Module loadable on LEZ testnet with a documented deployment procedure.
- End-to-end demo video(s) for at least 3 of the illustrative use cases, in which the builder narrates what they built and why, walks through the architecture and key implementation decisions, and demonstrates the full flow. A silent screencast is not sufficient (see [demo requirements](../README.md#evaluation-policies)).
- Evidence of at least 5 third-party agent deployments on LEZ testnet (e.g., linked public activity, attestations, or on-chain records).
- Reproducible deployment steps and evidence for three separate agent deployments on LEZ testnet — one agent per default skill category (Storage, Messaging, and Blockchain).
- Write-up covering: module architecture, skill interface design, spending threshold mechanism, agent-to-agent coordination protocol, security model (what the agent can and cannot do without owner approval), known limitations, and integration instructions.
## Evaluation Process
@@ -179,6 +183,6 @@ The following policies apply to all prizes (see [evaluation policies](../README.
- [LP-0002](LP-0002.md) — Private M-of-N Multisig (relevant for above-threshold approval flows)
- [LP-0005](LP-0005.md) — Private Token Balance Attestation (relevant for token-gated group access by agents)
## Potential for Subsequent λPrizes
## Potential for Subsequent λ Prizes
This prize targets the current LEZ testnet. Should a future testnet version introduce breaking changes, a subsequent λPrize may be opened to cover the necessary adaptation and redeployment.
This prize targets the current LEZ testnet. Should a future testnet version introduce breaking changes, a subsequent λ Prize may be opened to cover the necessary adaptation and redeployment.
+5 -1
View File
@@ -1,3 +1,7 @@
---
dependencies: []
---
# LP-0009: Keycard NIP-46 Nostr Signer Proxy [CLOSED]
**`Logos Circle: N/A`**
@@ -61,6 +65,6 @@ Submissions are evaluated first-come-first-served against the success criteria.
- [nexum-keycard](https://github.com/aspect-build/nexum-keycard) — Rust SDK and CLI
- [keycard-cli](https://github.com/status-im/keycard-cli) — Go CLI (useful as implementation reference)
## Potential for Subsequent λPrizes
## Potential for Subsequent λ Prizes
No follow-up prize is anticipated at this time.
+5 -1
View File
@@ -1,3 +1,7 @@
---
dependencies: []
---
# LP-0010: Shell dApp Integration Proof of Concept [CLOSED]
**`Logos Circle: N/A`**
@@ -81,6 +85,6 @@ Evaluators will independently clone the repository and run the application from
- [BIP-49: Derivation scheme for P2WPKH-nested-in-P2SH](https://github.com/bitcoin/bips/blob/master/bip-0049.mediawiki)
- [BIP-84: Derivation scheme for P2WPKH](https://github.com/bitcoin/bips/blob/master/bip-0084.mediawiki)
## Potential for Subsequent λPrizes
## Potential for Subsequent λ Prizes
No follow-up prize is anticipated at this time.
+5 -1
View File
@@ -1,3 +1,7 @@
---
dependencies: []
---
# LP-0011: Program development tooling: minimal Rust SDK for programs + CPI [DRAFT]
**`Status: Draft - To review with overlap with LEZ framework`**
@@ -132,6 +136,6 @@ The following policies apply to all prizes (see [evaluation policies](../README.
- [LEZ Github repository](https://github.com/logos-blockchain/logos-execution-zone)
## Potential for Subsequent λPrizes
## Potential for Subsequent λ Prizes
TBD
+6 -2
View File
@@ -1,3 +1,7 @@
---
dependencies: []
---
# LP-0012: Event/Log mechanism: Structured events for LEZ program execution [CLOSED]
**`Logos Circle: N/A`**
@@ -134,6 +138,6 @@ The following policies apply to all prizes (see [evaluation policies](../README.
- [LEZ Github repository](https://github.com/logos-blockchain/logos-execution-zone)
## Potential for Subsequent λPrizes
## Potential for Subsequent λ Prizes
This prize targets the current LEZ testnet. Should a future testnet version introduce breaking changes, a subsequent λPrize may be opened to cover the necessary adaptation and redeployment.
This prize targets the current LEZ testnet. Should a future testnet version introduce breaking changes, a subsequent λ Prize may be opened to cover the necessary adaptation and redeployment.
+10 -3
View File
@@ -1,4 +1,11 @@
# LP-0013: Token program improvements: authorities [OPEN]
---
dependencies:
- id: RFP-001
reason: Provides the standardised admin authority library that the
mint authority approval pattern must reuse, per Success Criteria.
---
# LP-0013: Token program improvements: authorities [CLOSED]
**`Logos Circle: N/A`**
## Overview
@@ -94,6 +101,6 @@ The following policies apply to all prizes (see [evaluation policies](../README.
- [Solana - Token Extensions](https://solana.com/docs/tokens/extensions)
- [Solana - Set Authority](https://solana.com/docs/tokens/basics/set-authority)
## Potential for Subsequent λPrizes
## Potential for Subsequent λ Prizes
This prize targets the current LEZ testnet. Should a future testnet version introduce breaking changes, a subsequent λPrize may be opened to cover the necessary adaptation and redeployment.
This prize targets the current LEZ testnet. Should a future testnet version introduce breaking changes, a subsequent λ Prize may be opened to cover the necessary adaptation and redeployment.
+6 -2
View File
@@ -1,3 +1,7 @@
---
dependencies: []
---
# LP-0014: Token program improvements: Associated Token Accounts (ATAs) + wallet tooling [CLOSED]
**`Logos Circle: N/A`**
@@ -74,6 +78,6 @@ By default, submissions are evaluated first-come-first-served against the succes
- [Solana - Token Extensions](https://solana.com/docs/tokens/extensions)
- [Solana - ATA](https://github.com/solana-labs/solana-program-library/blob/master/docs/src/associated-token-account.md)
## Potential for Subsequent λPrizes
## Potential for Subsequent λ Prizes
This prize targets the current LEZ testnet. Should a future testnet version introduce breaking changes, a subsequent λPrize may be opened to cover the necessary adaptation and redeployment.
This prize targets the current LEZ testnet. Should a future testnet version introduce breaking changes, a subsequent λ Prize may be opened to cover the necessary adaptation and redeployment.
+8 -4
View File
@@ -1,9 +1,13 @@
---
dependencies: []
---
# LP-0015: General cross-program calls via tail calls: external vs internal entrypoints + tooling [CLOSED]
**`Status: Closed`**
**`Logos Circle: N/A`**
This prize is closed **without an external λPrize submission**. The work was **delivered by the Logos Execution Zone (LEZ) team** as part of the core runtime and tooling rather than awarded through this competition.
This prize is closed **without an external λ Prize submission**. The work was **delivered by the Logos Execution Zone (LEZ) team** as part of the core runtime and tooling rather than awarded through this competition.
## Overview
This prize is for designing and implementing *general cross-program calls* (call mid-execution, then continue) while keeping *tail calls as the only execution primitive*. The system should let a program tail-call another program, have control return later via another tail call, and then continue execution in an *internal-only function* that cannot be invoked directly by users.
@@ -105,7 +109,7 @@ Open to any individual or team. Submissions must be original work. Teams must ho
## Evaluation Process
**Closed.** This prize is not accepting submissions. The capability was implemented by the **LEZ team**; there is **no external λPrize winner** or `solutions/LP-0015.md` entry.
**Closed.** This prize is not accepting submissions. The capability was implemented by the **LEZ team**; there is **no external λ Prize winner** or `solutions/LP-0015.md` entry.
The success criteria and submission requirements above are **retained as the original specification** of the intended work for historical reference.
@@ -115,6 +119,6 @@ The success criteria and submission requirements above are **retained as the ori
- [Cross Program Invocation](https://solana.com/docs/core/cpi)
- [Tail calls](https://github.com/WebAssembly/tail-call/blob/main/proposals/tail-call/Overview.md)
## Potential for Subsequent λPrizes
## Potential for Subsequent λ Prizes
This prize targets the current LEZ testnet. Should a future testnet version introduce breaking changes, a subsequent λPrize may be opened to cover the necessary adaptation and redeployment.
This prize targets the current LEZ testnet. Should a future testnet version introduce breaking changes, a subsequent λ Prize may be opened to cover the necessary adaptation and redeployment.
+6 -2
View File
@@ -1,6 +1,10 @@
# LP-0016: Anonymous Forum with Threshold Moderation and Membership Revocation [OPEN]
---
dependencies: []
---
**`Status: Open`**
# LP-0016: Anonymous Forum with Threshold Moderation and Membership Revocation [CLOSED]
**`Status: Closed`**
**`Logos Circle: N/A`**
## Overview
+8 -4
View File
@@ -1,6 +1,10 @@
# LP-0017: Whistleblower — censorship-resistant document upload and indexing Basecamp app [OPEN]
---
dependencies: []
---
**`Status: Open`**
# LP-0017: Whistleblower — censorship-resistant document upload and indexing Basecamp app [CLOSED]
**`Status: Closed`**
**`Logos Circle: N/A`**
## Overview
@@ -128,6 +132,6 @@ The following policies apply to all prizes (see [evaluation policies](../README.
- [LP-0008](./LP-0008.md) — Autonomous AI Module (reference for Logos Core module architecture and storage/delivery patterns)
- [LP-0012](./LP-0012.md) — Event/Log mechanism (relevant for on-chain event emission from the registry program)
## Potential for Subsequent λPrizes
## Potential for Subsequent λ Prizes
This prize targets the current LEZ testnet. Should a future testnet version introduce breaking changes, a subsequent λPrize may be opened to cover the necessary adaptation and redeployment. A follow-up prize may extend the app with search and discoverability features built on top of the document-indexing module.
This prize targets the current LEZ testnet. Should a future testnet version introduce breaking changes, a subsequent λ Prize may be opened to cover the necessary adaptation and redeployment. A follow-up prize may extend the app with search and discoverability features built on top of the document-indexing module.
+132
View File
@@ -0,0 +1,132 @@
# Solution: LP-0013 — Token Program Improvements: Authorities
**Submitted by:** bristinWild
## Summary
This submission implements a complete mint authority model for the LEZ Token program. Fungible tokens can now be created with a designated mint authority that can mint additional supply, rotate control to a new key, or permanently revoke minting to fix the supply. A standalone `lez-authority` crate provides the reusable authority primitive as defined in RFP-001.
## Demo Video
Link - https://www.youtube.com/watch?v=Q_uAv7xRD-c
## Repository
- **Repo:** https://github.com/bristinWild/lez-programs (PR: https://github.com/logos-blockchain/lez-programs/pull/125)
- **Fork:** https://github.com/bristinWild/lez-programs
- **Branch:** `solution/lp-0013-authorities`
- **Commit:** `c2d259e`
- **Key files:**
- `lez-authority/src/lib.rs``Authority` type + `Ownable` trait (RFP-001)
- `programs/token/core/src/lib.rs``TokenDefinition::Fungible` with `authority: Authority` field
- `programs/token/src/mint.rs` — authority-gated `Mint` handler (self/external authority)
- `programs/token/src/set_authority.rs``SetAuthority` handler (rotation + revocation)
- `programs/token/src/new_definition.rs``NewFungibleDefinition` with `mint_authority: Option<AccountId>`
- `programs/token/methods/guest/src/bin/token.rs` — guest binary dispatch for all instructions
- `programs/integration_tests/tests/token.rs` — 17 integration tests including full rotation flow
- `scripts/demo-full-flow.sh` — end-to-end demo script
- `scripts/examples/fixed_supply_token.sh` — fixed supply example
- `scripts/examples/variable_supply_token.sh` — variable supply + rotation example
- `docs/LP-0013-README.md` — architecture, CU costs, CLI usage, design docs
- `artifacts/token-idl.json` — regenerated IDL via SPEL framework
## Approach
### Authority Model
`authority: Authority` is embedded directly in `TokenDefinition::Fungible` via the `lez-authority` crate:
- `Authority(Some(key))` — the key holder controls minting and can rotate/revoke
- `Authority(None)` — supply is permanently fixed; minting is rejected deterministically
### `lez-authority` Crate (RFP-001)
A standalone crate with zero dependency on any specific program or `nssa_core`. Provides:
- `Authority(Option<[u8; 32]>)` newtype with `authority()`, `require()`, `rotate()`
- `Ownable` trait with `require_owner`, `transfer_ownership`, `renounce_ownership`
All logic is unit-tested independently (8 tests).
### Instructions
| Instruction | Description |
|---|---|
| `NewFungibleDefinition` | Create token with optional mint authority (`mint_authority: Option<AccountId>`) |
| `Mint` (updated) | Authority-gated — self-authority (empty rest accounts) or external rotated authority (rest account) |
| `SetAuthority` | Rotate to new key (`Some(key)`) or revoke permanently (`None`) |
### Authority Transfer (RFP-001)
The `Mint` and `SetAuthority` instructions support both self/PDA authority and external rotated authority passed as a rest account. After rotation, the new key can actually mint — proven by the `token_rotate_authority_then_new_authority_can_mint` integration test.
### Atomicity
`SetAuthority` only mutates `authority` after all authorization checks pass. Unauthorized calls return before any write — prior authority is preserved. Structural guarantee via `Authority::rotate()`.
## Success Criteria Checklist
- [x] **Variable-size tokens via mint authority**`NewFungibleDefinition` sets authority at init; `Mint` checks it
- [x] **Minting by the authority** — self-authority and external rotated-authority paths both supported and tested
- [x] **Authority rotation and revocation**`SetAuthority` with `Some(new_key)` rotates; with `None` revokes permanently
- [x] **Two example integrations**`scripts/examples/fixed_supply_token.sh` and `scripts/examples/variable_supply_token.sh`
- [x] **Self-sufficient agnostic authority library (RFP-001)**`lez-authority` crate, zero deps on token program or nssa
- [x] **SDK/module** — SPEL IDL + CLI integration; guest binary wired for all instructions
- [x] **IDL**`artifacts/token-idl.json` regenerated via SPEL framework
- [x] **Atomicity** — structural guarantee in `Authority::rotate()`, verified by unit tests
- [x] **Deterministic rejection**`"Mint authority check failed: Revoked"` on every revoked-authority mint attempt
- [x] **CU costs** — measured from LEZ sequencer execution logs on localnet:
`NewFungibleDefinition` ~11ms, `Mint` ~10ms, `SetAuthority` ~8ms (execution time
inside zkVM, measured via sequencer logs with `RISC0_DEV_MODE=1`; this reflects
actual program execution cost independent of proof generation). Full ZK proof
generation takes 310 minutes per tx with `RISC0_DEV_MODE=0` on Apple M-series
hardware. LEZ devnet/testnet deployment pending public sequencer availability.
- [x] **Integration tests** — 17 tests in `programs/integration_tests/tests/token.rs` against live sequencer (standalone mode), including full RFP-001 rotation flow
- [x] **CI green** — 60 unit tests + 17 integration tests passing
- [x] **README**`docs/LP-0013-README.md` with deployment steps, CLI instructions, architecture, error codes
- [x] **Demo script**`scripts/demo-full-flow.sh` — reproducible against local LEZ sequencer with `RISC0_DEV_MODE=0`
- [x] **Recorded video demo** — https://www.youtube.com/watch?v=Q_uAv7xRD-c (narrated, `RISC0_DEV_MODE=0` terminal output visible)
## FURPS Self-Assessment
### Functionality
- `NewFungibleDefinition`: creates fungible token with `mint_authority: Option<AccountId>``Some` = mintable, `None` = fixed supply
- `Mint`: self-authority (definition account is its own authority) or external rotated authority (rest account)
- `SetAuthority`: rotates to `Some(new_key)` or revokes to `None`; authorization check enforces caller identity
- Metadata fungibles carry a real `mint_authority` — intentional and tested
- AMM LP token authority correctly wired to pool PDA — all AMM tests pass unchanged
### Usability
- Single embedded `authority: Authority` field — minimal diff, easy to audit
- `lez-authority` importable by any LEZ program without token program dependency
- `artifacts/token-idl.json` enables full SPEL CLI interaction
- `docs/LP-0013-README.md` documents all flows with CLI examples and CU costs
### Reliability
- Atomicity: `Authority::rotate()` returns `Err` before mutating — no partial writes possible
- 13 dedicated authority unit tests cover all lifecycle cases
- 17 integration tests including full rotation flow at executor level
- All 60 unit tests + 17 integration tests pass
### Performance
- Authority check in `Mint`: single `Option` match — negligible overhead
- `SetAuthority`: single account read + write
- CU costs (LEZ localnet, `RISC0_DEV_MODE=1`): `NewFungibleDefinition` ~11ms, `Mint` ~10ms, `SetAuthority` ~8ms
### Supportability
- Demo script reproducible against local sequencer with `RISC0_DEV_MODE=0`
- `docs/LP-0013-README.md` documents deployment, CLI usage, architecture, error codes
- PR #125 on `logos-blockchain/lez-programs` — rebased onto upstream main
## Supporting Materials
- **PR:** https://github.com/logos-blockchain/lez-programs/pull/125
- **Architecture docs:** `docs/LP-0013-README.md`
- **Authority library:** `lez-authority/src/lib.rs`
- **SetAuthority handler:** `programs/token/src/set_authority.rs`
- **Mint handler:** `programs/token/src/mint.rs`
- **Demo script:** `scripts/demo-full-flow.sh`
- **Example scripts:** `scripts/examples/`
- **Demo video:** https://www.youtube.com/watch?v=Q_uAv7xRD-c
## Terms & Conditions
By submitting this solution, I confirm that I have read and agree to the [Terms & Conditions](../TERMS.md).
+323
View File
@@ -0,0 +1,323 @@
# Solution: LP-0016 — Anonymous Forum with Threshold Moderation and Membership Revocation
**Submitted by:** Davit Maisuradze ([@jeefxM](https://github.com/jeefxM))
## Summary
A complete LP-0016 implementation: a forum-agnostic moderation SDK plus a
reference Logos Basecamp module that drives the full lifecycle (registration
with stake, anonymous posting, N-of-M moderation, K-strike slashing,
retroactive deanonymization). Membership registration and slashing are
**on-chain** on the public LEZ testnet; posting and moderation are **off-chain**
over Waku, the way the protocol is designed (free common path, paid revocation).
- **Anonymous posting** with a Groth16 membership proof (≈5 s per post,
generated and verified off-chain by the local proof-daemon via snarkjs).
- **N-of-M moderation certificates** aggregated off-chain over Waku, with the
daemon enforcing the N threshold before a certificate is emitted.
- **K-strike slashing** via Shamir reconstruction of the member's nullifier
secret; one on-chain tx per slash; the slashed commitment enters the on-chain
revocation set and the published secret lets any verifier reject the member's
future posts.
- **Two parameterized forum instances live on LEZ testnet** under one program ID
(different K and N-of-M), each with register-with-stake on chain.
- **Reference Qt6 GUI** (standalone `ForumApp`; Logos Basecamp module packaging
in progress) built on the SDK's public, forum-agnostic API.
Non-CLI, click-driven: connect → create identity → create forum → register →
post → strike → slash, with a persistent MEMBER REVOKED banner, per-post
✓ valid / ✗ author revoked badges, a Shamir evidence panel that fills in
share-by-share as strikes land, and a chain-evidence panel showing the
registry account, tree root, and on-chain register/slash tx hashes.
## Repository
- **Repo:** https://github.com/jeefxM/LP-0016-Anonymous-forum-with-moderation
- **Branch:** `main`
- **Video Demo:** https://www.youtube.com/watch?v=Q6fMpLB_850
## Approach
Built on top of the Logos stack:
- **LEZ membership_registry program** (`programs/registry-spel/`, SPEL IDL at
`programs/registry-spel/registry-spel.idl.json`) holds the on-chain membership
tree, the revoked commitment set, and a slash verifier that runs inside the
RISC0 zkVM (ark-bn254 `poly_eval` + Ed25519 signature checks). Deployed once;
forum instances are seed-derived `ForumState` PDAs that carry their own
`ForumConfig` (K and N-of-M) — see `docs/deployments.md`.
- **Forum-agnostic SDK** (`sdk/`, `@logos-forum/moderation-sdk`) wraps a local
proof-daemon (Groth16 prover + chain submitter) and a Waku transport
(`@waku/sdk`). The SDK operates on abstract content identifiers and makes no
assumptions about forum structure, satisfying the bounty's
"forum-agnostic library" requirement.
- **ZK membership proof** is a Groth16 circuit (`circuits/`, ADR-010). The
circom + rapidsnark path was chosen over RISC0 for the per-post proof
because membership proof generation needed to fit under the bounty's 10 s
budget on a standard laptop (rapidsnark proves the circuit in ~5 s vs ~55 s
for an equivalent RISC0 STARK — the RISC0 number is measured by
`bench_post_proof` at `RISC0_DEV_MODE=0`, see `docs/cu-costs.md`).
- **Slash via Shamir**: each post envelope embeds a Shamir share of the
member's nullifier secret (degree-(K-1) polynomial, secret evaluates at
x = 0). Moderation certificates bind shares to content identifiers. Once K
certificates exist for a member's nullifier, anyone can reconstruct the
secret and submit a single on-chain slash tx (`/v1/slash/recover`
`submitSlash`). Below K, no information about the secret leaks — the
reconstruction is information-theoretically secure.
- **Basecamp module** (`basecamp/`) is a Qt6 UI module. QML is in
`basecamp/qml/Main.qml`; the C++ backend in `basecamp/src/ForumBackend.cpp`
drives a Node sidecar (`basecamp/sidecar/forum-sidecar.mjs`) via `QProcess`.
The sidecar consumes the same TS SDK that `sdk/tests/lifecycle.mjs` runs, so
the GUI's behaviour follows the proven path. The Basecamp module is built
entirely on the SDK's public, forum-agnostic API and adds no forum-specific
code to the library.
**Why Logos**: censorship resistance for the off-chain moderation record
(Waku is the only viable transport for moderator certificates that cannot be
silently deleted), and trustless enforcement at the point of revocation
(LEZ verifies the cert evidence cryptographically; no centralized
authority can selectively enforce or veto a slash). A centralized
alternative would either trust a server with the moderation record (defeats
auditability) or skip the revocation enforcement (defeats the threshold
moderation guarantee).
**Why not on-chain moderation per-strike**: every strike going on-chain
would impose a per-cert gas cost on moderators. Keeping certificates on
Waku and only the final slash on-chain (one tx per revocation) preserves
the protocol's economic invariant: free common path, paid revocation.
**Where each step runs**:
- **On-chain (LEZ testnet, `testnet.lez.logos.co`)**: forum initialize,
fund-escrow, register-with-stake, and slash. The testnet sequencer EXECUTES
these transactions; it does not produce an inline STARK per tx. The two live
parameterized instances carry on-chain state, register-with-stake, and slash.
The testnet wallet at `~/wallet-testnet` ships preconfigured genesis-funded
accounts (`6iArKUXx…` = 10 000, `7wHg9sb…` = 20 000,
authenticated-transfer-owned → spendable) which fund the escrow via
`auth-transfer 1000 → escrow` per ADR-011.
- **Off-chain (Waku + local proof-daemon)**: anonymous posting (Groth16 prove +
verify via snarkjs), moderation vote signing and certificate aggregation, and
the post-rejection check for revoked members. None of these touch the
sequencer.
- **Real RISC0 STARK**: the only real STARK in this submission is the membership
post-proof guest, benchmarked by `bench_post_proof` at `RISC0_DEV_MODE=0`
(~55 s, prove + verify OK) — see `docs/cu-costs.md` and ADR-002.
- **Local on-chain-logic test**: `crates/lez-runner/tests/staking_lifecycle.rs`
exercises register → post → K certs → slash → revoke through the in-process
V03State engine (it executes the program logic; it does not generate a STARK).
This is the canonical local end-to-end because the LEZ standalone-mode chain
has no runtime funding path (ADR-011 §"The faucet is genesis-only"), so
register-with-stake against a live local sequencer is not possible by design;
the funded path runs on testnet.
**Disclosures (deliberate scope decisions)**:
- **Posting is demonstrated at K = 3 only.** The membership circuit is
parameterized by K (`circuits/membership.circom`, `template Membership(TREE_DEPTH, K)`),
but only one instance is compiled and trusted-set-up: `Membership(16, 3)`
`membership_0.zkey`, and the live daemon runs `CIRCUIT_K=3`.
Each distinct K needs its own circuit compile + trusted setup, so Instance A
(K = 3) demos the full lifecycle including posting + slash, while Instance B
(K = 2) exercises the registry's parameterizability **on-chain** live
(different K and N-of-M, register-with-stake on testnet — see Program ID +
PDAs below) but its **posting** path is not exercised, because the running
daemon's circuit is K = 3. The bounty's two-instance requirement is about
instance *parameters* (`ForumConfig` K and N-of-M, which are fully general
on-chain), not a second compiled circuit. Supporting K = 2 posting is a
recompile + `snarkjs groth16 setup` away, but no K = 2 zkey is shipped today.
- The Basecamp module's moderator coordination is collapsed for the
single-operator demo: the backend holds all N moderator secrets locally
and signs N votes per Strike click. In a real deployment those N keys
live on N different machines and each moderator submits a vote
independently over Waku; the SDK's `aggregateCertificate` accepts
whichever ≥ N-threshold votes arrive first. Code path at
`basecamp/src/ForumBackend.cpp:moderate()` and
`basecamp/sidecar/forum-sidecar.mjs:case "moderate"`.
## Success Criteria Checklist
- [x] **Member can register with a stake and publish anonymous posts;
posts from the same member are unlinkable below the slash threshold.**
Register-with-stake runs on testnet (escrow funded via `auth-transfer`,
per ADR-011); posting runs off-chain with a Groth16 proof carrying an
epoch-derived nullifier (same per (member, epoch), distinct across members),
and each post embeds an independent Shamir share whose x-coordinate is the
strike index — the share alone reveals nothing under K. Exercised by
`sdk/tests/lifecycle.mjs` and the Basecamp GUI. See `docs/protocol.md §3`.
- [x] **Slash retroactively deanonymizes the slashed member's prior posts;
no other member is affected; documented in `docs/protocol.md`.**
See `docs/protocol.md §4` ("Retroactive deanonymization on slash"). The
reconstruction recovers exactly one member's secret; everyone else's
shares remain below K.
- [x] **N-of-M moderators can jointly produce a certificate; fewer cannot.**
The daemon's `/v1/moderation/aggregate` endpoint refuses to emit a
certificate when fewer than N valid votes are supplied. Enforced
client-side in `sdk/src/index.ts:aggregateCertificate`, and re-verified
by the on-chain slash verifier.
- [x] **K certs → slash → revocation, single on-chain tx.**
Demonstrated live on LEZ testnet by the full-lifecycle runner
(`programs/registry-spel/examples/src/bin/testnet_lifecycle.rs`):
3 posts × 3 certs with distinct content IDs → Shamir reconstruction →
one on-chain slash tx → the commitment enters the on-chain revocation set
(verified by reading the state PDA back). Tx hashes in `docs/deployments.md`.
The same flow is exercised locally (no funding required) by
`crates/lez-runner/tests/staking_lifecycle.rs` through the in-process
V03State engine.
- [x] **Slashed commitment is added to the revocation list; subsequent
posts from it are rejected.**
On slash, the reconstructed secret is published on-chain and the commitment
enters the revocation set. Post-rejection is enforced off-chain by the
proof-daemon: `verify_post` calls `post_proof_core::is_revoked_post`
(`crates/proof-daemon/src/proving.rs:252`), which recomputes the published
secret's nullifier `H("null" || secret || epoch)` for the proven epoch and
rejects any post whose nullifier matches — across epochs, so the member
cannot evade by changing epoch. Asserted by the unit test
`post_proof_core` (revoked-member-posts-rejected-across-epochs) and
end-to-end by `sdk/tests/lifecycle.mjs` (re-verifying the same post envelope
after slash returns `valid: false` with a `/revok/i` reason). At the GUI
layer the post sidecar runs `verifyPostProof` before publishing; a revoked
author gets a red ✗ badge and the `Post` button switches to a disabled
"Revoked" state once the GUI detects its own commitment in the revoked set.
- [x] **Parameterizable K and N-of-M per forum instance.**
Two live instances under one program ID — Instance A (K=3, 2-of-3) and
Instance B (K=2, 3-of-4) — share the SPEL `membership_registry` program
but carry distinct `ForumConfig` in their PDAs.
See `docs/deployments.md`.
- [x] **Forum-agnostic moderation library, public API, no forum
assumptions, uses Logos stack off-chain.**
`@logos-forum/moderation-sdk` exports `createIdentity`,
`createForumInstance`, `register`, `createPostProof`, `publishPost`,
`subscribePosts`, `listPosts`, `signModerationVote`, `aggregateCertificate`,
`publishCertificate`, `listCertificatesByNullifier`,
`tryReconstructSlashEvidence`, `submitSlash`, `verifyPostProof`,
`isRevoked`. Operates on `ContentId = Hex32`; the SDK never names a
body or content type.
- [x] **Working Logos Basecamp app built on the library, usable by a
non-technical user.**
`basecamp/` builds a Logos Basecamp UI module (`libforum_plugin.so`,
implementing the `IComponent` interface, IID `com.logos.component.IComponent`,
+ `metadata.json`/`manifest.json`). It is **verified loadable into
LogosBasecamp v0.1.2** via the AppImage's `ui-host` loader (the loader emits
`READY`; load log captured — see the release artifacts). The same QML/backend
also runs standalone as `ForumApp` for builders without Basecamp installed.
The module is built entirely on the SDK's public, forum-agnostic API. The user
sets the moderator count and N-of-M/K thresholds in the UI; the backend
provisions distinct real moderator keypairs (no hardcoded secrets) and shows
their public keys. Every lifecycle action is click-driven; the user never
crafts a tx or runs a CLI command.
- [x] **End-to-end demonstration on LEZ testnet with at least two
independent forum instances using different K and N-of-M.**
Both instances are live on `testnet.lez.logos.co` under a single
`membership_registry` deployment. The state PDAs decode to non-empty
`ForumState` with advanced `tree_root`, distinct `(K, N-of-M)` config,
and an escrow holding the staked balance (independently verifiable via
`wallet account get` against the testnet sequencer):
| | Instance A | Instance B |
|---|---|---|
| (K, N-of-M) | (3, 2-of-3) | (2, 3-of-4) |
| state PDA | `9zHLZn5qpMwaWurrs7DQgYDyF4XnF6EwE4HJfqkrDJ37` | `3gN9jzTbTL6WgxpqMMA5anUM8wavGdMk4isPY6HmX8p1` |
| escrow PDA | `8yiWGFYQ3vAatQfJdpyT6mUBGpTzqRfikF2yDwzNf7B1` | `5XbV2TAjonag397C5PQNuUBU5yd3f9n6SkprqM7LpYxw` |
| lifecycle on chain | register-with-stake → 3 posts → 3 N-of-M certs → **slash** | register-with-stake |
| `tree_root` after register | `ee499d794328661f…` | `c562c3f806c58ab7…` |
| escrow balance | `0` — stake **claimed by the slasher** when the slash executed | `1000` (staked, live) |
| slash | tx `22d391be447aa12c…`; commitment `0ba57a0c92e84302…` is in the on-chain revocation set | not run (the live daemon's circuit is K=3, so Instance B exercises parameterization on chain but not posting/slash) |
Program ID (both):
`4766fcc24cac757ab4c504b3844c354468f4d7fbb7b630957573513c6eb9a30d`,
guest ImageID
`69373bb59ef0468f8f8748229d79f7cf54ca08b954bef983c641dcedd6d91d47`.
Instance A's full on-chain lifecycle (initialize → fund-escrow → register →
moderate → slash → revoke) is demonstrated live on testnet through the Basecamp
sidecar; the drained escrow is the on-chain proof that the slash claimed the
stake. Tx hashes and state read-back are in `docs/deployments.md`.
## FURPS Self-Assessment
### Functionality
Full LP-0016 protocol — register-with-stake (on-chain, testnet), anonymous
posting with Groth16 proofs (off-chain), N-of-M moderation with off-chain
certificates over Waku, K-strike Shamir reconstruction, and on-chain slash that
revokes membership and claims stake. The Basecamp module surfaces the entire
flow as click-driven actions. Two parameterized instances confirmed on chain.
### Usability
- The Basecamp app is the only thing a forum user needs. No CLI, no tx
crafting. Each lifecycle action is a single click; the GUI shows
busy state, success toasts, and a persistent error line below the
feed.
- Per-post visual state surfaces protocol semantics: green ✓ valid pill
for posts that verify, red ✗ author revoked pill for posts whose
author has been slashed.
- A Shamir-evidence panel fills in one share-pill per strike, so the
cryptographic story (K shares accumulate → secret recoverable) is
visible without reading code.
- A chain-evidence panel exposes the on-chain registry account, tree
root, and most recent register / slash tx hashes for independent
verification.
### Reliability
- Proof generation failures bubble as typed `ForumError` from the SDK;
the GUI shows the daemon's error message verbatim and re-enables the
button so the user can retry without consuming the nullifier (the
nullifier is deterministic from `(secret, epoch)`, so retry is safe).
- The SDK's `aggregateCertificate` enforces the N threshold client-side
before any on-chain submission — a partial certificate cannot reach
the chain.
- A durable outbox retries failed Waku publishes with exponential backoff. A
publish that fails is persisted to disk (not dropped); the `flush-outbox`
sidecar command retries pending items and removes each on success. Retries are
idempotent because the nullifier and content id are deterministic (a duplicate
publish is a protocol no-op). See `basecamp/sidecar/forum-sidecar.mjs`
(`durablePublish` / `flush-outbox`).
### Performance
- Groth16 membership proof generation ≈ 5 s on the dev box
(target: < 10 s). See `docs/cu-costs.md`.
- On-chain register CU cost and slash CU cost documented in
`docs/cu-costs.md`.
### Supportability
- `docs/protocol.md` covers system model, primitives, unlinkability +
anonymity set, retroactive deanonymization on slash, revocation
mechanism, moderator trust model, threat model, known limitations.
- `docs/deployments.md` documents the live stack (Hetzner build host
with `RISC0_DEV_MODE=0` sequencer + nwaku + proof-daemon), the
deployed program ID, both instance PDAs, and tx hashes for each
lifecycle step.
- `docs/cu-costs.md` measures CU cost for every on-chain operation and
the real RISC0 STARK timing (`bench_post_proof`, `RISC0_DEV_MODE=0`).
- `docs/adr/` ADRs capture key implementation decisions (Groth16 vs
RISC0 for membership; share-binding scheme; SPEL port; ATA model).
- CI (`.github/workflows/ci.yml`) runs `cargo fmt`/`clippy`/`test` on the
LEZ-independent crates plus the SDK build and unit tests. The full
Waku + sequencer end-to-end (`sdk/tests/lifecycle.mjs`) needs a live
LEZ sequencer + nwaku and runs on the build host, not in GitHub-hosted CI.
- `basecamp/README.md` documents how to build the `.lgx` and load it
into Basecamp, plus how to run the standalone `ForumApp` preview.
## Supporting Materials
- **Video demo (narrated, full lifecycle, both instances)**: https://www.youtube.com/watch?v=Q6fMpLB_850
- **Live deployment** (Hetzner): see `docs/deployments.md`.
- **Architecture decisions**: `docs/adr/`.
- **Test suite**: `sdk/tests/lifecycle.mjs` (full protocol, build host) and the
crate unit tests run in CI.
## Terms & Conditions
By submitting this solution, I confirm that I have read and agree to
the [Terms & Conditions](../TERMS.md).
+204
View File
@@ -0,0 +1,204 @@
# Solution: LP-0017 — Whistleblower: censorship-resistant document upload and indexing
**Submitted by:** aegonmyy
## Summary
Whistleblower is a complete censorship-resistant document publishing pipeline on
the Logos stack, delivered as **two Logos Basecamp modules** plus a
**permissionless batch-anchor daemon**. A user picks a file; the app uploads it to
**Logos Storage** (obtaining a CID), broadcasts a metadata envelope over **Logos
Delivery** so the document is immediately discoverable, and can optionally anchor
the CID on-chain. Long-term anchoring is decoupled from publication: a standalone
CLI lets any altruistic third party gather broadcast CIDs and commit up to 50 per
transaction to a **LEZ SPEL registry program** — no coordination with the original
publisher, and the anchorer can be an anonymous `Private/` account so the index is
public while the publisher's identity is not. The upload → broadcast → anchor logic
is extracted into a reusable `logos-chronicle` module with a documented API.
## Repository
- **Repo:** https://github.com/aegonmyy/logoz
- **Branch / commit:** `main` @ `365273d`
- **v0.2.0 port branch:** [`port/v0.2.0`](https://github.com/aegonmyy/logoz/tree/port/v0.2.0)
- **Key paths:**
- `logos-chronicle/` — reusable Logos module: upload, broadcast, anchor, publish pipeline (the extracted document-indexing module)
- `logos-whistleblower/` — Logos Basecamp view plugin: QML desktop UI (file picker, publish status, history, anchor config)
- `chronicle-registry/` — SPEL registry program (`chronicle_registry_core` shared types, `methods/guest` RISC0 guest, `ffi/` C-ABI shim, `idl/` IDL)
- `batch-anchor/` — permissionless Waku-listener → dedup → batch-anchor CLI/daemon
- `scripts/demo.sh` — reproducible end-to-end demo against a real local sequencer at `RISC0_DEV_MODE=0`
- `scripts/bench-cu.sh` — CU benchmark harness (fresh-registry, dev-mode-off)
- `.github/workflows/ci.yml` — CI (fmt / build+test / publish smoke / on-chain anchor e2e)
## Approach
### Pipeline & module extraction
The core `upload → broadcast → anchor` logic lives in **`logos-chronicle`**, a
self-contained Logos module with a documented JSON API (`uploadFileJson`,
`uploadStatusJson`, `publishFileJson`, broadcast + anchor calls). The Whistleblower
Basecamp app (`logos-whistleblower`) is a thin QML view plugin on top of it, so any
other Logos app can reuse the pipeline without depending on the Whistleblower UI —
which is exactly what the prize's "standalone document-indexing module" asks for.
### On-chain registry — LEZ SPEL program (chosen approach)
We chose a **LEZ program via the SPEL framework** over direct zone-SDK consensus
inscription. Justification: the zone SDK path currently requires a single
designated actor to perform consensus inscription (decentralised zone sequencers
are not yet shipped), which reintroduces a trust bottleneck — the exact
centralisation Whistleblower exists to avoid. A LEZ program keeps anchoring
permissionless and verifiable by anyone. The registry stores
`(cid, metadata_hash, anchor_timestamp, anchored_by, version)` per document, is
queryable by CID, and `index_batch` accepts up to **50 CIDs per transaction**
(`MAX_BATCH = 50`, ≥ the required 10). An IDL is provided.
### Privacy-preserving anchoring
Because the anchorer can be a `Private/` account, the `index_batch` transaction
routes through the LEZ proving path and the on-chain `anchored_by` is an anonymous
key — the document index stays publicly verifiable while the whistleblower's
identity is not revealed.
### Metadata hash & envelope
`metadata_hash = v1:<sha-256-hex>` over alphabetically-sorted canonical JSON of the
envelope fields, stored on-chain and embedded in every Waku envelope
(`v`, `cid`, `title`, `description`, `content_type`, `size_bytes`, `timestamp`,
`tags`, `metadata_hash`) on topic `/chronicle/1/document-index/json`, so any node
can verify document integrity without fetching from Storage.
### Why the Logos stack
Whistleblower needs exactly what a centralised alternative cannot provide:
**Logos Storage** stores bytes durably without identifying the uploader; **Logos
Delivery** propagates the CID peer-to-peer so a document is findable the instant
it is published, with no index server to seize or block; and **LEZ** provides
trustless, permissionless on-chain anchoring with first-class private state so
anchoring never doxxes the publisher. On a centralised host, any one of the host,
the index, or the payment rail is a single point of censorship — the whole reason
the app exists.
### What was tried and did not work (documented as upstream issues)
- `spel program-id` requires a pre-built R0BF `ProgramBinary`, not a raw ELF, and
the format is undocumented — worked around with `tools/mk_program_binary.rs`
([spel#240](https://github.com/logos-co/spel/issues/240)).
- `lgs localnet start` hardcodes a pre-reorg LEZ config path and cannot start a
sequencer for recent `lez` pins; `scripts/demo.sh` applies a config-path bridge
automatically ([scaffold#230](https://github.com/logos-co/scaffold/issues/230)).
- Funding a fresh localnet account (`auth-transfer init`
`ClaimedUnauthorizedAccount` for non-genesis accounts) is undocumented
([scaffold#232](https://github.com/logos-co/scaffold/issues/232)).
- Also filed: [spel#241](https://github.com/logos-co/spel/issues/241),
[scaffold#231](https://github.com/logos-co/scaffold/issues/231).
## Success Criteria Checklist
### Functionality
- [x] **Upload** — app uploads a selected file to Logos Storage and obtains a CID (`logos-chronicle` → Codex). Verified by `nix run .#smoke-storage`.
- [x] **Broadcast** — a metadata envelope (`cid`, `title`, `description`, `content_type`, `size_bytes`, `timestamp`, `tags`, plus `metadata_hash`) is published to `/chronicle/1/document-index/json` immediately after upload. Verified by `nix run .#smoke-broadcast`.
- [x] **On-chain anchoring** — an explicit "anchor on-chain" action distinct from the basic upload flow, invocable at any time after upload.
- [x] **Batch anchor tool**`batch-anchor` subscribes to the Delivery topic, accumulates `(CID, metadata_hash)` tuples, submits them in a single batch tx, is permissionless (no publisher coordination), and is idempotent (re-submitting an already-registered CID does not fail).
- [x] **On-chain registry** — LEZ SPEL program (approach chosen + justified above); stores `(cid, metadata_hash, anchor_timestamp)` (plus `anchored_by`, `version`), queryable by CID, accepts batches up to 50 CIDs/tx.
- [x] **Document-indexing module**`logos-chronicle`, self-contained with a documented API, reusable independently of the Whistleblower app.
### Usability
- [x] **Basecamp GUI**`logos-whistleblower` QML app with local build instructions and a prebuilt `.lgx` asset, loadable in Logos Basecamp.
- [x] **Module as library/SDK**`logos-chronicle` shipped with a README covering its API and integration steps.
- [x] **IDL for the LEZ program** — provided (SPEL framework).
### Reliability
- [x] **Upload retries** on transient Storage failures with exponential back-off, surfacing a clear error after exhausting retries.
- [x] **Broadcast dedup** — re-broadcasting the same CID does not create duplicate entries for subscribers (dedup by `(CID, metadata_hash)`).
- [x] **Batch-anchor resume** — on start the tool catches up from the Waku store and skips already-registered CIDs, so it resumes after a network interruption without re-processing. Publish and anchor ledgers persist across daemon restarts (verified by `nix run .#smoke-publish`).
### Performance
- [x] **CU benchmarks** measured on a real local rc5 sequencer at `RISC0_DEV_MODE=0` (full Groth16), fresh registry per batch via `scripts/bench-cu.sh`:
| Operation | Batch size | CU (R0VM cycles) |
|-----------|-----------|------------------|
| `init_registry` | — | 414 |
| `index_batch` | 1 CID | 2,816 |
| `index_batch` | 50 CIDs (`MAX_BATCH`) | 213,348 |
### Supportability
- [x] **Registry deployed & tested on LEZ testnet** — deployed and exercised end-to-end on the live **Testnet v0.2.0** (`https://testnet.lez.logos.co`, LEZ `v0.2.0` / commit `a58fbce2`) at `RISC0_DEV_MODE=0`: program `96ad78fe…`, registry PDA `HvCtoPL6…` (reproducing the documented IDs exactly), a CID anchored via a **real Groth16 proof** (`index_batch` tx `02d8781403…`, confirmed on-chain and independently verified via `wallet chain-info transaction`), and `lookup` confirms it (a bogus CID is not-registered). Full evidence + reproduction steps: [`docs/testnet-v020-live-evidence-20260702.md`](https://github.com/aegonmyy/logoz/blob/main/docs/testnet-v020-live-evidence-20260702.md).
- [x] **E2E integration tests in CI** — upload → broadcast → batch anchor run against a LEZ sequencer in standalone mode in CI (`publish` + `anchor` jobs).
- [x] **CI green on default branch**`main` CI completed successfully on the code baseline (fmt, build+test, publish smoke, on-chain anchor e2e); `365273d` changes only docs (README + testnet evidence), no code or workflow files.
- [x] **README** — covers build steps, deployment addresses, running the Basecamp app, running the batch anchor tool, and querying the registry.
- [x] **Reproducible demo at `RISC0_DEV_MODE=0`**`scripts/demo.sh` runs the full pipeline against a real local sequencer with real Groth16 proofs; verified end-to-end on a clean run.
- [x] **Narrated video demo** showing terminal output incl. proof generation at `RISC0_DEV_MODE=0` — https://youtu.be/JY-joCR_2ag
> **Testnet note.** On-chain evidence was originally captured on the **rc5** testnet,
> which was wiped and replaced by **Testnet v0.2.0** mid-submission. The hosted
> testnet is **now live again at the `v0.2.0` tag**, and the registry has been
> **re-deployed and re-anchored there** (see the Supportability evidence above): the
> program ID `96ad78fe…` and PDA `HvCtoPL6…` reproduce the documented values exactly,
> and a CID was anchored with a real Groth16 proof (`index_batch` tx `02d8781403…`,
> confirmed on-chain). This was done by talking to the hosted sequencer directly with
> a `v0.2.0`-final wallet plus the `batch-anchor` CLI — the released `lgs` *localnet*
> tooling still lags v0.2.0's on-disk layout ([scaffold#230](https://github.com/logos-co/scaffold/issues/230)), but that only affects local bring-up, not testnet
> interaction. The earlier rc5 records (tx `f14e39c9…`) are no longer queryable on the
> current network but are retained as the original run record; the program is
> reproducible from source (`make build`), and a clean code port is on `port/v0.2.0`.
## FURPS Self-Assessment
### Functionality
Full upload → broadcast → anchor pipeline; explicit optional on-chain anchor;
permissionless idempotent batch-anchor CLI (dedup, Waku store catch-up, resume);
LEZ SPEL registry (`init_registry`, `index_batch` up to 50 CIDs/tx) queryable by
CID; privacy-preserving anchoring via `Private/` anchorer; reusable
`logos-chronicle` module. Enforced limits: 100 MB max file size, envelope size
cap, source filename never reaches Storage (title-derived staging).
### Usability
QML Basecamp app with file picker, publish status, history, and anchor-config
dialog; prebuilt `.lgx` plus local build instructions. `logos-chronicle` exposes a
small JSON API and ships as a reusable module with a README. IDL provided for the
SPEL program. `scripts/setup.sh` one-shot bootstrap and `scripts/run-app.sh` launch.
### Reliability
Exponential-backoff upload retries with a clear terminal error; broadcast dedup by
`(CID, metadata_hash)`; batch-anchor catches up from the Waku store and skips
already-registered CIDs on restart; publish and anchor ledgers persist across
daemon restarts (verified by a restart assertion in `smoke-publish`). 16/16
batch-anchor unit tests pass.
### Performance
`init_registry` = 414 CU; `index_batch` n=1 = 2,816 CU; n=50 = 213,348 CU
(fresh registry, `RISC0_DEV_MODE=0`). CU is the guest execution-cycle delta logged
at execution time, independent of dev-mode. Because the guest borsh-serialises the
whole registry per call, per-call CU grows with stored entries — documented, with a
fresh-registry harness (`bench-cu.sh`) to isolate the batch cost.
### Reliability / Supportability
CI runs four jobs (fmt; build + 16 tests; `publish` smoke against a live nwaku
node; `anchor` on-chain `index_batch` e2e against a local sequencer) and is green
on `main`. `RISC0_DEV_MODE=0` real-proof runs are shown via `scripts/demo.sh`
locally and in the demo video (dev-mode is used only on the hosted CI runner for
speed; CU is identical either way). Four isolated smoke tests
(`storage`/`broadcast`/`publish`/`anchor`) cover each pipeline stage. Codebase is
split into independently testable crates/modules; five upstream issues filed for
tooling gaps encountered.
## Supporting Materials
- **Narrated demo video (RISC0_DEV_MODE=0):** https://youtu.be/JY-joCR_2ag
- **Reproducible demo script:** [`scripts/demo.sh`](https://github.com/aegonmyy/logoz/blob/main/scripts/demo.sh)
- **CU benchmark harness:** [`scripts/bench-cu.sh`](https://github.com/aegonmyy/logoz/blob/main/scripts/bench-cu.sh)
- **Reusable module:** [`logos-chronicle/`](https://github.com/aegonmyy/logoz/tree/main/logos-chronicle)
- **Batch anchor CLI:** [`batch-anchor/`](https://github.com/aegonmyy/logoz/tree/main/batch-anchor)
- **SPEL registry program + IDL:** [`chronicle-registry/`](https://github.com/aegonmyy/logoz/tree/main/chronicle-registry)
- **v0.2.0 port branch:** [`port/v0.2.0`](https://github.com/aegonmyy/logoz/tree/port/v0.2.0)
- **Upstream issues filed:** spel [#240](https://github.com/logos-co/spel/issues/240) · [#241](https://github.com/logos-co/spel/issues/241) · scaffold [#230](https://github.com/logos-co/scaffold/issues/230) · [#231](https://github.com/logos-co/scaffold/issues/231) · [#232](https://github.com/logos-co/scaffold/issues/232)
## Terms & Conditions
By submitting this solution, I confirm that I have read and agree to the [Terms & Conditions](../TERMS.md).