rer@vaximile.UUCP (R.RICHARDSON) (10/15/85)
/* * "DHRYSTONE" Benchmark Program * * Version: C/1 * Date: 12/01/84, RESULTS updated 10/15/85 * Author: Reinhold P. Weicker, CACM Vol 27, No 10, 10/84 pg. 1013 * Translated from ADA by Rick Richardson * Every method to preserve ADA-likeness has been used, * at the expense of C-ness. * Compile: cc -O dry.c -o drynr : No registers * cc -O -DREG=register dry.c -o dryr : Registers * Defines: Defines are provided for old C compiler's * which don't have enums, and can't assign structures. * The time(2) function is library dependant; One is * provided for CI-C86. Your compiler may be different. * Run: drynr; dryr * 50000 Runs are made and the time is printed * Results: If you get any new machine/OS results, please send to: * ..!houxm!vaximile!rer * and thanks to all that do. Space prevents listing * the names of those who have provided some of these * results. * * MACHINE MICROPROCESSOR OPERATING COMPILER DHRYSTONES/SEC. * TYPE SYSTEM NO REG REGS * -------------------------- ------------ ----------- --------------- * IBM PC/XT 8088-4.77Mhz PCDOS 2.1 CI-C86 2.1 ???? ???? * IBM PC/XT 8088-4.77Mhz PC/IX cc ???? ???? * Lisa 68000-7.7Mhz ???? ?? ???? ???? * IBM PC/XT 8088-4.77Mhz VENIX/86 2.0 cc 297 324 * ATT PC6300 8086-8Mhz MSDOS 2.11 b16cc 2.0 632 684 * IBM PC/AT 80286-6Mhz PCDOS 3.0 CI-C86 2.1 666 684 * Macintosh 68000-7.7Mhz - MegaMax C 2.0 661 709 * ATT PC6300 8086-8Mhz MSDOS 2.11 CI-C86 2.20M 769 769 * ATT 3B2/300 MAC32-?Mhz UNIX 5.0.2 cc 735 806 * Fast Mac 68000-7.7Mhz - MegaMax C 2.0 839 904 + * IBM PC/AT 80286-6Mhz VENIX/86 2.1 cc 961 1000 * VAX 11/750 - VMS VAX-11 C 2.0 958 1091 * ATT PC7300 68010-10Mhz UNIX 5.2 cc 1041 1111 * Sun2/120 68010-10Mhz Sun 4.2BSD cc 1136 1219 * PDP 11/70 - UNIX 5.2 cc 1162 1250 * IBM PC/AT 80286-7.5Mhz VENIX/86 2.1 cc 1190 1315 * * VAX 11/780 - UNIX 5.2 cc 1515 1562 * ATT 3B20 - UNIX 5.2 cc 1515 1724 * Gould PN6005 - UTX 1.1(4.2BSD) cc 1675 1964 * Amdahl 580 - UTS 5.0 Rel 1.2 cc Ver. 1.5 23076 23076 * * * 15Mhz crystal substituted for original 12Mhz; * + This Macintosh was upgraded from 128K to 512K in such a way that * the new 384K of memory is not slowed down by video generator accesses. * ************************************************************************** * * The following program contains statements of a high-level programming * language (C) in a distribution considered representative: * * assignments 53% * control statements 32% * procedure, function calls 15% * * 100 statements are dynamically executed. The program is balanced with * respect to the three aspects: * - statement type * - operand type (for simple data types) * - operand access * operand global, local, parameter, or constant. * * The combination of these three aspects is balanced only approximately. * * The program does not compute anything meaningfull, but it is * syntactically and semantically correct. * */ /* Compiler dependent options */ #undef NOENUM /* Define if compiler has no enum's */ #undef NOSTRUCTASSIGN /* Define if compiler can't assign structures */ #undef NOTIME /* Define if no time() function in library */ #ifdef NOSTRUCTASSIGN #define structassign(d, s) memcpy(&(d), &(s), sizeof(d)) #else #define structassign(d, s) d = s #endif #ifdef NOENUM #define Ident1 1 #define Ident2 2 #define Ident3 3 #define Ident4 4 #define Ident5 5 typedef int Enumeration; #else typedef enum {Ident1, Ident2, Ident3, Ident4, Ident5} Enumeration; #endif typedef int OneToThirty; typedef int OneToFifty; typedef char CapitalLetter; typedef char String30[31]; typedef int Array1Dim[51]; typedef int Array2Dim[51][51]; struct Record { struct Record *PtrComp; Enumeration Discr; Enumeration EnumComp; OneToFifty IntComp; String30 StringComp; }; typedef struct Record RecordType; typedef RecordType * RecordPtr; typedef int boolean; #define NULL 0 #define TRUE 1 #define FALSE 0 #ifndef REG #define REG #endif extern Enumeration Func1(); extern boolean Func2(); main() { Proc0(); } /* * Package 1 */ int IntGlob; boolean BoolGlob; char Char1Glob; char Char2Glob; Array1Dim Array1Glob; Array2Dim Array2Glob; RecordPtr PtrGlb; RecordPtr PtrGlbNext; Proc0() { OneToFifty IntLoc1; REG OneToFifty IntLoc2; OneToFifty IntLoc3; REG char CharLoc; REG char CharIndex; Enumeration EnumLoc; String30 String1Loc; String30 String2Loc; #define LOOPS 50000 long time(); long starttime; long benchtime; long nulltime; register unsigned int i; starttime = time(0); for (i = 0; i < LOOPS; ++i); nulltime = time(0) - starttime; PtrGlbNext = (RecordPtr) malloc(sizeof(RecordType)); PtrGlb = (RecordPtr) malloc(sizeof(RecordType)); PtrGlb->PtrComp = PtrGlbNext; PtrGlb->Discr = Ident1; PtrGlb->EnumComp = Ident3; PtrGlb->IntComp = 40; strcpy(PtrGlb->StringComp, "DHRYSTONE PROGRAM, SOME STRING"); /***************** -- Start Timer -- *****************/ starttime = time(0); for (i = 0; i < LOOPS; ++i) { Proc5(); Proc4(); IntLoc1 = 2; IntLoc2 = 3; strcpy(String2Loc, "DHRYSTONE PROGRAM, 2'ND STRING"); EnumLoc = Ident2; BoolGlob = ! Func2(String1Loc, String2Loc); while (IntLoc1 < IntLoc2) { IntLoc3 = 5 * IntLoc1 - IntLoc2; Proc7(IntLoc1, IntLoc2, &IntLoc3); ++IntLoc1; } Proc8(Array1Glob, Array2Glob, IntLoc1, IntLoc3); Proc1(PtrGlb); for (CharIndex = 'A'; CharIndex <= Char2Glob; ++CharIndex) if (EnumLoc == Func1(CharIndex, 'C')) Proc6(Ident1, &EnumLoc); IntLoc3 = IntLoc2 * IntLoc1; IntLoc2 = IntLoc3 / IntLoc1; IntLoc2 = 7 * (IntLoc3 - IntLoc2) - IntLoc1; Proc2(&IntLoc1); /***************** -- Stop Timer -- *****************/ } benchtime = time(0) - starttime - nulltime; printf("Dhrystone time for %ld passes = %ld\n", (long) LOOPS, benchtime); printf("This machine benchmarks at %ld dhrystones/second\n", ((long) LOOPS) / benchtime); } Proc1(PtrParIn) REG RecordPtr PtrParIn; { #define NextRecord (*(PtrParIn->PtrComp)) structassign(NextRecord, *PtrGlb); PtrParIn->IntComp = 5; NextRecord.IntComp = PtrParIn->IntComp; NextRecord.PtrComp = PtrParIn->PtrComp; Proc3(NextRecord.PtrComp); if (NextRecord.Discr == Ident1) { NextRecord.IntComp = 6; Proc6(PtrParIn->EnumComp, &NextRecord.EnumComp); NextRecord.PtrComp = PtrGlb->PtrComp; Proc7(NextRecord.IntComp, 10, &NextRecord.IntComp); } else structassign(*PtrParIn, NextRecord); #undef NextRecord } Proc2(IntParIO) OneToFifty *IntParIO; { REG OneToFifty IntLoc; REG Enumeration EnumLoc; IntLoc = *IntParIO + 10; for(;;) { if (Char1Glob == 'A') { --IntLoc; *IntParIO = IntLoc - IntGlob; EnumLoc = Ident1; } if (EnumLoc == Ident1) break; } } Proc3(PtrParOut) RecordPtr *PtrParOut; { if (PtrGlb != NULL) *PtrParOut = PtrGlb->PtrComp; else IntGlob = 100; Proc7(10, IntGlob, &PtrGlb->IntComp); } Proc4() { REG boolean BoolLoc; BoolLoc = Char1Glob == 'A'; BoolLoc |= BoolGlob; Char2Glob = 'B'; } Proc5() { Char1Glob = 'A'; BoolGlob = FALSE; } extern boolean Func3(); Proc6(EnumParIn, EnumParOut) REG Enumeration EnumParIn; REG Enumeration *EnumParOut; { *EnumParOut = EnumParIn; if (! Func3(EnumParIn) ) *EnumParOut = Ident4; switch (EnumParIn) { case Ident1: *EnumParOut = Ident1; break; case Ident2: if (IntGlob > 100) *EnumParOut = Ident1; else *EnumParOut = Ident4; break; case Ident3: *EnumParOut = Ident2; break; case Ident4: break; case Ident5: *EnumParOut = Ident3; } } Proc7(IntParI1, IntParI2, IntParOut) OneToFifty IntParI1; OneToFifty IntParI2; OneToFifty *IntParOut; { REG OneToFifty IntLoc; IntLoc = IntParI1 + 2; *IntParOut = IntParI2 + IntLoc; } Proc8(Array1Par, Array2Par, IntParI1, IntParI2) Array1Dim Array1Par; Array2Dim Array2Par; OneToFifty IntParI1; OneToFifty IntParI2; { REG OneToFifty IntLoc; REG OneToFifty IntIndex; IntLoc = IntParI1 + 5; Array1Par[IntLoc] = IntParI2; Array1Par[IntLoc+1] = Array1Par[IntLoc]; Array1Par[IntLoc+30] = IntLoc; for (IntIndex = IntLoc; IntIndex <= (IntLoc+1); ++IntIndex) Array2Par[IntLoc][IntIndex] = IntLoc; ++Array2Par[IntLoc][IntLoc-1]; Array2Par[IntLoc+20][IntLoc] = Array1Par[IntLoc]; IntGlob = 5; } Enumeration Func1(CharPar1, CharPar2) CapitalLetter CharPar1; CapitalLetter CharPar2; { REG CapitalLetter CharLoc1; REG CapitalLetter CharLoc2; CharLoc1 = CharPar1; CharLoc2 = CharLoc1; if (CharLoc2 != CharPar2) return (Ident1); else return (Ident2); } boolean Func2(StrParI1, StrParI2) String30 StrParI1; String30 StrParI2; { REG OneToThirty IntLoc; REG CapitalLetter CharLoc; IntLoc = 1; while (IntLoc <= 1) if (Func1(StrParI1[IntLoc], StrParI2[IntLoc+1]) == Ident1) { CharLoc = 'A'; ++IntLoc; } if (CharLoc >= 'W' && CharLoc <= 'Z') IntLoc = 7; if (CharLoc == 'X') return(TRUE); else { if (strcmp(StrParI1, StrParI2) > 0) { IntLoc += 7; return (TRUE); } else return (FALSE); } } boolean Func3(EnumParIn) REG Enumeration EnumParIn; { REG Enumeration EnumLoc; EnumLoc = EnumParIn; if (EnumLoc == Ident3) return (TRUE); return (FALSE); } #ifdef NOSTRUCTASSIGN memcpy(d, s, l) register char *d; register char *s; int l; { while (l--) *d++ = *s++; } #endif /* * Library function for compilers with no time(2) function in the * library. */ #ifdef NOTIME long time(p) long *p; { /* CI-C86 time function - don't use around midnight */ long t; struct regval {unsigned int ax,bx,cx,dx,si,di,ds,es; } regs; regs.ax = 0x2c00; sysint21(®s, ®s); t = ((regs.cx>>8)*60L + (regs.cx & 0xff))*60L + (regs.dx>>8); if (p) *p = t; return t; } #endif
chris@umcp-cs.UUCP (Chris Torek) (10/17/85)
Here are some changes to get more accurate results under 4.2 and 4.3 BSD; and here is the result of running the benchmarks on our shiny new 8600 (not yet even fully installed, but already running 4.3BSD... for the moment, at least): * MACHINE MICROPROCESSOR OPERATING COMPILER DHRYSTONES/SEC. * TYPE SYSTEM NO REG REGS * -------------------------- ------------ ----------- --------------- * VAX 8600 - 4.3BSD cc 7092 7153 The speed of the 8600 is quite impressive. Oh yes, the changes. Without these I get 7142 for both `NO REG' and `REG', by the way. *** dry.c.old Thu Oct 17 01:55:55 1985 --- dry.c Thu Oct 17 02:23:02 1985 *************** *** 156,166 **** #define LOOPS 50000 long time(); ! long starttime; ! long benchtime; ! long nulltime; register unsigned int i; ! starttime = time(0); for (i = 0; i < LOOPS; ++i); ! nulltime = time(0) - starttime; PtrGlbNext = (RecordPtr) malloc(sizeof(RecordType)); --- 156,167 ---- #define LOOPS 50000 long time(); ! long starttime, startmil; ! long benchtime, benchmil; ! long nulltime, nullmil; register unsigned int i; ! gettime(&starttime, &startmil); for (i = 0; i < LOOPS; ++i); ! gettime(&nulltime, &nullmil); ! timesub(&nulltime, &nullmil, starttime, startmil); PtrGlbNext = (RecordPtr) malloc(sizeof(RecordType)); *************** *** 175,179 **** -- Start Timer -- *****************/ ! starttime = time(0); for (i = 0; i < LOOPS; ++i) { --- 176,180 ---- -- Start Timer -- *****************/ ! gettime(&starttime, &startmil); for (i = 0; i < LOOPS; ++i) { *************** *** 206,213 **** *****************/ } ! benchtime = time(0) - starttime - nulltime; ! printf("Dhrystone time for %ld passes = %ld\n", (long) LOOPS, benchtime); ! printf("This machine benchmarks at %ld dhrystones/second\n", ! ((long) LOOPS) / benchtime); } --- 207,217 ---- *****************/ } ! gettime(&benchtime, &benchmil); ! timesub(&benchtime, &benchmil, starttime, startmil); ! timesub(&benchtime, &benchmil, nulltime, nullmil); ! printf("Dhrystone time for %ld passes = %ld.%03d\n", (long) LOOPS, ! benchtime, benchmil); ! printf("This machine benchmarks at %8.0f dhrystones/second\n", ! (double)LOOPS / ((double)benchtime + (benchmil / 1000.0))); } *************** *** 415,417 **** --- 419,481 ---- return t; } + #endif + + #include <signal.h> /* horrible hack to detect 4.[23]BSD */ + #ifdef SIGVTALRM + #define GETTIMEOFDAY + #endif + + /* + * Gettime gets the time in seconds and milliseconds. timesub subtracts + * the second time (in sec, mil) from the first (sec, mil). + */ + #ifndef GETTIMEOFDAY + + gettime(s, m) + long *s, *m; + { + + (void) time(s); + *m = 0; + } + + timesub(ds, dm, s, m) + long *ds, *dm, s, m; + { + + *ds -= s; + } + + #else + + #include <sys/time.h> + + gettime(s, m) + long *s, *m; + { + struct timeval now; + + if (gettimeofday(&now, (struct timezone *)0)) + perror("gettimeofday"), exit(1); + *s = now.tv_sec; + *m = now.tv_usec / 1000; + } + + /* + * N.B.: we assume 0 <= m < 1000. + */ + timesub(ds, dm, s, m) + long *ds, *dm, s, m; + { + register long s1 = *ds, m1 = *dm; + + s1 -= s; + if ((m1 -= m) < 0) { + s1--; + m1 += 1000; + } + *ds = s1; + *dm = m1; + } + #endif -- In-Real-Life: Chris Torek, Univ of MD Comp Sci Dept (+1 301 454 4251) UUCP: seismo!umcp-cs!chris CSNet: chris@umcp-cs ARPA: chris@mimsy.umd.edu
frank@sagan.UUCP (Frank Whaley) (10/18/85)
I've tried mailing this, but my uuxqt urps on the path to rer. * MACHINE MICROPROCESSOR OPERATING COMPILER DHRYSTONES/SEC. * TYPE SYSTEM NO REG REGS * -------------------------- ------------ ----------- --------------- * IBM PC/XT 8088-4.77Mhz VENIX/86 2.0 cc 297 324 * Cosmos 68000-8Mhz UniSoft cc 305 322 * IBM PC/XT 8086-4.54Mhz PCDOS 3.1 Lattice 2.15 373 - @ * IBM PC/XT 8088-4.77Mhz PCDOS 2.1 Lattice 2.15 403 - @ * ATT PC6300 8086-8Mhz MSDOS 2.11 b16cc 2.0 632 684 * Macintosh 68000-7.7Mhz - MegaMax C 2.0 661 709 * IBM PC/AT 80286-6Mhz PCDOS 3.0 CI-C86 2.1 666 684 * Macintosh 68000-7.8Mhz 2M Mac Rom Mac C 32 bit int 694 704 * IBM PC/XT 8086-9.54Mhz PCDOS 3.1 Microsoft 3.0 724 781 * ATT 3B2/300 MAC32-?Mhz UNIX 5.0.2 cc 735 806 * NEC PC9801F 8086-8Mhz PCDOS 2.11 Lattice 2.15 768 - @ * ATT PC6300 8086-8Mhz MSDOS 2.11 CI-C86 2.20M 769 769 * Fast Mac 68000-7.7Mhz - MegaMax C 2.0 839 904 + * VAX 11/750 - Unix 4.2bsd cc 862 877 * Macintosh 68000-7.8Mhz 2M Mac Rom Mac C 16 bit int 877 909 * IBM PC/XT 8086-9.54Mhz PCDOS 3.1 Microsoft 3.0 724 781 * IBM PC/XT 8086-9.54Mhz PCDOS 3.1 Wizard 2.1 877 980 * IBM PC/XT 8086-9.54Mhz PCDOS 3.1 Wizard 2.1 877 980 * VAX 11/750 - VMS VAX-11 C 2.0 958 1091 * IBM PC/AT 80286-6Mhz VENIX/86 2.1 cc 961 1000 * IBM PC/XT 8086-9.54Mhz PCDOS 3.1 Lattice 2.15 980 - @ * ATT PC7300 68010-10Mhz UNIX 5.2 cc 1041 1111 * IBM PC/AT 80286-6Mhz PCDOS 3.1 Microsoft 3.0 1063 1086 * Sun2/120 68010-10Mhz Sun 4.2BSD cc 1136 1219 * PDP 11/70 - UNIX 5.2 cc 1162 1250 * IBM PC/AT 80286-7.5Mhz VENIX/86 2.1 cc 1190 1315 * * IBM PC/AT 80286-6Mhz PCDOS 3.1 Lattice 2.15 1250 - @ * VAX 11/780 - UNIX 5.2 cc 1515 1562 * ATT 3B20 - UNIX 5.2 cc 1515 1724 * uVAX-II - ? ? 1574 1582 * Gould PN6005 - UTX 1.1(4.2BSD) cc 1675 1964 * HP9000-500 B series CPU HP-UX 4.02 cc 1724 - * Pyramid 90x - OSx 2.5 cc 3125 3125 * SUN 3/75 68020-16.67Mhz SUN 4.2 V3 cc 3333 3571 * Amdahl 580 - UTS 5.0 Rel 1.2 cc Ver. 1.5 23076 23076 * * * 15Mhz crystal substituted for original 12Mhz; * @ vanilla Lattice compiler used with MicroPro standard library * + This Macintosh was upgraded from 128K to 512K in such a way that * the new 384K of memory is not slowed down by video generator accesses. * * The important ones (to me): * IBM PC/XT 8086-9.54Mhz PCDOS 3.1 Microsoft 3.0 819 877 * IBM PC/XT 8086-9.54Mhz PCDOS 3.1 Wizard 2.1 877 980 * IBM PC/XT 8086-9.54Mhz PCDOS 3.1 Lattice 2.15 980 - @ -- frank ... Frank Whaley, MicroPro Product Development {dual,hplabs,glacier,lll-crg}!well!micropro!sagan!frank "The heights by great men reached and kept, were not attained by sudden flight. But they, while their companions slept, were toiling upward in the night." -Longfellow