;redcode
;name FasterSpawnGeneratorV3
;author Skybuck Flying
;version 3
;history version 1,2 and 3 created on 7 december 2007
;
; version 3:
;
; Let's try to optimize further by for example using dual data variables and
such.
;
; If there was a division instruction which stored the remainder in a and
result in b then further optimization
; would be possible, now it's not possible
; only further optimization was one less variable used so code size a bit
smaller now.
;
; It looks pretty minimized so I see no further room for optimizations or
space gain without sacrificing program flexibility
;
; So the code looks done and pretty much final...
;
; Only 26 instructions used, nice !
; 154 cycles for 100 threads.
;
;
; version 2:
;
; Let's try to optimize it for even faster performance and less code size !

=D
;
; By using only one spawn program pointer cycles have been reduced further
to:
;
; 154 cycles for 100 threads ! 4% improvement.
;
; version 1:
; Tested with 101 threads (nice figure to test with)
;
; Tested with 100 threads to compare against others: 162 cycles needed.
; Code Size: 31 not to bad !
; Beats John's implementation in cycles.
;
; and this is not even the optimized version lol
;
; Let's implement John's spawning algorithm but let's also try to write it
more efficient,
; meaning no stack and the generated spawn program will be placed before the
program start.
ProgramStart
mov #100, ThreadsToSpawn
sub #1, ThreadsToSpawn
mov.b ThreadsToSpawn, DivThreadsToSpawn
mov.ba ThreadsToSpawn, ModThreadsToSpawn
; algoritm is simple:
; just divide threads to spawn by 2
; just mod threads to spawn by 2
; use mod result as binary indicator
; place mov spawn, 0 at binary zero's in front of program start at spawn
program pointer
; place spl 1 for binary one's in front of program start at spawn program
pointer
; repeat until div result is zero.
;
; so we need two copies of threads to spawn, maybe later we can place it in
a dual data variable.
; but for now I don't want to complicate things... so for now we use two
copies or even three lol.
; initialize spawn program pointer
mov #(ProgramStart - SpawnProgramPointer), SpawnProgramPointer
; algorithm implementation:
LoopBegin
div.ab #2, DivThreadsToSpawn
mod.a #2, ModThreadsToSpawn
OutputBegin
jmz.a OutputDoubleThreadsMinusOne, ModThreadsToSpawn
OutputDoubleThreads
mov DoubleThreadsInstruction, <SpawnProgramPointer
jmp OutputEnd
OutputDoubleThreadsMinusOne
mov DoubleThreadsMinusOneInstruction, <SpawnProgramPointer
OutputEnd
mov.ba DivThreadsToSpawn, ModThreadsToSpawn
jmn LoopBegin, DivThreadsToSpawn
LoopEnd
; execute spawn program
jmp @SpawnProgramPointer
ProgramData
ModThreadsToSpawn
DivThreadsToSpawn
dat #0, #0 ; A = ModThreadsToSpawn, B = DivThreadsToSpawn
ThreadsToSpawn dat $0, #0
SpawnProgramPointer dat $0, $0
DoubleThreadsInstruction spl 1, 0
DoubleThreadsMinusOneInstruction mov DoubleThreadsInstruction, 0
ProgramEnd