mirror of
https://github.com/vicliu624/trail-mate.git
synced 2026-10-23 05:32:18 +00:00
refactor(protocol): remove legacy meshcore direct secret fallback
This commit is contained in:
1 parent
1f3c86122f
commit
0b5bb6cea3
6 files changed
+15
-81
No files matched your search
@@ -304,13 +304,15 @@ Current state:
|
||||
- Confirmed platform gap, now documented in fine-grained capabilities.
|
||||
- ESP32 direct text/app-data sends now use `MeshCoreDirectRoutePolicy` for the shared decision table:
|
||||
missing peer pubkey -> discover/fail, selected route -> direct route path, no selected route -> flood,
|
||||
and preferred-channel secret derivation may fall back to the requested channel.
|
||||
and route/channel fallback remains explicit without redefining direct-secret material.
|
||||
- Incoming MeshCore discover request/response decisions now run through `MeshCoreRuntime`: request filter/since
|
||||
matching emits `SendDiscoverResponseEffect`, and responses emit `PublishNodeInfoEffect` plus
|
||||
`UpdatePeerRouteEffect`.
|
||||
- MeshCore direct shared-secret expansion and nRF peer-key derivation now use `MeshCoreDirectSecretCore`;
|
||||
ESP32 keeps identity storage and peer pubkey lookup in the adapter, then delegates key expansion to the
|
||||
shared helper.
|
||||
- ESP32 no longer accepts the historical group-secret-derived direct key fallback; MeshCore direct secrets are
|
||||
identity/pubkey-derived only.
|
||||
|
||||
Residual risk:
|
||||
|
||||
|
||||
@@ -369,13 +369,15 @@ Current C++17 migration state:
|
||||
|
||||
- Direct-route send decision for ESP32 MeshCore direct text/app-data now uses shared
|
||||
`MeshCoreDirectRoutePolicy`: missing peer pubkey triggers discover/failure, selected routes use direct path,
|
||||
and direct secret derivation may fall back from preferred route channel to requested channel.
|
||||
and route/channel fallback remains explicit without redefining direct-secret material.
|
||||
- Incoming MeshCore discover request/response control payloads now flow through `MeshCoreRuntime`: filter/since
|
||||
matching emits `SendDiscoverResponseEffect`, and discover responses emit `PublishNodeInfoEffect` plus
|
||||
`UpdatePeerRouteEffect`.
|
||||
- MeshCore identity shared-secret expansion and nRF peer-key derivation now use shared
|
||||
`MeshCoreDirectSecretCore`; ESP32 still owns private-key storage and route pubkey lookup before delegating
|
||||
key expansion to the runtime helper.
|
||||
- ESP32 no longer falls back to the historical group-secret-derived direct key; MeshCore direct secrets are
|
||||
identity/pubkey-derived only.
|
||||
- Peer route storage, pubkey persistence, private identity storage, response scheduling, and frame transmission
|
||||
are still platform adapter responsibilities until they can be represented as runtime state/effects.
|
||||
|
||||
|
||||
@@ -34,9 +34,6 @@ struct MeshCoreDirectRouteDecision
|
||||
MeshCoreDirectRouteStatus status = MeshCoreDirectRouteStatus::Ready;
|
||||
MeshCoreRouteMode route_mode = MeshCoreRouteMode::Flood;
|
||||
ChannelId tx_channel = ChannelId::PRIMARY;
|
||||
ChannelId primary_secret_channel = ChannelId::PRIMARY;
|
||||
ChannelId fallback_secret_channel = ChannelId::PRIMARY;
|
||||
bool allow_secret_fallback = false;
|
||||
bool should_discover = false;
|
||||
};
|
||||
|
||||
@@ -45,8 +42,6 @@ inline MeshCoreDirectRouteDecision resolveMeshCoreDirectRoutePolicy(
|
||||
{
|
||||
MeshCoreDirectRouteDecision decision{};
|
||||
decision.tx_channel = facts.requested_channel;
|
||||
decision.primary_secret_channel = facts.requested_channel;
|
||||
decision.fallback_secret_channel = facts.requested_channel;
|
||||
|
||||
if (facts.identity_ready && (!facts.has_peer_route || !facts.peer_has_public_key))
|
||||
{
|
||||
@@ -59,9 +54,6 @@ inline MeshCoreDirectRouteDecision resolveMeshCoreDirectRoutePolicy(
|
||||
{
|
||||
decision.route_mode = MeshCoreRouteMode::Direct;
|
||||
decision.tx_channel = facts.selected_route_channel;
|
||||
decision.primary_secret_channel = facts.selected_route_channel;
|
||||
decision.fallback_secret_channel = facts.requested_channel;
|
||||
decision.allow_secret_fallback = facts.selected_route_channel != facts.requested_channel;
|
||||
}
|
||||
|
||||
return decision;
|
||||
|
||||
@@ -26,8 +26,6 @@ int main()
|
||||
assert(decision.status == chat::runtime::MeshCoreDirectRouteStatus::Ready);
|
||||
assert(decision.route_mode == chat::runtime::MeshCoreRouteMode::Flood);
|
||||
assert(decision.tx_channel == chat::ChannelId::SECONDARY);
|
||||
assert(decision.primary_secret_channel == chat::ChannelId::SECONDARY);
|
||||
assert(!decision.allow_secret_fallback);
|
||||
}
|
||||
|
||||
{
|
||||
@@ -43,9 +41,6 @@ int main()
|
||||
assert(decision.status == chat::runtime::MeshCoreDirectRouteStatus::Ready);
|
||||
assert(decision.route_mode == chat::runtime::MeshCoreRouteMode::Direct);
|
||||
assert(decision.tx_channel == chat::ChannelId::SECONDARY);
|
||||
assert(decision.primary_secret_channel == chat::ChannelId::SECONDARY);
|
||||
assert(decision.fallback_secret_channel == chat::ChannelId::PRIMARY);
|
||||
assert(decision.allow_secret_fallback);
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
-2
@@ -339,8 +339,6 @@ class MeshCoreAdapter : public IMeshAdapter, public IMeshCoreBleBackend
|
||||
bool resolveGroupSecret(ChannelId channel, uint8_t out_key16[16],
|
||||
uint8_t out_key32[32], uint8_t* out_hash) const;
|
||||
ChannelId resolveChannelFromHash(uint8_t channel_hash, bool* out_match) const;
|
||||
bool deriveLegacyDirectSecret(ChannelId channel, uint8_t peer_hash,
|
||||
uint8_t out_key16[16], uint8_t out_key32[32]) const;
|
||||
bool deriveIdentitySecret(uint8_t peer_hash, uint8_t out_key16[16],
|
||||
uint8_t out_key32[32]) const;
|
||||
bool deriveDirectSecret(ChannelId channel, uint8_t peer_hash,
|
||||
|
||||
@@ -164,7 +164,6 @@ using chat::meshcore::ParsedPacket;
|
||||
using chat::meshcore::parsePacket;
|
||||
using chat::meshcore::saturatingAddU32;
|
||||
using chat::meshcore::scoreFromSnr;
|
||||
using chat::meshcore::sha256Trunc;
|
||||
using chat::meshcore::toHex;
|
||||
using chat::meshcore::toHmacKey32;
|
||||
|
||||
@@ -1481,39 +1480,11 @@ bool MeshCoreAdapter::deriveIdentitySecret(uint8_t peer_hash,
|
||||
out_key32, 32);
|
||||
}
|
||||
|
||||
bool MeshCoreAdapter::deriveLegacyDirectSecret(ChannelId channel, uint8_t peer_hash,
|
||||
uint8_t out_key16[16], uint8_t out_key32[32]) const
|
||||
{
|
||||
if (!out_key16 || !out_key32)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
uint8_t base_key16[16];
|
||||
uint8_t base_key32[32];
|
||||
if (!resolveGroupSecret(channel, base_key16, base_key32, nullptr))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
uint8_t material[18];
|
||||
memcpy(material, base_key16, sizeof(base_key16));
|
||||
material[16] = (peer_hash < self_hash_) ? peer_hash : self_hash_;
|
||||
material[17] = (peer_hash < self_hash_) ? self_hash_ : peer_hash;
|
||||
|
||||
sha256Trunc(out_key32, 32, material, sizeof(material));
|
||||
memcpy(out_key16, out_key32, 16);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool MeshCoreAdapter::deriveDirectSecret(ChannelId channel, uint8_t peer_hash,
|
||||
uint8_t out_key16[16], uint8_t out_key32[32]) const
|
||||
{
|
||||
if (deriveIdentitySecret(peer_hash, out_key16, out_key32))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
return deriveLegacyDirectSecret(channel, peer_hash, out_key16, out_key32);
|
||||
(void)channel;
|
||||
return deriveIdentitySecret(peer_hash, out_key16, out_key32);
|
||||
}
|
||||
|
||||
bool MeshCoreAdapter::tryDecryptPeerPayload(uint8_t src_hash,
|
||||
@@ -1582,24 +1553,6 @@ bool MeshCoreAdapter::tryDecryptPeerPayload(uint8_t src_hash,
|
||||
|
||||
for (size_t i = 0; i < order_len; ++i)
|
||||
{
|
||||
{
|
||||
uint8_t key16[16] = {};
|
||||
uint8_t key32[32] = {};
|
||||
if (deriveIdentitySecret(src_hash, key16, key32) &&
|
||||
tryCandidate(order[i], key16, key32))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
{
|
||||
uint8_t key16[16] = {};
|
||||
uint8_t key32[32] = {};
|
||||
if (deriveLegacyDirectSecret(order[i], src_hash, key16, key32) &&
|
||||
tryCandidate(order[i], key16, key32))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
{
|
||||
uint8_t key16[16] = {};
|
||||
uint8_t key32[32] = {};
|
||||
@@ -3169,13 +3122,9 @@ MeshActionResult MeshCoreAdapter::sendDirectTextDetailed(ChannelId channel, cons
|
||||
|
||||
uint8_t peer_key16[16];
|
||||
uint8_t peer_key32[32];
|
||||
if (!deriveDirectSecret(route_decision.primary_secret_channel, peer_hash, peer_key16, peer_key32))
|
||||
if (!deriveDirectSecret(route_decision.tx_channel, peer_hash, peer_key16, peer_key32))
|
||||
{
|
||||
if (!route_decision.allow_secret_fallback ||
|
||||
!deriveDirectSecret(route_decision.fallback_secret_channel, peer_hash, peer_key16, peer_key32))
|
||||
{
|
||||
return MeshActionResult::fail(MeshOperationFailure::PeerKeyMissing);
|
||||
}
|
||||
return MeshActionResult::fail(MeshOperationFailure::PeerKeyMissing);
|
||||
}
|
||||
|
||||
constexpr size_t kDirectPlainPrefixSize = 5; // ts(4) + flags(1)
|
||||
@@ -3352,16 +3301,12 @@ bool MeshCoreAdapter::sendAppData(ChannelId channel, uint32_t portnum,
|
||||
|
||||
uint8_t peer_key16[16];
|
||||
uint8_t peer_key32[32];
|
||||
if (!deriveDirectSecret(route_decision.primary_secret_channel, peer_hash, peer_key16, peer_key32))
|
||||
if (!deriveDirectSecret(route_decision.tx_channel, peer_hash, peer_key16, peer_key32))
|
||||
{
|
||||
if (!route_decision.allow_secret_fallback ||
|
||||
!deriveDirectSecret(route_decision.fallback_secret_channel, peer_hash, peer_key16, peer_key32))
|
||||
{
|
||||
MESHCORE_LOG("[MESHCORE] TX direct app-data dropped (no peer secret) peer=%08lX port=%u\n",
|
||||
static_cast<unsigned long>(dest),
|
||||
static_cast<unsigned>(portnum));
|
||||
return false;
|
||||
}
|
||||
MESHCORE_LOG("[MESHCORE] TX direct app-data dropped (no peer secret) peer=%08lX port=%u\n",
|
||||
static_cast<unsigned long>(dest),
|
||||
static_cast<unsigned>(portnum));
|
||||
return false;
|
||||
}
|
||||
(void)peer_key16;
|
||||
|
||||
|
||||
Reference in new issue
Block a user