116 lines
2.8 KiB
Rust
116 lines
2.8 KiB
Rust
use std::collections::HashSet;
|
|
|
|
use lazy_static::lazy_static;
|
|
use rpm_rs::rpm::{
|
|
get_installed_packages,
|
|
Package,
|
|
};
|
|
use rpm_rs::rpmio::rpmvercmp;
|
|
use updateinfo_xmlparser::{UpdateInfoDb, RpmInfo};
|
|
|
|
use crate::cli::Cli;
|
|
use crate::analyzer::db::PackgeDb;
|
|
|
|
lazy_static! {
|
|
pub static ref update_pkgs: PackgeDb= {
|
|
let mut updatedb = UpdateInfoDb::new();
|
|
updatedb.load_xml("test/updateinfo.xml").unwrap();
|
|
|
|
let mut pkgdb = PackgeDb::new();
|
|
pkgdb.load_from_updateinfodb(&updatedb);
|
|
pkgdb
|
|
};
|
|
}
|
|
|
|
pub mod db;
|
|
|
|
pub fn cuvat_run(cli: &Cli) -> crate::Result<()> {
|
|
// 只报告 cve 相关
|
|
if cli.cves {
|
|
return list_cves(cli)
|
|
}
|
|
|
|
// 只报告 sa 相关
|
|
if cli.sas {
|
|
return list_sas(cli)
|
|
}
|
|
|
|
// 生成报告
|
|
if cli.report {
|
|
return repoter(cli)
|
|
}
|
|
|
|
// 默认报告格式
|
|
summary(cli)
|
|
}
|
|
|
|
fn list_cves(cli: &Cli) -> crate::Result<()> {
|
|
Ok(())
|
|
}
|
|
|
|
fn list_sas(cli: &Cli) -> crate::Result<()> {
|
|
Ok(())
|
|
}
|
|
|
|
fn repoter(cli: &Cli) -> crate::Result<()> {
|
|
Ok(())
|
|
}
|
|
|
|
fn summary(cli: &Cli) -> crate::Result<()> {
|
|
let mut sa_ids: HashSet<String> = HashSet::new();
|
|
// 当前系统所有已安装的 rpm 包
|
|
let installed = get_installed_packages();
|
|
// installed 已被消费掉
|
|
// latest_installed 是所有最新版本软件包的 Vec
|
|
let latest_installed: Vec<Package> = installed.into_iter().map(|(_, pkgs)| {
|
|
let mut latest = pkgs[0].clone();
|
|
for pkg in pkgs.into_iter() {
|
|
latest = rpmdb_package_vercmp(latest, pkg);
|
|
}
|
|
latest
|
|
}).collect();
|
|
|
|
// 获取 sa 更新列表
|
|
for pkg in latest_installed {
|
|
let name = pkg.name();
|
|
if let Some(updates) = update_pkgs.db().get(name) {
|
|
for update in updates {
|
|
// epoch 判断
|
|
match (update.epoch(), pkg.epoch()) {
|
|
(Some(_), None) => {
|
|
let _ = sa_ids.insert(update.sa().into());
|
|
},
|
|
(None, Some(_)) => continue,
|
|
_ => {}
|
|
}
|
|
|
|
// evr 对比
|
|
if rpmvercmp(&update.evr(), &pkg.evr()) > 0 {
|
|
sa_ids.insert(update.sa().into());
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
println!("{:#?}", sa_ids.len());
|
|
// TODO: sa -> { rpms, cves }
|
|
|
|
Ok(())
|
|
}
|
|
|
|
// 对比两个 rpm Package 的版本,返回最新的一个
|
|
fn rpmdb_package_vercmp(pa: Package, pb: Package) -> Package {
|
|
// 首先进行 epoch 的比较
|
|
match (pa.epoch(), pb.epoch()) {
|
|
(Some(_), None) => return pa,
|
|
(None, Some(_)) => return pb,
|
|
_ => {}, // 继续往下对比
|
|
}
|
|
|
|
if rpmvercmp(&pa.evr(), &pb.evr()) > 0 {
|
|
return pa
|
|
} else {
|
|
return pb
|
|
}
|
|
}
|