Skip to content

Commit 0a65803

Browse files
committed
tugger-debian: parse multiple architecture values from dependency expression
Multiple values are clearly allowed by the specification.
1 parent 07edad3 commit 0a65803

1 file changed

Lines changed: 63 additions & 16 deletions

File tree

tugger-debian/src/dependency.rs

Lines changed: 63 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -54,7 +54,7 @@ pub static RE_DEPENDENCY: Lazy<Regex> = Lazy::new(|| {
5454
# Optional negation operator.
5555
(?P<arch_negate>!)?
5656
\s*
57-
# The architecture. May have spaces.
57+
# The architecture. May have spaces to delimit multiple values.
5858
(?P<arch>[^\]]+)
5959
\])?
6060
"#,
@@ -112,7 +112,7 @@ pub struct SingleDependency {
112112
/// Package the dependency is on.
113113
pub package: String,
114114
pub version_constraint: Option<DependencyVersionConstraint>,
115-
pub architecture: Option<(bool, String)>,
115+
pub architectures: Option<(bool, Vec<String>)>,
116116
}
117117

118118
impl Display for SingleDependency {
@@ -121,8 +121,8 @@ impl Display for SingleDependency {
121121
if let Some(constraint) = &self.version_constraint {
122122
write!(f, " ({} {})", constraint.relationship, constraint.version)?;
123123
}
124-
if let Some((negate, arch)) = &self.architecture {
125-
write!(f, " [{}{}]", if *negate { "!" } else { "" }, arch)?;
124+
if let Some((negate, arch)) = &self.architectures {
125+
write!(f, " [{}{}]", if *negate { "!" } else { "" }, arch.join(" "))?;
126126
}
127127

128128
Ok(())
@@ -158,16 +158,28 @@ impl SingleDependency {
158158
_ => None,
159159
};
160160

161-
let architecture = match (caps.name("arch_negate"), caps.name("arch")) {
162-
(Some(_), Some(arch)) => Some((true, arch.as_str().to_string())),
163-
(None, Some(arch)) => Some((false, arch.as_str().to_string())),
161+
let architectures = match (caps.name("arch_negate"), caps.name("arch")) {
162+
(Some(_), Some(arch)) => Some((
163+
true,
164+
arch.as_str()
165+
.split_ascii_whitespace()
166+
.map(|x| x.to_string())
167+
.collect::<Vec<_>>(),
168+
)),
169+
(None, Some(arch)) => Some((
170+
false,
171+
arch.as_str()
172+
.split_ascii_whitespace()
173+
.map(|x| x.to_string())
174+
.collect::<Vec<_>>(),
175+
)),
164176
_ => None,
165177
};
166178

167179
Ok(Self {
168180
package,
169181
version_constraint: dependency,
170-
architecture,
182+
architectures,
171183
})
172184
}
173185

@@ -181,9 +193,11 @@ impl SingleDependency {
181193
architecture: &str,
182194
) -> bool {
183195
if self.package == package {
184-
if let Some((negate, arch)) = &self.architecture {
196+
if let Some((negate, arches)) = &self.architectures {
197+
let contains = arches.iter().any(|x| x == architecture);
198+
185199
// Requesting an arch mismatch.
186-
if (*negate && arch == architecture) || (!*negate && arch != architecture) {
200+
if (*negate && contains) || (!*negate && !contains) {
187201
return false;
188202
}
189203
}
@@ -537,15 +551,15 @@ mod test {
537551
relationship: VersionRelationship::LaterOrEqual,
538552
version: PackageVersion::parse("2.4").unwrap()
539553
}),
540-
architecture: None,
554+
architectures: None,
541555
}
542556
);
543557
assert_eq!(
544558
dl.dependencies[1].0[0],
545559
SingleDependency {
546560
package: "libx11-6".into(),
547561
version_constraint: None,
548-
architecture: None,
562+
architectures: None,
549563
}
550564
);
551565

@@ -557,19 +571,19 @@ mod test {
557571
SingleDependency {
558572
package: "libc".into(),
559573
version_constraint: None,
560-
architecture: Some((false, "amd64".into())),
574+
architectures: Some((false, vec!["amd64".into()])),
561575
}
562576
);
563577

564-
let dl = DependencyList::parse("libc [!amd64]")?;
578+
let dl = DependencyList::parse("libc [!amd64 i386]")?;
565579
assert_eq!(dl.dependencies.len(), 1);
566580
assert_eq!(dl.dependencies[0].0.len(), 1);
567581
assert_eq!(
568582
dl.dependencies[0].0[0],
569583
SingleDependency {
570584
package: "libc".into(),
571585
version_constraint: None,
572-
architecture: Some((true, "amd64".into())),
586+
architectures: Some((true, vec!["amd64".into(), "i386".into()])),
573587
}
574588
);
575589

@@ -694,7 +708,6 @@ mod test {
694708
#[test]
695709
fn satisfies_architecture_constraints() -> Result<()> {
696710
let dl = DependencyList::parse("libc [amd64]")?;
697-
698711
assert!(dl.dependencies[0].package_satisfies(
699712
"libc",
700713
&PackageVersion::parse("2.4")?,
@@ -706,6 +719,23 @@ mod test {
706719
"x86"
707720
));
708721

722+
let dl = DependencyList::parse("libc [amd64 i386]")?;
723+
assert!(dl.dependencies[0].package_satisfies(
724+
"libc",
725+
&PackageVersion::parse("2.4")?,
726+
"amd64"
727+
));
728+
assert!(dl.dependencies[0].package_satisfies(
729+
"libc",
730+
&PackageVersion::parse("2.3")?,
731+
"i386"
732+
));
733+
assert!(!dl.dependencies[0].package_satisfies(
734+
"libc",
735+
&PackageVersion::parse("2.3")?,
736+
"arm64"
737+
));
738+
709739
let dl = DependencyList::parse("libc [!amd64]")?;
710740
assert!(!dl.dependencies[0].package_satisfies(
711741
"libc",
@@ -718,6 +748,23 @@ mod test {
718748
"x86"
719749
));
720750

751+
let dl = DependencyList::parse("libc [!amd64 i386]")?;
752+
assert!(!dl.dependencies[0].package_satisfies(
753+
"libc",
754+
&PackageVersion::parse("2.4")?,
755+
"amd64"
756+
));
757+
assert!(!dl.dependencies[0].package_satisfies(
758+
"libc",
759+
&PackageVersion::parse("2.3")?,
760+
"i386"
761+
));
762+
assert!(dl.dependencies[0].package_satisfies(
763+
"libc",
764+
&PackageVersion::parse("2.3")?,
765+
"arm64"
766+
));
767+
721768
Ok(())
722769
}
723770
}

0 commit comments

Comments
 (0)