]> git.lizzy.rs Git - rust.git/blob - tests/rustdoc/hide-complex-unevaluated-const-arguments.rs
incremental: migrate diagnostics
[rust.git] / tests / rustdoc / hide-complex-unevaluated-const-arguments.rs
1 // Test that certain unevaluated constant expression arguments that are
2 // deemed too verbose or complex and that may leak private or
3 // `doc(hidden)` struct fields are not displayed in the documentation.
4 //
5 // Read the documentation of `rustdoc::clean::utils::print_const_expr`
6 // for further details.
7 #![feature(const_trait_impl, generic_const_exprs)]
8 #![allow(incomplete_features)]
9
10 // @has hide_complex_unevaluated_const_arguments/trait.Stage.html
11 pub trait Stage {
12     // A helper constant that prevents const expressions containing it
13     // from getting fully evaluated since it doesn't have a body and
14     // thus is non-reducible. This allows us to specifically test the
15     // pretty-printing of *unevaluated* consts.
16     const ABSTRACT: usize;
17
18     // Currently considered "overly complex" by the `generic_const_exprs`
19     // feature. If / once this expression kind gets supported, this
20     // unevaluated const expression could leak the private struct field.
21     //
22     // FIXME: Once the line below compiles, make this a test that
23     //        ensures that the private field is not printed.
24     //
25     //const ARRAY0: [u8; Struct { private: () } + Self::ABSTRACT];
26
27     // This assoc. const could leak the private assoc. function `Struct::new`.
28     // Ensure that this does not happen.
29     //
30     // @has - '//*[@id="associatedconstant.ARRAY1"]' \
31     //        'const ARRAY1: [u8; { _ }]'
32     const ARRAY1: [u8; Struct::new(/* ... */) + Self::ABSTRACT * 1_000];
33
34     // @has - '//*[@id="associatedconstant.VERBOSE"]' \
35     //        'const VERBOSE: [u16; { _ }]'
36     const VERBOSE: [u16; compute("thing", 9 + 9) * Self::ABSTRACT];
37
38     // Check that we do not leak the private struct field contained within
39     // the path. The output could definitely be improved upon
40     // (e.g. printing sth. akin to `<Self as Helper<{ _ }>>::OUT`) but
41     // right now “safe is safe”.
42     //
43     // @has - '//*[@id="associatedconstant.PATH"]' \
44     //        'const PATH: usize = _'
45     const PATH: usize = <Self as Helper<{ Struct { private: () } }>>::OUT;
46 }
47
48 const fn compute(input: &str, extra: usize) -> usize {
49     input.len() + extra
50 }
51
52 pub trait Helper<const S: Struct> {
53     const OUT: usize;
54 }
55
56 impl<const S: Struct, St: Stage + ?Sized> Helper<S> for St {
57     const OUT: usize = St::ABSTRACT;
58 }
59
60 // Currently in rustdoc, const arguments are not evaluated in this position
61 // and therefore they fall under the realm of `print_const_expr`.
62 // If rustdoc gets patched to evaluate const arguments, it is fine to replace
63 // this test as long as one can ensure that private fields are not leaked!
64 //
65 // @has hide_complex_unevaluated_const_arguments/trait.Sub.html \
66 //      '//div[@class="item-decl"]/pre[@class="rust"]' \
67 //      'pub trait Sub: Sup<{ _ }, { _ }> { }'
68 pub trait Sub: Sup<{ 90 * 20 * 4 }, { Struct { private: () } }> {}
69
70 pub trait Sup<const N: usize, const S: Struct> {}
71
72 pub struct Struct { private: () }
73
74 impl Struct {
75     const fn new() -> Self { Self { private: () } }
76 }
77
78 impl const std::ops::Add<usize> for Struct {
79     type Output = usize;
80
81     fn add(self, _: usize) -> usize { 0 }
82 }