1pub use super::*;
21
22#[macro_export]
24macro_rules! whitelist {
25 ($acc:ident) => {
26 frame_benchmarking::benchmarking::add_to_whitelist(
27 frame_system::Account::<T>::hashed_key_for(&$acc).into(),
28 );
29 };
30}
31
32#[macro_export]
172macro_rules! benchmarks {
173 (
174 $( $rest:tt )*
175 ) => {
176 $crate::benchmarks_iter!(
177 { }
178 { }
179 { }
180 ( )
181 ( )
182 ( )
183 ( )
184 $( $rest )*
185 );
186 }
187}
188
189#[macro_export]
193macro_rules! benchmarks_instance {
194 (
195 $( $rest:tt )*
196 ) => {
197 $crate::benchmarks_iter!(
198 { }
199 { I: Instance }
200 { }
201 ( )
202 ( )
203 ( )
204 ( )
205 $( $rest )*
206 );
207 }
208}
209
210#[macro_export]
214macro_rules! benchmarks_instance_pallet {
215 (
216 $( $rest:tt )*
217 ) => {
218 $crate::benchmarks_iter!(
219 { }
220 { I: 'static }
221 { }
222 ( )
223 ( )
224 ( )
225 ( )
226 $( $rest )*
227 );
228 }
229}
230
231#[macro_export]
232#[doc(hidden)]
233macro_rules! benchmarks_iter {
234 (
237 { }
238 { $( $instance:ident: $instance_bound:tt )? }
239 { $( $where_clause:tt )* }
240 ( $( $names:tt )* )
241 ( $( $names_extra:tt )* )
242 ( $( $names_skip_meta:tt )* )
243 ( $( $pov_name:ident: $( $storage:path = $pov_mode:ident )*; )* )
244 impl_benchmark_test_suite!(
245 $bench_module:ident,
246 $new_test_ext:expr,
247 $test:path
248 $(, $( $args:tt )* )?);
249 $( $rest:tt )*
250 ) => {
251 $crate::benchmarks_iter! {
252 { $bench_module, $new_test_ext, $test $(, $( $args )* )? }
253 { $( $instance: $instance_bound )? }
254 { $( $where_clause )* }
255 ( $( $names )* )
256 ( $( $names_extra )* )
257 ( $( $names_skip_meta )* )
258 ( $( $pov_name: $( $storage = $pov_mode )*; )* )
259 $( $rest )*
260 }
261 };
262 (
264 { }
265 { $( $instance:ident: $instance_bound:tt )? }
266 { $( $where_clause:tt )* }
267 ( $( $names:tt )* )
268 ( $( $names_extra:tt )* )
269 ( $( $names_skip_meta:tt )* )
270 ( $( $pov_name:ident: $( $storage:path = $pov_mode:ident )*; )* )
271 impl_benchmark_test_suite!(
272 $bench_module:ident,
273 $new_test_ext:expr,
274 $test:path
275 $(, $( $args:tt )* )?)
276 $( $rest:tt )*
277 ) => {
278 $crate::benchmarks_iter! {
279 { $bench_module, $new_test_ext, $test $(, $( $args )* )? }
280 { $( $instance: $instance_bound )? }
281 { $( $where_clause )* }
282 ( $( $names )* )
283 ( $( $names_extra )* )
284 ( $( $names_skip_meta )* )
285 ( $( $pov_name: $( $storage = $pov_mode )*; )* )
286 $( $rest )*
287 }
288 };
289 (
291 { $($bench_module:ident, $new_test_ext:expr, $test:path $(, $( $args:tt )* )?)? }
292 { $( $instance:ident: $instance_bound:tt )? }
293 { $( $where_clause:tt )* }
294 ( $( $names:tt )* )
295 ( $( $names_extra:tt )* )
296 ( $( $names_skip_meta:tt )* )
297 ( $( $pov_name:ident: $( $storage:path = $pov_mode:ident )*; )* )
298 where_clause { where $( $where_bound:tt )* }
299 $( $rest:tt )*
300 ) => {
301 $crate::benchmarks_iter! {
302 { $($bench_module, $new_test_ext, $test $(, $( $args )* )?)? }
303 { $( $instance: $instance_bound)? }
304 { $( $where_bound )* }
305 ( $( $names )* )
306 ( $( $names_extra )* )
307 ( $( $names_skip_meta )* )
308 ( $( $pov_name: $( $storage = $pov_mode )*; )* )
309 $( $rest )*
310 }
311 };
312 (
314 { $($bench_module:ident, $new_test_ext:expr, $test:path $(, $( $args:tt )* )?)? }
315 { $( $instance:ident: $instance_bound:tt )? }
316 { $( $where_clause:tt )* }
317 ( $( $names:tt )* )
318 ( $( $names_extra:tt )* )
319 ( $( $names_skip_meta:tt )* )
320 ( $( $pov_name:ident: $( $storage:path = $pov_mode:ident )*; )* )
321 #[skip_meta]
322 $( #[ $($attributes:tt)+ ] )*
323 $name:ident
324 $( $rest:tt )*
325 ) => {
326 $crate::benchmarks_iter! {
327 { $($bench_module, $new_test_ext, $test $(, $( $args )* )?)? }
328 { $( $instance: $instance_bound )? }
329 { $( $where_clause )* }
330 ( $( $names )* )
331 ( $( $names_extra )* )
332 ( $( $names_skip_meta )* $name )
333 ( $( $pov_name: $( $storage = $pov_mode )*; )* )
334 $( #[ $( $attributes )+ ] )*
335 $name
336 $( $rest )*
337 }
338 };
339 (
341 { $($bench_module:ident, $new_test_ext:expr, $test:path $(, $( $args:tt )* )?)? }
342 { $( $instance:ident: $instance_bound:tt )? }
343 { $( $where_clause:tt )* }
344 ( $( $names:tt )* )
345 ( $( $names_extra:tt )* )
346 ( $( $names_skip_meta:tt )* )
347 ( $( $pov_name:ident: $( $storage:path = $pov_mode:ident )*; )* )
348 #[extra]
349 $( #[ $($attributes:tt)+ ] )*
350 $name:ident
351 $( $rest:tt )*
352 ) => {
353 $crate::benchmarks_iter! {
354 { $($bench_module, $new_test_ext, $test $(, $( $args )* )?)? }
355 { $( $instance: $instance_bound )? }
356 { $( $where_clause )* }
357 ( $( $names )* )
358 ( $( $names_extra )* $name )
359 ( $( $names_skip_meta )* )
360 ( $( $pov_name: $( $storage = $pov_mode )*; )* )
361 $( #[ $( $attributes )+ ] )*
362 $name
363 $( $rest )*
364 }
365 };
366 (
368 { $($bench_module:ident, $new_test_ext:expr, $test:path $(, $( $args:tt )* )?)? }
369 { $( $instance:ident: $instance_bound:tt )? }
370 { $( $where_clause:tt )* }
371 ( $( $names:tt )* )
372 ( $( $names_extra:tt )* )
373 ( $( $names_skip_meta:tt )* )
374 ( $( $old_pov_name:ident: $( $old_storage:path = $old_pov_mode:ident )*; )* )
375 #[pov_mode = $mode:ident $( { $( $storage:path: $pov_mode:ident )* } )?]
376 $( #[ $($attributes:tt)+ ] )*
377 $name:ident
378 $( $rest:tt )*
379 ) => {
380 $crate::benchmarks_iter! {
381 { $($bench_module, $new_test_ext, $test $(, $( $args )* )?)? }
382 { $( $instance: $instance_bound )? }
383 { $( $where_clause )* }
384 ( $( $names )* )
385 ( $( $names_extra )* )
386 ( $( $names_skip_meta )* )
387 ( $name: ALL = $mode $($( $storage = $pov_mode )*)?; $( $old_pov_name: $( $old_storage = $old_pov_mode )*; )* )
388 $( #[ $( $attributes )+ ] )*
389 $name
390 $( $rest )*
391 }
392 };
393 (
395 { $($bench_module:ident, $new_test_ext:expr, $test:path $(, $( $args:tt )* )?)? }
396 { $( $instance:ident: $instance_bound:tt )? }
397 { $( $where_clause:tt )* }
398 ( $( $names:tt )* ) ( $( $names_extra:tt )* )
400 ( $( $names_skip_meta:tt )* )
401 ( $( $pov_name:ident: $( $storage:path = $pov_mode:ident )*; )* )
402 $name:ident { $( $code:tt )* }: _ $(< $origin_type:ty>)? ( $origin:expr $( , $arg:expr )* )
403 verify $postcode:block
404 $( $rest:tt )*
405 ) => {
406 $crate::benchmarks_iter! {
407 { $($bench_module, $new_test_ext, $test $(, $( $args )* )?)? }
408 { $( $instance: $instance_bound )? }
409 { $( $where_clause )* }
410 ( $( $names )* )
411 ( $( $names_extra )* )
412 ( $( $names_skip_meta )* )
413 ( $( $pov_name: $( $storage = $pov_mode )*; )* )
414 $name { $( $code )* }: $name $(< $origin_type >)? ( $origin $( , $arg )* )
415 verify $postcode
416 $( $rest )*
417 }
418 };
419 (
421 { $($bench_module:ident, $new_test_ext:expr, $test:path $(, $( $args:tt )* )?)? }
422 { $( $instance:ident: $instance_bound:tt )? }
423 { $( $where_clause:tt )* }
424 ( $( $names:tt )* )
425 ( $( $names_extra:tt )* )
426 ( $( $names_skip_meta:tt )* )
427 ( $( $pov_name:ident: $( $storage:path = $pov_mode:ident )*; )* )
428 $name:ident { $( $code:tt )* }: $dispatch:ident $(<$origin_type:ty>)? ( $origin:expr $( , $arg:expr )* )
429 verify $postcode:block
430 $( $rest:tt )*
431 ) => {
432 $crate::__private::paste::paste! {
433 $crate::benchmarks_iter! {
434 { $($bench_module, $new_test_ext, $test $(, $( $args )* )?)? }
435 { $( $instance: $instance_bound )? }
436 { $( $where_clause )* }
437 ( $( $names )* )
438 ( $( $names_extra )* )
439 ( $( $names_skip_meta )* )
440 ( $( $pov_name: $( $storage = $pov_mode )*; )* )
441 $name {
442 $( $code )*
443 let __call = Call::<
444 T
445 $( , $instance )?
446 >:: [< new_call_variant_ $dispatch >] (
447 $($arg),*
448 );
449 let __benchmarked_call_encoded = $crate::__private::codec::Encode::encode(
450 &__call
451 );
452 }: {
453 let __call_decoded = <
454 Call<T $(, $instance )?>
455 as $crate::__private::codec::Decode
456 >::decode(&mut &__benchmarked_call_encoded[..])
457 .expect("call is encoded above, encoding must be correct");
458 let __origin = $crate::to_origin!($origin $(, $origin_type)?);
459 <Call<T $(, $instance)? > as $crate::__private::traits::UnfilteredDispatchable
460 >::dispatch_bypass_filter(__call_decoded, __origin)?;
461 }
462 verify $postcode
463 $( $rest )*
464 }
465 }
466 };
467 (
469 { $($bench_module:ident, $new_test_ext:expr, $test:path $(, $( $args:tt )* )?)? }
470 { $( $instance:ident: $instance_bound:tt )? }
471 { $( $where_clause:tt )* }
472 ( $( $names:tt )* )
473 ( $( $names_extra:tt )* )
474 ( $( $names_skip_meta:tt )* )
475 ( $( $pov_name:ident: $( $storage:path = $pov_mode:ident )*; )* )
476 $name:ident { $( $code:tt )* }: $eval:block
477 verify $postcode:block
478 $( $rest:tt )*
479 ) => {
480 $crate::benchmark_backend! {
481 { $( $instance: $instance_bound )? }
482 $name
483 { $( $where_clause )* }
484 { }
485 { $eval }
486 { $( $code )* }
487 $postcode
488 }
489
490 #[cfg(test)]
491 $crate::impl_benchmark_test!(
492 { $( $where_clause )* }
493 { $( $instance: $instance_bound )? }
494 $name
495 );
496
497 $crate::benchmarks_iter!(
498 { $($bench_module, $new_test_ext, $test $(, $( $args )* )?)? }
499 { $( $instance: $instance_bound )? }
500 { $( $where_clause )* }
501 ( $( $names )* { $( $instance )? } $name )
502 ( $( $names_extra )* )
503 ( $( $names_skip_meta )* )
504 ( $( $pov_name: $( $storage = $pov_mode )*; )* )
505 $( $rest )*
506 );
507 };
508 (
510 { $bench_module:ident, $new_test_ext:expr, $test:path $(, $( $args:tt )* )? }
511 { $( $instance:ident: $instance_bound:tt )? }
512 { $( $where_clause:tt )* }
513 ( $( $names:tt )* )
514 ( $( $names_extra:tt )* )
515 ( $( $names_skip_meta:tt )* )
516 ( $( $pov_name:ident: $( $storage:path = $pov_mode:ident )*; )* )
517 ) => {
518 $crate::selected_benchmark!(
519 { $( $where_clause)* }
520 { $( $instance: $instance_bound )? }
521 $( $names )*
522 );
523 $crate::impl_benchmark!(
524 { $( $where_clause )* }
525 { $( $instance: $instance_bound )? }
526 ( $( $names )* )
527 ( $( $names_extra ),* )
528 ( $( $names_skip_meta ),* )
529 ( $( $pov_name: $( $storage = $pov_mode )*; )* )
530 );
531 $crate::impl_test_function!(
532 ( $( $names )* )
533 ( $( $names_extra )* )
534 ( $( $names_skip_meta )* )
535 $bench_module,
536 $new_test_ext,
537 $test
538 $(, $( $args )* )?
539 );
540 };
541 (
543 { }
544 { $( $instance:ident: $instance_bound:tt )? }
545 { $( $where_clause:tt )* }
546 ( $( $names:tt )* )
547 ( $( $names_extra:tt )* )
548 ( $( $names_skip_meta:tt )* )
549 ( $( $pov_name:ident: $( $storage:path = $pov_mode:ident )*; )* )
550 ) => {
551 $crate::selected_benchmark!(
552 { $( $where_clause)* }
553 { $( $instance: $instance_bound )? }
554 $( $names )*
555 );
556 $crate::impl_benchmark!(
557 { $( $where_clause )* }
558 { $( $instance: $instance_bound )? }
559 ( $( $names )* )
560 ( $( $names_extra ),* )
561 ( $( $names_skip_meta ),* )
562 ( $( $pov_name: $( $storage = $pov_mode )*; )* )
563 );
564 };
565 (
567 { $($bench_module:ident, $new_test_ext:expr, $test:path $(, $( $args:tt )* )?)? }
568 { $( $instance:ident: $instance_bound:tt )? }
569 { $( $where_clause:tt )* }
570 ( $( $names:tt )* )
571 ( $( $names_extra:tt )* )
572 ( $( $names_skip_meta:tt )* )
573 ( $( $pov_name:ident: $( $storage:path = $pov_mode:ident )*; )* )
574 $name:ident { $( $code:tt )* }: _ $(<$origin_type:ty>)? ( $origin:expr $( , $arg:expr )* )
575 $( $rest:tt )*
576 ) => {
577 $crate::benchmarks_iter! {
578 { $($bench_module, $new_test_ext, $test $(, $( $args )* )?)? }
579 { $( $instance: $instance_bound )? }
580 { $( $where_clause )* }
581 ( $( $names )* )
582 ( $( $names_extra )* )
583 ( $( $names_skip_meta )* )
584 ( $( $pov_name: $( $storage = $pov_mode )*; )* )
585 $name { $( $code )* }: _ $(<$origin_type>)? ( $origin $( , $arg )* )
586 verify { }
587 $( $rest )*
588 }
589 };
590 (
592 { $($bench_module:ident, $new_test_ext:expr, $test:path $(, $( $args:tt )* )?)? }
593 { $( $instance:ident: $instance_bound:tt )? }
594 { $( $where_clause:tt )* }
595 ( $( $names:tt )* )
596 ( $( $names_extra:tt )* )
597 ( $( $names_skip_meta:tt )* )
598 ( $( $pov_name:ident: $( $storage:path = $pov_mode:ident )*; )* )
599 $name:ident { $( $code:tt )* }: $dispatch:ident $(<$origin_type:ty>)? ( $origin:expr $( , $arg:expr )* )
600 $( $rest:tt )*
601 ) => {
602 $crate::benchmarks_iter! {
603 { $($bench_module, $new_test_ext, $test $(, $( $args )* )?)? }
604 { $( $instance: $instance_bound )? }
605 { $( $where_clause )* }
606 ( $( $names )* )
607 ( $( $names_extra )* )
608 ( $( $names_skip_meta )* )
609 ( $( $pov_name: $( $storage = $pov_mode )*; )* )
610 $name { $( $code )* }: $dispatch $(<$origin_type>)? ( $origin $( , $arg )* )
611 verify { }
612 $( $rest )*
613 }
614 };
615 (
617 { $($bench_module:ident, $new_test_ext:expr, $test:path $(, $( $args:tt )* )?)? }
618 { $( $instance:ident: $instance_bound:tt )? }
619 { $( $where_clause:tt )* }
620 ( $( $names:tt )* )
621 ( $( $names_extra:tt )* )
622 ( $( $names_skip_meta:tt )* )
623 ( $( $pov_name:ident: $( $storage:path = $pov_mode:ident )*; )* )
624 $name:ident { $( $code:tt )* }: $(<$origin_type:ty>)? $eval:block
625 $( $rest:tt )*
626 ) => {
627 $crate::benchmarks_iter!(
628 { $($bench_module, $new_test_ext, $test $(, $( $args )* )?)? }
629 { $( $instance: $instance_bound )? }
630 { $( $where_clause )* }
631 ( $( $names )* )
632 ( $( $names_extra )* )
633 ( $( $names_skip_meta )* )
634 ( $( $pov_name: $( $storage = $pov_mode )*; )* )
635 $name { $( $code )* }: $(<$origin_type>)? $eval
636 verify { }
637 $( $rest )*
638 );
639 };
640}
641
642#[macro_export]
643#[doc(hidden)]
644macro_rules! to_origin {
645 ($origin:expr) => {
646 $origin.into()
647 };
648 ($origin:expr, $origin_type:ty) => {
649 <<T as frame_system::Config>::RuntimeOrigin as From<$origin_type>>::from($origin)
650 };
651}
652
653#[macro_export]
654#[doc(hidden)]
655macro_rules! benchmark_backend {
656 (
658 { $( $instance:ident: $instance_bound:tt )? }
659 $name:ident
660 { $( $where_clause:tt )* }
661 { $( PRE { $( $pre_parsed:tt )* } )* }
662 { $eval:block }
663 {
664 let $pre_id:tt $( : $pre_ty:ty )? = $pre_ex:expr;
665 $( $rest:tt )*
666 }
667 $postcode:block
668 ) => {
669 $crate::benchmark_backend! {
670 { $( $instance: $instance_bound )? }
671 $name
672 { $( $where_clause )* }
673 {
674 $( PRE { $( $pre_parsed )* } )*
675 PRE { $pre_id , $( $pre_ty , )? $pre_ex }
676 }
677 { $eval }
678 { $( $rest )* }
679 $postcode
680 }
681 };
682 (
683 { $( $instance:ident: $instance_bound:tt )? }
684 $name:ident
685 { $( $where_clause:tt )* }
686 { $( $parsed:tt )* }
687 { $eval:block }
688 {
689 let $param:ident in ( $param_from:expr ) .. $param_to:expr => $param_instancer:expr;
690 $( $rest:tt )*
691 }
692 $postcode:block
693 ) => {
694 $crate::benchmark_backend! {
695 { $( $instance: $instance_bound )? }
696 $name
697 { $( $where_clause )* }
698 {
699 $( $parsed )*
700 PARAM { $param , $param_from , $param_to , $param_instancer }
701 }
702 { $eval }
703 { $( $rest )* }
704 $postcode
705 }
706 };
707 (
709 { $( $instance:ident: $instance_bound:tt )? }
710 $name:ident
711 { $( $where_clause:tt )* }
712 { $( $parsed:tt )* }
713 { $eval:block }
714 {
715 let $param:ident in $param_from:tt .. $param_to:expr => $param_instancer:expr ;
716 $( $rest:tt )*
717 }
718 $postcode:block
719 ) => {
720 $crate::benchmark_backend! {
721 { $( $instance: $instance_bound )? }
722 $name
723 { $( $where_clause )* }
724 { $( $parsed )* }
725 { $eval }
726 {
727 let $param in ( $param_from ) .. $param_to => $param_instancer;
728 $( $rest )*
729 }
730 $postcode
731 }
732 };
733 (
735 { $( $instance:ident: $instance_bound:tt )? }
736 $name:ident
737 { $( $where_clause:tt )* }
738 { $( $parsed:tt )* }
739 { $eval:block }
740 {
741 let $param:ident in $param_from:tt .. $param_to:expr;
742 $( $rest:tt )*
743 }
744 $postcode:block
745 ) => {
746 $crate::benchmark_backend! {
747 { $( $instance: $instance_bound )? }
748 $name
749 { $( $where_clause )* }
750 { $( $parsed )* }
751 { $eval }
752 {
753 let $param in $param_from .. $param_to => ();
754 $( $rest )*
755 }
756 $postcode
757 }
758 };
759 (
761 { $( $instance:ident: $instance_bound:tt )? }
762 $name:ident
763 { $( $where_clause:tt )* }
764 {
765 $( PRE { $pre_id:tt , $( $pre_ty:ty , )? $pre_ex:expr } )*
766 $( PARAM { $param:ident , $param_from:expr , $param_to:expr , $param_instancer:expr } )*
767 }
768 { $eval:block }
769 { $( $post:tt )* }
770 $postcode:block
771 ) => {
772 #[allow(non_camel_case_types)]
773 struct $name;
774 #[allow(unused_variables)]
775 impl<T: Config $( <$instance>, $instance: $instance_bound )? >
776 $crate::BenchmarkingSetup<T $(, $instance)? > for $name
777 where $( $where_clause )*
778 {
779 fn components(&self) -> $crate::__private::Vec<($crate::BenchmarkParameter, u32, u32)> {
780 $crate::__private::vec! [
781 $(
782 ($crate::BenchmarkParameter::$param, $param_from, $param_to)
783 ),*
784 ]
785 }
786
787 fn instance(
788 &self,
789 recording: &mut impl $crate::Recording,
790 components: &[($crate::BenchmarkParameter, u32)],
791 verify: bool
792 ) -> Result<(), $crate::BenchmarkError> {
793 $(
794 let $param = components.iter()
796 .find(|&c| c.0 == $crate::BenchmarkParameter::$param)
797 .ok_or("Could not find component in benchmark preparation.")?
798 .1;
799 )*
800 $(
801 let $pre_id $( : $pre_ty )? = $pre_ex;
802 )*
803 $( $param_instancer ; )*
804 $( $post )*
805
806 recording.start();
807 $eval;
808 recording.stop();
809
810 if verify {
811 $postcode;
812 }
813 Ok(())
814 }
815 }
816 };
817}
818
819#[macro_export]
821#[doc(hidden)]
822macro_rules! impl_bench_case_tests {
823 (
824 { $module:ident, $new_test_exec:expr, $exec_name:ident, $test:path, $extra:expr }
825 { $( $names_extra:tt )* }
826 $( { $( $bench_inst:ident )? } $bench:ident )*
827 )
828 => {
829 $crate::impl_bench_name_tests!(
830 $module, $new_test_exec, $exec_name, $test, $extra,
831 { $( $names_extra )* },
832 $( { $bench } )+
833 );
834 }
835}
836
837#[macro_export]
839#[doc(hidden)]
840macro_rules! impl_bench_name_tests {
841 (
843 $module:ident, $new_test_exec:expr, $exec_name:ident, $test:path, $extra:expr,
844 { $( $names_extra:tt )* },
845 { $name:ident }
846 ) => {
847 $crate::__private::paste::paste! {
848 #[test]
849 fn [<bench_ $name>] () {
850 $new_test_exec.$exec_name(|| {
851 if !($extra) {
853 let disabled = $crate::__private::vec![ $( stringify!($names_extra).as_ref() ),* ];
854 if disabled.contains(&stringify!($name)) {
855 $crate::__private::log::debug!(
856 "extra benchmark skipped - {}",
857 stringify!($name),
858 );
859 return ();
860 }
861 }
862
863 match std::panic::catch_unwind(|| {
866 $module::<$test>::[< test_benchmark_ $name >] ()
867 }) {
868 Err(err) => {
869 panic!("{}: {:?}", stringify!($name), err);
870 },
871 Ok(Err(err)) => {
872 match err {
873 $crate::BenchmarkError::Stop(err) => {
874 panic!("{}: {:?}", stringify!($name), err);
875 },
876 $crate::BenchmarkError::Override(_) => {
877 $crate::__private::log::error!(
879 "benchmark error overridden - {}",
880 stringify!($name),
881 );
882 },
883 $crate::BenchmarkError::Skip => {
884 $crate::__private::log::debug!(
886 "benchmark skipped - {}",
887 stringify!($name),
888 );
889 },
890 $crate::BenchmarkError::Weightless => {
891 $crate::__private::log::debug!(
893 "benchmark weightless skipped - {}",
894 stringify!($name),
895 );
896 }
897 }
898 },
899 Ok(Ok(())) => (),
900 }
901 });
902 }
903 }
904 };
905 (
907 $module:ident, $new_test_exec:expr, $exec_name:ident, $test:path, $extra:expr,
908 { $( $names_extra:tt )* },
909 { $name:ident } $( { $rest:ident } )+
910 ) => {
911 $crate::impl_bench_name_tests!($module, $new_test_exec, $exec_name, $test, $extra,
913 { $( $names_extra )* }, { $name });
914 $crate::impl_bench_name_tests!($module, $new_test_exec, $exec_name, $test, $extra,
916 { $( $names_extra )* }, $( { $rest } )+);
917 };
918}
919
920#[macro_export]
935#[doc(hidden)]
936macro_rules! selected_benchmark {
937 (
938 { $( $where_clause:tt )* }
939 { $( $instance:ident: $instance_bound:tt )? }
940 $( { $( $bench_inst:ident )? } $bench:ident )*
941 ) => {
942 #[allow(non_camel_case_types)]
944 enum SelectedBenchmark {
945 $( $bench, )*
946 }
947
948 impl<T: Config $( <$instance>, $instance: $instance_bound )? >
950 $crate::BenchmarkingSetup<T $(, $instance )? > for SelectedBenchmark
951 where $( $where_clause )*
952 {
953 fn components(&self) -> $crate::__private::Vec<($crate::BenchmarkParameter, u32, u32)> {
954 match self {
955 $(
956 Self::$bench => <
957 $bench as $crate::BenchmarkingSetup<T $(, $bench_inst)? >
958 >::components(&$bench),
959 )*
960 }
961 }
962
963 fn instance(
964 &self,
965 recording: &mut impl $crate::Recording,
966 components: &[($crate::BenchmarkParameter, u32)],
967 verify: bool
968 ) -> Result<(), $crate::BenchmarkError> {
969 match self {
970 $(
971 Self::$bench => <
972 $bench as $crate::BenchmarkingSetup<T $(, $bench_inst)? >
973 >::instance(&$bench, recording, components, verify),
974 )*
975 }
976 }
977 }
978 };
979}
980
981#[macro_export]
982#[doc(hidden)]
983macro_rules! impl_benchmark {
984 (
985 { $( $where_clause:tt )* }
986 { $( $instance:ident: $instance_bound:tt )? }
987 ( $( { $( $name_inst:ident )? } $name:ident )* )
988 ( $( $name_extra:ident ),* )
989 ( $( $name_skip_meta:ident ),* )
990 ( $( $pov_name:ident: $( $storage:path = $pov_mode:ident )*; )* )
991 ) => {
992 #[cfg(any(feature = "runtime-benchmarks", test))]
994 impl<T: Config $(<$instance>, $instance: $instance_bound )? >
995 $crate::Benchmarking for Pallet<T $(, $instance)? >
996 where T: frame_system::Config, $( $where_clause )*
997 {
998 fn benchmarks(extra: bool) -> $crate::__private::Vec<$crate::BenchmarkMetadata> {
999 $($crate::validate_pov_mode!(
1000 $pov_name: $( $storage = $pov_mode )*;
1001 );)*
1002 let mut all_names = $crate::__private::vec![ $( stringify!($name).as_ref() ),* ];
1003 if !extra {
1004 let extra = [ $( stringify!($name_extra).as_ref() ),* ];
1005 all_names.retain(|x| !extra.contains(x));
1006 }
1007 let pov_modes: $crate::__private::Vec<($crate::__private::Vec<u8>, $crate::__private::Vec<($crate::__private::Vec<u8>, $crate::__private::Vec<u8>)>)> = $crate::__private::vec![
1008 $(
1009 (stringify!($pov_name).as_bytes().to_vec(),
1010 $crate::__private::vec![
1011 $( ( stringify!($storage).replace(" ", "").as_bytes().to_vec(),
1013 stringify!($pov_mode).as_bytes().to_vec() ), )*
1014 ]),
1015 )*
1016 ];
1017 all_names.into_iter().map(|benchmark| {
1018 let selected_benchmark = match benchmark {
1019 $( stringify!($name) => SelectedBenchmark::$name, )*
1020 _ => panic!("all benchmarks should be selectable"),
1021 };
1022 let name = benchmark.as_bytes().to_vec();
1023 let components = <
1024 SelectedBenchmark as $crate::BenchmarkingSetup<T $(, $instance)?>
1025 >::components(&selected_benchmark);
1026
1027 $crate::BenchmarkMetadata {
1028 name: name.clone(),
1029 components,
1030 pov_modes: pov_modes.iter().find(|p| p.0 == name).map(|p| p.1.clone()).unwrap_or_default(),
1031 }
1032 }).collect::<$crate::__private::Vec<_>>()
1033 }
1034
1035 fn run_benchmark(
1036 extrinsic: &[u8],
1037 c: &[($crate::BenchmarkParameter, u32)],
1038 whitelist: &[$crate::__private::TrackedStorageKey],
1039 verify: bool,
1040 internal_repeats: u32,
1041 ) -> Result<$crate::__private::Vec<$crate::BenchmarkResult>, $crate::BenchmarkError> {
1042 $crate::benchmarking::wipe_db();
1044 let extrinsic = $crate::__private::str::from_utf8(extrinsic)
1045 .map_err(|_| "`extrinsic` is not a valid utf8 string!")?;
1046 let selected_benchmark = match extrinsic {
1047 $( stringify!($name) => SelectedBenchmark::$name, )*
1048 _ => return Err("Could not find extrinsic.".into()),
1049 };
1050
1051 let mut whitelist = whitelist.to_vec();
1053 let whitelisted_caller_key =
1054 <frame_system::Account::<T> as $crate::__private::storage::StorageMap<_,_>>::hashed_key_for(
1055 $crate::whitelisted_caller::<T::AccountId>()
1056 );
1057 whitelist.push(whitelisted_caller_key.into());
1058 let transactional_layer_key = $crate::__private::TrackedStorageKey::new(
1060 $crate::__private::storage::transactional::TRANSACTION_LEVEL_KEY.into()
1061 );
1062 whitelist.push(transactional_layer_key);
1063 let extrinsic_index = $crate::__private::TrackedStorageKey::new(
1065 $crate::__private::well_known_keys::EXTRINSIC_INDEX.into()
1066 );
1067 whitelist.push(extrinsic_index);
1068 let intrablock_entropy = $crate::__private::TrackedStorageKey::new(
1070 $crate::__private::well_known_keys::INTRABLOCK_ENTROPY.into()
1071 );
1072 whitelist.push(intrablock_entropy);
1073
1074 $crate::benchmarking::set_whitelist(whitelist.clone());
1075
1076 let mut results: $crate::__private::Vec<$crate::BenchmarkResult> = $crate::__private::Vec::new();
1077 let on_before_start = || {
1078 if $crate::__private::Zero::is_zero(&frame_system::Pallet::<T>::block_number()) {
1080 frame_system::Pallet::<T>::set_block_number(1u32.into());
1081 }
1082
1083 $crate::benchmarking::commit_db();
1086
1087 for key in &whitelist {
1090 $crate::__private::storage::unhashed::get_raw(&key.key);
1091 }
1092
1093 $crate::benchmarking::reset_read_write_count();
1095 };
1096
1097 for _ in 0 .. internal_repeats.max(1) {
1099 $crate::__private::defer!($crate::benchmarking::wipe_db());
1101
1102 $crate::__private::log::trace!(
1104 target: "benchmark",
1105 "Start Benchmark: {} ({:?}) verify {}",
1106 extrinsic,
1107 c,
1108 verify
1109 );
1110
1111 let mut recording = $crate::BenchmarkRecording::new(&on_before_start);
1114 <SelectedBenchmark as $crate::BenchmarkingSetup<T $(, $instance)?>>::instance(&selected_benchmark, &mut recording, c, verify)?;
1115
1116 let elapsed_extrinsic = recording.elapsed_extrinsic().expect("elapsed time should be recorded");
1118 let diff_pov = recording.diff_pov().unwrap_or_default();
1119
1120 $crate::benchmarking::commit_db();
1122 $crate::__private::log::trace!(
1123 target: "benchmark",
1124 "End Benchmark: {} ns", elapsed_extrinsic
1125 );
1126 let read_write_count = $crate::benchmarking::read_write_count();
1127 $crate::__private::log::trace!(
1128 target: "benchmark",
1129 "Read/Write Count {:?}", read_write_count
1130 );
1131 $crate::__private::log::trace!(
1132 target: "benchmark",
1133 "Proof sizes: before {:?} after {:?} diff {}", recording.start_pov(), recording.end_pov(), &diff_pov
1134 );
1135
1136 let start_storage_root = $crate::current_time();
1138 $crate::__private::storage_root($crate::__private::StateVersion::V1);
1139 let finish_storage_root = $crate::current_time();
1140 let elapsed_storage_root = finish_storage_root - start_storage_root;
1141
1142 let skip_meta = [ $( stringify!($name_skip_meta).as_ref() ),* ];
1143 let read_and_written_keys = if skip_meta.contains(&extrinsic) {
1144 $crate::__private::vec![(b"Skipped Metadata".to_vec(), 0, 0, false)]
1145 } else {
1146 $crate::benchmarking::get_read_and_written_keys()
1147 };
1148
1149 results.push($crate::BenchmarkResult {
1150 components: c.to_vec(),
1151 extrinsic_time: elapsed_extrinsic,
1152 storage_root_time: elapsed_storage_root,
1153 reads: read_write_count.0,
1154 repeat_reads: read_write_count.1,
1155 writes: read_write_count.2,
1156 repeat_writes: read_write_count.3,
1157 proof_size: diff_pov,
1158 keys: read_and_written_keys,
1159 });
1160 }
1161
1162 return Ok(results);
1163 }
1164 }
1165
1166 #[cfg(test)]
1167 impl<T: Config $(<$instance>, $instance: $instance_bound )? >
1168 Pallet<T $(, $instance)? >
1169 where T: frame_system::Config, $( $where_clause )*
1170 {
1171 #[allow(unused)]
1181 fn test_bench_by_name(name: &[u8]) -> Result<(), $crate::BenchmarkError> {
1182 let name = $crate::__private::str::from_utf8(name)
1183 .map_err(|_| -> $crate::BenchmarkError { "`name` is not a valid utf8 string!".into() })?;
1184 match name {
1185 $( stringify!($name) => {
1186 $crate::__private::paste::paste! { Self::[< test_benchmark_ $name >]() }
1187 } )*
1188 _ => Err("Could not find test for requested benchmark.".into()),
1189 }
1190 }
1191 }
1192 };
1193}
1194
1195#[macro_export]
1201#[doc(hidden)]
1202macro_rules! impl_benchmark_test {
1203 (
1204 { $( $where_clause:tt )* }
1205 { $( $instance:ident: $instance_bound:tt )? }
1206 $name:ident
1207 ) => {
1208 $crate::__private::paste::item! {
1209 #[cfg(test)]
1210 impl<T: Config $(<$instance>, $instance: $instance_bound )? >
1211 Pallet<T $(, $instance)? >
1212 where T: frame_system::Config, $( $where_clause )*
1213 {
1214 #[allow(unused)]
1215 fn [<test_benchmark_ $name>] () -> Result<(), $crate::BenchmarkError> {
1216 let selected_benchmark = SelectedBenchmark::$name;
1217 let components = <
1218 SelectedBenchmark as $crate::BenchmarkingSetup<T, _>
1219 >::components(&selected_benchmark);
1220
1221 let execute_benchmark = |
1222 c: $crate::__private::Vec<($crate::BenchmarkParameter, u32)>
1223 | -> Result<(), $crate::BenchmarkError> {
1224 $crate::__private::defer!($crate::benchmarking::wipe_db());
1226
1227 let on_before_start = || {
1228 if $crate::__private::Zero::is_zero(&frame_system::Pallet::<T>::block_number()) {
1230 frame_system::Pallet::<T>::set_block_number(1u32.into());
1231 }
1232 };
1233
1234 <SelectedBenchmark as $crate::BenchmarkingSetup<T, _>>::test_instance(&selected_benchmark, &c, &on_before_start)
1236 };
1237
1238 if components.is_empty() {
1239 execute_benchmark(Default::default())?;
1240 } else {
1241 let num_values: u32 = if let Ok(ev) = std::env::var("VALUES_PER_COMPONENT") {
1242 ev.parse().map_err(|_| {
1243 $crate::BenchmarkError::Stop(
1244 "Could not parse env var `VALUES_PER_COMPONENT` as u32."
1245 )
1246 })?
1247 } else {
1248 6
1249 };
1250
1251 if num_values < 2 {
1252 return Err("`VALUES_PER_COMPONENT` must be at least 2".into());
1253 }
1254
1255 for (name, low, high) in components.clone().into_iter() {
1256 let mut values = $crate::__private::vec![low];
1261 let diff = (high - low).min(num_values - 1);
1262 let slope = (high - low) as f32 / diff as f32;
1263
1264 for i in 1..=diff {
1265 let value = ((low as f32 + slope * i as f32) as u32)
1266 .clamp(low, high);
1267 values.push(value);
1268 }
1269
1270 for component_value in values {
1271 let c: $crate::__private::Vec<($crate::BenchmarkParameter, u32)> = components
1273 .iter()
1274 .map(|(n, _, h)|
1275 if *n == name {
1276 (*n, component_value)
1277 } else {
1278 (*n, *h)
1279 }
1280 )
1281 .collect();
1282
1283 execute_benchmark(c)?;
1284 }
1285 }
1286 }
1287 Ok(())
1288 }
1289 }
1290 }
1291 };
1292}
1293
1294#[macro_export]
1435macro_rules! impl_benchmark_test_suite {
1436 (
1437 $bench_module:ident,
1438 $new_test_ext:expr,
1439 $test:path
1440 $(, $( $rest:tt )* )?
1441 ) => {
1442 $crate::impl_test_function!(
1443 ()
1444 ()
1445 ()
1446 $bench_module,
1447 $new_test_ext,
1448 $test
1449 $(, $( $rest )* )?
1450 );
1451 }
1452}
1453
1454#[macro_export]
1460macro_rules! validate_pov_mode {
1461 () => {};
1462 ( $_bench:ident: ; ) => { };
1463 ( $_bench:ident: $_car:path = Ignored ; ) => { };
1464 ( $bench:ident: $_car:path = Ignored $( $storage:path = $_pov_mode:ident )+; ) => {
1465 compile_error!(
1466 concat!(concat!("`pov_mode = Ignored` is exclusive. Please remove the attribute from keys: ", $( stringify!($storage) )+), " on benchmark '", stringify!($bench), "'"));
1467 };
1468 ( $bench:ident: $car:path = Measured $( $storage:path = $pov_mode:ident )*; ) => {
1469 $crate::validate_pov_mode!(
1470 $bench: $( $storage = $pov_mode )*;
1471 );
1472 };
1473 ( $bench:ident: $car:path = MaxEncodedLen $( $storage:path = $pov_mode:ident )*; ) => {
1474 $crate::validate_pov_mode!(
1475 $bench: $( $storage = $pov_mode )*;
1476 );
1477 };
1478 ( $bench:ident: $key:path = $unknown:ident $( $_storage:path = $_pov_mode:ident )*; ) => {
1479 compile_error!(
1480 concat!("Unknown pov_mode '", stringify!($unknown) ,"' for benchmark '", stringify!($bench), "' on key '", stringify!($key), "'. Must be one of: Ignored, Measured, MaxEncodedLen")
1481 );
1482 };
1483}
1484
1485#[macro_export]
1491#[doc(hidden)]
1492macro_rules! impl_test_function {
1493 (
1497 ( $( $names:tt )* )
1498 ( $( $names_extra:tt )* )
1499 ( $( $names_skip_meta:tt )* )
1500
1501 $bench_module:ident,
1502 $new_test_ext:expr,
1503 $test:path
1504 $(, $( $rest:tt )* )?
1505 ) => {
1506 $crate::impl_test_function!(
1507 @cases:
1508 ( $( $names )* )
1509 ( $( $names_extra )* )
1510 ( $( $names_skip_meta )* )
1511 @selected:
1512 $bench_module,
1513 $new_test_ext,
1514 $test,
1515 benchmarks_path = super,
1516 extra = true,
1517 exec_name = execute_with,
1518 @user:
1519 $( $( $rest )* )?
1520 );
1521 };
1522 (
1524 @cases:
1525 ( $( $names:tt )* )
1526 ( $( $names_extra:tt )* )
1527 ( $( $names_skip_meta:tt )* )
1528 @selected:
1529 $bench_module:ident,
1530 $new_test_ext:expr,
1531 $test:path,
1532 benchmarks_path = $old:ident,
1533 extra = $extra:expr,
1534 exec_name = $exec_name:ident,
1535 @user:
1536 benchmarks_path = $benchmarks_path:ident
1537 $(, $( $rest:tt )* )?
1538 ) => {
1539 $crate::impl_test_function!(
1540 @cases:
1541 ( $( $names )* )
1542 ( $( $names_extra )* )
1543 ( $( $names_skip_meta )* )
1544 @selected:
1545 $bench_module,
1546 $new_test_ext,
1547 $test,
1548 benchmarks_path = $benchmarks_path,
1549 extra = $extra,
1550 exec_name = $exec_name,
1551 @user:
1552 $( $( $rest )* )?
1553 );
1554 };
1555 (
1557 @cases:
1558 ( $( $names:tt )* )
1559 ( $( $names_extra:tt )* )
1560 ( $( $names_skip_meta:tt )* )
1561 @selected:
1562 $bench_module:ident,
1563 $new_test_ext:expr,
1564 $test:path,
1565 benchmarks_path = $benchmarks_path:ident,
1566 extra = $old:expr,
1567 exec_name = $exec_name:ident,
1568 @user:
1569 extra = $extra:expr
1570 $(, $( $rest:tt )* )?
1571 ) => {
1572 $crate::impl_test_function!(
1573 @cases:
1574 ( $( $names )* )
1575 ( $( $names_extra )* )
1576 ( $( $names_skip_meta )* )
1577 @selected:
1578 $bench_module,
1579 $new_test_ext,
1580 $test,
1581 benchmarks_path = $benchmarks_path,
1582 extra = $extra,
1583 exec_name = $exec_name,
1584 @user:
1585 $( $( $rest )* )?
1586 );
1587 };
1588 (
1590 @cases:
1591 ( $( $names:tt )* )
1592 ( $( $names_extra:tt )* )
1593 ( $( $names_skip_meta:tt )* )
1594 @selected:
1595 $bench_module:ident,
1596 $new_test_ext:expr,
1597 $test:path,
1598 benchmarks_path = $benchmarks_path:ident,
1599 extra = $extra:expr,
1600 exec_name = $old:ident,
1601 @user:
1602 exec_name = $exec_name:ident
1603 $(, $( $rest:tt )* )?
1604 ) => {
1605 $crate::impl_test_function!(
1606 @cases:
1607 ( $( $names )* )
1608 ( $( $names_extra )* )
1609 ( $( $names_skip_meta )* )
1610 @selected:
1611 $bench_module,
1612 $new_test_ext,
1613 $test,
1614 benchmarks_path = $benchmarks_path,
1615 extra = $extra,
1616 exec_name = $exec_name,
1617 @user:
1618 $( $( $rest )* )?
1619 );
1620 };
1621 (
1623 @cases:
1624 ( $( $names:tt )+ )
1625 ( $( $names_extra:tt )* )
1626 ( $( $names_skip_meta:tt )* )
1627 @selected:
1628 $bench_module:ident,
1629 $new_test_ext:expr,
1630 $test:path,
1631 benchmarks_path = $path_to_benchmarks_invocation:ident,
1632 extra = $extra:expr,
1633 exec_name = $exec_name:ident,
1634 @user:
1635 $(,)?
1636 ) => {
1637 $crate::impl_bench_case_tests!(
1638 { $bench_module, $new_test_ext, $exec_name, $test, $extra }
1639 { $( $names_extra:tt )* }
1640 $($names)+
1641 );
1642 };
1643 (
1645 @cases:
1646 ()
1647 ()
1648 ()
1649 @selected:
1650 $bench_module:ident,
1651 $new_test_ext:expr,
1652 $test:path,
1653 benchmarks_path = $path_to_benchmarks_invocation:ident,
1654 extra = $extra:expr,
1655 exec_name = $exec_name:ident,
1656 @user:
1657 $(,)?
1658 ) => {
1659 #[cfg(test)]
1660 mod benchmark_tests {
1661 use super::$bench_module;
1662
1663 #[test]
1664 fn test_benchmarks() {
1665 $new_test_ext.$exec_name(|| {
1666 use $crate::Benchmarking;
1667
1668 let mut anything_failed = false;
1669 println!("failing benchmark tests:");
1670 for benchmark_metadata in $bench_module::<$test>::benchmarks($extra) {
1671 let benchmark_name = &benchmark_metadata.name;
1672 match std::panic::catch_unwind(|| {
1673 $bench_module::<$test>::test_bench_by_name(benchmark_name)
1674 }) {
1675 Err(err) => {
1676 println!(
1677 "{}: {:?}",
1678 $crate::__private::str::from_utf8(benchmark_name)
1679 .expect("benchmark name is always a valid string!"),
1680 err,
1681 );
1682 anything_failed = true;
1683 },
1684 Ok(Err(err)) => {
1685 match err {
1686 $crate::BenchmarkError::Stop(err) => {
1687 println!(
1688 "{}: {:?}",
1689 $crate::__private::str::from_utf8(benchmark_name)
1690 .expect("benchmark name is always a valid string!"),
1691 err,
1692 );
1693 anything_failed = true;
1694 },
1695 $crate::BenchmarkError::Override(_) => {
1696 $crate::__private::log::error!(
1698 "WARNING: benchmark error overridden - {}",
1699 $crate::__private::str::from_utf8(benchmark_name)
1700 .expect("benchmark name is always a valid string!"),
1701 );
1702 },
1703 $crate::BenchmarkError::Skip => {
1704 $crate::__private::log::error!(
1706 "WARNING: benchmark error skipped - {}",
1707 $crate::__private::str::from_utf8(benchmark_name)
1708 .expect("benchmark name is always a valid string!"),
1709 );
1710 }
1711 $crate::BenchmarkError::Weightless => {
1712 $crate::__private::log::error!(
1714 "WARNING: benchmark weightless skipped - {}",
1715 $crate::__private::str::from_utf8(benchmark_name)
1716 .expect("benchmark name is always a valid string!"),
1717 );
1718 }
1719 }
1720 },
1721 Ok(Ok(())) => (),
1722 }
1723 }
1724 assert!(!anything_failed);
1725 });
1726 }
1727 }
1728 };
1729}
1730
1731pub fn show_benchmark_debug_info(
1734 instance_string: &[u8],
1735 benchmark: &[u8],
1736 components: &[(BenchmarkParameter, u32)],
1737 verify: &bool,
1738 error_message: &str,
1739) -> alloc::string::String {
1740 alloc::format!(
1741 "\n* Pallet: {}\n\
1742 * Benchmark: {}\n\
1743 * Components: {:?}\n\
1744 * Verify: {:?}\n\
1745 * Error message: {}",
1746 alloc::str::from_utf8(instance_string)
1747 .expect("it's all just strings ran through the wasm interface. qed"),
1748 alloc::str::from_utf8(benchmark)
1749 .expect("it's all just strings ran through the wasm interface. qed"),
1750 components,
1751 verify,
1752 error_message,
1753 )
1754}
1755
1756#[macro_export]
1819macro_rules! add_benchmark {
1820 ( $params:ident, $batches:ident, $name:path, $location:ty ) => {
1821 let pallet_string = stringify!($name).replace(" ", "").into_bytes();
1822 let instance_string = stringify!($location).replace(" ", "").into_bytes();
1823 let (config, whitelist) = $params;
1824 let $crate::BenchmarkConfig {
1825 pallet,
1826 instance,
1827 benchmark,
1828 selected_components,
1829 verify,
1830 internal_repeats,
1831 } = config;
1832 if &pallet[..] == &pallet_string[..] && &instance[..] == &instance_string[..] {
1833 let benchmark_result = <$location as $crate::Benchmarking>::run_benchmark(
1834 &benchmark[..],
1835 &selected_components[..],
1836 whitelist,
1837 *verify,
1838 *internal_repeats,
1839 );
1840
1841 let final_results = match benchmark_result {
1842 Ok(results) => Some(results),
1843 Err($crate::BenchmarkError::Override(mut result)) => {
1844 $crate::__private::log::error!(
1846 "WARNING: benchmark error overridden - {}",
1847 $crate::__private::str::from_utf8(benchmark)
1848 .expect("benchmark name is always a valid string!")
1849 );
1850 result.keys.insert(0, (b"Benchmark Override".to_vec(), 0, 0, false));
1851 Some($crate::__private::vec![result])
1852 },
1853 Err($crate::BenchmarkError::Stop(e)) => {
1854 $crate::show_benchmark_debug_info(
1855 &instance_string,
1856 benchmark,
1857 selected_components,
1858 verify,
1859 e,
1860 );
1861 return Err(e.into())
1862 },
1863 Err($crate::BenchmarkError::Skip) => {
1864 $crate::__private::log::error!(
1865 "WARNING: benchmark error skipped - {}",
1866 $crate::__private::str::from_utf8(benchmark)
1867 .expect("benchmark name is always a valid string!")
1868 );
1869 None
1870 },
1871 Err($crate::BenchmarkError::Weightless) => {
1872 $crate::__private::log::error!(
1873 "WARNING: benchmark weightless skipped - {}",
1874 $crate::__private::str::from_utf8(benchmark)
1875 .expect("benchmark name is always a valid string!")
1876 );
1877 Some($crate::__private::vec![$crate::BenchmarkResult {
1878 components: selected_components.clone(),
1879 ..Default::default()
1880 }])
1881 },
1882 };
1883
1884 if let Some(final_results) = final_results {
1885 $batches.push($crate::BenchmarkBatch {
1886 pallet: pallet_string,
1887 instance: instance_string,
1888 benchmark: benchmark.clone(),
1889 results: final_results,
1890 });
1891 }
1892 }
1893 };
1894}
1895
1896#[macro_export]
1916macro_rules! list_benchmark {
1917 ( $list:ident, $extra:ident, $name:path, $location:ty ) => {
1918 let pallet_string = stringify!($name).replace(" ", "").into_bytes();
1919 let instance_string = stringify!($location).replace(" ", "").into_bytes();
1920 let benchmarks = <$location as $crate::Benchmarking>::benchmarks($extra);
1921 let pallet_benchmarks = $crate::BenchmarkList {
1922 pallet: pallet_string,
1923 instance: instance_string,
1924 benchmarks: benchmarks.to_vec(),
1925 };
1926 $list.push(pallet_benchmarks)
1927 };
1928}
1929
1930#[macro_export]
1934macro_rules! define_benchmarks {
1935 ( $([ $names:path, $locations:ty ])* ) => {
1936 #[macro_export]
1944 macro_rules! list_benchmarks {
1945 ( $list:ident, $extra:ident ) => {
1946 $( $crate::list_benchmark!( $list, $extra, $names, $locations); )*
1947 }
1948 }
1949
1950 #[macro_export]
1958 macro_rules! add_benchmarks {
1959 ( $params:ident, $batches:ident ) => {
1960 $( $crate::add_benchmark!( $params, $batches, $names, $locations ); )*
1961 }
1962 }
1963 }
1964}
1965
1966pub use add_benchmark;
1967pub use benchmark_backend;
1968pub use benchmarks;
1969pub use benchmarks_instance;
1970pub use benchmarks_instance_pallet;
1971pub use benchmarks_iter;
1972pub use define_benchmarks;
1973pub use impl_bench_case_tests;
1974pub use impl_bench_name_tests;
1975pub use impl_benchmark;
1976pub use impl_benchmark_test;
1977pub use impl_benchmark_test_suite;
1978pub use impl_test_function;
1979pub use list_benchmark;
1980pub use selected_benchmark;
1981pub use to_origin;
1982pub use whitelist;