Skip to content

Commit

Permalink
Add: notus support for windows (#1626)
Browse files Browse the repository at this point in the history
  • Loading branch information
jjnicola authored Apr 26, 2024
1 parent b0e5cad commit 0917d57
Show file tree
Hide file tree
Showing 5 changed files with 177 additions and 1 deletion.
2 changes: 2 additions & 0 deletions rust/models/src/product.rs
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,8 @@ pub enum PackageType {
RPM,
#[cfg_attr(feature = "serde_support", serde(rename = "slack"))]
SLACK,
#[cfg_attr(feature = "serde_support", serde(rename = "msp"))]
MSP,
}

/// Representing a single Vulnerability Test entry
Expand Down
1 change: 1 addition & 0 deletions rust/notus/src/notus.rs
Original file line number Diff line number Diff line change
Expand Up @@ -170,6 +170,7 @@ where
Product::EBuild(adv) => Self::parse_and_compare(packages, adv)?,
Product::Rpm(adv) => Self::parse_and_compare(packages, adv)?,
Product::Slack(adv) => Self::parse_and_compare(packages, adv)?,
Product::Windows(adv) => Self::parse_and_compare(packages, adv)?,
};

Ok(results)
Expand Down
1 change: 1 addition & 0 deletions rust/notus/src/packages/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ pub mod deb;
pub mod ebuild;
pub mod rpm;
pub mod slack;
pub mod windows;

use lazy_regex::{lazy_regex, Lazy, Regex};
use std::cmp::{max, Ordering};
Expand Down
167 changes: 167 additions & 0 deletions rust/notus/src/packages/windows.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,167 @@
// SPDX-FileCopyrightText: 2023 Greenbone AG
//
// SPDX-License-Identifier: GPL-2.0-or-later WITH x11vnc-openssl-exception

use super::{Package, PackageVersion};
use std::cmp::Ordering;

/// Represent a based Windows package
#[derive(Debug, PartialEq, Clone)]
pub struct Windows {
full_name: String,
build: String,
revision: PackageVersion,
}

impl PartialOrd for Windows {
fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
if self.build != other.build {
return None;
}

if self.full_name == other.full_name {
return Some(Ordering::Equal);
}

self.revision.partial_cmp(&other.revision)
}
}

impl Package for Windows {
fn from_full_name(full_name: &str) -> Option<Self> {
if full_name.is_empty() {
return None;
}
let full_name = full_name.trim();

// Get all fields
let (build, revision) = match full_name.rsplit_once('.') {
Some((b, r)) => (b, r),
None => {
return None;
}
};
Some(Windows {
full_name: full_name.to_string(),
build: build.to_string(),
revision: PackageVersion(revision.to_string()),
})
}

fn from_name_and_full_version(name: &str, full_version: &str) -> Option<Self> {
if name.is_empty() || full_version.is_empty() {
return None;
}

let name = name.trim();
let revision = full_version.trim();

// Get all fields
let mut full_name = name.to_string();
full_name.push('.');
full_name.push_str(full_version);

Some(Windows {
full_name,
build: name.to_string(),
revision: PackageVersion(revision.to_string()),
})
}

fn get_name(&self) -> String {
self.build.clone()
}

fn get_version(&self) -> String {
self.revision.0.clone()
}
}

#[cfg(test)]
mod slack_tests {
use super::Package;
use super::Windows;
use crate::packages::PackageVersion;

#[test]
pub fn test_compare_gt() {
let package1 = Windows {
build: "10.0.22631".to_string(),
full_name: "10.0.22631.3447".to_string(),
revision: PackageVersion("3447".to_string()),
};
let package2 = Windows {
build: "10.0.22631".to_string(),
full_name: "10.0.22631.3449".to_string(),
revision: PackageVersion("3449".to_string()),
};
assert!(package2 > package1);
}

#[test]
pub fn test_compare_gt_different_name() {
let package1 = Windows {
build: "11.0.22631".to_string(),
full_name: "10.0.22631.3447".to_string(),
revision: PackageVersion("3447".to_string()),
};
let package2 = Windows {
build: "10.0.22631".to_string(),
full_name: "10.0.22631.3449".to_string(),
revision: PackageVersion("3449".to_string()),
};

assert!(package2.partial_cmp(&package1).is_none());
assert!(package1.partial_cmp(&package2).is_none());
}

#[test]
pub fn test_compare_less() {
let package1 = Windows {
build: "10.0.22631".to_string(),
full_name: "10.0.22631.3447".to_string(),
revision: PackageVersion("3447".to_string()),
};
let package2 = Windows {
build: "10.0.22631".to_string(),
full_name: "10.0.22631.3449".to_string(),
revision: PackageVersion("3449".to_string()),
};
assert!(package1 < package2);
}

#[test]
pub fn test_compare_equal() {
let package1 = Windows {
build: "10.0.22631".to_string(),
full_name: "10.0.22631.3447".to_string(),
revision: PackageVersion("3447".to_string()),
};
let package2 = Windows {
build: "10.0.22631".to_string(),
full_name: "10.0.22631.3447".to_string(),
revision: PackageVersion("3447".to_string()),
};
assert!(package1 == package2);
}

#[test]
pub fn test_from_full_name() {
assert!(Windows::from_full_name("").is_none());

let package = Windows::from_full_name("10.0.22631.3447").unwrap();
assert_eq!(package.build, "10.0.22631");
assert_eq!(package.full_name, "10.0.22631.3447");
assert_eq!(package.revision, PackageVersion("3447".to_string()));
}

#[test]
pub fn test_from_name_and_full_version() {
assert!(Windows::from_name_and_full_version("", "").is_none());

let package = Windows::from_name_and_full_version("10.0.22631", "3447").unwrap();
assert_eq!(package.build, "10.0.22631");
assert_eq!(package.full_name, "10.0.22631.3447");
assert_eq!(package.revision, PackageVersion("3447".to_string()));
}
}
7 changes: 6 additions & 1 deletion rust/notus/src/vts.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ use models::{FixedPackage, FixedVersion, Specifier};

use crate::{
error::Error,
packages::{deb::Deb, ebuild::EBuild, rpm::Rpm, slack::Slack, Package},
packages::{deb::Deb, ebuild::EBuild, rpm::Rpm, slack::Slack, windows::Windows, Package},
};

/// VulnerabilityTests is a collection of Tests to detect vulnerabilities, in case of notus these
Expand All @@ -23,6 +23,7 @@ pub enum Product {
EBuild(VulnerabilityTests<EBuild>),
Rpm(VulnerabilityTests<Rpm>),
Slack(VulnerabilityTests<Slack>),
Windows(VulnerabilityTests<Windows>),
}

impl Product {
Expand Down Expand Up @@ -83,6 +84,10 @@ impl TryFrom<models::Product> for Product {
let vts = Self::transform(value.vulnerability_tests)?;
Ok(Self::Slack(vts))
}
models::PackageType::MSP => {
let vts = Self::transform(value.vulnerability_tests)?;
Ok(Self::Windows(vts))
}
}
}

Expand Down

0 comments on commit 0917d57

Please sign in to comment.