Skip to content
Merged

TGDH #14

Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
26 commits
Select commit Hold shift + click to select a range
6451daf
Generalized key type
bwbush Jun 21, 2025
f67a763
Implemented BLS12-381 keys
bwbush Jun 22, 2025
186585d
Implemented command for printing the DID of a private key
bwbush Jun 22, 2025
19f73d3
Work in progress on refactoring signature verification
bwbush Jun 22, 2025
82ea056
Signature verification for BLS12-381
bwbush Jun 22, 2025
d8c7361
Created makefile
bwbush Jun 29, 2025
927ac05
Implemented tests for BLS12-381
bwbush Jun 29, 2025
6cb79ab
Implemented tests for Ed25519 keys
bwbush Jun 29, 2025
8fb9126
Implemented basics of TGDH shared secrets
bwbush Jun 29, 2025
79b5cbb
Implemented basic test of TGDH
bwbush Jun 29, 2025
6f7717d
Implemented recomputation of root private key
bwbush Jun 29, 2025
28fb80a
Handled edge case for recomputing roots
bwbush Jun 29, 2025
0f994fb
Improved private key derivation
bwbush Jun 30, 2025
a3acf6e
Implemented generic seed derivation function
bwbush Jun 30, 2025
cf11e95
Implemented AES256GCM encryption/decryption for TGDH
bwbush Jul 1, 2025
745ca36
Work in progress on TGDH JSON serialization
bwbush Jul 1, 2025
3c817c5
Equality of TGDH nodes
bwbush Jul 1, 2025
e12c431
Implemented CLI to TGDH functions
bwbush Jul 2, 2025
f7972d0
Added JWK support
bwbush Jul 3, 2025
6450a34
Fixed tests
bwbush Jul 3, 2025
1e0e314
Upgraded dependencies
bwbush Jul 3, 2025
9fffd1b
Implemented TGDH key removal
bwbush Jul 4, 2025
3665ce1
Added TGDH documentation
bwbush Jul 4, 2025
2e15666
Adjusted formatting of equations
bwbush Jul 4, 2025
558238c
Fixed typesetting of math
bwbush Jul 4, 2025
2badbd4
Fixed mathematics typesetting
bwbush Jul 4, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 19 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
#!/usr/bin/env nix-shell
#!nix-shell -i "make -f" -p go golint

PKGS=./cardano ./cmd ./header ./ipfs ./key ./ledger ./rdf ./tgdh

SRCS=$(shell find $(PKGS) -type f -name \*.go)

nacatgunma: main.go $(SRCS)
GOPATH= go build -o nacatgunma $<

test: $(SRCS)
GOPATH= go test -v $(PKGS)

format: $(SRCS)
GOPATH= go fmt $(PKGS)

.SUFFIXES:

.PHONY: test format
34 changes: 17 additions & 17 deletions RDF-Specialization.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,22 +3,22 @@

## RDF graph payload

Assume that the content identifier $\mathsf{body}(B) \in \mathcal{C}$ references a concrete RDF graph: $\mathsf{G}(B) \subseteq \mathcal{T}$ where $\mathcal{T}$ is the set of RDF triples of the form $(s, p, o)$.
Assume that the content identifier $`\mathsf{body}(B) \in \mathcal{C}`$ references a concrete RDF graph: $`\mathsf{G}(B) \subseteq \mathcal{T}`$ where $`\mathcal{T}`$ is the set of RDF triples of the form $`(s, p, o)`$.

We interpret $\mathsf{G}(B)$ as the **payload graph** authored by $\mathsf{issuer}(B)$.
We interpret $`\mathsf{G}(B)`$ as the **payload graph** authored by $`\mathsf{issuer}(B)`$.


## Reification

We define a reification function $\mathsf{reify}(B)$ that maps the signed graph to a **named graph** or **quads** with provenance.
We define a reification function $`\mathsf{reify}(B)`$ that maps the signed graph to a **named graph** or **quads** with provenance.

For each triple $t \in \mathsf{G}(B)$, define the reified form:
For each triple $`t \in \mathsf{G}(B)`$, define the reified form:

$$
\mathsf{reify}(B) = \{ (s, p, o, g\_B) \mid (s, p, o) \in \mathsf{G}(B) \}
$$

where $g\_B \in \mathcal{U}$ is a unique graph name associated with the block $B$, such as:
where $`g\_B \in \mathcal{U}`$ is a unique graph name associated with the block $`B`$, such as:

$$
g\_B := \texttt{did:} \mathsf{issuer}(B) \\# \mathsf{id}(B)
Expand All @@ -28,23 +28,23 @@ Alternatively, if using RDF-star or PROV-O, the reification can instead be:

- A named graph or blank node denoting the assertion
- Annotated with:
- $\texttt{prov:wasAttributedTo} \ \mathsf{issuer}(B)$
- $\texttt{prov:wasDerivedFrom} \ \mathsf{id}(B)$
- $`\texttt{prov:wasAttributedTo} \ \mathsf{issuer}(B)`$
- $`\texttt{prov:wasDerivedFrom} \ \mathsf{id}(B)`$

The exact form depends on the RDF dialect used, but semantically the payload is treated as **authored assertions by the signer**.


## State computation

Given a participant $u$, let $\mathcal{V}_u$ be the set of blocks **visible** under subjective traversal (see prior section with accept/reject logic).
Given a participant $`u`$, let $`\mathcal{V}_u`$ be the set of blocks **visible** under subjective traversal (see prior section with accept/reject logic).

Define the participant’s **assembled state graph** $\mathsf{S}_u$ as:
Define the participant’s **assembled state graph** $`\mathsf{S}_u`$ as:

$$
\mathsf{S}\_u := \bigcup\_{B \in \mathcal{V}\_u} \mathsf{reify}(B)
$$

That is, the total RDF graph is the union of all reified block payloads visible under $u$'s trust and traversal policy.
That is, the total RDF graph is the union of all reified block payloads visible under $`u`$'s trust and traversal policy.

If RDF-star is used, this could equivalently be:

Expand All @@ -56,7 +56,7 @@ $$

## Conflict handling

If blocks in $\mathcal{V}_u$ make **conflicting assertions** (e.g., two blocks claim different values for the same triple), this is **not a protocol error** — the provenance-aware model allows:
If blocks in $`\mathcal{V}_u`$ make **conflicting assertions** (e.g., two blocks claim different values for the same triple), this is **not a protocol error** — the provenance-aware model allows:

- Leaving conflicting assertions coexisting with different graph names
- Using downstream logic to resolve (e.g., trust-weighted resolution, query filtering)
Expand All @@ -68,9 +68,9 @@ Thus, **state** is:

## Summary

| Concept | Description |
|---------------------|----------------------------------------------------------------------------|
| $\mathsf{G}(B)$ | RDF graph payload of block $B$ |
| $\mathsf{reify}(B)$ | Provenance-aware named graph or RDF-star reification |
| $\mathsf{S}_u$ | State for participant $u$: union of all reified payloads of visible blocks |
| Conflicts | Allowed; resolution is subjective and external |
| Concept | Description |
|-----------------------|------------------------------------------------------------------------------|
| $`\mathsf{G}(B)`$ | RDF graph payload of block $`B`$ |
| $`\mathsf{reify}(B)`$ | Provenance-aware named graph or RDF-star reification |
| $`\mathsf{S}_u`$ | State for participant $`u`$: union of all reified payloads of visible blocks |
| Conflicts | Allowed; resolution is subjective and external |
1 change: 1 addition & 0 deletions ReadMe.md
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ The combination of signed RDF graphs + DAG tips + subjective tip choice constitu

- [General specification](Specification.md)
- [Specialization to RDF bodies](RDF-Specialization.md)
- [Specialization to TGDH encryption](TGDH-Specialization.md)
- [Using Cardano for Layer 1](Cardano-for-Layer-1.md)


Expand Down
70 changes: 35 additions & 35 deletions Specification.md
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ type Payload struct {

## Blocks

Let $\mathcal{C}$ be the set of content identifiers (e.g., CIDs), and let $\mathcal{P}$ be the set of participants with associated public keys.
Let $`\mathcal{C}`$ be the set of content identifiers (e.g., CIDs), and let $`\mathcal{P}`$ be the set of participants with associated public keys.

Each block is a tuple:

Expand All @@ -43,60 +43,60 @@ B = (\text{id}, \mathsf{accept}(B), \mathsf{reject}(B), \mathsf{body}(B), \maths
$$

where:
- $\text{id} \in \mathcal{C}$: the content identifier of the block itself.
- $\mathsf{accept}(B) \subset \mathcal{C}$: set of parent block CIDs that this block explicitly extends.
- $\mathsf{reject}(B) \subset \mathcal{C}$: set of block CIDs that this block rejects.
- $\mathsf{body}(B) \in \mathcal{C}$: CID of the block’s body (arbitrary content).
- $\mathsf{schema}(B) \in \mathbb{S}$: schema URI string.
- $\mathsf{media}(B) \in \mathbb{M}$: media type string.
- $\mathsf{comment}(B)$: comment string.
- $\mathsf{issuer}(B) \in \mathcal{P}$: DID of the block’s issuer.
- $\mathsf{sig}(B)$: digital signature over the payload fields, created using the issuer’s secret key.
- $`\text{id} \in \mathcal{C}`$: the content identifier of the block itself.
- $`\mathsf{accept}(B) \subset \mathcal{C}`$: set of parent block CIDs that this block explicitly extends.
- $`\mathsf{reject}(B) \subset \mathcal{C}`$: set of block CIDs that this block rejects.
- $`\mathsf{body}(B) \in \mathcal{C}`$: CID of the block’s body (arbitrary content).
- $`\mathsf{schema}(B) \in \mathbb{S}`$: schema URI string.
- $`\mathsf{media}(B) \in \mathbb{M}`$: media type string.
- $`\mathsf{comment}(B)`$: comment string.
- $`\mathsf{issuer}(B) \in \mathcal{P}`$: DID of the block’s issuer.
- $`\mathsf{sig}(B)`$: digital signature over the payload fields, created using the issuer’s secret key.


## DAG Structure and validity

Let the **global DAG** be a graph $\mathcal{D}$ where nodes are block identifiers and edges are induced by $\mathsf{accept}(B)$.
Let the **global DAG** be a graph $`\mathcal{D}`$ where nodes are block identifiers and edges are induced by $`\mathsf{accept}(B)`$.

A block $B$ is **valid** iff:
A block $`B`$ is **valid** iff:

1. All parent CIDs in $\mathsf{accept}(B)$ exist in the DAG.
2. The signature $\mathsf{sig}(B)$ verifies under $\mathsf{issuer}(B)$ against a canonical serialization of the payload.
3. $B$ does not create a cycle when added to $\mathcal{D}$.
1. All parent CIDs in $`\mathsf{accept}(B)`$ exist in the DAG.
2. The signature $`\mathsf{sig}(B)`$ verifies under $`\mathsf{issuer}(B)`$ against a canonical serialization of the payload.
3. $`B`$ does not create a cycle when added to $`\mathcal{D}`$.


## Participant trust and views

Each participant $u \in \mathcal{P}$ maintains:
Each participant $`u \in \mathcal{P}`$ maintains:

- A **trust function**:

$$
T\_u : \mathcal{P} \to [0,1]
$$

- A set of **trusted tips** $\mathcal{T}_u \subseteq \mathcal{C}$ used as starting points for state computation.
- A set of **trusted tips** $`\mathcal{T}_u \subseteq \mathcal{C}`$ used as starting points for state computation.


## Subjective traversal with rejection

For a participant $u$, the **visible subgraph** $\mathcal{D}_u \subseteq \mathcal{D}$ is constructed as follows:
For a participant $`u`$, the **visible subgraph** $`\mathcal{D}_u \subseteq \mathcal{D}`$ is constructed as follows:

1. Start from trusted tips $\mathcal{T}_u$.
2. Traverse backward along $\mathsf{accept}$ edges recursively.
3. Whenever a block $B$ is encountered:
- If any ancestor block $A$ declares $B \in \mathsf{reject}(A)$, then:
- Omit $B$ and all descendants reachable via $\mathsf{accept}$ edges **unless** they are also reachable via a separate path that does not pass through a rejecting ancestor.
1. Start from trusted tips $`\mathcal{T}_u`$.
2. Traverse backward along $`\mathsf{accept}`$ edges recursively.
3. Whenever a block $`B`$ is encountered:
- If any ancestor block $`A`$ declares $`B \in \mathsf{reject}(A)`$, then:
- Omit $`B`$ and all descendants reachable via $`\mathsf{accept}`$ edges **unless** they are also reachable via a separate path that does not pass through a rejecting ancestor.

This defines **rejection as a pruning operator** on traversal.

Formally, the **visible blocks** for participant $u$ are:
Formally, the **visible blocks** for participant $`u`$ are:

$$
\mathcal{V}_u = \{ B \in \mathcal{D} \mid B \text{ is reachable from } \mathcal{T}_u \text{ via non-rejected paths} \}
$$

A path is **non-rejected** if no intermediate block $A$ along the path has $\mathsf{reject}(A) \ni B'$ for any $B'$ also on the path.
A path is **non-rejected** if no intermediate block $`A`$ along the path has $`\mathsf{reject}(A) \ni B'`$ for any $`B'`$ also on the path.

The following non-normative pseudo-code sketches the subjective DAG traversal and rejection. See [Pruning.lean](Pruning.lean) for Lean4 code and examples of pruning rejected blocks. One can experiment with the pruning algorithm [here](https://live.lean-lang.org/#codez=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).

Expand Down Expand Up @@ -155,9 +155,9 @@ partial def computeVisibleView

## State interpretation

Each participant $u$ uses their local visible DAG $\mathcal{V}_u$ to compute a **state view**, interpreted according to application-specific logic on:
Each participant $`u`$ uses their local visible DAG $`\mathcal{V}_u`$ to compute a **state view**, interpreted according to application-specific logic on:

- Block bodies $\mathsf{body}(B)$, using $\mathsf{schema}(B)$ and $\mathsf{media}(B)$
- Block bodies $`\mathsf{body}(B)`$, using $`\mathsf{schema}(B)`$ and $`\mathsf{media}(B)`$
- Provenance (issuer of each block)
- Ordering (topological or heuristic over the DAG)

Expand All @@ -172,11 +172,11 @@ This may include reconstructing RDF graphs, applying CRDT logic, filtering by is

## Summary

| Concept | Formally |
|-----------|-----------------------------------------------------------------|
| Block | Tuple of accepted/rejected parents, body CID, issuer, signature |
| DAG | Induced by accepted parent links |
| Trust | Local function $T\_u : \mathcal{P} \to [0,1]$ |
| View | Blocks visible from tips via non-rejected paths |
| Rejection | Explicitly prunes traversal unless overridden later |
| State | Application-defined interpretation of visible block bodies |
| Concept | Formally |
|-----------|-------------------------------------------------------------------|
| Block | Tuple of accepted/rejected parents, body CID, issuer, signature |
| DAG | Induced by accepted parent links |
| Trust | Local function $`T\_u : \mathcal{P} \to [0,1]`$ |
| View | Blocks visible from tips via non-rejected paths |
| Rejection | Explicitly prunes traversal unless overridden later |
| State | Application-defined interpretation of visible block bodies |
Loading