Skip to main content

xbp_analysis/domain/
model.rs

1//! Language-independent analysis model built by adapters.
2
3use super::concepts::ConceptInstance;
4use super::types::{ControlFlow, ErrorPath, LanguageId, SourceFile};
5use serde::{Deserialize, Serialize};
6use std::path::PathBuf;
7
8/// Per-file abstract model consumed by language-independent rules.
9#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
10pub struct FileModel {
11    pub path: PathBuf,
12    pub language: LanguageId,
13    pub concepts: Vec<ConceptInstance>,
14    #[serde(default)]
15    pub control_flow: ControlFlow,
16    #[serde(default)]
17    pub error_paths: Vec<ErrorPath>,
18    /// True when the adapter marks the file as generated / macro-expanded only.
19    #[serde(default)]
20    pub generated: bool,
21}
22
23/// Workspace-level model for a single language analysis pass.
24#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize, Default)]
25pub struct LanguageModel {
26    pub language: LanguageId,
27    pub files: Vec<FileModel>,
28}
29
30impl LanguageModel {
31    pub fn new(language: LanguageId) -> Self {
32        Self {
33            language,
34            files: Vec::new(),
35        }
36    }
37
38    pub fn concepts(&self) -> impl Iterator<Item = (&FileModel, &ConceptInstance)> {
39        self.files
40            .iter()
41            .flat_map(|f| f.concepts.iter().map(move |c| (f, c)))
42    }
43}
44
45/// Result of parsing a single source file (opaque to domain rules).
46#[derive(Debug, Clone)]
47pub struct ParseResult {
48    pub file: SourceFile,
49    pub ok: bool,
50    pub diagnostics: Vec<String>,
51}