!Integer methodsFor: 'benchmarks'!

tinyBenchmarks
    "Report the results of running the two tiny Squeak benchmarks.
     
     The following table lists results for various Smalltalks on a
     300 MHz PentiumII PC under Windows NT 4.0, Service Pack 4 (Windoze
     has more Smalltalks running on it than a cool OS such as Linux...).
     Take these results with a grain of salt -- Squeak and Dolphin are
     bytecode interpreters, VisualWorks and IBM Smalltalk are dynamic
     compilers to native code, Smalltalk MT is a static compiler to
     native code.
     
     Notes:
     a) whatever the Squeak team says, coding the virtual machine in
     Smalltalk nicely kills performance by 25% relative to GST; and
     consider that the implementation of object memory in Squeak is
     a modern one with 32-bit direct pointers.  This leads to...
     b) An object table does hinder performance of course, but not
     that much.  VisualWorks is still 25% faster than IBM Smalltalk,
     and even 40% in the `send message' benchmark where the object
     table should penalize it more.  This in turn leads to...
     c) Squeak too is `at home' there, because of the absence of object
     table, but a few tricks in GNU Smalltalk (e.g. the non-Blue
     Book interpretation of return bytecodes, and stack-like handling
     of LIFO execution paths) allow it to gain more speed.  The gap
     with Dolphin is getting narrower and narrower -- but Dolphin is
     not as portable as Squeak and GNU Smalltalk, as it is written in
     assembly language.
     d) Smalltalk MT's sending performance is poor because numbers
     were obtained evaluating the benchmarks from the Transcript,
     which activates a non-optimized builds -- creating an indipendent
     executable would bring numbers considerably higher.  Not owning
     a copy Smalltalk MT I cannot do that and correct the figures.

	 ,--- (B)ytecode interpreter, (J)IT compiler, static (C)ompiler
	/ ,-- Uses (D)irect or (I)ndirect pointers
       / /
     ././.---------------------.---------------------.-----------------.
     |B|D| Squeak              | 13.8 Mbytecodes/sec |  810 Ksends/sec |
     |B|I| Dolphin Smalltalk   | 17.4 Mbytecodes/sec | 1112 Ksends/sec |
     |B|I| GST (with GCC)      | 18.8 Mbytecodes/sec | 1022 Ksends/sec |
     |J|D| IBM Smalltalk 3.0   | 61.9 Mbytecodes/sec | 4224 Ksends/sec |
     |J|I| VisualWorks         | 81.8 Mbytecodes/sec | 5950 Ksends/sec |
     |C|?| Smalltalk MT        |  128 Mbytecodes/sec | 1076 Ksends/sec |
     '-'-----------------------'---------------------'-----------------'"


    | t1 t2 r n1 n2 |
    n1 _ 1 bitShift: self.
    [t1 _ Time millisecondsToRun: [n1 benchmark].
     t1 < 5000] whileTrue:[ Smalltalk compact. n1 _ n1 * 2 ].

    n2 _ 24 + self.
    [t2 _ Time millisecondsToRun: [r _ n2 benchFib].
     t2 < 5000] whileTrue:[ Smalltalk compact. n2 _ n2 + 1 ].

    ^ ((n1 * 500000 * 1000) // t1) printString, ' bytecodes/sec; ',
      ((r * 1000) // t2) printString, ' sends/sec'!

benchFib
    "Handy send-heavy benchmark -- result is number of sends:
     (result // seconds to run) = approx calls per second"
    ^ self < 2
	ifTrue: [1] 
	ifFalse: [(self - 1) benchFib + (self - 2) benchFib + 1]
!

benchmark
	"Handy bytecode-heavy benchmark -- approx 500000 bytecodes per run:
	 (500000 * times ran // secs to run) = approx bytecodes per second"

    | size flags prime k count |
    size _ 8190.
    flags _ Array new: size.
    self timesRepeat: [
	count _ 0.
	flags atAllPut: true.
	1 to: size do:
	    [:i | (flags at: i) ifTrue:
		[prime _ i+1.
		k _ i + prime.
		[k <= size] whileTrue:
		    [flags at: k put: false.
		    k _ k + prime].
		count _ count + 1]]].
    ^ count
! !

Transcript showCr: 8 tinyBenchmarks!