Re: OpenMP parallel plugins in a single-threaded Cog VM

Tobias Pape via Squeak-dev <[email protected]> Sun, 5 Jul 2026 17:31:53 +0200
Newsgroups gmane.comp.lang.smalltalk.squeak.general
Message-ID <[email protected]>
Nice!
-t

> On 4. Jul 2026, at 12:19, Lauren Pullen <[email protected]> wrote:
> 
> Hi List,
> 
> I've been experimenting with using OpenMP to boost the performance of primitives in places where arranging to use SIMD is a hassle.
> 
> % ~/program/opensmalltalk-vm/building/macos64ARMv8/squeak.cog.spur/Squeak.app/Contents/MacOS/Squeak ./Spur64VMMaker-3756-sq23799.image simdExample2.st
> SIMDPlugin example2 "A*B+C".
> Size:     SIMD:                OpenMP:              Cogit:
> --------- -------------------- -------------------- --------------------
>    1,000 0:00:00:00.000000816 0:00:00:00.000037184 0:00:00:00.000006640
>   10,000 0:00:00:00.000002327 0:00:00:00.000029708 0:00:00:00.000066726
>  100,000 0:00:00:00.000023785 0:00:00:00.000034158 0:00:00:00.000671026
> 1,000,000 0:00:00:00.000242202 0:00:00:00.000149838 0:00:00:00.006793125
> 
> For a hardware instruction like fmadd.2d, SIMD is a clear winner, and then only loses out marginally to OpenMP under very large vector sizes. (It's starting at 10 million elements that Squeak starts to have trouble, first in Cogit, then in bulk primitives as well.  It's probably Mac virtual memory choking on an 80 million byte array.)
> 
> 
> In the ray tracer, the computation is a bit more involved than a few loads and a single fmadd.2d operation.  I tweaked the build script to use -O3 instead of -Os; this is what I get for computing the intermediate states for a 320x240 pixel view (the argument to the primitive is the number of hardware threads to use):
> 
> [self primIntermediate_compute: 1] benchFor: 2 seconds.
> '1,380 per second. 725 microseconds per run. 0 % GC time.' .
> [self primIntermediate_compute: 2] benchFor: 2 seconds.
> '2,680 per second. 373 microseconds per run. 0 % GC time.' .
> [self primIntermediate_compute: 4] benchFor: 2 seconds.
> '5,210 per second. 192 microseconds per run. 0 % GC time.' .
> [self primIntermediate_compute: 8] benchFor: 2 seconds.
> '5,350 per second. 187 microseconds per run. 0 % GC time.' .
> [self primIntermediate_compute: 10] benchFor: 2 seconds.
> '5,490 per second. 182 microseconds per run. 0 % GC time.' .
> 
> 
> Importantly, this doesn't crash the VM!  OpenMP ensures that only one thread actually returns to the interpreter loop, so smalltalk only ever sees 1 hardware thread accessing object memory.
> Squeak-dev mailing list -- [email protected]
> To unsubscribe send an email to [email protected]

Squeak-dev mailing list -- [email protected]
To unsubscribe send an email to [email protected]