pciutils 0.1.1

A clone of pciutils in Rust
Documentation
use crate::error::{Error, Result};
use std::str::FromStr;

#[derive(Debug, Clone)]
pub struct VendorDeviceClass {
    pub vendor: Option<u16>,
    pub device: Option<u16>,
    pub class: Option<u16>,
}

impl VendorDeviceClass {
    pub const FORMAT: &str = "[<vendor>]:[<device>][:<class>]";
    fn from_str(s: &str) -> Result<Self> {
        let mut parts: Vec<_> = s.split(':').collect();

        if parts.len() < 2 || parts.len() > 3 {
            return Err(Error::invalid_vdc(s));
        }

        let mut class = None;
        if parts.len() == 3 {
            if let Some(part) = parts.pop() {
                if !part.is_empty() {
                    class = Some(u16::from_str_radix(part, 16).map_err(|_| Error::invalid_bdf(s))?);
                }
            }
        }

        let mut device = None;
        if let Some(part) = parts.pop() {
            if !part.is_empty() {
                device = Some(u16::from_str_radix(part, 16).map_err(|_| Error::invalid_bdf(s))?);
            }
        }

        let mut vendor = None;
        if let Some(part) = parts.pop() {
            if !part.is_empty() {
                vendor = Some(u16::from_str_radix(part, 16).map_err(|_| Error::invalid_bdf(s))?);
            }
        }

        Ok(VendorDeviceClass {
            vendor,
            device,
            class,
        })
    }
}

impl FromStr for VendorDeviceClass {
    type Err = std::io::Error;

    fn from_str(s: &str) -> std::result::Result<Self, Self::Err> {
        Self::from_str(s).map_err(std::io::Error::from)
    }
}

impl PartialEq for VendorDeviceClass {
    fn eq(&self, other: &Self) -> bool {
        (self.vendor.is_none()
            || other.vendor.is_none()
            || self.vendor.unwrap() == other.vendor.unwrap())
            && (self.device.is_none()
                || other.device.is_none()
                || self.device.unwrap() == other.device.unwrap())
            && (self.class.is_none()
                || other.class.is_none()
                || self.class.unwrap() == other.class.unwrap())
    }
}