Better frame duplication logic

This commit is contained in:
Leon Böttger authored and Leon Böttger committed 2026-03-08 15:30:22 +01:00
1 parent e0407d9398
commit 3736605509
2 files changed
+80 -6

No files matched your search

@@ -123,9 +123,48 @@ class InboundNearbyConnection: NearbyConnection {
}
switch currentState {
case .sentConnectionResponse:
try processPairedKeyEncryptionFrame(frame)
if frame.hasV1, frame.v1.hasPairedKeyEncryption {
try processPairedKeyEncryptionFrame(frame)
return
}
if frame.hasV1, frame.v1.hasIntroduction {
log("[InboundNearbyConnection \(self.id)] Received introduction before paired-key exchange finished; continuing unauthenticated flow.")
try sendPairedKeyResult(status: .unable)
try processIntroductionFrame(frame)
return
}
if frame.hasV1, frame.v1.hasType {
if frame.v1.type == .pairedKeyResult || frame.v1.type == .progressUpdate {
log("[InboundNearbyConnection \(self.id)] Ignoring duplicate/intermediate transfer setup frame \(frame.v1.type) while waiting for pairedKeyEncryption.")
return
}
if frame.v1.type == .response, case .accept = frame.v1.connectionResponse.status {
log("[InboundNearbyConnection \(self.id)] Ignoring accept response while waiting for pairedKeyEncryption.")
return
}
}
throw NearbyError.requiredFieldMissing("shareNearbyFrame.v1.pairedKeyEncryption")
case .sentPairedKeyResult:
try processPairedKeyResultFrame(frame)
if frame.hasV1, frame.v1.hasPairedKeyResult {
try processPairedKeyResultFrame(frame)
return
}
if frame.hasV1, frame.v1.hasIntroduction {
log("[InboundNearbyConnection \(self.id)] Received introduction without pairedKeyResult; continuing for legacy compatibility.")
try processIntroductionFrame(frame)
return
}
if frame.hasV1, frame.v1.hasType {
if frame.v1.type == .pairedKeyEncryption || frame.v1.type == .progressUpdate {
log("[InboundNearbyConnection \(self.id)] Ignoring duplicate/intermediate transfer setup frame \(frame.v1.type) while waiting for pairedKeyResult.")
return
}
if frame.v1.type == .response, case .accept = frame.v1.connectionResponse.status {
log("[InboundNearbyConnection \(self.id)] Ignoring accept response while waiting for pairedKeyResult.")
return
}
}
throw NearbyError.requiredFieldMissing("shareNearbyFrame.v1.pairedKeyResult")
case .receivedPairedKeyResult:
if frame.hasV1, frame.v1.hasIntroduction {
try processIntroductionFrame(frame)
@@ -147,15 +147,50 @@ class OutboundNearbyConnection: NearbyConnection {
switch currentState {
case .sentPairedKeyEncryption:
try processPairedKeyEncryption(frame: frame)
if frame.hasV1, frame.v1.hasPairedKeyEncryption {
try processPairedKeyEncryption(frame: frame)
return
}
if frame.hasV1, frame.v1.hasPairedKeyResult {
log("[OutboundNearbyConnection \(self.id)] Received pairedKeyResult before pairedKeyEncryption; continuing for legacy compatibility.")
try processPairedKeyResult(frame: frame)
return
}
if frame.hasV1, frame.v1.hasType {
if frame.v1.type == .progressUpdate || frame.v1.type == .response {
log("[OutboundNearbyConnection \(self.id)] Ignoring duplicate/intermediate transfer setup frame \(frame.v1.type) while waiting for pairedKeyEncryption.")
return
}
}
throw NearbyError.requiredFieldMissing("sharingNearbyFrame.v1.pairedKeyEncryption")
case .sentPairedKeyResult:
try processPairedKeyResult(frame: frame)
if frame.hasV1, frame.v1.hasPairedKeyResult {
try processPairedKeyResult(frame: frame)
return
}
if frame.hasV1, frame.v1.hasType {
if frame.v1.type == .pairedKeyEncryption || frame.v1.type == .progressUpdate || frame.v1.type == .response {
log("[OutboundNearbyConnection \(self.id)] Ignoring duplicate/intermediate transfer setup frame \(frame.v1.type) while waiting for pairedKeyResult.")
return
}
}
throw NearbyError.requiredFieldMissing("sharingNearbyFrame.v1.pairedKeyResult")
case .sentIntroduction:
try processConsent(frame: frame)
if frame.version == .v1, frame.v1.type == .response {
try processConsent(frame: frame)
return
}
if frame.hasV1, frame.v1.hasType {
if frame.v1.type == .pairedKeyEncryption || frame.v1.type == .pairedKeyResult || frame.v1.type == .progressUpdate {
log("[OutboundNearbyConnection \(self.id)] Ignoring duplicate/intermediate transfer setup frame \(frame.v1.type) while waiting for consent.")
return
}
}
throw NearbyError.requiredFieldMissing("sharingNearbyFrame.v1.type==response")
case .sendingFiles:
break
default:
assertionFailure("[OutboundNearbyConnection \(self.id)] Unexpected state \(currentState)")
log("[OutboundNearbyConnection \(self.id)] Unexpected state \(currentState)")
}
}