From 0febcbea09fcd33ce8f555b254b6eaf1f8d3d3a5 Mon Sep 17 00:00:00 2001 From: Dominik Maier Date: Sun, 22 Nov 2020 01:51:17 +0100 Subject: [PATCH] fixed string handling --- llmp_test/src/main.rs | 54 +++++++++------------------------- src/events/llmp_translated.rs | 30 +++++++++---------- src/events/shmem_translated.rs | 28 ++++++++++-------- 3 files changed, 44 insertions(+), 68 deletions(-) diff --git a/llmp_test/src/main.rs b/llmp_test/src/main.rs index 1e927d293a..b0f5d2d6e8 100644 --- a/llmp_test/src/main.rs +++ b/llmp_test/src/main.rs @@ -10,7 +10,6 @@ fn llmp_test_clientloop(client: *mut llmp_client, _data: *mut c_void) { } fn main() { - let thread_count = 1; /* The main node has a broker, a tcp server, and a few worker threads */ @@ -24,45 +23,20 @@ fn main() { llmp_client_count: 0, llmp_clients: ptr::null_mut(), }; - unsafe {llmp_broker_init(&mut broker).expect("Could not init")}; - - unsafe {llmp_broker_register_childprocess_clientloop(&mut broker, llmp_test_clientloop, ptr::null_mut()).expect("could not add child clientloop")}; - - /*unsafe {llmp_broker_register_threaded_clientloop(broker, llmp_clientloop_print_u32, NULL)) { - - FATAL("error adding threaded client"); + let thread_count = 4; + unsafe { + llmp_broker_init(&mut broker).expect("Could not init"); + for i in 0..thread_count { + println!("Adding client {}", i); + llmp_broker_register_childprocess_clientloop( + &mut broker, + llmp_test_clientloop, + ptr::null_mut(), + ) + .expect("could not add child clientloop"); + } + println!("Spawning broker"); + llmp_broker_run(&mut broker); } - - int i; - for (i = 0; i < thread_count; i++) { - - if (!llmp_broker_register_threaded_clientloop(broker, llmp_clientloop_rand_u32, NULL)) { - - FATAL("error adding threaded client"); - - } - - } - - OKF("Spawning main on port %d", port); - llmp_broker_run(broker); - - } else { - - if (thread_count > 1) { WARNF("Multiple threads not supported for clients."); } - - OKF("Client will connect to port %d", port); - // Worker only needs to spawn client threads. - llmp_client_t *client_state = llmp_client_new(port); - if (!client_state) { FATAL("Error connecting to broker at port %d", port); } - llmp_clientloop_rand_u32(client_state, NULL); - - } - - FATAL("Unreachable"); - - - println!("Hello, world!"); - */ } diff --git a/src/events/llmp_translated.rs b/src/events/llmp_translated.rs index ff349520f9..0a0734a9cd 100644 --- a/src/events/llmp_translated.rs +++ b/src/events/llmp_translated.rs @@ -53,7 +53,7 @@ use ::libc; use core::sync::atomic::{compiler_fence, Ordering}; use libc::{c_int, c_uint, c_ulong, c_ushort, c_void}; use std::process::exit; -use std::str; +use std::ffi::CStr; use crate::AflError; use crate::utils::next_pow2; @@ -680,7 +680,7 @@ pub unsafe extern "C" fn llmp_broker_alloc_next( Be careful: Intenral realloc may change the location of the client map */ unsafe fn llmp_broker_register_client( mut broker: *mut llmp_broker_state, - shm_str: &str, + shm_str: &CStr, map_size: c_ulong, ) -> *mut llmp_broker_client_metadata { /* make space for a new client and calculate its id */ @@ -780,7 +780,7 @@ unsafe fn llmp_broker_handle_new_msgs( afl_shmem_deinit(client_map); if afl_shmem_by_str( client_map, - str::from_utf8(&(*pageinfo).shm_str).unwrap(), + CStr::from_bytes_with_nul(&(*pageinfo).shm_str).expect("Illegal shm_str"), (*pageinfo).map_size, ) .is_null() @@ -811,7 +811,7 @@ unsafe fn llmp_broker_handle_new_msgs( let client_id: u32 = (*(*client).client_state).id; if llmp_broker_register_client( broker, - str::from_utf8(&(*pageinfo).shm_str).unwrap(), + CStr::from_bytes_with_nul(&(*pageinfo).shm_str).expect("Illegal shm_str"), (*pageinfo).map_size, ) .is_null() @@ -901,8 +901,7 @@ pub unsafe extern "C" fn llmp_broker_once(broker: *mut llmp_broker_state) { } /* The broker walks all pages and looks for changes, then broadcasts them on * its own shared page */ -#[no_mangle] -pub unsafe extern "C" fn llmp_broker_loop(broker: *mut llmp_broker_state) { +pub unsafe fn llmp_broker_loop(broker: *mut llmp_broker_state) -> !{ loop { compiler_fence(Ordering::SeqCst); llmp_broker_once(broker); @@ -1000,8 +999,8 @@ pub unsafe extern "C" fn llmp_broker_launch_client( } //return 1 as c_int != 0; } -#[no_mangle] -pub unsafe extern "C" fn llmp_broker_launch_clientloops(broker: *mut llmp_broker_state) -> bool { + +pub unsafe fn llmp_broker_launch_clientloops(broker: *mut llmp_broker_state) -> Result<(), AflError> { let mut i: c_ulong = 0; while i < (*broker).llmp_client_count { if (*(*broker).llmp_clients.offset(i as isize)).client_type as c_uint @@ -1009,13 +1008,14 @@ pub unsafe extern "C" fn llmp_broker_launch_clientloops(broker: *mut llmp_broker { if !llmp_broker_launch_client(broker, &mut *(*broker).llmp_clients.offset(i as isize)) { println!("[!] WARNING: Could not launch all clients"); - return 0 as c_int != 0; + return Err(AflError::Unknown("Failed to launch clients".into())) } } i = i.wrapping_add(1) } - return 1 as c_int != 0; + Ok(()) } + /* The broker walks all pages and looks for changes, then broadcasts them on its own shared page. Never returns. */ @@ -1023,11 +1023,11 @@ Never returns. */ Same as llmp_broker_launch_threaded clients(); Never returns. */ /* Start all threads and the main broker. Never returns. */ -#[no_mangle] -pub unsafe extern "C" fn llmp_broker_run(broker: *mut llmp_broker_state) { - llmp_broker_launch_clientloops(broker); +pub unsafe fn llmp_broker_run(broker: *mut llmp_broker_state) -> ! { + llmp_broker_launch_clientloops(broker).expect("Failed to launch clients"); llmp_broker_loop(broker); } + /* For non zero-copy, we want to get rid of old pages with duplicate messages eventually. This function This funtion sees if we can unallocate older pages. @@ -1127,7 +1127,7 @@ pub unsafe extern "C" fn llmp_client_recv(mut client: *mut llmp_client) -> *mut afl_shmem_deinit(broadcast_map); if afl_shmem_by_str( (*client).current_broadcast_map, - str::from_utf8(&(*pageinfo).shm_str).unwrap(), + CStr::from_bytes_with_nul(&(*pageinfo).shm_str).expect("Illegal shm_str"), (*pageinfo).map_size, ) .is_null() @@ -1350,7 +1350,7 @@ pub unsafe fn llmp_broker_register_childprocess_clientloop( return Err(AflError::Unknown("Alloc".into())); } let mut client: *mut llmp_broker_client_metadata = - llmp_broker_register_client(broker, str::from_utf8(&client_map.shm_str).unwrap(), client_map.map_size); + llmp_broker_register_client(broker, CStr::from_ptr(&client_map.shm_str as *const i8), client_map.map_size); if client.is_null() { afl_shmem_deinit(&mut client_map); return Err(AflError::Unknown("Something in clients failed".into())); diff --git a/src/events/shmem_translated.rs b/src/events/shmem_translated.rs index 3823567702..3ffa692a31 100644 --- a/src/events/shmem_translated.rs +++ b/src/events/shmem_translated.rs @@ -1,5 +1,6 @@ use ::libc; use libc::{c_int, c_uint, c_char, c_uchar, c_ushort, c_long, c_ulong, c_void}; +use std::ffi::CStr; extern "C" { #[no_mangle] @@ -84,7 +85,7 @@ pub const AFL_RET_SUCCESS: c_uint = 0; #[derive(Copy, Clone)] #[repr(C)] pub struct afl_shmem { - pub shm_str: [u8; 20], + pub shm_str: [c_char; 20], pub shm_id: c_int, pub map: *mut c_uchar, pub map_size: c_ulong, @@ -96,8 +97,8 @@ pub unsafe fn afl_shmem_deinit(mut shm: *mut afl_shmem) { // Not set or not initialized; return } - (*shm).shm_str[0 as c_int as usize] = - '\u{0}' as i32 as u8; + (*shm).shm_str[0 as usize] = + '\u{0}' as c_char; shmctl((*shm).shm_id, 0 as c_int, 0 as *mut shmid_ds); (*shm).map = 0 as *mut c_uchar; } @@ -112,8 +113,8 @@ pub unsafe fn afl_shmem_init(mut shm: *mut afl_shmem, 0o1000 as c_int | 0o2000 as c_int | 0o600 as c_int); if (*shm).shm_id < 0 as c_int { - (*shm).shm_str[0 as c_int as usize] = - '\u{0}' as i32 as u8; + (*shm).shm_str[0] = + '\u{0}' as c_char; return 0 as *mut c_uchar } snprintf((*shm).shm_str.as_mut_ptr() as *mut i8, @@ -122,7 +123,7 @@ pub unsafe fn afl_shmem_init(mut shm: *mut afl_shmem, (*shm).shm_str[(::std::mem::size_of::<[c_char; 20]>() as c_ulong).wrapping_sub(1 as c_int as c_ulong) as - usize] = '\u{0}' as i32 as u8; + usize] = '\u{0}' as c_char; (*shm).map = shmat((*shm).shm_id, 0 as *const c_void, 0 as c_int) as *mut c_uchar; @@ -131,16 +132,16 @@ pub unsafe fn afl_shmem_init(mut shm: *mut afl_shmem, shmctl((*shm).shm_id, 0 as c_int, 0 as *mut shmid_ds); (*shm).shm_id = -(1 as c_int); (*shm).shm_str[0 as c_int as usize] = - '\u{0}' as i32 as u8; + '\u{0}' as c_char; return 0 as *mut c_uchar } return (*shm).map; } pub unsafe fn afl_shmem_by_str(mut shm: *mut afl_shmem, - shm_str: &str, + shm_str: &CStr, map_size: c_ulong) -> *mut c_uchar { - if shm.is_null() || shm_str.len() == 0 || map_size == 0 { + if shm.is_null() || shm_str.to_bytes().len() == 0 || map_size == 0 { return 0 as *mut c_uchar } (*shm).map = 0 as *mut c_uchar; @@ -149,7 +150,7 @@ pub unsafe fn afl_shmem_by_str(mut shm: *mut afl_shmem, (::std::mem::size_of::<[c_char; 20]>() as c_ulong).wrapping_sub(1 as c_int as c_ulong)); - (*shm).shm_id = shm_str.parse::().unwrap(); + (*shm).shm_id = shm_str.to_str().expect(&format!("illegal shm_str {:?}", shm_str)).parse::().unwrap(); (*shm).map = shmat((*shm).shm_id, 0 as *const c_void, 0 as c_int) as *mut c_uchar; @@ -157,7 +158,7 @@ pub unsafe fn afl_shmem_by_str(mut shm: *mut afl_shmem, (*shm).map = 0 as *mut c_uchar; (*shm).map_size = 0 as c_int as c_ulong; (*shm).shm_str[0 as c_int as usize] = - '\u{0}' as i32 as u8; + '\u{0}' as c_char; return 0 as *mut c_uchar } return (*shm).map; @@ -166,9 +167,10 @@ pub unsafe fn afl_shmem_by_str(mut shm: *mut afl_shmem, /* Write sharedmap as env var */ /* Write sharedmap as env var and the size as name#_SIZE */ pub unsafe fn afl_shmem_to_env_var(shmem: *mut afl_shmem, - env_name: &str) + env_name: &CStr) -> c_uint { - if shmem.is_null() || env_name.len() == 0 || env_name.len() > 200 || + let env_len = env_name.to_bytes().len(); + if shmem.is_null() || env_len == 0 || env_len > 200 || (*shmem).shm_str[0 as c_int as usize] == 0 { return AFL_RET_NULL_PTR }