diff --git a/examples/repl/cmdline.rs b/examples/repl/cmdline.rs index 04baad93e..215e4d5d7 100644 --- a/examples/repl/cmdline.rs +++ b/examples/repl/cmdline.rs @@ -11,7 +11,6 @@ use deltachat::dc_contact::*; use deltachat::dc_context::*; use deltachat::dc_dehtml::*; use deltachat::dc_e2ee::*; -use deltachat::dc_hash::*; use deltachat::dc_imap::*; use deltachat::dc_imex::*; use deltachat::dc_job::*; diff --git a/examples/repl/main.rs b/examples/repl/main.rs index a8dfcc6d4..0ae30285a 100644 --- a/examples/repl/main.rs +++ b/examples/repl/main.rs @@ -30,7 +30,6 @@ use deltachat::dc_contact::*; use deltachat::dc_context::*; use deltachat::dc_dehtml::*; use deltachat::dc_e2ee::*; -use deltachat::dc_hash::*; use deltachat::dc_imap::*; use deltachat::dc_imex::*; use deltachat::dc_job::*; diff --git a/src/dc_e2ee.rs b/src/dc_e2ee.rs index c3cc3d26c..31bc9b753 100644 --- a/src/dc_e2ee.rs +++ b/src/dc_e2ee.rs @@ -1,3 +1,4 @@ +use std::collections::HashSet; use std::ffi::{CStr, CString}; use std::str::FromStr; @@ -16,7 +17,6 @@ use mmime::{mailmime_substitute, MAILIMF_NO_ERROR, MAIL_NO_ERROR}; use crate::dc_aheader::*; use crate::dc_context::dc_context_t; -use crate::dc_hash::*; use crate::dc_key::*; use crate::dc_keyring::*; use crate::dc_log::*; @@ -35,14 +35,25 @@ use crate::x::*; // as an upper limit, we double the size; the core won't send messages larger than this // to get the netto sizes, we substract 1 mb header-overhead and the base64-overhead. // some defaults -#[derive(Copy, Clone)] -#[repr(C)] +#[derive(Clone)] pub struct dc_e2ee_helper_t { pub encryption_successfull: libc::c_int, pub cdata_to_free: *mut libc::c_void, pub encrypted: libc::c_int, - pub signatures: *mut dc_hash_t, - pub gossipped_addr: *mut dc_hash_t, + pub signatures: HashSet, + pub gossipped_addr: HashSet, +} + +impl Default for dc_e2ee_helper_t { + fn default() -> Self { + dc_e2ee_helper_t { + encryption_successfull: 0, + cdata_to_free: std::ptr::null_mut(), + encrypted: 0, + signatures: Default::default(), + gossipped_addr: Default::default(), + } + } } pub unsafe fn dc_e2ee_encrypt( @@ -53,7 +64,7 @@ pub unsafe fn dc_e2ee_encrypt( min_verified: libc::c_int, do_gossip: libc::c_int, mut in_out_message: *mut mailmime, - mut helper: *mut dc_e2ee_helper_t, + helper: &mut dc_e2ee_helper_t, ) { let mut current_block: u64 = 0; let mut col: libc::c_int = 0i32; @@ -63,19 +74,12 @@ pub unsafe fn dc_e2ee_encrypt( let mut keyring = Keyring::default(); let plain: *mut MMAPString = mmap_string_new(b"\x00" as *const u8 as *const libc::c_char); let mut peerstates: Vec = Vec::new(); - if !helper.is_null() { - memset( - helper as *mut libc::c_void, - 0, - ::std::mem::size_of::(), - ); - } + *helper = Default::default(); if !(recipients_addr.is_null() || in_out_message.is_null() || !(*in_out_message).mm_parent.is_null() - || plain.is_null() - || helper.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. */ let prefer_encrypt = if 0 @@ -574,7 +578,7 @@ unsafe fn load_or_generate_self_public_key( pub unsafe fn dc_e2ee_decrypt( context: &dc_context_t, in_out_message: *mut mailmime, - mut helper: *mut dc_e2ee_helper_t, + helper: &mut dc_e2ee_helper_t, ) { let mut iterations: libc::c_int; /* return values: 0=nothing to decrypt/cannot decrypt, 1=sth. decrypted @@ -587,14 +591,7 @@ pub unsafe fn dc_e2ee_decrypt( let mut private_keyring = Keyring::default(); let mut public_keyring_for_validate = Keyring::default(); let mut gossip_headers: *mut mailimf_fields = 0 as *mut mailimf_fields; - if !helper.is_null() { - memset( - helper as *mut libc::c_void, - 0i32, - ::std::mem::size_of::(), - ); - } - if !(in_out_message.is_null() || helper.is_null() || imffields.is_null()) { + if !(in_out_message.is_null() || imffields.is_null()) { if !imffields.is_null() { let mut field: *mut mailimf_field = mailimf_find_field(imffields, MAILIMF_FIELD_FROM as libc::c_int); @@ -665,8 +662,6 @@ pub unsafe fn dc_e2ee_decrypt( public_keyring_for_validate.add_ref(key); } } - (*helper).signatures = malloc(::std::mem::size_of::()) as *mut dc_hash_t; - dc_hash_init((*helper).signatures, 3i32, 1i32); iterations = 0i32; while iterations < 10i32 { let mut has_unencrypted_parts: libc::c_int = 0i32; @@ -675,19 +670,19 @@ pub unsafe fn dc_e2ee_decrypt( in_out_message, &private_keyring, &public_keyring_for_validate, - (*helper).signatures, + &mut helper.signatures, &mut gossip_headers, &mut has_unencrypted_parts, ) { break; } if iterations == 0i32 && 0 == has_unencrypted_parts { - (*helper).encrypted = 1i32 + helper.encrypted = 1i32 } iterations += 1 } if !gossip_headers.is_null() { - (*helper).gossipped_addr = + helper.gossipped_addr = update_gossip_peerstates(context, message_time, imffields, gossip_headers) } } @@ -707,10 +702,10 @@ unsafe fn update_gossip_peerstates( message_time: time_t, imffields: *mut mailimf_fields, gossip_headers: *const mailimf_fields, -) -> *mut dc_hash_t { +) -> HashSet { let mut cur1: *mut clistiter; - let mut recipients: *mut dc_hash_t = 0 as *mut dc_hash_t; - let mut gossipped_addr: *mut dc_hash_t = 0 as *mut dc_hash_t; + let mut recipients: Option> = None; + let mut gossipped_addr: HashSet = Default::default(); cur1 = (*(*gossip_headers).fld_list).first; while !cur1.is_null() { let field: *mut mailimf_field = (if !cur1.is_null() { @@ -733,16 +728,10 @@ unsafe fn update_gossip_peerstates( .unwrap(); let gossip_header = Aheader::from_str(value); if let Ok(ref header) = gossip_header { - if recipients.is_null() { - recipients = mailimf_get_recipients(imffields) + if recipients.is_none() { + recipients = Some(mailimf_get_recipients(imffields)); } - if !dc_hash_find( - recipients, - CString::new(header.addr.clone()).unwrap().as_ptr() as *const libc::c_void, - header.addr.len() as i32, - ) - .is_null() - { + if recipients.as_ref().unwrap().contains(&header.addr) { let mut peerstate = Peerstate::from_addr( context, &context.sql.clone().read().unwrap(), @@ -762,18 +751,7 @@ unsafe fn update_gossip_peerstates( } } - if gossipped_addr.is_null() { - gossipped_addr = - malloc(::std::mem::size_of::()) as *mut dc_hash_t; - dc_hash_init(gossipped_addr, 3i32, 1i32); - } - dc_hash_insert( - gossipped_addr, - CString::new(header.addr.clone()).unwrap().as_ptr() - as *const libc::c_void, - header.addr.len() as libc::c_int, - 1i32 as *mut libc::c_void, - ); + gossipped_addr.insert(header.addr.clone()); } else { dc_log_info( context, @@ -792,10 +770,6 @@ unsafe fn update_gossip_peerstates( 0 as *mut clistcell } } - if !recipients.is_null() { - dc_hash_clear(recipients); - free(recipients as *mut libc::c_void); - } gossipped_addr } @@ -806,7 +780,7 @@ unsafe fn decrypt_recursive( mime: *mut mailmime, private_keyring: &Keyring, public_keyring_for_validate: &Keyring, - ret_valid_signatures: *mut dc_hash_t, + ret_valid_signatures: &mut HashSet, ret_gossip_headers: *mut *mut mailimf_fields, ret_has_unencrypted_parts: *mut libc::c_int, ) -> libc::c_int { @@ -839,7 +813,7 @@ unsafe fn decrypt_recursive( ret_valid_signatures, &mut decrypted_mime, ) { - if (*ret_gossip_headers).is_null() && (*ret_valid_signatures).count > 0i32 { + if (*ret_gossip_headers).is_null() && ret_valid_signatures.len() > 0 { let mut dummy: size_t = 0i32 as size_t; let mut test: *mut mailimf_fields = 0 as *mut mailimf_fields; if mailimf_envelope_and_optional_fields_parse( @@ -913,10 +887,9 @@ unsafe fn decrypt_part( mime: *mut mailmime, private_keyring: &Keyring, public_keyring_for_validate: &Keyring, - ret_valid_signatures: *mut dc_hash_t, + ret_valid_signatures: &mut HashSet, ret_decrypted_mime: *mut *mut mailmime, ) -> libc::c_int { - let add_signatures: *mut dc_hash_t; let current_block: u64; let mime_data: *mut mailmime_data; let mut mime_transfer_encoding: libc::c_int = MAILMIME_MECHANISM_BINARY as libc::c_int; @@ -996,13 +969,13 @@ unsafe fn decrypt_part( /* encrypted, decoded data in decoded_data now ... */ if !(0 == has_decrypted_pgp_armor(decoded_data, decoded_data_bytes as libc::c_int)) { - add_signatures = if (*ret_valid_signatures).count <= 0i32 { - ret_valid_signatures + let add_signatures = if ret_valid_signatures.is_empty() { + Some(ret_valid_signatures) } else { - 0 as *mut dc_hash_t + None }; - /*if we already have fingerprints, do not add more; this ensures, only the fingerprints from the outer-most part are collected */ + /*if we already have fingerprints, do not add more; this ensures, only the fingerprints from the outer-most part are collected */ if let Some(plain) = dc_pgp_pk_decrypt( decoded_data as *const libc::c_void, decoded_data_bytes, @@ -1134,22 +1107,9 @@ unsafe fn contains_report(mime: *mut mailmime) -> libc::c_int { } /* frees data referenced by "mailmime" but not freed by mailmime_free(). After calling this function, in_out_message cannot be used any longer! */ -pub unsafe fn dc_e2ee_thanks(mut helper: *mut dc_e2ee_helper_t) { - if helper.is_null() { - return; - } - free((*helper).cdata_to_free); - (*helper).cdata_to_free = 0 as *mut libc::c_void; - if !(*helper).gossipped_addr.is_null() { - dc_hash_clear((*helper).gossipped_addr); - free((*helper).gossipped_addr as *mut libc::c_void); - (*helper).gossipped_addr = 0 as *mut dc_hash_t - } - if !(*helper).signatures.is_null() { - dc_hash_clear((*helper).signatures); - free((*helper).signatures as *mut libc::c_void); - (*helper).signatures = 0 as *mut dc_hash_t - }; +pub unsafe fn dc_e2ee_thanks(helper: &mut dc_e2ee_helper_t) { + free(helper.cdata_to_free); + helper.cdata_to_free = 0 as *mut libc::c_void; } /* makes sure, the private key exists, needed only for exporting keys and the case no message was sent before */ diff --git a/src/dc_hash.rs b/src/dc_hash.rs deleted file mode 100644 index bccb9d404..000000000 --- a/src/dc_hash.rs +++ /dev/null @@ -1,891 +0,0 @@ -use crate::types::*; -use crate::x::*; - -/* A complete hash table is an instance of the following structure. - * The internals of this structure are intended to be opaque -- client - * code should not attempt to access or modify the fields of this structure - * directly. Change this structure only by using the routines below. - * However, many of the "procedures" and "functions" for modifying and - * accessing this structure are really macros, so we can't really make - * this structure opaque. - */ -#[derive(Copy, Clone)] -#[repr(C)] -pub struct dc_hash_t { - pub keyClass: libc::c_char, - pub copyKey: libc::c_char, - pub count: libc::c_int, - pub first: *mut dc_hashelem_t, - pub htsize: libc::c_int, - pub ht: *mut _ht, -} - -#[derive(Copy, Clone)] -#[repr(C)] -pub struct _ht { - pub count: libc::c_int, - pub chain: *mut dc_hashelem_t, -} - -pub type dc_hashelem_t = _dc_hashelem; - -/* Each element in the hash table is an instance of the following - * structure. All elements are stored on a single doubly-linked list. - * - * Again, this structure is intended to be opaque, but it can't really - * be opaque because it is used by macros. - */ -#[derive(Copy, Clone)] -#[repr(C)] -pub struct _dc_hashelem { - pub next: *mut dc_hashelem_t, - pub prev: *mut dc_hashelem_t, - pub data: *mut libc::c_void, - pub pKey: *mut libc::c_void, - pub nKey: libc::c_int, -} - -/* - * There are 4 different modes of operation for a hash table: - * - * DC_HASH_INT nKey is used as the key and pKey is ignored. - * - * DC_HASH_POINTER pKey is used as the key and nKey is ignored. - * - * DC_HASH_STRING pKey points to a string that is nKey bytes long - * (including the null-terminator, if any). Case - * is ignored in comparisons. - * - * DC_HASH_BINARY pKey points to binary data nKey bytes long. - * memcmp() is used to compare keys. - * - * A copy of the key is made for DC_HASH_STRING and DC_HASH_BINARY - * if the copyKey parameter to dc_hash_init() is 1. - */ -/* - * Just to make the last parameter of dc_hash_init() more readable. - */ -/* - * Access routines. To delete an element, insert a NULL pointer. - */ -pub unsafe fn dc_hash_init( - mut pNew: *mut dc_hash_t, - keyClass: libc::c_int, - mut copyKey: libc::c_int, -) { - if 0 != pNew.is_null() as usize { - __assert_rtn( - (*::std::mem::transmute::<&[u8; 13], &[libc::c_char; 13]>(b"dc_hash_init\x00")) - .as_ptr(), - b"../src/dc_hash.c\x00" as *const u8 as *const libc::c_char, - 93i32, - b"pNew!=0\x00" as *const u8 as *const libc::c_char, - ); - } else { - }; - if 0 != !(keyClass >= 1i32 && keyClass <= 4i32) as usize { - __assert_rtn( - (*::std::mem::transmute::<&[u8; 13], &[libc::c_char; 13]>(b"dc_hash_init\x00")) - .as_ptr(), - b"../src/dc_hash.c\x00" as *const u8 as *const libc::c_char, - 94i32, - b"keyClass>=DC_HASH_INT && keyClass<=DC_HASH_BINARY\x00" as *const u8 - as *const libc::c_char, - ); - } else { - }; - (*pNew).keyClass = keyClass as libc::c_char; - if keyClass == 2i32 || keyClass == 1i32 { - copyKey = 0i32 - } - (*pNew).copyKey = copyKey as libc::c_char; - (*pNew).first = 0 as *mut dc_hashelem_t; - (*pNew).count = 0i32; - (*pNew).htsize = 0i32; - (*pNew).ht = 0 as *mut _ht; -} - -pub unsafe fn dc_hash_insert( - mut pH: *mut dc_hash_t, - pKey: *const libc::c_void, - nKey: libc::c_int, - data: *mut libc::c_void, -) -> *mut libc::c_void { - /* Raw hash value of the key */ - let hraw: libc::c_int; - /* the hash of the key modulo hash table size */ - let mut h: libc::c_int; - /* Used to loop thru the element list */ - let mut elem: *mut dc_hashelem_t; - /* New element added to the pH */ - let mut new_elem: *mut dc_hashelem_t; - /* The hash function */ - let xHash: Option libc::c_int>; - assert!(!pH.is_null()); - xHash = hashFunction((*pH).keyClass as libc::c_int); - assert!(xHash.is_some(), "missing hashing function"); - hraw = xHash.expect("non-null function pointer")(pKey, nKey); - - if 0 != !((*pH).htsize & (*pH).htsize - 1i32 == 0i32) as usize { - __assert_rtn( - (*::std::mem::transmute::<&[u8; 15], &[libc::c_char; 15]>(b"dc_hash_insert\x00")) - .as_ptr(), - b"../src/dc_hash.c\x00" as *const u8 as *const libc::c_char, - 433i32, - b"(pH->htsize & (pH->htsize-1))==0\x00" as *const u8 as *const libc::c_char, - ); - } else { - }; - h = hraw & (*pH).htsize - 1i32; - elem = findElementGivenHash(pH, pKey, nKey, h); - if !elem.is_null() { - let old_data: *mut libc::c_void = (*elem).data; - if data.is_null() { - removeElementGivenHash(pH, elem, h); - } else { - (*elem).data = data - } - return old_data; - } - if data.is_null() { - return 0 as *mut libc::c_void; - } - new_elem = - sjhashMalloc(::std::mem::size_of::() as libc::c_int) as *mut dc_hashelem_t; - if new_elem.is_null() { - return data; - } - if 0 != (*pH).copyKey as libc::c_int && !pKey.is_null() { - (*new_elem).pKey = malloc(nKey as usize); - if (*new_elem).pKey.is_null() { - free(new_elem as *mut libc::c_void); - return data; - } - memcpy((*new_elem).pKey as *mut libc::c_void, pKey, nKey as usize); - } else { - (*new_elem).pKey = pKey as *mut libc::c_void - } - (*new_elem).nKey = nKey; - (*pH).count += 1; - if (*pH).htsize == 0i32 { - rehash(pH, 8); - if (*pH).htsize == 0i32 { - (*pH).count = 0i32; - free(new_elem as *mut libc::c_void); - return data; - } - } - if (*pH).count > (*pH).htsize { - rehash(pH, (*pH).htsize * 2); - } - if 0 != !((*pH).htsize > 0i32) as usize { - __assert_rtn( - (*::std::mem::transmute::<&[u8; 15], &[libc::c_char; 15]>(b"dc_hash_insert\x00")) - .as_ptr(), - b"../src/dc_hash.c\x00" as *const u8 as *const libc::c_char, - 491i32, - b"pH->htsize>0\x00" as *const u8 as *const libc::c_char, - ); - } else { - }; - if 0 != !((*pH).htsize & (*pH).htsize - 1i32 == 0i32) as usize { - __assert_rtn( - (*::std::mem::transmute::<&[u8; 15], &[libc::c_char; 15]>(b"dc_hash_insert\x00")) - .as_ptr(), - b"../src/dc_hash.c\x00" as *const u8 as *const libc::c_char, - 492i32, - b"(pH->htsize & (pH->htsize-1))==0\x00" as *const u8 as *const libc::c_char, - ); - } else { - }; - h = hraw & (*pH).htsize - 1i32; - insertElement(pH, &mut *(*pH).ht.offset(h as isize), new_elem); - (*new_elem).data = data; - - 0 as *mut libc::c_void -} - -/* Link an element into the hash table - */ -unsafe fn insertElement( - mut pH: *mut dc_hash_t, - mut pEntry: *mut _ht, - mut pNew: *mut dc_hashelem_t, -) { - /* First element already in pEntry */ - let mut pHead: *mut dc_hashelem_t; - pHead = (*pEntry).chain; - if !pHead.is_null() { - (*pNew).next = pHead; - (*pNew).prev = (*pHead).prev; - if !(*pHead).prev.is_null() { - (*(*pHead).prev).next = pNew - } else { - (*pH).first = pNew - } - (*pHead).prev = pNew - } else { - (*pNew).next = (*pH).first; - if !(*pH).first.is_null() { - (*(*pH).first).prev = pNew - } - (*pNew).prev = 0 as *mut dc_hashelem_t; - (*pH).first = pNew - } - (*pEntry).count += 1; - (*pEntry).chain = pNew; -} - -/* Resize the hash table so that it cantains "new_size" buckets. - * "new_size" must be a power of 2. The hash table might fail - * to resize if sjhashMalloc() fails. - */ -unsafe fn rehash(mut pH: *mut dc_hash_t, new_size: libc::c_int) { - /* The new hash table */ - let new_ht: *mut _ht; - /* For looping over existing elements */ - let mut elem: *mut dc_hashelem_t; - let mut next_elem: *mut dc_hashelem_t; - /* The hash function */ - let xHash: Option libc::c_int>; - if 0 != !(new_size & new_size - 1i32 == 0i32) as usize { - __assert_rtn( - (*::std::mem::transmute::<&[u8; 7], &[libc::c_char; 7]>(b"rehash\x00")).as_ptr(), - b"../src/dc_hash.c\x00" as *const u8 as *const libc::c_char, - 287i32, - b"(new_size & (new_size-1))==0\x00" as *const u8 as *const libc::c_char, - ); - } else { - }; - new_ht = sjhashMalloc( - new_size.wrapping_mul(::std::mem::size_of::<_ht>() as libc::c_int) as libc::c_int, - ) as *mut _ht; - if new_ht.is_null() { - return; - } - if !(*pH).ht.is_null() { - free((*pH).ht as *mut libc::c_void); - } - (*pH).ht = new_ht; - (*pH).htsize = new_size; - xHash = hashFunction((*pH).keyClass as libc::c_int); - elem = (*pH).first; - (*pH).first = 0 as *mut dc_hashelem_t; - while !elem.is_null() { - let h: libc::c_int = - xHash.expect("non-null function pointer")((*elem).pKey, (*elem).nKey) & new_size - 1i32; - next_elem = (*elem).next; - insertElement(pH, &mut *new_ht.offset(h as isize), elem); - elem = next_elem - } -} - -/* Return a pointer to the appropriate hash function given the key class. - * - * About the syntax: - * The name of the function is "hashFunction". The function takes a - * single parameter "keyClass". The return value of hashFunction() - * is a pointer to another function. Specifically, the return value - * of hashFunction() is a pointer to a function that takes two parameters - * with types "const void*" and "int" and returns an "int". - */ -unsafe fn hashFunction( - keyClass: libc::c_int, -) -> Option libc::c_int> { - match keyClass { - 1 => return Some(intHash), - 2 => return Some(ptrHash), - 3 => return Some(strHash), - 4 => return Some(binHash), - _ => {} - } - - None -} - -/* Hash and comparison functions when the mode is SJHASH_BINARY - */ -unsafe fn binHash(pKey: *const libc::c_void, mut nKey: libc::c_int) -> libc::c_int { - let mut h: libc::c_int = 0i32; - let mut z: *const libc::c_char = pKey as *const libc::c_char; - loop { - let fresh0 = nKey; - nKey = nKey - 1; - if !(fresh0 > 0i32) { - break; - } - let fresh1 = z; - z = z.offset(1); - h = h << 3i32 ^ h ^ *fresh1 as libc::c_int - } - - h & 0x7fffffffi32 -} - -/* Hash and comparison functions when the mode is SJHASH_STRING - */ -unsafe fn strHash(pKey: *const libc::c_void, nKey: libc::c_int) -> libc::c_int { - sjhashNoCase(pKey as *const libc::c_char, nKey) -} - -/* This function computes a hash on the name of a keyword. - * Case is not significant. - */ -unsafe fn sjhashNoCase(mut z: *const libc::c_char, mut n: libc::c_int) -> libc::c_int { - let mut h: libc::c_int = 0i32; - if n <= 0i32 { - n = strlen(z) as libc::c_int - } - while n > 0i32 { - let fresh2 = z; - z = z.offset(1); - h = h << 3i32 ^ h ^ sjhashUpperToLower[*fresh2 as libc::c_uchar as usize] as libc::c_int; - n -= 1 - } - - h & 0x7fffffffi32 -} - -/* An array to map all upper-case characters into their corresponding - * lower-case character. - */ -static mut sjhashUpperToLower: [libc::c_uchar; 256] = [ - 0i32 as libc::c_uchar, - 1i32 as libc::c_uchar, - 2i32 as libc::c_uchar, - 3i32 as libc::c_uchar, - 4i32 as libc::c_uchar, - 5i32 as libc::c_uchar, - 6i32 as libc::c_uchar, - 7i32 as libc::c_uchar, - 8i32 as libc::c_uchar, - 9i32 as libc::c_uchar, - 10i32 as libc::c_uchar, - 11i32 as libc::c_uchar, - 12i32 as libc::c_uchar, - 13i32 as libc::c_uchar, - 14i32 as libc::c_uchar, - 15i32 as libc::c_uchar, - 16i32 as libc::c_uchar, - 17i32 as libc::c_uchar, - 18i32 as libc::c_uchar, - 19i32 as libc::c_uchar, - 20i32 as libc::c_uchar, - 21i32 as libc::c_uchar, - 22i32 as libc::c_uchar, - 23i32 as libc::c_uchar, - 24i32 as libc::c_uchar, - 25i32 as libc::c_uchar, - 26i32 as libc::c_uchar, - 27i32 as libc::c_uchar, - 28i32 as libc::c_uchar, - 29i32 as libc::c_uchar, - 30i32 as libc::c_uchar, - 31i32 as libc::c_uchar, - 32i32 as libc::c_uchar, - 33i32 as libc::c_uchar, - 34i32 as libc::c_uchar, - 35i32 as libc::c_uchar, - 36i32 as libc::c_uchar, - 37i32 as libc::c_uchar, - 38i32 as libc::c_uchar, - 39i32 as libc::c_uchar, - 40i32 as libc::c_uchar, - 41i32 as libc::c_uchar, - 42i32 as libc::c_uchar, - 43i32 as libc::c_uchar, - 44i32 as libc::c_uchar, - 45i32 as libc::c_uchar, - 46i32 as libc::c_uchar, - 47i32 as libc::c_uchar, - 48i32 as libc::c_uchar, - 49i32 as libc::c_uchar, - 50i32 as libc::c_uchar, - 51i32 as libc::c_uchar, - 52i32 as libc::c_uchar, - 53i32 as libc::c_uchar, - 54i32 as libc::c_uchar, - 55i32 as libc::c_uchar, - 56i32 as libc::c_uchar, - 57i32 as libc::c_uchar, - 58i32 as libc::c_uchar, - 59i32 as libc::c_uchar, - 60i32 as libc::c_uchar, - 61i32 as libc::c_uchar, - 62i32 as libc::c_uchar, - 63i32 as libc::c_uchar, - 64i32 as libc::c_uchar, - 97i32 as libc::c_uchar, - 98i32 as libc::c_uchar, - 99i32 as libc::c_uchar, - 100i32 as libc::c_uchar, - 101i32 as libc::c_uchar, - 102i32 as libc::c_uchar, - 103i32 as libc::c_uchar, - 104i32 as libc::c_uchar, - 105i32 as libc::c_uchar, - 106i32 as libc::c_uchar, - 107i32 as libc::c_uchar, - 108i32 as libc::c_uchar, - 109i32 as libc::c_uchar, - 110i32 as libc::c_uchar, - 111i32 as libc::c_uchar, - 112i32 as libc::c_uchar, - 113i32 as libc::c_uchar, - 114i32 as libc::c_uchar, - 115i32 as libc::c_uchar, - 116i32 as libc::c_uchar, - 117i32 as libc::c_uchar, - 118i32 as libc::c_uchar, - 119i32 as libc::c_uchar, - 120i32 as libc::c_uchar, - 121i32 as libc::c_uchar, - 122i32 as libc::c_uchar, - 91i32 as libc::c_uchar, - 92i32 as libc::c_uchar, - 93i32 as libc::c_uchar, - 94i32 as libc::c_uchar, - 95i32 as libc::c_uchar, - 96i32 as libc::c_uchar, - 97i32 as libc::c_uchar, - 98i32 as libc::c_uchar, - 99i32 as libc::c_uchar, - 100i32 as libc::c_uchar, - 101i32 as libc::c_uchar, - 102i32 as libc::c_uchar, - 103i32 as libc::c_uchar, - 104i32 as libc::c_uchar, - 105i32 as libc::c_uchar, - 106i32 as libc::c_uchar, - 107i32 as libc::c_uchar, - 108i32 as libc::c_uchar, - 109i32 as libc::c_uchar, - 110i32 as libc::c_uchar, - 111i32 as libc::c_uchar, - 112i32 as libc::c_uchar, - 113i32 as libc::c_uchar, - 114i32 as libc::c_uchar, - 115i32 as libc::c_uchar, - 116i32 as libc::c_uchar, - 117i32 as libc::c_uchar, - 118i32 as libc::c_uchar, - 119i32 as libc::c_uchar, - 120i32 as libc::c_uchar, - 121i32 as libc::c_uchar, - 122i32 as libc::c_uchar, - 123i32 as libc::c_uchar, - 124i32 as libc::c_uchar, - 125i32 as libc::c_uchar, - 126i32 as libc::c_uchar, - 127i32 as libc::c_uchar, - 128i32 as libc::c_uchar, - 129i32 as libc::c_uchar, - 130i32 as libc::c_uchar, - 131i32 as libc::c_uchar, - 132i32 as libc::c_uchar, - 133i32 as libc::c_uchar, - 134i32 as libc::c_uchar, - 135i32 as libc::c_uchar, - 136i32 as libc::c_uchar, - 137i32 as libc::c_uchar, - 138i32 as libc::c_uchar, - 139i32 as libc::c_uchar, - 140i32 as libc::c_uchar, - 141i32 as libc::c_uchar, - 142i32 as libc::c_uchar, - 143i32 as libc::c_uchar, - 144i32 as libc::c_uchar, - 145i32 as libc::c_uchar, - 146i32 as libc::c_uchar, - 147i32 as libc::c_uchar, - 148i32 as libc::c_uchar, - 149i32 as libc::c_uchar, - 150i32 as libc::c_uchar, - 151i32 as libc::c_uchar, - 152i32 as libc::c_uchar, - 153i32 as libc::c_uchar, - 154i32 as libc::c_uchar, - 155i32 as libc::c_uchar, - 156i32 as libc::c_uchar, - 157i32 as libc::c_uchar, - 158i32 as libc::c_uchar, - 159i32 as libc::c_uchar, - 160i32 as libc::c_uchar, - 161i32 as libc::c_uchar, - 162i32 as libc::c_uchar, - 163i32 as libc::c_uchar, - 164i32 as libc::c_uchar, - 165i32 as libc::c_uchar, - 166i32 as libc::c_uchar, - 167i32 as libc::c_uchar, - 168i32 as libc::c_uchar, - 169i32 as libc::c_uchar, - 170i32 as libc::c_uchar, - 171i32 as libc::c_uchar, - 172i32 as libc::c_uchar, - 173i32 as libc::c_uchar, - 174i32 as libc::c_uchar, - 175i32 as libc::c_uchar, - 176i32 as libc::c_uchar, - 177i32 as libc::c_uchar, - 178i32 as libc::c_uchar, - 179i32 as libc::c_uchar, - 180i32 as libc::c_uchar, - 181i32 as libc::c_uchar, - 182i32 as libc::c_uchar, - 183i32 as libc::c_uchar, - 184i32 as libc::c_uchar, - 185i32 as libc::c_uchar, - 186i32 as libc::c_uchar, - 187i32 as libc::c_uchar, - 188i32 as libc::c_uchar, - 189i32 as libc::c_uchar, - 190i32 as libc::c_uchar, - 191i32 as libc::c_uchar, - 192i32 as libc::c_uchar, - 193i32 as libc::c_uchar, - 194i32 as libc::c_uchar, - 195i32 as libc::c_uchar, - 196i32 as libc::c_uchar, - 197i32 as libc::c_uchar, - 198i32 as libc::c_uchar, - 199i32 as libc::c_uchar, - 200i32 as libc::c_uchar, - 201i32 as libc::c_uchar, - 202i32 as libc::c_uchar, - 203i32 as libc::c_uchar, - 204i32 as libc::c_uchar, - 205i32 as libc::c_uchar, - 206i32 as libc::c_uchar, - 207i32 as libc::c_uchar, - 208i32 as libc::c_uchar, - 209i32 as libc::c_uchar, - 210i32 as libc::c_uchar, - 211i32 as libc::c_uchar, - 212i32 as libc::c_uchar, - 213i32 as libc::c_uchar, - 214i32 as libc::c_uchar, - 215i32 as libc::c_uchar, - 216i32 as libc::c_uchar, - 217i32 as libc::c_uchar, - 218i32 as libc::c_uchar, - 219i32 as libc::c_uchar, - 220i32 as libc::c_uchar, - 221i32 as libc::c_uchar, - 222i32 as libc::c_uchar, - 223i32 as libc::c_uchar, - 224i32 as libc::c_uchar, - 225i32 as libc::c_uchar, - 226i32 as libc::c_uchar, - 227i32 as libc::c_uchar, - 228i32 as libc::c_uchar, - 229i32 as libc::c_uchar, - 230i32 as libc::c_uchar, - 231i32 as libc::c_uchar, - 232i32 as libc::c_uchar, - 233i32 as libc::c_uchar, - 234i32 as libc::c_uchar, - 235i32 as libc::c_uchar, - 236i32 as libc::c_uchar, - 237i32 as libc::c_uchar, - 238i32 as libc::c_uchar, - 239i32 as libc::c_uchar, - 240i32 as libc::c_uchar, - 241i32 as libc::c_uchar, - 242i32 as libc::c_uchar, - 243i32 as libc::c_uchar, - 244i32 as libc::c_uchar, - 245i32 as libc::c_uchar, - 246i32 as libc::c_uchar, - 247i32 as libc::c_uchar, - 248i32 as libc::c_uchar, - 249i32 as libc::c_uchar, - 250i32 as libc::c_uchar, - 251i32 as libc::c_uchar, - 252i32 as libc::c_uchar, - 253i32 as libc::c_uchar, - 254i32 as libc::c_uchar, - 255i32 as libc::c_uchar, -]; - -/* Hash and comparison functions when the mode is SJHASH_POINTER - */ -unsafe fn ptrHash(pKey: *const libc::c_void, _nKey: libc::c_int) -> libc::c_int { - let x: uintptr_t = pKey as uintptr_t; - (x ^ x << 8i32 ^ x >> 8i32) as libc::c_int -} - -/* Hash and comparison functions when the mode is SJHASH_INT - */ -unsafe fn intHash(_pKey: *const libc::c_void, nKey: libc::c_int) -> libc::c_int { - nKey ^ nKey << 8i32 ^ nKey >> 8i32 -} - -/* -** Based upon hash.c from sqlite which author disclaims copyright to this source code. In place of -** a legal notice, here is a blessing: -** -** May you do good and not evil. -** May you find forgiveness for yourself and forgive others. -** May you share freely, never taking more than you give. -*/ -unsafe fn sjhashMalloc(bytes: libc::c_int) -> *mut libc::c_void { - let p: *mut libc::c_void = malloc(bytes as size_t); - if !p.is_null() { - memset(p, 0i32, bytes as size_t); - } - p -} - -/* Remove a single entry from the hash table given a pointer to that - * element and a hash on the element's key. - */ -unsafe fn removeElementGivenHash( - mut pH: *mut dc_hash_t, - mut elem: *mut dc_hashelem_t, - h: libc::c_int, -) { - let mut pEntry: *mut _ht; - if !(*elem).prev.is_null() { - (*(*elem).prev).next = (*elem).next - } else { - (*pH).first = (*elem).next - } - if !(*elem).next.is_null() { - (*(*elem).next).prev = (*elem).prev - } - pEntry = &mut *(*pH).ht.offset(h as isize) as *mut _ht; - if (*pEntry).chain == elem { - (*pEntry).chain = (*elem).next - } - (*pEntry).count -= 1; - if (*pEntry).count <= 0i32 { - (*pEntry).chain = 0 as *mut dc_hashelem_t - } - if 0 != (*pH).copyKey as libc::c_int && !(*elem).pKey.is_null() { - free((*elem).pKey); - } - free(elem as *mut libc::c_void); - (*pH).count -= 1; -} - -/* This function (for internal use only) locates an element in an - * hash table that matches the given key. The hash for this key has - * already been computed and is passed as the 4th parameter. - */ -unsafe fn findElementGivenHash( - pH: *const dc_hash_t, - pKey: *const libc::c_void, - nKey: libc::c_int, - h: libc::c_int, -) -> *mut dc_hashelem_t { - /* Used to loop thru the element list */ - let mut elem: *mut dc_hashelem_t; - /* Number of elements left to test */ - let mut count: libc::c_int; - /* comparison function */ - let xCompare: Option< - unsafe fn( - _: *const libc::c_void, - _: libc::c_int, - _: *const libc::c_void, - _: libc::c_int, - ) -> libc::c_int, - >; - if !(*pH).ht.is_null() { - let pEntry: *mut _ht = &mut *(*pH).ht.offset(h as isize) as *mut _ht; - elem = (*pEntry).chain; - count = (*pEntry).count; - xCompare = compareFunction((*pH).keyClass as libc::c_int); - loop { - let fresh3 = count; - count = count - 1; - if !(0 != fresh3 && !elem.is_null()) { - break; - } - if xCompare.expect("non-null function pointer")((*elem).pKey, (*elem).nKey, pKey, nKey) - == 0i32 - { - return elem; - } - elem = (*elem).next - } - } - - 0 as *mut dc_hashelem_t -} - -/* Return a pointer to the appropriate hash function given the key class. - */ -unsafe fn compareFunction( - keyClass: libc::c_int, -) -> Option< - unsafe fn( - _: *const libc::c_void, - _: libc::c_int, - _: *const libc::c_void, - _: libc::c_int, - ) -> libc::c_int, -> { - match keyClass { - 1 => return Some(intCompare), - 2 => return Some(ptrCompare), - 3 => return Some(strCompare), - 4 => return Some(binCompare), - _ => {} - } - None -} - -unsafe fn binCompare( - pKey1: *const libc::c_void, - n1: libc::c_int, - pKey2: *const libc::c_void, - n2: libc::c_int, -) -> libc::c_int { - if n1 != n2 { - return 1i32; - } - memcmp(pKey1, pKey2, n1 as libc::size_t) -} - -unsafe fn strCompare( - pKey1: *const libc::c_void, - n1: libc::c_int, - pKey2: *const libc::c_void, - n2: libc::c_int, -) -> libc::c_int { - if n1 != n2 { - return 1i32; - } - sjhashStrNICmp( - pKey1 as *const libc::c_char, - pKey2 as *const libc::c_char, - n1, - ) -} - -/* Some systems have stricmp(). Others have strcasecmp(). Because - * there is no consistency, we will define our own. - */ -unsafe fn sjhashStrNICmp( - zLeft: *const libc::c_char, - zRight: *const libc::c_char, - mut N: libc::c_int, -) -> libc::c_int { - let mut a: *mut libc::c_uchar; - let mut b: *mut libc::c_uchar; - a = zLeft as *mut libc::c_uchar; - b = zRight as *mut libc::c_uchar; - loop { - let fresh4 = N; - N = N - 1; - if !(fresh4 > 0i32 - && *a as libc::c_int != 0i32 - && sjhashUpperToLower[*a as usize] as libc::c_int - == sjhashUpperToLower[*b as usize] as libc::c_int) - { - break; - } - a = a.offset(1isize); - b = b.offset(1isize) - } - return if N < 0i32 { - 0i32 - } else { - sjhashUpperToLower[*a as usize] as libc::c_int - - sjhashUpperToLower[*b as usize] as libc::c_int - }; -} - -unsafe fn ptrCompare( - pKey1: *const libc::c_void, - _n1: libc::c_int, - pKey2: *const libc::c_void, - _n2: libc::c_int, -) -> libc::c_int { - if pKey1 == pKey2 { - return 0i32; - } - if pKey1 < pKey2 { - return -1i32; - } - return 1i32; -} - -unsafe fn intCompare( - _pKey1: *const libc::c_void, - n1: libc::c_int, - _pKey2: *const libc::c_void, - n2: libc::c_int, -) -> libc::c_int { - return n2 - n1; -} - -pub unsafe fn dc_hash_find( - pH: *const dc_hash_t, - pKey: *const libc::c_void, - nKey: libc::c_int, -) -> *mut libc::c_void { - /* A hash on key */ - let h: libc::c_int; - /* The element that matches key */ - let elem: *mut dc_hashelem_t; - /* The hash function */ - let xHash: Option libc::c_int>; - if pH.is_null() || (*pH).ht.is_null() { - return 0 as *mut libc::c_void; - } - xHash = hashFunction((*pH).keyClass as libc::c_int); - if 0 != xHash.is_none() as libc::c_int { - __assert_rtn( - (*::std::mem::transmute::<&[u8; 13], &[libc::c_char; 13]>(b"dc_hash_find\x00")) - .as_ptr(), - b"../src/dc_hash.c\x00" as *const u8 as *const libc::c_char, - 397i32, - b"xHash!=0\x00" as *const u8 as *const libc::c_char, - ); - } else { - }; - h = xHash.expect("non-null function pointer")(pKey, nKey); - if 0 != !((*pH).htsize & (*pH).htsize - 1i32 == 0i32) as libc::c_int { - __assert_rtn( - (*::std::mem::transmute::<&[u8; 13], &[libc::c_char; 13]>(b"dc_hash_find\x00")) - .as_ptr(), - b"../src/dc_hash.c\x00" as *const u8 as *const libc::c_char, - 399i32, - b"(pH->htsize & (pH->htsize-1))==0\x00" as *const u8 as *const libc::c_char, - ); - } else { - }; - elem = findElementGivenHash(pH, pKey, nKey, h & (*pH).htsize - 1i32); - return if !elem.is_null() { - (*elem).data - } else { - 0 as *mut libc::c_void - }; -} - -pub unsafe fn dc_hash_clear(mut pH: *mut dc_hash_t) { - /* For looping over all elements of the table */ - let mut elem: *mut dc_hashelem_t; - if pH.is_null() { - return; - } - elem = (*pH).first; - (*pH).first = 0 as *mut dc_hashelem_t; - if !(*pH).ht.is_null() { - free((*pH).ht as *mut libc::c_void); - } - (*pH).ht = 0 as *mut _ht; - (*pH).htsize = 0i32; - while !elem.is_null() { - let next_elem: *mut dc_hashelem_t = (*elem).next; - if 0 != (*pH).copyKey as libc::c_int && !(*elem).pKey.is_null() { - free((*elem).pKey); - } - free(elem as *mut libc::c_void); - elem = next_elem - } - (*pH).count = 0i32; -} diff --git a/src/dc_mimefactory.rs b/src/dc_mimefactory.rs index c7df7bc2e..e7465c188 100644 --- a/src/dc_mimefactory.rs +++ b/src/dc_mimefactory.rs @@ -12,7 +12,6 @@ use crate::dc_chat::*; use crate::dc_contact::*; use crate::dc_context::dc_context_t; use crate::dc_e2ee::*; -use crate::dc_hash::*; use crate::dc_location::*; use crate::dc_log::*; use crate::dc_msg::*; @@ -352,18 +351,14 @@ pub unsafe fn dc_mimefactory_render(mut factory: *mut dc_mimefactory_t) -> libc: let mut force_plaintext: libc::c_int = 0i32; let mut do_gossip: libc::c_int = 0i32; let mut grpimage: *mut libc::c_char = 0 as *mut libc::c_char; - let mut e2ee_helper: dc_e2ee_helper_t = dc_e2ee_helper_t { + let mut e2ee_helper = dc_e2ee_helper_t { encryption_successfull: 0, cdata_to_free: 0 as *mut libc::c_void, encrypted: 0, - signatures: 0 as *mut dc_hash_t, - gossipped_addr: 0 as *mut dc_hash_t, + signatures: Default::default(), + gossipped_addr: Default::default(), }; - memset( - &mut e2ee_helper as *mut dc_e2ee_helper_t as *mut libc::c_void, - 0, - ::std::mem::size_of::(), - ); + if factory.is_null() || (*factory).loaded as libc::c_uint == DC_MF_NOTHING_LOADED as libc::c_int as libc::c_uint || !(*factory).out.is_null() diff --git a/src/dc_mimeparser.rs b/src/dc_mimeparser.rs index dceea54e6..e04091eaf 100644 --- a/src/dc_mimeparser.rs +++ b/src/dc_mimeparser.rs @@ -1,3 +1,4 @@ +use std::collections::{HashMap, HashSet}; use std::ffi::{CStr, CString}; use charset::Charset; @@ -13,7 +14,6 @@ use mmime::other::*; use crate::dc_contact::*; use crate::dc_context::dc_context_t; use crate::dc_e2ee::*; -use crate::dc_hash::*; use crate::dc_location::*; use crate::dc_log::*; use crate::dc_param::*; @@ -43,18 +43,17 @@ pub struct dc_mimepart_t { /* * * @class dc_mimeparser_t */ -#[derive(Copy, Clone)] -#[repr(C)] +#[derive(Clone)] pub struct dc_mimeparser_t<'a> { pub parts: *mut carray, pub mimeroot: *mut mailmime, - pub header: dc_hash_t, + pub header: HashMap, pub header_root: *mut mailimf_fields, pub header_protected: *mut mailimf_fields, pub subject: *mut libc::c_char, pub is_send_by_messenger: libc::c_int, pub decrypting_failed: libc::c_int, - pub e2ee_helper: *mut dc_e2ee_helper_t, + pub e2ee_helper: dc_e2ee_helper_t, pub is_forwarded: libc::c_int, pub context: &'a dc_context_t, pub reports: *mut carray, @@ -71,26 +70,27 @@ pub unsafe fn dc_no_compound_msgs() { // deprecated: flag to switch generation of compound messages on and off. static mut s_generate_compound_msgs: libc::c_int = 1i32; -pub unsafe fn dc_mimeparser_new(context: &dc_context_t) -> *mut dc_mimeparser_t { - let mut mimeparser: *mut dc_mimeparser_t; - mimeparser = calloc(1, ::std::mem::size_of::()) as *mut dc_mimeparser_t; - if mimeparser.is_null() { - exit(30i32); +pub unsafe fn dc_mimeparser_new(context: &dc_context_t) -> dc_mimeparser_t { + dc_mimeparser_t { + parts: carray_new(16i32 as libc::c_uint), + mimeroot: std::ptr::null_mut(), + header: Default::default(), + header_root: std::ptr::null_mut(), + header_protected: std::ptr::null_mut(), + subject: std::ptr::null_mut(), + is_send_by_messenger: 0, + decrypting_failed: 0, + e2ee_helper: Default::default(), + is_forwarded: 0, + context, + reports: carray_new(16i32 as libc::c_uint), + is_system_message: 0, + location_kml: std::ptr::null_mut(), + message_kml: std::ptr::null_mut(), } - (*mimeparser).context = context; - (*mimeparser).parts = carray_new(16i32 as libc::c_uint); - (*mimeparser).reports = carray_new(16i32 as libc::c_uint); - (*mimeparser).e2ee_helper = - calloc(1, ::std::mem::size_of::()) as *mut dc_e2ee_helper_t; - dc_hash_init(&mut (*mimeparser).header, 3i32, 0i32); - - mimeparser } -pub unsafe fn dc_mimeparser_unref(mimeparser: *mut dc_mimeparser_t) { - if mimeparser.is_null() { - return; - } +pub unsafe fn dc_mimeparser_unref(mimeparser: &mut dc_mimeparser_t) { dc_mimeparser_empty(mimeparser); if !(*mimeparser).parts.is_null() { carray_free((*mimeparser).parts); @@ -98,14 +98,9 @@ pub unsafe fn dc_mimeparser_unref(mimeparser: *mut dc_mimeparser_t) { if !(*mimeparser).reports.is_null() { carray_free((*mimeparser).reports); } - free((*mimeparser).e2ee_helper as *mut libc::c_void); - free(mimeparser as *mut libc::c_void); } -pub unsafe fn dc_mimeparser_empty(mut mimeparser: *mut dc_mimeparser_t) { - if mimeparser.is_null() { - return; - } +pub unsafe fn dc_mimeparser_empty(mimeparser: &mut dc_mimeparser_t) { if !(*mimeparser).parts.is_null() { let mut i: libc::c_int; let cnt: libc::c_int = carray_count((*mimeparser).parts) as libc::c_int; @@ -121,7 +116,7 @@ pub unsafe fn dc_mimeparser_empty(mut mimeparser: *mut dc_mimeparser_t) { carray_set_size((*mimeparser).parts, 0i32 as libc::c_uint); } (*mimeparser).header_root = 0 as *mut mailimf_fields; - dc_hash_clear(&mut (*mimeparser).header); + (*mimeparser).header.clear(); if !(*mimeparser).header_protected.is_null() { mailimf_fields_free((*mimeparser).header_protected); (*mimeparser).header_protected = 0 as *mut mailimf_fields @@ -139,7 +134,7 @@ pub unsafe fn dc_mimeparser_empty(mut mimeparser: *mut dc_mimeparser_t) { carray_set_size((*mimeparser).reports, 0i32 as libc::c_uint); } (*mimeparser).decrypting_failed = 0i32; - dc_e2ee_thanks((*mimeparser).e2ee_helper); + dc_e2ee_thanks(&mut (*mimeparser).e2ee_helper); dc_kml_unref((*mimeparser).location_kml); (*mimeparser).location_kml = 0 as *mut dc_kml_t; @@ -161,7 +156,7 @@ unsafe fn dc_mimepart_unref(mut mimepart: *mut dc_mimepart_t) { } pub unsafe fn dc_mimeparser_parse( - mut mimeparser: *mut dc_mimeparser_t, + mimeparser: &mut dc_mimeparser_t, body_not_terminated: *const libc::c_char, body_bytes: size_t, ) { @@ -179,7 +174,7 @@ pub unsafe fn dc_mimeparser_parse( dc_e2ee_decrypt( (*mimeparser).context, (*mimeparser).mimeroot, - (*mimeparser).e2ee_helper, + &mut (*mimeparser).e2ee_helper, ); dc_mimeparser_parse_mime_recursive(mimeparser, (*mimeparser).mimeroot); let field: *mut mailimf_field = dc_mimeparser_lookup_field( @@ -452,16 +447,14 @@ unsafe fn dc_mimepart_new() -> *mut dc_mimepart_t { mimepart } -pub unsafe fn dc_mimeparser_get_last_nonmeta( - mimeparser: *mut dc_mimeparser_t, -) -> *mut dc_mimepart_t { - if !mimeparser.is_null() && !(*mimeparser).parts.is_null() { +pub unsafe fn dc_mimeparser_get_last_nonmeta(mimeparser: &dc_mimeparser_t) -> *mut dc_mimepart_t { + if !(*mimeparser).parts.is_null() { let mut i: libc::c_int; let icnt: libc::c_int = carray_count((*mimeparser).parts) as libc::c_int; i = icnt - 1i32; while i >= 0i32 { let part: *mut dc_mimepart_t = - carray_get((*mimeparser).parts, i as libc::c_uint) as *mut dc_mimepart_t; + carray_get(mimeparser.parts, i as libc::c_uint) as *mut dc_mimepart_t; if !part.is_null() && 0 == (*part).is_meta { return part; } @@ -498,26 +491,26 @@ pub unsafe fn mailimf_find_first_addr(mb_list: *const mailimf_mailbox_list) -> * } /* the following functions can be used only after a call to dc_mimeparser_parse() */ -pub unsafe fn dc_mimeparser_lookup_field( - mimeparser: *mut dc_mimeparser_t, +pub fn dc_mimeparser_lookup_field( + mimeparser: &dc_mimeparser_t, field_name: *const libc::c_char, ) -> *mut mailimf_field { - dc_hash_find( - &mut (*mimeparser).header, - field_name as *const libc::c_void, - strlen(field_name) as libc::c_int, - ) as *mut mailimf_field + mimeparser + .header + .get(to_str(field_name)) + .map(|v| *v) + .unwrap_or_else(|| std::ptr::null_mut()) } pub unsafe fn dc_mimeparser_lookup_optional_field( - mimeparser: *mut dc_mimeparser_t, + mimeparser: &dc_mimeparser_t, field_name: *const libc::c_char, ) -> *mut mailimf_optional_field { - let field: *mut mailimf_field = dc_hash_find( - &mut (*mimeparser).header, - field_name as *const libc::c_void, - strlen(field_name) as libc::c_int, - ) as *mut mailimf_field; + let field = mimeparser + .header + .get(to_str(field_name)) + .map(|v| *v) + .unwrap_or_else(|| std::ptr::null_mut()); if !field.is_null() && (*field).fld_type == MAILIMF_FIELD_OPTIONAL_FIELD as libc::c_int { return (*field).fld_data.fld_optional_field; } @@ -526,12 +519,12 @@ pub unsafe fn dc_mimeparser_lookup_optional_field( } unsafe fn dc_mimeparser_parse_mime_recursive( - mut mimeparser: *mut dc_mimeparser_t, + mimeparser: &mut dc_mimeparser_t, mime: *mut mailmime, ) -> libc::c_int { let mut any_part_added: libc::c_int = 0i32; let mut cur: *mut clistiter; - if mimeparser.is_null() || mime.is_null() { + if mime.is_null() { return 0i32; } if !mailmime_find_ct_parameter( @@ -829,7 +822,11 @@ unsafe fn dc_mimeparser_parse_mime_recursive( any_part_added } -unsafe fn hash_header(out: *mut dc_hash_t, in_0: *const mailimf_fields, _context: &dc_context_t) { +unsafe fn hash_header( + out: &mut HashMap, + in_0: *const mailimf_fields, + _context: &dc_context_t, +) { if in_0.is_null() { return; } @@ -866,26 +863,16 @@ unsafe fn hash_header(out: *mut dc_hash_t, in_0: *const mailimf_fields, _context } if !key.is_null() { let key_len: libc::c_int = strlen(key) as libc::c_int; - if !dc_hash_find(out, key as *const libc::c_void, key_len).is_null() { + if out.contains_key(to_str(key)) { if (*field).fld_type != MAILIMF_FIELD_OPTIONAL_FIELD as libc::c_int || key_len > 5i32 && strncasecmp(key, b"Chat-\x00" as *const u8 as *const libc::c_char, 5) == 0i32 { - dc_hash_insert( - out, - key as *const libc::c_void, - key_len, - field as *mut libc::c_void, - ); + out.insert(to_string(key), field); } } else { - dc_hash_insert( - out, - key as *const libc::c_void, - key_len, - field as *mut libc::c_void, - ); + out.insert(to_string(key), field); } } cur1 = if !cur1.is_null() { @@ -1158,12 +1145,12 @@ pub unsafe fn mailmime_find_ct_parameter( } unsafe fn dc_mimeparser_add_single_part_if_known( - mut mimeparser: *mut dc_mimeparser_t, + mimeparser: &mut dc_mimeparser_t, mime: *mut mailmime, ) -> libc::c_int { let mut current_block: u64; let mut part: *mut dc_mimepart_t = 0 as *mut dc_mimepart_t; - let old_part_count: libc::c_int = carray_count((*mimeparser).parts) as libc::c_int; + let old_part_count: libc::c_int = carray_count(mimeparser.parts) as libc::c_int; let mime_type: libc::c_int; let mime_data: *mut mailmime_data; let file_suffix: *mut libc::c_char = 0 as *mut libc::c_char; @@ -1243,7 +1230,7 @@ unsafe fn dc_mimeparser_add_single_part_if_known( } } else { dc_log_warning( - (*mimeparser).context, + mimeparser.context, 0i32, b"Cannot convert %i bytes from \"%s\" to \"utf-8\".\x00" as *const u8 @@ -1262,7 +1249,7 @@ unsafe fn dc_mimeparser_add_single_part_if_known( /* check header directly as is_send_by_messenger is not yet set up */ let is_msgrmsg: libc::c_int = (dc_mimeparser_lookup_optional_field( - mimeparser, + &mimeparser, b"Chat-Version\x00" as *const u8 as *const libc::c_char, ) != 0 as *mut libc::c_void @@ -1499,7 +1486,7 @@ unsafe fn dc_mimeparser_add_single_part_if_known( } unsafe fn do_add_single_file_part( - parser: *mut dc_mimeparser_t, + parser: &dc_mimeparser_t, msg_type: libc::c_int, mime_type: libc::c_int, raw_mime: *const libc::c_char, @@ -1551,12 +1538,10 @@ unsafe fn do_add_single_file_part( dc_mimepart_unref(part); } -unsafe fn do_add_single_part(parser: *mut dc_mimeparser_t, part: *mut dc_mimepart_t) { - if 0 != (*(*parser).e2ee_helper).encrypted - && (*(*(*parser).e2ee_helper).signatures).count > 0i32 - { +unsafe fn do_add_single_part(parser: &dc_mimeparser_t, part: *mut dc_mimepart_t) { + if 0 != (*parser).e2ee_helper.encrypted && (*parser).e2ee_helper.signatures.len() > 0 { dc_param_set_int((*part).param, 'c' as i32, 1i32); - } else if 0 != (*(*parser).e2ee_helper).encrypted { + } else if 0 != (*parser).e2ee_helper.encrypted { dc_param_set_int((*part).param, 'e' as i32, 0x2i32); } carray_add( @@ -1651,14 +1636,9 @@ pub unsafe fn mailmime_transfer_decode( } // TODO should return bool /rtn -pub unsafe fn dc_mimeparser_is_mailinglist_message( - mimeparser: *mut dc_mimeparser_t, -) -> libc::c_int { - if mimeparser.is_null() { - return 0i32; - } +pub unsafe fn dc_mimeparser_is_mailinglist_message(mimeparser: &dc_mimeparser_t) -> libc::c_int { if !dc_mimeparser_lookup_field( - mimeparser, + &mimeparser, b"List-Id\x00" as *const u8 as *const libc::c_char, ) .is_null() @@ -1686,18 +1666,15 @@ pub unsafe fn dc_mimeparser_is_mailinglist_message( 0 } -pub unsafe fn dc_mimeparser_sender_equals_recipient( - mimeparser: *mut dc_mimeparser_t, -) -> libc::c_int { +pub unsafe fn dc_mimeparser_sender_equals_recipient(mimeparser: &dc_mimeparser_t) -> libc::c_int { let mut sender_equals_recipient: libc::c_int = 0i32; let fld: *const mailimf_field; let mut fld_from: *const mailimf_from = 0 as *const mailimf_from; let mb: *mut mailimf_mailbox; let mut from_addr_norm: *mut libc::c_char = 0 as *mut libc::c_char; - let mut recipients: *mut dc_hash_t = 0 as *mut dc_hash_t; - if !(mimeparser.is_null() || (*mimeparser).header_root.is_null()) { + if !(*mimeparser).header_root.is_null() { /* get From: and check there is exactly one sender */ - fld = mailimf_find_field((*mimeparser).header_root, MAILIMF_FIELD_FROM as libc::c_int); + fld = mailimf_find_field(mimeparser.header_root, MAILIMF_FIELD_FROM as libc::c_int); if !(fld.is_null() || { fld_from = (*fld).fld_data.fld_from; @@ -1714,32 +1691,23 @@ pub unsafe fn dc_mimeparser_sender_equals_recipient( }) as *mut mailimf_mailbox; if !mb.is_null() { from_addr_norm = dc_addr_normalize((*mb).mb_addr_spec); - recipients = mailimf_get_recipients((*mimeparser).header_root); - if !((*recipients).count != 1i32) { - if !dc_hash_find( - recipients, - from_addr_norm as *const libc::c_void, - strlen(from_addr_norm) as libc::c_int, - ) - .is_null() - { - sender_equals_recipient = 1i32 + let recipients = mailimf_get_recipients(mimeparser.header_root); + if recipients.len() == 1 { + if recipients.contains(to_str(from_addr_norm)) { + sender_equals_recipient = 1i32; } } } } } - dc_hash_clear(recipients); - free(recipients as *mut libc::c_void); free(from_addr_norm as *mut libc::c_void); sender_equals_recipient } -pub unsafe fn mailimf_get_recipients(imffields: *mut mailimf_fields) -> *mut dc_hash_t { - /* the returned value must be dc_hash_clear()'d and free()'d. returned addresses are normalized. */ - let recipients: *mut dc_hash_t = malloc(::std::mem::size_of::()) as *mut dc_hash_t; - dc_hash_init(recipients, 3i32, 1i32); +pub unsafe fn mailimf_get_recipients(imffields: *mut mailimf_fields) -> HashSet { + /* returned addresses are normalized. */ + let mut recipients: HashSet = Default::default(); let mut cur1: *mut clistiter; cur1 = (*(*imffields).fld_list).first; while !cur1.is_null() { @@ -1778,7 +1746,10 @@ pub unsafe fn mailimf_get_recipients(imffields: *mut mailimf_fields) -> *mut dc_ }) as *mut mailimf_address; if !adr.is_null() { if (*adr).ad_type == MAILIMF_ADDRESS_MAILBOX as libc::c_int { - mailimf_get_recipients__add_addr(recipients, (*adr).ad_data.ad_mailbox); + mailimf_get_recipients__add_addr( + &mut recipients, + (*adr).ad_data.ad_mailbox, + ); } else if (*adr).ad_type == MAILIMF_ADDRESS_GROUP as libc::c_int { let group: *mut mailimf_group = (*adr).ad_data.ad_group; if !group.is_null() && !(*group).grp_mb_list.is_null() { @@ -1786,7 +1757,7 @@ pub unsafe fn mailimf_get_recipients(imffields: *mut mailimf_fields) -> *mut dc_ cur3 = (*(*(*group).grp_mb_list).mb_list).first; while !cur3.is_null() { mailimf_get_recipients__add_addr( - recipients, + &mut recipients, (if !cur3.is_null() { (*cur3).data } else { @@ -1826,15 +1797,13 @@ pub unsafe fn mailimf_get_recipients(imffields: *mut mailimf_fields) -> *mut dc_ /* ****************************************************************************** * low-level-tools for getting a list of all recipients ******************************************************************************/ -unsafe fn mailimf_get_recipients__add_addr(recipients: *mut dc_hash_t, mb: *mut mailimf_mailbox) { +unsafe fn mailimf_get_recipients__add_addr( + recipients: &mut HashSet, + mb: *mut mailimf_mailbox, +) { if !mb.is_null() { let addr_norm: *mut libc::c_char = dc_addr_normalize((*mb).mb_addr_spec); - dc_hash_insert( - recipients, - addr_norm as *const libc::c_void, - strlen(addr_norm) as libc::c_int, - 1i32 as *mut libc::c_void, - ); + recipients.insert(to_string(addr_norm)); free(addr_norm as *mut libc::c_void); }; } @@ -1870,15 +1839,12 @@ pub unsafe fn mailimf_find_field( } pub unsafe fn dc_mimeparser_repl_msg_by_error( - mimeparser: *mut dc_mimeparser_t, + mimeparser: &dc_mimeparser_t, error_msg: *const libc::c_char, ) { let mut part: *mut dc_mimepart_t; let mut i: libc::c_int; - if mimeparser.is_null() - || (*mimeparser).parts.is_null() - || carray_count((*mimeparser).parts) <= 0i32 as libc::c_uint - { + if (*mimeparser).parts.is_null() || carray_count((*mimeparser).parts) <= 0i32 as libc::c_uint { return; } part = carray_get((*mimeparser).parts, 0i32 as libc::c_uint) as *mut dc_mimepart_t; diff --git a/src/dc_pgp.rs b/src/dc_pgp.rs index 0109eded2..0b91550c6 100644 --- a/src/dc_pgp.rs +++ b/src/dc_pgp.rs @@ -1,5 +1,6 @@ +use std::collections::HashSet; use std::convert::TryInto; -use std::ffi::{CStr, CString}; +use std::ffi::CStr; use std::io::Cursor; use pgp::composed::{ @@ -11,7 +12,6 @@ use pgp::types::{CompressionAlgorithm, KeyTrait, SecretKeyTrait, StringToKey}; use rand::thread_rng; use sha2::{Digest, Sha256}; -use crate::dc_hash::*; use crate::dc_key::*; use crate::dc_keyring::*; use crate::dc_tools::*; @@ -232,7 +232,7 @@ pub fn dc_pgp_pk_decrypt( ctext_bytes: size_t, private_keys_for_decryption: &Keyring, public_keys_for_validation: &Keyring, - ret_signature_fingerprints: *mut dc_hash_t, + ret_signature_fingerprints: Option<&mut HashSet>, ) -> Option> { assert!(!ctext.is_null() && ctext_bytes > 0, "invalid input"); @@ -255,33 +255,22 @@ pub fn dc_pgp_pk_decrypt( decryptor.next().expect("no message") }) .and_then(|dec_msg| { - if !ret_signature_fingerprints.is_null() - && !public_keys_for_validation.keys().is_empty() - { - let pkeys: Vec<&SignedPublicKey> = public_keys_for_validation - .keys() - .iter() - .filter_map(|key| { - let k: &Key = &key; - k.try_into().ok() - }) - .collect(); + if let Some(ret_signature_fingerprints) = ret_signature_fingerprints { + if !public_keys_for_validation.keys().is_empty() { + let pkeys: Vec<&SignedPublicKey> = public_keys_for_validation + .keys() + .iter() + .filter_map(|key| { + let k: &Key = &key; + k.try_into().ok() + }) + .collect(); - for pkey in &pkeys { - if dec_msg.verify(&pkey.primary_key).is_ok() { - let fp_r = hex::encode_upper(pkey.fingerprint()); - let len = fp_r.len() as libc::c_int; - let fp_c = CString::new(fp_r).unwrap(); - let fp = unsafe { strdup(fp_c.as_ptr()) }; - - unsafe { - dc_hash_insert( - ret_signature_fingerprints, - fp as *const _, - len, - 1 as *mut _, - ) - }; + for pkey in &pkeys { + if dec_msg.verify(&pkey.primary_key).is_ok() { + let fp = hex::encode_upper(pkey.fingerprint()); + ret_signature_fingerprints.insert(fp); + } } } } diff --git a/src/dc_receive_imf.rs b/src/dc_receive_imf.rs index 82e1a4ca4..092fbaa2f 100644 --- a/src/dc_receive_imf.rs +++ b/src/dc_receive_imf.rs @@ -11,7 +11,6 @@ use crate::dc_array::*; use crate::dc_chat::*; use crate::dc_contact::*; use crate::dc_context::dc_context_t; -use crate::dc_hash::*; use crate::dc_job::*; use crate::dc_location::*; use crate::dc_log::*; @@ -62,7 +61,7 @@ pub unsafe fn dc_receive_imf( let mut sort_timestamp: time_t = -1i32 as time_t; let mut sent_timestamp: time_t = -1i32 as time_t; let mut rcvd_timestamp: time_t = -1i32 as time_t; - let mime_parser: *mut dc_mimeparser_t = dc_mimeparser_new(context); + let mut mime_parser = dc_mimeparser_new(context); let mut field: *const mailimf_field; let mut mime_in_reply_to: *mut libc::c_char = 0 as *mut libc::c_char; let mut mime_references: *mut libc::c_char = 0 as *mut libc::c_char; @@ -82,19 +81,15 @@ pub unsafe fn dc_receive_imf( server_uid, ); to_ids = dc_array_new(16i32 as size_t); - if to_ids.is_null() - || created_db_entries.is_null() - || rr_event_to_send.is_null() - || mime_parser.is_null() - { + if to_ids.is_null() || created_db_entries.is_null() || rr_event_to_send.is_null() { dc_log_info( context, 0i32, b"Bad param.\x00" as *const u8 as *const libc::c_char, ); } else { - dc_mimeparser_parse(mime_parser, imf_raw_not_terminated, imf_raw_bytes); - if (*mime_parser).header.count == 0i32 { + dc_mimeparser_parse(&mut mime_parser, imf_raw_not_terminated, imf_raw_bytes); + if mime_parser.header.is_empty() { dc_log_info( context, 0i32, @@ -103,7 +98,7 @@ pub unsafe fn dc_receive_imf( } else { /* Error - even adding an empty record won't help as we do not know the message ID */ field = dc_mimeparser_lookup_field( - mime_parser, + &mut mime_parser, b"Date\x00" as *const u8 as *const libc::c_char, ); if !field.is_null() && (*field).fld_type == MAILIMF_FIELD_ORIG_DATE as libc::c_int { @@ -113,7 +108,7 @@ pub unsafe fn dc_receive_imf( } } field = dc_mimeparser_lookup_field( - mime_parser, + &mime_parser, b"From\x00" as *const u8 as *const libc::c_char, ); if !field.is_null() && (*field).fld_type == MAILIMF_FIELD_FROM as libc::c_int { @@ -130,7 +125,7 @@ pub unsafe fn dc_receive_imf( ); if 0 != check_self { incoming = 0i32; - if 0 != dc_mimeparser_sender_equals_recipient(mime_parser) { + if 0 != dc_mimeparser_sender_equals_recipient(&mime_parser) { from_id = 1i32 as uint32_t } } else if dc_array_get_cnt(from_list) >= 1 { @@ -142,7 +137,7 @@ pub unsafe fn dc_receive_imf( } } field = dc_mimeparser_lookup_field( - mime_parser, + &mime_parser, b"To\x00" as *const u8 as *const libc::c_char, ); if !field.is_null() && (*field).fld_type == MAILIMF_FIELD_TO as libc::c_int { @@ -163,9 +158,9 @@ pub unsafe fn dc_receive_imf( ); } } - if !dc_mimeparser_get_last_nonmeta(mime_parser).is_null() { + if !dc_mimeparser_get_last_nonmeta(&mime_parser).is_null() { field = dc_mimeparser_lookup_field( - mime_parser, + &mime_parser, b"Cc\x00" as *const u8 as *const libc::c_char, ); if !field.is_null() && (*field).fld_type == MAILIMF_FIELD_CC as libc::c_int { @@ -187,7 +182,7 @@ pub unsafe fn dc_receive_imf( } } field = dc_mimeparser_lookup_field( - mime_parser, + &mime_parser, b"Message-ID\x00" as *const u8 as *const libc::c_char, ); if !field.is_null() && (*field).fld_type == MAILIMF_FIELD_MESSAGE_ID as libc::c_int @@ -243,9 +238,9 @@ pub unsafe fn dc_receive_imf( ); current_block = 16282941964262048061; } else { - msgrmsg = (*mime_parser).is_send_by_messenger; + msgrmsg = mime_parser.is_send_by_messenger; if msgrmsg == 0i32 - && 0 != dc_is_reply_to_messenger_message(context, mime_parser) + && 0 != dc_is_reply_to_messenger_message(context, &mime_parser) { msgrmsg = 2i32 } @@ -271,7 +266,7 @@ pub unsafe fn dc_receive_imf( state = if 0 != flags & 0x1 { 16 } else { 10 }; to_id = 1 as uint32_t; if !dc_mimeparser_lookup_field( - mime_parser, + &mime_parser, b"Secure-Join\x00" as *const u8 as *const libc::c_char, ) .is_null() @@ -281,7 +276,7 @@ pub unsafe fn dc_receive_imf( allow_creation = 1i32; let handshake: libc::c_int = dc_handle_securejoin_handshake( context, - mime_parser, + &mime_parser, from_id, ); if 0 != handshake & 0x2i32 { @@ -309,7 +304,7 @@ pub unsafe fn dc_receive_imf( }; create_or_lookup_group( context, - mime_parser, + &mut mime_parser, allow_creation, create_blocked, from_id as int32_t, @@ -323,7 +318,7 @@ pub unsafe fn dc_receive_imf( } } if chat_id == 0i32 as libc::c_uint { - if 0 != dc_mimeparser_is_mailinglist_message(mime_parser) { + if 0 != dc_mimeparser_is_mailinglist_message(&mime_parser) { chat_id = 3i32 as uint32_t; dc_log_info( context, @@ -358,7 +353,7 @@ pub unsafe fn dc_receive_imf( dc_unblock_chat(context, chat_id); chat_id_blocked = 0i32 } else if 0 - != dc_is_reply_to_known_message(context, mime_parser) + != dc_is_reply_to_known_message(context, &mime_parser) { dc_scaleup_contact_origin(context, from_id, 0x100i32); dc_log_info(context, 0i32, @@ -389,7 +384,7 @@ pub unsafe fn dc_receive_imf( if chat_id == 0i32 as libc::c_uint { create_or_lookup_group( context, - mime_parser, + &mut mime_parser, allow_creation, 0i32, from_id as int32_t, @@ -488,7 +483,7 @@ pub unsafe fn dc_receive_imf( } } field = dc_mimeparser_lookup_field( - mime_parser, + &mime_parser, b"In-Reply-To\x00" as *const u8 as *const libc::c_char, ); if !field.is_null() @@ -504,7 +499,7 @@ pub unsafe fn dc_receive_imf( } } field = dc_mimeparser_lookup_field( - mime_parser, + &mime_parser, b"References\x00" as *const u8 as *const libc::c_char, ); if !field.is_null() @@ -519,7 +514,7 @@ pub unsafe fn dc_receive_imf( ) } } - icnt = carray_count((*mime_parser).parts) as size_t; + icnt = carray_count(mime_parser.parts) as size_t; stmt = dc_sqlite3_prepare( context, @@ -534,10 +529,10 @@ pub unsafe fn dc_receive_imf( break; } let part: *mut dc_mimepart_t = - carray_get((*mime_parser).parts, i as libc::c_uint) + carray_get(mime_parser.parts, i as libc::c_uint) as *mut dc_mimepart_t; if !(0 != (*part).is_meta) { - if !(*mime_parser).location_kml.is_null() + if !mime_parser.location_kml.is_null() && icnt == 1 && !(*part).msg.is_null() && (strcmp( @@ -554,19 +549,19 @@ pub unsafe fn dc_receive_imf( if (*part).type_0 == 10i32 { txt_raw = dc_mprintf( b"%s\n\n%s\x00" as *const u8 as *const libc::c_char, - if !(*mime_parser).subject.is_null() { - (*mime_parser).subject + if !mime_parser.subject.is_null() { + mime_parser.subject } else { b"\x00" as *const u8 as *const libc::c_char }, (*part).msg_raw, ) } - if 0 != (*mime_parser).is_system_message { + if 0 != mime_parser.is_system_message { dc_param_set_int( (*part).param, 'S' as i32, - (*mime_parser).is_system_message, + mime_parser.is_system_message, ); } sqlite3_reset(stmt); @@ -699,20 +694,19 @@ pub unsafe fn dc_receive_imf( match current_block { 16282941964262048061 => {} _ => { - if carray_count((*mime_parser).reports) > 0i32 as libc::c_uint { + if carray_count(mime_parser.reports) > 0i32 as libc::c_uint { let mdns_enabled: libc::c_int = dc_sqlite3_get_config_int( context, &context.sql.clone().read().unwrap(), b"mdns_enabled\x00" as *const u8 as *const libc::c_char, 1i32, ); - icnt = carray_count((*mime_parser).reports) as size_t; + icnt = carray_count(mime_parser.reports) as size_t; i = 0i32 as size_t; while i < icnt { let mut mdn_consumed: libc::c_int = 0i32; let report_root: *mut mailmime = - carray_get((*mime_parser).reports, i as libc::c_uint) - as *mut mailmime; + carray_get(mime_parser.reports, i as libc::c_uint) as *mut mailmime; let report_type: *mut mailmime_parameter = mailmime_find_ct_parameter( report_root, b"report-type\x00" as *const u8 as *const libc::c_char, @@ -878,12 +872,11 @@ pub unsafe fn dc_receive_imf( } } } - if 0 != (*mime_parser).is_send_by_messenger || 0 != mdn_consumed - { + if 0 != mime_parser.is_send_by_messenger || 0 != mdn_consumed { let param: *mut dc_param_t = dc_param_new(); dc_param_set(param, 'Z' as i32, server_folder); dc_param_set_int(param, 'z' as i32, server_uid as int32_t); - if 0 != (*mime_parser).is_send_by_messenger + if 0 != mime_parser.is_send_by_messenger && 0 != dc_sqlite3_get_config_int( context, &context.sql.clone().read().unwrap(), @@ -902,18 +895,18 @@ pub unsafe fn dc_receive_imf( i = i.wrapping_add(1) } } - if !(*mime_parser).message_kml.is_null() && chat_id > 9i32 as libc::c_uint { + if !mime_parser.message_kml.is_null() && chat_id > 9i32 as libc::c_uint { let mut location_id_written = false; let mut send_event = false; - if !(*mime_parser).message_kml.is_null() + if !mime_parser.message_kml.is_null() && chat_id > DC_CHAT_ID_LAST_SPECIAL as libc::c_uint { let newest_location_id: uint32_t = dc_save_locations( context, chat_id, from_id, - (*(*mime_parser).message_kml).locations, + (*mime_parser.message_kml).locations, 1, ); if 0 != newest_location_id && 0 == hidden { @@ -923,21 +916,21 @@ pub unsafe fn dc_receive_imf( } } - if !(*mime_parser).location_kml.is_null() + if !mime_parser.location_kml.is_null() && chat_id > DC_CHAT_ID_LAST_SPECIAL as libc::c_uint { let contact = dc_get_contact(context, from_id); - if !(*(*mime_parser).location_kml).addr.is_null() + if !(*mime_parser.location_kml).addr.is_null() && !contact.is_null() && !(*contact).addr.is_null() - && strcasecmp((*contact).addr, (*(*mime_parser).location_kml).addr) + && strcasecmp((*contact).addr, (*mime_parser.location_kml).addr) == 0i32 { let newest_location_id = dc_save_locations( context, chat_id, from_id, - (*(*mime_parser).location_kml).locations, + (*mime_parser.location_kml).locations, 0, ); if newest_location_id != 0 && hidden == 0 && !location_id_written { @@ -977,7 +970,7 @@ pub unsafe fn dc_receive_imf( } } } - dc_mimeparser_unref(mime_parser); + free(rfc724_mid as *mut libc::c_void); free(mime_in_reply_to as *mut libc::c_void); free(mime_references as *mut libc::c_void); @@ -1074,7 +1067,7 @@ So when the function returns, the caller has the group id matching the current state of the group. */ unsafe fn create_or_lookup_group( context: &dc_context_t, - mut mime_parser: *mut dc_mimeparser_t, + mime_parser: &mut dc_mimeparser_t, allow_creation: libc::c_int, create_blocked: libc::c_int, from_id: int32_t, @@ -1103,7 +1096,7 @@ unsafe fn create_or_lookup_group( let mut X_MrGrpImageChanged: *const libc::c_char = 0 as *const libc::c_char; let mut better_msg: *mut libc::c_char = 0 as *mut libc::c_char; let mut failure_reason: *mut libc::c_char = 0 as *mut libc::c_char; - if (*mime_parser).is_system_message == 8i32 { + if mime_parser.is_system_message == 8i32 { better_msg = dc_stock_system_msg( context, 64i32, @@ -1196,7 +1189,7 @@ unsafe fn create_or_lookup_group( ); if !optional_field.is_null() { X_MrRemoveFromGrp = (*optional_field).fld_value; - (*mime_parser).is_system_message = 5i32; + mime_parser.is_system_message = 5i32; let left_group: libc::c_int = (dc_lookup_contact_id_by_addr(context, X_MrRemoveFromGrp) == from_id as libc::c_uint) as libc::c_int; @@ -1214,7 +1207,7 @@ unsafe fn create_or_lookup_group( ); if !optional_field.is_null() { X_MrAddToGrp = (*optional_field).fld_value; - (*mime_parser).is_system_message = 4i32; + mime_parser.is_system_message = 4i32; optional_field = dc_mimeparser_lookup_optional_field( mime_parser, b"Chat-Group-Image\x00" as *const u8 as *const libc::c_char, @@ -1236,7 +1229,7 @@ unsafe fn create_or_lookup_group( ); if !optional_field.is_null() { X_MrGrpNameChanged = 1i32; - (*mime_parser).is_system_message = 2i32; + mime_parser.is_system_message = 2i32; better_msg = dc_stock_system_msg( context, 15i32, @@ -1251,7 +1244,7 @@ unsafe fn create_or_lookup_group( ); if !optional_field.is_null() { X_MrGrpImageChanged = (*optional_field).fld_value; - (*mime_parser).is_system_message = 3i32; + mime_parser.is_system_message = 3i32; better_msg = dc_stock_system_msg( context, if strcmp( @@ -1404,9 +1397,9 @@ unsafe fn create_or_lookup_group( ok = 1i32 } else { let mut i_0: libc::c_int = 0i32; - while (i_0 as libc::c_uint) < carray_count((*mime_parser).parts) { + while (i_0 as libc::c_uint) < carray_count(mime_parser.parts) { let part: *mut dc_mimepart_t = - carray_get((*mime_parser).parts, i_0 as libc::c_uint) + carray_get(mime_parser.parts, i_0 as libc::c_uint) as *mut dc_mimepart_t; if (*part).type_0 == 20i32 { grpimage = dc_param_get( @@ -1498,7 +1491,7 @@ unsafe fn create_or_lookup_group( } /* check the number of receivers - the only critical situation is if the user hits "Reply" instead of "Reply all" in a non-messenger-client */ - if to_ids_cnt == 1i32 && (*mime_parser).is_send_by_messenger == 0i32 { + if to_ids_cnt == 1i32 && mime_parser.is_send_by_messenger == 0i32 { let is_contact_cnt: libc::c_int = dc_get_chat_contact_cnt(context, chat_id); if is_contact_cnt > 3i32 { @@ -1539,7 +1532,7 @@ unsafe fn create_or_lookup_group( ******************************************************************************/ unsafe fn create_or_lookup_adhoc_group( context: &dc_context_t, - mime_parser: *mut dc_mimeparser_t, + mime_parser: &dc_mimeparser_t, allow_creation: libc::c_int, create_blocked: libc::c_int, from_id: int32_t, @@ -1602,10 +1595,10 @@ unsafe fn create_or_lookup_adhoc_group( - there is no need to check if this group exists; otherwise we would have catched it above */ grpid = create_adhoc_grp_id(context, member_ids); if !grpid.is_null() { - if !(*mime_parser).subject.is_null() - && 0 != *(*mime_parser).subject.offset(0isize) as libc::c_int + if !mime_parser.subject.is_null() + && 0 != *mime_parser.subject.offset(0isize) as libc::c_int { - grpname = dc_strdup((*mime_parser).subject) + grpname = dc_strdup(mime_parser.subject) } else { grpname = dc_stock_str_repl_int( context, @@ -1842,7 +1835,7 @@ unsafe fn search_chat_ids_by_contact_ids( } unsafe fn check_verified_properties( context: &dc_context_t, - mimeparser: *mut dc_mimeparser_t, + mimeparser: &dc_mimeparser_t, from_id: uint32_t, to_ids: *const dc_array_t, failure_reason: *mut *mut libc::c_char, @@ -1859,7 +1852,7 @@ unsafe fn check_verified_properties( b"Internal Error; cannot load contact.\x00" as *const u8 as *const libc::c_char, ); dc_log_warning(context, 0i32, *failure_reason); - } else if 0 == (*(*mimeparser).e2ee_helper).encrypted { + } else if 0 == mimeparser.e2ee_helper.encrypted { *failure_reason = dc_mprintf( b"%s. See \"Info\" for details.\x00" as *const u8 as *const libc::c_char, b"This message is not encrypted.\x00" as *const u8 as *const libc::c_char, @@ -1886,7 +1879,7 @@ unsafe fn check_verified_properties( dc_log_warning(context, 0i32, *failure_reason); current_block = 14837890932895028253; } else if let Some(peerstate) = peerstate { - if !peerstate.has_verified_key((*(*mimeparser).e2ee_helper).signatures) { + if !peerstate.has_verified_key(&mimeparser.e2ee_helper.signatures) { *failure_reason = dc_mprintf( b"%s. See \"Info\" for details.\x00" as *const u8 as *const libc::c_char, b"The message was sent with non-verified encryption.\x00" as *const u8 @@ -1925,12 +1918,10 @@ unsafe fn check_verified_properties( &context.sql.clone().read().unwrap(), to_str(to_addr), ); - if !dc_hash_find( - (*(*mimeparser).e2ee_helper).gossipped_addr, - to_addr as *const libc::c_void, - strlen(to_addr) as libc::c_int, - ) - .is_null() + if mimeparser + .e2ee_helper + .gossipped_addr + .contains(to_str(to_addr)) && peerstate.is_some() { let peerstate = peerstate.as_mut().unwrap(); @@ -1986,10 +1977,10 @@ unsafe fn check_verified_properties( everythings_okay } -unsafe fn set_better_msg(mime_parser: *mut dc_mimeparser_t, better_msg: *mut *mut libc::c_char) { +unsafe fn set_better_msg(mime_parser: &dc_mimeparser_t, better_msg: *mut *mut libc::c_char) { if !(*better_msg).is_null() && carray_count((*mime_parser).parts) > 0i32 as libc::c_uint { let mut part: *mut dc_mimepart_t = - carray_get((*mime_parser).parts, 0i32 as libc::c_uint) as *mut dc_mimepart_t; + carray_get(mime_parser.parts, 0i32 as libc::c_uint) as *mut dc_mimepart_t; if (*part).type_0 == 10i32 { free((*part).msg as *mut libc::c_void); (*part).msg = *better_msg; @@ -1999,7 +1990,7 @@ unsafe fn set_better_msg(mime_parser: *mut dc_mimeparser_t, better_msg: *mut *mu } unsafe fn dc_is_reply_to_known_message( context: &dc_context_t, - mime_parser: *mut dc_mimeparser_t, + mime_parser: &dc_mimeparser_t, ) -> libc::c_int { /* check if the message is a reply to a known message; the replies are identified by the Message-ID from `In-Reply-To`/`References:` (to support non-Delta-Clients) or from `Chat-Predecessor:` (Delta clients, see comment in dc_chat.c) */ @@ -2096,7 +2087,7 @@ unsafe fn is_known_rfc724_mid( } unsafe fn dc_is_reply_to_messenger_message( context: &dc_context_t, - mime_parser: *mut dc_mimeparser_t, + mime_parser: &dc_mimeparser_t, ) -> libc::c_int { /* function checks, if the message defined by mime_parser references a message send by us from Delta Chat. This is similar to is_reply_to_known_message() but diff --git a/src/dc_securejoin.rs b/src/dc_securejoin.rs index 5063f46b8..e599a3b72 100644 --- a/src/dc_securejoin.rs +++ b/src/dc_securejoin.rs @@ -8,7 +8,6 @@ use crate::dc_configure::*; use crate::dc_contact::*; use crate::dc_context::dc_context_t; use crate::dc_e2ee::*; -use crate::dc_hash::*; use crate::dc_key::*; use crate::dc_log::*; use crate::dc_lot::*; @@ -385,7 +384,7 @@ unsafe fn fingerprint_equals_sender( /* library private: secure-join */ pub unsafe fn dc_handle_securejoin_handshake( context: &dc_context_t, - mimeparser: *mut dc_mimeparser_t, + mimeparser: &dc_mimeparser_t, contact_id: uint32_t, ) -> libc::c_int { let mut current_block: u64; @@ -399,7 +398,7 @@ pub unsafe fn dc_handle_securejoin_handshake( let mut grpid: *mut libc::c_char = 0 as *mut libc::c_char; let mut ret: libc::c_int = 0i32; let mut contact: *mut dc_contact_t = 0 as *mut dc_contact_t; - if !(mimeparser.is_null() || contact_id <= 9i32 as libc::c_uint) { + if !(contact_id <= 9i32 as libc::c_uint) { step = lookup_field( mimeparser, b"Secure-Join\x00" as *const u8 as *const libc::c_char, @@ -515,7 +514,7 @@ pub unsafe fn dc_handle_securejoin_handshake( could_not_establish_secure_connection( context, contact_chat_id, - if 0 != (*(*mimeparser).e2ee_helper).encrypted { + if 0 != mimeparser.e2ee_helper.encrypted { b"No valid signature.\x00" as *const u8 as *const libc::c_char } else { b"Not encrypted.\x00" as *const u8 as *const libc::c_char @@ -924,7 +923,7 @@ unsafe fn secure_connection_established(context: &dc_context_t, contact_chat_id: } unsafe fn lookup_field( - mimeparser: *mut dc_mimeparser_t, + mimeparser: &dc_mimeparser_t, key: *const libc::c_char, ) -> *const libc::c_char { let mut value: *const libc::c_char = 0 as *const libc::c_char; @@ -999,20 +998,20 @@ unsafe fn mark_peer_as_verified( // TODO should return bool unsafe fn encrypted_and_signed( - mimeparser: *mut dc_mimeparser_t, + mimeparser: &dc_mimeparser_t, expected_fingerprint: *const libc::c_char, ) -> libc::c_int { - if 0 == (*(*mimeparser).e2ee_helper).encrypted { + if 0 == mimeparser.e2ee_helper.encrypted { dc_log_warning( - (*mimeparser).context, + mimeparser.context, 0i32, b"Message not encrypted.\x00" as *const u8 as *const libc::c_char, ); return 0i32; } - if (*(*(*mimeparser).e2ee_helper).signatures).count <= 0i32 { + if mimeparser.e2ee_helper.signatures.len() <= 0 { dc_log_warning( - (*mimeparser).context, + mimeparser.context, 0i32, b"Message not signed.\x00" as *const u8 as *const libc::c_char, ); @@ -1020,21 +1019,19 @@ unsafe fn encrypted_and_signed( } if expected_fingerprint.is_null() { dc_log_warning( - (*mimeparser).context, + mimeparser.context, 0i32, b"Fingerprint for comparison missing.\x00" as *const u8 as *const libc::c_char, ); return 0i32; } - if dc_hash_find( - (*(*mimeparser).e2ee_helper).signatures, - expected_fingerprint as *const libc::c_void, - strlen(expected_fingerprint) as libc::c_int, - ) - .is_null() + if !mimeparser + .e2ee_helper + .signatures + .contains(to_str(expected_fingerprint)) { dc_log_warning( - (*mimeparser).context, + mimeparser.context, 0i32, b"Message does not match expected fingerprint %s.\x00" as *const u8 as *const libc::c_char, diff --git a/src/dc_sqlite3.rs b/src/dc_sqlite3.rs index a21fa5b52..692731251 100644 --- a/src/dc_sqlite3.rs +++ b/src/dc_sqlite3.rs @@ -1,6 +1,7 @@ +use std::collections::HashSet; + use crate::constants::*; use crate::dc_context::dc_context_t; -use crate::dc_hash::*; use crate::dc_log::*; use crate::dc_param::*; use crate::dc_tools::*; @@ -1405,17 +1406,10 @@ pub unsafe fn dc_housekeeping(context: &dc_context_t) { let stmt; let dir_handle; let mut dir_entry; - let mut files_in_use = dc_hash_t { - keyClass: 0, - copyKey: 0, - count: 0, - first: 0 as *mut dc_hashelem_t, - htsize: 0, - ht: 0 as *mut _ht, - }; + let mut files_in_use = HashSet::new(); let mut path = 0 as *mut libc::c_char; let mut unreferenced_count = 0; - dc_hash_init(&mut files_in_use, 3, 1); + dc_log_info( context, 0, @@ -1461,7 +1455,7 @@ pub unsafe fn dc_housekeeping(context: &dc_context_t) { context, 0, b"%i files in use.\x00" as *const u8 as *const libc::c_char, - files_in_use.count as libc::c_int, + files_in_use.len() as libc::c_int, ); /* go through directory and delete unused files */ dir_handle = opendir(context.get_blobdir()); @@ -1492,18 +1486,18 @@ pub unsafe fn dc_housekeeping(context: &dc_context_t) { { continue; } - if 0 != is_file_in_use(&mut files_in_use, 0 as *const libc::c_char, name) - || 0 != is_file_in_use( + if is_file_in_use(&mut files_in_use, 0 as *const libc::c_char, name) + || is_file_in_use( &mut files_in_use, b".increation\x00" as *const u8 as *const libc::c_char, name, ) - || 0 != is_file_in_use( + || is_file_in_use( &mut files_in_use, b".waveform\x00" as *const u8 as *const libc::c_char, name, ) - || 0 != is_file_in_use( + || is_file_in_use( &mut files_in_use, b"-preview.jpg\x00" as *const u8 as *const libc::c_char, name, @@ -1557,7 +1551,7 @@ pub unsafe fn dc_housekeeping(context: &dc_context_t) { closedir(dir_handle); } sqlite3_finalize(stmt); - dc_hash_clear(&mut files_in_use); + free(path as *mut libc::c_void); dc_log_info( context, @@ -1567,10 +1561,10 @@ pub unsafe fn dc_housekeeping(context: &dc_context_t) { } unsafe fn is_file_in_use( - files_in_use: *mut dc_hash_t, + files_in_use: &HashSet, namespc: *const libc::c_char, name: *const libc::c_char, -) -> libc::c_int { +) -> bool { let name_to_check = dc_strdup(name); if !namespc.is_null() { let name_len: libc::c_int = strlen(name) as libc::c_int; @@ -1578,20 +1572,17 @@ unsafe fn is_file_in_use( if name_len <= namespc_len || strcmp(&*name.offset((name_len - namespc_len) as isize), namespc) != 0 { - return 0; + return false; } *name_to_check.offset((name_len - namespc_len) as isize) = 0 as libc::c_char } - let ret: libc::c_int = (dc_hash_find( - files_in_use, - name_to_check as *const libc::c_void, - strlen(name_to_check) as libc::c_int, - ) != 0 as *mut libc::c_void) as libc::c_int; + + let contains = files_in_use.contains(to_str(name_to_check)); free(name_to_check as *mut libc::c_void); - ret + contains } -unsafe fn maybe_add_file(files_in_use: *mut dc_hash_t, file: *const libc::c_char) { +unsafe fn maybe_add_file(files_in_use: &mut HashSet, file: *const libc::c_char) { if strncmp( file, b"$BLOBDIR/\x00" as *const u8 as *const libc::c_char, @@ -1600,18 +1591,13 @@ unsafe fn maybe_add_file(files_in_use: *mut dc_hash_t, file: *const libc::c_char { return; } - let raw_name = &*file.offset(9isize) as *const libc::c_char; - dc_hash_insert( - files_in_use, - raw_name as *const libc::c_void, - strlen(raw_name) as libc::c_int, - 1 as *mut libc::c_void, - ); + let raw_name = to_string(&*file.offset(9isize) as *const libc::c_char); + files_in_use.insert(raw_name); } unsafe fn maybe_add_from_param( context: &dc_context_t, - files_in_use: *mut dc_hash_t, + files_in_use: &mut HashSet, query: *const libc::c_char, param_id: libc::c_int, ) { diff --git a/src/lib.rs b/src/lib.rs index ce3c93251..5cdab0454 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -38,7 +38,6 @@ pub mod dc_contact; pub mod dc_context; pub mod dc_dehtml; pub mod dc_e2ee; -pub mod dc_hash; pub mod dc_imap; pub mod dc_imex; pub mod dc_job; diff --git a/src/oauth2.rs b/src/oauth2.rs index 9b2a0bf67..ef6540a60 100644 --- a/src/oauth2.rs +++ b/src/oauth2.rs @@ -243,7 +243,14 @@ impl Oauth2 { let userinfo_url = self.get_userinfo.unwrap_or_else(|| ""); let userinfo_url = replace_in_uri(&userinfo_url, "$ACCESS_TOKEN", access_token); - let response = reqwest::Client::new().post(&userinfo_url).send(); + // should returns sth. as + // { + // "id": "100000000831024152393", + // "email": "NAME@gmail.com", + // "verified_email": true, + // "picture": "https://lh4.googleusercontent.com/-Gj5jh_9R0BY/AAAAAAAAAAI/AAAAAAAAAAA/IAjtjfjtjNA/photo.jpg" + // } + let response = reqwest::Client::new().get(&userinfo_url).send(); if response.is_err() { warn!( context, diff --git a/src/peerstate.rs b/src/peerstate.rs index f38979086..2b5a6c37d 100644 --- a/src/peerstate.rs +++ b/src/peerstate.rs @@ -1,3 +1,4 @@ +use std::collections::HashSet; use std::ffi::CString; use num_traits::FromPrimitive; @@ -6,12 +7,10 @@ use crate::constants::*; use crate::dc_aheader::*; use crate::dc_chat::*; use crate::dc_context::dc_context_t; -use crate::dc_hash::*; use crate::dc_key::*; use crate::dc_sqlite3::*; use crate::dc_tools::{to_cstring, to_string}; use crate::types::*; -use crate::x::*; /// Peerstate represents the state of an Autocrypt peer. pub struct Peerstate<'a> { @@ -540,21 +539,10 @@ impl<'a> Peerstate<'a> { success } - pub fn has_verified_key(&self, fingerprints: *const dc_hash_t) -> bool { - if fingerprints.is_null() { - return false; - } - + pub fn has_verified_key(&self, fingerprints: &HashSet) -> bool { if self.verified_key.is_some() && self.verified_key_fingerprint.is_some() { - let vkc = to_cstring(self.verified_key_fingerprint.as_ref().unwrap()); - if !unsafe { - dc_hash_find( - fingerprints, - vkc.as_ptr() as *const libc::c_void, - strlen(vkc.as_ptr()) as libc::c_int, - ) - .is_null() - } { + let vkc = self.verified_key_fingerprint.as_ref().unwrap(); + if fingerprints.contains(vkc) { return true; } } diff --git a/tests/stress.rs b/tests/stress.rs index e13f7797f..ecb0daa0e 100644 --- a/tests/stress.rs +++ b/tests/stress.rs @@ -1,5 +1,6 @@ //! Stress some functions for testing; if used as a lib, this file is obsolete. +use std::collections::HashSet; use std::ffi::{CStr, CString}; use mmime::mailimf_types::*; @@ -9,7 +10,6 @@ use deltachat::constants::*; use deltachat::dc_array::*; use deltachat::dc_configure::*; use deltachat::dc_context::*; -use deltachat::dc_hash::*; use deltachat::dc_imex::*; use deltachat::dc_key::*; use deltachat::dc_keyring::*; @@ -2279,22 +2279,14 @@ fn test_encryption_decryption() { let mut public_keyring2 = Keyring::default(); public_keyring2.add_owned(public_key2.clone()); - let mut valid_signatures = dc_hash_t { - keyClass: 0, - copyKey: 0, - count: 0, - first: 0 as *mut dc_hashelem_t, - htsize: 0, - ht: 0 as *mut _ht, - }; - dc_hash_init(&mut valid_signatures, 3i32, 1i32); + let mut valid_signatures: HashSet = Default::default(); let plain = dc_pgp_pk_decrypt( ctext_signed.as_ptr() as *const _, ctext_signed_bytes, &keyring, &public_keyring, - &mut valid_signatures, + Some(&mut valid_signatures), ) .unwrap(); @@ -2302,9 +2294,9 @@ fn test_encryption_decryption() { std::str::from_utf8(&plain).unwrap(), CStr::from_ptr(original_text).to_str().unwrap() ); - assert_eq!(valid_signatures.count, 1); + assert_eq!(valid_signatures.len(), 1); - dc_hash_clear(&mut valid_signatures); + valid_signatures.clear(); let empty_keyring = Keyring::default(); let plain = dc_pgp_pk_decrypt( @@ -2312,32 +2304,32 @@ fn test_encryption_decryption() { ctext_signed_bytes, &keyring, &empty_keyring, - &mut valid_signatures, + Some(&mut valid_signatures), ) .unwrap(); assert_eq!( std::str::from_utf8(&plain).unwrap(), CStr::from_ptr(original_text).to_str().unwrap() ); - assert_eq!(valid_signatures.count, 0); + assert_eq!(valid_signatures.len(), 0); - dc_hash_clear(&mut valid_signatures); + valid_signatures.clear(); let plain = dc_pgp_pk_decrypt( ctext_signed.as_ptr() as *const _, ctext_signed_bytes, &keyring, &public_keyring2, - &mut valid_signatures, + Some(&mut valid_signatures), ) .unwrap(); assert_eq!( std::str::from_utf8(&plain).unwrap(), CStr::from_ptr(original_text).to_str().unwrap() ); - assert_eq!(valid_signatures.count, 0); + assert_eq!(valid_signatures.len(), 0); - dc_hash_clear(&mut valid_signatures); + valid_signatures.clear(); public_keyring2.add_ref(&public_key); @@ -2346,22 +2338,23 @@ fn test_encryption_decryption() { ctext_signed_bytes, &keyring, &public_keyring2, - &mut valid_signatures, + Some(&mut valid_signatures), ) .unwrap(); assert_eq!( std::str::from_utf8(&plain).unwrap(), CStr::from_ptr(original_text).to_str().unwrap() ); - assert_eq!(valid_signatures.count, 1); + assert_eq!(valid_signatures.len(), 1); + + valid_signatures.clear(); - dc_hash_clear(&mut valid_signatures); let plain = dc_pgp_pk_decrypt( ctext_unsigned.as_ptr() as *const _, ctext_unsigned_bytes, &keyring, &public_keyring, - &mut valid_signatures, + Some(&mut valid_signatures), ) .unwrap(); assert_eq!( @@ -2369,7 +2362,7 @@ fn test_encryption_decryption() { CStr::from_ptr(original_text).to_str().unwrap() ); - dc_hash_clear(&mut valid_signatures); + valid_signatures.clear(); let mut keyring = Keyring::default(); keyring.add_ref(&private_key2); @@ -2381,7 +2374,7 @@ fn test_encryption_decryption() { ctext_signed_bytes, &keyring, &public_keyring, - 0 as *mut dc_hash_t, + None, ) .unwrap(); assert_eq!( @@ -2469,21 +2462,21 @@ fn test_dc_mimeparser_with_context() { unsafe { let context = create_test_context(); - let mimeparser: *mut dc_mimeparser_t = dc_mimeparser_new(&context.ctx); + let mut mimeparser = dc_mimeparser_new(&context.ctx); let raw: *const libc::c_char = b"Content-Type: multipart/mixed; boundary=\"==break==\";\nSubject: outer-subject\nX-Special-A: special-a\nFoo: Bar\nChat-Version: 0.0\n\n--==break==\nContent-Type: text/plain; protected-headers=\"v1\";\nSubject: inner-subject\nX-Special-B: special-b\nFoo: Xy\nChat-Version: 1.0\n\ntest1\n\n--==break==--\n\n\x00" as *const u8 as *const libc::c_char; - dc_mimeparser_parse(mimeparser, raw, strlen(raw)); + dc_mimeparser_parse(&mut mimeparser, raw, strlen(raw)); assert_eq!( - CStr::from_ptr((*mimeparser).subject as *const libc::c_char) + CStr::from_ptr(mimeparser.subject as *const libc::c_char) .to_str() .unwrap(), "inner-subject", ); let mut of: *mut mailimf_optional_field = dc_mimeparser_lookup_optional_field( - mimeparser, + &mimeparser, b"X-Special-A\x00" as *const u8 as *const libc::c_char, ); assert_eq!( @@ -2494,7 +2487,7 @@ fn test_dc_mimeparser_with_context() { ); of = dc_mimeparser_lookup_optional_field( - mimeparser, + &mimeparser, b"Foo\x00" as *const u8 as *const libc::c_char, ); assert_eq!( @@ -2505,7 +2498,7 @@ fn test_dc_mimeparser_with_context() { ); of = dc_mimeparser_lookup_optional_field( - mimeparser, + &mimeparser, b"Chat-Version\x00" as *const u8 as *const libc::c_char, ); assert_eq!( @@ -2514,9 +2507,9 @@ fn test_dc_mimeparser_with_context() { .unwrap(), "1.0", ); - assert_eq!(carray_count((*mimeparser).parts), 1); + assert_eq!(carray_count(mimeparser.parts), 1); - dc_mimeparser_unref(mimeparser); + dc_mimeparser_unref(&mut mimeparser); } }