diff --git a/apps/ios/VMC.xcodeproj/project.pbxproj b/apps/ios/VMC.xcodeproj/project.pbxproj index 3f77350..faa23f1 100644 --- a/apps/ios/VMC.xcodeproj/project.pbxproj +++ b/apps/ios/VMC.xcodeproj/project.pbxproj @@ -345,7 +345,7 @@ ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor; CODE_SIGN_STYLE = Automatic; - CURRENT_PROJECT_VERSION = 57; + CURRENT_PROJECT_VERSION = 58; DEVELOPMENT_TEAM = X25NYX3K49; ENABLE_BITCODE = NO; ENABLE_PREVIEWS = YES; @@ -360,7 +360,7 @@ "$(inherited)", "@executable_path/Frameworks" ); - MARKETING_VERSION = 0.5.44; + MARKETING_VERSION = 0.5.45; OTHER_LDFLAGS = ("$(inherited)", "-ObjC"); PRODUCT_BUNDLE_IDENTIFIER = nl.vonas.mediacluster.ios; PRODUCT_NAME = "$(TARGET_NAME)"; @@ -378,7 +378,7 @@ ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor; CODE_SIGN_STYLE = Automatic; - CURRENT_PROJECT_VERSION = 57; + CURRENT_PROJECT_VERSION = 58; DEVELOPMENT_TEAM = X25NYX3K49; ENABLE_BITCODE = NO; ENABLE_PREVIEWS = YES; @@ -393,7 +393,7 @@ "$(inherited)", "@executable_path/Frameworks" ); - MARKETING_VERSION = 0.5.44; + MARKETING_VERSION = 0.5.45; OTHER_LDFLAGS = ("$(inherited)", "-ObjC"); PRODUCT_BUNDLE_IDENTIFIER = nl.vonas.mediacluster.ios; PRODUCT_NAME = "$(TARGET_NAME)"; diff --git a/apps/ios/VMC/Playback/CencMp4Decryptor.swift b/apps/ios/VMC/Playback/CencMp4Decryptor.swift index e6898b7..1415577 100644 --- a/apps/ios/VMC/Playback/CencMp4Decryptor.swift +++ b/apps/ios/VMC/Playback/CencMp4Decryptor.swift @@ -456,7 +456,11 @@ enum CencMp4Decryptor { ) } - guard !sampleSizes.isEmpty, sencSamples.count == sampleSizes.count || sencSamples.isEmpty == false else { + // cbcs audio (F1TV): tenc heeft constant_IV + iv_size=0, fragmenten hebben géén senc. + // ISO 23001-7: elk sample ontsleutelen met die IV (geen per-sample IV, geen subsample). + let constantIv = crypto?.constantIv + let canUseConstantIv = (constantIv?.count ?? 0) >= 8 + guard !sampleSizes.isEmpty, !sencSamples.isEmpty || canUseConstantIv else { diag("frag track=\(trackId) skip: samples=\(sampleSizes.count) senc=\(sencSamples.count) tfhd=0x\(String(tfhdFlagsSeen, radix: 16)) trun=0x\(String(trunFlagsSeen, radix: 16))") // Advance cursor even if we cannot decrypt. for sz in sampleSizes { mdatCursor += sz } @@ -478,34 +482,34 @@ enum CencMp4Decryptor { let cryptBlocks = crypto?.cryptByteBlock ?? 0 let skipBlocks = crypto?.skipByteBlock ?? 0 - var didDecrypt = false + var decryptedCount = 0 for i in 0.. 0, mdatCursor + size <= data.count else { break } let sampleRange = mdatCursor..<(mdatCursor + size) var sample = data.subdata(in: sampleRange) let senc = i < sencSamples.count ? sencSamples[i] : nil - if let senc { + let iv = senc?.iv ?? constantIv + if let iv { if let decrypted = decryptSample( sample, key: key, - iv: senc.iv, - subsamples: senc.subsamples, + iv: iv, + subsamples: senc?.subsamples, scheme: scheme, cryptByteBlock: cryptBlocks, skipByteBlock: skipBlocks ) { sample = decrypted data.replaceSubrange(sampleRange, with: sample) - didDecrypt = true + decryptedCount += 1 } } mdatCursor += size } - let decryptedCount = didDecrypt ? min(sencSamples.count, sampleSizes.count) : 0 diag("frag track=\(trackId) crypto=\(crypto != nil) scheme=\(scheme) pat=\(cryptBlocks):\(skipBlocks) samples=\(sampleSizes.count) senc=\(sencSamples.count) iv=\(sencSamples.first?.iv.count ?? 0) subs=\(sencSamples.first?.subsamples?.count ?? -1) size0=\(sampleSizes.first ?? 0) dec=\(decryptedCount) tfhd=0x\(String(tfhdFlagsSeen, radix: 16)) trun=0x\(String(trunFlagsSeen, radix: 16)) mdat=\(mdat.payloadLength)") // AVPlayer/VLC mogen geen tweede decrypt-poging doen op clear samples. - if didDecrypt { + if decryptedCount > 0 { for senc in findBoxesInRange(data, type: "senc", from: traf.payloadStart, to: traf.payloadEnd) { writeFourCC(&data, senc.start + 4, "free") } diff --git a/apps/ios/VMC/UI/SettingsScreen.swift b/apps/ios/VMC/UI/SettingsScreen.swift index a4c15f7..c374be0 100644 --- a/apps/ios/VMC/UI/SettingsScreen.swift +++ b/apps/ios/VMC/UI/SettingsScreen.swift @@ -96,7 +96,7 @@ struct SettingsScreen: View { Section("Info") { LabeledContent("App", value: "VMC iOS") - LabeledContent("Versie", value: "0.5.44") + LabeledContent("Versie", value: "0.5.45") LabeledContent("Live TV", value: app.iptvEnabled ? "Aan" : "Uit") LabeledContent("Events", value: app.eventsEnabled ? "Aan" : "Uit") }