I think people have been waiting for this for over year. I wrote a blog post describing the ISA used in the 5-tick CPU Alex and I made: Mira | chariotsofiron
Whoever implements Collatz Conjecture in fewest bytes wins.
Here is my attempt (uses 3 registers and assumes the input is on value, and output will be on register b):
value: .i16 13 ; number we start with
mov b, 0 ; number of iterations
start: mov a, value
loop: cmp b, 1
bec end ; branch if equal
inc b ; increment iterations
mov x, a ; save a copy of acc
shr a ; try to shr
bcs odd ; if it generate carry: its odd
jmp loop
odd: mov a, x ; restore acc
shl a ; mlt by 2
add x ; add the copy (mlt by 3)
inc a ; add 1
jmp loop
end:
note: im not sure i did the conditions correctly as im not familiar with the isa. i could optimize this if i knew how to ‘branch if not carry’ in 1 instruction.
edit: optimised 3 lines so it takes 1 less instruction.
Awesome submission! Sorry conditional branching was not clearer, I have added a sentence to the blog post to hopefully clarify. For each flag (N Z V C), you have two branch instructions, for e.g. for the carry flag, you have bcc (branch if carry clear) and bcs (branch if carry set). Your 3n+1 logic is perfect. Also perhaps instead of counting number of iterations, you could print the value using an instruction like
mov TICKER, a ; print value to ticker-tape device
If you replace the iteration count logic with a print, and assume the correct value is already in A, I count 18 bytes. There are a few tricks you could use to shave off some more bytes
In the meantime, here’s a neat program that swaps the nibbles in the accumulator i.e. 0x96 becomes 0x69:
; swap the nibbles of A
shl a
adc 0x80
rol a
shl a
adc 0x80
rol a
Yo embi your cpu is absolutley amazing. I may even take some stuff for my own designs, specially the addressing modes, love that
Could you link some screenshots of the cpu and maybe some of the devices like the ticker? I would like to see them
Could you also elaborate how your memory is managed? How big are your pages? How do you load them? What does the programmer have to do to manage them or do they not manage them?
im too lazy to write collatz btw
Also how do you manage to jump if your program counter is a shift register?
Im sure there are, im not used to write stuff for accumulator based cpus. Im more used to write in 3op (urcl cough cough). Tho atm i can only see 2 things: replacing the 2 branches i used to make branch if odd with 1, and using the temporary register, instead of reverting the changes. In fact ill edit the post including that change
; Collatz conjecture (14 bytes)
; starting value in A
loop: mov TICKER, a ; print value
shr a ; divide by 2
bzs end ; if we hit 0 we're done
bcc loop ; loop while even
rol a ; restore true odd value
mov b, a ; compute a = 3a+1
shl a
add b
inc a ; a = 3a+1 at this point
jmp loop
end:
Memory isn’t managed by the CPU; it is completely external. The CPU stalls on reads until memory indicates it has finished reading. Writing happens without stalling. The memory banking is a suggestion as to how to increase memory size. So far from what I’ve heard, there isn’t any built yet.
How can you jump on a shift register? Simply clear the shift register and set a bit at the decoded address.