Giter Club home page Giter Club logo

sysctl-rs's Introduction

This crate provides a safe interface for reading and writing information to the kernel using the sysctl interface.

Build Status

Current Version

FreeBSD, Linux, macOS and iOS are supported. Contributions for improvements and other platforms are welcome.

Documentation

Documentation is available on docs.rs

Usage

Add to Cargo.toml

[dependencies]
sysctl = "*"

macOS/iOS

  • Due to limitations in the sysctl(3) API, many of the methods of the Ctl take a mutable reference to self on macOS/iOS.
  • Sysctl descriptions are not available on macOS/iOS and Linux.
  • Some tests failures are ignored, as the respective sysctls do not exist on macos.

Example

sysctl comes with several examples, see the examples folder:

  • value.rs: shows how to get a sysctl value
  • value_as.rs: parsing values as structures
  • value_string.rs: parsing values as string. Use this for cross platform compatibility since all sysctls are strings on Linux.
  • value_oid_as.rs: getting a sysctl from OID constants from the libc crate.
  • set_value.rs: shows how to set a sysctl value
  • struct.rs: reading data into a struct
  • temperature.rs: parsing temperatures
  • iterate.rs: showcases iteration over the sysctl tree

Run with:

$ cargo run --example iterate

Or to use in your program:

extern crate sysctl;
use sysctl::Sysctl;

fn main() {
    let ctl = sysctl::Ctl::new("kern.osrevision").unwrap();
    println!("Description: {}", ctl.description().unwrap());
    println!("Value: {}", ctl.value_string().unwrap());
}

sysctl-rs's People

Contributors

35359595 avatar asomers avatar fabianfreyer avatar johalun avatar jvimal-eg avatar luozijun avatar mordak avatar nicklarsennz avatar phyber avatar stephanvanschaik avatar vv9k avatar ydirson avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar

sysctl-rs's Issues

Short reads

the issue

Some sysctls, e.g. vfs.bufspace on FreeBSD, exaggerate their length, i.e. they report being a Long, but read returns only 4 bytes:

info = CtlInfo { ctl_type: Long, fmt: "L\u{0}", flags: 2147745799 }

Attempting to read these will cause a panic, as we are calling LittleEndian::read_u64 on a Vec with less than 8 bytes length.

thread 'main' panicked at 'assertion failed: 8 <= buf.len()', [redacted]/.cargo/registry/src/github.com-1ecc6299db9ec823/byteorder-1.2.3/src/lib.rs:2024:9

expected behaviour

On short reads, the value should be zero-padded to the size of the target value.

steps to reproduce

The following program will panic on FreeBSD

extern crate sysctl;

fn main() {
    let value = sysctl::value("vfs.bufspace");
    println!("vfs.bufspace: {:?}", value);
}

Thoughts on sysctls that take arguments?

e.g. from the sysctl manpage:

         int i, mib[4];
           size_t len;
           struct kinfo_proc kp;

           /* Fill out the first three components of the mib */
           len = 4;
           sysctlnametomib("kern.proc.pid", mib, &len);

           /* Fetch and print entries for pid's < 100 */
           for (i = 0; i < 100; i++) {
                   mib[3] = i;
                   len = sizeof(kp);
                   if (sysctl(mib, 4, &kp, &len, NULL, 0) == -1)
                           perror("sysctl");
                   else if (len > 0)
                           printkproc(&kp);
           }

Question about list of longs

Hi,

First of all, thanks for this library. I'm very new to Rust so this might be a stupid question. I'm trying to read the "kern.cp_time" and "kern.cp_times" Ctl's on FreeBSD. This should be a list of long integers (user, nice, sys, intr, idle). sysctl-rs says it's a Long type value and the value I get is just one i64 value but sysctl kern.cp_time gives me the list of all 5 numbers. Could you point me the way on how to read all 5?

Thanks, Rudolph

bitflags crate is using deprecated try macro

Compile warning on Linux. Look into if we need a newer version of bitflags.

warning: use of deprecated macro `try`: use the `?` operator instead
  --> src/ctl_flags.rs:6:1
   |
6  | / bitflags! {
7  | |     pub struct CtlFlags : libc::c_uint {
8  | |         /// Allow reads of variable
9  | |         const RD = CTLFLAG_RD;
...  |
69 | |     }
70 | | }
   | |_^
   |
   = note: `#[warn(deprecated)]` on by default
   = note: this warning originates in the macro `__impl_bitflags` (in Nightly builds, run with -Z macro-backtrace for more info)

fails to build on openbsd

using the Cargo.toml and example code from the README on openbsd i get the following:

% cargo run
   Compiling sysctl v0.5.4
error[E0433]: failed to resolve: maybe a missing crate `sys`?
  --> /home/MYUSER/.cargo/registry/src/index.crates.io-6f17d22bba15001f/sysctl-0.5.4/src/lib.rs:77:9
   |
77 | pub use sys::ctl::*;
   |         ^^^ maybe a missing crate `sys`?
   |
   = help: consider adding `extern crate sys` to use the `sys` crate

error[E0433]: failed to resolve: maybe a missing crate `sys`?
  --> /home/MYUSER/.cargo/registry/src/index.crates.io-6f17d22bba15001f/sysctl-0.5.4/src/lib.rs:78:9
   |
78 | pub use sys::ctl_iter::*;
   |         ^^^ maybe a missing crate `sys`?
   |
   = help: consider adding `extern crate sys` to use the `sys` crate

error[E0432]: unresolved imports `sys::ctl::*`, `sys::ctl_iter::*`
  --> /home/MYUSER/.cargo/registry/src/index.crates.io-6f17d22bba15001f/sysctl-0.5.4/src/lib.rs:77:9
   |
77 | pub use sys::ctl::*;
   |         ^^^^^^^^^^^
78 | pub use sys::ctl_iter::*;
   |         ^^^^^^^^^^^^^^^^

Some errors have detailed explanations: E0432, E0433.
For more information about an error, try `rustc --explain E0432`.
error: could not compile `sysctl` (lib) due to 3 previous errors

adding target_os = "openbsd" to the lib where freebsd is ends up in a whole other errors and fails too.

docstest failure on FreeBSD

On FreeBSD, the doctest for temperature handling is failing. I've tried to bisect this, but it seems to go back to the initial commit.

$ cargo test --doc
    Updating registry `https://github.com/rust-lang/crates.io-index`
   Compiling sysctl v0.1.4 (file:///root/sysctl-rs)
    Finished dev [unoptimized + debuginfo] target(s) in 1.49s
   Doc-tests sysctl

running 10 tests
test src/lib.rs - CtlValue (line 205) ... ignored
test src/lib.rs - Temperature (line 271) ... FAILED
test src/lib.rs - description (line 961) ... ok
test src/lib.rs -  (line 6) ... ok
test src/lib.rs -  (line 33) ... ok
test src/lib.rs - set_value (line 862) ... ok
test src/lib.rs - value (line 503) ... ok
test src/lib.rs - value_as (line 697) ... ok
test src/lib.rs - value_oid (line 531) ... ok
test src/lib.rs - value_oid_as (line 740) ... ok

failures:

failures:
    src/lib.rs - Temperature (line 271)

test result: FAILED. 8 passed

Wrong type on macOS

The sysctl security.mac.asp.active_rule_version returns wrong type (integer instead of long unsigned) which is causing tests to fail when the value wraps over to negative value.

sysctl -d security.mac.asp.active_rule_version reports LU as type. Maybe use descriptions as source for types instead of current method?

Cirrus doesn't support OSX Mojave and High Sierra

On the Mojave and High Sierra tests, Cirrus says "Auto-upgraded from mojave-base to catalina-base". I guess that means there's no point to testing on those older releases. Should we just test on Catalina alone?

Capsicum support

FreeBSD's Capsicum facility is used to sandbox processes into a capability mode. Unable to access any global namespaces, their ability to harm the overall system is very limited. It's a terrific security feature. But the sysctl(3) functions do access global namespaces. So to use them in capability mode requires a helper: the Casper library. Once a process is in capability mode, it can use the cap_sysctl(3) facility to access sysctls. I originally attempted to implement cap_sysctl in a separate crate, but encountered difficulties. Basically, it's just way too complicated. Dealing with sysctls, as you know, requires lots of code to handle all the different data types. So instead of having a separate cap-sysctl-rs crate, I propose moving that functionality into here. If you agree, this is what I think we should do:

  1. Add libcasper(3) bindings to libc, or create a separate libcasper-sys crate. I'll raise the issue with the libc team and see which they prefer.
  2. Implement basic libcasper support within the capsicum-rs crate. I've already got a branch for this.
  3. Add a private SysctlProvider trait to this crate with three methods: sysctlbyname, sysctl, and sysctlnametomib. Existing functions like unix::funcs::value_oid will gain a new argument, a &dyn SysctlProvider.
  4. Create two implementors of this trait: NativeSysctlProvider and CasperSysctlProvider. The former will simply wrap the existing sysctl(3) functions. The latter will wrap cap_sysctl(3), and will also include methods to initialize the casper connection and configure limits.
  5. Create a public CasperSysctl struct and implement the Sysctl trait for it. In order to preserve the existing API, the actual casper connection will have to be a global variable.
  6. Optionally, gate all of this Casper stuff behind a feature flag. However, since Casper is only implemented on FreeBSD and all official FreeBSD releases have it, I don't think we need to add a feature flag .

What do you think? cc @dlrobertson .

missing docs and docstests on macos

It seems like it's necessary to repeat the rustdoc comments before the #[cfg(target_os = "macos")] macros.

The following will not generate any rustdoc documentation for foo on macos, and the docstest will not execute:

/// such docs, meny wow, amaze
///
/// # Example
/// ```
/// foo();
/// ```
#[cfg(not(target_os="macos"))]
fn foo() {
    println!("bar");
}

#[cfg(target_os="macos")]
fn foo() {
    println!("baz");
}

Struct interface

What's your opinion on providing a struct interface, maybe along the following lines:

extern crate sysctl;

fn main() {
    let kernversion: sysctl::Ctl = sysctl::Ctl::from_str("kern.osrevision");
    println!("Description: {:?}", kernversion.description());
    println!("Value: {:?}", kernversion.value());
    // etc...
}

This would set up the possibility of creating iterators over Ctls, e.g. for iterating through all children of a node.

I understand this would be a breaking API change, so it would probably require a major SemVer bump.

I would start drafting a PR for this.

Extracting CtlInfo / fmt

I'd like to be able to access CtlInfo.fmt in some way and was wondering what would be the nicest way to expose it:

  • publish struct CtlInfo and add a Ctl.info() method and add some methods to it (see #19)
  • Add a Ctl.fmt() method to return the format string
    @johalun maybe you have some other ideas?

doc fails on set_value

Because you need root access to do this. Hmm, can we tell cargo to ignore running this test?

`value_oid_as` is unsound

Transmuting bytes to an arbitrary type can cause undefined behavior.

The safety requirements:

  1. T must be Sized.
  2. The length of bytes must be equal to size_of::<T>().
  3. The alignment of bytes must be equal to align_of::<T>().
  4. T must be valid for any binary representation.

sysctl-rs/src/unix/funcs.rs

Lines 367 to 369 in 57c05e1

let val_array: Box<[u8]> = val.into_boxed_slice();
let val_raw: *mut T = Box::into_raw(val_array) as *mut T;
let val_box: Box<T> = unsafe { Box::from_raw(val_raw) };

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.