quil_rs/program/
source_map.rs1use std::fmt::Debug;
2
3use crate::instruction::GateSignature;
4
5use super::{CalibrationSource, InstructionIndex};
6
7#[derive(Clone, Debug, PartialEq, Eq)]
18pub struct SourceMap<SourceIndex, TargetIndex> {
19 pub(crate) entries: Vec<SourceMapEntry<SourceIndex, TargetIndex>>,
20}
21
22impl<SourceIndex, TargetIndex> SourceMap<SourceIndex, TargetIndex> {
23 pub fn new(entries: Vec<SourceMapEntry<SourceIndex, TargetIndex>>) -> Self {
24 Self { entries }
25 }
26
27 pub fn list_sources<QueryIndex>(&self, target_index: &QueryIndex) -> Vec<&SourceIndex>
31 where
32 TargetIndex: SourceMapIndexable<QueryIndex>,
33 {
34 self.entries
35 .iter()
36 .filter(|&entry| entry.target_location().contains(target_index))
37 .map(SourceMapEntry::source_location)
38 .collect()
39 }
40
41 pub fn list_targets<QueryIndex>(&self, source_index: &QueryIndex) -> Vec<&TargetIndex>
45 where
46 SourceIndex: SourceMapIndexable<QueryIndex>,
47 {
48 self.entries
49 .iter()
50 .filter(|entry| entry.source_location().contains(source_index))
51 .map(SourceMapEntry::target_location)
52 .collect()
53 }
54}
55
56impl<SourceIndex, TargetIndex> Default for SourceMap<SourceIndex, TargetIndex> {
57 fn default() -> Self {
58 Self {
59 entries: Vec::new(),
60 }
61 }
62}
63
64impl<SourceIndex, TargetIndex> SourceMap<SourceIndex, TargetIndex> {
65 pub fn entries(&self) -> &[SourceMapEntry<SourceIndex, TargetIndex>] {
66 &self.entries
67 }
68}
69
70#[derive(Clone, Debug, PartialEq, Eq)]
71pub struct SourceMapEntry<SourceIndex, TargetIndex> {
72 pub(crate) source_location: SourceIndex,
74
75 pub(crate) target_location: TargetIndex,
77}
78
79impl<SourceIndex, TargetIndex> SourceMapEntry<SourceIndex, TargetIndex> {
80 pub fn new(source_location: SourceIndex, target_location: TargetIndex) -> Self {
81 Self {
82 source_location,
83 target_location,
84 }
85 }
86
87 pub fn source_location(&self) -> &SourceIndex {
88 &self.source_location
89 }
90
91 pub fn target_location(&self) -> &TargetIndex {
92 &self.target_location
93 }
94}
95
96pub trait SourceMapIndexable<Index> {
98 fn contains(&self, other: &Index) -> bool;
100}
101
102impl SourceMapIndexable<InstructionIndex> for InstructionIndex {
103 fn contains(&self, other: &InstructionIndex) -> bool {
104 self == other
105 }
106}
107
108#[derive(Clone, Debug, PartialEq)]
109pub enum ExpansionResult<R> {
110 Unmodified(InstructionIndex),
111 Rewritten(R),
112}
113
114impl<R> SourceMapIndexable<InstructionIndex> for ExpansionResult<R>
115where
116 R: SourceMapIndexable<InstructionIndex>,
117{
118 fn contains(&self, other: &InstructionIndex) -> bool {
119 match self {
120 Self::Unmodified(index) => index == other,
121 Self::Rewritten(rewrite) => rewrite.contains(other),
122 }
123 }
124}
125
126impl<R> SourceMapIndexable<CalibrationSource> for ExpansionResult<R>
127where
128 R: SourceMapIndexable<CalibrationSource>,
129{
130 fn contains(&self, other: &CalibrationSource) -> bool {
131 if let Self::Rewritten(rewrite) = self {
132 rewrite.contains(other)
133 } else {
134 false
135 }
136 }
137}
138
139impl<'a, R> SourceMapIndexable<GateSignature<'a>> for ExpansionResult<R>
140where
141 R: SourceMapIndexable<GateSignature<'a>>,
142{
143 fn contains(&self, other: &GateSignature<'a>) -> bool {
144 if let Self::Rewritten(rewrite) = self {
145 rewrite.contains(other)
146 } else {
147 false
148 }
149 }
150}