# In-transit reconstruction
> @raulk, 2025-03-05
This note explores the topic of in-transit reconstruction. We do so by first positing a desired reliability model. We then evaluate various fault scenarios in the current and near-term, to finally wrap up by charting potential paths forward.
## Desirable reliability properties
The broad goal of in-transit reconstruction is to strengthen the reliability of live consensus, allowing Ethereum validators to recover from various fault modes during the slot critical path.
Out of scope of this note is another type of reconstruction: custody reconstruction, i.e. blobs held in custody whose availability is compromised and could be recovered by sampling and decoding, leveraging the built-in 2x information redundancy via Reed-Solomon. From the perspective of the protocol, this is an offline and optional process and has no bearing on consensus.
We propose a straightforward reliability goal during critical-path propagation: if sufficient cells exist somewhere in the network, every node should receive the cells they need in order to pass local DA checks in a timely fashion (within the attestation window).
## Weaknesses and solution space
We have identified a few weaknesses in the status quo:
- Nodes holding cells beyond their custody set don't share them with the network.
- The protocol does not mandate any form of reconstruction.
- Implementations that reconstruct columns locally (by implementer's choice) keep the results to themselves. They don't serve reconstructed columns to non-custody subnets.
Some options in the solution space:
- Offering cells we possess in our blobpool, beyond our custody column set (pull model).
- Mandating some form of reconstruction and reseeding for high-yet-partial custody nodes, namely those with custody count = (64, 128).
- Mandating that reconstructions also go through the first point.
- Gossip on row-level subnets to enable blob reconstruction from partial availability.
## Status quo: PeerDAS and dense blobpool
Today, every type 3 tx is propagated in full. If a publicly available blob is included in a block's matrix, a large portion of nodes are in disposition of seeding **all** its cells, not just those belonging to their custody set. We're not currently doing this, and it's a quick win: with cell-level deltas in the CL, nodes can begin to cross-seed cells to custody subnets they're not subscribed to simply by announcing them (pull model).
Furthermore, some clients already default to full-matrix reconstruction when custody >= 64, primarily as an optimization feature. The higher the custody above 64, the more effective this is: the more column subnets a node is subscribed to, the higher the chance they will receive _any_ k columns sooner and can trigger reconstruction earlier in order to pass DA checks for their actual custody group.
Today, after reconstruction, these nodes will **only** serve custody columns, disposing of the rest. This is a latent reservoir of reliability we are not utilizing. Buffering non-custody columns and announcing their availability (via gossipsub's lazy gossip) would be another easy win.
## Short-term: cell-level deltas
Cell-level deltas add another layer of refinement. Nodes holding just _some but not all_ of the included blobs in their blobpool can utilize the cells they have, and reconcile only missing ones from the network, to form full columns.
For a given column, if the network as a whole has 100% availability of its cells (the union of all honest blobpools), the network would cooperate to enable every node to reconcile the full custody column. Worth noting: we're up against critical-path latency. The scarcer a cell is, the longer it takes to reach every interested node. The network needs to "unwind" the reconciliation from sources to edges.
As we push the blob limit further, if nothing changes in the blobpool, we'll see more fragmentation, more getBlobsV3 availability misses, and stronger reliance on reconciliation. If a blob is present somewhere, its cells will get seeded through the mechanisms above. All good.
But the problematic case is when several conditions stack: a blob is poorly available in the blobpool at inclusion time, and it so happens that the union of the custody groups of all CL nodes has below 100% coverage. In this case, the network is not self-sufficient and instead becomes SPoF dependent on the builder to propagate all columns via the critical path.
This pathological situation can be solved today by making nodes announce beyond their custody set, to put us back in a more cooperative dynamic.
## Future: sparse blobpool
This is where it gets interesting. We go from full tx availability in the blobpool to a model where availability is cell-aligned with the custody set (plus some excess) in ~85% of cases, and full in ~15%.
It is worth noting that, from a consensus requirements perspective, the CL would not notice any logical changes with respect to the EL: the EL continues serving the cells the CL cares about (custody set). That said, there are three points that affect our reliability model:
1. In 15% of cases, the EL serves the full blob, and those CLs can offer non-custody cells to the network.
2. In the remaining 85%, the EL will serve _some_ excess beyond custody thanks to random noise sampling.
3. Given the bandwidth usage reduction, we expect to see a consistently higher hit rate via getBlobs than the dense blobpool would yield at the same blob limit.
## Future: async blobs and PTC
PTC changes the dynamics around inclusion risk. Today, the builder takes their view of the blobpool to be that of the network. But if a single poorly-available blob is included, the builder risks getting their entire block rejected if the critical path cannot reconcile in time. That risk, plus the possibility of an attacker manipulating a node's view of the network, makes reliance on network reconstruction fragile.
With async blobs, the PTC would attest to blob availability prior to inclusion, which also enables censorship resistant mechanisms like FOCIL to cover blobs. The builder could then include blobs with full confidence, and broadcast only the cells it actually has, strongly relying on the network to reconstruct the rest, with a protocol-backed guarantee that the cells exist somewhere. This shifts the question from "is network reconstruction safe to rely on?" to "how do we make it efficient?"
## Cross-seeding cells
The common thread across all scenarios is: nodes need to cooperate to serve their pre-existing local availability to the network during the critical path, not restricted to just their custody set, but also beyond.
Cell-level deltas enable nodes to announce availability at the most granular level: the cell. With this in place, the reliability increase during the critical path depends on how efficient the reconciliation protocol is.
The question becomes: to what interest channels are these announcements sent? Only to column-centric channels? Or do we introduce row-centric channels in addition to the column-centric channels? From the perspective of consensus, columns map to custody, attestation, and DA checks; nodes have standing interest in specific columns across blocks.
Conversely, rows have no durable semantic interest: their contents change every block because blob indices shift. No client has reason to durably subscribe to specific rows outside of some potential transient reconstruction utility. Row subnets would carry the standing cost of a gossip dimension (mesh maintenance, subscriptions, scoring) for something that's only useful during a narrow window of each slot, which the single column dimension is already fulfilling.
This changes if we attach some duty to row subscribers. Assigning this duty on the protocol is hard, as workload across rows is non-uniform: nodes on higher rows would have less work to do than nodes on lower rows, because the matrix grows downwards. But a more important question is: what fault would we be defending against?
Assuming a blob propagated in the blobpool well:
- In the dense blobpool, all nodes that have a blob have the full blob.
- In the sparse blobpool, 15% of nodes have the full blob, and the remaining have a bit more than their custody set, already satisfying consensus DA checks.
The natural fix is to cross-seed excess cells via cell announcements over column subnets, making them available via pull. This works because column subnets align with the protocol-mandated interests that determine attestation and PTC outcome: DA checks run over columns, not rows. No new gossip dimension needed.
What about poorly propagated blobs? The blobpool is inherently non-deterministic, and edge cases will occur. But row reconstruction is strictly dominated by full-matrix reconstruction here. Full-matrix reconstruction operates on full columns and produces every cell in the matrix, including every cell that row reconstruction would have recovered. And it's self-sustaining: nodes with custody >= 64 already do it because it's rational from a resource expenditure and attestation latency perspective, regardless of protocol mandate. It will always exist because it has real protocol utility.
## Conclusion and open questions
Column-centric cross-seeding beyond the custody set covers the reliability targets we set above without introducing new network infrastructure.
**Should we mandate cooperative full-matrix reconstruction?** Some clients already reconstruct selfishly when custody >= 64. We could mandate that nodes with custody in the (64, 128) range share reconstructed columns on non-custody topics.
There's a real case for this: it leverages swarm computation over partially available columns to achieve a shared goal and spares builder uplink bandwidth. A local builder could include more blobs than it has the uplink to propagate alone, relying on the network's inherent reconstruction capabilities. With PTC providing a deterministic signal of availability, this reliance is well-justified.
The worry is that mandating this enshrines a crutch builders leverage to underpropagate, shifting the burden to the network. I could see it going either way. Thoughts welcome.