[squeak-dev] Not Squeak but... Ni goes multithreaded

David T. Lewis lewis at mail.msen.com
Tue Feb 2 13:48:06 UTC 2016


Are the numbers in the factorial example values on the stack, or are
they "objects" in the Smalltalk sense? I'm curious how Ni might be
approaching a shared object space for the interpreters.

Thanks for posting.

On Tue, Feb 02, 2016 at 01:40:03PM +0100, G??ran Krampe wrote:
> Hey guys!
> I am unfortunately not hacking in Squeak/Pharo anymore but I am instead 
> playing along with my Ni-language in my spare time. But the Squeak 
> community is still very dear to me and I just couldn't help sharing some 
> fun I had last night! ;)
> As we all know native threads (multicore) and Smalltalk is not a "common 
> combo" but Ni is now sporting a first trivial native threading mechanism!
> Last night I threw together a first hack on utilizing the native 
> threadpool module in the underlying Nim. So in the REPL this works:
> gokr at yoda:~/nim/ni/src$ ./nirepl
> We are the knights who say... Ni! Enter shrubbary... eh, code and
> an empty line will evaluate previous lines, so hit enter twice.
> >>>5 timesRepeat: [spawn [echo "yo"]]
> >>>
> yo
> yo
> yo
> yo
> yo
> nil
> >>>
> The "nil" at the end is the return value from timesRepeat: so nothing 
> "wrong". If the code looks odd (spawn and echo) it's because Ni can use 
> prefix syntax for functions as well as Smalltalkish style.
> This is "shared nothing" threading, the spawned block gets run in a 
> completely separate instance of the Ni interpreter inside its own native 
> thread. The code block passed over is deep copied. Each native thread 
> has its own GC etc. Of course Nim has MUCH more advanced mechanisms for 
> intercommunication so... this is just a toe dipping.
> ...but the larger commented trixier example below runs fine too!
> Next up is probably to try to make Ni "stackless" (rewrite the 
> interpreter so that it doesn't nest the calls so). This would enable 
> even more fun stuff.
> regards, G??ran
> ---------------------------------
> # This is called a block in Ni. It is like an OrderedCollection.
> # At this point the block is just a series of nested words and literals.
> # Assignment is actually an infix function!
> code = [
>   # This is a local function to recursively calculate factorial.
>   # ifelse is currently a 3-argument prefix function, but Ni could use
>   # Smalltalk syntax for that too.
>   factorial = func [
>     # Arguments are sucked in as we go, so no need to declare n first
>     ifelse (:n > 0)
>       [n * factorial (n - 1)]
>       [1]
>   ]
>   # Echo is a prefix function.
>   echo factorial 1
> ]
> # Ni has keyword messages that can take the first argument from the left.
> # Ni also has closures and non local returns so we can implement 
> Smalltalkish
> # control structures and things like select: or reject: easily. Or we 
> can write
> # them as Nim primitive functions.
> 10 timesRepeat: [
>   # Ni is homoiconic so we can modify the block as if it is code.
>   # We remove the last element of the code block (the number) and add
>   # a random number from 1-20.
>   code removeLast
>   # In Ni the parenthesis is currently needed, evaluation is strict 
> from left to right.
>   code add: (20 random)
>   # Spawn fires upp a native thread from a threadpool and
>   # inside that thread a new fresh interpreter is created.
>   # Spawn will deep copy the Ni node being passed and will
>   # then run it as code in the new interpreter.
>   # Currently the result value is not handled.
>   spawn code
> ]
> echo "Spawned off threads"
> # Sleeping this thread to wait for the 10 above
> sleep 1000
> echo "Done sleeping, bye"

More information about the Squeak-dev mailing list