libnotcurses_sys/metric.rs
1//! `NcMetric`
2
3pub(crate) mod reimplemented {
4 use crate::{c_api::ffi, cstring, rstring, NcError, NcResult};
5
6 use core::ffi::c_ulong;
7
8 #[cfg(not(feature = "std"))]
9 use alloc::format;
10
11 // TODO: clarify, update and visibilize doc-comments
12
13 /// Takes an arbitrarily large number, and prints it into a fixed-size buffer by
14 /// adding the necessary SI suffix.
15 ///
16 /// Usually, pass a `|NC[IB]PREFIXSTRLEN+1|-sized` buffer to generate up to
17 /// `|NC[IB]PREFIXCOLUMNS|` columns' worth of EGCs. The characteristic can
18 /// occupy up through `|mult-1|` characters (3 for 1000, 4 for 1024).
19 /// The mantissa can occupy either zero or two characters.
20 ///
21 /// snprintf(3) is used internally, with `s` as its size bound. If the output
22 /// requires more size than is available, an error will be returned.
23 ///
24 /// Floating-point is never used, because an IEEE758 double can only losslessly
25 /// represent integers through 2^53-1.
26 ///
27 /// 2^64-1 is 18446744073709551615, 18.45E(xa). KMGTPEZY thus suffice to handle
28 /// an 89-bit uintmax_t. Beyond Z(etta) and Y(otta) lie lands unspecified by SI.
29 /// 2^-63 is 0.000000000000000000108, 1.08a(tto).
30 ///
31 /// val: value to print
32 /// s: maximum output size.
33 /// decimal: scaling. '1' if none has taken place.
34 /// buf: buffer in which string will be generated
35 /// omitdec: inhibit printing of all-0 decimal portions
36 /// mult: base of suffix system (almost always 1000 or 1024)
37 /// uprefix: character to print following suffix ('i' for kibibytes basically).
38 /// only printed if suffix is actually printed (input >= mult).
39 ///
40 /// You are encouraged to consult notcurses_metric(3).
41 ///
42 // FIXME, remove buf, return String, check mem leaks.
43 pub fn ncmetric(
44 val: c_ulong,
45 s: usize,
46 decimal: c_ulong,
47 buf: &str,
48 omitdec: i32,
49 mult: c_ulong,
50 uprefix: i32,
51 ) -> NcResult<&str> {
52 let cbuf = cstring![buf];
53 let res =
54 unsafe { ffi::ncnmetric(val, s, decimal, cbuf.into_raw(), omitdec, mult, uprefix) };
55
56 if res.is_null() {
57 Err(NcError::new_msg(&format![
58 "ncmetric({}, {}, {:?}, {}, {}, {})",
59 val, s, decimal, omitdec, mult, uprefix
60 ]))
61 } else {
62 Ok(rstring![res])
63 }
64 }
65}
66
67pub(crate) mod c_api {
68 use crate::c_api::ffi;
69
70 // The number of columns is one fewer, as the STRLEN expressions must leave
71 // an extra byte open in case 'ยต' (U+00B5, 0xC2 0xB5) shows up.
72
73 // This is the true number of columns;
74 //
75 // to set up a printf()-style maximum field width,
76 // you should use [IB]PREFIXFMT (see below).
77 pub const NCMETRIC_PREFIXCOLUMNS: u32 = ffi::NCPREFIXCOLUMNS;
78
79 // The maximum number of columns used by a mult == 1000 (standard)
80 // ncmetric() call.
81 pub const NCMETRIC_BPREFIXCOLUMNS: u32 = ffi::NCBPREFIXCOLUMNS;
82
83 // IPREFIXCOLUMNS is the maximum number of columns used by a mult == 1024
84 // (digital information) ncmetric().
85 pub const NCMETRIC_IPREFIXCOLUMNS: u32 = ffi::NCIPREFIXCOLUMNS;
86
87 //
88 // Does not include a '\0' (xxx.xxU)
89 pub const NCMETRIC_PREFIXSTRLEN: u32 = ffi::NCPREFIXSTRLEN;
90
91 // The maximum number of columns used by a mult == 1024 call making use of
92 // the 'i' suffix.
93 // Does not include a '\0' (xxxx.xxUi), i == prefix
94 pub const NCMETRIC_BPREFIXSTRLEN: u32 = ffi::NCBPREFIXSTRLEN;
95
96 // Does not include a '\0' (xxxx.xxU)
97 pub const NCMETRIC_IPREFIXSTRLEN: u32 = ffi::NCIPREFIXSTRLEN;
98}