mirror of
https://github.com/chatmail/core.git
synced 2026-04-17 21:46:35 +03:00
rustify references, in_reply_to, mimefactory's recipients_{addr,names}
This commit is contained in:
@@ -784,7 +784,7 @@ pub fn send_msg(context: &Context, chat_id: u32, msg: &mut Message) -> Result<u3
|
|||||||
}
|
}
|
||||||
|
|
||||||
ensure!(
|
ensure!(
|
||||||
unsafe { job_send_msg(context, msg.id) } != 0,
|
job_send_msg(context, msg.id) != 0,
|
||||||
"Failed to initiate send job"
|
"Failed to initiate send job"
|
||||||
);
|
);
|
||||||
|
|
||||||
@@ -1787,7 +1787,7 @@ pub fn forward_msgs(context: &Context, msg_ids: &[u32], chat_id: u32) {
|
|||||||
new_msg_id = chat
|
new_msg_id = chat
|
||||||
.prepare_msg_raw(context, &mut msg, fresh10)
|
.prepare_msg_raw(context, &mut msg, fresh10)
|
||||||
.unwrap_or_default();
|
.unwrap_or_default();
|
||||||
unsafe { job_send_msg(context, new_msg_id) };
|
job_send_msg(context, new_msg_id);
|
||||||
}
|
}
|
||||||
created_db_entries.push(chat_id);
|
created_db_entries.push(chat_id);
|
||||||
created_db_entries.push(new_msg_id);
|
created_db_entries.push(new_msg_id);
|
||||||
|
|||||||
@@ -39,16 +39,16 @@ pub struct MimeFactory<'a> {
|
|||||||
pub from_addr: String,
|
pub from_addr: String,
|
||||||
pub from_displayname: String,
|
pub from_displayname: String,
|
||||||
pub selfstatus: String,
|
pub selfstatus: String,
|
||||||
pub recipients_names: *mut clist,
|
pub recipients_names: Vec<String>,
|
||||||
pub recipients_addr: *mut clist,
|
pub recipients_addr: Vec<String>,
|
||||||
pub timestamp: i64,
|
pub timestamp: i64,
|
||||||
pub rfc724_mid: String,
|
pub rfc724_mid: String,
|
||||||
pub loaded: Loaded,
|
pub loaded: Loaded,
|
||||||
pub msg: Message,
|
pub msg: Message,
|
||||||
pub chat: Option<Chat>,
|
pub chat: Option<Chat>,
|
||||||
pub increation: bool,
|
pub increation: bool,
|
||||||
pub in_reply_to: *mut libc::c_char,
|
pub in_reply_to: String,
|
||||||
pub references: *mut libc::c_char,
|
pub references: String,
|
||||||
pub req_mdn: bool,
|
pub req_mdn: bool,
|
||||||
pub out: *mut MMAPString,
|
pub out: *mut MMAPString,
|
||||||
pub out_encrypted: bool,
|
pub out_encrypted: bool,
|
||||||
@@ -65,16 +65,16 @@ impl<'a> MimeFactory<'a> {
|
|||||||
from_displayname: cget(&context, "displayname").unwrap_or_default(),
|
from_displayname: cget(&context, "displayname").unwrap_or_default(),
|
||||||
selfstatus: cget(&context, "selfstatus")
|
selfstatus: cget(&context, "selfstatus")
|
||||||
.unwrap_or_else(|| context.stock_str(StockMessage::StatusLine).to_string()),
|
.unwrap_or_else(|| context.stock_str(StockMessage::StatusLine).to_string()),
|
||||||
recipients_names: clist_new(),
|
recipients_names: Vec::with_capacity(5),
|
||||||
recipients_addr: clist_new(),
|
recipients_addr: Vec::with_capacity(5),
|
||||||
timestamp: 0,
|
timestamp: 0,
|
||||||
rfc724_mid: String::default(),
|
rfc724_mid: String::default(),
|
||||||
loaded: Loaded::Nothing,
|
loaded: Loaded::Nothing,
|
||||||
msg,
|
msg,
|
||||||
chat: None,
|
chat: None,
|
||||||
increation: false,
|
increation: false,
|
||||||
in_reply_to: ptr::null_mut(),
|
in_reply_to: String::default(),
|
||||||
references: ptr::null_mut(),
|
references: String::default(),
|
||||||
req_mdn: false,
|
req_mdn: false,
|
||||||
out: ptr::null_mut(),
|
out: ptr::null_mut(),
|
||||||
out_encrypted: false,
|
out_encrypted: false,
|
||||||
@@ -88,17 +88,6 @@ impl<'a> MimeFactory<'a> {
|
|||||||
impl<'a> Drop for MimeFactory<'a> {
|
impl<'a> Drop for MimeFactory<'a> {
|
||||||
fn drop(&mut self) {
|
fn drop(&mut self) {
|
||||||
unsafe {
|
unsafe {
|
||||||
if !self.recipients_names.is_null() {
|
|
||||||
clist_free_content(self.recipients_names);
|
|
||||||
clist_free(self.recipients_names);
|
|
||||||
}
|
|
||||||
if !self.recipients_addr.is_null() {
|
|
||||||
clist_free_content(self.recipients_addr);
|
|
||||||
clist_free(self.recipients_addr);
|
|
||||||
}
|
|
||||||
|
|
||||||
free(self.in_reply_to as *mut libc::c_void);
|
|
||||||
free(self.references as *mut libc::c_void);
|
|
||||||
if !self.out.is_null() {
|
if !self.out.is_null() {
|
||||||
mmap_string_free(self.out);
|
mmap_string_free(self.out);
|
||||||
}
|
}
|
||||||
@@ -106,10 +95,7 @@ impl<'a> Drop for MimeFactory<'a> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub unsafe fn dc_mimefactory_load_msg(
|
pub fn dc_mimefactory_load_msg(context: &Context, msg_id: u32) -> Result<MimeFactory, Error> {
|
||||||
context: &Context,
|
|
||||||
msg_id: u32,
|
|
||||||
) -> Result<MimeFactory, Error> {
|
|
||||||
ensure!(msg_id > DC_CHAT_ID_LAST_SPECIAL, "Invalid chat id");
|
ensure!(msg_id > DC_CHAT_ID_LAST_SPECIAL, "Invalid chat id");
|
||||||
|
|
||||||
let msg = Message::load_from_db(context, msg_id)?;
|
let msg = Message::load_from_db(context, msg_id)?;
|
||||||
@@ -121,16 +107,10 @@ pub unsafe fn dc_mimefactory_load_msg(
|
|||||||
let chat = factory.chat.as_ref().unwrap();
|
let chat = factory.chat.as_ref().unwrap();
|
||||||
|
|
||||||
if chat.is_self_talk() {
|
if chat.is_self_talk() {
|
||||||
clist_insert_after(
|
factory
|
||||||
factory.recipients_names,
|
.recipients_names
|
||||||
(*factory.recipients_names).last,
|
.push(factory.from_displayname.to_string());
|
||||||
factory.from_displayname.strdup().cast(),
|
factory.recipients_addr.push(factory.from_addr.to_string());
|
||||||
);
|
|
||||||
clist_insert_after(
|
|
||||||
factory.recipients_addr,
|
|
||||||
(*factory.recipients_addr).last,
|
|
||||||
factory.from_addr.strdup().cast(),
|
|
||||||
);
|
|
||||||
} else {
|
} else {
|
||||||
context
|
context
|
||||||
.sql
|
.sql
|
||||||
@@ -148,22 +128,9 @@ pub unsafe fn dc_mimefactory_load_msg(
|
|||||||
|rows| {
|
|rows| {
|
||||||
for row in rows {
|
for row in rows {
|
||||||
let (authname, addr) = row?;
|
let (authname, addr) = row?;
|
||||||
let addr_c = addr.strdup();
|
if !vec_contains_lowercase(&factory.recipients_addr, &addr) {
|
||||||
if !clist_search_string_nocase(factory.recipients_addr, addr_c) {
|
factory.recipients_addr.push(addr);
|
||||||
clist_insert_after(
|
factory.recipients_names.push(authname);
|
||||||
factory.recipients_names,
|
|
||||||
(*factory.recipients_names).last,
|
|
||||||
if !authname.is_empty() {
|
|
||||||
authname.strdup()
|
|
||||||
} else {
|
|
||||||
std::ptr::null_mut()
|
|
||||||
} as *mut libc::c_void,
|
|
||||||
);
|
|
||||||
clist_insert_after(
|
|
||||||
factory.recipients_addr,
|
|
||||||
(*factory.recipients_addr).last,
|
|
||||||
addr_c as *mut libc::c_void,
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Ok(())
|
Ok(())
|
||||||
@@ -176,7 +143,6 @@ pub unsafe fn dc_mimefactory_load_msg(
|
|||||||
|
|
||||||
if command == SystemMessage::MemberRemovedFromGroup {
|
if command == SystemMessage::MemberRemovedFromGroup {
|
||||||
let email_to_remove = msg.param.get(Param::Arg).unwrap_or_default();
|
let email_to_remove = msg.param.get(Param::Arg).unwrap_or_default();
|
||||||
let email_to_remove_c = email_to_remove.strdup();
|
|
||||||
|
|
||||||
let self_addr = context
|
let self_addr = context
|
||||||
.sql
|
.sql
|
||||||
@@ -184,17 +150,9 @@ pub unsafe fn dc_mimefactory_load_msg(
|
|||||||
.unwrap_or_default();
|
.unwrap_or_default();
|
||||||
|
|
||||||
if !email_to_remove.is_empty() && email_to_remove != self_addr {
|
if !email_to_remove.is_empty() && email_to_remove != self_addr {
|
||||||
if !clist_search_string_nocase(factory.recipients_addr, email_to_remove_c) {
|
if !vec_contains_lowercase(&factory.recipients_addr, &email_to_remove) {
|
||||||
clist_insert_after(
|
factory.recipients_names.push("".to_string());
|
||||||
factory.recipients_names,
|
factory.recipients_addr.push(email_to_remove.to_string());
|
||||||
(*factory.recipients_names).last,
|
|
||||||
ptr::null_mut(),
|
|
||||||
);
|
|
||||||
clist_insert_after(
|
|
||||||
factory.recipients_addr,
|
|
||||||
(*factory.recipients_addr).last,
|
|
||||||
email_to_remove_c as *mut libc::c_void,
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -220,8 +178,8 @@ pub unsafe fn dc_mimefactory_load_msg(
|
|||||||
);
|
);
|
||||||
match row {
|
match row {
|
||||||
Ok((in_reply_to, references)) => {
|
Ok((in_reply_to, references)) => {
|
||||||
factory.in_reply_to = in_reply_to.strdup();
|
factory.in_reply_to = in_reply_to;
|
||||||
factory.references = references.strdup();
|
factory.references = references;
|
||||||
}
|
}
|
||||||
Err(err) => {
|
Err(err) => {
|
||||||
error!(
|
error!(
|
||||||
@@ -239,7 +197,7 @@ pub unsafe fn dc_mimefactory_load_msg(
|
|||||||
Ok(factory)
|
Ok(factory)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub unsafe fn dc_mimefactory_load_mdn<'a>(
|
pub fn dc_mimefactory_load_mdn<'a>(
|
||||||
context: &'a Context,
|
context: &'a Context,
|
||||||
msg_id: u32,
|
msg_id: u32,
|
||||||
) -> Result<MimeFactory, Error> {
|
) -> Result<MimeFactory, Error> {
|
||||||
@@ -266,20 +224,10 @@ pub unsafe fn dc_mimefactory_load_mdn<'a>(
|
|||||||
"Invalid chat id"
|
"Invalid chat id"
|
||||||
);
|
);
|
||||||
|
|
||||||
clist_insert_after(
|
factory
|
||||||
factory.recipients_names,
|
.recipients_names
|
||||||
(*factory.recipients_names).last,
|
.push(contact.get_authname().to_string());
|
||||||
(if !contact.get_authname().is_empty() {
|
factory.recipients_addr.push(contact.get_addr().to_string());
|
||||||
contact.get_authname().strdup()
|
|
||||||
} else {
|
|
||||||
ptr::null_mut()
|
|
||||||
}) as *mut libc::c_void,
|
|
||||||
);
|
|
||||||
clist_insert_after(
|
|
||||||
factory.recipients_addr,
|
|
||||||
(*factory.recipients_addr).last,
|
|
||||||
contact.get_addr().strdup() as *mut libc::c_void,
|
|
||||||
);
|
|
||||||
factory.timestamp = dc_create_smeared_timestamp(factory.context);
|
factory.timestamp = dc_create_smeared_timestamp(factory.context);
|
||||||
factory.rfc724_mid = dc_create_outgoing_rfc724_mid(None, &factory.from_addr);
|
factory.rfc724_mid = dc_create_outgoing_rfc724_mid(None, &factory.from_addr);
|
||||||
factory.loaded = Loaded::MDN;
|
factory.loaded = Loaded::MDN;
|
||||||
@@ -287,6 +235,8 @@ pub unsafe fn dc_mimefactory_load_mdn<'a>(
|
|||||||
Ok(factory)
|
Ok(factory)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// XXX push down unsafe to only guard mailimf_* operations
|
||||||
|
|
||||||
pub unsafe fn dc_mimefactory_render(
|
pub unsafe fn dc_mimefactory_render(
|
||||||
context: &Context,
|
context: &Context,
|
||||||
factory: &mut MimeFactory,
|
factory: &mut MimeFactory,
|
||||||
@@ -299,7 +249,7 @@ pub unsafe fn dc_mimefactory_render(
|
|||||||
from,
|
from,
|
||||||
mailimf_mailbox_new(
|
mailimf_mailbox_new(
|
||||||
if !factory.from_displayname.is_empty() {
|
if !factory.from_displayname.is_empty() {
|
||||||
dc_encode_header_words(&factory.from_displayname)
|
dc_encode_header_words(&factory.from_displayname).strdup()
|
||||||
} else {
|
} else {
|
||||||
ptr::null_mut()
|
ptr::null_mut()
|
||||||
},
|
},
|
||||||
@@ -307,47 +257,38 @@ pub unsafe fn dc_mimefactory_render(
|
|||||||
),
|
),
|
||||||
);
|
);
|
||||||
let mut to: *mut mailimf_address_list = ptr::null_mut();
|
let mut to: *mut mailimf_address_list = ptr::null_mut();
|
||||||
if !factory.recipients_names.is_null()
|
if !factory.recipients_names.is_empty() && !factory.recipients_addr.is_empty() {
|
||||||
&& !factory.recipients_addr.is_null()
|
|
||||||
&& (*factory.recipients_addr).count > 0
|
|
||||||
{
|
|
||||||
let name_iter = (*factory.recipients_names).into_iter();
|
|
||||||
let addr_iter = (*factory.recipients_addr).into_iter();
|
|
||||||
to = mailimf_address_list_new_empty();
|
to = mailimf_address_list_new_empty();
|
||||||
|
let name_iter = factory.recipients_names.iter();
|
||||||
|
let addr_iter = factory.recipients_addr.iter();
|
||||||
for (name, addr) in name_iter.zip(addr_iter) {
|
for (name, addr) in name_iter.zip(addr_iter) {
|
||||||
let name = name as *const libc::c_char;
|
|
||||||
let addr = addr as *const libc::c_char;
|
|
||||||
mailimf_address_list_add(
|
mailimf_address_list_add(
|
||||||
to,
|
to,
|
||||||
mailimf_address_new(
|
mailimf_address_new(
|
||||||
MAILIMF_ADDRESS_MAILBOX as libc::c_int,
|
MAILIMF_ADDRESS_MAILBOX as libc::c_int,
|
||||||
mailimf_mailbox_new(
|
mailimf_mailbox_new(
|
||||||
if !name.is_null() {
|
if !name.is_empty() {
|
||||||
dc_encode_header_words(as_str(name))
|
dc_encode_header_words(&name).strdup()
|
||||||
} else {
|
} else {
|
||||||
ptr::null_mut()
|
ptr::null_mut()
|
||||||
},
|
},
|
||||||
dc_strdup(addr),
|
addr.strdup(),
|
||||||
),
|
),
|
||||||
ptr::null_mut(),
|
ptr::null_mut(),
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
let mut references_list: *mut clist = ptr::null_mut();
|
let references_list = if !factory.references.is_empty() {
|
||||||
if !factory.references.is_null() && 0 != *factory.references.offset(0isize) as libc::c_int {
|
dc_str_to_clist(&factory.references, " ")
|
||||||
references_list = dc_str_to_clist(
|
} else {
|
||||||
factory.references,
|
ptr::null_mut()
|
||||||
b" \x00" as *const u8 as *const libc::c_char,
|
};
|
||||||
)
|
let in_reply_to_list = if !factory.in_reply_to.is_empty() {
|
||||||
}
|
dc_str_to_clist(&factory.in_reply_to, " ")
|
||||||
let mut in_reply_to_list: *mut clist = ptr::null_mut();
|
} else {
|
||||||
if !factory.in_reply_to.is_null() && 0 != *factory.in_reply_to.offset(0isize) as libc::c_int {
|
ptr::null_mut()
|
||||||
in_reply_to_list = dc_str_to_clist(
|
};
|
||||||
factory.in_reply_to,
|
|
||||||
b" \x00" as *const u8 as *const libc::c_char,
|
|
||||||
)
|
|
||||||
}
|
|
||||||
let imf_fields = mailimf_fields_new_with_data_all(
|
let imf_fields = mailimf_fields_new_with_data_all(
|
||||||
mailimf_get_date(factory.timestamp as i64),
|
mailimf_get_date(factory.timestamp as i64),
|
||||||
from,
|
from,
|
||||||
@@ -432,18 +373,8 @@ pub unsafe fn dc_mimefactory_render(
|
|||||||
if chat.typ == Chattype::Group || chat.typ == Chattype::VerifiedGroup {
|
if chat.typ == Chattype::Group || chat.typ == Chattype::VerifiedGroup {
|
||||||
add_mailimf_field(imf_fields, "Chat-Group-ID", &chat.grpid);
|
add_mailimf_field(imf_fields, "Chat-Group-ID", &chat.grpid);
|
||||||
|
|
||||||
// we can't use add_mailimf_field() because
|
let encoded = dc_encode_header_words(&chat.name);
|
||||||
// dc_encode_header_words returns char* and most of its call sites
|
add_mailimf_field(imf_fields, "Chat-Group-Name", &encoded);
|
||||||
// use it rather directly to pass something to the
|
|
||||||
// low-level mailimf_* API.
|
|
||||||
let res = mailimf_fields_add(
|
|
||||||
imf_fields,
|
|
||||||
mailimf_field_new_custom(
|
|
||||||
"Chat-Group-Name".strdup(),
|
|
||||||
dc_encode_header_words(&chat.name),
|
|
||||||
),
|
|
||||||
);
|
|
||||||
assert!(res == MAILIMF_NO_ERROR as i32);
|
|
||||||
|
|
||||||
match command {
|
match command {
|
||||||
SystemMessage::MemberRemovedFromGroup => {
|
SystemMessage::MemberRemovedFromGroup => {
|
||||||
@@ -742,7 +673,6 @@ pub unsafe fn dc_mimefactory_render(
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
let subject = mailimf_subject_new(dc_encode_header_words(subject_str));
|
|
||||||
mailimf_fields_add(
|
mailimf_fields_add(
|
||||||
imf_fields,
|
imf_fields,
|
||||||
mailimf_field_new(
|
mailimf_field_new(
|
||||||
@@ -765,7 +695,7 @@ pub unsafe fn dc_mimefactory_render(
|
|||||||
ptr::null_mut(),
|
ptr::null_mut(),
|
||||||
ptr::null_mut(),
|
ptr::null_mut(),
|
||||||
ptr::null_mut(),
|
ptr::null_mut(),
|
||||||
subject,
|
mailimf_subject_new(dc_encode_header_words(subject_str).strdup()),
|
||||||
ptr::null_mut(),
|
ptr::null_mut(),
|
||||||
ptr::null_mut(),
|
ptr::null_mut(),
|
||||||
ptr::null_mut(),
|
ptr::null_mut(),
|
||||||
@@ -775,7 +705,7 @@ pub unsafe fn dc_mimefactory_render(
|
|||||||
if force_plaintext != DC_FP_NO_AUTOCRYPT_HEADER {
|
if force_plaintext != DC_FP_NO_AUTOCRYPT_HEADER {
|
||||||
e2ee_helper.encrypt(
|
e2ee_helper.encrypt(
|
||||||
factory.context,
|
factory.context,
|
||||||
factory.recipients_addr,
|
&factory.recipients_addr,
|
||||||
force_plaintext == DC_FP_ADD_AUTOCRYPT_HEADER,
|
force_plaintext == DC_FP_ADD_AUTOCRYPT_HEADER,
|
||||||
e2ee_guaranteed,
|
e2ee_guaranteed,
|
||||||
min_verified,
|
min_verified,
|
||||||
@@ -823,37 +753,44 @@ fn get_subject(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub unsafe fn add_mailimf_field(fields: *mut mailimf_fields, name: &str, value: &str) {
|
pub fn add_mailimf_field(fields: *mut mailimf_fields, name: &str, value: &str) {
|
||||||
let field = mailimf_field_new_custom(name.strdup(), value.strdup());
|
unsafe {
|
||||||
let res = mailimf_fields_add(fields, field);
|
let field = mailimf_field_new_custom(name.strdup(), value.strdup());
|
||||||
assert!(
|
let res = mailimf_fields_add(fields, field);
|
||||||
res as u32 == MAILIMF_NO_ERROR,
|
assert!(
|
||||||
"could not create mailimf field"
|
res as u32 == MAILIMF_NO_ERROR,
|
||||||
);
|
"could not create mailimf field"
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
unsafe fn build_body_text(text: &str) -> *mut mailmime {
|
fn build_body_text(text: &str) -> *mut mailmime {
|
||||||
let mime_fields: *mut mailmime_fields;
|
let mime_fields: *mut mailmime_fields;
|
||||||
let message_part: *mut mailmime;
|
let message_part: *mut mailmime;
|
||||||
let content: *mut mailmime_content;
|
let content: *mut mailmime_content;
|
||||||
content = mailmime_content_new_with_str(b"text/plain\x00" as *const u8 as *const libc::c_char);
|
unsafe {
|
||||||
clist_insert_after(
|
content =
|
||||||
(*content).ct_parameters,
|
mailmime_content_new_with_str(b"text/plain\x00" as *const u8 as *const libc::c_char);
|
||||||
(*(*content).ct_parameters).last,
|
clist_insert_after(
|
||||||
mailmime_param_new_with_data(
|
(*content).ct_parameters,
|
||||||
b"charset\x00" as *const u8 as *const libc::c_char as *mut libc::c_char,
|
(*(*content).ct_parameters).last,
|
||||||
b"utf-8\x00" as *const u8 as *const libc::c_char as *mut libc::c_char,
|
mailmime_param_new_with_data(
|
||||||
) as *mut libc::c_void,
|
b"charset\x00" as *const u8 as *const libc::c_char as *mut libc::c_char,
|
||||||
);
|
b"utf-8\x00" as *const u8 as *const libc::c_char as *mut libc::c_char,
|
||||||
mime_fields = mailmime_fields_new_encoding(MAILMIME_MECHANISM_8BIT as libc::c_int);
|
) as *mut libc::c_void,
|
||||||
message_part = mailmime_new_empty(content, mime_fields);
|
);
|
||||||
|
mime_fields = mailmime_fields_new_encoding(MAILMIME_MECHANISM_8BIT as libc::c_int);
|
||||||
|
message_part = mailmime_new_empty(content, mime_fields);
|
||||||
|
}
|
||||||
set_body_text(message_part, text);
|
set_body_text(message_part, text);
|
||||||
|
|
||||||
message_part
|
message_part
|
||||||
}
|
}
|
||||||
|
|
||||||
unsafe fn set_body_text(part: *mut mailmime, text: &str) {
|
fn set_body_text(part: *mut mailmime, text: &str) {
|
||||||
mailmime_set_body_text(part, text.strdup(), text.len());
|
unsafe {
|
||||||
|
mailmime_set_body_text(part, text.strdup(), text.len());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[allow(non_snake_case)]
|
#[allow(non_snake_case)]
|
||||||
@@ -950,7 +887,7 @@ fn build_body_file(context: &Context, msg: &Message, base_name: &str) -> (*mut m
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
let content = mailmime_content_new_with_str(mimetype.strdup());
|
let content = mailmime_content_new_with_str(mimetype.strdup());
|
||||||
let filename_encoded = dc_encode_header_words(&filename_to_send);
|
let filename_encoded = dc_encode_header_words(&filename_to_send).strdup();
|
||||||
clist_insert_after(
|
clist_insert_after(
|
||||||
(*content).ct_parameters,
|
(*content).ct_parameters,
|
||||||
(*(*content).ct_parameters).last,
|
(*(*content).ct_parameters).last,
|
||||||
@@ -969,6 +906,16 @@ fn build_body_file(context: &Context, msg: &Message, base_name: &str) -> (*mut m
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub(crate) fn vec_contains_lowercase(vec: &Vec<String>, part: &str) -> bool {
|
||||||
|
let partlc = part.to_lowercase();
|
||||||
|
for cur in vec.iter() {
|
||||||
|
if (*cur).to_lowercase() == partlc {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
false
|
||||||
|
}
|
||||||
|
|
||||||
/*******************************************************************************
|
/*******************************************************************************
|
||||||
* Render
|
* Render
|
||||||
******************************************************************************/
|
******************************************************************************/
|
||||||
|
|||||||
@@ -25,7 +25,7 @@ use crate::dc_tools::*;
|
|||||||
* @return Returns the encoded string which must be free()'d when no longed needed.
|
* @return Returns the encoded string which must be free()'d when no longed needed.
|
||||||
* On errors, NULL is returned.
|
* On errors, NULL is returned.
|
||||||
*/
|
*/
|
||||||
pub unsafe fn dc_encode_header_words(to_encode_r: impl AsRef<str>) -> *mut libc::c_char {
|
pub unsafe fn dc_encode_header_words(to_encode_r: impl AsRef<str>) -> String {
|
||||||
let to_encode =
|
let to_encode =
|
||||||
CString::new(to_encode_r.as_ref().as_bytes()).expect("invalid cstring to_encode");
|
CString::new(to_encode_r.as_ref().as_bytes()).expect("invalid cstring to_encode");
|
||||||
|
|
||||||
@@ -116,7 +116,9 @@ pub unsafe fn dc_encode_header_words(to_encode_r: impl AsRef<str>) -> *mut libc:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ret_str
|
let s = to_string(ret_str);
|
||||||
|
free(ret_str.cast());
|
||||||
|
s
|
||||||
}
|
}
|
||||||
|
|
||||||
unsafe fn quote_word(
|
unsafe fn quote_word(
|
||||||
@@ -330,7 +332,7 @@ unsafe fn print_hex(target: *mut libc::c_char, cur: *const libc::c_char) {
|
|||||||
mod tests {
|
mod tests {
|
||||||
use super::*;
|
use super::*;
|
||||||
|
|
||||||
use libc::{strcmp, strncmp};
|
use libc::strcmp;
|
||||||
use std::ffi::CStr;
|
use std::ffi::CStr;
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
@@ -353,19 +355,15 @@ mod tests {
|
|||||||
assert_eq!(CStr::from_ptr(buf1).to_str().unwrap(), "just ascii test");
|
assert_eq!(CStr::from_ptr(buf1).to_str().unwrap(), "just ascii test");
|
||||||
free(buf1 as *mut libc::c_void);
|
free(buf1 as *mut libc::c_void);
|
||||||
|
|
||||||
buf1 = dc_encode_header_words("abcdef");
|
assert_eq!(dc_encode_header_words("abcdef"), "abcdef");
|
||||||
assert_eq!(CStr::from_ptr(buf1).to_str().unwrap(), "abcdef");
|
|
||||||
free(buf1 as *mut libc::c_void);
|
|
||||||
|
|
||||||
buf1 = dc_encode_header_words(
|
let r = dc_encode_header_words(
|
||||||
std::string::String::from_utf8(b"test\xc3\xa4\xc3\xb6\xc3\xbc.txt".to_vec())
|
std::string::String::from_utf8(b"test\xc3\xa4\xc3\xb6\xc3\xbc.txt".to_vec())
|
||||||
.unwrap(),
|
.unwrap(),
|
||||||
);
|
);
|
||||||
assert_eq!(
|
assert!(r.starts_with("=?utf-8"));
|
||||||
strncmp(buf1, b"=?utf-8\x00" as *const u8 as *const libc::c_char, 7),
|
|
||||||
0
|
|
||||||
);
|
|
||||||
|
|
||||||
|
buf1 = r.strdup();
|
||||||
let buf2: *mut libc::c_char = dc_decode_header_words(buf1);
|
let buf2: *mut libc::c_char = dc_decode_header_words(buf1);
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
strcmp(
|
strcmp(
|
||||||
@@ -374,7 +372,6 @@ mod tests {
|
|||||||
),
|
),
|
||||||
0
|
0
|
||||||
);
|
);
|
||||||
free(buf1 as *mut libc::c_void);
|
|
||||||
free(buf2 as *mut libc::c_void);
|
free(buf2 as *mut libc::c_void);
|
||||||
|
|
||||||
buf1 = dc_decode_header_words(
|
buf1 = dc_decode_header_words(
|
||||||
@@ -388,7 +385,6 @@ mod tests {
|
|||||||
),
|
),
|
||||||
0
|
0
|
||||||
);
|
);
|
||||||
free(buf1 as *mut libc::c_void);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
180
src/dc_tools.rs
180
src/dc_tools.rs
@@ -9,7 +9,7 @@ use std::time::SystemTime;
|
|||||||
use std::{fmt, fs, ptr};
|
use std::{fmt, fs, ptr};
|
||||||
|
|
||||||
use chrono::{Local, TimeZone};
|
use chrono::{Local, TimeZone};
|
||||||
use libc::{free, memcpy, strcpy, strlen, strstr, uintptr_t};
|
use libc::{memcpy, strcpy, strlen, uintptr_t};
|
||||||
use mmime::clist::*;
|
use mmime::clist::*;
|
||||||
use mmime::mailimf_types::*;
|
use mmime::mailimf_types::*;
|
||||||
use rand::{thread_rng, Rng};
|
use rand::{thread_rng, Rng};
|
||||||
@@ -241,32 +241,14 @@ pub(crate) unsafe fn dc_str_from_clist(
|
|||||||
res.strdup()
|
res.strdup()
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) unsafe fn dc_str_to_clist(
|
pub(crate) fn dc_str_to_clist(str: &str, delimiter: &str) -> *mut clist {
|
||||||
str: *const libc::c_char,
|
unsafe {
|
||||||
delimiter: *const libc::c_char,
|
let list: *mut clist = clist_new();
|
||||||
) -> *mut clist {
|
for cur in str.split(&delimiter) {
|
||||||
let list: *mut clist = clist_new();
|
clist_insert_after(list, (*list).last, cur.strdup().cast());
|
||||||
assert!(!list.is_null());
|
|
||||||
|
|
||||||
if !str.is_null() && !delimiter.is_null() && strlen(delimiter) >= 1 {
|
|
||||||
let mut p1: *const libc::c_char = str;
|
|
||||||
loop {
|
|
||||||
let p2: *const libc::c_char = strstr(p1, delimiter);
|
|
||||||
if p2.is_null() {
|
|
||||||
clist_insert_after(list, (*list).last, strdup(p1) as *mut libc::c_void);
|
|
||||||
break;
|
|
||||||
} else {
|
|
||||||
clist_insert_after(
|
|
||||||
list,
|
|
||||||
(*list).last,
|
|
||||||
strndup(p1, p2.wrapping_offset_from(p1) as libc::c_ulong) as *mut libc::c_void,
|
|
||||||
);
|
|
||||||
p1 = p2.add(strlen(delimiter))
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
list
|
||||||
}
|
}
|
||||||
|
|
||||||
list
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* the colors must fulfill some criterions as:
|
/* the colors must fulfill some criterions as:
|
||||||
@@ -293,32 +275,6 @@ pub(crate) fn dc_str_to_color(s: impl AsRef<str>) -> u32 {
|
|||||||
COLORS[color_index]
|
COLORS[color_index]
|
||||||
}
|
}
|
||||||
|
|
||||||
/* clist tools */
|
|
||||||
|
|
||||||
/* calls free() for each item content */
|
|
||||||
pub(crate) unsafe fn clist_free_content(haystack: *const clist) {
|
|
||||||
let mut iter = (*haystack).first;
|
|
||||||
|
|
||||||
while !iter.is_null() {
|
|
||||||
free((*iter).data);
|
|
||||||
(*iter).data = ptr::null_mut();
|
|
||||||
iter = if !iter.is_null() {
|
|
||||||
(*iter).next
|
|
||||||
} else {
|
|
||||||
ptr::null_mut()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub(crate) unsafe fn clist_search_string_nocase(
|
|
||||||
haystack: *const clist,
|
|
||||||
needle: *const libc::c_char,
|
|
||||||
) -> bool {
|
|
||||||
(&*haystack)
|
|
||||||
.into_iter()
|
|
||||||
.any(|data| strcasecmp(data.cast(), needle) == 0)
|
|
||||||
}
|
|
||||||
|
|
||||||
/* date/time tools */
|
/* date/time tools */
|
||||||
/* the result is UTC or DC_INVALID_TIMESTAMP */
|
/* the result is UTC or DC_INVALID_TIMESTAMP */
|
||||||
pub(crate) unsafe fn dc_timestamp_from_date(date_time: *mut mailimf_date_time) -> i64 {
|
pub(crate) unsafe fn dc_timestamp_from_date(date_time: *mut mailimf_date_time) -> i64 {
|
||||||
@@ -496,25 +452,15 @@ pub(crate) fn dc_extract_grpid_from_rfc724_mid(mid: &str) -> Option<&str> {
|
|||||||
None
|
None
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) unsafe fn dc_extract_grpid_from_rfc724_mid_list(
|
pub(crate) fn dc_extract_grpid_from_rfc724_mid_list(list: *const clist) -> *mut libc::c_char {
|
||||||
list: *const clist,
|
|
||||||
) -> *mut libc::c_char {
|
|
||||||
if !list.is_null() {
|
if !list.is_null() {
|
||||||
let mut cur: *mut clistiter = (*list).first;
|
unsafe {
|
||||||
while !cur.is_null() {
|
for cur in (*list).into_iter() {
|
||||||
let mid = if !cur.is_null() {
|
let mid = as_str(cur as *const libc::c_char);
|
||||||
as_str((*cur).data as *const libc::c_char)
|
|
||||||
} else {
|
|
||||||
""
|
|
||||||
};
|
|
||||||
|
|
||||||
if let Some(grpid) = dc_extract_grpid_from_rfc724_mid(mid) {
|
if let Some(grpid) = dc_extract_grpid_from_rfc724_mid(mid) {
|
||||||
return grpid.strdup();
|
return grpid.strdup();
|
||||||
}
|
}
|
||||||
cur = if !cur.is_null() {
|
|
||||||
(*cur).next
|
|
||||||
} else {
|
|
||||||
ptr::null_mut()
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1082,21 +1028,6 @@ pub(crate) unsafe fn strdup(s: *const libc::c_char) -> *mut libc::c_char {
|
|||||||
result as *mut _
|
result as *mut _
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) fn strndup(s: *const libc::c_char, n: libc::c_ulong) -> *mut libc::c_char {
|
|
||||||
if s.is_null() {
|
|
||||||
return std::ptr::null_mut();
|
|
||||||
}
|
|
||||||
|
|
||||||
let end = std::cmp::min(n as usize, unsafe { strlen(s) });
|
|
||||||
unsafe {
|
|
||||||
let result = libc::malloc(end + 1);
|
|
||||||
memcpy(result, s as *const _, end);
|
|
||||||
std::ptr::write_bytes(result.offset(end as isize), b'\x00', 1);
|
|
||||||
|
|
||||||
result as *mut _
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub(crate) unsafe fn strcasecmp(s1: *const libc::c_char, s2: *const libc::c_char) -> libc::c_int {
|
pub(crate) unsafe fn strcasecmp(s1: *const libc::c_char, s2: *const libc::c_char) -> libc::c_int {
|
||||||
let s1 = std::ffi::CStr::from_ptr(s1)
|
let s1 = std::ffi::CStr::from_ptr(s1)
|
||||||
.to_string_lossy()
|
.to_string_lossy()
|
||||||
@@ -1115,7 +1046,7 @@ pub(crate) unsafe fn strcasecmp(s1: *const libc::c_char, s2: *const libc::c_char
|
|||||||
mod tests {
|
mod tests {
|
||||||
use super::*;
|
use super::*;
|
||||||
|
|
||||||
use libc::strcmp;
|
use libc::{free, strcmp};
|
||||||
use std::convert::TryInto;
|
use std::convert::TryInto;
|
||||||
use std::ffi::CStr;
|
use std::ffi::CStr;
|
||||||
|
|
||||||
@@ -1147,24 +1078,6 @@ mod tests {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
|
||||||
fn test_dc_strdup_keep_null() {
|
|
||||||
unsafe {
|
|
||||||
let str_a = b"foobar\x00" as *const u8 as *const libc::c_char;
|
|
||||||
let str_a_copy = dc_strdup_keep_null(str_a);
|
|
||||||
assert_eq!(
|
|
||||||
CStr::from_ptr(str_a_copy),
|
|
||||||
CString::new("foobar").unwrap().as_c_str()
|
|
||||||
);
|
|
||||||
assert_ne!(str_a, str_a_copy);
|
|
||||||
|
|
||||||
let str_a = ptr::null();
|
|
||||||
let str_a_copy = dc_strdup_keep_null(str_a);
|
|
||||||
assert_eq!(str_a.is_null(), true);
|
|
||||||
assert_eq!(str_a_copy.is_null(), true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_dc_ltrim() {
|
fn test_dc_ltrim() {
|
||||||
unsafe {
|
unsafe {
|
||||||
@@ -1273,49 +1186,50 @@ mod tests {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* calls free() for each item content */
|
||||||
|
unsafe fn clist_free_content(haystack: *const clist) {
|
||||||
|
let mut iter = (*haystack).first;
|
||||||
|
|
||||||
|
while !iter.is_null() {
|
||||||
|
free((*iter).data);
|
||||||
|
(*iter).data = ptr::null_mut();
|
||||||
|
iter = if !iter.is_null() {
|
||||||
|
(*iter).next
|
||||||
|
} else {
|
||||||
|
ptr::null_mut()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn strndup(s: *const libc::c_char, n: libc::c_ulong) -> *mut libc::c_char {
|
||||||
|
if s.is_null() {
|
||||||
|
return std::ptr::null_mut();
|
||||||
|
}
|
||||||
|
|
||||||
|
let end = std::cmp::min(n as usize, unsafe { strlen(s) });
|
||||||
|
unsafe {
|
||||||
|
let result = libc::malloc(end + 1);
|
||||||
|
memcpy(result, s as *const _, end);
|
||||||
|
std::ptr::write_bytes(result.offset(end as isize), b'\x00', 1);
|
||||||
|
|
||||||
|
result as *mut _
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_dc_str_to_clist_1() {
|
fn test_dc_str_to_clist_1() {
|
||||||
unsafe {
|
unsafe {
|
||||||
let list = dc_str_to_clist(ptr::null(), b" \x00" as *const u8 as *const libc::c_char);
|
let list = dc_str_to_clist("", " ");
|
||||||
assert_eq!((*list).count, 0);
|
|
||||||
clist_free_content(list);
|
|
||||||
clist_free(list);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#[test]
|
|
||||||
fn test_dc_str_to_clist_2() {
|
|
||||||
unsafe {
|
|
||||||
let list: *mut clist = dc_str_to_clist(
|
|
||||||
b"\x00" as *const u8 as *const libc::c_char,
|
|
||||||
b" \x00" as *const u8 as *const libc::c_char,
|
|
||||||
);
|
|
||||||
assert_eq!((*list).count, 1);
|
assert_eq!((*list).count, 1);
|
||||||
clist_free_content(list);
|
clist_free_content(list);
|
||||||
clist_free(list);
|
clist_free(list);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
|
||||||
fn test_dc_str_to_clist_3() {
|
|
||||||
unsafe {
|
|
||||||
let list: *mut clist = dc_str_to_clist(
|
|
||||||
b" \x00" as *const u8 as *const libc::c_char,
|
|
||||||
b" \x00" as *const u8 as *const libc::c_char,
|
|
||||||
);
|
|
||||||
assert_eq!((*list).count, 2);
|
|
||||||
clist_free_content(list);
|
|
||||||
clist_free(list);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_dc_str_to_clist_4() {
|
fn test_dc_str_to_clist_4() {
|
||||||
unsafe {
|
unsafe {
|
||||||
let list: *mut clist = dc_str_to_clist(
|
let list: *mut clist = dc_str_to_clist("foo bar test", " ");
|
||||||
b"foo bar test\x00" as *const u8 as *const libc::c_char,
|
|
||||||
b" \x00" as *const u8 as *const libc::c_char,
|
|
||||||
);
|
|
||||||
assert_eq!((*list).count, 3);
|
assert_eq!((*list).count, 3);
|
||||||
let str: *mut libc::c_char =
|
let str: *mut libc::c_char =
|
||||||
dc_str_from_clist(list, b" \x00" as *const u8 as *const libc::c_char);
|
dc_str_from_clist(list, b" \x00" as *const u8 as *const libc::c_char);
|
||||||
|
|||||||
12
src/e2ee.rs
12
src/e2ee.rs
@@ -53,7 +53,7 @@ impl E2eeHelper {
|
|||||||
pub unsafe fn encrypt(
|
pub unsafe fn encrypt(
|
||||||
&mut self,
|
&mut self,
|
||||||
context: &Context,
|
context: &Context,
|
||||||
recipients_addr: *const clist,
|
recipients_addr: &Vec<String>,
|
||||||
force_unencrypted: bool,
|
force_unencrypted: bool,
|
||||||
e2ee_guaranteed: bool,
|
e2ee_guaranteed: bool,
|
||||||
min_verified: libc::c_int,
|
min_verified: libc::c_int,
|
||||||
@@ -69,10 +69,7 @@ impl E2eeHelper {
|
|||||||
let plain: *mut MMAPString = mmap_string_new(b"\x00" as *const u8 as *const libc::c_char);
|
let plain: *mut MMAPString = mmap_string_new(b"\x00" as *const u8 as *const libc::c_char);
|
||||||
let mut peerstates: Vec<Peerstate> = Vec::new();
|
let mut peerstates: Vec<Peerstate> = Vec::new();
|
||||||
|
|
||||||
if !(recipients_addr.is_null()
|
if !(in_out_message.is_null() || !(*in_out_message).mm_parent.is_null() || plain.is_null())
|
||||||
|| in_out_message.is_null()
|
|
||||||
|| !(*in_out_message).mm_parent.is_null()
|
|
||||||
|| plain.is_null())
|
|
||||||
{
|
{
|
||||||
/* libEtPan's pgp_encrypt_mime() takes the parent as the new root. We just expect the root as being given to this function. */
|
/* libEtPan's pgp_encrypt_mime() takes the parent as the new root. We just expect the root as being given to this function. */
|
||||||
let prefer_encrypt = if 0
|
let prefer_encrypt = if 0
|
||||||
@@ -97,9 +94,8 @@ impl E2eeHelper {
|
|||||||
/*only for random-seed*/
|
/*only for random-seed*/
|
||||||
if prefer_encrypt == EncryptPreference::Mutual || e2ee_guaranteed {
|
if prefer_encrypt == EncryptPreference::Mutual || e2ee_guaranteed {
|
||||||
do_encrypt = 1i32;
|
do_encrypt = 1i32;
|
||||||
for cur_data in (*recipients_addr).into_iter() {
|
for recipient_addr in recipients_addr.iter() {
|
||||||
let recipient_addr = to_string(cur_data as *const libc::c_char);
|
if *recipient_addr != addr {
|
||||||
if recipient_addr != addr {
|
|
||||||
let peerstate =
|
let peerstate =
|
||||||
Peerstate::from_addr(context, &context.sql, &recipient_addr);
|
Peerstate::from_addr(context, &context.sql, &recipient_addr);
|
||||||
if peerstate.is_some()
|
if peerstate.is_some()
|
||||||
|
|||||||
39
src/job.rs
39
src/job.rs
@@ -1,8 +1,6 @@
|
|||||||
use std::ptr;
|
|
||||||
use std::time::Duration;
|
use std::time::Duration;
|
||||||
|
|
||||||
use deltachat_derive::{FromSql, ToSql};
|
use deltachat_derive::{FromSql, ToSql};
|
||||||
use mmime::clist::*;
|
|
||||||
use rand::{thread_rng, Rng};
|
use rand::{thread_rng, Rng};
|
||||||
|
|
||||||
use crate::chat;
|
use crate::chat;
|
||||||
@@ -642,7 +640,7 @@ pub fn job_action_exists(context: &Context, action: Action) -> bool {
|
|||||||
|
|
||||||
/* special case for DC_JOB_SEND_MSG_TO_SMTP */
|
/* special case for DC_JOB_SEND_MSG_TO_SMTP */
|
||||||
#[allow(non_snake_case)]
|
#[allow(non_snake_case)]
|
||||||
pub unsafe fn job_send_msg(context: &Context, msg_id: u32) -> libc::c_int {
|
pub fn job_send_msg(context: &Context, msg_id: u32) -> libc::c_int {
|
||||||
let mut success = 0;
|
let mut success = 0;
|
||||||
|
|
||||||
/* load message data */
|
/* load message data */
|
||||||
@@ -680,7 +678,7 @@ pub unsafe fn job_send_msg(context: &Context, msg_id: u32) -> libc::c_int {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
/* create message */
|
/* create message */
|
||||||
if let Err(msg) = dc_mimefactory_render(context, &mut mimefactory) {
|
if let Err(msg) = unsafe { dc_mimefactory_render(context, &mut mimefactory) } {
|
||||||
let e = msg.to_string();
|
let e = msg.to_string();
|
||||||
message::set_msg_failed(context, msg_id, Some(e));
|
message::set_msg_failed(context, msg_id, Some(e));
|
||||||
} else if 0
|
} else if 0
|
||||||
@@ -704,20 +702,12 @@ pub unsafe fn job_send_msg(context: &Context, msg_id: u32) -> libc::c_int {
|
|||||||
Some("End-to-end-encryption unavailable unexpectedly."),
|
Some("End-to-end-encryption unavailable unexpectedly."),
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
let from_addr_c = mimefactory.from_addr.strdup();
|
if !vec_contains_lowercase(&mimefactory.recipients_addr, &mimefactory.from_addr) {
|
||||||
if !clist_search_string_nocase(mimefactory.recipients_addr, from_addr_c) {
|
mimefactory.recipients_names.push("".to_string());
|
||||||
clist_insert_after(
|
mimefactory
|
||||||
mimefactory.recipients_names,
|
.recipients_addr
|
||||||
(*mimefactory.recipients_names).last,
|
.push(mimefactory.from_addr.to_string());
|
||||||
ptr::null_mut(),
|
|
||||||
);
|
|
||||||
clist_insert_after(
|
|
||||||
mimefactory.recipients_addr,
|
|
||||||
(*mimefactory.recipients_addr).last,
|
|
||||||
mimefactory.from_addr.strdup().cast(),
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
libc::free(from_addr_c.cast());
|
|
||||||
if mimefactory.out_gossiped {
|
if mimefactory.out_gossiped {
|
||||||
chat::set_gossiped_timestamp(context, mimefactory.msg.chat_id, time());
|
chat::set_gossiped_timestamp(context, mimefactory.msg.chat_id, time());
|
||||||
}
|
}
|
||||||
@@ -1000,7 +990,7 @@ fn connect_to_inbox(context: &Context, inbox: &Imap) -> libc::c_int {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fn send_mdn(context: &Context, msg_id: u32) {
|
fn send_mdn(context: &Context, msg_id: u32) {
|
||||||
if let Ok(mut mimefactory) = unsafe { dc_mimefactory_load_mdn(context, msg_id) } {
|
if let Ok(mut mimefactory) = dc_mimefactory_load_mdn(context, msg_id) {
|
||||||
if unsafe { dc_mimefactory_render(context, &mut mimefactory) }.is_ok() {
|
if unsafe { dc_mimefactory_render(context, &mut mimefactory) }.is_ok() {
|
||||||
add_smtp_job(context, Action::SendMdn, &mut mimefactory);
|
add_smtp_job(context, Action::SendMdn, &mut mimefactory);
|
||||||
}
|
}
|
||||||
@@ -1010,7 +1000,6 @@ fn send_mdn(context: &Context, msg_id: u32) {
|
|||||||
#[allow(non_snake_case)]
|
#[allow(non_snake_case)]
|
||||||
fn add_smtp_job(context: &Context, action: Action, mimefactory: &MimeFactory) -> libc::c_int {
|
fn add_smtp_job(context: &Context, action: Action, mimefactory: &MimeFactory) -> libc::c_int {
|
||||||
let mut success: libc::c_int = 0i32;
|
let mut success: libc::c_int = 0i32;
|
||||||
let mut recipients: *mut libc::c_char = ptr::null_mut();
|
|
||||||
let mut param = Params::new();
|
let mut param = Params::new();
|
||||||
let path_filename = dc_get_fine_path_filename(context, "$BLOBDIR", &mimefactory.rfc724_mid);
|
let path_filename = dc_get_fine_path_filename(context, "$BLOBDIR", &mimefactory.rfc724_mid);
|
||||||
let bytes = unsafe {
|
let bytes = unsafe {
|
||||||
@@ -1027,14 +1016,9 @@ fn add_smtp_job(context: &Context, action: Action, mimefactory: &MimeFactory) ->
|
|||||||
path_filename.display(),
|
path_filename.display(),
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
recipients = unsafe {
|
let recipients = mimefactory.recipients_addr.join("\x1e");
|
||||||
dc_str_from_clist(
|
|
||||||
mimefactory.recipients_addr,
|
|
||||||
b"\x1e\x00" as *const u8 as *const libc::c_char,
|
|
||||||
)
|
|
||||||
};
|
|
||||||
param.set(Param::File, path_filename.to_string_lossy());
|
param.set(Param::File, path_filename.to_string_lossy());
|
||||||
param.set(Param::Recipients, as_str(recipients));
|
param.set(Param::Recipients, &recipients);
|
||||||
job_add(
|
job_add(
|
||||||
context,
|
context,
|
||||||
action,
|
action,
|
||||||
@@ -1048,9 +1032,6 @@ fn add_smtp_job(context: &Context, action: Action, mimefactory: &MimeFactory) ->
|
|||||||
);
|
);
|
||||||
success = 1;
|
success = 1;
|
||||||
}
|
}
|
||||||
unsafe {
|
|
||||||
libc::free(recipients.cast());
|
|
||||||
}
|
|
||||||
success
|
success
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user