From 7365f0c5758954ea29b3e34648baca4b9876e624 Mon Sep 17 00:00:00 2001 From: Tomasz Kramkowski Date: Sun, 29 Jan 2023 17:26:42 +0000 Subject: Remove dependency on pam-bindings --- Cargo.toml | 1 - src/lib.rs | 20 ++++++++++---------- src/pam.rs | 39 +++++++++++++++++++++++++++++++++++++++ 3 files changed, 49 insertions(+), 11 deletions(-) create mode 100644 src/pam.rs diff --git a/Cargo.toml b/Cargo.toml index 9b5594d..060453e 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -14,4 +14,3 @@ crate-type = ["cdylib"] [dependencies] cap-std = "1.0.4" libc = "0.2.139" -pam-bindings = "0.1.1" diff --git a/src/lib.rs b/src/lib.rs index c104a23..3fd0630 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -1,11 +1,12 @@ // Copyright (C) 2023 Tomasz Kramkowski // SPDX-License-Identifier: MIT +mod pam; mod passwd; use cap_std::fs::{Dir, OpenOptions}; -use pam::module::PamHandle; -use std::ffi::{c_char, c_int, CString}; +use pam::PAMHandle; +use std::ffi::{c_char, c_int, CStr}; use std::io::{ErrorKind, Write}; use std::panic; use std::path::Path; @@ -31,9 +32,8 @@ impl From for SessionError { } } -fn open_session(h: &PamHandle, mountpoint: &str) -> Result<(), SessionError> { - let user = h.get_user(None).or(Err(SessionError))?; - let user = CString::new(user).or(Err(SessionError))?; +fn open_session(h: &PAMHandle, mountpoint: &str) -> Result<(), SessionError> { + let user = h.get_user::(None).or(Err(SessionError))?; let uid = passwd::get_uid_by_name(&user).ok_or(SessionError)?; let uid = uid.to_string(); let d = Dir::open_ambient_dir(mountpoint, cap_std::ambient_authority())?; @@ -52,23 +52,23 @@ const CG_MOUNT: &str = "/sys/fs/cgroup"; #[no_mangle] pub extern "C" fn pam_sm_open_session( - h: &mut PamHandle, + h: &mut PAMHandle, _flags: c_int, _argc: c_int, _argv: *const *const c_char, ) -> c_int { match panic::catch_unwind(|| open_session(h, CG_MOUNT)) { - Ok(Ok(())) => 0, - _ => 14, + Ok(Ok(())) => pam::SUCCESS, + _ => pam::SESSION_ERR, } } #[no_mangle] pub extern "C" fn pam_sm_close_session( - _h: &mut PamHandle, + _h: &mut PAMHandle, _flags: c_int, _argc: c_int, _argv: *const *const c_char, ) -> c_int { - 0 + pam::SUCCESS } diff --git a/src/pam.rs b/src/pam.rs new file mode 100644 index 0000000..17e4590 --- /dev/null +++ b/src/pam.rs @@ -0,0 +1,39 @@ +use core::marker::{PhantomData, PhantomPinned}; +use std::ffi::{c_char, c_int, CStr, CString}; + +#[repr(C)] +pub struct PAMHandle { + _data: [u8; 0], + _marker: PhantomData<(*mut u8, PhantomPinned)>, +} + +pub const SUCCESS: c_int = 0; +pub const SESSION_ERR: c_int = 14; + +extern "C" { + fn pam_get_user( + pamh: *const PAMHandle, + user: &*const c_char, + prompt: *const c_char, + ) -> c_int; +} + +impl PAMHandle { + pub fn get_user + ?Sized>( + &self, + prompt: Option<&S>, + ) -> Result { + let ptr: *const c_char = std::ptr::null_mut(); + let prompt = match prompt { + Some(prompt) => prompt.as_ref().as_ptr(), + None => core::ptr::null(), + }; + match unsafe { pam_get_user(self, &ptr, prompt) } { + SUCCESS if !ptr.is_null() => { + let cstr = unsafe { CStr::from_ptr(ptr) }; + Ok(CString::from(cstr)) + } + e => Err(e), + } + } +} -- cgit v1.2.3-54-g00ecf