From 5699d5d1bcb27fc3beaf9bd5d882e8f8a7eea64e Mon Sep 17 00:00:00 2001 From: "Evgeny @ SimpleX Chat" <259188159+evgeny-simplex@users.noreply.github.com> Date: Sat, 7 Nov 2026 09:23:36 +0000 Subject: [PATCH] ios: free call media frame buffers, drop frames that fail crypto (#8065) --- apps/ios/Shared/Views/Call/WebRTCClient.swift | 29 +++++++++++-------- 1 file changed, 17 insertions(+), 12 deletions(-) diff --git a/apps/ios/Shared/Views/Call/WebRTCClient.swift b/apps/ios/Shared/Views/Call/WebRTCClient.swift index b79b6048d1..71f8024118 100644 --- a/apps/ios/Shared/Views/Call/WebRTCClient.swift +++ b/apps/ios/Shared/Views/Call/WebRTCClient.swift @@ -618,8 +618,11 @@ final class WebRTCClient: NSObject, RTCVideoViewDelegate, RTCFrameEncryptorDeleg if var key: [CChar] = activeCall?.aesKey?.cString(using: .utf8), let pointer: UnsafeMutableRawPointer = malloc(encrypted.count) { memcpy(pointer, (encrypted as NSData).bytes, encrypted.count) - logCrypto("decrypt", chat_decrypt_media(&key, pointer.advanced(by: clearTextBytesSize), Int32(encrypted.count - clearTextBytesSize))) - return Data(bytes: pointer, count: encrypted.count - WebRTCClient.ivTagBytes) + guard checkCrypto("decrypt", chat_decrypt_media(&key, pointer.advanced(by: clearTextBytesSize), Int32(encrypted.count - clearTextBytesSize))) else { + free(pointer) + return nil + } + return Data(bytesNoCopy: pointer, count: encrypted.count - WebRTCClient.ivTagBytes, deallocator: .free) } else { return nil } @@ -633,22 +636,24 @@ final class WebRTCClient: NSObject, RTCVideoViewDelegate, RTCFrameEncryptorDeleg if var key: [CChar] = activeCall?.aesKey?.cString(using: .utf8), let pointer: UnsafeMutableRawPointer = malloc(unencrypted.count + WebRTCClient.ivTagBytes) { memcpy(pointer, (unencrypted as NSData).bytes, unencrypted.count) - logCrypto("encrypt", chat_encrypt_media(chat_ctrl, &key, pointer.advanced(by: clearTextBytesSize), Int32(unencrypted.count + WebRTCClient.ivTagBytes - clearTextBytesSize))) - return Data(bytes: pointer, count: unencrypted.count + WebRTCClient.ivTagBytes) + guard checkCrypto("encrypt", chat_encrypt_media(chat_ctrl, &key, pointer.advanced(by: clearTextBytesSize), Int32(unencrypted.count + WebRTCClient.ivTagBytes - clearTextBytesSize))) else { + free(pointer) + return nil + } + return Data(bytesNoCopy: pointer, count: unencrypted.count + WebRTCClient.ivTagBytes, deallocator: .free) } else { return nil } } - private func logCrypto(_ op: String, _ r: UnsafeMutablePointer?) { - if let r = r { - let err = fromCString(r) - if err != "" { - logger.error("\(op) error: \(err)") -// } else { -// logger.debug("\(op) ok") - } + private func checkCrypto(_ op: String, _ r: UnsafeMutablePointer?) -> Bool { + guard let r = r else { return true } + let err = fromCString(r) + if err != "" { + logger.error("\(op) error: \(err)") + return false } + return true } func addRemoteCameraRenderer(_ renderer: RTCVideoRenderer) {