Skip to content

Commit f3401bd

Browse files
committed
Add const parameter REPLACEMENT_ALLOWED to DisallowedPath
1 parent 7534c4c commit f3401bd

File tree

7 files changed

+67
-18
lines changed

7 files changed

+67
-18
lines changed

clippy_config/src/conf.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -445,7 +445,7 @@ define_Conf! {
445445
avoid_breaking_exported_api: bool = true,
446446
/// The list of types which may not be held across an await point.
447447
#[lints(await_holding_invalid_type)]
448-
await_holding_invalid_types: Vec<DisallowedPath> = Vec::new(),
448+
await_holding_invalid_types: Vec<DisallowedPath<false>> = Vec::new(),
449449
/// DEPRECATED LINT: BLACKLISTED_NAME.
450450
///
451451
/// Use the Disallowed Names lint instead

clippy_config/src/types.rs

Lines changed: 41 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -11,9 +11,33 @@ pub struct Rename {
1111
pub rename: String,
1212
}
1313

14-
#[derive(Debug, Deserialize)]
14+
#[derive(Debug, Serialize)]
15+
pub struct DisallowedPath<const REPLACEMENT_ALLOWED: bool = true> {
16+
path: String,
17+
reason: Option<String>,
18+
replacement: Option<String>,
19+
}
20+
21+
impl<'de, const REPLACEMENT_ALLOWED: bool> Deserialize<'de> for DisallowedPath<REPLACEMENT_ALLOWED> {
22+
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
23+
where
24+
D: Deserializer<'de>,
25+
{
26+
let enum_ = DisallowedPathEnum::deserialize(deserializer)?;
27+
if !REPLACEMENT_ALLOWED && enum_.replacement().is_some() {
28+
return Err(de::Error::custom("replacement not allowed for this configuration"));
29+
}
30+
Ok(Self {
31+
path: enum_.path().to_owned(),
32+
reason: enum_.reason().map(ToOwned::to_owned),
33+
replacement: enum_.replacement().map(ToOwned::to_owned),
34+
})
35+
}
36+
}
37+
38+
#[derive(Debug, Deserialize, Serialize)]
1539
#[serde(untagged)]
16-
pub enum DisallowedPath {
40+
pub enum DisallowedPathEnum {
1741
Simple(String),
1842
WithReason {
1943
path: String,
@@ -22,27 +46,33 @@ pub enum DisallowedPath {
2246
},
2347
}
2448

25-
impl DisallowedPath {
49+
impl<const REPLACEMENT_ALLOWED: bool> DisallowedPath<REPLACEMENT_ALLOWED> {
2650
pub fn path(&self) -> &str {
27-
let (Self::Simple(path) | Self::WithReason { path, .. }) = self;
28-
29-
path
51+
&self.path
3052
}
3153

32-
pub fn diag_amendment(&self, span: Span) -> impl FnOnce(&mut Diag<'_, ()>) + use<'_> {
54+
pub fn diag_amendment(&self, span: Span) -> impl FnOnce(&mut Diag<'_, ()>) + use<'_, REPLACEMENT_ALLOWED> {
3355
move |diag| {
34-
if let Some(replacement) = self.replacement() {
56+
if let Some(replacement) = &self.replacement {
3557
diag.span_suggestion(
3658
span,
37-
self.reason().map_or_else(|| String::from("use"), ToOwned::to_owned),
59+
self.reason.as_ref().map_or_else(|| String::from("use"), Clone::clone),
3860
replacement,
3961
Applicability::MachineApplicable,
4062
);
41-
} else if let Some(reason) = self.reason() {
42-
diag.note(reason.to_owned());
63+
} else if let Some(reason) = &self.reason {
64+
diag.note(reason.clone());
4365
}
4466
}
4567
}
68+
}
69+
70+
impl DisallowedPathEnum {
71+
pub fn path(&self) -> &str {
72+
let (Self::Simple(path) | Self::WithReason { path, .. }) = self;
73+
74+
path
75+
}
4676

4777
fn reason(&self) -> Option<&str> {
4878
match &self {
@@ -449,7 +479,6 @@ macro_rules! unimplemented_serialize {
449479
}
450480

451481
unimplemented_serialize! {
452-
DisallowedPath,
453482
Rename,
454483
MacroMatcher,
455484
}

clippy_lints/src/await_holding_invalid.rs

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -174,7 +174,7 @@ declare_clippy_lint! {
174174
impl_lint_pass!(AwaitHolding => [AWAIT_HOLDING_LOCK, AWAIT_HOLDING_REFCELL_REF, AWAIT_HOLDING_INVALID_TYPE]);
175175

176176
pub struct AwaitHolding {
177-
def_ids: DefIdMap<(&'static str, &'static DisallowedPath)>,
177+
def_ids: DefIdMap<(&'static str, &'static DisallowedPath<false>)>,
178178
}
179179

180180
impl AwaitHolding {
@@ -255,7 +255,12 @@ impl AwaitHolding {
255255
}
256256
}
257257

258-
fn emit_invalid_type(cx: &LateContext<'_>, span: Span, path: &'static str, disallowed_path: &'static DisallowedPath) {
258+
fn emit_invalid_type(
259+
cx: &LateContext<'_>,
260+
span: Span,
261+
path: &'static str,
262+
disallowed_path: &'static DisallowedPath<false>,
263+
) {
259264
span_lint_and_then(
260265
cx,
261266
AWAIT_HOLDING_INVALID_TYPE,

clippy_utils/src/lib.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -750,10 +750,10 @@ pub fn def_path_def_ids(tcx: TyCtxt<'_>, path: &[&str]) -> impl Iterator<Item =
750750
}
751751

752752
/// Creates a map of disallowed items to the reason they were disallowed.
753-
pub fn create_disallowed_map(
753+
pub fn create_disallowed_map<const REPLACEMENT_ALLOWED: bool>(
754754
tcx: TyCtxt<'_>,
755-
disallowed: &'static [DisallowedPath],
756-
) -> DefIdMap<(&'static str, &'static DisallowedPath)> {
755+
disallowed: &'static [DisallowedPath<REPLACEMENT_ALLOWED>],
756+
) -> DefIdMap<(&'static str, &'static DisallowedPath<REPLACEMENT_ALLOWED>)> {
757757
disallowed
758758
.iter()
759759
.map(|x| (x.path(), x.path().split("::").collect::<Vec<_>>(), x))
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
fn main() {}
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
error: error reading Clippy's configuration file: replacement not allowed for this configuration
2+
--> $DIR/tests/ui-toml/await_holding_invalid_type_with_replacement/clippy.toml:1:31
3+
|
4+
LL | await-holding-invalid-types = [
5+
| _______________________________^
6+
LL | | { path = "std::string::String", replacement = "std::net::Ipv4Addr" },
7+
LL | | ]
8+
| |_^
9+
10+
error: aborting due to 1 previous error
11+
Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
await-holding-invalid-types = [
2+
{ path = "std::string::String", replacement = "std::net::Ipv4Addr" },
3+
]

0 commit comments

Comments
 (0)