plan to cleanup the fd generation code
[trinity.git] / fds.c
blobfb1a3c678fb4f88670f7d60adcbf7c81457062a0
1 #include <errno.h>
2 #include <stdio.h>
3 #include <stdlib.h>
4 #include <string.h>
5 #include <unistd.h>
6 #include <sys/epoll.h>
7 #include <sys/eventfd.h>
9 #include "epoll.h"
10 #include "eventfd.h"
11 #include "files.h"
12 #include "log.h"
13 #include "net.h"
14 #include "params.h"
15 #include "perf.h"
16 #include "pids.h"
17 #include "pipes.h"
18 #include "random.h"
19 #include "sanitise.h"
20 #include "shm.h"
21 #include "trinity.h"
23 static int get_new_random_fd(void)
25 unsigned int i;
26 int fd = 0;
28 retry:
29 i = rand() % 6;
31 if (do_specific_proto == TRUE)
32 i = 1;
34 if (no_files == TRUE)
35 i = 1;
37 /* Ugly special case.
38 * Sometimes, we can get here without any fd's setup.
39 * If this happens, we divide by zero if we pick case 0 because
40 * nr_file_fds is zero
42 * When this circumstance occurs, we just force it to use another network socket.
44 * FIXME: A better solution would be to like, actually open an fd. duh.
46 if (nr_file_fds == 0)
47 i = 1;
49 switch (i) {
50 case 0:
51 fd = rand_file_fd();
52 break;
54 case 1:
55 /* When using victim files, sockets can be 0.
56 * Use files as a fallback, or pipes if no files are open.
58 if (nr_sockets == 0) {
59 if (nr_file_fds > 0)
60 fd = rand_file_fd();
61 else
62 fd = rand_pipe_fd();
63 return fd;
65 fd = shm->sockets[rand() % nr_sockets].fd;
66 break;
68 case 2:
69 fd = rand_pipe_fd();
70 break;
72 case 3:
73 if (shm->perf_fds[0] == 0) /* perf unavailable/disabled. */
74 goto retry;
76 fd = rand_perf_fd();
77 break;
79 case 4:
80 fd = rand_epoll_fd();
81 break;
83 case 5:
84 fd = rand_eventfd_fd();
85 break;
89 return fd;
92 int get_random_fd(void)
94 /* 25% chance of returning something new. */
95 if ((rand() % 4) == 0)
96 return get_new_random_fd();
98 /* the rest of the time, return the same fd as last time. */
99 regen:
100 if (shm->fd_lifetime == 0) {
101 shm->current_fd = get_new_random_fd();
102 shm->fd_lifetime = (rand() % max_children) + 5;
103 } else
104 shm->fd_lifetime--;
106 if (shm->current_fd == 0) {
107 shm->fd_lifetime = 0;
108 goto regen;
111 return shm->current_fd;
114 unsigned int setup_fds(void)
116 int ret = TRUE;
118 /* If we have victim files, don't worry about sockets. */
119 if (victim_path == NULL) {
120 ret = open_sockets();
121 if (ret == FALSE)
122 return FALSE;
125 open_pipes();
127 open_perf_fds();
129 open_epoll_fds();
131 open_eventfd_fds();
133 if (no_files == FALSE)
134 ret = open_files();
136 return ret;
139 void regenerate_fds(void)
141 if (no_files == TRUE)
142 return;
144 close_files();
145 open_files();