Fix the creation of the dumpdir directory in stress_floppy Makefile
[ltp-debian.git] / testcases / kernel / io / stress_cd / stress_cd.c
blobe7d00b0e357c31e939de03f706ec5e31d39e0c0e
1 /*
3 * Copyright (c) International Business Machines Corp., 2001
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See
13 * the GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
21 * FILE : stress_cd.c
22 * DESCRIPTION : creates multiple read threads on the cdrom device.
23 * HISTORY:
24 * 06/20/2001 Robbie Williamson (robbiew@us.ibm.com)
25 * -Ported
26 * 11/08/2001 Manoj Iyer (manjo@austin.ibm.com)
27 * - Modified.
28 * - removed compiler warnings.
29 * - Added #include <sys/types.h>, #include <unistd.h> and
30 * #include <string.h>
31 * - print unsigned long correctly in printf() use "lx" instead of "x"
32 * - added missing parameter in usage message.
34 +--------------------------------------------------------------------+
35 | |
36 | Usage: cdtest [-n n] [-f file] [-m xx] [-d] |
37 | |
38 | where: |
39 | -n n Number of threads to create |
40 | -f file File or device to read from |
41 | -m xx Number of MB to read from file |
42 | -b xx Number of bytes to read from file |
43 | -d Enable debugging messages |
44 | |
45 | |
46 +-------------------------------------------------------------------*/
48 #include <pthread.h>
49 #include <fcntl.h>
50 #include <stdlib.h>
51 #include <stdio.h>
52 #include <assert.h>
53 #include <errno.h>
54 #include <sys/types.h>
55 #include <unistd.h>
56 #include <string.h>
59 /* Defines
61 * DEFAULT_NUM_THREADS: Default number of threads to create,
62 * user can specifiy with [-n] command line option.
64 * USAGE: usage statement
66 #define DEFAULT_NUM_THREADS 10
67 #define DEFAULT_NUM_BYTES 1024*1024*100 /* 100Mb */
68 #define DEFAULT_FILE "/dev/cdrom"
71 * Function prototypes
73 * sys_error (): System error message function
74 * error (): Error message function
75 * parse_args (): Parses command line arguments
77 static void sys_error (const char *, int);
78 static void error (const char *, int);
79 static void parse_args (int, char **);
80 void *thread (int *);
81 int read_data (int, unsigned long);
84 * Global Variables
86 int num_threads = DEFAULT_NUM_THREADS;
87 int num_bytes = DEFAULT_NUM_BYTES;
88 char *file = DEFAULT_FILE;
89 unsigned long checksum = 0;
90 int debug = 0;
93 /*-------------------------------------------------------------------+
94 | main () |
95 | ================================================================== |
96 | |
97 | Function: Main program (see prolog for more details) |
98 | |
99 +-------------------------------------------------------------------*/
100 int main (int argc, char **argv)
102 pthread_attr_t attr;
103 pthread_t *array;
104 int *arg;
105 int rc = 0, i;
107 /* Parse command line arguments and print out program header */
108 parse_args (argc, argv);
110 /* Read data from CDROM & compute checksum */
111 read_data (0, checksum);
112 if (debug)
113 printf("Thread [main] checksum: %-#12lx \n", checksum);
115 if (pthread_attr_init (&attr))
116 sys_error ("pthread_attr_init failed", __LINE__);
117 if (pthread_attr_setdetachstate (&attr, PTHREAD_CREATE_JOINABLE))
118 sys_error ("pthread_attr_setdetachstate failed", __LINE__);
120 /* Create num_thread threads... */
121 printf("\tThread [main] Creating %d threads\n", num_threads);
123 array = (pthread_t *) malloc (sizeof (pthread_t) * num_threads);
124 arg = (int *) malloc (sizeof (int) * num_threads);
125 assert (array);
126 assert (arg);
127 for (i=0; i < num_threads; i++)
129 if (debug)
130 printf("\tThread [main]: creating thread %d\n", i + 1);
131 arg[i] = i + 1;
132 if (pthread_create ((pthread_t *) &array [i], &attr, (void *)thread, (void *) &arg[i]))
134 if (errno == EAGAIN)
135 fprintf(stderr, "\tThread [main]: unable to create thread %d\n", i);
136 else
137 sys_error ("pthread_create failed", __LINE__);
139 if (debug)
140 printf("\tThread [main]: created thread %d\n", i+1);
142 if (pthread_attr_destroy (&attr))
143 sys_error ("pthread_attr_destroy failed", __LINE__);
145 for (i=0; i<num_threads; i++)
147 int exit_value;
148 printf("\tThread [main]: waiting for thread: %d\n", i+1);
149 /*if (pthread_join ((pthread_t*) array [i], (void **) &exit_value))*/
150 if (pthread_join ((pthread_t) array [i], (void **) &exit_value))
151 sys_error ("pthread_join failed", __LINE__);
153 if (debug)
154 printf("\tThread [%d]: return %d\n", i + 1, exit_value);
155 rc += exit_value;
157 free(array);
158 free(arg);
160 /* One or more of the threads did not complete sucessfully! */
161 if (rc != 0)
163 printf("test failed!\n");
164 exit (-1);
167 /* Program completed successfully... */
168 printf("\tThread [main] All threads completed successfully...\n");
169 exit (0);
173 /*-------------------------------------------------------------------+
174 | thread () |
175 | ================================================================== |
177 | Function: ... |
179 +-------------------------------------------------------------------*/
180 void *thread (int *parm)
182 int num = *parm;
183 unsigned long cksum = 0;
186 if (debug)
187 printf("\tThread [%d]: begin\n", num);
189 read_data (num, cksum);
190 if (checksum != cksum)
192 fprintf(stderr, "\tThread [%d]: checksum mismatch!\n", num);
193 pthread_exit ((void *) -1);
196 if (debug)
197 printf("\tThread [%d]: done\n", num);
199 pthread_exit ((void *) 0);
200 return (NULL);
204 /*-------------------------------------------------------------------+
205 | read_data () |
206 | ================================================================== |
208 | Function: Reads data from the CDROM |
210 +-------------------------------------------------------------------*/
211 int read_data (int num, unsigned long cksum)
213 int fd;
214 const int bufSize = 1024;
215 char *buffer;
216 int bytes_read = 0;
217 int n;
218 char *p;
221 if (debug)
222 printf("\tThread [%d]: read_data()\n", num);
224 if ((fd = open (file, O_RDONLY, NULL)) < 0)
225 sys_error ("open failed", __LINE__);
227 buffer = (char *) malloc (sizeof(char) * bufSize);
228 assert (buffer);
230 lseek(fd,1024*36,SEEK_SET);
231 while (bytes_read < num_bytes)
233 if ((n = read (fd, buffer, bufSize)) < 0)
234 sys_error ("read failed", __LINE__);
235 bytes_read += n;
237 for (p=buffer; p < buffer+n; p++)
238 cksum += *p;
240 if (debug)
241 printf("\tThread [%d] bytes read: %5d checksum: %-#12lx\n",
242 num, bytes_read, cksum);
244 free(buffer);
246 if (debug)
247 printf("\tThread [%d] bytes read: %5d checksum: %-#12lx\n",
248 num, bytes_read, cksum);
250 if (close (fd) < 0)
251 sys_error ("close failed", __LINE__);
253 if (debug)
254 printf("\tThread [%d]: done\n", num);
256 return (0);
260 /*-------------------------------------------------------------------+
261 | parse_args () |
262 | ================================================================== |
264 | Function: Parse the command line arguments & initialize global |
265 | variables. |
267 | Updates: (command line options) |
269 | [-n] num number of threads to create |
271 | [-d] enable debugging messages |
273 +-------------------------------------------------------------------*/
274 static void parse_args (int argc, char **argv)
276 int i;
277 int errflag = 0;
278 char *program_name = *argv;
279 extern char *optarg; /* Command line option */
282 while ((i = getopt(argc, argv, "df:n:b:m:?")) != EOF)
284 switch (i)
286 case 'd': /* debug option */
287 debug++;
288 break;
289 case 'f': /* file to read from */
290 file = optarg;
291 break;
292 case 'm': /* num MB to read */
293 num_bytes = atoi (optarg) * 1024 * 1024 ;
294 break;
295 case 'b': /* num bytes to read */
296 num_bytes = atoi (optarg);
297 break;
298 case 'n': /* number of threads */
299 num_threads = atoi (optarg);
300 break;
301 case '?': /* help */
302 errflag++;
303 break;
306 if (num_bytes < 0)
308 errflag++;
309 fprintf(stderr, "ERROR: num_bytes must be greater than 0");
312 if (errflag)
314 fprintf(stderr, "\nUsage: %s"
315 " [-n xx] [-m|b xx] [-d]\n\n"
316 "\t-n xx Number of threads to create (up to %d)\n"
317 "\t-f file File to read from\n"
318 "\t-m xx Number of MB to read\n"
319 "\t-b xx Number of bytes to read\n"
320 "\t-d Debug option\n", program_name,
321 DEFAULT_NUM_THREADS);
322 exit (2);
327 /*-------------------------------------------------------------------+
328 | sys_error () |
329 | ================================================================== |
331 | Function: Creates system error message and calls error () |
333 +-------------------------------------------------------------------*/
334 static void sys_error (const char *msg, int line)
336 char syserr_msg [256];
338 sprintf (syserr_msg, "%s: %s\n", msg, strerror(errno));
339 error (syserr_msg, line);
343 /*-------------------------------------------------------------------+
344 | error () |
345 | ================================================================== |
347 | Function: Prints out message and exits... |
349 +-------------------------------------------------------------------*/
350 static void error (const char *msg, int line)
352 fprintf(stderr, "ERROR [line: %s] \n", msg);
353 exit (-1);