123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264 |
- [
- This routine is a demonstration of checking for the three cell sizes
- that are normal for Brainfuck. The demo code also checks for bugs
- that have been noted in various interpreters and compilers.
- It should print one of three slight variations of "Hello world" followed
- by an exclamation point then the maximum cell value (if it's less than a
- few thousand) and a newline.
- If the interpreter is broken in some way it can print a lot of other
- different strings and frequently causes the interpreter to crash.
- It does work correctly with 'bignum' cells.
- ]
- +>>
- +[-<<+>>]
- This code runs at pointer offset two and unknown bit width; don't
- assume you have more that eight bits
- ======= DEMO CODE =======
- First just print "Hello"
- Notice that I reset the cells despite knowing that they are zero
- this is a test for proper functioning of the ability to skip over
- a loop that's never executed but isn't actually a comment loop
- Secondly there's a NOP movement between the two 'l' characters
- Also there's some commented out code afterwards
- >[-]<[-]++++++++[->+++++++++<]>.----[--<+++>]<-.+++++++.><.+++.
- [-][[-]>[-]+++++++++[<+++++>-]<+...--------------.>++++++++++[<+
- ++++>-]<.+++.-------.>+++++++++[<----->-]<.-.>++++++++[<+++++++>
- -]<++.-----------.--.-----------.+++++++.----.++++++++++++++.>++
- ++++++++[<----->-]<..[-]++++++++++.[-]+++++++[.,]-]
- ===== END DEMO CODE =====
- <<-
- Calculate the value 256 and test if it's zero
- If the interpreter errors on overflow this is where it'll happen
- ++++++++[>++++++++<-]>[<++++>-]
- +<[>-<
- Multiply by 256 again to get 65536
- [>++++<-]>[<++++++++>-]<[>++++++++<-]
- +>[>
- Cells should be 32bits at this point
- The pointer is at cell two and you can continue your code confident
- that there are big cells
- ======= DEMO CODE =======
- This code rechecks that the test cells are in fact nonzero
- If the compiler notices the above is constant but doesn't
- properly wrap the values this will generate an incorrect
- string
- An optimisation barrier; unbalanced loops aren't easy
- >+[<]>-<
- Print a message
- ++>[-]++++++[<+++++++>-]<.------------.[-]
- <[>+<[-]]>
- ++++++++>[-]++++++++++[<+++++++++++>-]<.--------.+++.------.
- --------.[-]
- ===== END DEMO CODE =====
- <[-]<[-]>] <[>>
- Cells should be 16bits at this point
- The pointer is at cell two and you can continue your code confident
- that there are medium sized cells; you can use all the cells on the
- tape but it is recommended that you leave the first two alone
- If you need 32bit cells you'll have to use a BF doubler
- ======= DEMO CODE =======
- Space
- ++>[-]+++++[<++++++>-]<.[-]
- I'm rechecking that the cells are 16 bits
- this condition should always be true
- +>>++++[-<<[->++++<]>[-<+>]>]< + <[ >>
- Print a message
- >[-]++++++++++[<+++++++++++>-]<+++++++++.--------.
- +++.------.--------.[-]
- <[-]<[-] ] >[> > Dead code here
- This should never be executed because it's in an 8bit zone hidden
- within a 16bit zone; a really good compiler should delete this
- If you see this message you have dead code walking
- Print a message
- [-]>[-]+++++++++[<++++++++++>-]<.
- >++++[<+++++>-]<+.--.-----------.+++++++.----.
- [-]
- <<[-]]<
- ===== END DEMO CODE =====
- <<[-]] >[-]< ] >[>
- Cells should be 8bits at this point
- The pointer is at cell two but you only have 8 bits cells
- and it's time to use the really big and slow BF quad encoding
- ======= DEMO CODE =======
- A broken wrapping check
- +++++[>++++<-]>[<+++++++++++++>-]<----[[-]>[-]+++++[<++++++>-]<++.
- >+++++[<+++++++>-]<.>++++++[<+++++++>-]<+++++.>++++[<---->-]<-.++.
- ++++++++.------.-.[-]]
- Space
- ++>[-]+++++[<++++++>-]<.[-]
- An exponent checker for github user btzy
- >++[>++<-]>[<<+>>[-<<[>++++<-]>[<++++>-]>]]<<[>++++[>---<++++]>++.
- [<++>+]<.[>+<------]>.+++.[<--->++]<--.[-]<[-]]
- Another dead code check
- [-]>[-]>[-]<++[>++++++++<-]>[<++++++++>-]<[>++++++++<-]>[<++++++++>-
- ]<[<++++++++>-]<[[-]>[-]+++++++++[<++++++++++>-]<.>++++[<+++++>-]<+.
- --.-----------.+++++++.----.>>[-]<+++++[>++++++<-]>++.<<[-]]
- Print a message
- [-] <[>+<[-]]> +++++>[-]+++++++++[<+++++++++>-]<.
- >++++[<++++++>-]<.+++.------.--------.
- [-]
- ===== END DEMO CODE =====
- <[-]]<
- +[[>]<-] Check unbalanced loops are ok
- >>
- ======= DEMO CODE =======
- Back out and print the last two characters
- [<[[<[[<[[<[,]]]<]<]<]<][ Deep nesting non-comment comment loop ]]
- Check that an offset of 128 will work
- +>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
- >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>-[+<-]
- And back
- +++[->++++++<]>[-<+++++++>]<[->>[>]+[<]<]>>[->]<<<<<<<<<<<<<<<<<<<<<
- <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
- <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
- And inside a loop
- --[>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
- >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>++<<<
- <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
- <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<+]+>----[++
- ++>----]-[+<-]
- This is a simple multiply loop that looks like it goes off the
- start of the tape
- +[>]<- [-
- <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
- <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
- <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
- <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
- <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
- <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
- ++++
- >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
- >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
- >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
- >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
- >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
- >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
- ]
- [ Check there are enough cells. This takes 18569597 steps. ]
- [
- >++++++[<+++>-]<+[>+++++++++<-]>+[[->+>+<<]>>
- [-<<+>>]<[<[->>+<<]+>[->>+<<]+[>]<-]<-]<[-<]
- ]
- This loop is a bug check for handling of nested loops; it goes
- round the outer loop twice and the inner loop is skipped on the
- first pass but run on the second
- BTW: It's unlikely that an optimiser will notice how this works
- >
- +[>[
- Print the exclamation point
- [-]+++>
- [-]+++++ +#-
- [<+++2+++>-]<
- .
- <[-]>[-]]+<]
- <
- Clean up any debris
- ++++++++[[>]+[<]>-]>[>]<[[-]<]
- This is a hard optimisation barrier
- It contains several difficult to 'prove' constructions close together
- and is likely to prevent almost all forms of optimisation
- +[[>]<-[,]+[>]<-[]]
- This part finds the actual value that the cell wraps at; even
- if it's not one of the standard ones; but it gets bored after
- a few thousand: any higher and we print nothing
- This has a reasonably deep nested loop and a couple of loops
- that have unbalanced pointer movements
- Find maxint (if small)
- [-]>[-]>[-]>[-]>[-]>[-]>[-]>[-]<<<<<<<++++[->>++++>>++++>>++
- ++<<<<<<]++++++++++++++>>>>+>>++<<<<<<[->>[->+>[->+>[->+>+[>
- >>+<<]>>[-<<+>]<-[<<<[-]<<[-]<<[-]<<[-]>>>[-]>>[-]>>[-]>->+]
- <<<]>[-<+>]<<<]>[-<+>]<<<]>[-<+>]<<<]>+>[[-]<->]<[->>>>>>>[-
- <<<<<<<<+>>>>>>>>]<<<<<<<]<
- The number is only printed if we found the actual maxint
- >+<[
- Space
- >[-]>[-]+++++[<++++++>-]<++.[-]<
- Print the number
- [[->>+<<]>>[-<++>[-<+>[-<+>[-<+>[-<+>[-<+>[-<+>[-<+>[-<+>[<[-]+>
- ->+<[<-]]]]]]]]]]>]<<[>++++++[<++++++++>-]<-.[-]<]]
- ]
- Check if we should have had a value but didn't
- >[
- >[-]>[-]++++[<++++++++>-]<[<++++++++>-]>+++[<++++++++>-]<+++++++
- [<-------->-]<------->+<[[-]>-<]>[>[-]<[-]++++[->++++++++<]>.+++
- +++[-<++>]<.[-->+++<]>++.<++++[>----<-]>.[-]<]<
- [-]>[-]++++++++[<++++++++>-]<[>++++<-]+>[<->[-]]<[>[-]<[-]++++[-
- >++++++++<]>.---[-<+++>]<.---.--------------.[-->+<]>--.[-]<]
- ]<
- Clean up any debris
- ++++++++[[>]+[<]>-]>[>]<[[-]<]
- One last thing: an exclamation point is not a valid BF instruction!
- Print the newline
- [-]++++++++++.[-]
- [
- Oh, and now that I can use "!" the string you see should be one of:
- Hello World! 255
- Hello world! 65535
- Hello, world!
- And it should be followed by a newline.
- ]
- ===== END DEMO CODE =====
- << Finish at cell zero
|