summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/mqueue.rs33
-rw-r--r--test/test_mq.rs17
2 files changed, 40 insertions, 10 deletions
diff --git a/src/mqueue.rs b/src/mqueue.rs
index 63078192..ee2e5f2d 100644
--- a/src/mqueue.rs
+++ b/src/mqueue.rs
@@ -33,30 +33,40 @@ mod consts {
}
mod ffi {
- use libc::{c_char, size_t, ssize_t, c_uint, c_int, mode_t};
+ use libc::{c_char, size_t, ssize_t, c_uint, c_int};
use super::MQd;
use super::MqAttr;
- extern {
- pub fn mq_open(name: *const c_char, oflag: c_int, mode: mode_t, attr: *const MqAttr) -> MQd;
+ extern "C" {
+ pub fn mq_open(name: *const c_char, oflag: c_int, ...) -> MQd;
- pub fn mq_close (mqdes: MQd) -> c_int;
+ pub fn mq_close (mqd: MQd) -> c_int;
- pub fn mq_receive (mqdes: MQd, msg_ptr: *const c_char, msg_len: size_t, msq_prio: *const c_uint) -> ssize_t;
+ pub fn mq_receive (mqd: MQd, msg_ptr: *const c_char, msg_len: size_t, msq_prio: *const c_uint) -> ssize_t;
- pub fn mq_send (mqdes: MQd, msg_ptr: *const c_char, msg_len: size_t, msq_prio: c_uint) -> c_int;
+ pub fn mq_send (mqd: MQd, msg_ptr: *const c_char, msg_len: size_t, msq_prio: c_uint) -> c_int;
+
+ pub fn mq_getattr(mqd: MQd, attr: *mut MqAttr) -> c_int;
}
}
#[repr(C)]
-#[derive(Clone, Copy, Debug)]
+#[derive(Clone, Copy, Debug, Eq, PartialEq)]
pub struct MqAttr {
pub mq_flags: c_long,
pub mq_maxmsg: c_long,
pub mq_msgsize: c_long,
pub mq_curmsgs: c_long,
+ pad: [c_long; 4]
+}
+
+impl MqAttr {
+ pub fn new(mq_flags: c_long, mq_maxmsg: c_long, mq_msgsize: c_long, mq_curmsgs: c_long) -> MqAttr {
+ MqAttr { mq_flags: mq_flags, mq_maxmsg: mq_maxmsg, mq_msgsize: mq_msgsize, mq_curmsgs: mq_curmsgs, pad: [0; 4] }
+ }
}
+
#[inline]
pub fn mq_open(name: &CString, oflag: MQ_OFlag, mode: Mode, attr: &MqAttr) -> Result<MQd> {
let res = unsafe { ffi::mq_open(name.as_ptr(), oflag.bits(), mode.bits() as mode_t, attr as *const MqAttr) };
@@ -95,3 +105,12 @@ pub fn mq_send(mqdes: MQd, message: &CString, msq_prio: u32) -> Result<usize> {
Ok(res as usize)
}
+
+pub fn mq_getattr(mqd: MQd) -> Result<MqAttr> {
+ let mut attr = MqAttr::new(0, 0, 0, 0);
+ let res = unsafe { ffi::mq_getattr(mqd, &mut attr) };
+ if res < 0 {
+ return Err(Error::Sys(Errno::last()));
+ }
+ Ok(attr)
+}
diff --git a/test/test_mq.rs b/test/test_mq.rs
index 36e9dc7c..7821ba51 100644
--- a/test/test_mq.rs
+++ b/test/test_mq.rs
@@ -1,4 +1,4 @@
-use nix::mqueue::{mq_open, mq_close, mq_send, mq_receive};
+use nix::mqueue::{mq_open, mq_close, mq_send, mq_receive, mq_getattr};
use nix::mqueue::{O_CREAT, O_WRONLY, O_RDONLY};
use nix::mqueue::MqAttr;
use nix::sys::stat::{S_IWUSR, S_IRUSR, S_IRGRP, S_IROTH};
@@ -16,8 +16,7 @@ use nix::sys::wait::*;
fn mq_send_and_receive() {
const MSG_SIZE: c_long = 32;
-
- let attr = MqAttr { mq_flags: 0, mq_maxmsg: 10, mq_msgsize: MSG_SIZE, mq_curmsgs: 0 };
+ let attr = MqAttr::new(0, 10, MSG_SIZE, 0);
let mq_name_in_parent = &CString::new(b"/a_nix_test_queue".as_ref()).unwrap();
let mqd_in_parent = mq_open(mq_name_in_parent, O_CREAT | O_WRONLY, S_IWUSR | S_IRUSR | S_IRGRP | S_IROTH, &attr).unwrap();
let msg_to_send = &CString::new("msg_1").unwrap();
@@ -51,3 +50,15 @@ fn mq_send_and_receive() {
Err(_) => panic!("Error: Fork Failed")
}
}
+
+
+#[test]
+fn mq_get_attr() {
+ const MSG_SIZE: c_long = 32;
+ let initial_attr = MqAttr::new(0, 10, MSG_SIZE, 0);
+ let mq_name = &CString::new("/attr_test_get_attr".as_bytes().as_ref()).unwrap();
+ let mqd = mq_open(mq_name, O_CREAT | O_WRONLY, S_IWUSR | S_IRUSR | S_IRGRP | S_IROTH, &initial_attr).unwrap();
+ let read_attr = mq_getattr(mqd);
+ assert!(read_attr.unwrap() == initial_attr);
+ mq_close(mqd).unwrap();
+}