diff --git a/src/config.rs b/src/config.rs index ac2fc8440..af775bc6c 100644 --- a/src/config.rs +++ b/src/config.rs @@ -455,12 +455,6 @@ pub enum Config { /// Return an error from `receive_imf_inner()`. For tests. SimulateReceiveImfError, - /// Enable composing emails with Header Protection as defined in - /// "Header Protection for Cryptographically - /// Protected Email". - #[strum(props(default = "1"))] - StdHeaderProtectionComposing, - /// Who can call me. /// /// The options are from the `WhoCanCallMe` enum. diff --git a/src/mimefactory.rs b/src/mimefactory.rs index 88853ac59..07a899e7a 100644 --- a/src/mimefactory.rs +++ b/src/mimefactory.rs @@ -1030,16 +1030,12 @@ impl MimeFactory { is_securejoin_message, ); - let use_std_header_protection = context - .get_config_bool(Config::StdHeaderProtectionComposing) - .await?; let outer_message = if let Some(encryption_pubkeys) = self.encryption_pubkeys { let mut message = add_headers_to_encrypted_part( message, &unprotected_headers, hidden_headers, protected_headers, - use_std_header_protection, ); // Add gossip headers in chats with multiple recipients @@ -1941,7 +1937,6 @@ fn add_headers_to_encrypted_part( unprotected_headers: &[(&'static str, HeaderType<'static>)], hidden_headers: Vec<(&'static str, HeaderType<'static>)>, protected_headers: Vec<(&'static str, HeaderType<'static>)>, - use_std_header_protection: bool, ) -> MimePart<'static> { // Store protected headers in the inner message. let message = protected_headers @@ -1957,21 +1952,19 @@ fn add_headers_to_encrypted_part( message.header(header, value) }); - if use_std_header_protection { - message = unprotected_headers - .iter() - // Structural headers shouldn't be added as "HP-Outer". They are defined in - // . - .filter(|(name, _)| { - !(name.eq_ignore_ascii_case("mime-version") - || name.eq_ignore_ascii_case("content-type") - || name.eq_ignore_ascii_case("content-transfer-encoding") - || name.eq_ignore_ascii_case("content-disposition")) - }) - .fold(message, |message, (name, value)| { - message.header(format!("HP-Outer: {name}"), value.clone()) - }); - } + message = unprotected_headers + .iter() + // Structural headers shouldn't be added as "HP-Outer". They are defined in + // . + .filter(|(name, _)| { + !(name.eq_ignore_ascii_case("mime-version") + || name.eq_ignore_ascii_case("content-type") + || name.eq_ignore_ascii_case("content-transfer-encoding") + || name.eq_ignore_ascii_case("content-disposition")) + }) + .fold(message, |message, (name, value)| { + message.header(format!("HP-Outer: {name}"), value.clone()) + }); // Set the appropriate Content-Type for the inner message for (h, v) in &mut message.headers { @@ -1980,9 +1973,7 @@ fn add_headers_to_encrypted_part( { let mut ct_new = ct.clone(); ct_new = ct_new.attribute("protected-headers", "v1"); - if use_std_header_protection { - ct_new = ct_new.attribute("hp", "cipher"); - } + ct_new = ct_new.attribute("hp", "cipher"); *ct = ct_new; break; } @@ -2324,13 +2315,11 @@ pub(crate) async fn render_symm_encrypted_securejoin_message( ); let outer_message = { - let use_std_header_protection = true; let message = add_headers_to_encrypted_part( message, &unprotected_headers, hidden_headers, protected_headers, - use_std_header_protection, ); // Disable compression for SecureJoin to ensure diff --git a/src/mimefactory/mimefactory_tests.rs b/src/mimefactory/mimefactory_tests.rs index 2893bd672..32ee79849 100644 --- a/src/mimefactory/mimefactory_tests.rs +++ b/src/mimefactory/mimefactory_tests.rs @@ -730,21 +730,14 @@ async fn test_hp_outer_headers() -> Result<()> { let t = &tcm.alice().await; let chat_id = t.get_self_chat().await.id; - for std_hp_composing in [false, true] { - t.set_config_bool(Config::StdHeaderProtectionComposing, std_hp_composing) - .await?; - chat::send_text_msg(t, chat_id, "hi!".to_string()).await?; - let sent_msg = t.pop_sent_msg().await; - let msg = MimeMessage::from_bytes(t, sent_msg.payload.as_bytes()).await?; - assert_eq!(msg.header_exists(HeaderDef::HpOuter), std_hp_composing); - for hdr in ["Date", "From", "Message-ID"] { - assert_eq!( - msg.decoded_data_contains(&format!("HP-Outer: {hdr}:")), - std_hp_composing, - ); - } - assert!(!msg.decoded_data_contains("HP-Outer: Content-Type")); + chat::send_text_msg(t, chat_id, "hi!".to_string()).await?; + let sent_msg = t.pop_sent_msg().await; + let msg = MimeMessage::from_bytes(t, sent_msg.payload.as_bytes()).await?; + assert!(msg.header_exists(HeaderDef::HpOuter)); + for hdr in ["Date", "From", "Message-ID"] { + assert!(msg.decoded_data_contains(&format!("HP-Outer: {hdr}:")),); } + assert!(!msg.decoded_data_contains("HP-Outer: Content-Type")); Ok(()) } diff --git a/src/mimeparser/mimeparser_tests.rs b/src/mimeparser/mimeparser_tests.rs index c2246b53d..562ea644a 100644 --- a/src/mimeparser/mimeparser_tests.rs +++ b/src/mimeparser/mimeparser_tests.rs @@ -1404,23 +1404,17 @@ async fn test_extra_imf_headers() -> Result<()> { let t = &tcm.alice().await; let chat_id = t.get_self_chat().await.id; - for std_hp_composing in [false, true] { - t.set_config_bool(Config::StdHeaderProtectionComposing, std_hp_composing) - .await?; - chat::send_text_msg(t, chat_id, "hi!".to_string()).await?; - let sent_msg = t.pop_sent_msg().await; - // Check removal of some nonexistent "Chat-*" header to protect the code from future - // breakages. But headers not prefixed with "Chat-" remain unless a message has standard - // Header Protection. - let payload = sent_msg.payload.replace( - "Message-ID:", - "Chat-Forty-Two: 42\r\nForty-Two: 42\r\nMessage-ID:", - ); - let msg = MimeMessage::from_bytes(t, payload.as_bytes()).await?; - assert!(msg.headers.contains_key("chat-version")); - assert!(!msg.headers.contains_key("chat-forty-two")); - assert_ne!(msg.headers.contains_key("forty-two"), std_hp_composing); - } + chat::send_text_msg(t, chat_id, "hi!".to_string()).await?; + let sent_msg = t.pop_sent_msg().await; + // Check that extra headers are ignored with RFC 9788 Header Protection. + let payload = sent_msg.payload.replace( + "Message-ID:", + "Chat-Forty-Two: 42\r\nForty-Two: 42\r\nMessage-ID:", + ); + let msg = MimeMessage::from_bytes(t, payload.as_bytes()).await?; + assert!(msg.headers.contains_key("chat-version")); + assert!(!msg.headers.contains_key("chat-forty-two")); + assert!(!msg.headers.contains_key("forty-two")); Ok(()) }