]> git.lizzy.rs Git - rust.git/blob - src/test/codegen/coverage-experiments/src/coverage_injection_test_alt.rs
20c4835dd882ec0201785ac0d8e0a8f26b9e7991
[rust.git] / src / test / codegen / coverage-experiments / src / coverage_injection_test_alt.rs
1 /*                       */ use std::io::Error;
2 /*                       */ use std::io::ErrorKind;
3 /*                       */
4 /*                       */ /// Align Rust counter increment with with:
5 /*                       */ /// [‘llvm.instrprof.increment’ Intrinsic](https://llvm.org/docs/LangRef.html#llvm-instrprof-increment-intrinsic)
6 /*                       */ ///
7 /*                       */ /// declare void @llvm.instrprof.increment(i8* <name>, i64 <hash>, i32 <num-counters>, i32 <index>)
8 /*                       */ ///
9 /*                       */ /// The first argument is a pointer to a global variable containing the name of the entity
10 /*                       */ /// being instrumented. This should generally be the (mangled) function name for a set of
11 /*                       */ /// counters.
12 /*                       */ ///
13 /*                       */ /// The second argument is a hash value that can be used by the consumer of the profile data
14 /*                       */ /// to detect changes to the instrumented source, and the third is the number of counters
15 /*                       */ /// associated with name. It is an error if hash or num-counters differ between two
16 /*                       */ /// instances of instrprof.increment that refer to the same name.
17 /*                       */ ///
18 /*                       */ /// The last argument refers to which of the counters for name should be incremented. It
19 /*                       */ /// should be a value between 0 and num-counters.
20 /*                       */ ///
21 /*                       */ /// # Arguments
22 /*                       */ ///
23 /*                       */ /// `mangled_fn_name` - &'static ref to computed and injected static str, using:
24 /*                       */ ///
25 /*                       */ ///     ```
26 /*                       */ ///     fn rustc_symbol_mangling::compute_symbol_name(
27 /*                       */ ///         tcx: TyCtxt<'tcx>,
28 /*                       */ ///         instance: Instance<'tcx>,
29 /*                       */ ///         compute_instantiating_crate: impl FnOnce() -> CrateNum,
30 /*                       */ ///     ) -> String
31 /*                       */ ///     ```
32 /*                       */ ///
33 /*                       */ /// `source_version_hash` - Compute hash based that only changes if there are "significant"
34 /*                       */ /// to control-flow inside the function.
35 /*                       */ ///
36 /*                       */ /// `num_counters` - The total number of counter calls [MAX(counter_index) + 1] within the
37 /*                       */ /// function.
38 /*                       */ ///
39 /*                       */ /// `counter_index` - zero-based counter index scoped by the function. (Ordering of
40 /*                       */ /// counters, relative to the source code location, is apparently not expected.)
41 /*                       */ ///
42 /*                       */ /// # Notes
43 /*                       */ ///
44 /*                       */ /// * The mangled_fn_name may not be computable until generics are monomorphized (see
45 /*                       */ ///   parameters required by rustc_symbol_mangling::compute_symbol_name).
46 /*                       */ /// * The version hash may be computable from AST analysis, and may not benefit from further
47 /*                       */ ///   lowering.
48 /*                       */ /// * num_counters depends on having already identified all counter insertion locations.
49 /*                       */ /// * counter_index can be computed at time of counter insertion (incrementally).
50 /*                       */ /// * Numeric parameters are signed to match the llvm increment intrinsic parameter types.
51 /*                       */ fn __lower_incr_cov(_mangled_fn_name: &'static str, _fn_version_hash: i64, _num_counters: i32, _counter_index: i32) {
52 /*                       */ }
53 /*                       */
54 /*                       */ /// A coverage counter implementation that will work as both an intermediate coverage
55 /*                       */ /// counting and reporting implementation at the AST-level only--for debugging and
56 /*                       */ /// development--but also serves as a "marker" to be replaced by calls to LLVM
57 /*                       */ /// intrinsic coverage counter APIs during the lowering process.
58 /*                       */ ///
59 /*                       */ /// Calls to this function will be injected automatically into the AST. When LLVM intrinsics
60 /*                       */ /// are enabled, the counter function calls that were injected into the AST serve as
61 /*                       */ /// placeholders, to be replaced by an alternative, such as:
62 /*                       */ ///
63 /*                       */ ///     * direct invocation of the `llvm.instrprof.increment()` intrinsic; or
64 /*                       */ ///     * the `__lower_incr_cov()` function, defined above, that would invoke the
65 /*                       */ ///       `llvm.instrprof.increment()` intrinsic; or
66 /*                       */ ///     * a similar expression wrapper, with the additional parameters (as defined above
67 /*                       */ ///       for `__lower_incr_cov()`, that invokes `llvm.instrprof.increment()` and returns the
68 /*                       */ ///       result of the wrapped expression)
69 /*                       */ ///
70 /*                       */ /// The first two options would require replacing the inlined wrapper call with something
71 /*                       */ /// like:
72 /*                       */ ///
73 /*                       */ /// ```
74 /*                       */ /// { let result = {expr}; __inlined_incr_cov(context, counter); result }
75 /*                       */ /// ```
76 /*                       */ ///
77 /*                       */ /// But if the lowering process is already unwrapping the inlined call to `__incr_cov()`, then
78 /*                       */ /// it may be a perfect opportunity to replace the function with one of these more
79 /*                       */ /// direct methods.
80 /*                       */ ///
81 /*                       */ #[inline(always)]
82 /*                       */ pub fn __incr_cov(region_loc: &str, /*index: u32,*/) {
83 /*                       */     // Either call the intermediate non-llvm coverage counter API or
84 /*                       */     // replace the call to this function with the expanded `__lower_incr_cov()` call.
85 /*                       */
86 /*                       */     // let _lock = increment_counter(counter);
87 /*                       */     println!("{}", region_loc);
88 /*                       */ }
89 /*                       */
90 /*                       */ /// Write a report identifying each incremented counter and the number of times each counter
91 /*                       */ /// was incremented.
92 /*                       */ fn __report() {
93 /*                       */     println!("WRITE REPORT!");
94 /*                       */ }
95 /*                       */
96 /*                       */ /// Increment the counter after evaluating the wrapped expression (see `__incr_cov()`), then
97 /*                       */ /// write a report identifying each incremented counter and the number of times each counter
98 /*                       */ /// was incremented.
99 /*                       */ #[inline(always)]
100 /*                       */ pub fn __incr_cov_and_report<T>(region_loc: &str, /*counter: u32,*/ result: T) -> T {
101 /*                       */     __incr_cov(region_loc, /*counter,*/);
102 /*                       */     __report();
103 /*                       */     result
104 /*                       */ }
105 /*                       */
106 /*                       */ macro_rules! from {
107 /*                       */     ($from:expr) => { &format!("from: {}\n  to: {}:{}:{}", $from, file!(), line!(), column!()) };
108 /*                       */ }
109 /*                       */
110 /*                       */ macro_rules! to {
111 /*                       */     ($to:expr) => { &format!("to: {}\n  to: {}:{}:{}", $to, file!(), line!(), column!()) };
112 /*                       */ }
113 /*                       */
114 /*                       */ #[derive(Debug)]
115 /*                       */ enum TestEnum {
116 /*                       */     Red,
117 /*                       */     Green,
118 /*                       */     Blue,
119 /*                       */ }
120 /*                       */
121 /*                       */ struct TestStruct {
122 /*                       */     field: i32,
123 /*                       */ }
124 /*                       */
125 /*                       */ // IMPORTANT! IS WRAPPING main() ENOUGH? OR DO I ALSO NEED TO WRAP THREAD FUNCTIONS, ASSUMING
126 /*                       */ // THEY ARE STILL RUNNING WITH MAIN EXITS? (IF THEY CAN). NOT SURE HOW RUST HANDLES THAT.
127 /*                       */
128 /*                       */ // I SUSPECT USING THREAD_LOCAL COUNTERS MAY NOT ACTUALLY BE AN OPTIMIZATION OVER MUTEX LOCKS,
129 /*                       */ // BUT MAYBE I SHOULD ASK.
130 /*                       */
131 /*                       */ impl TestStruct {
132 /*    -                  */     fn new() -> Self {
133 /*    ┃                  */         __incr_cov(to!("end of fn new()")); // function-scoped counter index = 0
134 /*    ┃                  */         Self::new_with_value(31415)
135 /*    -                  */     }
136 /*                       */
137 /*    -                  */     fn new_with_value(field: i32) -> Self {
138 /*    ┃                  */         __incr_cov(to!("end of fn new_with_value()")); // function-scoped counter index = 0
139 /*    ┃                  */         Self {
140 /*    ┃                  */             field,
141 /*    ┃                  */         }
142 /*    -                  */     }
143 /*                       */
144 /*                       */     fn call_closure<F>(&self, closure: F) -> bool
145 /*                       */     where
146 /*                       */         F: FnOnce(
147 /*                       */             i32,
148 /*                       */         ) -> bool,
149 /*    -                  */     {
150 /*    ┃                  */         __incr_cov(to!("end of fn call_closure()")); // function-scoped counter index = 0
151 /*    ┃                  */         closure(123)
152 /*    -                  */     }
153 /*                       */
154 /*    -                  */     fn various(&self) -> Result<(),Error> {
155 /*    ┃                  */         __incr_cov(to!("just before next branch: after `match color`: pattern selection"));
156 /*    ┃                  */         use TestEnum::*;
157 /*    ┃                  */         let mut color = Red;
158 /*    ┃                  */         let _ = color;
159 /*    ┃                  */         color = Blue;
160 /*    ┃                  */         let _ = color;
161 /*    ┃                  */         color = Green;
162 /*    ┃                  */         match color { // function-scoped counter index = 0
163 /*    :                  */
164 /*    :                  */             // !!! RECORD SPAN FROM START OF INNERMOST CONTAINING BLOCK (THE FUNCTION IN THIS CASE) TO END OF MATCH EXPRESSION
165 /*    :                  */             // If `match`, `while`, `loop`, `for`, `if`, etc. expression has a `return`, `break`, or `continue`
166 /*    :                  */             // (if legal), then RECORD SPAN FROM START OF INNERMOST CONTAINING BLOCK TO END OF `return` EXPRESSION
167 /*    :                  */             // If the expression includes lazy booleans, nest calls to `__incr_cov()`.
168 /*    :   -              */             Red => {
169 /*    :   ┃              */                 __incr_cov(to!("end of matched Red"));
170 /*    :   ┃              */                 println!("roses");
171 /*    :   -              */             }
172 /*    :   -              */             Green => {
173 /*    :   ┃              */                 __incr_cov(to!("just before next branch: after `if spidey > goblin`"));
174 /*    :   ┃              */                 let spidey = 100;
175 /*    :   ┃              */                 let goblin = 50;
176 /*    :   ┃              */                 // if spidey > goblin {__incr_cov(from!(""),{
177 /*    :   ┃              */                 //     println!("what ev");
178 /*    :   ┃              */                 // })}
179 /*    :   ┃              */                 // ACTUALLY, WRAPPING THE ENTIRE IF BLOCK IN `__incr_cov` IS NOT A GREAT GENERAL RULE.
180 /*    :   ┃              */                 // JUST INSERTING A `return`, `break`, or `continue` IN THAT BLOCK (without an intermediate condition)
181 /*    :   ┃              */                 // MAKES THE `__incr_cov()` CALL UNREACHABLE!
182 /*    :   ┃              */                 // MY ORIGINAL SOLUTION WORKS BETTER (WRAP LAST EXPRESSION OR AFTER LAST SEMICOLON STATEMENT IN BLOCK)
183 /*    :   ┃              */                 // UNLESS THE EXPRESSION IS NOT A BLOCK.
184 /*    :   ┃   -          */                 if spidey > goblin {
185 /*    :   :   ┃          */                     __incr_cov(to!("end of if block, if no earlier branch in this scope"));
186 /*    :   :   ┃          */                     println!("spidey beats goblin");
187 /*    :   :   ┃          */
188 /*    :   ┃   -          */                 } else if {
189 /*    :   :   :          */                     // Make sure we can't compute the coverage count here.
190 /*    :   :   :          */                     // We know the expression executed if the previous if block DID NOT
191 /*    :   :   :          */                     // execute, and either this `else if` block does execute OR any subsequent
192 /*    :   :   :          */                     // `else if` or `else` blocks execute, OR none of the blocks in the
193 /*    :   :   :          */                     // `if`, `else if` or `else` blocks execute.
194 /*    :   :   :          */                     // `if`, `else if` or `else` blocks execute.
195 /*    :   :   ┃          */                     __incr_cov(to!("end of `else if spidey == goblin` expression"));
196 /*    :   :   ┃          */                     spidey == goblin
197 /*    :   ┃   -          */                 } {
198 /*    :   :   ┃          */                     __incr_cov(to!("end of if block, if no earlier branch in this scope"));
199 /*    :   :   ┃          */                     // COVERAGE NOTE: Do we mark only the expression span (that may be trivial, as in this case),
200 /*    :   :   ┃          */                     // or associate it with the outer block, similar to how the `if` expression is associated with
201 /*    :   :   ┃          */                     // the outer block? (Although it is a continuation, in a sense, it is discontiguous in this case,
202 /*    :   :   ┃          */                     // so I think simpler to just make it its own coverage region.)
203 /*    :   :   ┃          */                     println!("it's a draw");
204 /*    :   :   ┃          */
205 /*    :   ┃   -   -   -  */                 } else if {
206 /*    :   :   ┃          */                         __incr_cov(to!("end of `if true`"));
207 /*    :   ┃   -   -   -  */                         if true {
208 /*    :   :       :   ┃  */                             __incr_cov(to!("end of `return Ok(())`"));
209 /*  ┏-:---:-------:---<  */                             return Ok(());
210 /*  V :   :       ┃   -  */                         } else {
211 /*    :   :       :   ┃  */                             // __incr_cov(to!("end of else block"));
212 /*    :   :       :   ┃  */                             // computed counter expression
213 /*    :   :       :   ┃  */                             false
214 /*    :   :       :   -  */                         }
215 /*    :   :   -   -   -  */                     } {
216 /*    :   :   ┃          */                     __incr_cov(to!("end of if block"));
217 /*    :   :   ┃          */                     println!("wierd science");
218 /*    :   ┃   -          */                 } else {
219 /*    :   :   ┃          */                     // __incr_cov(to!("end of `return Ok(())"));
220 /*    :   :   ┃          */                     // counter expression: (start of Green match arm) - (if spidey > goblin) - (previous `} else if {`)
221 /*    :   :   ┃          */                     println!("goblin wins");
222 /*  ┏-:---:---<          */                     return Ok(()); // THIS COUNTS LAST STATEMENT IN `else` BLOCK
223 /*  V :   :   :          */                     // COVERAGE NOTE: When counting the span for `return`,
224 /*    :   :   :          */                     // `break`, or `continue`, also report the outer spans
225 /*    :   :   :          */                     // got this far--including this `else` block. Record
226 /*    :   :   :          */                     // The start positions for those outer blocks, but:
227 /*    :   :   :          */                     // * For the block containing the `return`, `break`, or
228 /*    :   :   :          */                     //   `continue`, end report the end position is the
229 /*    :   :   :          */                     //   start of the `return` span (or 1 char before it).
230 /*    :   :   :          */                     // * Anything else?
231 /*    :   ┃   -          */                 }
232 /*    :   :              */                 // __incr_cov(to!("end of matched Green"));
233 /*    :   :              */                 //  // DO NOT COUNT HERE IF NO STATEMENTS AFTER LAST `if` or `match`
234 /*    :   -              */             },
235 /*    :   -              */             Blue => {
236 /*    :   ┃              */                 __incr_cov(to!("end of matched Blue"));
237 /*    :   ┃              */                 println!("violets");
238 /*    :   -              */             }
239 /*    ┃                  */         }
240 /*    ┃                  */         __incr_cov(to!("just before next branch: after `if condition1` (HIR: 'match condition1')"));
241 /*    ┃                  */
242 /*    ┃                  */         let condition1 = true;
243 /*    ┃                  */         let condition2 = false;
244 /*    ┃                  */         let condition3 = true;
245 /*    ┃                  */
246 /*    ┃                  */         println!("Called `various()` for TestStruct with field={}", self.field);
247 /*    ┃                  */
248 /*    ┃   -              */         if condition1 {
249 /*    :   ┃              */             println!("before while loop");
250 /*    :   ┃              */             let mut countdown = 10;
251 /*    :   ┃              */              // Must increment before repeated while text expression
252 /*    :   :   I          */             while  countdown > 0 { // span is just the while test expression
253 /*    :   :   ┃          */                 println!("top of `while` loop");
254 /*    :   :   ┃          */                 countdown -= 1;
255 /*    :   :   ┃          */                 //  // Counter not needed, but span is computed as "while test" minus "block start"
256 /*    :   :   ┃          */                                                        // If test expression is 11, and the outer block runs only once, 11-1 = 10
257 /*    :   ┃   -          */             }
258 /*    :   ┃              */             println!("before for loop");
259 /*    :   ┃   -          */             for index in 0..10 {
260 /*    :   :   ┃          */                 println!("top of `for` loop");
261 /*    :   :   ┃   -      */                 if index == 8 {
262 /*    :   :   :   ┃      */                     println!("before break");
263 /*    :   :   :   ┃      */                     // note the following is not legal here:
264 /*    :   :   :   ┃      */                     //   "can only break with a value inside `loop` or breakable block"
265 /*    :   :   :   ┃      */                     // break
266 /*    :   :   :   ┃      */
267 /*    :   : ┏-----<      */                     break;
268 /*    :   : V :   :      */
269 /*    :   :   :   :      */                     // FIXME(richkadel): add examples with loop labels, breaking out of inner and outer loop to outer loop label, with expression.
270 /*    :   :   :   :      */                     // May want to record both the span and the start position after the broken out block depdnding on label
271 /*    :   :   ┃   -      */                 }
272 /*    :   :   ┃          */                 println!("after `break` test");
273 /*    :   :   ┃   -      */                 if condition2 {
274 /*  ┏-:---:---:---<      */                     return Ok(());
275 /*  V :   :   ┃   -      */                 }
276 /*    :   :   ┃          */
277 /*    :   :   ┃          */                 // BECAUSE THE PREVIOUS COVERAGE REGION HAS A `return`, THEN
278 /*    :   :   ┃          */                 // IF PREVIOUS COVERAGE REGION IS NOT COUNTED THEN OUTER REGION REACHED HERE.
279 /*    :   :   ┃          */                 // ADD A COVERAGE REGION FOR THE SPAN FROM JUST AFTER PREVIOUS REGION TO END
280 /*    :   :   ┃          */                 // OF OUTER SPAN, THEN TRUNCATE TO NEXT REGION NOT REACHED.
281 /*    :   :   ┃   -      */                 if index % 3 == 2 { // NO __incr_cov() HERE BECAUSE NO STATEMENTS BETWEEN LAST CONDITIONAL BLOCK AND START OF THIS ONE
282 /*    :   : Λ :   ┃      */
283 /*    :   : ┗-----<      */                     continue;
284 /*    :   :   ┃   -      */                 }
285 /*    :   :   ┃          */                 println!("after `continue` test");
286 /*    :   :   ┃          */                 // maybe add a runtime flag for a possible `return` here?
287 /*    :   :   ┃          */
288 /*    :   ┃   -          */             }
289 /*    :   ┃              */             println!("after for loop");
290 /*    :   ┃              */             let result = if { // START OF NEW CONDITIONAL EXPRESSION. NEXT "GUARANTEED" COUNTER SHOULD COUNT FROM END OF LAST CONDITIONAL EXPRESSION
291 /*    :   ┃              */                               // A "GUARANTEED" COUNTER CALL IS ONE THAT WILL BE CALLED REGARDLESS OF OTHER CONDITIONS. THIS INCLUDES:
292 /*    :   ┃              */                               //   * A CONDITIONAL EXPRESSION THAT IS NOT A BLOCK (OR ANOTHER CONDITIONAL STATEMENT, WHICH WOULD CONTAIN A BLOCK)
293 /*    :   ┃              */                               //   * OR IF THE NEXT CONDITIONAL EXPRESSION IS A BLOCK OR CONDITIONAL STATEMENT, THEN THE FIRST "GUARANTEED" COUNTER IN THAT BLOCK
294 /*    :   ┃              */                               //   * END OF BLOCK IF THE BLOCK DOES NOT HAVE INNER CONDITIONAL EXPRESSIONS
295 /*    :   ┃              */                               //   * BRANCHING STATEMENTS (`return`, `break`, `continue`) BY EITHER WRAPPING THE BRANCH STATEMENT NON-BLOCK EXPRESSION,
296 /*    :   ┃              */                               //     OR PREPENDING A COUNTER WITH EMPTY TUPLE IF NO EXPRESSION, OR IF EXPRESSION IS A BLOCK, THEN THE NEXT "GUARANTEED"
297 /*    :   ┃              */                               //     COUNTER CALL WITHIN THAT BLOCK.
298 /*    :   ┃              */                               //   BASICALLY, CARRY THE START OF COVERAGE SPAN FORWARD UNTIL THE GUARANTEED COUNTER IS FOUND
299 /*    :   ┃              */                 println!("after result = if ...");
300 /*    :   ┃       -      */                 if condition2 {
301 /*    :   :       ┃      */                     println!("before first return");
302 /*  ┏-:---:-------<      */                     return Ok(());
303 /*  V :   :       -      */                 } else if condition3 {
304 /*    :   :       ┃      */                     // THE ABOVE COUNTER IS _NOT_ REALLY NECESSARY IF EXPRESSION IS GUARANTEED TO EXECUTE.
305 /*    :   :       ┃      */                     // IF WE GET COUNTER IN `else if` BLOCK WE COVERED EXPRESSION.
306 /*    :   :       ┃      */                     // IF WE GET TO ANY REMAINING `else` or `else if` BLOCK WE KNOW WE EVALUATED THIS CONDITION
307 /*    :   :       ┃      */                     // AND ALL OTHERS UP TO THE EXECUTED BLOCK. BUT THE SPAN WOULD HAVE "HOLES" FOR UNEXECUTED BLOCKS.
308 /*    :   :       ┃      */                     println!("not second return");
309 /*  ┏-:---:-------<      */                     return Ok(());
310 /*  V :   :       -      */                 } else {
311 /*    :   :       ┃      */                     println!("not returning");
312 /*    :   :       ┃      */                     false
313 /*    :   :       -      */                 }
314 /*    :   ┃              */                 // NO COUNTER HERE BECAUSE NO STATEMENTS AFTER CONDITIONAL BLOCK
315 /*    :   ┃   -          */             } {
316 /*    :   :   ┃          */                 println!("branched condition returned true");
317 /*    :   :   ┃          */                 Ok(())
318 /*    :   ┃   -          */             } else if self.call_closure(
319 /*    :   :       -      */                     |closure_param|
320 /*    :   :       ┃   -  */                         if condition3 {
321 /*    :   :       :   ┃  */                             println!("in closure, captured condition said to print the param {}", closure_param);
322 /*    :   :       :   ┃  */                             false
323 /*    :   :       ┃   -  */                         } else {
324 /*    :   :       :   ┃  */                             println!("in closure, captured condition was false");
325 /*    :   :       :   ┃  */                             true
326 /*    :   :       ┃   -  */                         }
327 /*    :   :       -      */
328 /*    :   :   -          */                 ) {
329 /*    :   :   ┃          */                 println!("closure returned true");
330 /*    :   :   ┃          */                 Err(Error::new(ErrorKind::Other, "Result is error if closure returned true"))
331 /*    :   ┃   -          */             } else {
332 /*    :   :   ┃          */                 println!("closure returned false");
333 /*    :   :   ┃          */                 Err(Error::new(ErrorKind::Other, "Result is error if closure returned false"))
334 /*    :   ┃   -          */             };
335 /*    :   ┃              */             println!("bottom of function might be skipped if early `return`");
336 /*    :   ┃              */             result
337 /*    ┃   -              */         } else {
338 /*    :   ┃              */             println!("skipping everything in `various()`");
339 /*    :   ┃              */             Ok(())
340 /*    ┃   -              */         }
341 /*    ┃   -              */         // 0 // DO NOT COUNT IF NO STATEMENTS AFTER CONDITIONAL BLOCK. ALL COVERAGE IS ALREADY COUNTED
342 /*    -                  */     }
343 /*                       */ }
344 /*                       */
345 /*    -                  */ fn main() -> Result<(), std::io::Error> {
346 /*    ┃                  */     //let mut status: u8 = 2;
347 /*    ┃                  */     let mut status: u8 = 1;
348 /*    :       -          */     let result = if status < 2 &&
349 /*    :       ┃          */             {
350 /*    :       ┃          */                 status -= 1;
351 /*    :       ┃          */                 status == 0
352 /*    :   -   -          */             } {
353 /*    :   ┃              */         let test_struct = TestStruct::new_with_value(100);
354 /*    :   ┃              */         let _ = test_struct.various();
355 /*  ┏-:---<              */         return __incr_cov_and_report(from!(""),Err(Error::new(ErrorKind::Other, format!("Error status {}", status))))
356 /*  V :   -              */     } else {
357 /*    :   ┃              */         let test_struct = TestStruct::new();
358 /*    :   ┃              */         test_struct.various()
359 /*    :   -              */     };
360 /*    ┃                  */     println!("done");
361 /*    ┃                  */     __incr_cov_and_report(from!(""),result) // function-scoped counter index = 0
362 /*    -                  */ }