2 * Call a single random syscall with random args.
10 #include "arch.h" // biarch
22 * This function decides if we're going to be doing a 32bit or 64bit syscall.
23 * There are various factors involved here, from whether we're on a 32-bit only arch
24 * to 'we asked to do a 32bit only syscall' and more.. Hairy.
27 static int *active_syscalls
;
29 static bool choose_syscall_table(void)
33 if (biarch
== FALSE
) {
34 active_syscalls
= shm
->active_syscalls
;
38 /* First, check that we have syscalls enabled in either table. */
39 if (validate_syscall_table_64() == FALSE
) {
41 /* If no 64bit syscalls enabled, force 32bit. */
45 if (validate_syscall_table_32() == FALSE
)
48 /* If both tables enabled, pick randomly. */
49 if ((use_64bit
== TRUE
) && (use_32bit
== TRUE
)) {
50 /* 10% possibility of a 32bit syscall */
51 if (rand() % 100 < 10)
56 syscalls
= syscalls_64bit
;
57 active_syscalls
= shm
->active_syscalls64
;
58 max_nr_syscalls
= max_nr_64bit_syscalls
;
60 syscalls
= syscalls_32bit
;
61 active_syscalls
= shm
->active_syscalls32
;
62 max_nr_syscalls
= max_nr_32bit_syscalls
;
68 bool child_random_syscalls(int childno
)
70 unsigned int syscallnr
;
74 if (no_syscalls_enabled() == TRUE
) {
75 output(0, "[%d] No more syscalls enabled. Exiting\n", getpid());
76 shm
->exit_reason
= EXIT_NO_SYSCALLS_ENABLED
;
80 /* Ok, we're doing another syscall, let's pick one. */
81 do32
= choose_syscall_table();
82 syscallnr
= rand() % max_nr_syscalls
;
84 /* If we got a syscallnr which is not active repeat the attempt,
85 * since another child has switched that syscall off already.*/
86 if (active_syscalls
[syscallnr
] == 0)
89 syscallnr
= active_syscalls
[syscallnr
] - 1;
91 if (validate_specific_syscall_silent(syscalls
, syscallnr
) == FALSE
) {
92 if (biarch
== FALSE
) {
93 deactivate_syscall(syscallnr
);
96 deactivate_syscall32(syscallnr
);
98 deactivate_syscall64(syscallnr
);
103 /* critical section for shm updates. */
104 lock(&shm
->syscall_lock
);
105 shm
->syscall
[childno
].do32bit
= do32
;
106 shm
->syscall
[childno
].nr
= syscallnr
;
107 unlock(&shm
->syscall_lock
);
110 if (shm
->total_syscalls_done
>= syscalls_todo
) {
111 output(0, "Reached maximum syscall count (todo = %d, done = %d), exiting...\n",
112 syscalls_todo
, shm
->total_syscalls_done
);
113 shm
->exit_reason
= EXIT_REACHED_COUNT
;
117 /* Do the actual syscall. */
118 return mkcall(childno
);