Fix all clippy lints and pass CI checks
- Box large enum variants in EventData to reduce memory footprint - Add Default trait implementations for types with new() methods - Replace or_insert_with(Vec::new) with or_default() - Convert vec init+push patterns to vec! macro - Fix field reassignment with default initialization - Convert match to if for simple equality checks - Remove unused Backend type parameters from TUI draw functions - Apply rustfmt formatting All tests passing (24 total). Zero clippy warnings. Ready for CI/CD.
This commit is contained in:
@@ -75,11 +75,11 @@ pub enum EventSeverity {
|
||||
|
||||
#[derive(Debug, Clone, Serialize, Deserialize)]
|
||||
pub enum EventData {
|
||||
Detection(DetectionEventData),
|
||||
ThreatIntel(ThreatIntelEventData),
|
||||
Detection(Box<DetectionEventData>),
|
||||
ThreatIntel(Box<ThreatIntelEventData>),
|
||||
Evasion(EvasionEventData),
|
||||
System(SystemEventData),
|
||||
Alert(AlertEventData),
|
||||
Alert(Box<AlertEventData>),
|
||||
Performance(PerformanceEventData),
|
||||
}
|
||||
|
||||
@@ -559,11 +559,11 @@ impl EventStreamingSystem {
|
||||
ThreatLevel::Suspicious => EventSeverity::Medium,
|
||||
ThreatLevel::Malicious => EventSeverity::High,
|
||||
},
|
||||
data: EventData::Detection(DetectionEventData {
|
||||
data: EventData::Detection(Box::new(DetectionEventData {
|
||||
detection_result: detection,
|
||||
analysis_duration: Duration::from_millis(100), // Would be actual duration
|
||||
confidence_threshold: 0.7,
|
||||
}),
|
||||
})),
|
||||
correlation_id: None,
|
||||
tags: vec!["process-injection".to_string(), "detection".to_string()],
|
||||
};
|
||||
|
||||
@@ -398,80 +398,78 @@ impl TestFramework {
|
||||
|
||||
/// Create detection engine unit tests
|
||||
fn create_detection_engine_tests(&mut self) {
|
||||
let mut test_cases = Vec::new();
|
||||
|
||||
// Test clean process detection
|
||||
test_cases.push(TestCase {
|
||||
name: "clean_process_detection".to_string(),
|
||||
description: "Verify clean processes are not flagged".to_string(),
|
||||
test_function: TestFunction::DetectionTest(DetectionTestParams {
|
||||
process_data: ProcessTestData {
|
||||
name: "notepad.exe".to_string(),
|
||||
pid: 1234,
|
||||
path: Some("C:\\Windows\\System32\\notepad.exe".to_string()),
|
||||
thread_count: 1,
|
||||
suspicious_indicators: Vec::new(),
|
||||
},
|
||||
memory_data: vec![MemoryTestData {
|
||||
base_address: 0x400000,
|
||||
size: 0x10000,
|
||||
protection: MemoryProtection::ReadExecute,
|
||||
contains_shellcode: false,
|
||||
shellcode_pattern: None,
|
||||
}],
|
||||
thread_data: vec![ThreadTestData {
|
||||
tid: 5678,
|
||||
entry_point: 0x401000,
|
||||
stack_base: 0x500000,
|
||||
stack_size: 0x10000,
|
||||
is_suspicious: false,
|
||||
}],
|
||||
injection_type: None,
|
||||
}),
|
||||
expected_result: ExpectedResult::ThreatLevel(ThreatLevel::Clean),
|
||||
timeout: Duration::from_secs(5),
|
||||
tags: vec!["unit".to_string(), "detection".to_string()],
|
||||
});
|
||||
|
||||
// Test malicious process detection
|
||||
test_cases.push(TestCase {
|
||||
name: "malicious_process_detection".to_string(),
|
||||
description: "Verify malicious processes are properly detected".to_string(),
|
||||
test_function: TestFunction::DetectionTest(DetectionTestParams {
|
||||
process_data: ProcessTestData {
|
||||
name: "malware.exe".to_string(),
|
||||
pid: 9999,
|
||||
path: Some("C:\\Temp\\malware.exe".to_string()),
|
||||
thread_count: 5,
|
||||
suspicious_indicators: vec![
|
||||
"High RWX memory usage".to_string(),
|
||||
"Suspicious API calls".to_string(),
|
||||
],
|
||||
},
|
||||
memory_data: vec![MemoryTestData {
|
||||
base_address: 0x200000,
|
||||
size: 0x1000,
|
||||
protection: MemoryProtection::ReadWriteExecute,
|
||||
contains_shellcode: true,
|
||||
shellcode_pattern: Some(vec![0x90, 0x90, 0xEB, 0xFE]), // NOP NOP JMP -2
|
||||
}],
|
||||
thread_data: vec![ThreadTestData {
|
||||
tid: 1111,
|
||||
entry_point: 0x200000,
|
||||
stack_base: 0x600000,
|
||||
stack_size: 0x10000,
|
||||
is_suspicious: true,
|
||||
}],
|
||||
injection_type: Some(InjectionTestType::ShellcodeInjection),
|
||||
}),
|
||||
expected_result: ExpectedResult::ThreatLevel(ThreatLevel::Malicious),
|
||||
timeout: Duration::from_secs(10),
|
||||
tags: vec![
|
||||
"unit".to_string(),
|
||||
"detection".to_string(),
|
||||
"malware".to_string(),
|
||||
],
|
||||
});
|
||||
let test_cases = vec![
|
||||
TestCase {
|
||||
name: "clean_process_detection".to_string(),
|
||||
description: "Verify clean processes are not flagged".to_string(),
|
||||
test_function: TestFunction::DetectionTest(DetectionTestParams {
|
||||
process_data: ProcessTestData {
|
||||
name: "notepad.exe".to_string(),
|
||||
pid: 1234,
|
||||
path: Some("C:\\Windows\\System32\\notepad.exe".to_string()),
|
||||
thread_count: 1,
|
||||
suspicious_indicators: Vec::new(),
|
||||
},
|
||||
memory_data: vec![MemoryTestData {
|
||||
base_address: 0x400000,
|
||||
size: 0x10000,
|
||||
protection: MemoryProtection::ReadExecute,
|
||||
contains_shellcode: false,
|
||||
shellcode_pattern: None,
|
||||
}],
|
||||
thread_data: vec![ThreadTestData {
|
||||
tid: 5678,
|
||||
entry_point: 0x401000,
|
||||
stack_base: 0x500000,
|
||||
stack_size: 0x10000,
|
||||
is_suspicious: false,
|
||||
}],
|
||||
injection_type: None,
|
||||
}),
|
||||
expected_result: ExpectedResult::ThreatLevel(ThreatLevel::Clean),
|
||||
timeout: Duration::from_secs(5),
|
||||
tags: vec!["unit".to_string(), "detection".to_string()],
|
||||
},
|
||||
// Test malicious process detection
|
||||
TestCase {
|
||||
name: "malicious_process_detection".to_string(),
|
||||
description: "Verify malicious processes are properly detected".to_string(),
|
||||
test_function: TestFunction::DetectionTest(DetectionTestParams {
|
||||
process_data: ProcessTestData {
|
||||
name: "malware.exe".to_string(),
|
||||
pid: 9999,
|
||||
path: Some("C:\\Temp\\malware.exe".to_string()),
|
||||
thread_count: 5,
|
||||
suspicious_indicators: vec![
|
||||
"High RWX memory usage".to_string(),
|
||||
"Suspicious API calls".to_string(),
|
||||
],
|
||||
},
|
||||
memory_data: vec![MemoryTestData {
|
||||
base_address: 0x200000,
|
||||
size: 0x1000,
|
||||
protection: MemoryProtection::ReadWriteExecute,
|
||||
contains_shellcode: true,
|
||||
shellcode_pattern: Some(vec![0x90, 0x90, 0xEB, 0xFE]), // NOP NOP JMP -2
|
||||
}],
|
||||
thread_data: vec![ThreadTestData {
|
||||
tid: 1111,
|
||||
entry_point: 0x200000,
|
||||
stack_base: 0x600000,
|
||||
stack_size: 0x10000,
|
||||
is_suspicious: true,
|
||||
}],
|
||||
injection_type: Some(InjectionTestType::ShellcodeInjection),
|
||||
}),
|
||||
expected_result: ExpectedResult::ThreatLevel(ThreatLevel::Malicious),
|
||||
timeout: Duration::from_secs(10),
|
||||
tags: vec![
|
||||
"unit".to_string(),
|
||||
"detection".to_string(),
|
||||
"malware".to_string(),
|
||||
],
|
||||
},
|
||||
];
|
||||
|
||||
let test_suite = TestSuite {
|
||||
name: "detection_engine_tests".to_string(),
|
||||
@@ -487,10 +485,7 @@ impl TestFramework {
|
||||
|
||||
/// Create shellcode detection tests
|
||||
fn create_shellcode_detection_tests(&mut self) {
|
||||
let mut test_cases = Vec::new();
|
||||
|
||||
// Test common shellcode patterns
|
||||
test_cases.push(TestCase {
|
||||
let test_cases = vec![TestCase {
|
||||
name: "common_shellcode_patterns".to_string(),
|
||||
description: "Detect common shellcode patterns".to_string(),
|
||||
test_function: TestFunction::DetectionTest(DetectionTestParams {
|
||||
@@ -519,7 +514,7 @@ impl TestFramework {
|
||||
expected_result: ExpectedResult::IndicatorPresent("Shellcode detected".to_string()),
|
||||
timeout: Duration::from_secs(5),
|
||||
tags: vec!["unit".to_string(), "shellcode".to_string()],
|
||||
});
|
||||
}];
|
||||
|
||||
let test_suite = TestSuite {
|
||||
name: "shellcode_detection_tests".to_string(),
|
||||
@@ -535,9 +530,7 @@ impl TestFramework {
|
||||
|
||||
/// Create process hollowing detection tests
|
||||
fn create_process_hollowing_tests(&mut self) {
|
||||
let mut test_cases = Vec::new();
|
||||
|
||||
test_cases.push(TestCase {
|
||||
let test_cases = vec![TestCase {
|
||||
name: "process_hollowing_detection".to_string(),
|
||||
description: "Detect process hollowing techniques".to_string(),
|
||||
test_function: TestFunction::DetectionTest(DetectionTestParams {
|
||||
@@ -564,7 +557,7 @@ impl TestFramework {
|
||||
expected_result: ExpectedResult::IndicatorPresent("Process hollowing".to_string()),
|
||||
timeout: Duration::from_secs(10),
|
||||
tags: vec!["unit".to_string(), "hollowing".to_string()],
|
||||
});
|
||||
}];
|
||||
|
||||
let test_suite = TestSuite {
|
||||
name: "process_hollowing_tests".to_string(),
|
||||
@@ -580,9 +573,7 @@ impl TestFramework {
|
||||
|
||||
/// Create evasion detection tests
|
||||
fn create_evasion_detection_tests(&mut self) {
|
||||
let mut test_cases = Vec::new();
|
||||
|
||||
test_cases.push(TestCase {
|
||||
let test_cases = vec![TestCase {
|
||||
name: "anti_debug_detection".to_string(),
|
||||
description: "Detect anti-debugging techniques".to_string(),
|
||||
test_function: TestFunction::DetectionTest(DetectionTestParams {
|
||||
@@ -603,7 +594,7 @@ impl TestFramework {
|
||||
expected_result: ExpectedResult::IndicatorPresent("Evasion technique".to_string()),
|
||||
timeout: Duration::from_secs(15),
|
||||
tags: vec!["unit".to_string(), "evasion".to_string()],
|
||||
});
|
||||
}];
|
||||
|
||||
let test_suite = TestSuite {
|
||||
name: "evasion_detection_tests".to_string(),
|
||||
@@ -625,39 +616,38 @@ impl TestFramework {
|
||||
|
||||
/// Create performance benchmark tests
|
||||
fn create_performance_tests(&mut self) {
|
||||
let mut benchmarks = Vec::new();
|
||||
|
||||
benchmarks.push(Benchmark {
|
||||
name: "single_process_analysis".to_string(),
|
||||
description: "Benchmark single process analysis performance".to_string(),
|
||||
benchmark_function: BenchmarkFunction::ProcessAnalysis(ProcessAnalysisBenchmark {
|
||||
process_count: 1,
|
||||
complexity_level: ComplexityLevel::Moderate,
|
||||
}),
|
||||
warm_up_iterations: 10,
|
||||
measurement_iterations: 100,
|
||||
target_metrics: vec![
|
||||
PerformanceMetric::ExecutionTime,
|
||||
PerformanceMetric::MemoryUsage,
|
||||
PerformanceMetric::CPUUtilization,
|
||||
],
|
||||
});
|
||||
|
||||
benchmarks.push(Benchmark {
|
||||
name: "bulk_process_analysis".to_string(),
|
||||
description: "Benchmark bulk process analysis performance".to_string(),
|
||||
benchmark_function: BenchmarkFunction::ProcessAnalysis(ProcessAnalysisBenchmark {
|
||||
process_count: 100,
|
||||
complexity_level: ComplexityLevel::Simple,
|
||||
}),
|
||||
warm_up_iterations: 5,
|
||||
measurement_iterations: 20,
|
||||
target_metrics: vec![
|
||||
PerformanceMetric::ThroughputRate,
|
||||
PerformanceMetric::LatencyP95,
|
||||
PerformanceMetric::MemoryUsage,
|
||||
],
|
||||
});
|
||||
let benchmarks = vec![
|
||||
Benchmark {
|
||||
name: "single_process_analysis".to_string(),
|
||||
description: "Benchmark single process analysis performance".to_string(),
|
||||
benchmark_function: BenchmarkFunction::ProcessAnalysis(ProcessAnalysisBenchmark {
|
||||
process_count: 1,
|
||||
complexity_level: ComplexityLevel::Moderate,
|
||||
}),
|
||||
warm_up_iterations: 10,
|
||||
measurement_iterations: 100,
|
||||
target_metrics: vec![
|
||||
PerformanceMetric::ExecutionTime,
|
||||
PerformanceMetric::MemoryUsage,
|
||||
PerformanceMetric::CPUUtilization,
|
||||
],
|
||||
},
|
||||
Benchmark {
|
||||
name: "bulk_process_analysis".to_string(),
|
||||
description: "Benchmark bulk process analysis performance".to_string(),
|
||||
benchmark_function: BenchmarkFunction::ProcessAnalysis(ProcessAnalysisBenchmark {
|
||||
process_count: 100,
|
||||
complexity_level: ComplexityLevel::Simple,
|
||||
}),
|
||||
warm_up_iterations: 5,
|
||||
measurement_iterations: 20,
|
||||
target_metrics: vec![
|
||||
PerformanceMetric::ThroughputRate,
|
||||
PerformanceMetric::LatencyP95,
|
||||
PerformanceMetric::MemoryUsage,
|
||||
],
|
||||
},
|
||||
];
|
||||
|
||||
let benchmark_suite = BenchmarkSuite {
|
||||
name: "performance_benchmarks".to_string(),
|
||||
|
||||
@@ -296,6 +296,12 @@ pub struct CertificateInfo {
|
||||
pub valid_to: SystemTime,
|
||||
}
|
||||
|
||||
impl Default for ThreatIntelligence {
|
||||
fn default() -> Self {
|
||||
Self::new()
|
||||
}
|
||||
}
|
||||
|
||||
impl ThreatIntelligence {
|
||||
pub fn new() -> Self {
|
||||
Self {
|
||||
@@ -551,6 +557,12 @@ impl ThreatIntelligence {
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for IocDatabase {
|
||||
fn default() -> Self {
|
||||
Self::new()
|
||||
}
|
||||
}
|
||||
|
||||
impl IocDatabase {
|
||||
pub fn new() -> Self {
|
||||
Self {
|
||||
@@ -570,13 +582,13 @@ impl IocDatabase {
|
||||
IocType::FileHash => {
|
||||
self.hash_index
|
||||
.entry(ioc.value.clone())
|
||||
.or_insert_with(Vec::new)
|
||||
.or_default()
|
||||
.push(ioc.id.clone());
|
||||
}
|
||||
IocType::MemorySignature | IocType::BehaviorPattern => {
|
||||
self.pattern_index
|
||||
.entry(ioc.value.clone())
|
||||
.or_insert_with(Vec::new)
|
||||
.or_default()
|
||||
.push(ioc.id.clone());
|
||||
}
|
||||
_ => {}
|
||||
@@ -637,6 +649,12 @@ impl IocDatabase {
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for AttributionEngine {
|
||||
fn default() -> Self {
|
||||
Self::new()
|
||||
}
|
||||
}
|
||||
|
||||
impl AttributionEngine {
|
||||
pub fn new() -> Self {
|
||||
Self {
|
||||
@@ -725,6 +743,12 @@ impl AttributionEngine {
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for SimilarityCalculator {
|
||||
fn default() -> Self {
|
||||
Self::new()
|
||||
}
|
||||
}
|
||||
|
||||
impl SimilarityCalculator {
|
||||
pub fn new() -> Self {
|
||||
Self {
|
||||
@@ -735,6 +759,12 @@ impl SimilarityCalculator {
|
||||
}
|
||||
}
|
||||
|
||||
impl Default for ReputationCache {
|
||||
fn default() -> Self {
|
||||
Self::new()
|
||||
}
|
||||
}
|
||||
|
||||
impl ReputationCache {
|
||||
pub fn new() -> Self {
|
||||
Self {
|
||||
|
||||
@@ -139,8 +139,10 @@ mod tests {
|
||||
let config = DetectionConfig::default();
|
||||
assert!(config.validate().is_ok());
|
||||
|
||||
let mut invalid_config = DetectionConfig::default();
|
||||
invalid_config.confidence_threshold = 1.5; // Invalid
|
||||
let mut invalid_config = DetectionConfig {
|
||||
confidence_threshold: 1.5, // Invalid
|
||||
..Default::default()
|
||||
};
|
||||
assert!(invalid_config.validate().is_err());
|
||||
|
||||
invalid_config.confidence_threshold = -0.1; // Invalid
|
||||
@@ -165,8 +167,10 @@ mod tests {
|
||||
|
||||
#[test]
|
||||
fn test_engine_with_custom_config() {
|
||||
let mut config = DetectionConfig::default();
|
||||
config.hook_detection = false;
|
||||
let config = DetectionConfig {
|
||||
hook_detection: false,
|
||||
..Default::default()
|
||||
};
|
||||
|
||||
let mut engine =
|
||||
DetectionEngine::with_config(Some(config)).expect("Failed to create engine");
|
||||
|
||||
@@ -379,19 +379,16 @@ impl App {
|
||||
}
|
||||
|
||||
pub fn select_item(&mut self) {
|
||||
match self.current_tab {
|
||||
TabIndex::Processes => {
|
||||
if let Some(i) = self.processes_state.selected() {
|
||||
if let Some(process) = self.processes.get(i) {
|
||||
self.selected_process = Some(process.clone());
|
||||
self.add_log_message(format!(
|
||||
"Selected process: {} (PID: {})",
|
||||
process.name, process.pid
|
||||
));
|
||||
}
|
||||
if self.current_tab == TabIndex::Processes {
|
||||
if let Some(i) = self.processes_state.selected() {
|
||||
if let Some(process) = self.processes.get(i) {
|
||||
self.selected_process = Some(process.clone());
|
||||
self.add_log_message(format!(
|
||||
"Selected process: {} (PID: {})",
|
||||
process.name, process.pid
|
||||
));
|
||||
}
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -69,7 +69,7 @@ async fn run_app<B: Backend>(terminal: &mut Terminal<B>, app: Arc<Mutex<App>>) -
|
||||
// Draw the UI
|
||||
terminal.draw(|f| {
|
||||
if let Ok(app) = app.try_lock() {
|
||||
ui::draw::<CrosstermBackend<std::io::Stdout>>(f, &app);
|
||||
ui::draw(f, &app);
|
||||
}
|
||||
})?;
|
||||
|
||||
|
||||
@@ -32,7 +32,7 @@ mod colors {
|
||||
|
||||
use colors::*;
|
||||
|
||||
pub fn draw<B: Backend>(f: &mut Frame, app: &App) {
|
||||
pub fn draw(f: &mut Frame, app: &App) {
|
||||
let size = f.size();
|
||||
|
||||
// Create main layout
|
||||
@@ -46,23 +46,23 @@ pub fn draw<B: Backend>(f: &mut Frame, app: &App) {
|
||||
.split(size);
|
||||
|
||||
// Draw header
|
||||
draw_header::<B>(f, chunks[0], app);
|
||||
draw_header(f, chunks[0], app);
|
||||
|
||||
// Draw main content based on selected tab
|
||||
match app.current_tab {
|
||||
TabIndex::Overview => draw_overview::<B>(f, chunks[1], app),
|
||||
TabIndex::Processes => draw_processes::<B>(f, chunks[1], app),
|
||||
TabIndex::Detections => draw_detections::<B>(f, chunks[1], app),
|
||||
TabIndex::Memory => draw_memory::<B>(f, chunks[1], app),
|
||||
TabIndex::Logs => draw_logs::<B>(f, chunks[1], app),
|
||||
TabIndex::Overview => draw_overview(f, chunks[1], app),
|
||||
TabIndex::Processes => draw_processes(f, chunks[1], app),
|
||||
TabIndex::Detections => draw_detections(f, chunks[1], app),
|
||||
TabIndex::Memory => draw_memory(f, chunks[1], app),
|
||||
TabIndex::Logs => draw_logs(f, chunks[1], app),
|
||||
TabIndex::ThreatIntel => {} // TODO: Implement threat intel view
|
||||
}
|
||||
|
||||
// Draw footer
|
||||
draw_footer::<B>(f, chunks[2], app);
|
||||
draw_footer(f, chunks[2], app);
|
||||
}
|
||||
|
||||
fn draw_header<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
fn draw_header(f: &mut Frame, area: Rect, app: &App) {
|
||||
let titles = app.get_tab_titles();
|
||||
let tabs = Tabs::new(titles)
|
||||
.block(
|
||||
@@ -84,7 +84,7 @@ fn draw_header<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
f.render_widget(tabs, area);
|
||||
}
|
||||
|
||||
fn draw_footer<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
fn draw_footer(f: &mut Frame, area: Rect, app: &App) {
|
||||
let help_text = match app.current_tab {
|
||||
TabIndex::Overview => {
|
||||
"Up/Down: Navigate | Tab: Switch tabs | R: Refresh | C: Clear | Q: Quit"
|
||||
@@ -112,7 +112,7 @@ fn draw_footer<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
f.render_widget(footer, area);
|
||||
}
|
||||
|
||||
fn draw_overview<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
fn draw_overview(f: &mut Frame, area: Rect, app: &App) {
|
||||
let chunks = Layout::default()
|
||||
.direction(Direction::Vertical)
|
||||
.constraints([
|
||||
@@ -123,16 +123,16 @@ fn draw_overview<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
.split(area);
|
||||
|
||||
// Statistics panel
|
||||
draw_stats_panel::<B>(f, chunks[0], app);
|
||||
draw_stats_panel(f, chunks[0], app);
|
||||
|
||||
// Threat level gauge
|
||||
draw_threat_gauge::<B>(f, chunks[1], app);
|
||||
draw_threat_gauge(f, chunks[1], app);
|
||||
|
||||
// Recent detections
|
||||
draw_recent_detections::<B>(f, chunks[2], app);
|
||||
draw_recent_detections(f, chunks[2], app);
|
||||
}
|
||||
|
||||
fn draw_stats_panel<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
fn draw_stats_panel(f: &mut Frame, area: Rect, app: &App) {
|
||||
let stats_chunks = Layout::default()
|
||||
.direction(Direction::Horizontal)
|
||||
.constraints([
|
||||
@@ -204,7 +204,7 @@ fn draw_stats_panel<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
f.render_widget(perf_gauge, stats_chunks[3]);
|
||||
}
|
||||
|
||||
fn draw_threat_gauge<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
fn draw_threat_gauge(f: &mut Frame, area: Rect, app: &App) {
|
||||
let threat_level = if app.stats.malicious_processes > 0 {
|
||||
100
|
||||
} else if app.stats.suspicious_processes > 0 {
|
||||
@@ -239,7 +239,7 @@ fn draw_threat_gauge<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
f.render_widget(threat_gauge, area);
|
||||
}
|
||||
|
||||
fn draw_recent_detections<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
fn draw_recent_detections(f: &mut Frame, area: Rect, app: &App) {
|
||||
let items: Vec<ListItem> = app
|
||||
.detections
|
||||
.iter()
|
||||
@@ -277,7 +277,7 @@ fn draw_recent_detections<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
f.render_widget(list, area);
|
||||
}
|
||||
|
||||
fn draw_processes<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
fn draw_processes(f: &mut Frame, area: Rect, app: &App) {
|
||||
let chunks = Layout::default()
|
||||
.direction(Direction::Horizontal)
|
||||
.constraints([Constraint::Percentage(70), Constraint::Percentage(30)])
|
||||
@@ -334,10 +334,10 @@ fn draw_processes<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
f.render_stateful_widget(table, chunks[0], &mut state);
|
||||
|
||||
// Process details panel
|
||||
draw_process_details::<B>(f, chunks[1], app);
|
||||
draw_process_details(f, chunks[1], app);
|
||||
}
|
||||
|
||||
fn draw_process_details<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
fn draw_process_details(f: &mut Frame, area: Rect, app: &App) {
|
||||
let details = if let Some(ref process) = app.selected_process {
|
||||
format!(
|
||||
"PID: {}\nPPID: {}\nName: {}\nPath: {}\nThreads: {}",
|
||||
@@ -364,7 +364,7 @@ fn draw_process_details<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
f.render_widget(paragraph, area);
|
||||
}
|
||||
|
||||
fn draw_detections<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
fn draw_detections(f: &mut Frame, area: Rect, app: &App) {
|
||||
let items: Vec<ListItem> = app
|
||||
.detections
|
||||
.iter()
|
||||
@@ -420,7 +420,7 @@ fn draw_detections<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
f.render_stateful_widget(list, area, &mut state);
|
||||
}
|
||||
|
||||
fn draw_memory<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
fn draw_memory(f: &mut Frame, area: Rect, app: &App) {
|
||||
let chunks = Layout::default()
|
||||
.direction(Direction::Vertical)
|
||||
.constraints([Constraint::Length(8), Constraint::Min(0)])
|
||||
@@ -459,7 +459,7 @@ fn draw_memory<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
f.render_widget(memory_info, chunks[1]);
|
||||
}
|
||||
|
||||
fn draw_logs<B: Backend>(f: &mut Frame, area: Rect, app: &App) {
|
||||
fn draw_logs(f: &mut Frame, area: Rect, app: &App) {
|
||||
let items: Vec<ListItem> = app
|
||||
.logs
|
||||
.iter()
|
||||
|
||||
Reference in New Issue
Block a user