size_of/
human_bytes.rs

1use crate::{Context, SizeOf};
2use core::fmt::{self, Display};
3
4/// Friendlier formatting for byte values
5#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash, Default)]
6#[repr(transparent)]
7pub struct HumanBytes {
8    /// The inner bytes
9    pub bytes: u64,
10}
11
12impl HumanBytes {
13    /// Create a new `HumanBytes`
14    #[inline]
15    pub const fn new(bytes: u64) -> Self {
16        Self { bytes }
17    }
18
19    /// Fetch the inner bytes of the `HumanBytes`
20    #[inline]
21    pub const fn into_inner(self) -> u64 {
22        self.bytes
23    }
24}
25
26impl From<u64> for HumanBytes {
27    #[inline]
28    fn from(bytes: u64) -> Self {
29        Self { bytes }
30    }
31}
32
33impl From<u32> for HumanBytes {
34    #[inline]
35    fn from(bytes: u32) -> Self {
36        Self {
37            bytes: bytes as u64,
38        }
39    }
40}
41
42impl From<usize> for HumanBytes {
43    #[inline]
44    fn from(bytes: usize) -> Self {
45        Self {
46            bytes: bytes as u64,
47        }
48    }
49}
50
51const KB: f64 = 1024.0;
52const MB: f64 = KB * KB;
53const GB: f64 = KB * KB * KB;
54const TB: f64 = KB * KB * KB * KB;
55const PB: f64 = KB * KB * KB * KB * KB;
56const EB: f64 = KB * KB * KB * KB * KB * KB;
57// const ZB: u64 = KB * KB * KB * KB * KB * KB * KB;
58// const YB: u64 = KB * KB * KB * KB * KB * KB * KB * KB;
59
60impl Display for HumanBytes {
61    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
62        let bytes = self.bytes as f64;
63
64        if bytes / EB > 1.0 {
65            write!(f, "{:.02} EiB", bytes / EB)
66        } else if bytes / PB > 1.0 {
67            write!(f, "{:.02} PiB", bytes / PB)
68        } else if bytes / TB > 1.0 {
69            write!(f, "{:.02} TiB", bytes / TB)
70        } else if bytes / GB > 1.0 {
71            write!(f, "{:.02} GiB", bytes / GB)
72        } else if bytes / MB > 1.0 {
73            write!(f, "{:.02} MiB", bytes / MB)
74        } else if bytes / KB > 1.0 {
75            write!(f, "{:.02} KiB", bytes / KB)
76        } else {
77            write!(f, "{} B", self.bytes)
78        }
79    }
80}
81
82impl SizeOf for HumanBytes {
83    fn size_of_children(&self, _context: &mut Context) {}
84}