2019-09-25 17:46:14 +00:00
|
|
|
// does not test any rustfixable lints
|
2018-07-28 15:34:52 +00:00
|
|
|
#![warn(clippy::clone_on_ref_ptr)]
|
2022-10-06 07:44:38 +00:00
|
|
|
#![allow(unused)]
|
|
|
|
#![allow(clippy::redundant_clone, clippy::uninlined_format_args, clippy::unnecessary_wraps)]
|
2023-07-27 11:40:22 +00:00
|
|
|
//@no-rustfix
|
2018-10-19 04:03:56 +00:00
|
|
|
use std::cell::RefCell;
|
2017-10-10 04:07:12 +00:00
|
|
|
use std::rc::{self, Rc};
|
|
|
|
use std::sync::{self, Arc};
|
|
|
|
|
2018-01-15 03:58:09 +00:00
|
|
|
trait SomeTrait {}
|
|
|
|
struct SomeImpl;
|
|
|
|
impl SomeTrait for SomeImpl {}
|
|
|
|
|
2017-10-10 04:07:12 +00:00
|
|
|
fn main() {}
|
|
|
|
|
|
|
|
fn clone_on_ref_ptr() {
|
|
|
|
let rc = Rc::new(true);
|
|
|
|
let arc = Arc::new(true);
|
|
|
|
|
|
|
|
let rcweak = Rc::downgrade(&rc);
|
|
|
|
let arc_weak = Arc::downgrade(&arc);
|
|
|
|
|
|
|
|
rc.clone();
|
2023-07-28 19:35:48 +00:00
|
|
|
//~^ ERROR: using `.clone()` on a ref-counted pointer
|
|
|
|
//~| NOTE: `-D clippy::clone-on-ref-ptr` implied by `-D warnings`
|
2017-10-10 04:07:12 +00:00
|
|
|
Rc::clone(&rc);
|
|
|
|
|
|
|
|
arc.clone();
|
2023-07-28 19:35:48 +00:00
|
|
|
//~^ ERROR: using `.clone()` on a ref-counted pointer
|
2017-10-10 04:07:12 +00:00
|
|
|
Arc::clone(&arc);
|
|
|
|
|
|
|
|
rcweak.clone();
|
2023-07-28 19:35:48 +00:00
|
|
|
//~^ ERROR: using `.clone()` on a ref-counted pointer
|
2017-10-10 04:07:12 +00:00
|
|
|
rc::Weak::clone(&rcweak);
|
|
|
|
|
|
|
|
arc_weak.clone();
|
2023-07-28 19:35:48 +00:00
|
|
|
//~^ ERROR: using `.clone()` on a ref-counted pointer
|
2017-10-10 04:07:12 +00:00
|
|
|
sync::Weak::clone(&arc_weak);
|
|
|
|
|
2018-01-15 03:58:09 +00:00
|
|
|
let x = Arc::new(SomeImpl);
|
2019-05-30 06:23:47 +00:00
|
|
|
let _: Arc<dyn SomeTrait> = x.clone();
|
2023-07-28 19:35:48 +00:00
|
|
|
//~^ ERROR: using `.clone()` on a ref-counted pointer
|
2017-10-10 04:07:12 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
fn clone_on_copy_generic<T: Copy>(t: T) {
|
|
|
|
t.clone();
|
2023-07-28 19:35:48 +00:00
|
|
|
//~^ ERROR: using `clone` on type `T` which implements the `Copy` trait
|
|
|
|
//~| NOTE: `-D clippy::clone-on-copy` implied by `-D warnings`
|
2017-10-10 04:07:12 +00:00
|
|
|
|
|
|
|
Some(t).clone();
|
2023-07-28 19:35:48 +00:00
|
|
|
//~^ ERROR: using `clone` on type `Option<T>` which implements the `Copy` trait
|
2017-10-10 04:07:12 +00:00
|
|
|
}
|
|
|
|
|
2018-10-19 18:51:25 +00:00
|
|
|
mod many_derefs {
|
|
|
|
struct A;
|
|
|
|
struct B;
|
|
|
|
struct C;
|
|
|
|
struct D;
|
|
|
|
#[derive(Copy, Clone)]
|
|
|
|
struct E;
|
|
|
|
|
|
|
|
macro_rules! impl_deref {
|
|
|
|
($src:ident, $dst:ident) => {
|
|
|
|
impl std::ops::Deref for $src {
|
|
|
|
type Target = $dst;
|
2018-12-09 22:26:16 +00:00
|
|
|
fn deref(&self) -> &Self::Target {
|
|
|
|
&$dst
|
|
|
|
}
|
2018-10-19 18:51:25 +00:00
|
|
|
}
|
2018-12-09 22:26:16 +00:00
|
|
|
};
|
2018-10-19 18:51:25 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
impl_deref!(A, B);
|
|
|
|
impl_deref!(B, C);
|
|
|
|
impl_deref!(C, D);
|
|
|
|
impl std::ops::Deref for D {
|
|
|
|
type Target = &'static E;
|
2018-12-09 22:26:16 +00:00
|
|
|
fn deref(&self) -> &Self::Target {
|
|
|
|
&&E
|
|
|
|
}
|
2018-10-19 18:51:25 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
fn go1() {
|
|
|
|
let a = A;
|
|
|
|
let _: E = a.clone();
|
2023-07-28 19:35:48 +00:00
|
|
|
//~^ ERROR: using `clone` on type `E` which implements the `Copy` trait
|
2018-10-19 18:51:25 +00:00
|
|
|
let _: E = *****a;
|
|
|
|
}
|
|
|
|
}
|
2020-08-28 14:10:16 +00:00
|
|
|
|
|
|
|
mod issue2076 {
|
|
|
|
use std::rc::Rc;
|
|
|
|
|
|
|
|
macro_rules! try_opt {
|
|
|
|
($expr: expr) => {
|
|
|
|
match $expr {
|
|
|
|
Some(value) => value,
|
|
|
|
None => return None,
|
|
|
|
}
|
|
|
|
};
|
|
|
|
}
|
|
|
|
|
|
|
|
fn func() -> Option<Rc<u8>> {
|
|
|
|
let rc = Rc::new(42);
|
|
|
|
Some(try_opt!(Some(rc)).clone())
|
2023-07-28 19:35:48 +00:00
|
|
|
//~^ ERROR: using `.clone()` on a ref-counted pointer
|
2020-08-28 14:10:16 +00:00
|
|
|
}
|
|
|
|
}
|