use crate::*;
use crate::alloc::*;
use crate::token::*;
use winapi::shared::winerror::*;
use winapi::um::securitybaseapi::GetTokenInformation;
use winapi::um::winnt::*;
use core::ops::Deref;
use core::ptr::null_mut;
pub fn user(token: &token::OwnedHandle) -> Result<BoxTokenUser, Error> { unsafe { Ok(BoxTokenUser::from_raw(raw_bytes(token, TokenUser)?)) } }
pub fn groups(token: &token::OwnedHandle) -> Result<BoxTokenGroups, Error> { unsafe { Ok(BoxTokenGroups::from_raw(raw_bytes(token, TokenGroups)?)) } }
pub fn privileges(token: &token::OwnedHandle) -> Result<BoxTokenPrivileges, Error> { unsafe { Ok(BoxTokenPrivileges::from_raw(raw_bytes(token, TokenPrivileges)?)) } }
pub fn owner(token: &token::OwnedHandle) -> Result<BoxTokenOwner, Error> { unsafe { Ok(BoxTokenOwner::from_raw(raw_bytes(token, TokenOwner)?)) } }
pub fn primary_group(token: &token::OwnedHandle) -> Result<BoxTokenPrimaryGroup, Error> { unsafe { Ok(BoxTokenPrimaryGroup::from_raw(raw_bytes(token, TokenPrimaryGroup)?)) } }
pub fn default_dacl(token: &token::OwnedHandle) -> Result<BoxTokenDefaultDacl, Error> { unsafe { Ok(BoxTokenDefaultDacl::from_raw(raw_bytes(token, TokenDefaultDacl)?)) } }
pub fn source(token: &token::OwnedHandle) -> Result<Source, Error> { unsafe { raw_fixed(token, TokenSource) } }
pub fn r#type(token: &token::OwnedHandle) -> Result<token::Type, Error> { unsafe { raw_fixed(token, TokenType) } }
pub use r#type as ty;
pub fn impersonation_level(token: &token::OwnedHandle) -> Result<security::ImpersonationLevel, Error> { unsafe { raw_fixed(token, TokenImpersonationLevel) } }
pub fn statistics(token: &token::OwnedHandle) -> Result<TOKEN_STATISTICS, Error> { unsafe { raw_fixed(token, TokenStatistics) } }
pub fn restricted_sids(token: &token::OwnedHandle) -> Result<BoxTokenGroups, Error> { unsafe { Ok(BoxTokenGroups::from_raw(raw_bytes(token, TokenRestrictedSids)?)) } }
pub fn session_id(token: &token::OwnedHandle) -> Result<u32, Error> { unsafe { raw_fixed(token, TokenSessionId) } }
pub fn groups_and_privileges(token: &token::OwnedHandle) -> Result<BoxTokenGroupsAndPrivileges, Error> { unsafe { Ok(BoxTokenGroupsAndPrivileges::from_raw(raw_bytes(token, TokenGroupsAndPrivileges)?)) } }
pub fn sandbox_inert(token: &token::OwnedHandle) -> Result<bool, Error> { unsafe { raw_bool(token, TokenSandBoxInert) } }
pub fn origin(token: &token::OwnedHandle) -> Result<TOKEN_ORIGIN, Error> { unsafe { raw_fixed(token, TokenOrigin) } }
pub fn elevation_type(token: &token::OwnedHandle) -> Result<token::ElevationType, Error> { unsafe { raw_fixed(token, TokenElevationType) } }
pub fn linked_token(token: &token::OwnedHandle) -> Result<TOKEN_LINKED_TOKEN, Error> { unsafe { raw_fixed(token, TokenLinkedToken) } }
pub fn elevation(token: &token::OwnedHandle) -> Result<token::Elevation, Error> { unsafe { raw_fixed(token, TokenElevation) } }
pub fn is_elevated(token: &token::OwnedHandle) -> Result<bool, Error> { elevation(token).map(|e| !!e.token_is_elevated) }
pub fn has_restrictions(token: &token::OwnedHandle) -> Result<bool, Error> { unsafe { raw_bool(token, TokenHasRestrictions) } }
pub fn access_information(token: &token::OwnedHandle) -> Result<impl Deref<Target=TOKEN_ACCESS_INFORMATION>, Error> { unsafe { raw_header(token, TokenAccessInformation) } }
pub fn virtualization_allowed(token: &token::OwnedHandle) -> Result<bool, Error> { unsafe { raw_bool(token, TokenVirtualizationAllowed) } }
pub fn virtualization_enabled(token: &token::OwnedHandle) -> Result<bool, Error> { unsafe { raw_bool(token, TokenVirtualizationEnabled) } }
pub fn integrity_level(token: &token::OwnedHandle) -> Result<BoxTokenMandatoryLabel, Error> { unsafe { Ok(BoxTokenMandatoryLabel::from_raw(raw_bytes(token, TokenIntegrityLevel)?)) } }
pub fn ui_access(token: &token::OwnedHandle) -> Result<bool, Error> { unsafe { raw_bool(token, TokenUIAccess) } }
pub fn mandatory_policy(token: &token::OwnedHandle) -> Result<token::MandatoryPolicy, Error> { unsafe { raw_fixed(token, TokenMandatoryPolicy) } }
pub fn logon_sid(token: &token::OwnedHandle) -> Result<BoxTokenGroups, Error> { unsafe { Ok(BoxTokenGroups::from_raw(raw_bytes(token, TokenLogonSid)?)) } }
pub fn is_app_container(token: &token::OwnedHandle) -> Result<bool, Error> { unsafe { raw_bool(token, TokenIsAppContainer) } }
pub fn capabilities(token: &token::OwnedHandle) -> Result<BoxTokenGroups, Error> { unsafe { Ok(BoxTokenGroups::from_raw(raw_bytes(token, TokenCapabilities)?)) } }
pub fn app_container_sid(token: &token::OwnedHandle) -> Result<BoxTokenAppcontainerInformation, Error> { unsafe { Ok(BoxTokenAppcontainerInformation::from_raw(raw_bytes(token, TokenAppContainerSid)?)) } }
pub fn app_container_number(token: &token::OwnedHandle) -> Result<u32, Error> { unsafe { raw_fixed(token, TokenAppContainerNumber) } }
pub fn user_claim_attributes(token: &token::OwnedHandle) -> Result<impl Deref<Target=CLAIM_SECURITY_ATTRIBUTES_INFORMATION>, Error> { unsafe { raw_header(token, TokenUserClaimAttributes) } }
pub fn device_claim_attributes(token: &token::OwnedHandle) -> Result<impl Deref<Target=CLAIM_SECURITY_ATTRIBUTES_INFORMATION>, Error> { unsafe { raw_header(token, TokenDeviceClaimAttributes) } }
pub fn device_groups(token: &token::OwnedHandle) -> Result<BoxTokenGroups, Error> { unsafe { Ok(BoxTokenGroups::from_raw(raw_bytes(token, TokenDeviceGroups)?)) } }
pub fn restricted_device_groups(token: &token::OwnedHandle) -> Result<BoxTokenGroups, Error> {
unsafe { Ok(BoxTokenGroups::from_raw(raw_bytes(token, TokenRestrictedDeviceGroups)?)) }
}
impl token::OwnedHandle {
pub fn user(&self) -> Result<BoxTokenUser, Error> { user(self) }
pub fn groups(&self) -> Result<BoxTokenGroups, Error> { groups(self) }
pub fn privileges(&self) -> Result<BoxTokenPrivileges, Error> { privileges(self) }
pub fn owner(&self) -> Result<BoxTokenOwner, Error> { owner(self) }
pub fn primary_group(&self) -> Result<BoxTokenPrimaryGroup, Error> { primary_group(self) }
pub fn default_dacl(&self) -> Result<BoxTokenDefaultDacl, Error> { default_dacl(self) }
pub fn source(&self) -> Result<Source, Error> { source(self) }
pub fn r#type(&self) -> Result<token::Type, Error> { r#type(self) }
pub fn ty(&self) -> Result<token::Type, Error> { ty(self) }
pub fn impersonation_level(&self) -> Result<security::ImpersonationLevel, Error> { impersonation_level(self) }
pub fn statistics(&self) -> Result<TOKEN_STATISTICS, Error> { statistics(self) }
pub fn restricted_sids(&self) -> Result<BoxTokenGroups, Error> { restricted_sids(self) }
pub fn session_id(&self) -> Result<u32, Error> { session_id(self) }
pub fn groups_and_privileges(&self) -> Result<BoxTokenGroupsAndPrivileges, Error> { groups_and_privileges(self) }
pub fn sandbox_inert(&self) -> Result<bool, Error> { sandbox_inert(self) }
pub fn origin(&self) -> Result<TOKEN_ORIGIN, Error> { origin(self) }
pub fn elevation_type(&self) -> Result<token::ElevationType, Error> { elevation_type(self) }
pub fn linked_token(&self) -> Result<TOKEN_LINKED_TOKEN, Error> { linked_token(self) }
pub fn elevation(&self) -> Result<token::Elevation, Error> { elevation(self) }
pub fn is_elevated(&self) -> Result<bool, Error> { is_elevated(self) }
pub fn has_restrictions(&self) -> Result<bool, Error> { has_restrictions(self) }
pub fn access_information(&self) -> Result<impl Deref<Target=TOKEN_ACCESS_INFORMATION>, Error> { access_information(self) }
pub fn virtualization_allowed(&self) -> Result<bool, Error> { virtualization_allowed(self) }
pub fn virtualization_enabled(&self) -> Result<bool, Error> { virtualization_enabled(self) }
pub fn integrity_level(&self) -> Result<BoxTokenMandatoryLabel, Error> { integrity_level(self) }
pub fn ui_access(&self) -> Result<bool, Error> { ui_access(self) }
pub fn mandatory_policy(&self) -> Result<token::MandatoryPolicy, Error> { mandatory_policy(self) }
pub fn logon_sid(&self) -> Result<BoxTokenGroups, Error> { logon_sid(self) }
pub fn is_app_container(&self) -> Result<bool, Error> { is_app_container(self) }
pub fn capabilities(&self) -> Result<BoxTokenGroups, Error> { capabilities(self) }
pub fn app_container_sid(&self) -> Result<BoxTokenAppcontainerInformation, Error> { app_container_sid(self) }
pub fn app_container_number(&self) -> Result<u32, Error> { app_container_number(self) }
pub fn user_claim_attributes(&self) -> Result<impl Deref<Target=CLAIM_SECURITY_ATTRIBUTES_INFORMATION>, Error> { user_claim_attributes(self) }
pub fn device_claim_attributes(&self) -> Result<impl Deref<Target=CLAIM_SECURITY_ATTRIBUTES_INFORMATION>, Error> { device_claim_attributes(self) }
pub fn device_groups(&self) -> Result<BoxTokenGroups, Error> { device_groups(self) }
pub fn restricted_device_groups(&self) -> Result<BoxTokenGroups, Error> { restricted_device_groups(self) }
}
unsafe fn raw_len(token: &token::OwnedHandle, class: TOKEN_INFORMATION_CLASS) -> Result<u32, Error> {
let mut size = 0;
Error::get_last_if(0 == unsafe { GetTokenInformation(token.as_handle(), class, null_mut(), 0, &mut size) }).unerr(ERROR_INSUFFICIENT_BUFFER, ())?;
Ok(size)
}
unsafe fn raw_bytes<T: Default>(token: &token::OwnedHandle, class: TOKEN_INFORMATION_CLASS) -> Result<CBoxSized<T>, Error> {
let mut size = 0;
let r_size = unsafe { raw_len(token, class)? };
let mut result = CBoxSized::<T>::new_oversized(T::default(), usize::from32(r_size));
Error::get_last_if(0 == unsafe { GetTokenInformation(token.as_handle(), class, result.as_mut_ptr().cast(), r_size, &mut size) })?;
if size != r_size { return Err(Error(ERROR_INCORRECT_SIZE)) }
Ok(result)
}
unsafe fn raw_fixed<R: Copy + Default>(token: &token::OwnedHandle, class: TOKEN_INFORMATION_CLASS) -> Result<R, Error> {
let mut size = 0;
let mut r = R::default();
let r_size = u32::try_from(core::mem::size_of_val(&r)).map_err(|_| Error(ERROR_INSUFFICIENT_BUFFER))?;
Error::get_last_if(0 == unsafe { GetTokenInformation(token.as_handle(), class, &mut r as *mut _ as *mut _, r_size, &mut size) })?;
if size != r_size { return Err(Error(ERROR_INCORRECT_SIZE)) }
Ok(r)
}
unsafe fn raw_bool(token: &token::OwnedHandle, class: TOKEN_INFORMATION_CLASS) -> Result<bool, Error> {
let mut size = 0;
let mut result = 0u32;
Error::get_last_if(0 == unsafe { GetTokenInformation(token.as_handle(), class, &mut result as *mut _ as *mut _, 4, &mut size) })?;
Ok(result != 0)
}
unsafe fn raw_header<H: Copy + Default>(token: &token::OwnedHandle, class: TOKEN_INFORMATION_CLASS) -> Result<impl Deref<Target = H>, Error> {
let cbs = unsafe { raw_bytes::<H>(token, class)? };
Ok(CBox::from(cbs))
}