Properly double buffering
This commit is contained in:
@@ -5,13 +5,10 @@ pub struct ShmPool {
|
||||
pub fd: i32,
|
||||
pub addr: *mut c_void,
|
||||
pub size: usize,
|
||||
pub width: usize,
|
||||
}
|
||||
|
||||
impl ShmPool {
|
||||
pub fn new(width: usize, height: usize) -> std::io::Result<ShmPool> {
|
||||
let size = width * height * 4;
|
||||
|
||||
pub fn new(size: usize) -> std::io::Result<ShmPool> {
|
||||
let shm_path: *const i8 = b"/chlorostart\0".as_ptr() as *const i8;
|
||||
let fd = unsafe { shm_open(shm_path, O_RDWR | O_EXCL | O_CREAT, 0o600) };
|
||||
if fd == -1 {
|
||||
@@ -39,17 +36,16 @@ impl ShmPool {
|
||||
fd,
|
||||
addr,
|
||||
size,
|
||||
width,
|
||||
})
|
||||
}
|
||||
|
||||
pub fn from_fd(fd: i32, size: usize) -> std::io::Result<ShmPool> {
|
||||
let addr = unsafe { mmap(std::ptr::null_mut(), size, PROT_READ, MAP_PRIVATE, fd, 0) };
|
||||
if addr == MAP_FAILED {
|
||||
eprint!("mmap in ShmPool::from_fd() failed: ");
|
||||
eprint!("mmap in ShmPool::from_fd() failed with fd {}", fd);
|
||||
return Err(std::io::Error::last_os_error());
|
||||
}
|
||||
Ok(ShmPool {fd, addr, size, width: 0})
|
||||
Ok(ShmPool {fd, addr, size})
|
||||
}
|
||||
|
||||
pub fn read_string(&self, offset: usize) -> std::io::Result<String> {
|
||||
@@ -74,30 +70,31 @@ impl ShmPool {
|
||||
}
|
||||
|
||||
pub fn write(&mut self, data: &Vec<u32>, offset: usize) {
|
||||
if offset > self.size {
|
||||
if offset + data.len() >= self.size {
|
||||
return;
|
||||
}
|
||||
unsafe {
|
||||
std::ptr::copy_nonoverlapping(
|
||||
data.as_ptr() as *const u32, // src: data as *const u32
|
||||
self.addr.offset(4*offset as isize) as *mut u32, // dst: ShmPool address as *mut u32
|
||||
if offset + data.len() * 4 <= self.size {
|
||||
data.len()
|
||||
} else {
|
||||
data.len() - offset
|
||||
}
|
||||
data.len()
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn write_pixel(&mut self, data: u32, offset: isize) {
|
||||
// TODO: Bounds check
|
||||
unsafe {*(self.addr.offset(offset*4) as *mut u32) = data;}
|
||||
pub fn write_pixel(&mut self, data: u32, offset: usize) {
|
||||
// TODO: Return error if out of bounds
|
||||
if offset + 3 > self.size {
|
||||
return;
|
||||
}
|
||||
unsafe {*(self.addr.offset(offset as isize*4) as *mut u32) = data;}
|
||||
}
|
||||
|
||||
pub fn read_pixel(&self, offset: usize) -> u32 {
|
||||
// TODO: Bounds check
|
||||
return unsafe {*(self.addr.offset(4*offset as isize) as *const u32)};
|
||||
pub fn read_pixel(&self, offset: usize) -> Option<u32> {
|
||||
if offset + 3 > self.size {
|
||||
return None;
|
||||
}
|
||||
return Some(unsafe {*(self.addr.offset(4*offset as isize) as *const u32)});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user