annotate src/libpam/response.rs @ 75:c30811b4afae

rename pam_ffi submodule to libpam.
author Paul Fisher <paul@pfish.zone>
date Fri, 06 Jun 2025 22:35:08 -0400
parents src/pam_ffi/response.rs@ac6881304c78
children 351bdc13005e
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
1 //! Types used when dealing with PAM conversations.
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
2
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
3 use crate::conv::BinaryData;
75
c30811b4afae rename pam_ffi submodule to libpam.
Paul Fisher <paul@pfish.zone>
parents: 73
diff changeset
4 use crate::libpam::memory;
c30811b4afae rename pam_ffi submodule to libpam.
Paul Fisher <paul@pfish.zone>
parents: 73
diff changeset
5 use crate::libpam::memory::{CBinaryData, Immovable, NulError, TooBigError};
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
6 use crate::Response;
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
7 use std::ffi::{c_int, c_void, CStr};
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
8 use std::ops::{Deref, DerefMut};
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
9 use std::result::Result as StdResult;
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
10 use std::str::Utf8Error;
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
11 use std::{iter, mem, ptr, slice};
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
12
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
13 #[repr(transparent)]
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
14 #[derive(Debug)]
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
15 pub struct RawTextResponse(RawResponse);
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
16
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
17 impl RawTextResponse {
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
18 /// Interprets the provided `RawResponse` as a text response.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
19 ///
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
20 /// # Safety
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
21 ///
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
22 /// It's up to you to provide a response that is a `RawTextResponse`.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
23 pub unsafe fn upcast(from: &mut RawResponse) -> &mut Self {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
24 // SAFETY: We're provided a valid reference.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
25 &mut *(from as *mut RawResponse).cast::<Self>()
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
26 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
27
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
28 /// Fills in the provided `RawResponse` with the given text.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
29 ///
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
30 /// You are responsible for calling [`free`](Self::free_contents)
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
31 /// on the pointer you get back when you're done with it.
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
32 pub fn fill(dest: &mut RawResponse, text: impl AsRef<str>) -> StdResult<&mut Self, NulError> {
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
33 dest.data = memory::malloc_str(text)?.cast();
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
34 // SAFETY: We just filled this in so we know it's a text response.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
35 Ok(unsafe { Self::upcast(dest) })
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
36 }
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
37
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
38 /// Gets the string stored in this response.
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
39 pub fn contents(&self) -> StdResult<&str, Utf8Error> {
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
40 if self.0.data.is_null() {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
41 Ok("")
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
42 } else {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
43 // SAFETY: This data is either passed from PAM (so we are forced to
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
44 // trust it) or was created by us in TextResponseInner::alloc.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
45 // In either case, it's going to be a valid null-terminated string.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
46 unsafe { CStr::from_ptr(self.0.data.cast()) }.to_str()
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
47 }
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
48 }
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
49
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
50 /// Releases memory owned by this response.
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
51 pub fn free_contents(&mut self) {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
52 // SAFETY: We know we own this data.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
53 // After we're done, it will be null.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
54 unsafe {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
55 memory::zero_c_string(self.0.data);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
56 libc::free(self.0.data);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
57 self.0.data = ptr::null_mut()
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
58 }
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
59 }
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
60 }
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
61
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
62 /// A [`RawResponse`] with [`CBinaryData`] in it.
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
63 #[repr(transparent)]
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
64 #[derive(Debug)]
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
65 pub struct RawBinaryResponse(RawResponse);
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
66
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
67 impl RawBinaryResponse {
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
68 /// Interprets the provided `RawResponse` as a binary response.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
69 ///
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
70 /// # Safety
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
71 ///
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
72 /// It's up to you to provide a response that is a `RawBinaryResponse`.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
73 pub unsafe fn upcast(from: &mut RawResponse) -> &mut Self {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
74 // SAFETY: We're provided a valid reference.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
75 &mut *(from as *mut RawResponse).cast::<Self>()
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
76 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
77
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
78 /// Fills in a `RawResponse` with the provided binary data.
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
79 ///
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
80 /// The `data_type` is a tag you can use for whatever.
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
81 /// It is passed through PAM unchanged.
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
82 ///
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
83 /// The referenced data is copied to the C heap. We do not take ownership.
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
84 /// You are responsible for calling [`free`](Self::free_contents)
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
85 /// on the pointer you get back when you're done with it.
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
86 pub fn fill<'a>(
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
87 dest: &'a mut RawResponse,
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
88 data: &[u8],
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
89 data_type: u8,
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
90 ) -> StdResult<&'a mut Self, TooBigError> {
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
91 dest.data = CBinaryData::alloc(data, data_type)?.cast();
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
92 // SAFETY: We just filled this in, so we know it's binary.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
93 Ok(unsafe { Self::upcast(dest) })
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
94 }
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
95
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
96 /// Gets the binary data in this response.
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
97 pub fn data(&self) -> &[u8] {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
98 self.contents().map(CBinaryData::contents).unwrap_or(&[])
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
99 }
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
100
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
101 /// Gets the `data_type` tag that was embedded with the message.
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
102 pub fn data_type(&self) -> u8 {
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
103 self.contents().map(CBinaryData::data_type).unwrap_or(0)
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
104 }
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
105
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
106 fn contents(&self) -> Option<&CBinaryData> {
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
107 // SAFETY: This was either something we got from PAM (in which case
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
108 // we trust it), or something that was created with
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
109 // BinaryResponseInner::alloc. In both cases, it points to valid data.
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
110 unsafe { self.0.data.cast::<CBinaryData>().as_ref() }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
111 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
112
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
113 pub fn to_owned(&self) -> BinaryData {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
114 BinaryData::new(self.data().into(), self.data_type())
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
115 }
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
116
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
117 /// Releases memory owned by this response.
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
118 pub fn free_contents(&mut self) {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
119 // SAFETY: We know that our data pointer is either valid or null.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
120 // Once we're done, it's null and the response is safe.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
121 unsafe {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
122 let data_ref = self.0.data.cast::<CBinaryData>().as_mut();
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
123 if let Some(d) = data_ref {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
124 d.zero_contents()
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
125 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
126 libc::free(self.0.data);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
127 self.0.data = ptr::null_mut()
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
128 }
70
9f8381a1c09c Implement low-level conversation primitives.
Paul Fisher <paul@pfish.zone>
parents: 69
diff changeset
129 }
9f8381a1c09c Implement low-level conversation primitives.
Paul Fisher <paul@pfish.zone>
parents: 69
diff changeset
130 }
9f8381a1c09c Implement low-level conversation primitives.
Paul Fisher <paul@pfish.zone>
parents: 69
diff changeset
131
9f8381a1c09c Implement low-level conversation primitives.
Paul Fisher <paul@pfish.zone>
parents: 69
diff changeset
132 /// Generic version of response data.
9f8381a1c09c Implement low-level conversation primitives.
Paul Fisher <paul@pfish.zone>
parents: 69
diff changeset
133 ///
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
134 /// This has the same structure as [`RawBinaryResponse`]
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
135 /// and [`RawTextResponse`].
70
9f8381a1c09c Implement low-level conversation primitives.
Paul Fisher <paul@pfish.zone>
parents: 69
diff changeset
136 #[repr(C)]
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
137 #[derive(Debug)]
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
138 pub struct RawResponse {
70
9f8381a1c09c Implement low-level conversation primitives.
Paul Fisher <paul@pfish.zone>
parents: 69
diff changeset
139 /// Pointer to the data returned in a response.
9f8381a1c09c Implement low-level conversation primitives.
Paul Fisher <paul@pfish.zone>
parents: 69
diff changeset
140 /// For most responses, this will be a [`CStr`], but for responses to
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
141 /// [`MessageStyle::BinaryPrompt`]s, this will be [`CBinaryData`]
70
9f8381a1c09c Implement low-level conversation primitives.
Paul Fisher <paul@pfish.zone>
parents: 69
diff changeset
142 /// (a Linux-PAM extension).
9f8381a1c09c Implement low-level conversation primitives.
Paul Fisher <paul@pfish.zone>
parents: 69
diff changeset
143 data: *mut c_void,
9f8381a1c09c Implement low-level conversation primitives.
Paul Fisher <paul@pfish.zone>
parents: 69
diff changeset
144 /// Unused.
9f8381a1c09c Implement low-level conversation primitives.
Paul Fisher <paul@pfish.zone>
parents: 69
diff changeset
145 return_code: c_int,
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
146 _marker: Immovable,
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
147 }
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
148
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
149 /// A contiguous block of responses.
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
150 #[derive(Debug)]
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
151 pub struct OwnedResponses {
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
152 base: *mut RawResponse,
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
153 count: usize,
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
154 }
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
155
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
156 impl OwnedResponses {
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
157 /// Allocates an owned list of responses on the C heap.
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
158 fn alloc(count: usize) -> Self {
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
159 OwnedResponses {
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
160 // SAFETY: We are doing allocation here.
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
161 base: unsafe { libc::calloc(count, size_of::<RawResponse>()) }.cast(),
72
47eb242a4f88 Fill out the PamHandle trait.
Paul Fisher <paul@pfish.zone>
parents: 71
diff changeset
162 count,
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
163 }
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
164 }
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
165
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
166 pub fn build(value: &[Response]) -> StdResult<Self, FillError> {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
167 let mut outputs = OwnedResponses::alloc(value.len());
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
168 // If we fail in here after allocating OwnedResponses,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
169 // we still free all memory, even though we don't zero it first.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
170 // This is an acceptable level of risk.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
171 for (input, output) in iter::zip(value.iter(), outputs.iter_mut()) {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
172 match input {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
173 Response::NoResponse => {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
174 RawTextResponse::fill(output, "")?;
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
175 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
176 Response::Text(data) => {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
177 RawTextResponse::fill(output, data)?;
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
178 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
179 Response::MaskedText(data) => {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
180 RawTextResponse::fill(output, data.unsecure())?;
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
181 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
182 Response::Binary(data) => {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
183 RawBinaryResponse::fill(output, data.data(), data.data_type())?;
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
184 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
185 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
186 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
187 Ok(outputs)
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
188 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
189
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
190 /// Converts this into a `*RawResponse` for passing to PAM.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
191 ///
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
192 /// The pointer "owns" its own data (i.e., this will not be dropped).
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
193 pub fn into_ptr(self) -> *mut RawResponse {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
194 let ret = self.base;
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
195 mem::forget(self);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
196 ret
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
197 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
198
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
199 /// Takes ownership of a list of responses allocated on the C heap.
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
200 ///
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
201 /// # Safety
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
202 ///
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
203 /// It's up to you to make sure you pass a valid pointer.
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
204 pub unsafe fn from_c_heap(base: *mut RawResponse, count: usize) -> Self {
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
205 OwnedResponses { base, count }
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
206 }
66
a674799a5cd3 Make `PamHandle` and `PamModuleHandle` traits.
Paul Fisher <paul@pfish.zone>
parents: 64
diff changeset
207 }
60
05cc2c27334f The Big Refactor: clean up docs and exports.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
208
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
209 #[derive(Debug, thiserror::Error)]
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
210 #[error("error converting responses: {0}")]
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
211 pub enum FillError {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
212 NulError(#[from] NulError),
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
213 TooBigError(#[from] TooBigError),
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
214 }
60
05cc2c27334f The Big Refactor: clean up docs and exports.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
215
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
216 impl Deref for OwnedResponses {
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
217 type Target = [RawResponse];
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
218 fn deref(&self) -> &Self::Target {
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
219 // SAFETY: This is the memory we manage ourselves.
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
220 unsafe { slice::from_raw_parts(self.base, self.count) }
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
221 }
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
222 }
60
05cc2c27334f The Big Refactor: clean up docs and exports.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
223
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
224 impl DerefMut for OwnedResponses {
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
225 fn deref_mut(&mut self) -> &mut Self::Target {
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
226 // SAFETY: This is the memory we manage ourselves.
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
227 unsafe { slice::from_raw_parts_mut(self.base, self.count) }
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
228 }
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
229 }
66
a674799a5cd3 Make `PamHandle` and `PamModuleHandle` traits.
Paul Fisher <paul@pfish.zone>
parents: 64
diff changeset
230
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
231 impl Drop for OwnedResponses {
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
232 fn drop(&mut self) {
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
233 // SAFETY: We allocated this ourselves, or it was provided to us by PAM.
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
234 unsafe {
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
235 for resp in self.iter_mut() {
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
236 libc::free(resp.data)
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
237 }
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
238 libc::free(self.base.cast())
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
239 }
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
240 }
60
05cc2c27334f The Big Refactor: clean up docs and exports.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
241 }
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
242
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
243 #[cfg(test)]
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
244 mod tests {
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
245 use super::{BinaryData, OwnedResponses, RawBinaryResponse, RawTextResponse, Response};
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
246
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
247 #[test]
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
248 fn test_round_trip() {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
249 let responses = [
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
250 Response::Binary(BinaryData::new(vec![1, 2, 3], 99)),
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
251 Response::Text("whats going on".to_owned()),
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
252 Response::MaskedText("well then".into()),
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
253 Response::NoResponse,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
254 Response::Text("bogus".to_owned()),
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
255 ];
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
256 let sent = OwnedResponses::build(&responses).unwrap();
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
257 let heap_resps = sent.into_ptr();
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
258 let mut received = unsafe { OwnedResponses::from_c_heap(heap_resps, 5) };
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
259
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
260 let assert_text = |want, raw| {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
261 let up = unsafe { RawTextResponse::upcast(raw) };
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
262 assert_eq!(want, up.contents().unwrap());
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
263 up.free_contents();
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
264 assert_eq!("", up.contents().unwrap());
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
265 };
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
266 let assert_bin = |want_data: &[u8], want_type, raw| {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
267 let up = unsafe { RawBinaryResponse::upcast(raw) };
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
268 assert_eq!(want_data, up.data());
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
269 assert_eq!(want_type, up.data_type());
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
270 up.free_contents();
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
271 let empty: [u8; 0] = [];
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
272 assert_eq!(&empty, up.data());
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
273 assert_eq!(0, up.data_type());
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
274 };
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
275 if let [zero, one, two, three, four] = &mut received[..] {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
276 assert_bin(&[1, 2, 3], 99, zero);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
277 assert_text("whats going on", one);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
278 assert_text("well then", two);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
279 assert_text("", three);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
280 assert_text("bogus", four);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
281 } else {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
282 panic!("wrong size!")
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
283 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
284 }
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
285
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
286 #[test]
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
287 fn test_text_response() {
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
288 let mut responses = OwnedResponses::alloc(2);
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
289 let text = RawTextResponse::fill(&mut responses[0], "hello").unwrap();
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
290 let data = text.contents().expect("valid");
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
291 assert_eq!("hello", data);
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
292 text.free_contents();
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
293 text.free_contents();
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
294 RawTextResponse::fill(&mut responses[1], "hell\0").expect_err("should error; contains nul");
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
295 }
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
296
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
297 #[test]
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
298 fn test_binary_response() {
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
299 let mut responses = OwnedResponses::alloc(1);
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
300 let real_data = [1, 2, 3, 4, 5, 6, 7, 8];
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
301 let resp = RawBinaryResponse::fill(&mut responses[0], &real_data, 7)
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
302 .expect("alloc should succeed");
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
303 let data = resp.data();
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
304 assert_eq!(&real_data, data);
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
305 assert_eq!(7, resp.data_type());
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
306 resp.free_contents();
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents: 72
diff changeset
307 resp.free_contents();
70
9f8381a1c09c Implement low-level conversation primitives.
Paul Fisher <paul@pfish.zone>
parents: 69
diff changeset
308 }
9f8381a1c09c Implement low-level conversation primitives.
Paul Fisher <paul@pfish.zone>
parents: 69
diff changeset
309
9f8381a1c09c Implement low-level conversation primitives.
Paul Fisher <paul@pfish.zone>
parents: 69
diff changeset
310 #[test]
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
311 #[ignore]
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
312 fn test_binary_response_too_big() {
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
313 let big_data: Vec<u8> = vec![0xFFu8; 10_000_000_000];
71
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
314 let mut responses = OwnedResponses::alloc(1);
58f9d2a4df38 Reorganize everything again???
Paul Fisher <paul@pfish.zone>
parents: 70
diff changeset
315 RawBinaryResponse::fill(&mut responses[0], &big_data, 0).expect_err("this is too big!");
69
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
316 }
8f3ae0c7ab92 Rework conversation data types and make safe wrappers.
Paul Fisher <paul@pfish.zone>
parents: 66
diff changeset
317 }