selinux-sys-0.5.1/.cargo_vcs_info.json0000644000000001120000000000100133340ustar { "git": { "sha1": "3492c33d0e1fa6adabde43049e031d87d65d1618" } } selinux-sys-0.5.1/.gitignore000064400000000000000000000000700072674642500141470ustar 00000000000000/target Cargo.lock *.code-workspace .directory *.tar.gz selinux-sys-0.5.1/CHANGELOG.md000064400000000000000000000024750072674642500140030ustar 00000000000000# Change log This project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). ## [0.5.1] - 2021-08-01 ### Changed - Stopped using `std::slice::strip_prefix()`, in order to reduce the minimum supported Rust version for this crate. ## [0.5.0] - 2021-07-28 ### Changed - Update dependencies: `bindgen`. ### Removed - Removed all fixed C integer types, such as `__uint8_t`, `__uint32_t`, etc. **This is a breaking change.** ## [0.4.2] - 2021-06-01 ### Added - Implemented `Eq` and `Ord` for generated structures. ## [0.4.1] - 2021-05-09 ### Added - Exposed the `getseuser()` API. ## [0.4.0] - 2021-05-04 ### Changed - Instead of using the `pkg-config` crate, we now detect compilers and flags mostly based on the `cc` crate. This allows cross-compilation. - Updated documentation. ## [0.3.1] - 2021-04-17 ### Changed - Updated documentation. ## [0.3.0] - 2021-04-17 ### Changed - Building for the following platforms is now supported, but it results in an empty crate: - Non-Linux systems. - The Linux kernel. ## [0.2.1] - 2021-04-17 ### Changed - Update dependencies: `bindgen`. ## [0.2.0] - 2021-03-17 ### Fixed - Make sure `DEP_SELINUX_INCLUDE` and `DEP_SELINUX_LIB` point to directories. They previously pointed to files. ## [0.1.0] - 2021-03-06 ### Added - Initial release. selinux-sys-0.5.1/Cargo.toml0000644000000061170000000000100113450ustar # THIS FILE IS AUTOMATICALLY GENERATED BY CARGO # # When uploading crates to the registry Cargo will automatically # "normalize" Cargo.toml files for maximal compatibility # with all versions of Cargo and also rewrite `path` dependencies # to registry (e.g., crates.io) dependencies # # If you believe there's an error in this file please file an # issue against the rust-lang/cargo repository. If you're # editing this file be aware that the upstream Cargo.toml # will likely look very different (and much more reasonable) [package] edition = "2018" name = "selinux-sys" version = "0.5.1" authors = ["Koutheir Attouchi "] build = "build.rs" links = "selinux" description = "Flexible Mandatory Access Control (MAC) for Linux" documentation = "https://docs.rs/selinux-sys" readme = "README.md" keywords = ["selinux", "security", "access-control", "linux", "filesystem"] categories = ["external-ffi-bindings", "filesystem", "os", "os::linux-apis"] license = "MIT" repository = "https://github.com/koutheir/selinux-sys" [package.metadata.docs.rs] default-target = "x86_64-unknown-linux-gnu" targets = ["aarch64-linux-android", "aarch64-unknown-linux-gnu", "aarch64-unknown-linux-gnu_ilp32", "aarch64-unknown-linux-musl", "aarch64_be-unknown-linux-gnu", "aarch64_be-unknown-linux-gnu_ilp32", "arm-linux-androideabi", "arm-unknown-linux-gnueabi", "arm-unknown-linux-gnueabihf", "arm-unknown-linux-musleabi", "arm-unknown-linux-musleabihf", "armv4t-unknown-linux-gnueabi", "armv5te-unknown-linux-gnueabi", "armv5te-unknown-linux-musleabi", "armv5te-unknown-linux-uclibceabi", "armv7-linux-androideabi", "armv7-unknown-linux-gnueabi", "armv7-unknown-linux-gnueabihf", "armv7-unknown-linux-musleabi", "armv7-unknown-linux-musleabihf", "hexagon-unknown-linux-musl", "i586-unknown-linux-gnu", "i586-unknown-linux-musl", "i686-linux-android", "i686-unknown-linux-gnu", "i686-unknown-linux-musl", "mips-unknown-linux-gnu", "mips-unknown-linux-musl", "mips-unknown-linux-uclibc", "mips64-unknown-linux-gnuabi64", "mips64-unknown-linux-muslabi64", "mips64el-unknown-linux-gnuabi64", "mips64el-unknown-linux-muslabi64", "mipsel-unknown-linux-gnu", "mipsel-unknown-linux-musl", "mipsel-unknown-linux-uclibc", "mipsisa32r6-unknown-linux-gnu", "mipsisa32r6el-unknown-linux-gnu", "mipsisa64r6-unknown-linux-gnuabi64", "mipsisa64r6el-unknown-linux-gnuabi64", "powerpc-unknown-linux-gnu", "powerpc-unknown-linux-gnuspe", "powerpc-unknown-linux-musl", "powerpc64-unknown-linux-gnu", "powerpc64-unknown-linux-musl", "powerpc64le-unknown-linux-gnu", "powerpc64le-unknown-linux-musl", "riscv32gc-unknown-linux-gnu", "riscv64gc-unknown-linux-gnu", "s390x-unknown-linux-gnu", "sparc-unknown-linux-gnu", "sparc64-unknown-linux-gnu", "thumbv7neon-linux-androideabi", "thumbv7neon-unknown-linux-gnueabihf", "thumbv7neon-unknown-linux-musleabihf", "x86_64-linux-android", "x86_64-unknown-linux-gnu", "x86_64-unknown-linux-gnux32", "x86_64-unknown-linux-musl"] [build-dependencies.bindgen] version = "0.59" [build-dependencies.cc] version = "1.0" [build-dependencies.dunce] version = "1.0" [build-dependencies.walkdir] version = "2.3" [features] static = [] selinux-sys-0.5.1/Cargo.toml.orig000064400000000000000000000057420072674642500150610ustar 00000000000000[package] name = "selinux-sys" description = "Flexible Mandatory Access Control (MAC) for Linux" version = "0.5.1" # Remember to update `html_root_url`. authors = ["Koutheir Attouchi "] edition = "2018" readme = "README.md" license = "MIT" keywords = [ "selinux", "security", "access-control", "linux", "filesystem" ] categories = [ "external-ffi-bindings", "filesystem", "os", "os::linux-apis" ] build = "build.rs" links = "selinux" repository = "https://github.com/koutheir/selinux-sys" documentation = "https://docs.rs/selinux-sys" [build-dependencies] bindgen = { version = "0.59" } walkdir = { version = "2.3" } dunce = { version = "1.0" } cc = { version = "1.0" } [features] static = [] [package.metadata.docs.rs] default-target = "x86_64-unknown-linux-gnu" # Supported target are all user-land Linux platforms. # # Building on musl-based systems requires: # ``` # env RUSTFLAGS=-Ctarget-feature=-crt-static cargo test # ``` targets = [ "aarch64-linux-android", "aarch64-unknown-linux-gnu", "aarch64-unknown-linux-gnu_ilp32", "aarch64-unknown-linux-musl", "aarch64_be-unknown-linux-gnu", "aarch64_be-unknown-linux-gnu_ilp32", "arm-linux-androideabi", "arm-unknown-linux-gnueabi", "arm-unknown-linux-gnueabihf", "arm-unknown-linux-musleabi", "arm-unknown-linux-musleabihf", "armv4t-unknown-linux-gnueabi", "armv5te-unknown-linux-gnueabi", "armv5te-unknown-linux-musleabi", "armv5te-unknown-linux-uclibceabi", "armv7-linux-androideabi", "armv7-unknown-linux-gnueabi", "armv7-unknown-linux-gnueabihf", "armv7-unknown-linux-musleabi", "armv7-unknown-linux-musleabihf", "hexagon-unknown-linux-musl", "i586-unknown-linux-gnu", "i586-unknown-linux-musl", "i686-linux-android", "i686-unknown-linux-gnu", "i686-unknown-linux-musl", "mips-unknown-linux-gnu", "mips-unknown-linux-musl", "mips-unknown-linux-uclibc", "mips64-unknown-linux-gnuabi64", "mips64-unknown-linux-muslabi64", "mips64el-unknown-linux-gnuabi64", "mips64el-unknown-linux-muslabi64", "mipsel-unknown-linux-gnu", "mipsel-unknown-linux-musl", "mipsel-unknown-linux-uclibc", "mipsisa32r6-unknown-linux-gnu", "mipsisa32r6el-unknown-linux-gnu", "mipsisa64r6-unknown-linux-gnuabi64", "mipsisa64r6el-unknown-linux-gnuabi64", "powerpc-unknown-linux-gnu", "powerpc-unknown-linux-gnuspe", "powerpc-unknown-linux-musl", "powerpc64-unknown-linux-gnu", "powerpc64-unknown-linux-musl", "powerpc64le-unknown-linux-gnu", "powerpc64le-unknown-linux-musl", "riscv32gc-unknown-linux-gnu", "riscv64gc-unknown-linux-gnu", "s390x-unknown-linux-gnu", "sparc-unknown-linux-gnu", "sparc64-unknown-linux-gnu", "thumbv7neon-linux-androideabi", "thumbv7neon-unknown-linux-gnueabihf", "thumbv7neon-unknown-linux-musleabihf", "x86_64-linux-android", "x86_64-unknown-linux-gnu", "x86_64-unknown-linux-gnux32", "x86_64-unknown-linux-musl", ] selinux-sys-0.5.1/LICENSE.txt000064400000000000000000000021100072674642500137770ustar 00000000000000MIT License Copyright (c) 2021 Koutheir Attouchi. Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. selinux-sys-0.5.1/README.md000064400000000000000000000053230072674642500134440ustar 00000000000000[![crates.io](https://img.shields.io/crates/v/selinux-sys.svg)](https://crates.io/crates/selinux-sys) [![docs.rs](https://docs.rs/selinux-sys/badge.svg)](https://docs.rs/selinux-sys) [![license](https://img.shields.io/github/license/koutheir/selinux-sys?color=black)](https://raw.githubusercontent.com/koutheir/selinux-sys/master/LICENSE.txt) # `selinux-sys`: Unsafe Rust bindings for `libselinux` SELinux is a flexible Mandatory Access Control (MAC) for Linux. This crate exposes neither *deprecated* nor *undocumented* SELinux API functions and types. This crate is Linux-specific. Building it for non-Linux platforms, or for the Linux kernel, results in an empty crate. ## Supported environment variables This crate depends on some environment variables, and *variants* of those. For each environment variable (e.g., `CC`), the following are the accepted variants of it: - `_`, e.g., `CC_aarch64-unknown-linux-gnu`. - `_`, e.g., `CC_aarch64_unknown_linux_gnu`. - `TARGET_`, e.g., `TARGET_CC`. - ``, e.g., `CC`. The following environment variables (and their variants) affect how this crate is built: - `SELINUX_STATIC` - `SELINUX_PATH` - `SELINUX_INCLUDE_DIR` - `SELINUX_LIB_DIR` - `CC` - `CFLAGS` ## Dynamic or static linking This crate links to `libselinux` dynamically if possible, except when targeting platforms based on the `musl` C library. This behavior can be changed either by setting the environment variable `SELINUX_STATIC` to `1`, or by enabling the crate feature `static`. If both are defined, then the value of `SELINUX_STATIC` takes precedence. Setting `SELINUX_STATIC` to `0` mandates dynamic linking. ## Finding SELinux library and headers By default, this crate finds SELinux headers and library based on the default target C compiler. This behavior can be changed by: - Either defining the environment variable `SELINUX_PATH` to the path of a directory containing the sub-directories `include` and `lib` where the headers and library are installed. - Or by defining one or both of the environment variables `SELINUX_INCLUDE_DIR` and `SELINUX_LIB_DIR` to paths to the directories where headers and library are present. If `SELINUX_PATH` is also defined, then `SELINUX_INCLUDE_DIR` and `SELINUX_LIB_DIR` take precedence. ## Depending on this crate This crate provides the following variables to other crates that depend on it: - `DEP_SELINUX_INCLUDE`: Path of the directory where library C header files reside. - `DEP_SELINUX_LIB`: Path of the directory where the library binary resides. ## Versioning This project adheres to [Semantic Versioning]. The `CHANGELOG.md` file details notable changes over time. [Semantic Versioning]: https://semver.org/spec/v2.0.0.html selinux-sys-0.5.1/build.rs000064400000000000000000000304470072674642500136370ustar 00000000000000use std::ffi::OsString; use std::path::{Path, PathBuf}; use std::{env, io, process, str}; use walkdir::WalkDir; fn main() { let target = env::var("TARGET").expect("selinux-sys: Environment variable 'TARGET' was not defined"); let out_dir = env::var_os("OUT_DIR") .map(PathBuf::from) .expect("selinux-sys: Environment variable 'OUT_DIR' was not defined"); println!("cargo:root={}", path_to_str(&out_dir)); if !target.contains("-linux-") || target.ends_with("-kernel") { return; // Nothing to build for this architecture. } let explicit_static = get_static_linking(&target); let compiler_search_paths = get_compiler_search_paths(&target); let include_path = find_and_output_include_dir(&compiler_search_paths.include_paths); find_and_output_lib_dir(&compiler_search_paths.link_paths, &target, explicit_static); generate_bindings(&out_dir, &include_path) } fn path_to_str(path: &Path) -> &str { path.to_str().expect("selinux-sys: Path is not valid UTF-8") } #[cfg(feature = "static")] fn get_static_linking(target: &str) -> Option { target_env_var_os("SELINUX_STATIC", target) .map(|v| v == "1" || v == "true") .or_else(|| Some(true)) } #[cfg(not(feature = "static"))] fn get_static_linking(target: &str) -> Option { target_env_var_os("SELINUX_STATIC", target).map(|v| v == "1" || v == "true") } fn get_compiler_search_paths(target: &str) -> CompilerSearchPaths { let explicit_path = target_env_var_os("SELINUX_PATH", target).map(PathBuf::from); let mut include_dir = target_env_var_os("SELINUX_INCLUDE_DIR", target).map(PathBuf::from); let mut link_dir = target_env_var_os("SELINUX_LIB_DIR", target).map(PathBuf::from); for &name in &["CC", "CFLAGS"] { target_env_var_os(name, target); } if let Some(explicit_path) = explicit_path { if include_dir.is_none() { include_dir = Some(explicit_path.join("include")); } if link_dir.is_none() { link_dir = Some(explicit_path.join("lib")); } } CompilerSearchPaths::new(include_dir, link_dir) } #[derive(Debug)] struct CompilerSearchPaths { include_paths: Vec, link_paths: Vec, } impl CompilerSearchPaths { fn new(include_dir: Option, link_dir: Option) -> Self { env::set_var("LANG", "C"); let include_paths = if let Some(include_dir) = include_dir { vec![include_dir] } else { Self::get_compiler_include_paths() .expect("selinux-sys: Failed to discover default compiler search paths") }; let link_paths = if let Some(link_dir) = link_dir { vec![link_dir] } else { Self::get_compiler_link_paths() .expect("selinux-sys: Failed to discover default linker search paths") }; CompilerSearchPaths { include_paths, link_paths, } } fn get_compiler_include_paths() -> io::Result> { let compiler = cc::Build::new() .flag("-E") .flag("-v") .flag("-x") .flag("c") .get_compiler(); let child = compiler .to_command() .arg("-") .stdin(process::Stdio::null()) .stdout(process::Stdio::null()) .stderr(process::Stdio::piped()) .env("LANG", "C") .spawn()?; let output = child.wait_with_output()?; if !output.status.success() { return Err(io::Error::new( io::ErrorKind::Other, "Compiler failed to print search directories", )); } let mut paths: Vec = output .stderr .split(|&b| b == b'\n') .skip_while(|&line| line != b"#include <...> search starts here:") .take_while(|&line| line != b"End of search list.") .filter_map(|bytes| str::from_utf8(bytes).ok()) .map(str::trim) .filter_map(|s| dunce::canonicalize(s).ok()) .collect(); paths.dedup(); Ok(paths) } fn get_compiler_link_paths() -> io::Result> { let compiler = cc::Build::new() .flag("-v") .flag("-print-search-dirs") .get_compiler(); let child = compiler .to_command() .stdout(process::Stdio::piped()) .stderr(process::Stdio::null()) .env("LANG", "C") .spawn()?; let output = child.wait_with_output()?; if !output.status.success() { return Err(io::Error::new( io::ErrorKind::Other, "Compiler failed to print search directories", )); } let line = output .stdout .split(|&b| b == b'\n') .find_map(|line| strip_bytes_prefix(line, b"libraries:")) .and_then(|bytes| str::from_utf8(bytes).ok()) .map(str::trim) .map(|line| line.trim_start_matches('=')) .ok_or_else(|| { io::Error::new( io::ErrorKind::Other, "Compiler search directories format is unrecognized", ) })?; let mut paths = Vec::::with_capacity(8); if let Some(lib_paths) = env::var_os("LIBRARY_PATH") { paths.extend(env::split_paths(&lib_paths).filter_map(|s| dunce::canonicalize(s).ok())); } paths.extend(env::split_paths(line).filter_map(|s| dunce::canonicalize(s).ok())); paths.dedup(); Ok(paths) } } fn target_env_var_os(name: &str, target: &str) -> Option { rerun_if_env_changed(name, target); let target_underscores = target.replace('-', "_"); env::var_os(format!("{}_{}", name, target)) .or_else(|| env::var_os(format!("{}_{}", name, target_underscores))) .or_else(|| env::var_os(format!("TARGET_{}", name))) .or_else(|| env::var_os(name.to_string())) } fn rerun_if_env_changed(name: &str, target: &str) { let target_underscores = target.replace('-', "_"); println!("cargo:rerun-if-env-changed={}_{}", name, target); println!("cargo:rerun-if-env-changed={}_{}", name, target_underscores); println!("cargo:rerun-if-env-changed=TARGET_{}", name); println!("cargo:rerun-if-env-changed={}", name); } fn rerun_if_dir_changed(dir: &Path) { for file in WalkDir::new(dir).follow_links(false).same_file_system(true) { if let Ok(file) = file { println!("cargo:rerun-if-changed={}", file.path().display()); } else { panic!( "selinux-sys: Failed to list directory contents: {}", dir.display() ); } } } fn find_and_output_include_dir(include_paths: &[PathBuf]) -> PathBuf { let include_path = find_file_in_dirs("selinux/selinux.h", include_paths) .expect("selinux-sys: Failed to find 'selinux/selinux.h'"); rerun_if_dir_changed(&include_path.join("selinux")); println!("cargo:include={}", path_to_str(&include_path)); include_path } fn output_lib_dir(dir: &Path, file: &Path, static_lib: bool) { println!("cargo:rerun-if-changed={}", file.display()); println!("cargo:lib={}", path_to_str(dir)); println!("cargo:rustc-link-search=native={}", path_to_str(dir)); println!( "cargo:rustc-link-lib={}=selinux", if static_lib { "static" } else { "dylib" } ); } fn find_and_output_lib_dir(link_paths: &[PathBuf], target: &str, explicit_static: Option) { let lib_configs = match explicit_static { Some(false) => vec![false], Some(true) => vec![true], None => { if target.contains("-musl") { vec![true, false] } else { vec![false, true] } } }; for static_lib in lib_configs { let file_name = format!("libselinux{}", if static_lib { ".a" } else { ".so" }); if let Ok(lib_path) = find_file_in_dirs(&file_name, link_paths) { output_lib_dir(&lib_path, &lib_path.join(&file_name), static_lib); return; } if let Some(link_path) = link_paths.get(0) { let triplet = target.replace("-unknown-", "-").replace("-none-", "-"); for &lib_dir in &[ link_path, &link_path.join(&target), &link_path.join(&triplet), ] { let lib_path = lib_dir.join(&file_name); if let Ok(md) = lib_path.metadata() { if md.is_file() { output_lib_dir(lib_dir, &lib_path, static_lib); return; } } } } } } fn generate_bindings(out_dir: &Path, include_path: &Path) { let mut builder = bindgen::Builder::default() .rustfmt_bindings(true) .default_enum_style(bindgen::EnumVariation::ModuleConsts) .default_macro_constant_type(bindgen::MacroTypeVariation::Signed) .size_t_is_usize(true) .derive_debug(true) .derive_copy(true) .derive_eq(true) .derive_ord(true) .impl_debug(true); // Do not expose deprecated functions. for &blacklisted_function in &[ "(avc_init|security_load_booleans|checkPasswdAccess|rpm_execcon)", "selinux_(booleans_path|users_path|check_passwd_access)", "security_compute_user(_raw)?", "sid(get|put)", "matchpathcon(_init|_init_prefix|_fini|_index)?", ] { builder = builder.blocklist_function(blacklisted_function); } // Do not expose deprecated types. for &type_re in &["security_context_t", "^__u?int[0-9]+_t$"] { builder = builder.blocklist_type(type_re); } // Expose documented functions. for &function in &[ "(f|l)?(g|s)et(file|exec|fscreate|keycreate|sockcreate|peer|pid|prev)?con(_raw)?", "freecon(ary)?", "(set_)?match(path|media)con(_.+)?", "(is_)?(security|selabel|selinux|avc|context)_.+", "(init|fini|set)_selinuxmnt", "get_(default|ordered)_(context|type).*", "(string|mode)_to_(security_class|av_perm)", "getseuser(byname)?", "manual_user_enter_context", "print_access_vector", "query_user_context", ] { builder = builder.allowlist_function(function); } // Expose documented types and constants. builder = builder .allowlist_type("(security|selinux|access|av|avc|SEL)_.+") .allowlist_var("(SELINUX|SELABEL|MATCHPATHCON|SECSID|AVC)_.+"); // Include all SELinux headers. builder = builder.header("src/selinux-sys.h"); // Define macros to include headers that actually exist. for &optional_header in &["restorecon.h", "get_context_list.h", "get_default_type.h"] { let path = include_path.join("selinux").join(optional_header); if let Ok(md) = path.metadata() { if md.file_type().is_file() { let mut def = format!("SELINUX_SYS_{}", optional_header.replace('.', "_")); def.make_ascii_uppercase(); builder = builder.clang_args(&["-D", &def]); } } } let bindings = builder.generate().expect( "selinux-sys: Failed to generate Rust bindings for 'selinux/selinux.h' and other headers", ); bindings .write_to_file(out_dir.join("selinux-sys.rs")) .expect("selinux-sys: Failed to write 'selinux-sys.rs'") } fn find_file_in_dirs(path_suffix: &str, dirs: &[PathBuf]) -> io::Result { for dir in dirs { if let Ok(md) = dir.join(path_suffix).metadata() { if md.file_type().is_file() { return Ok(dir.clone()); } } } Err(io::ErrorKind::NotFound.into()) } // This is used instead of `std::slice::strip_prefix()`, in order to reduce the // minimum supported Rust version for this crate. // This should be removed once we can assume at least Rust version 1.51.0. #[must_use] fn strip_bytes_prefix<'a, 'b>(slice: &'a [u8], prefix: &'b [u8]) -> Option<&'a [u8]> { let prefix_len = prefix.len(); if prefix_len <= slice.len() { let (head, tail) = slice.split_at(prefix_len); if head == prefix { return Some(tail); } } None } selinux-sys-0.5.1/src/lib.rs000064400000000000000000000061420072674642500140700ustar 00000000000000#![cfg(all(target_os = "linux", not(target_env = "kernel")))] #![doc(html_root_url = "https://docs.rs/selinux-sys/0.5.1")] #![allow(non_upper_case_globals, non_camel_case_types, non_snake_case)] #![allow(clippy::redundant_static_lifetimes, clippy::upper_case_acronyms)] /*! # `selinux-sys`: Unsafe Rust bindings for `libselinux` SELinux is a flexible Mandatory Access Control (MAC) for Linux. This crate exposes neither *deprecated* nor *undocumented* SELinux API functions and types. This crate is Linux-specific. Building it for non-Linux platforms, or for the Linux kernel, results in an empty crate. ## Supported environment variables This crate depends on some environment variables, and *variants* of those. For each environment variable (e.g., `CC`), the following are the accepted variants of it: - `_`, e.g., `CC_aarch64-unknown-linux-gnu`. - `_`, e.g., `CC_aarch64_unknown_linux_gnu`. - `TARGET_`, e.g., `TARGET_CC`. - ``, e.g., `CC`. The following environment variables (and their variants) affect how this crate is built: - `SELINUX_STATIC` - `SELINUX_PATH` - `SELINUX_INCLUDE_DIR` - `SELINUX_LIB_DIR` - `CC` - `CFLAGS` ## Dynamic or static linking This crate links to `libselinux` dynamically if possible, except when targeting platforms based on the `musl` C library. This behavior can be changed either by setting the environment variable `SELINUX_STATIC` to `1`, or by enabling the crate feature `static`. If both are defined, then the value of `SELINUX_STATIC` takes precedence. Setting `SELINUX_STATIC` to `0` mandates dynamic linking. ## Finding SELinux library and headers By default, this crate finds SELinux headers and library based on the default target C compiler. This behavior can be changed by: - Either defining the environment variable `SELINUX_PATH` to the path of a directory containing the sub-directories `include` and `lib` where the headers and library are installed. - Or by defining one or both of the environment variables `SELINUX_INCLUDE_DIR` and `SELINUX_LIB_DIR` to paths to the directories where headers and library are present. If `SELINUX_PATH` is also defined, then `SELINUX_INCLUDE_DIR` and `SELINUX_LIB_DIR` take precedence. ## Depending on this crate This crate provides the following variables to other crates that depend on it: - `DEP_SELINUX_INCLUDE`: Path of the directory where library C header files reside. - `DEP_SELINUX_LIB`: Path of the directory where the library binary resides. ## Versioning This project adheres to [Semantic Versioning]. The `CHANGELOG.md` file details notable changes over time. [Semantic Versioning]: https://semver.org/spec/v2.0.0.html */ include!(concat!(env!("OUT_DIR"), "/selinux-sys.rs")); /// Unspecified SID. pub const SECSID_WILD: security_id_t = std::ptr::null_mut(); /// Initialize an `avc_entry_ref` structure. /// /// # Safety /// `aeref` is assumed to be a valid pointer to a mutable `avc_entry_ref` structure. pub unsafe fn avc_entry_ref_init(aeref: *mut avc_entry_ref) { if let Some(aeref) = aeref.as_mut() { aeref.ae = std::ptr::null_mut(); } } #[cfg(test)] mod tests; selinux-sys-0.5.1/src/selinux-sys.h000064400000000000000000000006760072674642500154360ustar 00000000000000#include #include #include #include #ifdef SELINUX_SYS_RESTORECON_H #include #endif // SELINUX_SYS_RESTORECON_H #ifdef SELINUX_SYS_GET_CONTEXT_LIST_H #include #endif // SELINUX_SYS_GET_CONTEXT_LIST_H #ifdef SELINUX_SYS_GET_DEFAULT_TYPE_H #include #endif // SELINUX_SYS_GET_DEFAULT_TYPE_H selinux-sys-0.5.1/src/tests.rs000064400000000000000000000007060072674642500144640ustar 00000000000000#![cfg(all(test, target_os = "linux", not(target_env = "kernel")))] use std::os::raw::c_char; use std::ptr; #[test] fn is_selinux_enabled() { let r = unsafe { super::is_selinux_enabled() }; assert!(r == 0 || r == 1); } #[test] fn getcon() { let mut context: *mut c_char = ptr::null_mut(); let r = unsafe { super::getcon(&mut context) }; assert_ne!(r, -1); assert!(!context.is_null()); unsafe { super::freecon(context) } }