@@ -438,18 +438,21 @@ static const struct hwcap_data {
438
438
},
439
439
};
440
440
441
- static bool seen_sigill ;
442
-
443
- static void handle_sigill (int sig , siginfo_t * info , void * context )
444
- {
445
- ucontext_t * uc = context ;
446
-
447
- seen_sigill = true;
448
-
449
- /* Skip over the offending instruction */
450
- uc -> uc_mcontext .pc += 4 ;
441
+ typedef void (* sighandler_fn )(int , siginfo_t * , void * );
442
+
443
+ #define DEF_SIGHANDLER_FUNC (SIG , NUM ) \
444
+ static bool seen_##SIG; \
445
+ static void handle_##SIG(int sig, siginfo_t *info, void *context) \
446
+ { \
447
+ ucontext_t *uc = context; \
448
+ \
449
+ seen_##SIG = true; \
450
+ /* Skip over the offending instruction */ \
451
+ uc -> uc_mcontext .pc += 4 ; \
451
452
}
452
453
454
+ DEF_SIGHANDLER_FUNC (sigill , SIGILL );
455
+
453
456
bool cpuinfo_present (const char * name )
454
457
{
455
458
FILE * f ;
@@ -492,25 +495,77 @@ bool cpuinfo_present(const char *name)
492
495
return false;
493
496
}
494
497
495
- int main ( void )
498
+ static int install_sigaction ( int signum , sighandler_fn handler )
496
499
{
497
- const struct hwcap_data * hwcap ;
498
- int i , ret ;
499
- bool have_cpuinfo , have_hwcap ;
500
+ int ret ;
500
501
struct sigaction sa ;
501
502
502
- ksft_print_header ();
503
- ksft_set_plan (ARRAY_SIZE (hwcaps ) * TESTS_PER_HWCAP );
504
-
505
503
memset (& sa , 0 , sizeof (sa ));
506
- sa .sa_sigaction = handle_sigill ;
504
+ sa .sa_sigaction = handler ;
507
505
sa .sa_flags = SA_RESTART | SA_SIGINFO ;
508
506
sigemptyset (& sa .sa_mask );
509
- ret = sigaction (SIGILL , & sa , NULL );
507
+ ret = sigaction (signum , & sa , NULL );
510
508
if (ret < 0 )
511
509
ksft_exit_fail_msg ("Failed to install SIGILL handler: %s (%d)\n" ,
512
510
strerror (errno ), errno );
513
511
512
+ return ret ;
513
+ }
514
+
515
+ static void uninstall_sigaction (int signum )
516
+ {
517
+ if (sigaction (signum , NULL , NULL ) < 0 )
518
+ ksft_exit_fail_msg ("Failed to uninstall SIGILL handler: %s (%d)\n" ,
519
+ strerror (errno ), errno );
520
+ }
521
+
522
+ #define DEF_INST_RAISE_SIG (SIG , NUM ) \
523
+ static bool inst_raise_##SIG(const struct hwcap_data *hwcap, \
524
+ bool have_hwcap) \
525
+ { \
526
+ if (!hwcap->SIG##_fn) { \
527
+ ksft_test_result_skip(#SIG"_%s\n", hwcap->name); \
528
+ /* assume that it would raise exception in default */ \
529
+ return true; \
530
+ } \
531
+ \
532
+ install_sigaction (NUM , handle_ ##SIG ); \
533
+ \
534
+ seen_##SIG = false; \
535
+ hwcap->SIG##_fn(); \
536
+ \
537
+ if (have_hwcap) { \
538
+ /* Should be able to use the extension */ \
539
+ ksft_test_result (!seen_ ##SIG , \
540
+ #SIG"_%s\n", hwcap->name); \
541
+ } else if (hwcap->SIG##_reliable) { \
542
+ /* Guaranteed a SIGNAL */ \
543
+ ksft_test_result (seen_ ##SIG , \
544
+ #SIG"_%s\n", hwcap->name); \
545
+ } else { \
546
+ /* Missing SIGNAL might be fine */ \
547
+ ksft_print_msg (#SIG "_%sreported for %s\n", \
548
+ seen_##SIG ? "" : "not ", \
549
+ hwcap->name); \
550
+ ksft_test_result_skip(#SIG"_%s\n", \
551
+ hwcap->name); \
552
+ } \
553
+ \
554
+ uninstall_sigaction(NUM); \
555
+ return seen_##SIG; \
556
+ }
557
+
558
+ DEF_INST_RAISE_SIG (sigill , SIGILL );
559
+
560
+ int main (void )
561
+ {
562
+ int i ;
563
+ const struct hwcap_data * hwcap ;
564
+ bool have_cpuinfo , have_hwcap ;
565
+
566
+ ksft_print_header ();
567
+ ksft_set_plan (ARRAY_SIZE (hwcaps ) * TESTS_PER_HWCAP );
568
+
514
569
for (i = 0 ; i < ARRAY_SIZE (hwcaps ); i ++ ) {
515
570
hwcap = & hwcaps [i ];
516
571
@@ -523,30 +578,7 @@ int main(void)
523
578
ksft_test_result (have_hwcap == have_cpuinfo ,
524
579
"cpuinfo_match_%s\n" , hwcap -> name );
525
580
526
- if (hwcap -> sigill_fn ) {
527
- seen_sigill = false;
528
- hwcap -> sigill_fn ();
529
-
530
- if (have_hwcap ) {
531
- /* Should be able to use the extension */
532
- ksft_test_result (!seen_sigill , "sigill_%s\n" ,
533
- hwcap -> name );
534
- } else if (hwcap -> sigill_reliable ) {
535
- /* Guaranteed a SIGILL */
536
- ksft_test_result (seen_sigill , "sigill_%s\n" ,
537
- hwcap -> name );
538
- } else {
539
- /* Missing SIGILL might be fine */
540
- ksft_print_msg ("SIGILL %sreported for %s\n" ,
541
- seen_sigill ? "" : "not " ,
542
- hwcap -> name );
543
- ksft_test_result_skip ("sigill_%s\n" ,
544
- hwcap -> name );
545
- }
546
- } else {
547
- ksft_test_result_skip ("sigill_%s\n" ,
548
- hwcap -> name );
549
- }
581
+ inst_raise_sigill (hwcap , have_hwcap );
550
582
}
551
583
552
584
ksft_print_cnts ();
0 commit comments