annotate src/libpam/handle.rs @ 87:05291b601f0a

Well and truly separate the Linux extensions. This separates the Linux extensions on the libpam side, and disables the two enums on the interface side. Users can still call the Linux extensions from non-Linux PAM impls, but they'll get a conversation error back.
author Paul Fisher <paul@pfish.zone>
date Tue, 10 Jun 2025 04:40:01 -0400
parents 5aa1a010f1e8
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
1 use super::conversation::LibPamConversation;
80
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
2 use crate::constants::{ErrorCode, Result};
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
3 use crate::conv::Message;
80
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
4 use crate::handle::PamShared;
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
5 pub use crate::libpam::pam_ffi::LibPamHandle;
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
6 use crate::libpam::{memory, pam_ffi};
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
7 use crate::{Conversation, PamHandleModule};
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
8 use num_enum::{IntoPrimitive, TryFromPrimitive};
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
9 use std::cell::Cell;
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
10 use std::ffi::{c_char, c_int};
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
11 use std::ops::{Deref, DerefMut};
80
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
12 use std::ptr;
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
13
80
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
14 struct HandleWrap(*mut LibPamHandle);
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
15
80
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
16 impl Deref for HandleWrap {
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
17 type Target = LibPamHandle;
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
18 fn deref(&self) -> &Self::Target {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
19 unsafe { &*self.0 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
20 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
21 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
22
80
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
23 impl DerefMut for HandleWrap {
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
24 fn deref_mut(&mut self) -> &mut Self::Target {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
25 unsafe { &mut *self.0 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
26 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
27 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
28
80
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
29 /// An owned PAM handle.
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
30 pub struct OwnedLibPamHandle {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
31 handle: HandleWrap,
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
32 last_return: Cell<Result<()>>,
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
33 }
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
34
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
35 // TODO: pam_authenticate - app
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
36 // pam_setcred - app
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
37 // pam_acct_mgmt - app
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
38 // pam_chauthtok - app
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
39 // pam_open_session - app
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
40 // pam_close_session - app
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
41 // pam_putenv - shared
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
42 // pam_getenv - shared
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
43 // pam_getenvlist - shared
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
44
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
45 impl Drop for OwnedLibPamHandle {
80
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
46 /// Closes the PAM session on an owned PAM handle.
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
47 ///
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
48 /// See the [`pam_end` manual page][man] for more information.
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
49 ///
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
50 /// [man]: https://www.man7.org/linux/man-pages/man3/pam_end.3.html
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
51 fn drop(&mut self) {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
52 unsafe {
80
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
53 pam_ffi::pam_end(
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
54 self.handle.0,
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
55 ErrorCode::result_to_c(self.last_return.get()),
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
56 );
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
57 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
58 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
59 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
60
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
61 macro_rules! cstr_item {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
62 (get = $getter:ident, item = $item_type:path) => {
80
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
63 fn $getter(&self) -> Result<Option<&str>> {
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
64 unsafe { self.get_cstr_item($item_type) }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
65 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
66 };
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
67 (set = $setter:ident, item = $item_type:path) => {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
68 fn $setter(&mut self, value: Option<&str>) -> Result<()> {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
69 unsafe { self.set_cstr_item($item_type, value) }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
70 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
71 };
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
72 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
74 impl PamShared for LibPamHandle {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
75 fn get_user(&mut self, prompt: Option<&str>) -> Result<&str> {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
76 let prompt = memory::option_cstr(prompt)?;
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
77 let mut output: *const c_char = ptr::null();
80
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
78 let ret = unsafe {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
79 pam_ffi::pam_get_user(self, &mut output, memory::prompt_ptr(prompt.as_ref()))
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
80 };
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
81 ErrorCode::result_from(ret)?;
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
82 unsafe { memory::wrap_string(output) }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
83 .transpose()
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
84 .unwrap_or(Err(ErrorCode::ConversationError))
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
85 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
86
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
87 cstr_item!(get = user_item, item = ItemType::User);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
88 cstr_item!(set = set_user_item, item = ItemType::User);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
89 cstr_item!(get = service, item = ItemType::Service);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
90 cstr_item!(set = set_service, item = ItemType::Service);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
91 cstr_item!(get = user_prompt, item = ItemType::UserPrompt);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
92 cstr_item!(set = set_user_prompt, item = ItemType::UserPrompt);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
93 cstr_item!(get = tty_name, item = ItemType::Tty);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
94 cstr_item!(set = set_tty_name, item = ItemType::Tty);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
95 cstr_item!(get = remote_user, item = ItemType::RemoteUser);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
96 cstr_item!(set = set_remote_user, item = ItemType::RemoteUser);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
97 cstr_item!(get = remote_host, item = ItemType::RemoteHost);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
98 cstr_item!(set = set_remote_host, item = ItemType::RemoteHost);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
99 cstr_item!(set = set_authtok_item, item = ItemType::AuthTok);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
100 cstr_item!(set = set_old_authtok_item, item = ItemType::OldAuthTok);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
101 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
102
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
103 impl Conversation for LibPamHandle {
77
351bdc13005e Update the libpam module to work with the new structure.
Paul Fisher <paul@pfish.zone>
parents: 75
diff changeset
104 fn communicate(&mut self, messages: &[Message]) {
351bdc13005e Update the libpam module to work with the new structure.
Paul Fisher <paul@pfish.zone>
parents: 75
diff changeset
105 match self.conversation_item() {
351bdc13005e Update the libpam module to work with the new structure.
Paul Fisher <paul@pfish.zone>
parents: 75
diff changeset
106 Ok(conv) => conv.communicate(messages),
351bdc13005e Update the libpam module to work with the new structure.
Paul Fisher <paul@pfish.zone>
parents: 75
diff changeset
107 Err(e) => {
351bdc13005e Update the libpam module to work with the new structure.
Paul Fisher <paul@pfish.zone>
parents: 75
diff changeset
108 for msg in messages {
351bdc13005e Update the libpam module to work with the new structure.
Paul Fisher <paul@pfish.zone>
parents: 75
diff changeset
109 msg.set_error(e)
351bdc13005e Update the libpam module to work with the new structure.
Paul Fisher <paul@pfish.zone>
parents: 75
diff changeset
110 }
351bdc13005e Update the libpam module to work with the new structure.
Paul Fisher <paul@pfish.zone>
parents: 75
diff changeset
111 }
351bdc13005e Update the libpam module to work with the new structure.
Paul Fisher <paul@pfish.zone>
parents: 75
diff changeset
112 }
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
113 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
114 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
115
80
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
116 impl PamHandleModule for LibPamHandle {
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
117 fn get_authtok(&mut self, prompt: Option<&str>) -> Result<&str> {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
118 let prompt = memory::option_cstr(prompt)?;
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
119 let mut output: *const c_char = ptr::null_mut();
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
120 // SAFETY: We're calling this with known-good values.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
121 let res = unsafe {
80
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
122 pam_ffi::pam_get_authtok(
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
123 self,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
124 ItemType::AuthTok.into(),
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
125 &mut output,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
126 memory::prompt_ptr(prompt.as_ref()),
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
127 )
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
128 };
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
129 ErrorCode::result_from(res)?;
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
130 // SAFETY: We got this string from PAM.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
131 unsafe { memory::wrap_string(output) }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
132 .transpose()
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
133 .unwrap_or(Err(ErrorCode::ConversationError))
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
134 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
135
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
136 cstr_item!(get = authtok_item, item = ItemType::AuthTok);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
137 cstr_item!(get = old_authtok_item, item = ItemType::OldAuthTok);
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
138 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
139
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
140 /// Function called at the end of a PAM session that is called to clean up
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
141 /// a value previously provided to PAM in a `pam_set_data` call.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
142 ///
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
143 /// You should never call this yourself.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
144 extern "C" fn set_data_cleanup<T>(_: *const libc::c_void, c_data: *mut libc::c_void, _: c_int) {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
145 unsafe {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
146 let _data: Box<T> = Box::from_raw(c_data.cast());
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
147 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
148 }
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
149
80
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
150 impl LibPamHandle {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
151 /// Gets a C string item.
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
152 ///
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
153 /// # Safety
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
154 ///
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
155 /// You better be requesting an item which is a C string.
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
156 unsafe fn get_cstr_item(&self, item_type: ItemType) -> Result<Option<&str>> {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
157 let mut output = ptr::null();
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
158 let ret = unsafe { pam_ffi::pam_get_item(self, item_type as c_int, &mut output) };
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
159 ErrorCode::result_from(ret)?;
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
160 memory::wrap_string(output.cast())
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
161 }
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
162
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
163 /// Sets a C string item.
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
164 ///
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
165 /// # Safety
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
166 ///
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
167 /// You better be setting an item which is a C string.
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
168 unsafe fn set_cstr_item(&mut self, item_type: ItemType, data: Option<&str>) -> Result<()> {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
169 let data_str = memory::option_cstr(data)?;
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
170 let ret = unsafe {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
171 pam_ffi::pam_set_item(
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
172 self,
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
173 item_type as c_int,
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
174 memory::prompt_ptr(data_str.as_ref()).cast(),
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
175 )
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
176 };
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
177 ErrorCode::result_from(ret)
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
178 }
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
179
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
180 /// Gets the `PAM_CONV` item from the handle.
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
181 fn conversation_item(&mut self) -> Result<&mut LibPamConversation<'_>> {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
182 let output: *mut LibPamConversation = ptr::null_mut();
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
183 let result = unsafe {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
184 pam_ffi::pam_get_item(
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
185 self,
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
186 ItemType::Conversation.into(),
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
187 &mut output.cast_const().cast(),
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
188 )
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
189 };
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
190 ErrorCode::result_from(result)?;
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
191 // SAFETY: We got this result from PAM, and we're checking if it's null.
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
192 unsafe { output.as_mut() }.ok_or(ErrorCode::ConversationError)
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
193 }
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
194 }
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
195
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
196 macro_rules! delegate {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
197 (fn $meth:ident(&self $(, $param:ident: $typ:ty)*) -> Result<$ret:ty>) => {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
198 fn $meth(&self $(, $param: $typ)*) -> Result<$ret> {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
199 let result = self.handle.$meth($($param),*);
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
200 self.last_return.set(split(&result));
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
201 result
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
202 }
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
203 };
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
204 (fn $meth:ident(&mut self $(, $param:ident: $typ:ty)*) -> Result<$ret:ty>) => {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
205 fn $meth(&mut self $(, $param: $typ)*) -> Result<$ret> {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
206 let result = self.handle.$meth($($param),*);
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
207 self.last_return.set(split(&result));
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
208 result
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
209 }
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
210 };
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
211 (get = $get:ident$(, set = $set:ident)?) => {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
212 delegate!(fn $get(&self) -> Result<Option<&str>>);
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
213 $(delegate!(set = $set);)?
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
214 };
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
215 (set = $set:ident) => {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
216 delegate!(fn $set(&mut self, value: Option<&str>) -> Result<()>);
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
217 };
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
218 }
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
219
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
220 fn split<T>(result: &Result<T>) -> Result<()> {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
221 result.as_ref().map(drop).map_err(|&e| e)
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
222 }
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
223
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
224 impl PamShared for OwnedLibPamHandle {
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
225 delegate!(fn get_user(&mut self, prompt: Option<&str>) -> Result<&str>);
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
226 delegate!(get = user_item, set = set_user_item);
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
227 delegate!(get = service, set = set_service);
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
228 delegate!(get = user_prompt, set = set_user_prompt);
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
229 delegate!(get = tty_name, set = set_tty_name);
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
230 delegate!(get = remote_user, set = set_remote_user);
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
231 delegate!(get = remote_host, set = set_remote_host);
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
232 delegate!(set = set_authtok_item);
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
233 delegate!(set = set_old_authtok_item);
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
234 }
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
235
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
236 /// Identifies what is being gotten or set with `pam_get_item`
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
237 /// or `pam_set_item`.
80
5aa1a010f1e8 Start using PAM headers; improve owned/borrowed distinction.
Paul Fisher <paul@pfish.zone>
parents: 78
diff changeset
238 #[derive(TryFromPrimitive, IntoPrimitive)]
73
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
239 #[repr(i32)]
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
240 #[non_exhaustive] // because C could give us anything!
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
241 pub enum ItemType {
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
242 /// The PAM service name.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
243 Service = 1,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
244 /// The user's login name.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
245 User = 2,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
246 /// The TTY name.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
247 Tty = 3,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
248 /// The remote host (if applicable).
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
249 RemoteHost = 4,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
250 /// The conversation struct (not a CStr-based item).
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
251 Conversation = 5,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
252 /// The authentication token (password).
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
253 AuthTok = 6,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
254 /// The old authentication token (when changing passwords).
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
255 OldAuthTok = 7,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
256 /// The remote user's name.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
257 RemoteUser = 8,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
258 /// The prompt shown when requesting a username.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
259 UserPrompt = 9,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
260 /// App-supplied function to override failure delays.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
261 FailDelay = 10,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
262 /// X display name.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
263 XDisplay = 11,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
264 /// X server authentication data.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
265 XAuthData = 12,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
266 /// The type of `pam_get_authtok`.
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
267 AuthTokType = 13,
ac6881304c78 Do conversations, along with way too much stuff.
Paul Fisher <paul@pfish.zone>
parents:
diff changeset
268 }