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
22 * DESCRIPTION : creates multiple read threads on the cdrom device.
24 * 06/20/2001 Robbie Williamson (robbiew@us.ibm.com)
26 * 11/08/2001 Manoj Iyer (manjo@austin.ibm.com)
28 * - removed compiler warnings.
29 * - Added #include <sys/types.h>, #include <unistd.h> and
31 * - print unsigned long correctly in printf() use "lx" instead of "x"
32 * - added missing parameter in usage message.
34 +--------------------------------------------------------------------+
36 | Usage: cdtest [-n n] [-f file] [-m xx] [-d] |
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 |
46 +-------------------------------------------------------------------*/
54 #include <sys/types.h>
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"
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 **);
81 int read_data (int, unsigned long);
86 int num_threads
= DEFAULT_NUM_THREADS
;
87 int num_bytes
= DEFAULT_NUM_BYTES
;
88 char *file
= DEFAULT_FILE
;
89 unsigned long checksum
= 0;
93 /*-------------------------------------------------------------------+
95 | ================================================================== |
97 | Function: Main program (see prolog for more details) |
99 +-------------------------------------------------------------------*/
100 int main (int argc
, char **argv
)
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
);
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
);
127 for (i
=0; i
< num_threads
; i
++)
130 printf("\tThread [main]: creating thread %d\n", i
+ 1);
132 if (pthread_create ((pthread_t
*) &array
[i
], &attr
, (void *)thread
, (void *) &arg
[i
]))
135 fprintf(stderr
, "\tThread [main]: unable to create thread %d\n", i
);
137 sys_error ("pthread_create failed", __LINE__
);
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
++)
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__
);
154 printf("\tThread [%d]: return %d\n", i
+ 1, exit_value
);
160 /* One or more of the threads did not complete sucessfully! */
163 printf("test failed!\n");
167 /* Program completed successfully... */
168 printf("\tThread [main] All threads completed successfully...\n");
173 /*-------------------------------------------------------------------+
175 | ================================================================== |
179 +-------------------------------------------------------------------*/
180 void *thread (int *parm
)
183 unsigned long cksum
= 0;
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);
197 printf("\tThread [%d]: done\n", num
);
199 pthread_exit ((void *) 0);
204 /*-------------------------------------------------------------------+
206 | ================================================================== |
208 | Function: Reads data from the CDROM |
210 +-------------------------------------------------------------------*/
211 int read_data (int num
, unsigned long cksum
)
214 const int bufSize
= 1024;
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
);
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__
);
237 for (p
=buffer
; p
< buffer
+n
; p
++)
241 printf("\tThread [%d] bytes read: %5d checksum: %-#12lx\n",
242 num
, bytes_read
, cksum
);
247 printf("\tThread [%d] bytes read: %5d checksum: %-#12lx\n",
248 num
, bytes_read
, cksum
);
251 sys_error ("close failed", __LINE__
);
254 printf("\tThread [%d]: done\n", num
);
260 /*-------------------------------------------------------------------+
262 | ================================================================== |
264 | Function: Parse the command line arguments & initialize global |
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
)
278 char *program_name
= *argv
;
279 extern char *optarg
; /* Command line option */
282 while ((i
= getopt(argc
, argv
, "df:n:b:m:?")) != EOF
)
286 case 'd': /* debug option */
289 case 'f': /* file to read from */
292 case 'm': /* num MB to read */
293 num_bytes
= atoi (optarg
) * 1024 * 1024 ;
295 case 'b': /* num bytes to read */
296 num_bytes
= atoi (optarg
);
298 case 'n': /* number of threads */
299 num_threads
= atoi (optarg
);
309 fprintf(stderr
, "ERROR: num_bytes must be greater than 0");
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
);
327 /*-------------------------------------------------------------------+
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 /*-------------------------------------------------------------------+
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
);