jpp@specialix.co.uk (John Pettitt) (06/27/89)
Terminal Benchmarks. The file below contains a set of public domain benchmarks written by anvil for the Stallion card. I am trying to gather information on the performance of other I/O boards. If you have a smart I/O board in a Xenix system please take the time to run the tests and mail me the results. I will be posting a grand summary to the net. If you don't want your name or results used please say so. John Pettitt Specialix # This is a shell archive. Remove anything before this line # then unpack it by saving it in a file and typing "sh file" # (Files unpacked will be owned by you and have default permissions). # This archive contains the following files: # ./README # ./popen.c # ./tbench # ./tbench1 # ./tbench2 # ./tbench3 # ./tinput.c # ./total.c # ./tsetup # if `test ! -s ./README` then echo "writing ./README" cat > ./README << '\Rogue\Monster\' Terminal Benchmarks. The file below contains a set of public domain benchmarks written by anvil for the Stallion card. I am trying to gather information on the performance of other I/O boards. If you have a smart I/O board in a Xenix system please take the time to run the tests and mail me the results. I will be posting a grand summary to the net. If you don't want your name or results used please say so. The information I would like from the results is shown below: RESULTS OF BENCHMARKS PERFORMED USING "TBENCH" ON 16MHZ DELL-386 WITH SI-16. TESTS PERFORMED AT 19.2K BAUD IN "COOKED" MODE PORTS: 1 2 3 4 5 6 7 8 %CPU: 3.2 4.4 5.7 7.0 8.3 9.3 10.9 12.3 THROUGHPUT: 18727 37594 56391 75188 93985 113208 131579 150943 AVERAGE: 18727 18797 18797 18797 18797 18868 18797 18868 PORTS: 9 10 11 12 13 14 15 16 %CPU: 13.5 15.0 16.2 17.5 18.8 20.1 21.5 22.7 THROUGHPUT: 170455 188679 207547 226415 246212 263158 281955 299625 AVERAGE: 18939 18868 18868 18868 18939 18797 18797 18727 If you can go above 16 ports then great - please do so. If you only have 4 or 8 then thats fine too. How to build the benchmarks. Copy the benchmark programs to a suitable place and make the following programs: total popen tinput The built in make rules are all thats needed to there is no Makefile. Running the Benchmarks. Performing benchmarks using the XENIX/UNIX 'time' program gives a good guide to performance but can be very inaccurate. Any device which turns interrupts off while running will not be timed for that period. To achieve accurate benchmarks, it is necessary to get an exact measure of the ammount of CPU that is missing from the system due to device I/O activity. The 'total' program measures precisely the ammount of CPU that is missing from the system due to terminal I/O activity, ie. it catches time spent in device drivers with interrupts off. However, before the 'total' program can be used it must be calibrated to the host system cpu. With absolutely no activity on the system run 'total -c -s60'. This will count for 60 seconds, write a calibration file 'total.dat' and then exit. To select these more exact benchmarks, set the environment variable 'TEST' to 2 in '.profile', then logout and log in again to cause the change to take effect. The 'tbench' program can now be run. This benchmark generates total baud rate and average baud rate per channel statistics. These actual baud rates are those baud rates as percieved by the system and not real physical baud rates, ie. they may be higher than the requested baud rate due to buffering on intelligent cards. Some cards still manage to cheat the test by causing the system clock to loose time, some as high as 30% time lost !!. It is wise to check the time before and after the test by running the 'date' program. \Rogue\Monster\ else echo "will not over write ./README" fi if `test ! -s ./popen.c` then echo "writing ./popen.c" cat > ./popen.c << '\Rogue\Monster\' /* * port open program */ #include <stdio.h> #include <fcntl.h> #include <termio.h> /* * Main program and argument parsing */ #define MAXLINE 80 #define MAXFILES 100 struct termio tbuf; int iop[MAXFILES]; int period = 10 * 60 * 60; char buf[5120]; main(argc, argv) char **argv; { register int i; int errflg, c; char modes[132]; FILE *fp; extern char *optarg; extern optind; errflg = 0; while ((c = getopt(argc, argv, "cs:")) != EOF) switch(c) { case 'c': /* check++; */ break; case 's': period = atoi(optarg); break; case '?': errflg++; break; } if (errflg || optind >= argc) { fprintf(stderr, "usage: popen -c -s [sleep period] [files...]\n"); exit(2); } if ((fp = fopen("modes.dat", "r")) == (FILE *) NULL) { fprintf(stderr, "popen : cannot open %s\n", "modes.dat"); exit(2); } fgets(modes, MAXLINE, fp); fclose(fp); if ((iop[0] = open(argv[optind], O_RDONLY)) < 0) { fprintf(stderr, "popen : cannot open %s\n", argv[optind]); exit(2); } modes[strlen(modes) - 1] = '\0'; sprintf(buf, "stty %s <%s", modes, argv[optind]); system(buf); if (ioctl(iop[0], TCGETA, &tbuf) < 0) { fprintf(stderr, "popen : cannot set modes for %s\n", argv[optind]); exit(2); } for (i = 1, optind++; optind < argc; optind++, i++) { if ((iop[i] = open(argv[optind], O_RDONLY)) < 0) { fprintf(stderr, "popen : cannot open %s\n", argv[optind]); exit(2); } if (ioctl(iop[i], TCSETA, &tbuf) < 0) { fprintf(stderr, "popen : cannot set modes for %s\n", argv[optind]); exit(2); } } sleep(period); } \Rogue\Monster\ else echo "will not over write ./popen.c" fi if `test ! -s ./tbench` then echo "writing ./tbench" cat > ./tbench << '\Rogue\Monster\' #!/bin/sh # # Intelligent Terminal Subtystem # Benchmark Procedures V1.2 # # # Specialix and Chase support added by John Pettitt (jpp@specialix.co.uk) # # Define Environment Variables # # : ${ARNET:=no} : ${AFTER4:=no} : ${BAUD:=9600} : ${BLOCKS:=50} : ${BRD_DIGIT:=none} : ${DEBUG:=no} : ${DEFAULT:=2} : ${DIGICOM:=no} : ${FILE:=/tmp/data.tmp} : ${HZ:=50} : ${LETTERS:=no} : ${LETTERS2:=no} : ${LINE:=0} : ${LOOP:=0} : ${MODE:=COOKED_OUTPUT} : ${NBRD:=1} : ${PORTS:=} : ${PROMPT:=} : ${SIGNLE:=no} : ${T:=.d.tmp} : ${TNAME:=/dev/tty} : ${TEST:=2} : ${TMODE:=COOKED} : ${TTYPE:=OUTPUT} : ${S_VER:=v2.0} : ${test_done:=0} : ${setup_done:=0} ############################################################################### # functions # ############################################################################### nkill() { ps | grep $1 | awk '{ printf "kill "; print $1 }' >/tmp/kill.tmp$$ sh /tmp/kill.tmp$$ rm -f /tmp/kill.tmp$$ } cleanup() { [ $setup_done = 1 ] && nkill popen [ $setup_done = 1 ] && [ $LOOP = 1 ] && nkill cat [ $test_done = 1 ] && [ $TTYPE = INPUT ] && nkill tinput } stop() { [ $test_done = 1 ] && [ $TEST = 2 ] && nkill total } clear_page() { echo "\033[H\033[J\c" } bell() { echo "\c" } # # Page header # header() { lines=$1 clear_page echo " Terminal Subsystem Benchmarks $S_VER Multiple Port Tests " for i in $lines do echo done } getval() { while : do echo ${2}${3}${4}${5}${6}${7}${8}${9} >&2 read ans if [ $ans ] then break else ans=$1 ; break fi done } ports_build() { if [ "$ARNET" = "yes" ] then PORTS="a b c d" else if [ "$DIGICOM" = "yes" ] then PORTS="11 12 13 14 15 16 17 18" else if [ "$LETTERS" = "yes" ] then PORTS="a b c d e f g h" else if [ "$SINGLE" = "yes" ] then PORTS="0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15" else if [ "$AFTER4" = "yes" ] then PORTS="4 5 6 7 8 9 10 11 12 13 14 15" else if [ "$HEX" = "yes" ] then PORTS="0 1 2 3 4 5 6 7 8 9 a b c d e f" else if [ "$LETTERS2" = "yes" ] then PORTS="a b c d e f g h i j k l m n o p" else if [ "$SPECIALIX" = "yes" ] then PORTS="1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32" else PORTS="00 01 02 03 04 05 06 07 08 09 10 11 12 13 14 15" fi fi fi fi fi fi fi fi } ############################################################################### # main prgoram # ############################################################################### # # Trap processing Interrupt occurrs # trap 'echo Terminating Benchmarks; stop; cleanup; exit $STOP' 1 2 3 15 if [ ! -w /dev/mem ] then echo "Please become super user" exit 10 fi if [ ! -r /bin/time ] then echo "Please install the 'time' program from the development kit" exit 10 fi header echo "\ See /usr/tbench/README.bench for full details Select Board to Test 1. Standard Comms 2. Anvil Stallion / Brumby 3. Digicom 4. Wyse-995 5. RT Standard Comms 6. Computone 4 port 7. Computone 8 port 8. Bell Technologies ICC 9. Arnet Smartport 4 10. Arnet Smartport 8 11. Specialix SI 12. Chase Enter Selection ($DEFAULT) : \c" getval $DEFAULT "\c" DEFAULT=$ans case $DEFAULT in 1 ) NAME=com1 BRD_DIGIT=1 LETTERS=yes : ${NTERMS:=2} ;; 2 ) NAME=stallion BRD_DIGIT=0 GETBRD=yes : ${NTERMS:=8} ;; 3 ) NAME=digicom TNAME=/dev/ttyi GETBRD=yes DIGICOM=yes : ${NTERMS:=8} ;; 4 ) NAME=wyse-995 BRD_DIGIT=5 LETTERS=yes GETBRD=yes : ${NTERMS:=6} ;; 5 ) NAME=RT_comms : ${NTERMS:=2} SINGLE=yes GETBRD= ;; 6 ) NAME=Computone-X4P AFTER4=yes TNAME=/dev/ttya : ${NTERMS:=4} GETBRD= ;; 7 ) NAME=Computone-X8P HEX=yes TNAME=/dev/ttya : ${NTERMS:=8} GETBRD= ;; 8 ) NAME="Bell" LETTERS2=yes TNAME=/dev/ttyi : ${NTERMS:=6} GETBRD= ;; 9 ) NAME="Smartport-4" ARNET=yes TNAME=/dev/tty : ${NTERMS:=4} GETBRD= BRD_DIGIT=1 ;; 10 ) NAME="Smartport-8" LETTERS=yes TNAME=/dev/tty : ${NTERMS:=8} GETBRD= BRD_DIGIT=1 ;; 11) NAME="Specialix-SI" SPECIALIX=yes TNAME=/dev/ttya : ${NTERMS:=8} ;; 12) NAME="Chase" LETTERS=yes : ${NTERMS:=8} BRD_DIGIT=8 ;; * ) echo "Not supported" exit 255 ;; esac header a a a a [ $GETBRD ] && getval 1 "Please enter the number of boards to test (1) : \c" && NBRD=$ans getval $NTERMS "\nPlease enter the number of ports to test (" \ $NTERMS ") : \c" [ $NAME = com1 ] && NBRD=$ans ; NTERMS=1 [ $NAME != com1 ] && NTERMS=$ans getval $BAUD \ "\nPlease enter the required baud rate (" \ $BAUD ") : \c" BAUD=$ans getval $BLOCKS \ "\nPlease enter the size in Kbytes to input/output to each port (" \ $BLOCKS ") : \c" BLOCKS=$ans getval $TTYPE \ "\nSelect required test [INPUT, OUTPUT] (" \ $TTYPE ") : \c" TTYPE=$ans getval $TMODE \ "\nPlease enter the terminal mode [COOKED, RAW] (" \ $TMODE ") : \c" TMODE=$ans getval $LINE \ "\nPlease enter the terminal line discipline number (" \ $LINE ") : \c" LINE=$ans MODE=`echo ${TMODE}_${TTYPE} | tr '[a-z]' '[A-Z]'` export BAUD BRD_DIGIT BLOCKS HEX HZ LETTERS export LETTERS2 LINE NTERMS NBRD PORTS PROMPT export TNAME MODE TTYPE TMODE SINGLE header a a a a a a setup_done=1 ports_build ./tsetup || (cleanup ; exit 255) [ $TEST = 2 ] && header a a a a test_done=1 ./tbench${TEST} echo "Exiting benchmark, please wait ..." cleanup \Rogue\Monster\ else echo "will not over write ./tbench" fi if `test ! -s ./tbench1` then echo "writing ./tbench1" cat > ./tbench1 << '\Rogue\Monster\' #! /bin/sh # # Terminal Benchmark #1 # Test Output System Loading # # : ${BAUD:=exta} : ${DEBUG:=no} : ${FILE:=/tmp/data.tmp} : ${MODE:=COOKED_OUTPUT} : ${NBRD:=1} : ${NTERMS:=8} : ${SINGLE:=no} : ${T:=.d.tmp} : ${TNAME:=/dev/tty} : ${TMODE:=COOKED} : ${TTY:=/dev/null} : ${TTYPE:=OUTPUT} [ $BRD_DIGIT = none ] && BRD_DIGIT= clear_page() { echo "\033[H\033[J\c" } if [ ! -w /dev/mem ] then echo "Please become super user" exit 10 fi if [ ! -r /bin/time ] then echo "Please install the 'time' program from the development kit" exit 10 fi rm -f /tmp/bench clear_page echo "\ tbench1 Version 2.0 Terminal Load Benchmark `date '+%d/%m/%y %H:%m'`\ " : ${total:=`expr $NTERMS \* $NBRD`} if [ $total = 1 ] then echo "\nOutput Test copying to $total terminal port (using $MODE stty flags)\n" else echo "\nOutput Test copying to $total terminal ports (using $MODE stty flags)\n" fi echo " time (" b=0 brd=$BRD_DIGIT while [ $b -lt $NBRD ] do i=0 for t in $PORTS do if [ $i -ge $NTERMS ] then break fi if [ $TTYPE = INPUT ] then echo " tinput -b $BLOCKS ${TNAME}${brd}${t} &" echo " tinput -b $BLOCKS ${TNAME}${brd}${t} &" >>/tmp/bench else echo " cp $FILE ${TNAME}${brd}${t} &" echo " cp $FILE ${TNAME}${brd}${t} &" >>/tmp/bench fi i=`expr $i + 1` done brd=${brd:+`expr $brd + 1`} b=`expr $b + 1` done echo " )" echo "wait" >>/tmp/bench # # Output Banner # cat <<!EOF >/tmp/awk.tmp { printf " %-6s %6s\n", \$1, \$2 } !EOF cat <<!EOF1 >/tmp/awk2.tmp { if (\$2 ~ /:/) { ind = index(\$2, ":"); min = substr(\$2, 0, ind - 1); sec = substr(\$2, ind + 1, 99); sys = min * 60 + sec; } else { sys = \$2; } if (\$4 ~ /:/) { ind = index(\$4, ":"); min = substr(\$4, 0, ind - 1); sec = substr(\$4, ind + 1, 99); real = min * 60 + sec; } else { real = \$4; } printf " Total CPU consumed %4.1f %%\n", sys * 100.0 / real; } !EOF1 # # Execute the benchmark # time sh /tmp/bench 2>/tmp/bench.tmp if [ $? -ne 0 ] then echo "Benchmark error" else # # Format the output # grep -v "user" </tmp/bench.tmp | grep -v "^$" >/tmp/bench2.tmp echo awk -f /tmp/awk.tmp </tmp/bench2.tmp echo `grep sys /tmp/bench2.tmp` `grep real /tmp/bench2.tmp` | \ awk -f /tmp/awk2.tmp fi # # Tidy up # rm -f /tmp/bench /tmp/bench.tmp /tmp/bench2.tmp /tmp/awk.tmp /tmp/awk2.tmp rm -f $FILE \Rogue\Monster\ else echo "will not over write ./tbench1" fi if `test ! -s ./tbench2` then echo "writing ./tbench2" cat > ./tbench2 << '\Rogue\Monster\' #! /bin/sh # # Terminal Benchmark #2 # Test Output System Loading # # : ${BAUD:=9600} : ${DEBUG:=no} : ${FILE:=/tmp/data.tmp} : ${MODE:=COOKED_OUTPUT} : ${NBRD:=1} : ${NTERMS:=8} : ${PROMPT:=} : ${SINGLE:=no} : ${T:=.d.tmp} : ${TNAME:=/dev/tty} : ${TMODE:=COOKED} : ${TTY:=/dev/null} : ${TTYPE:=OUTPUT} : ${HEADER:="$TTYPE test : "} [ $BRD_DIGIT = none ] && BRD_DIGIT= [ -r /xenix ] && : ${XENIX_SW:=-x} clear_page() { echo "\033[H\033[J\c" } prompt() { echo "Press return when ready for benchmark : \c" read ans echo } if [ ! -w /dev/mem ] then echo "Please become super user" exit 10 fi if [ ! -r /bin/time ] then echo "Please install the 'time' program from the development kit" exit 10 fi bench_gen() { b=0 brd=$BRD_DIGIT while [ $b -lt $NBRD ] do i=0 for t in $PORTS do if [ $i -ge $NTERMS ] then break fi if [ $TTYPE = INPUT ] then echo "tinput -b $NBLOCKS ${TNAME}${brd}${t} &" else echo "cp $FILE ${TNAME}${brd}${t} &" fi i=`expr $i + 1` done brd=${brd:+`expr $brd + 1`} b=`expr $b + 1` done echo wait } # # Output Banner # cat <<!EOF >/tmp/awk.tmp { printf " %-6s %6s\n", \$1, \$2 } !EOF cat <<!EOF1 >/tmp/awk2.tmp { if (\$2 ~ /:/) { ind = index(\$2, ":"); min = substr(\$2, 0, ind - 1); sec = substr(\$2, ind + 1, 99); user = min * 60 + sec; } else user = \$2; if (\$4 ~ /:/) { ind = index(\$4, ":"); min = substr(\$4, 0, ind - 1); sec = substr(\$4, ind + 1, 99); sys = min * 60 + sec; } else sys = \$4; if (\$6 ~ /:/) { ind = index(\$6, ":"); min = substr(\$6, 0, ind - 1); sec = substr(\$6, ind + 1, 99); real = min * 60 + sec; } else real = \$6; printf " CPU used %4.1f%%", ((user + sys) * 100.0) / real; printf " (excludes time in device driver with\n"; printf " interrupts off)\n"; } !EOF1 cat <<!EOF2 >/tmp/awk3.tmp { if (\$4 ~ /:/) { ind = index(\$4, ":"); min = substr(\$4, 0, ind - 1); sec = substr(\$4, ind + 1, 99); real = min * 60 + sec; } else real = \$4; overhead = \$2; real = real - overhead; ports = \$5; bytes = \$10; printf "Benchmark overhead \n" printf "(accounted for) %4.1f\n", overhead; printf "Aggregate baud rate %7.0f\n", (bytes * ports * 10) / real; printf "Average baud rate %7.0f", (bytes * 10) / real; printf " (may exceed stated baud rate on\n"; printf " intelligent cards with large buffers\n"; } !EOF2 # # Execute the benchmark # : ${total:=`expr $NTERMS \* $NBRD`} [ $total = 1 ] && echo "$HEADER $total port \n" [ $total != 1 ] && echo "$HEADER $total ports \n" # # generate script for real benchmark # rm -f /tmp/bench /tmp/bench.null [ $TTYPE = INPUT ] && NBLOCKS=$BLOCKS ; export NBLOCKS bench_gen >/tmp/bench # # generate script for null benchmark (to test overhead) # OLD_FILE=$FILE; FILE=/dev/null; export FILE NBLOCKS=0; export NBLOCKS bench_gen >/tmp/bench.null FILE=$OLD_FILE; export FILE # # Cache all tools needed # time cp $FILE /dev/null 2>/dev/null # # do benchmark # time sh /tmp/bench.null 2>/tmp/overhead.tmp [ $PROMPT ] && prompt ./total $XENIX_SW & pid=$! time sh /tmp/bench 2>/tmp/result1.tmp if [ $? -ne 0 ] then echo "Benchmark error" kill -2 $! ; sleep 2 kill -3 $! else kill -2 $! ; sleep 2 kill -3 $! # # Format the output # grep -v "^$" </tmp/result1.tmp >/tmp/result2.tmp awk -f /tmp/awk.tmp </tmp/result2.tmp echo `grep user /tmp/result2.tmp` `grep sys /tmp/result2.tmp` \ `grep real /tmp/result2.tmp` | awk -f /tmp/awk2.tmp echo `grep real /tmp/overhead.tmp` `grep real /tmp/result2.tmp` \ $total `ls -l $FILE` | awk -f /tmp/awk3.tmp echo fi # # Tidy up # rm -f /tmp/bench /tmp/bench.null /tmp/result?.tmp /tmp/awk?.tmp /tmp/overhead.tmp rm -f /tmp/awk.tmp $FILE \Rogue\Monster\ else echo "will not over write ./tbench2" fi if `test ! -s ./tbench3` then echo "writing ./tbench3" cat > ./tbench3 << '\Rogue\Monster\' #! /bin/sh # # Terminal Benchmark #2 # Test Output System Loading # # : ${BAUD:=9600} : ${DEBUG:=no} : ${FILE:=/tmp/data.tmp} : ${MODE:=COOKED_OUTPUT} : ${NBRD:=1} : ${NTERMS:=8} : ${PROMPT:=} : ${SINGLE:=no} : ${T:=.d.tmp} : ${TNAME:=/dev/tty} : ${TMODE:=COOKED} : ${TTY:=/dev/null} : ${TTYPE:=OUTPUT} : ${HEADER:="$TTYPE test : "} [ $BRD_DIGIT = none ] && BRD_DIGIT= [ -r /xenix ] && : ${XENIX_SW:=-x} clear_page() { echo "\033[H\033[J\c" } prompt() { echo "Press return when ready for benchmark : \c" read ans echo } if [ ! -w /dev/mem ] then echo "Please become super user" exit 10 fi if [ ! -r /bin/time ] then echo "Please install the 'time' program from the development kit" exit 10 fi bench_gen() { b=0 brd=$BRD_DIGIT while [ $b -lt $NBRD ] do i=0 for t in $PORTS do if [ $i -ge $NTERMS ] then break fi if [ $TTYPE = INPUT ] then echo "tinput -b $NBLOCKS ${TNAME}${brd}${t} &" else echo "cp $FILE ${TNAME}${brd}${t} &" fi i=`expr $i + 1` done brd=${brd:+`expr $brd + 1`} b=`expr $b + 1` done echo wait } # # Output Banner # cat <<!EOF >/tmp/awk.tmp { printf " %-6s %6s\n", \$1, \$2 } !EOF cat <<!EOF1 >/tmp/awk2.tmp { if (\$2 ~ /:/) { ind = index(\$2, ":"); min = substr(\$2, 0, ind - 1); sec = substr(\$2, ind + 1, 99); user = min * 60 + sec; } else user = \$2; if (\$4 ~ /:/) { ind = index(\$4, ":"); min = substr(\$4, 0, ind - 1); sec = substr(\$4, ind + 1, 99); sys = min * 60 + sec; } else sys = \$4; if (\$6 ~ /:/) { ind = index(\$6, ":"); min = substr(\$6, 0, ind - 1); sec = substr(\$6, ind + 1, 99); real = min * 60 + sec; } else real = \$6; } !EOF1 cat <<!EOF2 >/tmp/awk3.tmp { if (\$4 ~ /:/) { ind = index(\$4, ":"); min = substr(\$4, 0, ind - 1); sec = substr(\$4, ind + 1, 99); real = min * 60 + sec; } else real = \$4; overhead = \$2; real = real - overhead; ports = \$5; bytes = \$10; printf "Aggregate baud rate %7.0f\n", (bytes * ports * 10) / real; printf "Average baud rate %7.0f", (bytes * 10) / real; } !EOF2 # # Execute the benchmark # : ${total:=`expr $NTERMS \* $NBRD`} [ $total = 1 ] && echo "$HEADER $total port \n" [ $total != 1 ] && echo "$HEADER $total ports \n" # # generate script for real benchmark # rm -f /tmp/bench /tmp/bench.null [ $TTYPE = INPUT ] && NBLOCKS=$BLOCKS ; export NBLOCKS bench_gen >/tmp/bench # # generate script for null benchmark (to test overhead) # OLD_FILE=$FILE; FILE=/dev/null; export FILE NBLOCKS=0; export NBLOCKS bench_gen >/tmp/bench.null FILE=$OLD_FILE; export FILE # # Cache all tools needed # time cp $FILE /dev/null 2>/dev/null # # do benchmark # time sh /tmp/bench.null 2>/tmp/overhead.tmp [ $PROMPT ] && prompt ./total $XENIX_SW & pid=$! time sh /tmp/bench 2>/tmp/result1.tmp if [ $? -ne 0 ] then echo "Benchmark error" kill -2 $! ; sleep 2 kill -3 $! else kill -2 $! ; sleep 2 kill -3 $! # # Format the output # grep -v "^$" </tmp/result1.tmp >/tmp/result2.tmp awk -f /tmp/awk.tmp </tmp/result2.tmp echo `grep user /tmp/result2.tmp` `grep sys /tmp/result2.tmp` \ `grep real /tmp/result2.tmp` | awk -f /tmp/awk2.tmp echo `grep real /tmp/overhead.tmp` `grep real /tmp/result2.tmp` \ $total `ls -l $FILE` | awk -f /tmp/awk3.tmp echo fi # # Tidy up # rm -f /tmp/bench /tmp/bench.null /tmp/result?.tmp /tmp/awk?.tmp /tmp/overhead.tmp rm -f /tmp/awk.tmp $FILE \Rogue\Monster\ else echo "will not over write ./tbench3" fi if `test ! -s ./tinput.c` then echo "writing ./tinput.c" cat > ./tinput.c << '\Rogue\Monster\' /* * port open program */ #include <stdio.h> #include <fcntl.h> /* * Main program and argument parsing */ #define MAXLINE 256 #define BLKSIZ 1024 char buf[MAXLINE]; char blk[BLKSIZ]; int blocks = -1; main(argc, argv) char **argv; { register int i; int errflg, c; FILE *fp; extern char *optarg; extern optind; errflg = 0; while ((c = getopt(argc, argv, "b:")) != EOF) switch(c) { case 'b': blocks = atoi(optarg); break; case '?': errflg++; break; } if (errflg || optind >= argc) { fprintf(stderr, "usage: tinput -b [blocks] files\n"); exit(2); } if ((fp = fopen(argv[optind], "r")) < 0) { fprintf(stderr, "tinput : cannot open %s\n", argv[optind]); exit(2); } if (blocks >= 0) block_input(fp, blocks); else for (;;) { if (fgets(buf, MAXLINE, fp) == NULL) exit(2); if (buf[0] == 'E' && buf[1] == 'O' && buf[2] == 'F') { buf[strlen(buf) - 1] = '\0'; if (strcmp(buf, "EOF!!") == 0) { break; } } } fclose(fp); exit(0); } block_input(fp, blocks) FILE *fp; { int got; long nchars; nchars = (long) blocks * BLKSIZ; while (nchars > 0) { if ((got = fread(buf, 1, BLKSIZ, fp)) <= 0) { fprintf(stderr, "tinput: fread error\n"); exit(255); } nchars -= got; } } \Rogue\Monster\ else echo "will not over write ./tinput.c" fi if `test ! -s ./total.c` then echo "writing ./total.c" cat > ./total.c << '\Rogue\Monster\' /* * total -- Real cpu availability */ #include <stdio.h> #include <signal.h> #include <fcntl.h> #if M_XENIX #include <sys/types.h> #include <sys/timeb.h> struct timeb tbuf; #endif /* * Main program and argument parsing */ #define FNAME "total.dat" #define TICKS_PER_SEC 50 #define MAXDELAY 50 #define NICE_CAL 1 #define NICE_RUN 39 unsigned long lcount; unsigned long start, finish; unsigned long rate; int period, calibrate, xenix, delay_inc; extern unsigned long sys_time(); extern int intrpt(); extern int report(); extern int quit(); main(argc, argv) char **argv; { register int i; int errflg, c, nvalue, old, iop; register FILE *fp; extern char *optarg; extern optind; errflg = 0; nvalue = -99; signal(SIGQUIT, quit); while ((c = getopt(argc, argv, "cxn:s:")) != EOF) switch(c) { case 'c': calibrate++; break; case 'n': nvalue = atoi(optarg); break; case 's': period = atoi(optarg); break; case 'x': xenix++; break; case '?': errflg++; break; } if (errflg) { fprintf(stderr, "usage: total -c -x -n [ nice value ] -s [sleep period]\n"); exit(2); } if (access("/xenix", 0) == 0) xenix++; if (nvalue == -99) if (calibrate) nvalue = NICE_CAL; else nvalue = NICE_RUN; lcount = 0; old = nice(0) + 20; nice(nvalue - old); if (calibrate) { if (period) { signal(SIGALRM, intrpt); alarm(period); } else signal(SIGINT, intrpt); sys_time(&start); loop(); } else { if ((fp = fopen(FNAME, "r")) < 0) { fprintf(stderr, "Cannot open %s\n", FNAME); exit(2); } fscanf(fp, "%ld", &rate); if (period) { signal(SIGALRM, report); alarm(period); } else signal(SIGINT, report); sys_time(&start); loop(); } } loop() { register int i; for (;;) { for (i = 0; i < MAXDELAY; i++) delay_inc++; lcount++; } } report() { unsigned long nticks; unsigned long persec; double cpu; sys_time(&finish); nticks = finish - start; if (nticks <= 0) { fprintf(stderr, "no time elapsed\n"); exit(2); } persec = (lcount * TICKS_PER_SEC) / nticks; if (persec > rate) persec = rate; cpu = ((double) persec * 100.0) / (double) rate; printf("Total CPU used %6.1f%%", 100.0 - cpu); printf(" (includes time in device driver with\n"); printf(" interrupts off)\n"); lcount = 0; if (period) { signal(SIGALRM, report); alarm(period); } else signal(SIGINT, report); sys_time(&start); } quit() { exit(0); } intrpt() { register FILE *fp; unsigned long nticks; sys_time(&finish); if ((fp = fopen(FNAME, "w")) < 0) { fprintf(stderr, "Cannot open %s\n", FNAME); exit(2); } nticks = finish - start; if (nticks <= 0) { fprintf(stderr, "no time elapsed\n"); exit(2); } printf("Calibrated to %s, %ld seconds, %ld\n", FNAME, nticks / TICKS_PER_SEC, (lcount * TICKS_PER_SEC) / nticks); fprintf(fp, "%ld\n", (lcount * TICKS_PER_SEC) / nticks); fclose(fp); exit(0); } unsigned long sys_time(tloc) unsigned long *tloc; { #if M_XENIX if (xenix) { ftime(&tbuf); *tloc = tbuf.time; *tloc *= TICKS_PER_SEC; *tloc += (tbuf.millitm / (1000 / TICKS_PER_SEC)); } else { #endif time(tloc); *tloc *= TICKS_PER_SEC; #if M_XENIX } #endif return(*tloc); } \Rogue\Monster\ else echo "will not over write ./total.c" fi if `test ! -s ./tsetup` then echo "writing ./tsetup" cat > ./tsetup << '\Rogue\Monster\' #! /bin/sh # # Terminal Benchmark setup program # See tbench and README.bench for details # # : ${AFTER4:=no} : ${BAUD:=exta} : ${BLOCKS:=20} : ${DEBUG:=no} : ${FILE:=/tmp/data.tmp} : ${HEX:=no} : ${LETTERS:=no} : ${LOOP:=0} : ${MODE:=COOKED_OUTPUT} : ${NBRD:=1} : ${SINGLE:=no} : ${T:=.d.tmp} : ${TNAME:=/dev/tty} : ${NTERMS:=8} : ${TMODE:=COOKED} : ${TTY:=/dev/null} : ${TTYPE:=OUTPUT} need_cat=0 [ $LOOP = 1 ] && need_cat=1 [ $LETTERS = yes ] && : ${BRD_DIGIT:=1} [ $LETTERS = no ] && : ${BRD_DIGIT:=0} [ $BRD_DIGIT = none ] && BRD_DIGIT= if [ ! -w /dev/mem ] then echo "Please become super user" exit 10 fi if [ ! -r /bin/time ] then echo "Please install the 'time' program from the development kit" exit 10 fi psetup() { err=1 case "$MODE" in COOKED_OUTPUT ) echo $BAUD sane -echo ixon -ixoff -ixany line $LINE; err=0 ;; RAW_OUTPUT ) echo $BAUD -icanon -opost -echo ixon -ixoff -ixany line $LINE; err=0 ;; COOKED_INPUT ) echo $BAUD sane -echo ixon ixoff -ixany line $LINE; err=0 ;; RAW_INPUT ) echo $BAUD -icanon -opost -echo ixon ixoff -ixany line $LINE; err=0 ;; esac [ $err = 1 ] && echo "Unknown mode $MODE" 1>&2 && exit 255 } arg_build() { b=0 brd=$BRD_DIGIT while [ $b -lt $NBRD ] do i=0 args= for t in $PORTS do if [ $i -ge $NTERMS ] then break fi args="$args ${TNAME}${brd}${t}" if [ $need_cat = 1 ] then cat >$TTY <${TNAME}${brd}${t} & fi i=`expr $i + 1` done echo opening $args ./popen $args & b=`expr $b + 1` brd=${brd:+`expr $brd + 1`} done } data() { HOM=`pwd` cd /tmp # # Create test data file # cat <<!EOF3 >$T aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb cccccccccccccccccccccccccccccccccccccccc cccccccccccccccccccccccccccccccccccccccc dddddddddddddddddddddddddddddddddddddddd dddddddddddddddddddddddddddddddddddddddd eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee ffffffffffffffffffffffffffffffffffffffff ffffffffffffffffffffffffffffffffffffffff gggggggggggggggggggggggggggggggggggggggg gggggggggggggggggggggggggggggggggggggggg hhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhh hhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhhh iiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiii iiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiiii jjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjj jjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjj kkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkk kkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkkk llllllllllllllllllllllllllllllllllllllll llllllllllllllllllllllllllllllllllllllll mmmmmmmmmmmmmmm !EOF3 >$FILE i=0 while [ $i -lt $BLOCKS ] do cat $T $T $T $T $T $T $T $T $T $T >>$FILE i=`expr $i + 10` done [ $TTYPE = INPUT ] && echo 'EOF!!\n' >>$FILE rm -f $T cd $HOM } echo "Setting terminal modes ..." psetup >modes.dat arg_build [ $TTYPE = OUTPUT ] && echo "Create test data file ..." && data echo "Setup done" rm -f modes.dat \Rogue\Monster\ else echo "will not over write ./tsetup" fi echo "Finished archive 1 of 1" # if you want to concatenate archives, remove anything after this line exit -- John Pettitt, Specialix, Giggs Hill Rd, Thames Ditton, Surrey, U.K., KT7 0TR {backbone}!ukc!slxsys!jpp jpp%slxinc@uunet.uu.net jpp@specialix.co.uk Tel: +44-1-941-2564 Fax: +44-1-941-4098 Telex: 918110 SPECIX G >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>><<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<