@@ -141,19 +142,19 @@ Location: US - United States of America
To build:
-
make all
+
make all
To use:
-
./anonymous
+
./anonymous
Alternate code:
The original version of this entry was added, by request,
in order to show the code that was turned into the
tattoo,
as the alternate code. See below for the tattoo side-by-side with the code.
Alternate build:
-
make alt
+
make alt
Alternate use:
NOTE: this version might not work on some systems like macOS.
-
./anonymous.alt
+
./anonymous.alt
Judges’ remarks:
The author was too embarrassed that they could write such trash, so I
promised to protect their identity. I will say that the author of this
@@ -221,10 +222,10 @@ ends in a smily face: ;}.
@@ -141,7 +142,7 @@ Location: US - United States of America
To build:
-
make all
+
make all
NOTE: there is an alternate version which will only work if
you have an old enough compiler or a compiler that supports -traditional-cpp.
The original code was fixed in 2023 to not require this.
@@ -150,15 +151,15 @@ The original code was fixed in 2023 to not require this.
This alternate code, the original, requires a compiler that supports
-traditional-cpp or an old enough compiler. If you have such a compiler you
can use this version.
Alternate build:
-
make alt
+
make alt
Alternate use:
-
./decot.alt
+
./decot.alt
Judges’ remarks:
This program prints out what looks like a fragment of C code.
Is this a bug or is this a feature? To help choose
@@ -166,13 +167,13 @@ the judges offer this one comment: understand remarks!
Historical remarks:
Some new (in 1984) compilers disliked line 15 of the original source, so we
changed it from:
-
for(signal=0;*k * x * __FILE__ *i;) do {
+
for(signal=0;*k * x * __FILE__ *i;) do {
to:
-
for(signal=0;*k *x * __FILE__ *i;) do {
+
for(signal=0;*k *x * __FILE__ *i;) do {
To see what we mean look at the original source file. The
alternate code is the version that has this modification. The
fixed version has instead:
-
for(signal=0;*k *= * __FILE__ *i;) do {
+
for(signal=0;*k *= * __FILE__ *i;) do {
Author’s remarks:
No remarks were provided by the author.
To build:
-
make all
+
make all
To use:
-
./laman <positive number>
+
./laman <positive number>
Try:
The program accepts ONE POSITIVE number. Seeing is believing, so try things
like:
-
./try.sh
+
./try.sh
This code should run you in circles.
Judges’ remarks:
Some new compilers (in 1984) dislike lines 6 and 10 of the source, so we changed
them from:
@@ -144,7 +145,7 @@ Location: NL - Kingdom of the Netherlan
To build:
-
make alt
+
make alt
NOTE: the original code will not work on any system other than
VAX-11 and
PDP-11 and this is why we encourage you
@@ -155,7 +156,7 @@ the original version.
The default microseconds is 190000 as this is approximately how long it slept in
the original entry but it can be no lower than 5000 as any lower doesn’t work
@@ -169,7 +170,7 @@ overflow!
BTW: is there such a thing as too fast a CPU ? :-) Actually yes for certain code
which is probably not as uncommon as you think :-).
Try:
-
./mullender.alt
+
./mullender.alt
./mullender.alt 5000 # wait for 5000 microseconds and see what happens
@@ -184,9 +185,9 @@ happens after some time of waiting?
PDP-11. In the following years, 1985 on,
machine dependent code was discouraged.
Original build:
-
make all
+
make all
Original use:
-
./mullender
+
./mullender
Judges’ remarks:
Without question, this C program is the one of the most obfuscated C program
that has ever been received! Like all great contest entries, it resulted in a
@@ -225,11 +226,11 @@ in the fabulousgentab build:
The PDP and
VAX codes implement the same algorithm:
-
for (;;) {
+
for (;;) {
write(1, " :-)\b\b\b\b", 9);
delay();
}
@@ -333,7 +334,7 @@ simple.
PDP code in assembly.
We both knew PDP-11 assembly so that was
no problem. The assembly code we came up with is as follows:
-
pdp:
+
pdp:
mov pc,r4
tst -(r4)
sub $9, r4
@@ -373,7 +374,7 @@ VAX assembly, we w
VAX code in C and massaged the
compiler output. The VAX assembly
program that we came up with is as follows:
-
vax: .word 0400 + (pdp - vax) / 2 - 1
+
vax: .word 0400 + (pdp - vax) / 2 - 1
1:
pushl $9
pushal str
@@ -426,7 +427,7 @@ extracted the machine code from the object file.
NOTE from judges: see gentab.c for a copy of this file that can be
compiled in modern systems.
-
#include <stdio.h>
+
#include <stdio.h>
#include <a.out.h>
main(argc, argv) char **argv;
@@ -522,10 +523,10 @@ the comment to &&.
@@ -141,15 +142,15 @@ Location: SE - Kingdom of Sweden (
To build:
-
make all
+
make all
To use:
-
./august
+
./august
Try:
-
./try.sh
+
./try.sh
If you have the primes(6) tool (sometimes part of BSD
Games) you can see
what of the output in the first N (say 15 or 25) lines are primes:
-
./primes.sh # 15
+
./primes.sh # 15
./primes.sh 25
Note that try.sh will run this script anyway, telling you where to get
primes(6) if you don’t have it installed, but it will only run with the
@@ -193,10 +194,10 @@ anything funny going on with the output?
To see why we recommend the alternate version instead of the original version,
see below and the Original code section.
Try:
@@ -152,20 +153,20 @@ original, slows down the output so that you can see what it looked like back in
This will be more enjoyable. It is slowed down by the usleep(3) library
call with a configurable time to sleep. The default is 500 microseconds but you can
reconfigure it like:
-
make SLEEP=700 clobber alt
+
make SLEEP=700 clobber alt
which would set it at 700. Then, whether you use the default value or not, try:
-
./try.alt.sh
+
./try.alt.sh
Original code:
As explained above, because modern systems run this entry way too fast to fully
appreciate what it does, we encourage you to first try the alternate version.
After this, however, you might wish to try the original version, fixed for
modern systems.
@@ -141,23 +142,23 @@ Location: US - United States of America
To build:
-
make all
+
make all
There is alternate code which allows one to change the size of the maze. See
Alternate code below.
To run:
-
./shapiro
+
./shapiro
Alternate code:
The code has a define C set to 39 but this can be modified to change the size
of the maze. The alt code allows one to easily do this.
Alternate build:
-
make alt
+
make alt
Alternate try:
If you wish to change the value you can do it like:
-
make clobber SIZE=5 alt
+
make clobber SIZE=5 alt
Note that if it is not a number then obviously there will be a compilation
error. If it’s <= 0 || >= 5000 then it is set to 39, the default.
You might also wish to try:
-
./try.alt.sh
+
./try.alt.sh
This script will compile the program five times with a random value and then
prompt you in an infinite loop for values to try, exiting only if non-digits are
in the input.
@@ -199,10 +200,10 @@ arguments and notice the output.
@@ -141,19 +142,19 @@ Location: US - United States of America
To build:
-
make all
+
make all
There is another version that will be compiled in case the first fails. This
should happen automatically. See Alternate code below for
more details on it.
To use:
-
./sicherman < file
+
./sicherman < file
echo foo | ./sicherman
./sicherman
# type or paste some text, making sure to hit enter after each line typed
Try:
-
./try.sh
+
./try.sh
Alternate code:
The sicherman.alt.c is a slight change in the fixed version
(fixed so it does not require -traditional-cpp) in that it has two args to
@@ -164,12 +165,12 @@ audience.
Alternate build:
Although this will be built if the original fails to compile you can do it
manually like:
-
make alt
+
make alt
In this case it will be built as sicherman.alt.
Alternate use:
-
./sicherman.alt < file
+
./sicherman.alt < file
Alternate try:
-
./try.alt.sh
+
./try.alt.sh
Judges’ remarks:
This program abuses the C preprocessor so much that some cpps fail to strip
out all of the comments on the first pass! If you were able to understand
@@ -182,7 +183,7 @@ Like the program says, what’s that mean?
on a line. Now enter the letters ‘n’ through ‘z’. But to borrow a quote
from Richard Stallman: If you think you understand what this code
does, then you don’t, so read it again! Explain why:
-
@@ -141,11 +142,11 @@ Location: US - United States of America
To build:
-
make all
+
make all
To use:
-
./applin
+
./applin
Try:
-
./applin.c
+
./applin.c
Judges’ remarks:
The judges were so amused by this little program that we created an
award just for it. This program is portable to the C and Fortran 77
@@ -178,10 +179,10 @@ compilers as well as executable by the Bourne shell!
This program computes a specific mathematical value. Simply compile
and give it an infinite amount of stack space and CPU time. Otherwise
@@ -183,10 +184,10 @@ enough to try and parse it correctly.
@@ -141,12 +142,12 @@ Location: GB - United Kingdom of Great
To build:
-
make all
+
make all
To use:
-
./hague 2>/dev/null
+
./hague 2>/dev/null
# enter some text
Try:
-
./try.sh
+
./try.sh
Note that you can run the program without feeding it anything and then type in a
message and line by line it will show the right output. Notice also how certain
characters will print a ?.
@@ -189,10 +190,10 @@ credit, what Morse message does the program spell out?
@@ -141,9 +142,9 @@ Location: US - United States of America
To build:
-
make all
+
make all
Try:
-
./holloway
+
./holloway
Judges’ remarks:
Believe it or not, this is the old standard “Hello, world” program
performed in a very complex way. The judges and the author defy you
@@ -177,10 +178,10 @@ this version as the first C program!
@@ -162,7 +163,7 @@ because of the call to _exit() (see below).
enable the optimiser clang will generate code that prints the string twice and
dumps core just like before! What about the call to _exit()?
The call was:
-
_exit(argv[(int)*argc-2/cc[1*(int)*argc]|-1<<4]);
+
_exit(argv[(int)*argc-2/cc[1*(int)*argc]|-1<<4]);
Changing it to not refer to these variables and just exit 1 and the problems
disappear!
macOS
@@ -172,7 +173,7 @@ it works fine but if it’s disabled it prints out the string and then enters an
infinite loop!
After we fix the infinite loop if we change the _exit() call in macOS and
disable the optimiser we might get something like:
-
$ ./marshall
+
$ ./marshall
choo choo
Segmentation fault: 11
Observe how it doesn’t print it twice. But of course it segfaults so it’s not
diff --git a/1986/marshall/index.html b/1986/marshall/index.html
index 08d816359..641df2f2a 100644
--- a/1986/marshall/index.html
+++ b/1986/marshall/index.html
@@ -88,6 +88,7 @@
@@ -141,7 +142,7 @@ Location: US - United States of America
To build:
-
make all
+
make all
NOTE: we FORCE disable the optimiser due to a funny problem with different
compilers and systems. See below and compilers.html for details.
There is an alternate version. The reason is a funny problem:
@@ -152,7 +153,7 @@ might work but the other one would not. We describe this in more detail in
compilers.html and we encourage you to read it for entertainment
if nothing else.
To use:
-
./marshall
+
./marshall
Alternate code:
Due to the different conflicting problems with gcc and clang, we
instead offer the problematic code as an alternate version whereas
@@ -160,9 +161,9 @@ instead offer the problematic code as an alternate version whereas
_exit() commented out, changing the value passed into _exit() to 1.
Alternate build:
To see if your compiler has the problems noted:
-
make alt
+
make alt
Alternate use:
-
./marshall.alt
+
./marshall.alt
Does it work in your system? That is does it not segfault, does it print it only
once and does it not enter an infinite loop? Or more generally does it print the
text exactly once and then exit?
The judges found this entry to be one of hardest to read without the
aid of /lib/cpp and a good editor. When run, the program asks if it
@@ -176,10 +177,10 @@ is obfuscated, of all things!
NOTE: to avoid problems with news and mail, the single line was split
into 3 lines. Join all lines into a single line to recreate
@@ -151,7 +152,7 @@ the original file.
The \015 in the above printf(1) command produces a control-N.
One some machines, a control-M control-N arg is needed
to get the command to output cleanly:
-
./stein $(printf "\014\015"); echo
+
./stein $(printf "\014\015"); echo
Your system may require another set of characters.
In time, you will figure out what it does. :-)
Author’s remarks:
@@ -183,10 +184,10 @@ In time, you will figure out what it does. :-)
@@ -141,9 +142,9 @@ Location: US - United States of America
To build:
-
make all
+
make all
To use:
-
./wall
+
./wall
Judges’ remarks:
The original version did not have a ‘;’ character in the first line.
This caused a number of System V C pre-preprocessors to gripe about a
@@ -182,10 +183,10 @@ compiler documents the program.
some_command | ./biggar | od -c
./biggar < file | od -c
Try:
-
./try.sh
+
./try.sh
Judges’ remarks:
By changing the compile line you can make this program do anything you
want. This is a very efficient way to transfer source, though it
@@ -193,10 +194,10 @@ an infinite loop by this entry.
This program was designed to maximize the bother function for
structured programmers. This program takes goto statements to their
@@ -185,10 +186,10 @@ See the Communications of the ACM, March 1987, Page 195-196.
@@ -141,9 +142,9 @@ Location: US - United States of America
To build:
-
make all
+
make all
To use:
-
./korn
+
./korn
Judges’ remarks:
The Judges believe that this is the best one line entry ever received.
Compile on a UNIX system, or at least one using a C implementation that
@@ -158,17 +159,17 @@ section right now and see if you are one of the few people who can.
What is the value of the symbol "have"? (hint: the value is NOT 4
characters, or 'h', or a string) Consider the fact that:
-
char *x;
+
char *x;
defines a pointer to a char (i.e. an address), and that the = assigns
things of compatible types. Since:
-
x = "have";
+
x = "have";
is legal C, what type of value is "have"?
Note that the following expressions yield the same value:
-
x[3] *(x+3) *(3+x)
+
x[3] *(x+3) *(3+x)
since addition is commutative. What can be said about this value?
-
3[x]
+
3[x]
David
Korn’s
/bin/ksh provides us with a greatly
@@ -203,10 +204,10 @@ greatly inspired this contest.
@@ -141,13 +142,13 @@ Location: NL - Kingdom of the Netherlan
To build:
-
make all
+
make all
To use:
-
./lievaart
+
./lievaart
# enter a level and start playing as described below
Try:
To see what it would have looked like without the size restrictions:
-
./lievaart2
+
./lievaart2
# enter a level and start playing as described below
Judges’ remarks:
We believe that you too will be amazed at just how much power Mr. Lievaart
@@ -198,10 +199,10 @@ logic and displays the board after each move! See above for how to use this.
@@ -141,18 +142,18 @@ Location: US - United States of America
To build:
-
make all
+
make all
A smaller version, originally called zsmall.c (and still exists as such, as
the source of the alt code), of applin.c, can be found in
applin.alt.c. Your machine may have an easier time with this
program. See the Alternate code section below for details.
Try:
-
./applin
+
./applin
Alternate code:
As noted above a smaller version can be used in case your cpp has a hard time
with this entry.
Alternate build:
-
make alt
+
make alt
Use applin.alt as you would applin above.
History about the smaller version:
Way back in 1988 ..
@@ -205,10 +206,10 @@ Clearly the GNU C preprocessor is faster.
Observe that three of the commands in the script are:
-
./dale these files are in this directory: *
+
./dale these files are in this directory: *
./dale $(printf "the following files exist in this directory:\n%s\n" *)
./dale "$(printf "the following files exist in this directory:\n%s\n" *)"
As the script asks what do the last two do and why do they do it? Why do they
@@ -189,10 +190,10 @@ system calls.
There is an alternate version, the original, that can’t be compiled in modern
systems but can be if you have an old enough compiler. See Alternate
code below.
To use:
-
./isaak
+
./isaak
Alternate code:
The original version of this code is in isaak.alt.c.
The original entry starts with the line:
-
main(){};
+
main(){};
This works on some systems. Why? Note that #include <stdio.h> is given on
the last line. Why is this needed? Note the unusual calls to sprintf(3).
This version also relied on being able to define #define to something else and
@@ -158,7 +159,7 @@ using that macro for #define.
This version will not likely work on modern systems if you can even get it to
compile.
Alternate build:
-
make alt
+
make alt
Use isaak.alt as you would isaak above.
Judges’ remarks:
The program relies heavily on ASCII. Don’t even think of running it on
@@ -173,7 +174,7 @@ from a single macro (e.g., "O/**/O" creates either ++
NOTE: Most System V machines were not be able to execute this program correctly
due to the fact that BSD style systems have an sprintf(3) that returns a char *. Due to the above problems, we placed the output of this program in the
file: isaak.encode. To read this file do.
-
uudecode < isaak.encode
+
uudecode < isaak.encode
cat isaak.output
Since this was fixed, this file is not strictly necessary. See the
isaak.alt.c for the original source.
@@ -208,10 +209,10 @@ file: isaak.encode. To read this file do.
There is an alternate version provided. See the Alternate
code section below.
Try:
-
./litmaath eschew obfuscation
+
./litmaath eschew obfuscation
Alternate code:
This alternate code, added to help understand the entry and for fun, is code
that we suggested at the time of the entry publication but which we never put in
a file.
Alternate build:
-
make alt
+
make alt
Use litmaath.alt as you would litmaath above.
Alternate try:
-
./litmaath.alt six was afraid of seven because seven eight nine
+
./litmaath.alt six was afraid of seven because seven eight nine
Judges’ remarks:
Note the unusual structure:
-
while (<condition>)
+
while (<condition>)
;
Did you notice that the body is empty?
Furthermore, it’s interesting to note that only two variables are
@@ -168,7 +169,7 @@ used to achieve everything.
two small strings as arguments, and follow the program closely. One
could make the body of the while loop an fprintf with interesting
variables like:
-
What happens if you input, and what you do about it?
-
char *(*(*(*(*(*fun[32])))))());
+
char *(*(*(*(*(*fun[32])))))());
Judges’ remarks:
This is a somewhat restricted version of a useful program that has been
posted to Usenet. What is unusual is what it is able to do so much
@@ -180,10 +181,10 @@ in such little space.
@@ -141,16 +142,16 @@ Location: US - United States of America
To build:
-
make all
+
make all
Try:
-
./robison 80 10
+
./robison 80 10
./robison 40 16
The first and second parameters are optional. You might also try:
-
./robison 80 2 # <--- can you find the bug?
+
./robison 80 2 # <--- can you find the bug?
./robison 80 -246
Judges’ remarks:
The following might make an interesting benchmark:
-
./robison 100
+
./robison 100
[Amdahl 5890-300E with System V cc: 8.40 seconds]
We suggest that you C pre-process and perhaps C-beautify this program.
All is not what it may appear to be in this program. Why does a whi1e
@@ -188,10 +189,10 @@ ANSI committee should look into this practical simplification of C.
@@ -141,27 +142,27 @@ Location: GR - Hellenic Republic (
To build:
-
make clobber all
+
make clobber all
and follow the instructions this will give you.
If your compiler will not read from /dev/tty see the Alternate
code section below.
To use:
-
./spinellis
+
./spinellis
Type in or copy paste some C code, perhaps from input.txt, and send
EOF (typically ctrl-d).
Now run again:
-
./spinellis
+
./spinellis
Alternate code:
For clang or compilers that won’t read from /dev/tty, we provide this version.
Alternate build:
-
make clobber alt
+
make clobber alt
and follow the instructions.
Alternate use:
-
./spinellis.alt
+
./spinellis.alt
Type in or copy paste some C code, perhaps from input.txt, and send
EOF (typically ctrl-d).
Now run again:
-
./spinellis.alt
+
./spinellis.alt
Judges’ remarks:
We enjoyed this entry this year; however in the future programs must be able to
be compiled from within a Makefile without the need of human intervention.
@@ -141,37 +142,37 @@ Location: US - United States of America
To build:
-
make all
+
make all
NOTE: this version is a fixed version for modern C compilers. See the Alternate
code section below for how to use the original and why one
might wish to do so.
Try:
-
./westley
+
./westley
Also try:
-
./try.sh
+
./try.sh
to show the code with followed by the result so you can truly see the magic.
Alternate code:
This version is the original which might not work as you expect nowadays.
Alternate build:
-
make alt
+
make alt
Alternate use:
To see if your compiler has the problem described in the Judges’ remarks below,
try:
-
./westley.alt
+
./westley.alt
Does it show the same output as westley?
Judges’ remarks:
Your compiler must parse
-
#define _ -a
+
#define _ -a
-_
as --a and not -(-a) or some other tokenized form. Some strictly
conforming ANSI C Preprocessors may object to this: for such
compilers, you can elide the non-standard token-pasting requirement
by changing the #define line to:
-
#define _ F-->00||F-OO--;
+
#define _ F-->00||F-OO--;
This is what the modified code in westley.c does whereas the alt
code is the original.
@@ -147,15 +148,15 @@ Location: US - United States of America
To build:
-
make all
+
make all
To use:
-
./jar.2
+
./jar.2
[enter some lisp]
./jar.2 < some_lisp_file
NOTE: this entry will likely segfault on invalid input.
Try:
-
./try.sh
+
./try.sh
./try.sh chocolate_cake.lisp
@@ -192,7 +193,7 @@ The program implements a conventional lisp listener, i.e. you type in
lisp expressions (followed by CR), the program evaluates them and
prints out the return values. End execution by typing an end-of-file
character.
-
To get this to compile with a modern CPP, we had to replace #D with #define.
To use:
Run the program this way:
-
./ovdluhe < textfile
+
./ovdluhe < textfile
The program stops when it reaches the end of the template buffer
by chance or is killed.
Try:
-
./try.sh ; sleep 2 ; ./try.sh
+
./try.sh ; sleep 2 ; ./try.sh
Alternate code:
The author suggested that one varies the definition of P from 2 through 10. As
it’s a #define it’s easy to set up.
Alternate build:
-
make P=9 clobber alt
+
make P=9 clobber alt
You do not have to define P but if you do you can replace the value with
whatever you wish, as long as it’s a positive int (or evaluates to a positive
int like the default (A<<AP) does). Too high a value will likely cause the
program to fail and a negative value will cause a compilation error.
Alternate use:
-
./ovdluhe.alt
+
./ovdluhe.alt
Alternate try:
-
./try.alt.sh
+
./try.alt.sh
P=5 ./try.alt.sh
NOTE: if you specify too high a value for P the program might fail. If you
@@ -216,10 +217,10 @@ observe the result.
@@ -141,11 +142,11 @@ Location: US - United States of America
To build:
-
make all
+
make all
There is an alternate version with a trace routine that the author had commented
out. See alternate code below for more details.
Try:
-
./paul
+
./paul
Alternate code:
This version was described by the author like:
@@ -156,9 +157,9 @@ and forth as the program runs. A much better debugger or trace
could easily be added.
Alternate build:
-
make alt
+
make alt
Alternate use:
-
./paul.alt
+
./paul.alt
Judges’ remarks:
The author’s comments is a detailed program explanation and spoiler. If you
want a real challenge, don’t read any further and try to understand the program
@@ -268,10 +269,10 @@ could easily be added.
@@ -141,11 +142,11 @@ Location: US - United States of America
To build:
-
make all
+
make all
To use:
-
./tromp [drops_per_sec [cmd_string]]
+
./tromp [drops_per_sec [cmd_string]]
Try:
-
./tromp 5
+
./tromp 5
./tromp 10 "hkl jq"
The second command, ./tromp 10 "hkl jq", will set up the keys kind of like
@@ -171,7 +172,7 @@ loser :-)
The author provided an alternate version of the code with some improvements. See
the judges’ additional remarks in the author’s remarks, for more details.
Alternate build:
-
make alt
+
make alt
Alternate use:
Use tromp.alt as you would tromp above.
NOTE: testing more than one user updating the high score file, one of the
@@ -231,7 +232,7 @@ temporary file.
at the start and -raw at the end. This further reduces the size of
the program, but has the possible disadvantage that the program
can only by stopped by ‘q’ or by the `kill -9’ command.
-
long h[4];t(){h[3]-=h[3]/3000;setitimer(0,h,0);}c,d,l,v[]={(int)t,0,2},w,s,I,K
+
long h[4];t(){h[3]-=h[3]/3000;setitimer(0,h,0);}c,d,l,v[]={(int)t,0,2},w,s,I,K
=0,i=276,j,k,q[276],Q[276],*n=q,*m,x=17,f[]={7,-13,-12,1,8,-11,-12,-1,9,-1,1,
12,3,-13,-12,-1,12,-1,11,1,15,-1,13,1,18,-1,1,2,0,-12,-1,11,1,-12,1,13,10,-12,
1,12,11,-12,-1,1,2,-12,-1,12,13,-12,12,13,14,-11,-1,1,4,-13,-12,12,16,-11,-12,
@@ -278,10 +279,10 @@ can only by stopped by ‘q’ or by the `kill -9’ command.
This program computes all proper subsets of the set of
arguments passed to it. Each subset is printed with one
@@ -185,10 +186,10 @@ value is negative.
Try compiling and running the 4 resulting programs like:
-
./compile.sh
+
./compile.sh
If you need to specify an alternate compiler path, say because your default
compiler is clang (or in the case of macOS gcc is clang) you can do so like:
-
CC=/opt/local/bin/gcc-mp-12 ./compile.sh
+
CC=/opt/local/bin/gcc-mp-12 ./compile.sh
If you wish to delay the script or remove the delay you can do so like:
-
DELAY=2 ./compile.sh
+
DELAY=2 ./compile.sh
Finally try:
-
./westley
+
./westley
# input some lines of text, sending EOF (usually ctrl-d) to end
./try.sh # demo of some input
@@ -175,7 +176,7 @@ different algorithm for each version (hereafter referred to as
(ROT13 and reversed)).
When compiling these versions, one needs to define trgpune
in the compile line (which the Makefile now has). Example:
-
cc -Dtrgpune=putchar ver3.c -o ver3
+
cc -Dtrgpune=putchar ver3.c -o ver3
trgpune is the ROT13 of getchar(), so getchar() and putchar()
are exchanged in the ROT13 counterpart. It is easy to see that
this is unavoidable. I must have a #define for a library
@@ -207,14 +208,14 @@ first argument (argc) must be at least one).
function vs() to define in the ROT13 version. But a function
called vs() turns into a function called if() in the original,
so it can’t be done. Therefore, I do:
-
expr1 && expr2 && (expr3=etc);
+
expr1 && expr2 && (expr3=etc);
which is the same as:
-
if (expr1 && expr2) expr3=etc;
+
if (expr1 && expr2) expr3=etc;
A/UX on the Macintosh doesn’t get this right; it evaluates ALL
expressions if they aren’t in an assignment or conditional
statement. This might warrant a warning, since other compilers
may do this. I found MANY compilers botched:
-
expr1 && (expr2,expr3);
+
expr1 && (expr2,expr3);
expr2 was OFTEN evaluated even if expr1 was false. I removed
such statements to make it more portable.
Variable names worth noting
@@ -224,11 +225,11 @@ such statements to make it more portable.
tang and gnat are both ROT13 and palindrome pairs!
–
Normally (!), a reversible C program is done thus:
-
/**/ forward code /*/ edoc drawkcab /**/
+
/**/ forward code /*/ edoc drawkcab /**/
If your compiler nests comments, it will get this wrong.
However, I have made some bits of the code palindromic,
(or different, but reversible) so it is more like:
This alternate code is for the very fewusers
@@ -165,7 +166,7 @@ the " #Q" string was not changed as that showed worse looking outpu
of improved output though admittedly we have no way to test the compilers in
question. YMMV.
Alternate build:
-
make alt
+
make alt
Alternate use:
Use baruch.alt as you would baruch.
Judges’ remarks:
@@ -227,10 +228,10 @@ to replace the " #Q" string with " \261\2".
@@ -141,12 +142,12 @@ Location: GR - Hellenic Republic (
To build:
-
make all
+
make all
To use:
-
./dds
+
./dds
Try:
Give the following lines as input:
-
OLD LANDER.BAS
+
OLD LANDER.BAS
RUN
NOTE: this entry is probably one of the only times CAPS LOCK might be worth
having (though still not useful enough to enable :-) ) as all input has to be
@@ -256,10 +257,10 @@ fits in an 80*25 screen).
which should apply the identity transformation to a minimal holoalphabetic
sentence.
Also try:
-
./try.sh
+
./try.sh
Judges’ remarks:
The program, in its base form, implements two useful utilities:
@@ -165,10 +166,10 @@ sentence.
it to 1530 bytes) which implements the complete shark utility. The script,
shark.sh, contains a jaw.c embedded within it!
The sender must have compress and btoa. To send, try:
-
./shark.sh jaw.* README.md > receive
+
./shark.sh jaw.* README.md > receive
The resulting file, receive, unpacks the input files
even if the receiver lacks uncompress and btoa:
-
mkdir -p test
+
mkdir -p test
cd test
sh ../receive
cmp ../jaw.c jaw.c
@@ -262,7 +263,7 @@ left, and source-to-source transformations galore.
Construct sharkmail, to auto-split sharkives into mailable segments and mail
them. Here’s a simple one, which could be extended to enable auto-reassembly
with one shell cmd at the far end.
@@ -141,24 +142,24 @@ Location: GB - United Kingdom of Great
To build:
-
make all
+
make all
There is an alternate version that does something different
that can be used if your compiler is incapable of compiling X=g()... in
main(). It can be used for another purpose too.
To use:
-
./pjr
+
./pjr
Alternate code:
Note that some compilers will be unable to compile the expression X=g()... in
main() due to lack of temporary stack space. One might want to try replacing
main() with:
The addition of trigraphs has made it easier to make programs hard to read. It
was a dark and stormy night for C when the ANSI C committee added trigraphs to
@@ -199,10 +200,10 @@ would allow for sequence numbers to be punched in columns 73-80 :-).
The authors provided another version of this program. See the alternate
version section below.
Bugs and (Mis)features:
@@ -155,7 +156,7 @@ version section below.
In 2023 it was noticed that in some systems like macOS there was confusing
output due to a warning at runtime that was interspersed with the output of the
program. For instance it would show:
-
./tbr
+
./tbr
$ warning: this program uses gets(), which is unsafe.
which kind of hid the prompt. Thus the entry was changed to use fgets(3) which
is referred to later in this file.
@@ -163,14 +164,14 @@ is referred to later in this file.
this entry would not compile in modern systems. This fix is also referred to
below, in the alternate version section.
To use:
-
./tbr
+
./tbr
$ enter some shell commands
NOTE: globs do not work with this entry. Why?
NOTE: exit does not work and neither does logout. To exit try sending ctrl-d
or ctrl-c (or kill it from another terminal :-) ). But why does it not work with
just exit or logout? Hint: see the authors’ remarks.
Try:
-
./tbr
+
./tbr
$ ls -l tbr tbr.c
# notice how the following does not work:
@@ -187,7 +188,7 @@ documented, are not considered bugs as such in the context of the contest.
Alternate code:
The authors supplied us with a slightly smaller unformatted version
of the program which we include below:
-
#define D ,close(
+
#define D ,close(
char*c,q[512],m[256],*v[99],**u,*i[3];int f[2],p;main(){for(m[m[60]=m[62]=
32]=m[*m=124[m]=9]=6;e(-8),gets(1+(c=q))||(exit(0),0);r(0,0))for(;*++c;);}
r(t,o){*i=i[2]=0;for(u=v+98;m[*--c]^9;m[*c]&32?i[*c&2]=
@@ -201,9 +202,9 @@ of the program which we include below:
as well as the gets() to fgets() fix applied to it to make it functionally
equivalent like the authors intended.
Alternate build:
-
make alt
+
make alt
Alternate use:
-
./tbr.alt
+
./tbr.alt
Judges’ remarks:
This program touches on a well known Unix utility, the 6th edition Bourne Shell
(/bin/sh), whose original source was considered to be extremely obfuscated by
@@ -245,9 +246,9 @@ is parsed; a pointer to the stack of arguments is assigned and an
argument is stolen every time a > or < is encountered. The
shell flags an error if no arguments are on the stack. Thus, for
example:
-
cat > foo > bar
+
cat > foo > bar
cats to foo, since it was pushed last, but
-
cat > > foo bar
+
cat > > foo bar
cats to bar, since bar was pushed under foo (remember we’re
parsing right-left).
Depending on your flavor of Unix, cd without an argument will
@@ -281,10 +282,10 @@ all ed(1) does too.
expression - function f(x,y) (see below)
x1 - start of interval
@@ -155,7 +156,7 @@ Location: US - United States of America
h - step size
y1 - initial value (y(x1) == y1)
Try:
-
./try.sh
+
./try.sh
Judges’ remarks:
The program’s source implements four functions, all from the
same source file!
@@ -169,23 +170,23 @@ operators:
integer powers. Also note that all expressions are evaluated strictly
left to right. (i.e., parenthesis aren’t supported).
This version changes the keys f for forward, l for left and r for right by
default to k for forward, l for right and h for left, which is more
@@ -157,9 +158,9 @@ natural for those who use vi(m). Also one can just hit q followed b
quit the maze. It is problematic to reconfigure the keys except by modifying the
code directly so the keys are not made a -D at the compiler.
Alternate build:
-
make alt
+
make alt
Alternate use:
-
./buzzard.alt
+
./buzzard.alt
Judges’ remarks:
You will be A-mazed.
You are invited to try to cheat, … if you can figure out how! :-)
@@ -186,7 +187,7 @@ separate physical rows in the maze; a space indicates a corridor,
and any other character is a wall. Tabs are also considered walls,
so make sure to convert tabs to spaces before using it.
@@ -155,7 +156,7 @@ a winning entry for the past 5 years!
would deny awards to more deserving entries. These categories have not
been eliminated, and will likely be considered in future years.
A number of entries made use of the following C pre-processor feature:
-
#define X define
+
#define X define
#X foo bar
This is not permitted under ANSI C. Some ANSI C compilers do allow this. In
the future, we do not want programs to use this feature. Because this request
diff --git a/1991/rince/.entry.json b/1991/rince/.entry.json
index ab5df1051..4baeb247c 100644
--- a/1991/rince/.entry.json
+++ b/1991/rince/.entry.json
@@ -51,7 +51,7 @@
},
{
"file_path" : "1991_rince.tar.bz2",
- "inventory_order" : 100000,
+ "inventory_order" : 1415926535,
"OK_to_edit" : false,
"display_as" : "tbz2",
"display_via_github" : false,
diff --git a/1991/rince/index.html b/1991/rince/index.html
index 38da79c3e..3ad21c505 100644
--- a/1991/rince/index.html
+++ b/1991/rince/index.html
@@ -88,6 +88,7 @@
@@ -141,12 +142,12 @@ Location: GB - United Kingdom of Great
To build:
-
make all
+
make all
There are two alternate versions which allow one to not be
restricted in movements or to change the maximum number of movements, even if
that’s fewer than the original program.
To use:
-
./rince
+
./rince
Alternate code:
The first alternate version, rince.alt.c, disables a maximum move
count so that anyone with enough patience and time can complete the puzzle,
@@ -156,18 +157,18 @@ reconfigure at compilation the maximum number of moves, even if that is lowering
the count.
The author set the maximum number of moves to 484.
Alternate build:
-
make alt
+
make alt
This will build both alt versions where the first one, rince.alt, has no
restrictions in the number of movements and the second one, rince.alt2, has a
configurable maximum number of moves allowed, defaulting to the entry’s max,
484.
To reconfigure the maximum number of moves to 700:
-
make clobber MAXMOVES=700 alt
+
make clobber MAXMOVES=700 alt
Alternate use:
To run the first alt version:
-
./rince.alt
+
./rince.alt
To run the second alt version:
-
./rince.alt2
+
./rince.alt2
Can you figure out how to make the two alternate versions equivalent in
functionality without modifying the code? That is can you make the second alt
version end up allowing any number of movements?
@@ -237,10 +238,10 @@ Take care that it’s facing in the correct direction.
NOTE: we have provided a script to perform the below procedure which we include
for the interested. See the try section if you just want to play.
Make and then run as follows:
-
./westley [move_location] | tee nextmove.c
+
./westley [move_location] | tee nextmove.c
where the move_location is a digit from 1 to 9 that represents
a move on a tic-tac-toe board:
1 2 3
@@ -160,25 +161,25 @@ a move on a tic-tac-toe board:
7 8 9
If you omit move_location, then the computer moves first. For your
next move, recompile nextmove.c and play it again:
-
make nextmove
+
make nextmove
./nextmove move_location | tee nextmove.c
Try:
We have provided the shell script, ttt, to make it easier to play the
game:
-
make ttt
+
make ttt
./ttt [first_move] # <- omit first arg to have it move first
./ttt next_move
The shell script determines when the game is over, and automatically replaces
merlyn.c (copied from westley.c with an improved version after a
loss). The ttt script has two other modes:
-
./ttt quitgame # cancel any game in progress, revert to merlyn.c
+
./ttt quitgame # cancel any game in progress, revert to merlyn.c
./ttt clobber # remove all game files, revert to original source
For example here is a potentially losing game:
-
./ttt 1
+
./ttt 1
./ttt 4
./ttt 6
The final might look like:
-
a(X){/*/X=- a(X){/*/X=-
+
a(X){/*/X=- a(X){/*/X=-
X -1;F;X=- -1;F;X=-
-1;F;}/*/ -1;F;}/*/
char z[][100]={"char z[][100]={","a(X){/*/X=-","-1;F;X=-","-1;F;}/*/","1999999999 :-) ",
@@ -212,7 +213,7 @@ loss). The ttt script has two other modes:
This version is based on the author’s remarks. It is not supposed to lose but it
can lose if you cheat. That’s supposed to happen. Can you win any other time?
Alternate build:
-
make alt
+
make alt
Alternate use:
Rather than use ttt try the script ttt.alt instead.
Judges’ remarks:
@@ -259,7 +260,7 @@ longer loses games.
function as a(), b(), or c(). After each function is called, the global
variables X and O contain bitmasks of where all the Xs and Os are placed.
The statement:
-
X=- <char> -1;
+
X=- <char> -1;
evaluates to 1, -1, or -2 when X is 1 and <char> is one of "X",
"0", or " ". The function S(&X) sets the appropriate bits in (global
vars) X and O and resets the value of &X to 1. This is how the current
@@ -372,10 +373,10 @@ found. A template is scanned from bottom to top, right to left
Once you get past the obfuscation, you have an opportunity to learn
about regular expressions and state machines.
@@ -214,7 +215,7 @@ character list.
[q5]
With the automaton specification in filename, invoke the program by
typing
-
./adrian filename
+
./adrian filename
It will read the file and print out all the lines which the automaton
accepts. If the file cannot be opened, a system error message will
be printed. If the input contains errors, then an error message along
@@ -225,7 +226,7 @@ being processed is printed. Error no_destination occurs if you spec
set of characters, but no destination state, and error too_many_states
occurs if your automaton has more than 257 states.
Running:
-
./adrian from < your_mailbox
+
./adrian from < your_mailbox
will perform a function similar to that of the unix from command.
If no filename is specified on the command line, then __FILE__ is used as the
specification for the automaton. (Originally this was "adgrep.c" but the file
@@ -234,23 +235,23 @@ changed to __FILE__.) In this case, the program will search for mat
the regular expression:
^.[^|C][^w[Q]*(Q|[w[]c).*|^.[C|]$
I suggest using adrian.c as input, and storing the output in adwc.c:
-
./adrian < adrian.c > adwc.c
+
./adrian < adrian.c > adwc.c
Compiling the new file, adwc.c, yields a clone of the unix wc command. It
runs on one file, defaulting to "adrian.c" if no file is given (again, this
was changed to be __FILE__) and displays the number of lines, words, and bytes
in the input file.
Another possibly interesting automaton can be created by slightly
adjusting the adrian.c file. Change the first line to read
-
/* . echo| . */
+
/* . echo| . */
and repeat the process above
-
./adrian <adrian.c > adecho.c
+
./adrian <adrian.c > adecho.c
The new file now contains all lines which match
^.[^5|m^]*[m^]([e=p,;]|[^e=+p,;].*)$
Compile and run. This is an echo(1) clone. Note the efficient algorithm
employed.
Two other adjustments to the first line also yield useful results. By
changing it to
-
/* . head; . */
+
/* . head; . */
you can search for matches to
^.[^W]*W..*$
By some freak happenstance, lines of adrian.c which match this regular
@@ -258,7 +259,7 @@ expression form a unix head(1) command. It prints the first ten lin
the file specified on the command line or adrian.c if no file is
specified (again this was changed to __FILE__).
By setting the first line to
-
/* . basename . */
+
/* . basename . */
a clone of the unix basename(1) command can be unearthed. The automaton will
search for
^.[^j]*jr.*$
@@ -268,7 +269,7 @@ filename, and the second, an extension. All leading pathname components
are removed from the filename, and the extension is removed if present.
The resulting base name is printed to stdout.
Lastly, by setting the first line to
-
/* . sleep . */
+
/* . sleep . */
you can search for
^.[^(~][^s]*sl.*$
Filtering adrian.c through this search yields a clone of the sleep(1)
@@ -327,10 +328,10 @@ when compiled depending on the compiler.
An alternate version of this entry, albert.alt.c, is provided.
Leo Broukhis, before he was an IOCCC judge, sent the IOCCC
@@ -173,11 +174,11 @@ judges this Email message:
albert.c is the file before applying Leo Broukhis’ fix.
Alternate build:
To compile this alternate version:
-
make alt
+
make alt
Alternate use:
Use albert.alt as you would albert above.
Alternate try:
-
./try.alt.sh
+
./try.alt.sh
Judges’ remarks:
We were impressed with the speed at which it was able to factor
arbitrarily large numbers consisting of factors that fit into
@@ -194,10 +195,10 @@ multiplication, until the candidate factor no longer fits in a signed long.
if you want to factor Fermat’s 4th number. Then just run it.
Or you may type ./albert <some-number>
A nice one is also (30 ones):
-
./albert 111111111111111111111111111111
+
./albert 111111111111111111111111111111
Apart from the foregoing there are no special execution instructions.
To customize the program into a factorizer of a fixed number, use
-
cc albert.c -o 4294967297
+
cc albert.c -o 4294967297
or some such.
There are no data files used, and it is not possible to feed input
via stdin.
@@ -259,10 +260,10 @@ Observation: “if it ends in a zero, it is divisible by ten”.
Notice how many statements it takes to do anything useful?
Author’s remarks:
@@ -162,11 +163,11 @@ short strings.
What it does
buzzard.1 is a simple mathematical program. It expects two numeric
arguments.
-
./buzzard.1 0 <num>
+
./buzzard.1 0 <num>
will print out the factorial of <num>.
-
./buzzard.1 <num1> <num2>
+
./buzzard.1 <num1> <num2>
will print out the largest common factor of num1 and num2.
-
./buzzard.1 1 <num2>
+
./buzzard.1 1 <num2>
will print out a factor of num2 if it’s composite, or else
it will print a string informing you that num2 is prime.
If the first argument is less than 0, it prints out an
@@ -244,13 +245,13 @@ BCD, so it can be output by the hexadecimal output statement.
programs is the conditional (given that we have loops).
Since all you can do in the given operation output set is
assignment, we implement “conditional assignment”:
-
if (x) y = z;
+
if (x) y = z;
To implement this, we constrain x to be either 0 or 1, and
simply compute:
-
y = (z * x) + (y * (1-x));
+
y = (z * x) + (y * (1-x));
This is more obscured by factoring out common terms and restricting
ourselves to two operand operations:
-
temp = z; (temp == z)
+
temp = z; (temp == z)
temp -= y; (temp == z-y)
temp *= x; (temp == (z-y)*x)
y += temp; (y == (z-y)*x + y)
@@ -260,7 +261,7 @@ ourselves to two operand operations:
“I’m supposed to execute statement pc next”, says our emulator. But suppose
we’re not currently coming up on statement pc. To handle this, we simply make
every operation conditional on the pc having the correct value:
-
if (pc == some_constant) y = z;
+
if (pc == some_constant) y = z;
To combine this with other operations, we simply multiply by our
(pc == some_constant) flag right after the above temp *= x.
To evaluate pc == some_constant requires one more trick. We assume that
@@ -310,10 +311,10 @@ dedicated to the memory of Charles Barrett.
There is an alternate version of this program. See Alternate
code below for details.
To use:
First, you must make sure that first is made first (even though make all
should make first first :-) ):
-
make first
+
make first
Second:
-
# get help:
+
# get help:
echo help | cat third help.th - | ./first
# try out a demo:
cat third demo5.th | ./first
Third:
-
cat third help.th - | ./first
+
cat third help.th - | ./first
NOTE: Wait until ‘Ok’ is printed and the type:
2 3 + . cr
Yes you should really type the 2 letters: cr.
Fourth:
Sorry, this is third!
Try:
-
./try.sh
+
./try.sh
Alternate code:
This alternate version, buzzard.2.alt.c, does not contain a
fix that the author notes in their remarks.
Alternate build:
-
make alt
+
make alt
Alternate use:
Use buzzard.2.alt as you would buzzard.2 above.
Alternate try:
-
./try.alt.sh
+
./try.alt.sh
Judges’ remarks:
Have fun!
Author’s remarks:
@@ -204,7 +205,7 @@ included, but it only works on ASCII systems.
Do not expect to be able to do anything interesting with first.
To do something interesting, you need to feed first the file
third first. In unix, you can do
-
cat third help.th - | ./first
+
cat third help.th - | ./first
to do this. Hopefully most operating systems will provide a way to do this. It
may take some time for this to complete (I seem to remember it taking several
minutes on an 8086 PC); THIRD will prompt you when it is finished. The file
@@ -283,7 +284,7 @@ take a significant amount of time in THIRD.
FORTH code
(first has no way of knowing if keyboard input is waiting, so it can’t actually prompt
you in a normal way. It only prints 'Ok.' after you define a word).
-
2 3 + . cr
+
2 3 + . cr
(which adds 2 and 3, and print the result and a newline.)
THIRD responds:
5
@@ -349,10 +350,10 @@ and thus indirectly inspiring me to write this program.
This script will determine (or try and determine) where your system dictionary
is located and assuming that it can find one it’ll use that. It checks the
following locations though the last one is more ironic:
@@ -160,7 +161,7 @@ following locations though the last one is more ironic:
/usr/ucblib/dict/words
/dev/null # <-- for machines with nothing to say
Then using the proper dictionary file it does:
-
./ag free software foundation < /usr/share/dict/words
+
./ag free software foundation < /usr/share/dict/words
./ag obfuscated c contest < /usr/share/dict/words
./ag unix international < /usr/share/dict/words
./ag george bush < /usr/share/dict/words
@@ -179,7 +180,7 @@ names listed above. Run this program to find the anagrams they
weren’t allowed to print!
The author provided an obfuscated script that can be used to construct
dictionaries which has been put in as mkdict.sh. To use try:
-
cat README.md | ./mkdict.sh > words
+
cat README.md | ./mkdict.sh > words
Then try using the program as shown above with the file words.
Author’s remarks:
The name of the game:
@@ -195,7 +196,7 @@ natural language of your choice, one word on each line. If your machine doesn’
have one already, you can make your own dictionary by concatenating a few
hundred of your favourite Usenet articles and piping them through the following
obfuscated shell script:
-
Using articles from alt.folklore.computers is likely to make
a more professional-looking dictionary than rec.arts.erotica.
@@ -323,7 +324,7 @@ the carries generated in incrementing i propagate straight across
those bits that should remain zero. For example, the following
program prints all those 16-bit integers that contain zeroes in all
even bit positions:
-
AG uses a similar method but works in the opposite direction, finding
the next lower value with zeroes in given bit positions by propagating
borrows across those bits. Some additional adjustments are made
@@ -362,10 +363,10 @@ the word directly from standard input to standard output.
@@ -141,15 +142,15 @@ Location: GB - United Kingdom of Great
To build:
-
make all
+
make all
To use:
-
# text mode
+
# text mode
./imc -text
./imc
Try:
To see a number of options and configurations:
-
./try.sh
+
./try.sh
Judges’ remarks:
The program is more interesting to run on workstations that can make use of a
Sun raster file. Others can make use of the -text flag for character oriented
@@ -263,7 +264,7 @@ bits (e.g. 8).
standard error to indicate its progress (one dot per pixel line).
The program uses error messages issued by the C Preprocessor to
generate its message to the world. One program’s error is another
@@ -183,10 +184,10 @@ generates when compiling the source.
@@ -141,9 +142,9 @@ Location: IT - Italian Republic (<
To build:
-
make all
+
make all
To use:
-
./marangon
+
./marangon
Judges’ remarks:
The object is to refill the table with 5’s, by incrementing or decrementing
numbers as needed. It is the side effects that get you into trouble. If you
@@ -184,10 +185,10 @@ number, all the other eight numbers next to it decrease and vice-versa.
@@ -141,13 +142,13 @@ Location: GB - United Kingdom of Great
To build:
-
make all
+
make all
To use:
-
./nathan
+
./nathan
# enter some text
Try:
To see some other fun uses:
-
./try.sh
+
./try.sh
Judges’ remarks:
WARNING:
The judges make no claim as to the strength or security
@@ -173,7 +174,7 @@ fall under this restricted category, the judges originally were not able to
distribute some winning entries outside of the US.
Nathan Sidwell stated that he was willing to distribute the winning source. To
read HIS instructions of how to obtain his winning program one was able to run:
-
make nathan
+
make nathan
./nathan
to learn how to get a copy of the code.
See the 1992/nathan.c file in the
@@ -247,10 +248,10 @@ operator, or argument separator?).
You might start off by giving the following input:
63 43
@@ -158,7 +159,7 @@ Location: US - United States of America
The judges assume no responsibility for the obfuscated opening
suggested above. :-)
For a real quick game try:
-
./vern
+
./vern
65 55
66 46
@@ -225,7 +226,7 @@ at build time into much-needed text. Without this hack the program
wouldn’t pass the character limit. A nice side effect is that the
initial source is gloriously difficult to peruse. In particular, the Makefile
does:
-
sed <vern.c 's/{ /(/g;s/} /)/g;s/; /#define /' | \
+
sed <vern.c 's/{ /(/g;s/} /)/g;s/; /#define /' | \
sed 's/} /=/g;s/{ /i/g' >vern.tmp.c
and compiles vern.tmp.c.
Second, the rather ho-hum step has been taking of naming each variable
@@ -281,10 +282,10 @@ nearest multiple of 4, and then the other constants are derived fro
Where lat and long correspond to your latitude and longitude.
NOTE: you MUST have a terminal that is at least 80 columns for this to show
properly. The whereami and whereami.alt code checks this but it is not
prohibitive if it cannot be compiled and linked (it uses curses); instead one
should just use the westley and westley.alt programs directly.
Try:
-
./try.sh
+
./try.sh
Alternate code:
The author provided a version for the US which we added. To build:
Alternate build:
-
make alt
+
make alt
Alternate use:
-
./whereami.alt.sh lat long
+
./whereami.alt.sh lat long
NOTE: this alternative version also needs a terminal with at least 80 columns.
Alternate try:
The try.sh script uses both the original entry and the alternate code
so one can try the same script for both:
-
./try.sh
+
./try.sh
Judges’ remarks:
To find the approximate place where this entry was judged, type:
-
./whereami 37 -122 # NOTE: - means west of meridian
+
./whereami 37 -122 # NOTE: - means west of meridian
# or if you don't have curses installed:
./westley 37 -122 # NOTE: - means west of meridian
@@ -243,12 +244,12 @@ is reasonably accurate.
Tokyo 36 140
For a domestic (US) version with higher resolution, try:
main(l,a,n,d)char**a;{for(d=atoi(a[1])/2*80-atoi(a[2])-2043;
n="bnaBCOCXdBBHGYdAP[A M E R I C A].AqandkmavX|ELC}BOCd"
[l++-3];)for(;n-->64;)putchar(!d+++33^l&1);}
The code will test the 80-column wrap and document itself if it is
joined together as one 160-character line and listed. You should see:
-
main(l,a,n,d)...
+
main(l,a,n,d)...
[A M E R I C A]...
…going down the left edge if your terminal auto-wraps at 80 characters.
@@ -144,19 +145,19 @@ Location: US - United States of America
We recommend you try the alt version first so you can get a better idea of what
this entry was like back in 1993. See the original code
section below to run the original.
datafile is the initial pattern (default: dgibson.data1)
Try:
-
./try.sh
+
./try.sh
Judges’ remarks:
We have provided the shell script dgibson.sh to make it easier
to run this entry. Run this shell script several times to
@@ -219,10 +220,10 @@ necessary to recurse main() in two “directions” simultaneously.
A negative argument plays the patience puzzle. An argument
greater than 0 plays the Tower of Hanoi puzzle. In either case
@@ -160,11 +161,11 @@ the argument 127 to this program and want to see it finish!
Author’s remarks:
What this program does
Output solution to Towers of Hanoi for five rings:
-
./ejb 5
+
./ejb 5
The format of the output for the Towers of Hanoi case is simply a
text description of how to solve the puzzle.
Output solution to the Patience puzzle for six rings:
-
./ejb -6
+
./ejb -6
For the patience puzzle, the output is a sequence binary codes representing
successive states of the puzzle. The rightmost digit represents the first ring.
A 1 means the ring is on the U; a 0 means it is off the U. The program
@@ -224,10 +225,10 @@ compiler since it uses signed char and ANSI-style function declarat
@@ -145,9 +146,9 @@ Location: NO - Kingdom of Norway (
compile. macOS users running Mountain Lion and later will need to download and
install XQuartz in order to compile and run this
entry.
-
make all
+
make all
To use:
-
./jonth # must be run on an X11 server
+
./jonth # must be run on an X11 server
Judges’ remarks:
Use h and l to shift objects left or right. Use k to
rotate and press SPACE to drop.
@@ -185,10 +186,10 @@ This program will not work on machines where sizeof(int)!=sizeof(void *)
If you have gcc < 2.3.3 (i.e. the entry can compile):
-
./lmfjyh
+
./lmfjyh
Alternate code:
This version does what the code did but in a way that will work with modern
compilers. We’d like to say there’s something special about it but there isn’t.
Nonetheless it will be compiled in case the original entry fails to compile.
Alternate build:
Should you wish to build this version manually:
-
make alt
+
make alt
Alternate use:
Use lmfjyh.alt as you would lmfjyh above. Note that other code could also be
done with the bug that the entry abuses but that would have to be manually
@@ -189,7 +190,7 @@ best with C-source code.
As an example, I have taken a simple “Hello world!” program
that should be familiar to all C-programmers.
Listing 1: A simple “Hello World” program
-
main()
+
main()
{
puts("Hello World!");
}
@@ -200,9 +201,9 @@ PROGRAM. There is no need to waste valuable disk space to store source
The program is embedded in the file name, only a minor portion of it is inside
the file.
Listing 2: Compressed “Hello world”
-
char*_=__FILE__;
+
char*_=__FILE__;
Listing 3: Code embedded in the file name
-
";main(){puts("Hello World!");}char*C=".c
+
";main(){puts("Hello World!");}char*C=".c
The sample program in listing 1 is 36 bytes long. By using the new
compression method, the example program may be squeezed to sixteen
bytes. In the example the compression ratio is 2:1. It is evident
@@ -303,10 +304,10 @@ be new standard.
We recommend that you try the alternate version first to get a better idea of
what this entry looked like back in 1993. The alternate version sleeps (via
usleep(3)) in between writes, defaulting at 1000 microseconds (but
reconfigurable). If you wish to see the original entry then see original
code below.
If you wish to speed the entry up, say to 500 microseconds between writes, try:
-
make clobber SLEEP=500 alt
+
make clobber SLEEP=500 alt
Alternatively if you wish to slow it down, say to 1500 microseconds between
writes, try:
@@ -141,7 +142,7 @@ Location: GB - United Kingdom of Great
To build:
-
make all
+
make all
NOTE: there are two alternate versions of this program, both allowing one to
slow down the game and the second one with movements more familiar to vi users.
See the Alternate code section below.
@@ -150,22 +151,22 @@ See the Alternate code section below.
to another value like 18 or 19 which you can do with the alternate code.
In the case of rince.alt2.c the movement keys for the default
game are slightly different and will feel more familiar to vi users: h for
left, l for right (that was not changed) and k for fire (that was also not
changed).
Alternate build:
-
make SLEEP=18 clobber alt
+
make SLEEP=18 clobber alt
Replace 18 with whatever number you wish.
Alternate use:
Use rince.alt or rince.alt2 as you would rince above.
@@ -194,7 +195,7 @@ with it.
/usr/local/include/curses.h if not /usr/include/curses.h) is not compatible
with the curses library (typically /lib/libcurses.a for static libraries)
used. It has been suggested that the following gcc command may help:
-
This is a Cellular Automata Based, Beautifully Abysmal Game Environment (or
CABBAGE for short). To execute the program simply type ./rince gamefile,
@@ -301,10 +302,10 @@ mechanism other than control-c.
where exp is an octal expression. See below for how it can also have
hexadecimal and decimal numbers.
Try:
-
./try.sh
+
./try.sh
What happens if you use something other than valid digits?
Judges’ remarks:
The octal expression may contain:
@@ -217,7 +218,7 @@ involving **O7 and octal constants are looking for certain characte
Here’s a version of the program before it got formatted into the VIII,
augmented with comments showing where each state begins. N1 and N2 are
notes:
-
#define O5 main
+
#define O5 main
O5(O2,O7,O3)char**O7;
{
return
@@ -258,9 +259,9 @@ program with no parameters, in which case it just returns 0.
the first state it will go into. This state just invokes
printf, and sends the parser to state 012 (which is <E>).
The E and T states work like this:
-
int e(){ return eprime( t() ); }
+
int e(){ return eprime( t() ); }
The E' and T' states work like this:
-
int eprime( int intermediate )
+
int eprime( int intermediate )
{
if( ch == '+' )
{
@@ -271,7 +272,7 @@ printf, and sends the parser to state 012 (which is <E>
}
The D, X and O states work like this (they assume that they’re initially
called with 0):
-
int octal( int intermediate )
+
int octal( int intermediate )
{
if( ch>='0' && ch<='7' )
{
@@ -310,10 +311,10 @@ called with 0):
@@ -141,7 +142,7 @@ Location: US - United States of America
To build:
-
make all
+
make all
There is an alternate version that allows you to cheat, giving you configurable
amount of arrows at the start of the game. See the Alternate
code section below.
This version allows you to choose how many arrows to start with, instead of the
default 0. If one tries specifying a value < 0 it will set it to 0.
Fun fact: this version helped uncover and fix a bug that prevented the entry
from working in some cases.
Alternate build:
-
make alt
+
make alt
The default number of arrows in this version is 3 but if you want to change it,
say to 5, try:
-
make clobber ARROWS=5 alt
+
make clobber ARROWS=5 alt
Alternate use:
-
./dodsond2.alt
+
./dodsond2.alt
Judges’ remarks:
Each year people find new ways to squeeze more and more out of the
contest rules. Next year, entries that use compression utilities
@@ -235,10 +236,10 @@ of the current room again.
@@ -141,22 +142,22 @@ Location: US - United States of America
To build:
-
make all
+
make all
To use:
-
./horton A B C D
+
./horton A B C D
A, B, C and D are numeric arguments.
Try:
-
./try.sh
+
./try.sh
Alternate code:
This confuses cb greatly. See horton.alt.c for an unobfuscated/enhanced
version.
Alternate build:
-
make alt
+
make alt
Alternate use:
-
./horton.alt A B C D
+
./horton.alt A B C D
Where A, B, C and D are numbers like with horton.
Alternate try:
-
./try.alt.sh
+
./try.alt.sh
Judges’ remarks:
Try to figure out how this program prints, for a given slope, the
right character. And for extra credit, try to figure out which
@@ -176,7 +177,7 @@ cogs in the wheels of the grand plot to overthrow the cubics!
Oh, by the way, it uses a self-contained graphtab and frame buffer.
It’s easily modified to graph any 96x160 bitmap on a dumb terminal.
There are two alternate versions, one that has an increased buffer size and one
that uses fgets(); neither are completely functional.
See below section bugs and (mis)features for details and the alternate
@@ -151,9 +152,9 @@ code section for how to use.
STATUS: uses gets() - change to fgets() if possible
The first version, schnitzi.alt.c, uses fgets(3) but when fed its own code
it will generate code that still uses gets(3). What’s more is it will not
@@ -163,15 +164,15 @@ its own source code it will generate code that can compile but with the original
buffer size. This is due to a comment which is explained in more detail in
1994/schnitzi bugs.
Alternate build:
-
make alt
+
make alt
Alternate use:
Use schnitzi.alt and schnitzi.alt2 as you would schnitzi above except that
feeding the source code to it will not work right.
Alternate try:
-
./try.alt.sh
+
./try.alt.sh
Judges’ remarks:
Try:
-
./schnitzi < schnitzi.c
+
./schnitzi < schnitzi.c
Compare the output of the program with its source. Sure the output
is different, but there is more than meets the diff’s eye. Can you
find out why?
@@ -187,10 +188,10 @@ second row is written down the second column, etc. The program
is run by redirecting a file into the executable on the command
line; for instance, for the file ‘info’, the program
would be run as follows:
-
./schnitzi < info
+
./schnitzi < info
The program generates interesting results when its source file is
used as input:
-
./schnitzi < schnitzi.c
+
./schnitzi < schnitzi.c
The result of this command is a program which does the exact same
thing – in other words, both the program and the “flipped”
version of itself work identically (you’ll need to redirect the
@@ -245,10 +246,10 @@ needed to pad it put it over the limit – it nearly filled a 79 by
@@ -141,11 +142,11 @@ Location: US - United States of America
To build:
-
make all
+
make all
To use:
-
./smr
+
./smr
Try:
-
./try.sh
+
./try.sh
Judges’ remarks:
Nearly every year, one or more people would submit what they claimed
was the world’s smallest self reproducing program. While the sizes
@@ -190,10 +191,10 @@ Produces a listing of itself on stdout.
./try.color.sh # for colour displays
./try.bw.sh # for Black & White displays
Alternate code:
The author provided us a spoiler version that might be of interest to some.
Alternate build:
-
make alt
+
make alt
Alternate use:
-
./tvr.alt altmode screensize/2 < colormapfile
+
./tvr.alt altmode screensize/2 < colormapfile
where altmode1 - 4 correspond to mode 0 - 3 in the original entry and
altmode 0 calculates Mandelbrot/Julian sets correctly.
Alternate try:
-
./try.alt.color.sh # for colour displays
+
./try.alt.color.sh # for colour displays
./try.alt.bw.sh # for Black & White displays
Judges’ remarks:
This entry requires the use of X11. It will form two windows (hopefully your
@@ -208,7 +209,7 @@ noise.
second is a variation of that. The third makes nice 3D-look-a-like effects and
the fourth is a variation of that with more nice effects.
Usage:
-
./tvr mode screensize/2 < colormapfile
+
./tvr mode screensize/2 < colormapfile
The first parameter is the operating-mode of the program. There are 4 fractal
pairs and 3 display modes, making total of 12 modes. screensize is half of the
actual screenlength/width. I.e. if you use 128 as a second parameter, you will
@@ -326,10 +327,10 @@ mono).
try.color.sh - demonstrate alt code in colour mode
There is an alternate version that uses more memory. See alternate
code below for more details.
To use:
-
./weisberg
+
./weisberg
Try:
-
./try.sh
+
./try.sh
If you have primes(1) installed you might also wish to try:
-
./primes.sh number
+
./primes.sh number
where number is a positive number, defaulting to 15. The try.sh
script will also do this.
Alternate code:
@@ -157,9 +158,9 @@ script will also do this.
have some 512 Megabytes of virtual memory lying around with to do
something with you might try this version.
Alternate build:
-
make alt
+
make alt
Alternate use:
-
./weisberg.alt
+
./weisberg.alt
Lesser systems will find this alternative version a good way to create
a core file. :-)
Judges’ remarks:
@@ -218,10 +219,10 @@ a bonus, the understandability of the code was reduced to zero.
@@ -141,7 +142,7 @@ Location: US - United States of America
To build:
-
make alt
+
make alt
We recommend that you try the alternate version first as the original entry
requires (for better display) 80 columns and 8 character tabs with wraparound.
The alt code uses the same logic as the original code except that the original
@@ -149,7 +150,7 @@ code used #includes of files that do not exist to generate the mess
compiler errors) whereas the alt code uses printf(3). For the original entry
see Original code below.
To use:
-
./westley.alt
+
./westley.alt
The purpose of the game is to escape the dungeon. Depending on the compiler line
you will get a different message when you run the program. One compiler line
will make you win the game (escape the dungeon) and others will show something
@@ -164,10 +165,10 @@ from start to finish.
Try:
For something more interesting try compiling it with different cc -D arguments
and then run the program each time. For example:
-
cc -Describe -Door westley.alt.c -o westley.alt && ./westley.alt
+
cc -Describe -Door westley.alt.c -o westley.alt && ./westley.alt
cc -Describe -Drain westley.alt.c -o westley.alt && ./westley.alt
To see the game from start to finish, try:
-
./try.alt.sh
+
./try.alt.sh
Original code:
The purpose of the game is to escape the dungeon via the compiler line
where you get messages as compiler errors. Depending on the compiler line you
@@ -177,7 +178,7 @@ game!
wraparound. The alternate code does not have this limitation and it is for this
reason that we recommend you try it first.
Original build:
-
make all
+
make all
There are a variety of different -D flags you can give to cc that change the
message you get. You might wish to look at the source code to get a
better idea or see below in the Original try section for
@@ -196,15 +197,15 @@ error messages; there is no running the program.
Original try:
For something more interesting try compiling it with different cc -D
arguments:
-
cc -Describe -Door westley.c
+
cc -Describe -Door westley.c
cc -Describe -Drain westley.c
To see the game from start to complete, try:
-
./try.sh
+
./try.sh
Judges’ remarks:
Not all compiler errors are bad.
For spoilers see the end of the notes from the author below.
To use:
-
./try.sh
+
./try.sh
Author’s remarks:
This program, in accordance with the rules, compiles into a legal
C program without human intervention. However, it simply compiles
@@ -213,7 +214,7 @@ to actually compile the program.
This program is a simple adventure game which uses only C preprocessor
error messages (for missing #include files) as output. To begin,
try to compile the program with no options:
-
cc westley.c
+
cc westley.c
This will fail, producing an error message for a missing #include
file as the opening description. Your terminal should be set for
80 columns, 8 character tabs, and wraparound, as there is no way
@@ -232,7 +233,7 @@ to reliably output newlines. You should see something like this
missing include file name, which functions as the game text.
To “do” things, all words must start with -D. For example, to
look at the door, do:
-
cc -Describe -Door prog.c
+
cc -Describe -Door prog.c
…and you will get another error message telling you about the door.
(note: some compilers will stop after the first missing include file,
while others will continue to try compiling; the latter will repeat
@@ -241,7 +242,7 @@ with “verbose” turned on).
The goal of the game is to escape the dungeon.
Here is a walk-through for the game, including a few dead-ends:
SPOILER
-
cc -Describe -Door westley.c
+
cc -Describe -Door westley.c
cc -Describe -Drain westley.c
cc -Describe -Dwarf westley.c
cc -Describe -Debris westley.c # or -Dungeon
@@ -291,10 +292,10 @@ unimportant.
@@ -144,7 +145,7 @@ Location: ZZ - Unknown locationWe recommend that you try the alternate version first so you can see what this
entry looked like back in 1995 (with a configurable speed). See the original
code section below for the original entry.
-
make alt
+
make alt
The alternate version uses usleep(3) with SLEEP (defined in the Makefile,
default 3000) microseconds to make it easier to see the maze being solved in
real time. You can redefine SLEEP at compile time to reconfigure it in case
@@ -155,13 +156,13 @@ making it 100000 (which is actually fun :-) ).
make SLEEP=1500 clobber alt
./cdua.alt # press enter and watch it go much faster!
You might also like to try:
-
make SLEEP=65000 clobber alt
+
make SLEEP=65000 clobber alt
./cdua.alt # press enter and watch it go much slower!
Do you see anything strange in this version when SLEEP is a high value like
@@ -174,9 +175,9 @@ actually see it being solved in real time rather than have it go by in a flash.<
If you wish to use the original version, for instance if you wish to see how
fast your computer is :-) or use both to see the difference, you can do so.
Original build:
-
make all
+
make all
Original use:
-
./cdua
+
./cdua
Judges’ remarks:
This could be used as the basis of an a-maze-ing screen exerciser.
Author’s remarks:
@@ -211,10 +212,10 @@ statement to solve the maze.
@@ -141,11 +142,11 @@ Location: US - United States of America
To build:
-
make all
+
make all
To use:
-
./dodsond1 < text_file
+
./dodsond1 < text_file
Try:
-
./dodsond1 < README.md
+
./dodsond1 < README.md
Judges’ remarks:
You might consider giving the following input:
... a male (who) gets very, very frustrated sitting in a chair all
@@ -153,7 +154,7 @@ Location: US - United States of America
giraffes.
-- Adjunct Professor Newt Gingrich, Reinhardt College, 1/7/95
@@ -141,9 +142,9 @@ Location: US - United States of America
To build:
-
make all
+
make all
To use:
-
./dodsond2
+
./dodsond2
Judges’ remarks:
An amazing entry!
The official chef enjoyed solving the maze, which she did on the first
@@ -181,10 +182,10 @@ in an unknown labyrinth, areas which you have not visited cannot be seen.
@@ -141,22 +142,22 @@ Location: DE - Federal Republic of Germ
To build:
-
make all
+
make all
To use:
-
./garry <input_file >output_file
+
./garry <input_file >output_file
Try:
-
./try.sh
+
./try.sh
Alternate code:
While it may not have been the intention of the author, the
judges noted that the C pre-processed version (with the #includes
left intact) looked very much like a rat “dropping core”. See
garry.alt.c and judge for yourself!
Alternate build:
-
make alt
+
make alt
Alternate use:
-
./garry.alt <input_file >output_file
+
./garry.alt <input_file >output_file
Alternate try:
-
./try.alt.sh
+
./try.alt.sh
Judges’ remarks:
The author was kind enough to provide a less obfuscated version of
the source called garry.fmt.c.
@@ -166,9 +167,9 @@ incorporating the ability to create binary from escaped data in the
environment variables.
The calling syntax is pretty simple, just use it with stdio-redirection
or inside pipelines, e.g.:
-
./garry <file_to_convert >converted_file
+
./garry <file_to_convert >converted_file
or
-
cat all_my_files/* | ./garry | lp
+
cat all_my_files/* | ./garry | lp
The syntax of the conversion of the input file is as follows: To include the
value of an environment variable in the output file, place the name of the
variable between $-signs in the input, e.g.:
@@ -177,7 +178,7 @@ variable between $-signs in the input, e.g.:
Unknown Env-variables or malformed expressions are ignored and kept intact.
Additionally, the filter replaces escaped octal values in the environment
variables by their binary representation, e.g.:
./leo [ deep ] [ right ] [ Variable ] [ cycle [ freq ] ]
+
./leo [ deep ] [ right ] [ Variable ] [ cycle [ freq ] ]
See the author’s information below on these details.
Try:
-
./try.sh
+
./try.sh
Judges’ remarks:
Press return after each image is drawn.
The variable names are element-ary. If you find this confusing,
@@ -163,7 +164,7 @@ the secret switches that the author doesn’t divulge ! (All switches are single
characters on the command line - anything that’s not a number is a candidate.)
Author’s remarks:
The usage is:
-
./leo [ deep ] [ right ] [ Variable ] [ cycle [ freq ] ]
+
./leo [ deep ] [ right ] [ Variable ] [ cycle [ freq ] ]
where the first three are literal words, cycle is a positive integer (0 is
ignored), and freq is an integer (default = 0) that’s supposed to be in the
range 0..100 (bigger values are allowed, however). Invalid parameters and
@@ -173,7 +174,7 @@ equivalent to ./leo 0 0 0 1 Variable 70 right, etc.
If Variable is used, cycle is almost ignored (see below) but has
to be present if you want to enter freq (and you usually do).
Some options to try (besides the obvious):
-
./leo 1 | cat - /dev/tty | gs -
+
./leo 1 | cat - /dev/tty | gs -
This draws the basic pattern I invented in high school:
You take a big sheet of “arithmetic” paper and draw a line
of length 1 (between 2 crossings) at the center of the sheet:
@@ -253,11 +254,11 @@ the opening for step 1 is not a single line but a cross:
\./
/ \
To watch it repeatedly (as a screen saver), use:
-
./leo 2 | cat - /dev/tty | gs -
+
./leo 2 | cat - /dev/tty | gs -
The command line:
-
./leo Variable 1 | cat - /dev/tty | gs -
+
./leo Variable 1 | cat - /dev/tty | gs -
draws the same as above. Try:
-
./leo Variable 1 1 | cat - /dev/tty | gs -
+
./leo Variable 1 1 | cat - /dev/tty | gs -
What happened to the picture? Increase freq and watch the changes.
If cycle is more than 1, the program loops, allowing the user to
enjoy randomly changing patterns (the delay is 3 seconds),
@@ -272,7 +273,7 @@ if you want to pipe the output to a printer.
If Variable is used, the actual value of cycle doesn’t matter,
as far as it is > 1. To figure out what difference
cycle makes when Variable is not used, try
-
./leo Variable 37 80 | cat - /dev/tty | gs -
+
./leo Variable 37 80 | cat - /dev/tty | gs -
and other values of cycle; smaller values usually require
smaller values of freq for the patterns to be non-trivial.
The options deep and right make the patterns to be drawn in different
@@ -323,10 +324,10 @@ even want to explain what it does. You’ve been warned!
The authors provided a spoiler version of the program. Originally uuencoded we
have decoded it for the wider audience in vanschnitz.alt.c. The
uuencoded blob is still available in their remarks below. They encourage you
to first try and figure out the program without the spoiler.
Alternate build:
-
make alt
+
make alt
Alternate use:
Use vanschnitz.alt as you would vanschnitz above.
Judges’ remarks:
@@ -187,7 +188,7 @@ for. This is done by defining the symbol n on the compile
line. For instance, to cause the compiler to solve the Towers
of Hanoi problem with four disks, you would compile the program
like this:
-
gcc hanoi.c -o hanoi -Dn=4
+
gcc hanoi.c -o hanoi -Dn=4
A default value of 5 will be used for n if you do not define
it on the command line. The value of n cannot be greater than
fifteen (the compiler we used to test has a limit on the #include
@@ -208,7 +209,7 @@ ANSI C feature in which adjacent character strings are
concatenated; a version that does not use this feature has been
included for people who can only run K&R). A good way to see
the resulting program (on a Unix system) is to do the command
-
gcc hanoi.c -E -Dn=5 | grep -v \# | grep -v ^\$
+
gcc hanoi.c -E -Dn=5 | grep -v \# | grep -v ^\$
For an odd number of disks, the program will provide a
solution wherein the disks end up on peg 2; for an even
number of disks, they will end on peg 3. This should
@@ -321,10 +322,10 @@ to try to decipher the program without it…
NOTE: some compilers will compile this code into infinite loops! If the above
cat line (or one of the ones later in the try section) does not execute in a
very short amount of time, then you may need to fix your compiler or use gcc.
The above should print a ! followed by a newline.
Try:
-
./try.sh
+
./try.sh
Judges’ remarks:
This entry can feed on itself. If you C pre-process the source,
you can compile the interpreter:
-
make august.oc
+
make august.oc
We can now compile the interpreter as follows:
-
cat august.c august.oc | ./august > august.oo
+
cat august.c august.oc | ./august > august.oo
and use the compiled interpreter to execute some previously
compiled code:
-
cat august.oo test.oo | ./august
+
cat august.oo test.oo | ./august
And we can have the compiled interpreter interpret itself which
in turn compiles the test program:
-
cat august.oo august.oo fac.oo | ./august
+
cat august.oo august.oo fac.oo | ./august
And if you have lots of spare time, you can recurse one level deeper:
We (the judges) recommend that you spend some time studying this
entry as it surely will make the ‘best of the IOCCC’ list. It was
very well received by those who attended the IOCCC BOF.
@@ -194,13 +195,13 @@ of operators, and control constructs.
can go wrong. But this is what seasoned C programmers are used to.
Assume that the interpreter has been compiled (source in august.c
and binary in august) and that we have this in a file named test.oc:
The compiler for OC is naturally written in OC (where did you think the byte
code came from?). It is in the file parse.oc.
@@ -210,20 +211,20 @@ preprocessor (hey, what do you expect from a program that is this small), so we
need to use an external one. To pre-process august.c use the
command from the Makefile, but add the -E flag and change 60000 to 40000,
i.e.:
-
cc -E -DZ=40000 .... august.c > august.oc
+
cc -E -DZ=40000 .... august.c > august.oc
If august.oc contain some junk line starting with a # (most likely
it does) then remove it like:
-
sed -i'' '/^#/d' august.oc
+
sed -i'' '/^#/d' august.oc
OK, we can now compile the interpreter:
-
cat august.c august.oc | ./august > august.oo
+
cat august.c august.oc | ./august > august.oo
And we can run it:
-
cat august.oo test.oo | ./august
+
cat august.oo test.oo | ./august
Here we have the interpreter interpreting another interpreter that runs
the program. Did you think that was too fast? Just throw in another
level of interpretation:
Fitting the byte code for the compiler into the initial comment
was a challenge. I had to strip the compiler/interpreter of
@@ -337,10 +338,10 @@ defined. getchar() and putchar() are predefined functi
We recommend that you use the alt version to see what the entry looked like back
in 1996. For the original version see the original code
section.
To use:
-
./eldby.alt
+
./eldby.alt
To quit send intr (typically ctrl-c).
NOTE: to reset the sanity of your terminal after this program ends try reset.
Try:
@@ -155,12 +156,12 @@ happening with modern systems, and to not flash too quickly, which can be
problematic for some people, can be configured to different speeds by way of the
value used in usleep(). The default is 35000 but you can easily change
it. To do so try:
-
make SLEEP=20000 clobber alt
+
make SLEEP=20000 clobber alt
./eldby.alt
Original code:
This version is the original which has no sleep time in between updates.
Original build:
-
make all
+
make all
Original use:
Use ./eldby as you would ./eldby.alt above.
Judges’ remarks:
@@ -197,10 +198,10 @@ must be VT100 or better with 80 columns and 24 rows or more.
As the script asks, care to guess why these execute differently? Only the
compiler knows … ok maybe other things like the author, the judges and perhaps
you too?
@@ -157,7 +158,7 @@ you too?
Gandalf. Go ahead, ‘try’ it! :-)
Judges’ remarks:
For misleading C pre-processor output, try:
-
cc -E gandalf.c
+
cc -E gandalf.c
Author’s remarks:
The program requires an ASCII system.
To build:
-
make all
+
make all
Bugs and (Mis)features:
The current status of this entry is:
STATUS: uses gets() - change to fgets() if possible
@@ -141,7 +142,7 @@ Location: NO - Kingdom of Norway (
To build:
-
make all
+
make all
NOTE: this entry requires X11/Xlib.h header file and the X11 library to
compile. macOS users running Mountain Lion and later will need to download and
install XQuartz in order to compile and run this
@@ -152,17 +153,17 @@ entry.
STATUS: missing or dead link - please provide them
@@ -141,13 +142,13 @@ Location: DE - Federal Republic of Germ
To build:
-
make all
+
make all
To use:
-
./schweikh1
+
./schweikh1
Try:
To find the day that Easter falls on in the current year and to show all Easter
dates from 1582 to 2199:
-
./try.sh
+
./try.sh
Judges’ remarks:
Look at the source. There is something very odd going on here.
Where does the real code come from if everything is a C pre-processor
@@ -251,10 +252,10 @@ problems on other systems.
@@ -141,9 +142,9 @@ Location: DE - Federal Republic of Germ
To build:
-
make all
+
make all
To use:
-
./schweikh2
+
./schweikh2
The program accepts up to 4 parameters:
The number of operators in the expression [default: 9]
@@ -152,11 +153,11 @@ Location: DE - Federal Republic of Germ
The goal value or 0/0 [default: 42]
Try:
-
./try.sh
+
./try.sh
What happens if you pass only three parameters like the below?
-
./schweikh2 15 1 0
+
./schweikh2 15 1 0
The author also suggests:
-
while :; do grep -v '#' schweikh2.c; done
+
while :; do grep -v '#' schweikh2.c; done
(and we do too) which works with sh, bash, ksh and zsh as well. Press
ctrl-c to stop it. Observe how the try.sh script does this once to
make it easier to see what is happening.
@@ -164,7 +165,7 @@ make it easier to see what is happening.
The original program, with only slight obfuscations, may be found
in hunni.c. The perl script, hunni.pl, obfuscates it
appropriately. Try:
-
less hunni.c
+
less hunni.c
perl ./hunni.pl < hunni.c
This entry was another crowd pleaser at the IOCCC BOF.
@@ -230,7 +231,7 @@ operators but you will probably wait quite some time for every of the
on a 50 MHz SPARC, 4^11 expressions are evaluated in about 3 cpu
minutes (gcc -O3).
The diamond pattern can be continued without a break.
For a nice printout try this on your Bourne compatible shell:
-
while :; do grep -v '#' schweikh2.c; done
+
while :; do grep -v '#' schweikh2.c; done
To build:
-
make all
+
make all
To use:
WARNING: DO NOT RUN this program without reading this text down to the end!
It may render your system unusable for a limited amount of time
or force you to reboot using the Big Red Button! This is NOT a joke.
You have been warned.
-
./schweikh3
+
./schweikh3
Judges’ remarks:
The source fails to compile on compilers that recognize the inline
keyword by default. For gcc, you may need to use -ansi.
See the file schweikh3.info for example output from various
systems.
But still it is a useful utility. To use try:
-
./schweikh3
+
./schweikh3
and thanks for the virtual memories! :-)
Author’s remarks:
Why I think my entry is obfuscated
@@ -171,7 +172,7 @@ COBOL, F77, awk etc.
You have to select maximum ANSI C conformance of your
compiler. The source fails to compile under a C++ compiler due to
the `new’ identifier which is a C++ reserved word:
-
$ g++ schweikh3.c
+
$ g++ schweikh3.c
schweikh3.c:9: parse error before `new'
schweikh3.c:16: parse error before `new'
schweikh3.c:46: parse error before `void'
@@ -181,7 +182,7 @@ the `new’ identifier which is a C++ reserved word:
schweikh3.c:91: confused by earlier errors, bailing out
The source fails to compile on compilers that recognize the inline
keyword by default, e.g. gcc:
-
$ gcc schweikh3.c
+
$ gcc schweikh3.c
schweikh3.c:46: parse error before `void'
schweikh3.c: In function `main':
schweikh3.c:91: parse error before `inline'
@@ -275,10 +276,10 @@ minute or so.
@@ -141,24 +142,24 @@ Location: US - United States of America
To build:
-
make all
+
make all
There is another version which is the original entry. See alternate
version for details as to how to use and why it was made the
alt version.
To use:
-
./clock1.sh
+
./clock1.sh
./clock2.sh
./clock3.sh
Try:
-
./try.sh
+
./try.sh
Alternate code:
The original version had a display problem in modern systems which somewhat
affected the usability of the program. This alternate code, the original, is
provided, to show the differences.
Alternate build:
-
make alt
+
make alt
Alternate try:
-
./try.alt.sh
+
./try.alt.sh
Judges’ remarks:
Time and time again, Brian Westley seems to come up with a winning entry!
We are amazed at how much is being done with only one relatively
@@ -183,7 +184,7 @@ my sample scripts.
These assumptions are pretty reasonable. 2) can be eliminated but makes the code
larger.
The program merely takes the minute (0-59) and the hour (0-23)
values, looks up the offsets in minute_map and hour_map
and writes the hand_symbol for each into the clock_image
@@ -236,10 +237,10 @@ position. It won’t move until both hands click over at 4:00.
@@ -141,7 +142,7 @@ Location: US - United States of America
To build:
-
make all
+
make all
If you do not have a page up or page down key you might wish to see the
Alternate code section below. You may redefine all the keys
and the time step with predefined macros, however, so one lacking page up / page
@@ -164,10 +165,10 @@ Instructions section.
to use. The name of the macro in the header file is what you need to set the
macros to, depending on what controls you wish to redefine. For instance, to set
the throttle up and down to u and d:
-
make clobber IT=XK_u DT=XK_d all
+
make clobber IT=XK_u DT=XK_d all
because in the header file you can see that XK_u corresponds to u and XK_d
corresponds to d:
-
#define XK_d 0x0064 /* U+0064 LATIN SMALL LETTER D */
+
#define XK_d 0x0064 /* U+0064 LATIN SMALL LETTER D */
#define XK_u 0x0075 /* U+0075 LATIN SMALL LETTER U */
Note that the keysym.h file is not complete from X11; it’s just the
more likely candidates (and some that are probably unlikely :-) ).
@@ -181,7 +182,7 @@ instructions. Since you can use the original entry to redefine these this is not
a problem and is purely a convenience .. if only for those who are okay with the
preselected alternative keys.
To use:
-
cat horizon.sc pittsburgh.sc | ./banks
+
cat horizon.sc pittsburgh.sc | ./banks
See the author’s remarks in scenery for more details on the scenery
files.
Try:
@@ -208,7 +209,7 @@ you should use the original entry as described in the to build section above.
To use the default settings for the alternate build:
-
make alt
+
make alt
You may change the other keys as described in the build instructions, above, but
this alt code can be seen as an alternative for those who don’t have or don’t
want to use page up and page down.
You can simulate flying through a cloud bank as well:
-
./banks < /dev/null
+
./banks < /dev/null
You will usually want at least a horizon, though.
The format of scenery files is simple, by the way. They’re just
a list of 3D coordinates, and the simulator simply draws line
@@ -371,10 +372,10 @@ flicker.
@@ -141,15 +142,15 @@ Location: US - United States of America
To build:
-
make chaos
+
make chaos
NOTE: Some systems do not implement halfdelay() in their libcurses.
You might try compiling with -lncurses if you have that library.
Or you can build this entry without the halfdelay() call by:
-
make chaos_nohalf
+
make chaos_nohalf
To use:
-
./chaos
+
./chaos
Try:
-
./try.sh
+
./try.sh
This script will run the program on each data file. To quit the program hit q.
If not all files have been used it will go to the next one; otherwise the script
will be finished. To end the script early send intr/ctrl-c.
./pootify.sh URL=https://microsoft.com | less
./pootify.sh -r URL=https://microsoft.com > ms.html
where the first one would show the text as rendered but without links, images
etc. and the second one would write the html to ms.html so that you could open
it in a browser.
For an old example of it working as a CGI script see:
There is an alternate version available that has a key configuration that will
be more familiar to vi(m) users and also allows one to quit. See alternate
code below.
@@ -153,7 +154,7 @@ code below.
STATUS: missing or dead link - please provide them
Pressing a moves the current letter position counterclockwise/anticlockwise
(a)round the border of the playing field.
Pressing s moves the current letter one position clockwise around the border
@@ -165,9 +166,9 @@ counterclockwise/anticlockwise h does as well; and in addition to <
clockwise l does as well. Instead of using d to drop the letter you can do
j or space. Finally to quit this version you can press q.
Alternate build:
-
make alt
+
make alt
Alternate use:
-
./pootris.alt [X size of board] [Y size of board]
+
./pootris.alt [X size of board] [Y size of board]
Judges’ remarks:
Read the authors’ remarks below to find out how to play. We believe that your
experience may mirror one of our experiences:
@@ -176,7 +177,7 @@ experience may mirror one of our experiences:
I spelled my first "poot". I was hooked ...
Author’s remarks:
Usage
-
./pootris [X size of board] [Y size of board]
+
./pootris [X size of board] [Y size of board]
Synopsis
The object of this game is to spell POOT as much as possible. There
is no time pressure. You’re given one letter at a time (sort of randomly
@@ -276,10 +277,10 @@ places.
That means bits 6 and 5 set to 00 is length 1, set to 01 is length 2, etc.
But this would mean that we would have to extract the length into a
counter before shifting out each symbol, such as
-
length = (encoding & 96) >> 5;
+
length = (encoding & 96) >> 5;
do {
putchar(encoding & 1 ? '-' : '.');
encoding >>= 1;
@@ -162,7 +163,7 @@ counter before shifting out each symbol, such as
length 4: 00.1xxxx Z > 00.11100
length 5: 0.1xxxxx 3 > 0.100111
with 1 bit still to be chosen freely (let’s assume it is 0). Now we can do
-
do {
+
do {
putchar(encoding & 1 ? '-' : '.');
encoding >>= 1;
while (encoding > 1);
@@ -179,7 +180,7 @@ following
Notice these encodings in the initialization string. Only the coding for
5 needs an escape (5 = ..... > 01111111 = '\177'). The way the length
is encoded still allows the encoding to be its own counter:
@@ -188,12 +189,12 @@ Note that the calculation for the next value of encoding is done at
precision, so that the actual value of the char remains <= 127.
The character '-' (ASCII 45) and '.' (ASCII 46) are conveniently in
sequence, so the putchar can simply be
-
putchar(45 + encoding % 2);
+
putchar(45 + encoding % 2);
I used the modulo operator this time, because + takes precedence over &.
The assignment can be incorporated into the while control test, and a
do-while loop with a body of a single expression statement can be written
as a while loop with a comma operator in the test:
Now, the decoding of Morse codes is just the reverse. We shift in 0s
and 1s as we scan the line. But: we have to scan from back to front
diff --git a/1998/dorssel/index.html b/1998/dorssel/index.html
index 7860fe4f3..4b99eea30 100644
--- a/1998/dorssel/index.html
+++ b/1998/dorssel/index.html
@@ -88,6 +88,7 @@
The file dorssel.md contains all the information needed to
understand this program. For an obfuscated spoiler, try
-
./dorssel < dorssel.md
+
./dorssel < dorssel.md
To build:
-
make all
+
make all
NOTE: this may take a while. Some systems may have problems building
this entry because of the system resources it requires.
To use:
-
./fanf
+
./fanf
Try:
Enter an expression on standard input. To try some we have selected:
-
./try.sh
+
./try.sh
Judges’ remarks:
Historical aside:
At a time the code in fanf.c was that of fanf.orig.c
@@ -165,7 +166,7 @@ source.
fanftmp2.c C program. Take a look at that final C program again,
can you begin to understand what it is doing?
Look at the first stage of the C pre-processing which was done like:
-
cc fanf.c -E > fanftmp1.c
+
cc fanf.c -E > fanftmp1.c
Skip to the bottom of fanftmp1.c (after all of the C pre-processor header
stuff … look for a line of the form: # 38 "fanf.c" near the bottom)
and look at the resulting code. This code, when C pre-processed
@@ -451,10 +452,10 @@ International Logic Programming Symposium, 1995.
./schnitzi n > sort.c
make sort
./sort
# enter three numbers, space separated
@@ -155,10 +156,10 @@ Location: ZZ - Unknown location
where n and x, y and z are numbers.
Try:
-
./try.sh
+
./try.sh
What happens if at the command line you don’t specify n numbers that the
program expects? For instance try:
-
./schnitzi 5 > sort.c
+
./schnitzi 5 > sort.c
make sort
# try running the next command four or five times:
@@ -201,13 +202,13 @@ memory capacity, since the function call stack never goes beyond
a depth of one.
So what does it do? Give it an integer (1 < n < 27) on the command
line, such as
-
./schnitzi 5
+
./schnitzi 5
The output will itself be a lipographic program, one which expects input of
(in this case) five numbers and prints them out sorted. It sorts
them, however, using only if/else statements, without arrays or
looping. To see the resulting program run, redirect the output from
schnitzi into another file, like this
-
./schnitzi 4 > sort.c
+
./schnitzi 4 > sort.c
and then compile it.
Spoilers And Hints:
The big key to this program is figuring out what the names of the
@@ -243,10 +244,10 @@ other functions all the time. Or, almost all the time.
@@ -141,13 +142,13 @@ Location: DE - Federal Republic of Germ
To build:
-
make all
+
make all
There is an alternate version of this entry that will work with macOS. See the
Alternate code section below. We recommend you look at it
even if you don’t have a Mac, unless you want to figure it out yourself, as it
includes some interesting details about the entry.
@@ -220,7 +221,7 @@ macros are explicitly enumerated. In a compliant implementation no other
macros can be defined, because you could write strictly conforming
programs that may fail to compile due to syntax errors: supposing that
<stdio.h> defines PIPE_BUF, then the conforming
-
#include <assert.h>
+
#include <assert.h>
#include <stdio.h> /* <- or where the bogus macro is defined */
#include <string.h>
#define STR(x) #x
@@ -243,12 +244,12 @@ C compilers.
must resemble one of the canonical forms, "foo.h" or <bar.h>.
This lets us write things like
-
#define HEADER "foo.h"
+
#define HEADER "foo.h"
#include HEADER
I could not find a compiler rejecting this. However, if we’re
torturing the preprocessor a little more, by using token pasting,
at least one compiler falls over.
-
#define H(x) <st##x##.h>
+
#define H(x) <st##x##.h>
#include H(dio) /* expands to <stdio.h> */
is rejected by tcc version 4.1.2, the TenDRA compiler:
"t.c", line 3: Error:\ [ISO 6.8.3.3]: Invalid result for '##' operator in macro 'H'.
@@ -264,7 +265,7 @@ allows: in #line num "file" the "file" is an s-char-se
ISO 6.8.4. ISO 6.1.4 defines string literals as s-char-sequences,
which may include octal escape sequences. Let’s look at
-
#include <stdio.h>
+
#include <stdio.h>
#line 42 "foo\0bar"
int main (void) {
printf ("%s %d\n", __FILE__, (int)sizeof __FILE__);
@@ -283,7 +284,7 @@ ISO 6.6.4.2. Then make fun of the guru’s answer by waving case __LINE__:
under his/her nose. Easy money from a bet! Make sure your guru has
no chance to use Standardese weasel words as an escape: can I have
-
case <some_token>:
+
case <some_token>:
case <some_token>:
in the same switch? (Note that you need the [invisible] newline. You
can generously allow the additional constraint that no #undefs or
@@ -315,14 +316,14 @@ I could have used a lot more ^K and ^L probably undete
counter but decided to err on the side of safety. I use a perl
script to compute the character count according to the rules.
The advantages of an independent clean room approach…
I have tried, as suggested in the guidelines, to let the code look
like ordinary C code. Apart from a few long lines I think I left
the indentation like I would in RL. You should however not try to
@@ -364,10 +365,10 @@ That describes exactly my modest attempts…
@@ -138,7 +139,7 @@ a file was not found (this limitation was removed in both versions in 2023). see
However, as noted, macOS does not have /usr/include so this would never
work for macOS without some changes, described next. For macOS you will need the
command line tools installed which can be done like:
-
sudo xcode-select --install
+
sudo xcode-select --install
An important point is that the original version hard-coded gcc but just like
the entry, the alternate version has also removed this limitation despite gcc
existing (though it’s clang) in macOS.
Shortly below that you will see, as noted above, the numbers:
-
if ((H = fopen (__FILE__+43, 43+__FILE__)))
+
if ((H = fopen (__FILE__+43, 43+__FILE__)))
while ((fgets (L, (int)sizeof L, H)) != 0) {
I[strcspn (I, 45+__FILE__)] = O = 0;
The first number in the above C means the length starting from 0 up through the
diff --git a/1998/schweikh2/.entry.json b/1998/schweikh2/.entry.json
index dec7ff93b..89b78d5cd 100644
--- a/1998/schweikh2/.entry.json
+++ b/1998/schweikh2/.entry.json
@@ -43,7 +43,7 @@
},
{
"file_path" : "1998_schweikh2.tar.bz2",
- "inventory_order" : 100000,
+ "inventory_order" : 1415926535,
"OK_to_edit" : false,
"display_as" : "tbz2",
"display_via_github" : false,
diff --git a/1998/schweikh2/index.html b/1998/schweikh2/index.html
index 0d184e184..9f2f58e68 100644
--- a/1998/schweikh2/index.html
+++ b/1998/schweikh2/index.html
@@ -88,6 +88,7 @@
@@ -141,13 +142,13 @@ Location: DE - Federal Republic of Germ
To build:
-
make all
+
make all
To use:
-
./yarng
+
./yarng
or
-
./yarng integer_number
+
./yarng integer_number
Try:
-
./try.sh
+
./try.sh
./yarng
# watch what it does
@@ -160,24 +161,24 @@ results different? Why?
At the time of judging, some non-gcc compilers that were not fully ANSI standard
did not compile this entry correctly. Also at that time, some gcc and egcs
implementations ran into a problem when building the entry. Doing:
-
make schweikh2
+
make schweikh2
often produced an error of the form:
-
gcc -ansi schweikh2.alt.c -o schweikh2.alt
+
gcc -ansi schweikh2.alt.c -o schweikh2.alt
as: Error: cca00NzV.s, line 58: Missing " at end of string
"
as: Error: cca00NzV.s, line 58: malformed statement
*** Error code 1 (bu21)
because the line:
-
#line 10 ONE(O(1,1,2,6,0,6))
+
#line 10 ONE(O(1,1,2,6,0,6))
turned into the line:
-
# 9 "01\012"
+
# 9 "01\012"
(note, though, how that line is on line 11) which caused gcc to give to the
assembler the following two lines:
-
.stabs "schweikh2.c
+
.stabs "schweikh2.c
",132,0,0,Ltext1
and the lone " after the #.file line resulted in an assembly syntax error.
In some cases one had to compile using gcc -g:
-
make schweikh2 CFLAGS=-g
+
make schweikh2 CFLAGS=-g
to trigger this error.
With the proper text beyond the \012, it was even possible to have all kinds
of fun adding inline assembly via #line directives. :-)
@@ -191,7 +192,7 @@ for that matter :-) ).
you could have emailed the author for a free pat on the back (and maybe you
still can :-) ).
Because of this bug, the code was changed to be instead:
-
#line 10 "01\015"
+
#line 10 "01\015"
However in 2023 it was observed that it is gcc (at least some versions?) that
has a problem with the compilation of the modified program, giving an internal
compiler error:
@@ -223,7 +224,7 @@ bits may be specified by an argument and defaults either to UINT_MAXUINT_MAX+1 (most likely). Extra credit: why the
different values? How long would you need for an empirical test?
@@ -141,7 +142,7 @@ Location: DE - Federal Republic of Germ
To build:
-
make all
+
make all
The author stated:
In the remote event that the input has more than `8192` files with
the same size (on systems where `sizeof (char *) == 4`, or `4096` when
@@ -153,11 +154,11 @@ code below.
If dir is the directory (or a directory tree) where you keep
all your favorite pictures off the Internet or from
alt.binaries.pictures.*, do
-
find dir -type f -print | ./samefile
+
find dir -type f -print | ./samefile
Maybe you will not need to buy another 10 GB disk to store them. :-)
Try:
If you’re in this winning entry’s directory:
-
./try.sh
+
./try.sh
Notice that the tool finds some files that are duplicates.
Alternate code:
If you run into the problem that the author described (above) you can redefine
@@ -165,7 +166,7 @@ the size as described; this was done with the SZ macro defined in t
which if (in the code) is unset will be set to the default, 32767.
Alternate build:
If you wish to change the size to say, 55555:
-
make clobber SIZE=55555 alt
+
make clobber SIZE=55555 alt
or whatever you wish to redefine it to.
Judges’ remarks:
This program is not as smart as to detect identity of JPEG files with the same
@@ -181,13 +182,13 @@ Thank God the IEEE does not standardize a coding style…
What this program does
This is best explained in the man page. The troff source for this
man page can be found in the file samefile.1. To render try:
-
`man ./samefile.1
+
`man ./samefile.1
Otherwise:
SAMEFILE(1) User Manuals SAMEFILE(1)
NAME
samefile - find identical files
SYNOPSIS
-
./samefile
+
./samefile
DESCRIPTION
samefile reads a list of file names (one file name per
line) from stdin. For each file name pair with identical
@@ -219,7 +220,7 @@ the output for a group of identical files with different
inode numbers is also minimized. Suppose you have six
identical files of size 100 in an inode group consisting
of the three inodes with numbers 10, 20 and 30:
-
$ ls -i # output edited for readability:
+
$ ls -i # output edited for readability:
10 file1 20 file4 30 file6
10 file2 20 file5
10 file3
@@ -245,13 +246,13 @@ more than a couple dozen files of the same size.
EXAMPLES
For everybody:
What are the duplicates under my home directory?
-
find $HOME | ./samefile
+
find $HOME | ./samefile
For the sysadmin folks:
Report all duplicate files under /usr larger than 16k:
-
find /usr -size +16384c -a -type f | ./samefile
+
find /usr -size +16384c -a -type f | ./samefile
For the ftp and WWW admins:
How much space is wasted below our site’s /pub directory?
-
find /pub -type f | samefile | awk '{sum += $1} END {print sum}'
+
find /pub -type f | samefile | awk '{sum += $1} END {print sum}'
EXIT STATUS
If samefile runs out of memory the exit status is 1, zero
otherwise.
@@ -323,10 +324,10 @@ the same size (on systems where sizeof (char *) == 4, or 4096
filename : file to calculate the CRC of
bitwidth : width of the CRC in bits (decimal)
@@ -152,7 +153,7 @@ Location: ZZ - Unknown location
Try:
-
./try.sh
+
./try.sh
Judges’ remarks:
If you don’t believe the program is correct, try and compare the output
of the program with the value of CRCs computed by PKZIP or any other
@@ -169,13 +170,13 @@ archiver that uses the CRC-32 algorithm.
xor : value to xor the final CRC with (hexadecimal)
The program assumes CHAR_BIT==8. Results are undefined if bitwidth > sizeof(unsigned long) * 8. It is also assumed that EOF is -1 and 1 is a
valid exit value to indicate failure (replace them with EOF resp.
@@ -245,10 +246,10 @@ for writing this. You can find it in crc.txt.
This small program might be a nice addition to a digital personal
organizer; just in case you are stranded on a desert island and need to
@@ -229,10 +230,10 @@ source file.
@@ -141,9 +142,9 @@ Location: FR - French Republic (
To build:
-
make
+
make
To use:
-
./bellard
+
./bellard
Judges’ remarks:
This code is a nice compact example of a Modular Fast Fourier Transform. While
its output is very specific, the internal FFT has a wide variety of uses.
Compile with the maximum possible optimization on your system.
If your system has 80-bit internal representation of floating
@@ -184,9 +185,9 @@ output a compressed version to stdout. Feed it a compressed file
on stdin, and it will decompress it to stdout — as either raw or
ASCII .PGM, depending on what format it was compressed from. For
example:
-
./glicbawls < michael.pgm > michael.glic
+
./glicbawls < michael.pgm > michael.glic
and then
-
./glicbawls < michael.glic > michael.decoded.pgm
+
./glicbawls < michael.glic > michael.decoded.pgm
As it turns out, glicbawls compresses greyscale images (or, more
precisely, “natural” greyscale images) better than any other
program I am aware of (with the exception of the not-yet-published
@@ -199,7 +200,7 @@ have trouble recognizing the image, try squinting at it ;-).
If you still have trouble, simply use a terminal or xterm with
more than 80 columns, and tell glicbawls about it by giving the
number of columns as an argument. For example
-
./glicbawls 260 <lavabus.pgm >lavabus.glic
+
./glicbawls 260 <lavabus.pgm >lavabus.glic
will allow glicbawls to use up to 260 columns, which makes things
much more recognizable.
Still running out of space? Need to compress those images just a
@@ -212,13 +213,13 @@ error of 2 is allowed, an original pixel value of 37 could be
decoded as 35, 36, 37, 38 or 39. In order to use this mode, simply
give the maximum allowed error as an argument, with a dash (-)
before it. For example:
-
./glicbawls -2 < graph.pgm > graph.2.glic
+
./glicbawls -2 < graph.pgm > graph.2.glic
will compress in a way that allows decompression with a maximum
error of two. You can combine both types of arguments, i.e.:
-
./glicbawls -3 180 < graph.pgm >graph.3.glic
+
./glicbawls -3 180 < graph.pgm >graph.3.glic
will compress with a maximum error of 3, using a 180 column
terminal for the progress display, and:
But wait, there is more — you can also feed glicbawls .PPM files
(i.e. colour images), raw or ASCII, your choice. glicbawls will
@@ -421,10 +422,10 @@ guarantee decoding within the requested maximum error.michael.pgm - author’s Godchild and Nephew
@@ -141,11 +142,11 @@ Location: US - United States of America
To build:
-
make
+
make
To use:
-
./dhyang
+
./dhyang
Try:
-
./try.sh
+
./try.sh
Judges’ remarks:
A beautiful combination of solving several different problems, but
mostly, the single most impressive layout we’ve ever seen. Many
@@ -200,10 +201,10 @@ type (a source of compile warnings).
When this entry was submitted the rules of the IOCCC did not prohibit
the use of embedded language interpreters. The judges considered
@@ -213,7 +214,7 @@ or EOF is encountered.
the results of an operation are really huge (> 10^308)
This bug appears to be fixed in perl5.6.0
Examples:
-
$ echo '12 13 14 15 16 + + + + f' | ./dlowe
+
$ echo '12 13 14 15 16 + + + + f' | ./dlowe
70
$ echo '12 13 14 15 16 17 + - * / p' | ./dlowe
-0.0515873015873016
@@ -365,10 +366,10 @@ DEC Tru64 5.0+, again according to the Perl people.
@@ -144,13 +145,13 @@ Location: FI - Republic of Finland
To build:
-
make
+
make
You will need X11 header files and libraries installed to build this program.
To use:
-
./jarijyrki < infile.info > outfile.info
+
./jarijyrki < infile.info > outfile.info
You will need a system capable of displaying the results of X Window programs.
Try:
-
./jarijyrki < finance.sheet > myedits.info
+
./jarijyrki < finance.sheet > myedits.info
Then click on cell C3 and type in the following:
C5 C6 C7 @
Click on cell D4 and type in the following:
@@ -190,7 +191,7 @@ supports are:
2. USAGE INSTRUCTIONS
2.1. Quick Guide
Starting
-
./jarijyrki < finance.sheet > myedits.info
+
./jarijyrki < finance.sheet > myedits.info
Stopping
Use the ESC key.
Movement
@@ -214,14 +215,14 @@ character at the end of the formula; press backspace to delete the last one.
To start the spreadsheet program with an existing
spreadsheet, for instance finance.sheet, use the following
command line:
-
./jarijyrki < finance.sheet
+
./jarijyrki < finance.sheet
The file finance.sheet has been provided as an example. This
file contains a set of financial numbers and two graphical entities - a pie
chart and a histogram - based on them. We recommend starting the use of the
program from this file, as a way to study and learn the formula language
supported by the program.
To start the program with an empty sheet, use
-
./jarijyrki < /dev/null
+
./jarijyrki < /dev/null
Alternatively, /dev/zero could be used but that may not exist on all systems.
2.3. Exiting and Saving Spreadsheets
Normally the user obviously wants to edit the spreadsheet. After the
@@ -229,7 +230,7 @@ spreadsheet program finishes, it outputs the edited spreadsheet to the standard
output. Hence, when the spreadsheet window has come up, you’ve made your
changes, and you press the ESC key the program finishes. To save the results in
a file, the following typical command line would be used:
-
./jarijyrki < finance.sheet > myedits.info
+
./jarijyrki < finance.sheet > myedits.info
2.4. Visual Overview
On top of the window the Formula Area shows the formula (or text) of the
currently selected cell. The program starts with A1 as being the current cell.
@@ -418,10 +419,10 @@ currently.
An alt version exists for those in the southern hemisphere (or those who want to
see what it would be in the southern hemisphere). See alternate
version below.
To use:
-
./natori
+
./natori
Try:
-
./try.sh
+
./try.sh
Try running this on different days, say a few days apart (even better if the
Moon phase changes), and each time run it several times in a row (or several
times in a day).
@@ -160,9 +161,9 @@ input or else just by the code itself. Bonus points if you can make it show all.
acos(l/2) into acos(-l/2) which we have done in the alternate version.
Alternate build:
To run the alternate code that supports the southern hemisphere:
-
make alt
+
make alt
Alternate use:
-
./natori.alt
+
./natori.alt
Try running this on different days, say a few days apart, and each time run it
several times in a row (or several times in a day).
What happens if you run it in the northern hemisphere? Are there any
@@ -170,7 +171,7 @@ differences?
Can you identify any Moon phases that result in the same output of both
versions? Or are there any?
Alternate try:
-
./try.alt.sh
+
./try.alt.sh
Like with try.sh, try using this multiple times in a row or throughout
the day on different days (if different phases of the Moon you’ll see more of a
difference, of course).
Don’t read the author remarks until you’re ready for the spoiler.
Just stop and read the program; it won’t take long. Once you’ve figured
@@ -174,7 +175,7 @@ syntax “mistakes” (e.g. LessThanOrEqualTo) and blatant “erro
Instead, the program reads input from stdin and returns garbled text on
stdout. Fortunately, you can recover the original message simply by
running the program a second time. Try:
-
./primenum n < textfile | ./primenum n > textfile2
+
./primenum n < textfile | ./primenum n > textfile2
diff textfile textfile2
where n is the same number (modulo 64). So, the prime number generator
is actually a simple text encoder/decoder! Of course, don’t forget that
@@ -231,10 +232,10 @@ number front. But ye be warned: “not a11 variab1es1es are identica1” :-)
If DISPLAY is not set the program will very likely crash or do something
different.
Try:
-
./try.sh
+
./try.sh
This will run the program several times with different parameters to show
different types of things. See the author’s remarks for more details.
Judges’ remarks:
@@ -162,7 +163,7 @@ observation.
Author’s remarks:
How to use it
The simplest way to run it is with no arguments. Just type:
-
./rince
+
./rince
You will need to have access to X windows, although it doesn’t require
desperately high resolution and there are no known limitations on colour
depth.
@@ -171,11 +172,11 @@ or more to be visible. For those that cannot wait that long the program
has a built in time machine. Indeed the program knows the speed of light,
which is used to ensure that we see the “live” pictures. Simply specify
the fraction of a day to skip forward for each screen refresh. I suggest:
-
./rince 0.01
+
./rince 0.01
To display the output (still guessing?) for a given date, specify two
arguments. The first argument is as before and the second argument is a
Julian day number (given as a fractional component). E.g.:
-
./rince 0 2441193.6
+
./rince 0 2441193.6
./rince 0.01 2441193.6
A Julian day is defined to be the number of days since January 1st in the year
-4712 (4713BC), starting at 12 noon GMT.12 To aid conversion from our time
@@ -248,12 +249,12 @@ states the following:
Here he could see for himself that somehow, a planet could
orbit the sun, and not leave a moon behind!
Thus we can plot Galileo’s discoveries using the following three plots:
However we can go one better by seeing what Galileo would have seen if it
wasn’t cloudy on the 9th. Try:
-
./rince 0 $(./dmy2jd 9.85 1 1610)
+
./rince 0 $(./dmy2jd 9.85 1 1610)
to see what he was missing out on. I wonder what he’d have made of that!
Galileo discovered the fourth moon a few days later.
I’ve tried typing these dates into two Java based Jovian moon plotters,
@@ -415,10 +416,10 @@ Jean Meeus. Published by Willmann-Bell Inc.rince.orig.c - original source
@@ -141,9 +142,9 @@ Location: US - United States of America
To build:
-
make
+
make
To use:
-
./robison
+
./robison
Judges’ remarks:
The program plays almost always reasonably, but does not always detect
illegal moves. Try “9 1” as your first move, then “13 2”. Also it
@@ -290,10 +291,10 @@ them, in lg(N) time, depending upon a parameter.
If you have a long while to spare (and you’re bored enough that you could watch
paint dry :-) ) you might also try:
-
./try.sh
+
./try.sh
Alternatively, you can check on it later on, to see all the entry does. Or if
you wish to make it run faster, you can override how long it sleeps per
iterations and how many iterations it runs. For instance to make it sleep only
30 seconds and run only twice:
-
SLEEP=30 ITERATIONS=2 ./try.sh
+
SLEEP=30 ITERATIONS=2 ./try.sh
Judges’ remarks:
Very nice play by the rules and portable text obfuscation.
This far surpasses old tricks like adding or subtracting 1
@@ -229,10 +230,10 @@ in a normal 3270 environment.
looked like back in 2000 (with a configurable speed). See the
original code section for the original entry.
To use:
-
./thadgavin.alt
+
./thadgavin.alt
You can press ‘q’ at any time to exit.
Try:
If you have SDL1 installed:
-
./thadgavin_sdl
+
./thadgavin_sdl
Whereas the curses version has an early exit the SDL version does not. You will
have to kill it yourself.
You might also wish to reconfigure the speed at which the programs run. The code
@@ -167,9 +168,9 @@ redefine the values: SLEEP is how long the program sleeps (in micro
between output with curses and SDL_SLEEP is how long it sleeps (also in
microseconds) for the SDL version.
To change the SDL one to something like 15000 you can do:
-
make SDL_SLEEP=15000 clobber alt
+
make SDL_SLEEP=15000 clobber alt
and to change the curses one to 40:
-
make SLEEP=40 clobber alt
+
make SLEEP=40 clobber alt
Then use the program(s) in the same way.
The different macros is because the curses version is already much slower and so
it’s better to not tie the two values together. You may of course redefine both
@@ -184,12 +185,12 @@ typically ctrl-c) as the program does not call endwin(). Using
Original build:
-
make all
+
make all
Original use:
-
./thadgavin
+
./thadgavin
Original try:
If you have SDL1 installed:
-
./thadgavin_sdl
+
./thadgavin_sdl
Judges’ remarks:
This entry is a nice play by the rules. It can use curses, if the
SDL graphic library is not present, and is quite good at that,
@@ -198,11 +199,11 @@ less than dazzling. We could not test this entry in DOS mode.
This alternate code is based on the author’s remarks with a slight fix so that
it will do what it once did, compile and run mkentry.c. You can use
it in a similar way as tomx.c, both executing the source file and
using it as a Makefile and running the code ends up running mkentry.
Alternate build:
-
make alt
+
make alt
Alternate try:
-
./try.alt.sh
+
./try.alt.sh
Judges’ remarks:
Polyglots have come and gone, but this was the first one we’d seen
where one language used another to perform its tasks. An interesting
@@ -249,10 +250,10 @@ or converting tabs to spaces can be disastrous.
@@ -141,7 +142,7 @@ Location: GB - United Kingdom of Great
To build:
-
make
+
make
The programs that this program is supposed to act on,
anonymous.ten.c and anonymous.bed.c,
compiled with make, MUST be compiled as 32-bit ELF binaries. In the case that
@@ -155,9 +156,9 @@ whatever your system will compile them as).
./try.sh
./anonymous anonymous.bed # if able to compile as a 32-bit (-m32) ELF binary
NOTE: if the 32-bit version cannot be compiled the script will at least compile
@@ -176,9 +177,9 @@ program or do something terribly wrong like slaughtering all the
Imladris! :-) so please don’t do
that :-(
Alternate build:
-
make alt
+
make alt
Alternate use:
-
./anonymous.ten.alt
+
./anonymous.ten.alt
./anonymous.bed.alt
A 2023 note about the warning from the author:
@@ -327,10 +328,10 @@ just C programs that generate C code as their output.
@@ -161,7 +162,7 @@ compilable by a standard ANSI C compiler. OTCC compiles,
assembles, links and runs C code without the need of any other
program.
You can use it by typing:
-
./bellard bellard.c [args]...
+
./bellard bellard.c [args]...
or by giving the C source to its standard input.
args are given to the main() function of bellard.c (argv[0] is
bellard.c).
@@ -169,15 +170,15 @@ program.
Sample compilation and execution:
-
./bellard bellard.otccex.c 10
+
./bellard bellard.otccex.c 10
Self compilation:
-
./bellard bellard.c bellard.otccex.c 10
+
./bellard bellard.c bellard.otccex.c 10
Self compilation iterated…
-
./bellard bellard.c bellard.c bellard.otccex.c 10
+
./bellard bellard.c bellard.c bellard.otccex.c 10
An alternate syntax is to use it as a script interpreter: you can
put #!/usr/local/bin/otcc at the beginning of your C source if
you installed otcc at this place.
@@ -271,10 +272,10 @@ be used when you compile and link it.
@@ -141,11 +142,11 @@ Location: US - United States of America
To build:
-
make
+
make
To use:
-
./cheong digits
+
./cheong digits
Try:
-
./try.sh
+
./try.sh
Judges’ remarks:
Be sure to give an even number of digits in the argument. Add a
leading 0 if needed.
@@ -156,7 +157,7 @@ as all good programs should be! :-)
Compile normally and run with one argument, an integer with 2n digits.
Program will return the integer part of its square root (n-digits).
For example,
-
$ cc -o cheong cheong.c
+
$ cc -o cheong cheong.c
$ ./cheong 1234567890
35136
$ ./cheong 0200000000000000000000000000
@@ -165,7 +166,7 @@ For example,
Portability
This program runs normally on any ANSI C compiler and is ASCII dependent.
Strict compiling gives just one unavoidable warning:
-
gcc -ansi -Wall cheong.c
+
gcc -ansi -Wall cheong.c
cheong.c:3: warning: third argument of `main' should probably be `char **'
Obfuscation
The main obfuscation is the algorithm used to calculate square roots,
@@ -225,10 +226,10 @@ the program.
You may need to run this a few times to understand exactly what is
being said. You might even need to look somewhere on your desktop,
@@ -170,7 +171,7 @@ fixed-format audio interface that is supported by the majority of Unices
that can do sound, as a lowest-denominator sound I/O interface.
Program usage
To listen to what the program says directly, invoke
-
./coupard > /dev/audio
+
./coupard > /dev/audio
The program then speaks out something like
The time is HH hours MM minutes SS seconds
@@ -181,7 +182,7 @@ the speakers connected … :-)
If you want to convert the audio output of the program into another audio
format, you can pipe it to SoX for example
(sox is the Swiss army knife of Unix audio tools). The command:
The author provided a way to speed it up a bit and also how to make it so it
doesn’t crash on losing. The idea that it crashes on losing was too good to
lose but this alternate version has the former change. If you wish to remove
this you can look at the author’s remarks and make the change.
Alternate build:
-
make alt
+
make alt
Alternate use:
-
./dgbeards.alt
+
./dgbeards.alt
Try:
See if you can figure out how to make the computer always lose (‘win’ :-) ).
It’s a very simple thing to do. Read the author’s remarks for clues.
@@ -346,10 +347,10 @@ the > to a >= and the bug will be gone.
NOTE: this entry seems to rely on older versions of gcc for the compilation
stage and as such if you wish to see that part like it was designed you will
need an older compiler perhaps gcc 2.95.
Try:
-
./try.sh
+
./try.sh
Judges’ remarks:
There are some clear hints in the source code as to the
purpose of this program. Perhaps the only way to figure out what is
@@ -192,7 +193,7 @@ terminal!
For the impatient
The info files herrmann1.turing and herrmann1.gcd are sample
programs for the Turing machine. For example, type
-
./herrmann1.sh 'prg=herrmann1.times2'
+
./herrmann1.sh 'prg=herrmann1.times2'
and watch the animated Turing machine multiply 8 by two (in
unary representation). Here’s a screen shot during compilation:
/*
@@ -217,7 +218,7 @@ result.)
In the previous example, the Turing machine started on the default
tape of the program times2.turing. To provide your own tape, type
(for example)
-
./herrmann1 prg=times2.turing tape="O O O I I I O O O"
+
./herrmann1 prg=times2.turing tape="O O O I I I O O O"
(The Os and Is are letters, not digits.) You might prefer to
provide only a finite portion of the tape, like I did above. In
this case, the remainder of the tape is filled with Os. ;-)
@@ -234,7 +235,7 @@ better. Simply try some out.
number in unary representation. (That is, a row of I’s is
expected, and one more I is appended to the row.) Let’s call it
plus1.turing. Here’s what it could look like:
-
/* Search beginning of number. */
+
/* Search beginning of number. */
#define start_O O, right, start
/* Number found. Move one step to the left. */
#define start_I I, left, st2
@@ -251,21 +252,21 @@ line defining st2_I has been left out.)
- The order of the lines is irrelevant.
- You may use C-style comments. (Would you have guessed it?)
Now, the program can be used with
-
./herrmann1.sh 'prg=plus1.turing' 'tape="I I I"'
+
./herrmann1.sh 'prg=plus1.turing' 'tape="I I I"'
But what happens if no tape is provided? Up to now, the Turing
machine would start on an empty tape (that is, a tape filled with
Os). For many programs, this doesn’t make much sense (as is
the case for plus1.turing). So you might want to provide a
default tape by adding a line like
-
#define tape O O O O O I I I I
+
#define tape O O O O O I I I I
to your program.
Debugging
When writing long programs, the most common errors are to forget
to define a state or to misspell one. Let’s assume you forgot the
line
@@ -141,11 +142,11 @@ Location: DE - Federal Republic of Germ
To build:
-
make
+
make
To use:
-
./herrmann2
+
./herrmann2
Try:
-
./try.sh
+
./try.sh
If you use vi(m) you can see a pattern in herrmann2.cup and
[herrmann2.ioccc][(herrmann2.ioccc]) by say:
/[pon]\
@@ -177,7 +178,7 @@ to about 9k.
3D picture, constructed of random characters (with ASCII code between
32 and 126). For example, type
-
./herrmann2 < herrmann2.ioccc
+
./herrmann2 < herrmann2.ioccc
If you want to control the characters used in the output (for
example if your picture is to consist only of digits), pass them
@@ -186,7 +187,7 @@ new random character, it will take the next one from the
argument. When it arrives at the end of the argument, it will
start over at the beginning. Example:
@@ -216,7 +217,7 @@ get it (if you lost it or if you don’t have it already) is to use
the program itself on the right picture and with the right
argument:
-
./herrmann2 \
+
./herrmann2 \
'char*d,A[9876];e;b;*ad,a,c; tw,ndr,T; wri; ;*h; _,ar ;on;'\
' ;l ;i(V)man,n {-!har ; =Aadre(0,&e,o||n -- +,o4,=9,l=b=8,'\
'!( te-*Aim)|(0~l),srand (l),,!A,d=,b))&&+((A + te-A(&(*)=+ +95>'\
@@ -267,7 +268,7 @@ only needs a logarithmic recursion depth! (Find out how this
works.)
When still in doubt about how to judge this program, type
./kev # in one terminal
./kev hostname # in another terminal
NOTE: each player’s paddle is at the bottom and the opponent at the top.
Try:
-
./kev # in one terminal
+
./kev # in one terminal
./kev localhost # in another terminal on the same host
If you need to change the speed you can reconfigure it like (say
for over a network and not the same host):
-
make clobber SPEED=50 all # original default value which is very fast
+
make clobber SPEED=50 all # original default value which is very fast
If you wish to change the port you can do so like:
-
make clobber PORT=3773 all
+
make clobber PORT=3773 all
Of course if you want a port < 1024 you’ll need to be root so don’t do that.
And if you know what you’re doing you can redefine the call to the socket(2)
syscall with the l_ macro, changing the L variable like one would PORT. Of
course you can do more than one at the same time. For instance to change the
speed and port:
-
make clobber SPEED=512 PORT=3773 all
+
make clobber SPEED=512 PORT=3773 all
If you have xterm try on one system:
-
xterm -geometry 80x40 -fg green -bg black -fn 9x15bold -e ./kev &
+
xterm -geometry 80x40 -fg green -bg black -fn 9x15bold -e ./kev &
and then the other, the client system:
-
xterm -geometry 80x40 -fg green -bg black -fn 9x15bold -e ./kev localhost&
+
xterm -geometry 80x40 -fg green -bg black -fn 9x15bold -e ./kev localhost&
This might look nicer than just the terminal itself.
Alternate code:
This version allows you to use arrow keys on the keyboard rather than the more
awkward , and . keys to move your paddle.
Alternate build:
-
make alt
+
make alt
You can reconfigure the macros described above in the same way.
Alternate use:
Use kev.alt as you would kev.
@@ -185,9 +186,9 @@ awkward , and . keys to move your paddle.
terminal?
Alternate try:
If you have xterm try on one system:
-
xterm -geometry 80x40 -fg green -bg black -fn 9x15bold -e ./kev.alt &
+
xterm -geometry 80x40 -fg green -bg black -fn 9x15bold -e ./kev.alt &
and then the other, the client system:
-
xterm -geometry 80x40 -fg green -bg black -fn 9x15bold -e ./kev.alt localhost&
+
xterm -geometry 80x40 -fg green -bg black -fn 9x15bold -e ./kev.alt localhost&
Judges’ remarks:
Continuing with this year’s “retro game” theme, this is another old game;
arguably, one of the oldest. Requires a functioning network, and curses.
@@ -212,16 +213,16 @@ speeds. Each player has a paddle to hit the ball, and you get points for
getting the ball past your opponent’s paddle. It’s pretty fun! :)
RUNNING
Run the server first without any command line arguments, i.e.
-
./kev
+
./kev
Then run the client with a single command line argument which is
the name of the machine running the server, e.g.
-
./kev localhost
+
./kev localhost
Make sure that the terminals on both ends are the same size. Also, the TCP port
number (by default 5455) specified in the Makefile mustn’t be
blocked by a firewall.
Here’s a good quick example to see it in action on your own
machine, assuming you have Xwindows:
-
xterm -geometry 80x40 -fg green -bg black -fn 9x15bold -e ./kev &
+
xterm -geometry 80x40 -fg green -bg black -fn 9x15bold -e ./kev &
xterm -geometry 80x40 -fg green -bg black -fn 9x15bold -e ./kev localhost&
PLAYING
Your paddle is the one at the bottom of the screen, your opponent
@@ -326,10 +327,10 @@ though.
WARNING: this will mess with your mouse and can make it hard to quit the
program. Use at your own risk.
NOTE: number is floating point.
Try:
-
./rosten 1.03
+
./rosten 1.03
./rosten 1.00
For some abuse, try:
-
./rosten 0.99
+
./rosten 0.99
Judges’ remarks:
Friction can be your friend if it does not rub you (or your mouse
cursor) in the wrong way. :-)
@@ -163,7 +164,7 @@ cursor) in the wrong way. :-)
NAME
rosten - make the mouse act as if it has been greased
SYNOPSIS
-
./rosten [greasiness]
+
./rosten [greasiness]
DESCRIPTION
This program is designed primarily to make your X windows interface more
obfuscated. Try doing something mouse driven (such as using a mouse
@@ -183,7 +184,7 @@ required is a large desk and some good grease.
portable, but compile with almost no warnings on most of the compilers
tested. It’s a kind of shame that none of the compilers do anything
like this:
-
$ make greasymouse
+
$ make greasymouse
cc greasymouse.c -o greasymouse -lX11
greasymouse.c:30: This macro should have more text and spaces in it
greasymouse.c:32: This is a really stupid way to perform this operation
@@ -213,7 +214,7 @@ would never do a thing like that: I just haven’t used them in
the way it’s used to.
The MIPS compiler suggests an == instead of an = in expressions
such as:
-
&&(a=b)
+
&&(a=b)
but its suggestions would break my program. It also reckons
that r() has no prototype.
Giving the -pedantic option to the MIPS compiler causes it to generate
@@ -251,10 +252,10 @@ beginning of the line wrecks the layout but makes it compile.
@@ -170,7 +171,7 @@ the whole string, so you may want to use * at the beginning and end
pattern if you are looking for something in the middle.
You can use it for your shell scripting needs similar to a silent grep
(and without stdout redirected to /dev/null):
-
if prog "${VARIABLE}" '<glob>'; then
+
if prog "${VARIABLE}" '<glob>'; then
echo VARIABLE matches
else
echo no match
@@ -229,10 +230,10 @@ try again. For extra credit implement character classes like [a-z].
./westley 2>/dev/null
# enter some input, terminate with EOF
echo foo | ./westley 2>/dev/null
./westley < westley.c 2>/dev/null
Try:
-
./try.sh
+
./try.sh
Sorted code:
The author stated that one can sort (ignoring leading blanks i.e. sort -b) the
code by line and it will always sort the order of the input.
@@ -171,12 +172,12 @@ code by line and it will always sort the order of the input.
westley.punch.c code is specifically so that Westley can punch
everyone in the face! :-) This is also compiled by default.
Punch card try:
-
echo 'Brian Westley does it again!' | ./westley.punch 2>/dev/null
+
echo 'Brian Westley does it again!' | ./westley.punch 2>/dev/null
Alternate code:
An alternate version of this entry, westley.alt.c, is provided.
This alternate code might be less portable.
Alternate build:
-
make alt
+
make alt
Alternate use:
Use westley.alt as you would westley above.
Judges’ remarks:
@@ -195,7 +196,7 @@ were becoming obsolete just as C was becoming more popular*; this is rather
unfortunate, because C has an advantage over many other languages when it comes
to punch cards - C programs can be written to be “drop proof”.
@@ -204,13 +205,13 @@ lines are in. If you punch it on cards (one line of code per
card, naturally) and drop them, you don’t need to put them in
any particular order**; it will always produce ABC as output.
It would be trivial to write an entire C program that is
“drop proof” using the above techniques; surprisingly, it’s
possible to write a program that will always compile but
behave differently depending on the line order:
This program will print out T if the #define statement
@@ -218,7 +219,7 @@ falls between the declaration of test() and its use in
main(), otherwise it will print out F. Furthermore,
you can use the same call to test() repeatedly in
different lines to return different values:
@@ -141,9 +142,9 @@ Location: SG - Republic of Singapore
To build:
-
make
+
make
To use:
-
./anonymous 'foo' > bar.pgm
+
./anonymous 'foo' > bar.pgm
Now open the output using your favourite
pgm viewer. If you don’t
have a pgm viewer then we suggest the netpbm
@@ -151,7 +152,7 @@ toolkit to convert the image to a graphics
format that you can view. Most graphical web browsers can display PNG or JPEG
images.
Try:
-
./try.sh
+
./try.sh
NOTE: technically the text is supposed to be in all lower case but the script
does use some upper case letters for demonstration purposes.
Judges’ remarks:
@@ -220,7 +221,7 @@ in lower case.
The following command thus writes a rendering of the Ring
inscription to
the file ring.pgm:
The source code assumes the ASCII character set; also, due to space
constraints, the program uses rather inefficient algorithms, so it may
@@ -258,10 +259,10 @@ included in the font.
There is an alt version for rogue players, vi(m) users and Dvorak typist (i.e.
those who need hljk for moving left, right, down and up. See alternate
code below.
To use:
-
./arachnid [mazefile]
+
./arachnid [mazefile]
Try:
-
./arachnid arachnid.txt
+
./arachnid arachnid.txt
and then try:
-
./arachnid arachnid.c
+
./arachnid arachnid.c
Navigation is through the use of the wasd inverted-T formation on
QWERTY keyboards. Rogue players, vi users, and Dvorak typists are
invited to get lost (or use the alt version)!
@@ -158,7 +159,7 @@ invited to get lost (or use the alt version)!
If you don’t like the wasd movement keys you can try the vi(m) movement keys
instead.
Alternate build:
-
make alt
+
make alt
Alternate use:
Use arachnid.alt as you would arachnid above.
Judges’ remarks:
@@ -181,7 +182,7 @@ Another maze, arachnid.txt has also been provided. Th
255x255, about the largest maze supported, for the particularly insane maze
explorers out there.
Usage
-
./arachnid [mazefile]
+
./arachnid [mazefile]
You can explore the maze using the w,a,s, and d keys.
To build:
-
make
+
make
NOTE: We FORCE the use of -O0 even if someone overrides it because this entry
will not work with it enabled.
To use:
-
./burley
+
./burley
NOTE: you need to input a number first. See judges’ remarks below for
information on how to play.
Judges’ remarks:
@@ -213,10 +214,10 @@ statements such as if, for, do, whi
@@ -141,18 +142,18 @@ Location: SE - Kingdom of Sweden (
To build:
-
make
+
make
There are three alternate versions; see alternate code below
for more details.
To use:
-
./gavare > ioccc_ray.ppm
+
./gavare > ioccc_ray.ppm
Open ioccc_ray.ppm with a viewer capable of viewing PPM files. Alternatively,
if you have ImageMagick installed, you can convert it to a jpeg:
-
convert ioccc_ray.ppm ioccc_ray.jpg
+
convert ioccc_ray.ppm ioccc_ray.jpg
and then view ioccc_ray.jpg in a graphics viewer, editor or web browser.
Try:
If you have xv(1) you can do:
-
./gavare | xv -
+
./gavare | xv -
to not worry about writing it to a file and just viewing the image it creates.
Alternate code:
The alt code gavare.alt.c allows you to change the size of the
@@ -165,18 +166,18 @@ was used during development, which we have included in the file
on stdout which theoretically should work in Windows.
Alternate build:
To build the configurable and unobfuscated versions:
-
make alt
+
make alt
To change the default size from 1024x768 try:
-
make clobber XX=640 YY=480 alt
+
make clobber XX=640 YY=480 alt
You might also wish to change the anti-alias setting:
-
make clobber AA=2 alt
+
make clobber AA=2 alt
You may of course combine the above two commands and give any combination you
wish.
This is not possible with the author’s version but it is with the alt versions
(Windows - see below - and otherwise).
As the Windows version will not compile on most viewers’ systems we do not build
it with make alt; instead try:
-
make alt2
+
make alt2
Alternate use:
Use gavare.alt, gavare.r3 or gavare.alt2 as you would gavare above.
Judges’ remarks:
@@ -247,10 +248,10 @@ with no reserved words, and our world will be a better place.
There is an alternate version for those who wish to use QEMU rather than having
to reboot and rely on having a floppy drive (if you even remember what those are
:-) ) etc. See alternate code below.
@@ -152,31 +153,31 @@ to reboot and rely on having a floppy drive (if you even remember what those are
STATUS: INABIAF - please **DO NOT** fix
To enjoy the results (on a Linux/x86 machine) with a floppy drive (remember
those? We do!):
-
su
+
su
Make a floppy with an ext2 filesystem (mke2fs /dev/fd0 replacing fd0 with
whatever the floppy device is!), mount it under /mnt/floppy and then:
-
cp kernel fs.tar lilo.conf boot.b /mnt/floppy
+
cp kernel fs.tar lilo.conf boot.b /mnt/floppy
NOTE: If the version of your lilo is not 21.4, use the appropriate boot.b file.
NOTE: If your floppy drive is not /dev/fd0, edit lilo.conf appropriately.
-
lilo -C /mnt/floppy/lilo.conf
+
lilo -C /mnt/floppy/lilo.conf
Boot from the floppy on an x86 machine with a PS/2 keyboard and mouse.
Move the window away from the corner.
-
vi gavin.c
+
vi gavin.c
Scroll up and down the file with up-arrow and down-arrow.
-
sh
+
sh
You can have several shell windows:
-
vi README.md
+
vi README.md
./prim
Press and hold any key.
Alternate code:
This version’s main difference is that the macro K is redefined to 1 so that
you can use it with QEMU.
Alternate build:
-
make alt
+
make alt
Alternate use:
The use is mostly the same as gavin except that one initially executes gavin.alt
(which make alt will do) and one will have to use QEMU instead. The files
@@ -290,10 +291,10 @@ at which a Linux bootloader loads an x86 kernel image).
Then use your web browser to visit http://localhost:8008/. When you’re
finished make sure to kill hibachi.
NOTE: you must be in the build directory when running hibachi-start.sh for
@@ -163,7 +164,7 @@ so the file does not exist here.
There is a hibachi.tgz file (NOTE: this file was removed by the judges after
extraction) that unpacks several support files and a subdirectory tree
containing the documentation and examples. It can be viewed by:
-
tar -zxf hibachi.tgz
+
tar -zxf hibachi.tgz
lynx hibachi/localhost/index.html
Or once Hibachi is running, use a web browser (preferably one that
supports images and JavaScript, to view the documentation and try
@@ -171,11 +172,11 @@ some of the CGI examples) to visit: http://localhost:8008/.
Building
To build just the executable:
For Cygwin, FreeBSD, Linux (newer), Mac OS X:
-
gcc -o hibachi hibachi.c
+
gcc -o hibachi hibachi.c
For Linux (older):
-
gcc -DSHUT_WR=1 -o hibachi hibachi.c
+
gcc -DSHUT_WR=1 -o hibachi hibachi.c
For SunOS:
-
gcc -o hibachi hibachi.c -lnsl -lsocket
+
gcc -o hibachi hibachi.c -lnsl -lsocket
Since some systems place socket and network functions into other libraries, a
GNU autoconfconfigure script has been
@@ -185,12 +186,12 @@ examples. In which case the preferred build commands are:
./configure [--enable-port=number]
make
To start the server on the default port (8008):
-
cd build;
+
cd build;
./hibachi-start.sh &
To test the server:
-
lynx http://localhost:8008/
+
lynx http://localhost:8008/
To stop the server:
-
kill %1
+
kill %1
Features
Supports virtual hosts.
@@ -282,10 +283,10 @@ paragraph 3 sentence 2, and so fails to display responses from
@@ -141,11 +142,11 @@ Location: US - United States of America
To build:
-
make
+
make
To use:
-
./hoyle point ...
+
./hoyle point ...
Try:
-
./try.sh
+
./try.sh
Judges’ remarks:
The obfuscation functions at several levels. Note the clever
use of use of #defines. The #define do(if,else), for example,
@@ -167,9 +168,9 @@ passed in.
dashes rather than a simple block of Xs.
For example, to graph y = x^2:
-
./hoyle 0 0 1
+
./hoyle 0 0 1
Note that:
-
./hoyle 0 0 2
+
./hoyle 0 0 2
will produce the same graph, since the y-axis is auto scaling.
To build:
-
make
+
make
There is an alternate version that allows one to control the number of numbers
to print on a line. See alternate code below.
Bugs and (Mis)features:
@@ -149,27 +150,27 @@ to print on a line. See alternate code below.
This version lets you control how many numbers to show on a line before adding a
newline as it can be harder to see when there are a lot of numbers. For lines
that don’t end up having too many line breaks it also makes it easier to see
which line it is on.
Alternate build:
-
make alt
+
make alt
The macro Ag (silver) controls how
many number of lines to print on a line. Set at default to 11 protons, salt, if
you wish to make it silver, 47 (a prime) protons, do:
-
make clobber Ag=47 alt
+
make clobber Ag=47 alt
though it might be odd to have 47 numbers on a line as it would defeat the
purpose. :-) Or if you prefer some prime, golden irony:
-
make clobber Ag=79 alt
+
make clobber Ag=79 alt
Alternate use:
Use jdalbec.alt as you would jdalbec above.
Alternate try:
-
./try.alt.sh
+
./try.alt.sh
Judges’ remarks:
We still aren’t sure whether or not this is a useful program, but
it’s the first atomic fission we’ve seen in the IOCCC.
@@ -325,10 +326,10 @@ type, a structure, a structure member, a macro parameter, and a variable.).
@@ -141,13 +142,13 @@ Location: PL - Republic of Poland
To build:
-
make
+
make
NOTE: We FORCE the use of -O0 even if someone overrides it because this entry
will not work with it enabled.
To use:
-
./kopczynski < input_file
+
./kopczynski < input_file
Try:
-
./try.sh
+
./try.sh
What happens if you feed the program source to the program? Can you figure out
why?
Alternate code:
@@ -155,9 +156,9 @@ why?
program returned the result as an exit code which is what the alternate version
does.
Alternate build:
-
make alt
+
make alt
Alternate try:
-
./kopczynski.alt < kopczynski-10
+
./kopczynski.alt < kopczynski-10
echo $?
Judges’ remarks:
What is in a line? A lot when you obfuscate the way Eryk Kopczynski
@@ -311,10 +312,10 @@ comes from this. For additional obfuscation and conciseness, if mea
@@ -141,9 +142,9 @@ Location: US - United States of America
To build:
-
make
+
make
To use:
-
./omoikane infile layout outfile
+
./omoikane infile layout outfile
Try:
./try.sh
Judges’ remarks:
@@ -161,7 +162,7 @@ Comments refer to it as such.
strange file names or package .SFVs with your files! Rinia will
insert a human-readable checksum string in the text itself! ^_^
Usage
-
./omoikane <infile> <layout> <outfile>
+
./omoikane <infile> <layout> <outfile>
All three arguments may reference the same file. All files is
assumed to be of ASCII character set.
NOTE: if you’re one of those who don’t know how to exit vi :-) don’t worry as
it will exit for you.
Judges’ remarks:
@@ -221,11 +222,11 @@ scene, the other a bit of scrolling text.
Redirect the output directly to vi, like this:
-
./schnitzi < input.dat | vi
+
./schnitzi < input.dat | vi
Redirect the output to a file, like this:
-
./schnitzi < input.dat > output.dat
+
./schnitzi < input.dat > output.dat
Then, open the output file, select the text, and copy it
to your system pasteboard/cut/selection buffer and paste
it into vi. The paste is NOT the vi paste command, but
@@ -267,10 +268,10 @@ royalties on this technique.
Why not use the program to hide another program in the program? It
must have seemed reasonable at the time.
@@ -174,19 +175,19 @@ provide a separate encoding program, you should not be surprised to
learn that I opted to steganographically hide the encoder inside the
decoder.
Try it out. Compile the program, then type
-
./sds < sds.c
+
./sds < sds.c
You should see the encoder program displayed. Now save it, like:
-
./sds < sds.c > encoder.c
+
./sds < sds.c > encoder.c
Then compile encoder.c. You now have the complete system ready.
The encoder expects to get a filename as an argument. This filename
is the name of the file containing the information to be hidden. It
expects the file in which to hide the information to be on the
standard input, and will output the results on the standard output.
You can use it like this (assuming you have a file called remarks):
C programs are mostly unaffected by adding steganographic content,
but it is possible in certain circumstances for whitespace to be
@@ -233,10 +234,10 @@ GNU C.
@@ -141,11 +142,11 @@ Location: US - United States of America
To build:
-
make
+
make
To use:
-
./vik1 [arg]
+
./vik1 [arg]
Try:
-
./vik1
+
./vik1
./vik1 a
@@ -184,7 +185,7 @@ glance at the feature list he provided below. Amazing!
Compile the source code and link X libraries if necessary.
The program takes three options which have to be typed in a specific
order as described below.
-
Usage: ./vik1 ['a']['d'][#]
+
Usage: ./vik1 ['a']['d'][#]
a - Advanced racing in a winter landscape
d - Racing in at night in the dark
@@ -256,10 +257,10 @@ low) are { 0, RED, GREEN, BLUE }.
@@ -141,9 +142,9 @@ Location: US - United States of America
To build:
-
make
+
make
To use:
-
./vik2
+
./vik2
Judges’ remarks:
The fun thing about CPP abuses
is that, in most cases, running the
@@ -234,16 +235,16 @@ symbol must be defined to the name of the output file. If you want to
speed up the compilation, define the STOP symbol to anything from _3 to
_10. (The default value is _10 which will make the compilation take some
time.) Prime numbers up to 2^STOP will be calculated.
-
cpp '-DSTOP=_5' '-DFNAME="tmp1.c"' prog.c tmp1.c
+
cpp '-DSTOP=_5' '-DFNAME="tmp1.c"' prog.c tmp1.c
Then use cpp or any other
pre-processor to do the actual
work. This will take some time….
-
cpp tmp1.c > tmp2.c
+
cpp tmp1.c > tmp2.c
Finally compile the pre-processed file
-
cc -O tmp2.c -o prog
+
cc -O tmp2.c -o prog
Then run the program to reveal all prime numbers up to 32 (if you used
STOP=_5 as above):
-
./vik2
+
./vik2
Verification
I wasn’t able to compile the full program which calculates prime
numbers up to 1024 using GNU cpp
@@ -323,10 +324,10 @@ with 512Mb ram and a lot of disk.
@@ -141,25 +142,25 @@ Location: GB - United Kingdom of Great
To build:
-
make
+
make
There is an alternate version based on the author’s remarks. See alternate
code.
To use:
-
./aidan < puzzle
+
./aidan < puzzle
./aidan seed
where seed is a number.
Try:
-
./try.sh
+
./try.sh
Alternate code:
This code is formatted differently and is not the approach used by the author
which is slower, inelegant and not as obscure, as the author put it.
Alternate build:
-
make alt
+
make alt
Alternate use:
Use aidan.alt as you would aidan above.
Alternate try:
-
./try.alt.sh
+
./try.alt.sh
Judges’ remarks:
Are you puzzled about puzzles? This entry might puzzle you
more while it puzzles out some puzzles: all in a puzzling way!
@@ -223,7 +224,7 @@ figure out how to solve them, but there’s a useful tutorial on
http://www.sudoku.org.uk/, which is roughly affiliated with the Daily
Telegraph, a UK newspaper.
Now, with modern computers this can be solved using brute force, e.g.:
-
#include <stdio.h> /* sudoku-bfi.c */
+
#include <stdio.h> /* sudoku-bfi.c */
#define S(t) for(n=0;n<9;v[n++]=0);for(n=0;n<81;n++)if(i[n]){z=1<<i[n];if(v[t]\\
&z)for(;;){if(p<0)goto d;if(i[p]++<9)goto f;i[p]=0;p=s[p];}v[t]|=z;}
int i[82],s[81],v[9],n,p,z;int main(void){for(n=0;n<81;){p=getchar()^48;if(p==
@@ -259,17 +260,17 @@ also has trouble - it took 66 seconds to solve it - but probably for different
reasons. That’s the worst performance I’ve had from brute-force so far!)
Note that this requires Perl 5 (I use 5.8.5, earlier versions untested) and is
somewhat slow (should take under a minute on a fairly modern PC - try
appending -n 0 if you’re in a hurry). I wrote it mostly for my own benefit,
really.
Solving
-
./aidan < somefile.txt
+
./aidan < somefile.txt
Input should be the numbers of each row in turn. Empty spaces can be
represented as a full stop (.) or zero (0). Other characters are ignored, so you
can cut-and-paste either example sudoku puzzle from above into a file and feed that
@@ -282,7 +283,7 @@ an extra 15 bytes of (very simple) code to add, so it doesn’t really matter to
me. (It’s the same as the normal mode for most input you’re likely to feed it,
though slightly slower. See if you can figure out what it does.)
Generating
-
./sudoku <seed>
+
./sudoku <seed>
Output is a blank grid, then the solution, then the problem. There’s no
control over the difficulty. Sorry. However, all generated sudokus should have
exactly one solution - if one doesn’t, that’s a bug.
@@ -321,7 +322,7 @@ can’t help you figure out where the mistake is, sadly.
Dependant on ASCII, requires that an int is at least 15 bits and a long at
least 32. (No, that isn’t a typo - I did say 15, not 16).
Also requires that cpp can properly handle something like:
-
#define foo(x,y) x y
+
#define foo(x,y) x y
foo(bar,)
Apparently, a few can’t (ANSI C specifically doesn’t require that this works,
though it usually does). Unfortunately, I didn’t discover this issue until too
@@ -397,10 +398,10 @@ that way somehow…
NOTE: there is an alternate version for vi(m) like movements. See alternate
version below. If your terminal has problems with the
stty(1) commands try:
-
make anon-no_stty
+
make anon-no_stty
This will compile anon.c as anon to not use stty(1).
After a very large number of moves this program will deliberately force itself
@@ -162,18 +163,18 @@ to destroy its runtime stack. This is the author’s way to prevent you from bei
frustrated (which might happen as it likes to create unsolvable puzzles just to
hook you) and spending too much time playing. :-)
If you want to see this in action you can easily do this:
-
yes 'please crash on me :-)' | ./anon 4 4
+
yes 'please crash on me :-)' | ./anon 4 4
What happens if you specify a larger board? For instance:
-
yes 'please crash on me :-)' | ./anon 10 10 10
+
yes 'please crash on me :-)' | ./anon 10 10 10
If you specify more than three args the program might also crash or do
something strange. This might also happen if you specify excessively large board
dimensions. Try 100 100 100 for instance and see what happens!
Alternate version:
The alternate version uses vi(m) like movement keys.
Alternate build:
-
make alt
+
make alt
To compile the version without stty(1):
-
make alt-no_stty
+
make alt-no_stty
Alternate use:
Use anon.alt as you would anon with the change in movements:
k | Move empty spot up
@@ -200,9 +201,9 @@ spaces on the board, and the goal is to rearrange them so that they appear
sorted in the order they appear on the screen.
The program takes 2 or 3 arguments, specifying the dimensions of the board.
For example, to play the original version of the Fifteen Puzzle:
-
./anon 4 4
+
./anon 4 4
To play with a 3D board, do something like this:
-
./anon 3 3 3
+
./anon 3 3 3
WARNING: do NOT run the program with more than 3 command-line arguments.
This will trigger a bug that will cause it to crash or do something strange.
:-)
@@ -394,7 +395,7 @@ allocation. It’s the only state that needs to return a value from the boolean
expression, since once the MASS is initialized any return value can simply be
stored in a well-known location in the MASS.
if(p,q,r,s) is, in fact, an if statement. :-) It is equivalent to:
-
if (p) { q; r } else {s}
+
if (p) { q; r } else {s}
Why are q and r split up? Because it’s cleaner (in whatever twisted sense of
the word that can be applied to an IOCCC entry) to implement using boolean
expressions. Keep in mind that all statements are assumed to evaluate to
@@ -415,11 +416,11 @@ closes the current state and opens a new one behind the programmer’s back.
i is the index variable (well, the index into the MASS of the index
variable); x and y-1 define the starting and ending values of i, and z
is the loop body. Z is the post-loop code in the current state. For example:
-
for(s,i, 0, 10,
+
for(s,i, 0, 10,
some_code ,
other_code)
is equivalent to:
-
for (i=0; i<10; i++) {
+
for (i=0; i<10; i++) {
some_code;
}
other_code;
It will also create an SVG file with the file input.txt.
The script will check if convert is available and if so it will try converting
the SVG file(s) to PNG file(s) which you should be able to view in most any
@@ -178,7 +179,7 @@ square.
This will possibly save a compressed SVG file and may be useful:
-
./boutines | gzip > result.svg.gz
+
./boutines | gzip > result.svg.gz
Input consists of a list of floating points values separated by whitespaces
(ranging preferably in [0,1]). Alternating a horizontal coordinate, a
whitespace then the other coordinate (pointing downwards in the resulting
@@ -292,10 +293,10 @@ viewport and potentially every
@@ -141,9 +142,9 @@ Location: SG - Republic of Singapore
To build:
-
make
+
make
To use:
-
./chia
+
./chia
Judges’ remarks:
Have you had your morning cup of Java? You might want a
second cup before parsing this entry. And give your C
@@ -201,10 +202,10 @@ when they see macro parameters that don’t look like C tokens.
@@ -145,9 +146,9 @@ Location: FI - Republic of Finland for information on how to install it if you
haven’t already.
If you have SDL installed:
-
make
+
make
To use:
-
./jetro
+
./jetro
Judges’ remarks:
We have seen entries with SDL graphics in the past, now it’s time for SDL
sound. This entry can even be run on a computer without a sound card with an
@@ -186,10 +187,10 @@ with one call to getchar() before it quits.
@@ -141,11 +142,11 @@ Location: US - United States of America
To build:
-
make
+
make
To use:
-
./klausler arg1 arg2 | head
+
./klausler arg1 arg2 | head
Try:
-
./try.sh
+
./try.sh
Judges’ remarks:
To reduce the size of the source, include other people’s data.
That is what Peter suggests when he describes how to generate
@@ -205,10 +206,10 @@ recursion, or other tricks. Enjoy!
NOTE: the author stated that they tested this under i386 machines but this works
under 64-bit (x86_64, arm64) machines too.
Try:
-
./try.sh
+
./try.sh
Judges’ remarks:
Having problems speaking code? Do you LISP? Parenthetically
speaking, this entry takes advantage of C99 features, while
@@ -175,12 +176,12 @@ constant string, due to different string escape semantics in C and Lisp, and
some implicit integer-to-pointer conversions due to the implicitly-declared
functions.
Try:
-
echo '(format t "~s" (+ 2 2 ))' | ./mikeash
+
echo '(format t "~s" (+ 2 2 ))' | ./mikeash
You should see 4" echoed on your command prompt. The " after the 4 and
the lack of a newline are due to the somewhat broken implementation of
the format function. More sophisticated arithmetic expressions may be
used:
This evaluates the expression (2+2) * (5 - 9/3) giving the correct result,
8" (with the same issue of no newline after the "). Note that due to the
highly ad-hoc nature of the tokenizer, the spaces before the closing parentheses
@@ -219,7 +220,7 @@ nowhere near
Basically, the LISP interpreter is good for some basic math operations, and
for running itself. To do the latter, try this:
@@ -171,11 +172,11 @@ to either come up with a pipeline (or some other command line) that allows it to
work with https or to update the code to support https they may. Otherwise you
must just appreciate the entry for what it once was.
Alternate build:
-
make alt
+
make alt
Alternate use:
Use mynx.alt as you would mynx. You’d have to specify a port at the end of
the URL like:
-
./mynx.alt https://www.ioccc.org:443
+
./mynx.alt https://www.ioccc.org:443
but again unless you have a clever workaround or hack to the problem, this sadly
won’t work.
Judges’ remarks:
@@ -188,16 +189,16 @@ get a functioning LAMP stack.
I was rather impressed by last year’s mini webserver. So much so that
it inspired me to try my hand at writing the client side complement.
A typical build command would be:
-
cc -o mynx mynx.c
+
cc -o mynx mynx.c
While some others like to be a little different:
-
cc -o mynx mynx.c -lnsl -lsocket
+
cc -o mynx mynx.c -lnsl -lsocket
I even managed to figure out a basic configure script, given last year’s
example, which is kinda of useful when you consider how many OSes put
all the network functions in a variety of places. So a simpler build
command sequence would be:
-
cd source ; ./configure ; make
+
cd source ; ./configure ; make
After which, the rest of the documentation can be read by saying:
-
./mynx ../manual.html
+
./mynx ../manual.html
To build:
-
make
+
make
There is an alternate version of this entry which should work for Windows by
setting binary mode on stdout. See alternate code below.
To use:
-
./persano p q [num frames]
+
./persano p q [num frames]
Try:
-
./try.sh
+
./try.sh
Open the GIF files with a viewer capable of
displaying animated GIFs and watch closely at the bottom of the picture (you may
need to use gifsicle - a great tool to
@@ -162,7 +163,7 @@ let it work with Windows.
Alternate use:
Use persano.alt as you would persano above.
Alternate try:
-
./persano.alt 3 16 > knot3-16.gif
+
./persano.alt 3 16 > knot3-16.gif
Follow the same instructions, using different tools if necessary, as the above
try section.
Judges’ remarks:
@@ -179,7 +180,7 @@ linker option).
knot writes animated GIF images of rendered torus
knots to standard output.
SYNOPSIS
-
./persano p q [num frames]
+
./persano p q [num frames]
DESCRIPTION
A (p,q)-torus knot is a closed,
non-intersecting curve on the surface of a
@@ -190,10 +191,10 @@ resulting curve will not be a knot (that is, imagining the resulting cu
a loop of rubber, there will be a way to bend, twist and stretch it, without
cutting it 1, until it ends up looking just like a circle embedded in R3 2).
Sample usage:
-
./persano 3 2 1 > foo.gif
+
./persano 3 2 1 > foo.gif
writes a non-animated GIF (a single frame) stream of a rendered trefoil
knot to the file foo.gif.
-
./persano 5 2
+
./persano 5 2
writes a GIF stream with a rendering of Solomon’s Seal
knot to standard
output; since the number of frames is not specified, an animation with
@@ -265,10 +266,10 @@ was not implemented in order to avoid the Unisys patent can no longer be used.persano.alt.c - alternative source
For your convenience, we have added the above mentioned files to this entry directory.
They were used to form the pet.rom file.
Author’s remarks:
@@ -180,7 +181,7 @@ to not infringe the rules.
Compile the program, then test the
6502emulation like this:
-
./sykes 6502test
+
./sykes 6502test
A basic test is done for each instruction and addressing mode, all tests
should pass. At the end of the tests, it loops forever - break out with
control-C.
@@ -196,15 +197,15 @@ Transactor.
Make sure you have a terminal
window of 40x25 chars or
bigger, and then run the emulator like this:
-
./sykes pet.rom
+
./sykes pet.rom
You should see the startup message. Try typing in some
BASIC - for instance:
PRINT "HELLO, WORLD"
There is an optional numeric parameter, which controls the speed. For a
slower cursor blink, try
-
./sykes pet.rom 6
+
./sykes pet.rom 6
and for faster
-
./sykes pet.rom 2
+
./sykes pet.rom 2
The default is 4.
The control keys are as follows:
^A HOME
@@ -243,7 +244,7 @@ The filenames must be upper case in order to be loaded by the emulator.
Supplied as a demonstration is a
compiled-for-6502
version a chess program (heh, I found a use for a previous losing entry :) ). Try:
-
./sykes chess
+
./sykes chess
It works as you would expect (it plays very badly). There’s no castling
or en-passant, and to win you must actually take the opponent’s king.
Unlike most BF interpreters that we
have been receiving for the last few years, this one, in our opinion, is the
@@ -218,10 +219,10 @@ hardest thing to figure out is how it finds the matching square brackets.
@@ -141,18 +142,18 @@ Location: MX - United Mexican States
To build:
-
make
+
make
To use:
-
./toledo [a ...]
+
./toledo [a ...]
Try:
-
./toledo a
+
./toledo a
./toledo a b
Alternate code:
Two alternate versions of this entry, toledo2.c and
toledo3.c are provided.
Alternate build:
To compile the alternate versions:
-
make alt
+
make alt
Alternate use:
Use Use toledo2 and toledo3 as you would toledo above.
Judges’ remarks:
@@ -170,14 +171,14 @@ single function.
This is a chess program, it can work in
two modes: two-players, and one player (always white) against the machine. To
get the first mode, run the program without arguments:
-
./toledo
+
./toledo
The other mode is accessible running the program with one argument
(5-ply
analysis):
And each successive argument will analyze one
ply more. There is no ply
limit, but beyond 7 ply is very slow, try it at your own risk and computing
@@ -266,10 +267,10 @@ and compiles faster… but I’m still not seeing the difference.
@@ -141,11 +142,11 @@ Location: US - United States of America
To build:
-
make
+
make
To use:
-
./vik [file.map]
+
./vik [file.map]
Try:
-
./vik maze.map
+
./vik maze.map
Judges’ remarks:
An amazing use of the X libraries with twisty code passages, all different. One
risks running in code path circles as main() is called again and again. Be
@@ -177,18 +178,18 @@ backward).
Compile the source code and link in X
libraries if necessary. The program takes
three options which have to be typed in a specific order as described below.
-
./vik [-w <width>] [mapfile]
+
./vik [-w <width>] [mapfile]
where:
width - Specifies the width of the window
mapfile - Filename containing a map
Examples
Start the engine using a built in labyrinth and texture bitmaps:
-
./vik
+
./vik
Start the engine and loads the labyrinth defined in the file
maze.map:
-
./vik maze.map
+
./vik maze.map
Start the engine using maze.map in a window that is 400 pixels wide:
-
./vik -w 400 maze.map
+
./vik -w 400 maze.map
Note that the mapfile has to be the last argument and the -w option if present
has to be the first. The map definition files and the bitmap files should be
located in the current directory.
We recommend you input for the filename example.gif and for the string
ioccc@example.com. The script will not overwrite files. It runs the program in
a loop until you answer that you do not wish to make another.
@@ -175,7 +176,7 @@ line. To avoid complications with patent issues the Usage:
-
@@ -141,11 +142,11 @@ Location: NO - Kingdom of Norway (
To build:
-
make
+
make
To use:
-
./hamre math_expression_string
+
./hamre math_expression_string
Try:
-
./try.sh
+
./try.sh
Judges’ remarks:
An irrationally coded source presents rational things!
A rational person might want to attempt the
@@ -162,7 +163,7 @@ an obfuscated one.
supported operators are: +, - (binary and unary), *, / and (). Run it
by supplying an expression as the first argument, and the normalized
result will be written to stdout.
-
./hamre '-1+4/3*(2+1/(3/2*(7/2-7/3+1/6)))/2'
+
./hamre '-1+4/3*(2+1/(3/2*(7/2-7/3+1/6)))/2'
2/3
If you do not supply an argument, the calculator will crash. Other
arguments are ignored. Supplying more arguments may further limit the
@@ -208,10 +209,10 @@ some language, meaningful to the purpose(s) of the macro, I hope.
@@ -141,11 +142,11 @@ Location: US - United States of America
To build:
-
make
+
make
To use:
-
./meyer [SEED]
+
./meyer [SEED]
Try:
-
./meyer [SEED]
+
./meyer [SEED]
For your first input try:
a 0 1
where a is the row (a-i), 0 is the column (0-8) and 1 is the
@@ -183,7 +184,7 @@ it is obvious, that object-oriented code isn’t ‘WYWIWID’ (‘
you write is what it does’). It may be tempting to think that
Object o;
might do something similar as
-
struct not_an_object o;
+
struct not_an_object o;
But this program reveals that it doesn’t. Even worse, this program only
reveals the tip of the iceberg, what kind of black magic is involved in
a simple declaration of an object.
Incorrect formulas will ungracefully crash the program.
Try:
-
./try.sh
+
./try.sh
Alternate code:
This alternate code lets you specify the width and height of the image as well
as the number of iterations to perform.
Alternate build:
To use the default values, the same as monge.c, just do:
-
make alt
+
make alt
But if you wish to actually make use of it you will want to redefine one or more
of the variables W, H and I. The defaults are (respectively) 400, 300 and
\128. If you wish to change the image size to 500x500 but keep the iterations
the same then do:
-
make clobber WIDTH=500 HEIGHT=500 alt
+
make clobber WIDTH=500 HEIGHT=500 alt
If you wish to keep the dimensions the same but change the iterations to 512:
-
make clobber ITERATIONS=512 alt
+
make clobber ITERATIONS=512 alt
If you specify a value less than 1 for any of these it sets it back to the
default. The value 1 was selected arbitrarily and such a small number as 1 will
not do anything useful but as long as it’s at least 1 it’ll not be redefined.
@@ -176,7 +177,7 @@ anyway.
Alternate use:
Use monge.alt exactly as you would monge above.
Alternate try:
-
./try.alt.sh
+
./try.alt.sh
Judges’ remarks:
For those who are familiar with the previous IOCCC entries,
this program is best described as “1994/tvr meets
@@ -193,11 +194,11 @@ effort to work on both i386 and x86_64. Portable it is
Keep clicking with left or right button to zoom in or out.
Use the number pad + and - to increase/decrease the iteration count when
@@ -240,35 +241,35 @@ as you like (as understood by the C function isspace()).
We recommend the alt version so that you can see what this looked like back in 2006.
If you wish to see the original faster version see original
code below.
To use:
-
./slone.alt
+
./slone.alt
Try:
The alternate version, which we recommend that you use in order to see what is
happening with modern systems, and to not flash too quickly, which can be
problematic for some people, can be configured to different speeds by way of the
value used in usleep(). The default is 75000 but you can easily change
it. To do so try:
-
make clobber SLEEP=70000 clobber alt
+
make clobber SLEEP=70000 clobber alt
./sloane.alt
If you wish to make it like the original, as if the below Original
code was being used, you can do:
-
make SLEEP=0 clobber alt
+
make SLEEP=0 clobber alt
./sloane.alt
Original code:
Should you wish to see the original you may do so with the original code,
sloane.c.
Original build:
-
make clobber all
+
make clobber all
Original use:
-
./sloane
+
./sloane
WARNING: if you are easily overstimulated with fast movement or have
photosensitivity please be careful running this version and instead see the
above!
@@ -242,10 +243,10 @@ place? Can you find a smaller encoding?
After running the program on a few files it will ask you if you wish to run it
on the remaining files.
The script will try converting the xbm files created by the program to png
@@ -171,7 +172,7 @@ a reasonably experienced user who can parse formats in their mind. :-)
Author’s remarks:
Execution
The program should be run with the following
-
./stewart <m> <n> <ifs>
+
./stewart <m> <n> <ifs>
where:
m = The size of the picture (picture will be m X m in size).
n = The number of iterations to run (More will make for a
@@ -181,7 +182,7 @@ a reasonably experienced user who can parse formats in their mind. :-)
on standard out. Minimal checking is done on the arguments mainly that there
are 3. Wrong arguments will cause the program to bomb out.
Example:
-
./stewart 1024 1000000 gasket > gasket.xbm
+
./stewart 1024 1000000 gasket > gasket.xbm
Compilation/Testing
The program compiles without warning with gcc -ansi -Wall.
lint also seems to like the code. This must be a bug in lint.
@@ -330,10 +331,10 @@ choice from a file size standpoint. 1024x1024 image is 641k in size.
@@ -141,7 +142,7 @@ Location: FI - Republic of Finland
To build:
-
make
+
make
There is an alt version based on the author’s remarks. The try.sh
script will compile and use both but if you wish to see the alternate version
specifically see the Alternate code section below.
@@ -150,18 +151,18 @@ specifically see the Alternate code section below.
This will run both the original entry and the alt code to show some differences.
Also try:
If you have all day :-) and wish to find out how fast your machine can solve the
maximum:
-
time ./sykes1 19186
+
time ./sykes1 19186
This was done on a Rocky Linux 9.2 server with Intel(R) Core(TM) i9-9900K CPU @ 3.60GHz with 16 cores (via HyperThreading):
real 6m35.524s
user 6m35.159s
@@ -173,17 +174,17 @@ maximum:
Alternate code:
This alternate code is based on the author’s remarks.
Alternate build:
-
make alt
+
make alt
Alternate use:
Use sykes1.alt as you would sykes1 above.
Alternate try:
The try.sh script will use both versions to show some differences. You
can do so like:
-
./try.sh
+
./try.sh
Judges’ remarks:
Read the sykes1.html page source.
Now then read the C source. Confused? :-) If it’s not clear try:
-
diff -s sykes1.c sykes1.html
+
diff -s sykes1.c sykes1.html
For extra credit, understand what happens when you give this entry
an negative number argument, and why.
See the author’s remarks for how to make your own shapes as well.
@@ -200,7 +201,7 @@ together. I have not known anyone to solve it in this way - you would
need to be very lucky indeed to stumble across a solution.
Instructions
Compile the program, then test that it works:
-
./sykes1
+
./sykes1
Shortly you should see the first solution pop out on your screen. It
shows you how to build the cube piece by piece, rendered in glorious
3D ASCII.
@@ -210,18 +211,18 @@ open the file sykes1.html. This html file is just a co
the browser display for you a nice animated GIF, showing you how to build the
cube. Rendered in glorious 3D color.
Want to see another solution? Try:
-
./sykes1 some_number
+
./sykes1 some_number
The program will discard solutions up to the number, and output numbered
solution. Refresh your browser window to see the new solution.
Try some more - there are exactly 19186 solutions to choose from.
If you have a fast machine you might try the last solution:
-
./sykes1 19186
+
./sykes1 19186
On my machine this takes about half an hour to run.
Implementation
The implementation is an optimized recursive algorithm that tries to fit
the pieces into the cube one by one. The cube pieces are defined near
the start of the program:
Each piece is a bitmap, and represents a 3x3x3 cube.
@@ -256,7 +257,7 @@ shape:
the pieces, and provided that a solution is possible, it will be found.
For example, if you modify line 13 of the source like this, the program
will solve for a different piece set:
-
int s[ ] = { 187, 94, 402, 3098
+
int s[ ] = { 187, 94, 402, 3098
And of course you can make your own.
After the pieces are defined, the first thing the program does it to
fit them into a 4x4 cube. It collects every possible placing of each
@@ -334,10 +335,10 @@ advantage - at least I don’t violate any of those old Unisys patents!
@@ -141,7 +142,7 @@ Location: MX - United Mexican States
To build:
-
make
+
make
There is alternate code that is based on the author’s notes
for DOS/Windows. This cannot be tested by us, not even to compile, but it appears
that it should be fine, after the proper header files were added.
@@ -150,12 +151,12 @@ that it should be fine, after the proper header files were added.
To end execution press ctrl-z. As mentioned in the author’s remarks and in the
below section, it is supposed to crash on termination though some noted this
does not seem to happen in macOS or linux in 2023.
Try:
-
./toledo2
+
./toledo2
and then type in the following:
10 PRINT "HELLO WORLD!"
LIST
@@ -165,7 +166,7 @@ does not seem to happen in macOS or linux in 2023.
This version, as noted, should work for DOS/Windows. It uses non-standard
functions in place of read(2) and write(2).
Alternate build:
-
make alt
+
make alt
Alternate use:
The author noted that for PC/DOS you will have to add ANSI.SYS to your
CONFIG.SYS but this is also something we can’t test.
@@ -141,14 +142,14 @@ Location: MX - United Mexican States
To build:
-
make
+
make
The author provided two alternate versions, one which adds a status bar and
another that makes it text only. The author also provided a version that they
tested with Windows. See alternate code below.
To use:
-
./toledo3 [1 | 2 | 3 [b]]
+
./toledo3 [1 | 2 | 3 [b]]
Try:
-
./toledo3 1
+
./toledo3 1
Alternate code:
The author provided two additional versions, toledo3-sbar.c
and toledo3-txt.c. Respectively these create a status bar and
@@ -172,7 +173,7 @@ the code for Deep Blue.
So I managed to do a graphical X11 chess program (‘WYSIAIE’, or ‘What You See
Is An IOCCC Entry’). Pointing and clicking to move pieces is the only required
action, and of course the command-line options:
-
./toledo3 # Two-players mode (useful if you don't have a board at hand)
+
./toledo3 # Two-players mode (useful if you don't have a board at hand)
./toledo3 1 # Human white - Computer black, level 1 (fast)
./toledo3 2 # Human white - Computer black, level 2 (medium)
./toledo3 3 # Human white - Computer black, level 3 (slow)
@@ -196,7 +197,7 @@ optimizations use valuable IOCCC characters.
number generator.
Because it is resource-hungry, I strongly recommend to compile it
using maximum optimization. With GCC you can use:
Anything that is not parsable as PGM or PPM will be downsampled as
ASCII art. Since the source code is formatted as ASCII art, it’s only
natural to try:
-
./akari akari.c akari2.c
+
./akari akari.c akari2.c
akari2.c is also a valid C program, and accepts up to 1 argument.
By default, this second program reads text from stdin and writes
expanded output to stdout. If the extra argument is specified, the
output text will also pass through a rot13 filter.
You can combine the two programs together to have just a regular rot13
filter:
-
./akari2 rot13 < input.txt | ./akari > rot13.txt
+
./akari2 rot13 < input.txt | ./akari > rot13.txt
Of course, we wouldn’t stop with just 2 programs, you can downsample
the source again and get yet another C program:
-
./akari < akari.c | ./akari > akari3.c
+
./akari < akari.c | ./akari > akari3.c
We must go deeper:
-
./akari < akari.c | ./akari | ./akari > akari4.c
+
./akari < akari.c | ./akari | ./akari > akari4.c
akari3.c and akari4.c are still (mostly valid) C programs.
gcc -Wall will output a few warnings, but still produce output
executables. The output executables each print a message to stdout.
@@ -243,10 +244,10 @@ a brainf#$% program in a C program, for example. For comparison, a
@@ -141,14 +142,14 @@ Location: GB - United Kingdom of Great
To build:
-
make
+
make
To use:
Zoom out and make your terminal window 53 or more lines deep.
-
./blakely < blakely.c | head -300
+
./blakely < blakely.c | head -300
Try:
-
./try.sh
+
./try.sh
For those who have a lot of time, try:
-
./blakely < t0_3.dat
+
./blakely < t0_3.dat
though one might or might not need to kill it, depending on your boredom
threshold.
Judges’ remarks:
@@ -158,14 +159,14 @@ if given its own source as input, and allows to check if your garden
is a Garden of Eden, all in one source.
If you have enough time to spare, put the plan of your garden in a text file,
and run:
-
./blakely - < garden.txt
+
./blakely - < garden.txt
Author’s remarks:
This program uses a well-known algorithm in order to display pi to fifteen
decimal places. The source-layout itself demonstrates the importance of using
the correct amount of whitespace in code and the clear superiority of spaces
over tabs.
In order to see the main feature of the code, type:
-
./blakely < blakely.c
+
./blakely < blakely.c
and wait for about four seconds before using Ctrl-C (or whatever) to end the program. The
results are best viewed in a terminal window at least 60 characters
high and wide. Alternatively, redirect the output to a separate file
@@ -176,12 +177,12 @@ Life”, using standard input as a starting grid. The
layout of the source-code is such that it evolves to a digital representation of
the first 15 decimal places of pi after 4 time steps. This was setup using the
other feature of the program which can be demonstrated as follows:
-
./blakely - < 3.dat
+
./blakely - < 3.dat
The program will first display the grid given in 3.dat, and then three
more grids (taking a few minutes to display the last). Waiting for any more
grids will take a substantial amount of time. The final grid has been put into
evolve_to_3.dat, and if you type
-
./blakely < evolve_to_3.dat
+
./blakely < evolve_to_3.dat
then the 3 will reappear after three time steps.
As should now be clear, this use of the program will attempt to evolve a given setup
backwards in time according to the Life rules. The resulting grid is clearly not
@@ -329,10 +330,10 @@ universe.
This is a nice quick histogram
plotter. A useful utility when you need to look at the distribution of some
@@ -223,10 +224,10 @@ and each of them is put into its own bin afterwards. But where are the bins?data.1 - sample input
The match of dlowe.c to the lose/win trailed network was:
dlowe.c 0.125108
@@ -203,7 +204,7 @@ mean it will win or lose a future IOCCC. On the other hand … it just might!While we cannot supply you with the losing IOCCC source code, the author did supply a number
data sets on which to test:
@@ -242,7 +243,7 @@ which can be trained, using on-line
neuron.
The neurons’ activation function is the logistic function 1 / (1 + e ^ -x).
Classifying
-
./dlowe file [file ...] < trained.net
+
./dlowe file [file ...] < trained.net
To classify files, one specifies a trained network (on stdin) and one or more
files to classify. The program will output one line per successfully-classified
file to stderr, with the filename and the classification: a number between 0
@@ -251,7 +252,7 @@ and 1.
trained, but it’s geared toward interpretation as a probability or a
confidence.
NOTE: The directory args must end in a/ for them to work.
To train a network, one specifies a starting network (on stdin), two or more
corpora (directories containing training data), and the number of training
@@ -415,10 +416,10 @@ by a network trained to recognize IOCCC entries
@@ -141,14 +142,14 @@ Location: US - United States of America
To build:
-
make
+
make
To use:
-
./eastman
+
./eastman
NOTE: to restore your cursor in your shell, try reset.
Try:
Run the program. Quit it (ctrl-c/intr). Resize your terminal window. Run it
again. Try doing this a number of times with different sizes each time.
-
./eastman
+
./eastman
NOTE: to restore your cursor in your shell, try reset.
Judges’ remarks:
This round program will generate a classic spherical result!
@@ -173,7 +174,7 @@ is also just part of the texture, not an actual raytraced shadow.
so try enlarging the window to get higher resolution. Don’t resize while the
program is running, though. It only checks the size once, when it starts up.
To compile:
-
cc -lm eastman.c
+
cc -lm eastman.c
Portability
It should be completely portable. I’ve tested with gcc on Mac OS X 10.7 (Lion)
and Fedora 10. I would expect it to work in any Unix-like environment.
NOTE: you need to be allowed to change your stack size or else the last command
in the script would likely cause the program to dump core, which is why the
script checks the exit code of ulimit first.
@@ -165,7 +166,7 @@ program and calls it. As an exercise, try writing the compressor.
Implements a variant of grep.
Usage
To search regexp from file, do:
-
./fredriksson [-icvtnk#] regexp < file
+
./fredriksson [-icvtnk#] regexp < file
Pipes might not work, see the section Limitations.
The options -i, -c, -v and -n are the classic ones:
@@ -220,11 +221,11 @@ expressions by putting ] as the first character, and putting
It is assumed that the user knows how to feed correct input to the
@@ -256,7 +257,7 @@ you can easily use long long instead,
Depending on the file, it might require a lot of stack space. If the
program segfaults (because of this), say
-
ulimit -s unlimited
+
ulimit -s unlimited
cross your fingers, hope it is enough, and try again.
Assumes C99 standard, because of the one very long line. Most C compilers
@@ -284,7 +285,7 @@ as well as its name and commands to build and run it, all
extracts and builds that, and then calls it. More precisely, the command
to build is
-
gcc -O3 ag.c -o ag
+
gcc -O3 ag.c -o ag
To change that you need to edit the char array p[] and (possibly) two
specially encoded constants, -~('('*'(') and 'C'*' '-'-'.
The extracted source (ag.c) is obfuscated as well.
@@ -333,10 +334,10 @@ Two’s complement representation of integers is also abused. E.g. instead
of writing x++ or x-1, it is much better to write x=-~x and ~-x.
No numerical values, other than in the initialized char array, try
-
./fredriksson -ck0 [0-9] < fredriksson.c
+
./fredriksson -ck0 [0-9] < fredriksson.c
This should print 1, as there is a number 3 in the char array (only).
You can also try
-
./fredriksson -ck0 [0-9] < ag.c
+
./fredriksson -ck0 [0-9] < ag.c
after running fredriksson at least once (since this generates that
ag.c file), and this should print 0.
@@ -391,10 +392,10 @@ apply to the generated source ag.c.)
If you have perl installed you should be able to reproduce
dragon.nono like:
-
perl c2nono.pl hamaji.c | ./hamaji
+
perl c2nono.pl hamaji.c | ./hamaji
Judges’ remarks:
This program solves Nonograms which is
also known as “Paint by Numbers”.
@@ -260,7 +261,7 @@ with the well obfuscated code.
Portability
This program uses two C99 features. One line comments and long long.
GCC’s -ansi -pedantic check should pass:
-
cc -ansi -pedantic -std=c99 hamaji.c
+
cc -ansi -pedantic -std=c99 hamaji.c
I checked my program with gcc-4.6.2 on linux, llvm-gcc-4.2 on Mac, and
clang-3.0 on Mac.
Note that the behavior of scanf(3) differs on linux and mac, but this
@@ -269,7 +270,7 @@ program supports both semantics.
memory layout, undefined evaluation order (e.g., a[i++]=i), etc.
This program won’t work if the size of long long literal is less than 8.
By grepping the source code of gcc
-
grep LONG_LONG_TYPE_SIZE gcc/config/*/*
+
grep LONG_LONG_TYPE_SIZE gcc/config/*/*
I found long long may be 32bit integers only on AVR.
This tiny program outputs what looks like a tiny keyboard.
OK, so the letters are missing. But that is no problem because
@@ -192,10 +193,10 @@ Can you then minimize the size of that code?
The first alt version, toledo.alt.c, allows you to reconfigure
the controls and the dimensions more easily.
@@ -168,7 +169,7 @@ have the right names you can define the macros FIRE, FORWARD<
HEIGHT= 288
but you can change them about however you like, even with other keys. For
instance to swap LEFT and RIGHT:
-
make clobber LEFT=XK_Right:XK_d RIGHT=XK_Left:XK_a alt
+
make clobber LEFT=XK_Right:XK_d RIGHT=XK_Left:XK_a alt
but you can specify something completely else and you can pick and choose which
controls you wish to redefine. You might also wish to change the dimensions of
the game, WIDTH and HEIGHT which have an arbitrarily selected lower limit as
@@ -184,7 +185,7 @@ the source early on, right before the code gets hard to follow, or using the
alternate version.
Like Oscar’s previous winning X11 program for the 19th IOCCC, if
you remove both the X11 include files and replace them with
-
#include "layer.c"
+
#include "layer.c"
you ought to be able to compile and run this program on Windows.
NOTE: this is what toledo.alt2.c is for.
and then play file.wav with a program that can play WAV files.
Try:
-
./try.sh
+
./try.sh
The script checks that you have mplayer(1) installed and if it is it will pipe
vik to mplayer. In this case it will also use raw2wav to convert the file
to a WAV file. If mplayer(1) cannot be found it will just use raw2wav. This
@@ -168,7 +169,7 @@ Archive.
This version is based on the author’s remarks and it should work for Windows.
Alternate build:
Assuming that make is similar enough try:
-
make alt
+
make alt
Alternate use:
Use vik.alt as you would vik above.
Judges’ remarks:
@@ -178,7 +179,7 @@ in a most pleasing manner if you don’t like tremolo or vibrato.
initialized 32MB array. Can you tell what that partial
initialization for?
Does it take your system a long time to compile? You may want to do:
-
cc -S vik.c
+
cc -S vik.c
and examine the resulting assembly file vik.s. On some platforms
the assembly file is about 128MB in size!
NOTE: The randowan.mod and mad_world.mod files were
@@ -225,12 +226,12 @@ Bertilsson, also known as Deelite:
Build
Compiling for Unix systems (including cygwin) is straight forward:
-
gcc -o vik vik.c
+
gcc -o vik vik.c
Usage
Convert MOD file to raw 44.1kHz stereo audio file
-
./vik mad_world.mod > audio_file.raw
+
./vik mad_world.mod > audio_file.raw
Listen to the MOD file (streaming to mplayer)
-
./vik randowan.mod | mplayer -demuxer rawaudio -
+
./vik randowan.mod | mplayer -demuxer rawaudio -
(Don’t forget the last - as it makes mplayer read from stdin.)
Obfuscation
The IOCCC rules did not put a limit on the entropy of the source code,
@@ -256,7 +257,7 @@ that the program relies on writing binary data to stdout.
Microsoft compilers adds a carriage return to newlines, and to compile
the program with this platform, the following line can be added after
the main declaration in order for the program to run correctly:
@@ -141,14 +142,14 @@ Location: US - United States of America
To build:
-
make
+
make
There is an alternate version which should work for Windows which distinguishes
binary mode from text mode. See alternate code below.
To use:
-
./zucker > image.ppm
+
./zucker > image.ppm
Now open image.ppm with your image viewer of choice.
Try:
-
./try.sh
+
./try.sh
After running try.sh, open the PPM images ioccc.ppm, hello.ppm and
image2.ppm with your image viewer of choice.
Alternate code:
@@ -156,7 +157,7 @@ binary mode from text mode. See alternate code bel
binary mode on stdout which the author noted would be necessary for systems
that distinguish binary and text.
Alternate build:
-
make alt
+
make alt
Alternate use:
Use zucker.alt as you would zucker above.
Alternate try:
@@ -170,7 +171,7 @@ The vector font is proportional.
What it does:
This program makes pretty pictures. To see the default output, try
running
-
./zucker > ioccc2011.ppm
+
./zucker > ioccc2011.ppm
On the author’s 2.5 GHz MacBook Pro, this command takes approximately 1 minute
and 18 seconds to run – your runtime may vary. You will need an image viewer
capable of displaying Netpbm images in
@@ -179,20 +180,20 @@ well; otherwise ImageMagick and/or
GraphicsMagick are both capable of displaying
Netpbm files, and are available on multiple platforms.
With macOS you can type at the command line:
-
open ioccc2021.ppm
+
open ioccc2021.ppm
and it will open image in the default application Preview.app.
To use ImageMagick you might do something like:
-
convert ioccc2011.ppm ioccc2011.png
+
convert ioccc2011.ppm ioccc2011.png
and then open ioccc2011.png in your viewer of choice.
To use GraphicsMagick you might do something like:
-
gm convert ioccc2011.ppm ioccc2011.png
+
gm convert ioccc2011.ppm ioccc2011.png
and then open ioccc2011.png in your viewer of choice.
Aside from the default image, you may create your own by running the
program as follows:
-
./zucker "your text" > image.ppm
+
./zucker "your text" > image.ppm
To mitigate long runtime, the program can be invoked in a “preview”
mode by appending -preview to the command line arguments, like so:
-
./zucker faster\! -preview > image.ppm
+
./zucker faster\! -preview > image.ppm
If your platform distinguishes between binary and text streams, you may need to
insert some code to reopen standard output in binary mode at the start of
main() (the provided alternate version will set binary mode
@@ -306,10 +307,10 @@ Python, respectively).
Several IOCCC themes (RPN
calculator, animated
@@ -169,7 +170,7 @@ resolution, and an animated GIF showing a fly-around of the resulting surface is
output to stdout.
Usage
The program should be run as:
-
./blakely xy* 32 > pic.gif
+
./blakely xy* 32 > pic.gif
where the first parameter is a
RPN expression, and the
second is the width of the required GIF, up
@@ -201,7 +202,7 @@ and more complex expressions take longer to compute. For example, increasing the
resolution of ripple.gif
to 250 took ~35 minutes to render on an i7
processor.
This minimalistic music notator expects two command line arguments. The first is
the font description embedded in the source code. Notice that you don’t pass the
@@ -186,7 +187,7 @@ clef. "K" followed by any other letter will just default to a stand
Examples
Blank music paper (with G clef):
-
./deckmyn "`cat deckmyn.c`" "sz sa x s1 x s1 x s1 x s1 x s1 "> blank.pbm
+
./deckmyn "`cat deckmyn.c`" "sz sa x s1 x s1 x s1 x s1 x s1 "> blank.pbm
With an F clef:
./deckmyn "`cat deckmyn.c`" "KF sz sa x s1 x s1 x s1 x s1 x s1 "> blank.pbm
Notice how only the first staff (or any staff) needs to have the full length.
The C of this entry is definitely sharp. The program cleverly uses its own
source at runtime to define the notes, time signature and accidental bitmaps.
@@ -168,14 +169,14 @@ is not done in the author’s remarks, however.
You need the source code and example input (either one of the example files, or
manual input as below) ready and a program capable of showing .pbm bitmap
format images.
There are two alt versions that let you control the compile time variables that
control the fluid behaviour and the added variables to speed up or slow down the
fluid as well as setting a timeout (if not 0): one for the original black and
@@ -149,12 +150,12 @@ judges at the time of the contest). Another version is the deobfuscated version
provided by the author as well. See the Alternate code
section below for more details.
To use:
-
./endoh1 < file
+
./endoh1 < file
WARNING: if you’re sensitive to/don’t like flashing colours/text or just want to
see what this looks like not going so fast then you might wish to try the
Alternate code instead.
Try:
-
./try.bw.sh endoh1.c
+
./try.bw.sh endoh1.c
./try.sh endoh1.c
./try.bw.sh pour-out.txt
@@ -170,39 +171,39 @@ the fluid and change the behaviour of the fluid. The file
endoh1.alt2.c is deobfuscated and was provided by the author.
Alternate build:
For the default values, try:
-
make alt
+
make alt
In the alt versions a default time of 10 seconds is set as an alarm so that
one can more easily go through the list of files to see them all in succession,
for fun. That is controlled by the variable TIMER at compilation.
For instance if you wish to change the value to 5:
-
make clobber TIMER=5 alt
+
make clobber TIMER=5 alt
If you want to disable the alarm time, set it to 0:
-
make clobber TIMER=0 alt
+
make clobber TIMER=0 alt
It cannot be < 0 or > 60 (arbitrarily selected).
The SLEEP variable is to delay the time between updates to make it easier to
see and to not flash too quickly. The code protects against a value < 0 and
defaults to 12321 but you can change it to. For instance to slow it down you
could increase the sleep time from 12321 to 50000:
-
make clobber SLEEP=50000 alt
+
make clobber SLEEP=50000 alt
If you wish to speed it up you might decrease the sleep time from 12321 to
9999:
-
make clobber SLEEP=9999 alt
+
make clobber SLEEP=9999 alt
WARNING: the lower the value the faster it will flash so be careful if you’re
sensitive to this.
If you wish to change the gravity factor, pressure factor and/or
viscosity factor, you should redefine the values GRAVITY, PRESSURE and/or
VISCOSITY macros, respectively. For instance if you wish to change the
viscosity and pressure factors but leave the other values alone:
-
make clobber VISCOSITY=X PRESSURE=Y alt
+
make clobber VISCOSITY=X PRESSURE=Y alt
where X and Y are numbers or the letter I and which are, respectively, the
viscosity and pressure factors. There is no attempt to check the value or type
because doing so prevents the macros from being defined to I which would
prevent the author’s remarks about it from being done.
You might also wish to try redefining the macros G, P and/or V. For
instance:
-
make clobber GRAVITY=5 PRESSURE=5 VISCOSITY=5 alt
+
make clobber GRAVITY=5 PRESSURE=5 VISCOSITY=5 alt
You might try even:
-
make clobber GRAVITY=I alt
+
make clobber GRAVITY=I alt
See the author’s remarks for details on these macros where:
G = GRAVITY
P = PRESSURE
@@ -213,10 +214,10 @@ and endoh1_color above.
Alternate try:
To see two different ways run on the source file and each of the text files,
try:
-
./try.alt.sh
+
./try.alt.sh
The second run of each will be with the gravity factor set to I.
To see the same thing but in the original uncoloured version, try:
A: An obfuscated program that deals with complex numbers and produces animated ASCII graphics.
@@ -231,7 +232,7 @@ entry.
Synopsis
DO NOT FORGET-DG=1 -DP=4 -DV=8 and make your terminal window larger
than 80 x 25.
-
cc endoh1.c -DG=1 -DP=4 -DV=8 -D_BSD_SOURCE -o endoh1 -lm
+
cc endoh1.c -DG=1 -DP=4 -DV=8 -D_BSD_SOURCE -o endoh1 -lm
./endoh1 < endoh1.c
./endoh1 < logo.txt
./endoh1 < column.txt
@@ -284,7 +285,7 @@ comments. It also uses usleep(3), which may require -D_BSD_SO
to build with no warning. Under these conditions, it should be portable.
At least, recent compilers with -std=c99 -Wall -W -Wextra -pedantic say
nothing.
-
warning, it requires two C99 features: allow string literal to be more than 509
characters and not requiring a return in main(). In fact, recent compilers
with -std=c99 -Wall -W -Wextra -pedantic would say nothing.
-
Also known as ‘Best abuse of the judging process’.
The IOCCC 2012 submission page didn’t enforce the 2048 meaningful character
@@ -184,12 +185,12 @@ into 3 parts and require two of them be available to extract the original recipe
Example usage
To split a secret into 4 pieces of which at least 3 will be needed to get it (in
this case the cookie recipe) back:
The script will generate a number of PDF files and it will suggest you look at
them as well. You can read hint.pdf with a PDF reader like acroread hint.pdf
or evince hint.pdf. With macOS you can do open hint.pdf which by default
@@ -155,13 +156,13 @@ directly instead.
the PDF file will then be compiled as C (itself!) and executed so that it shows
README.md!
That procedure looks like:
-
./hamano < README.md > hint.pdf
+
./hamano < README.md > hint.pdf
cc -xc hint.pdf -o hint
./hint
Another PDF generated is an obfuscated Hello World! program (obfuscated inside
the PDF). Once this is done it will compile the PDF as if it was C (itself!). It
will look like:
The regex engine is also algorithmically efficient. To illustrate the point,
ansi.txt contains a pathological expression [2] that guarantees a hang for the
competing Perl engine while matching itself. Try to compare these two engines:
The regex engine is also algorithmically efficient. To illustrate the point,
ansi.txt contains a pathological expression 1 that guarantees a
hang for the competing Perl engine while matching itself. Try to compare these
two engines:
-
./hou ansi.txt ansi.txt
+
./hou ansi.txt ansi.txt
perl patho.pl < ansi.txt
Limitations
Finally, there are a few limitations…
@@ -260,10 +261,10 @@ amount of spaghetti branches and virtual thread creations. Finally, the VM in
@@ -141,13 +142,13 @@ Location: KR - Republic of Korea (
To build:
-
make
+
make
There is alternate code which fixes some German at the expense of other German.
See Alternate code below for the (fun) rationale here.
To use:
-
echo "full spelling of an English cardinal numeral less than a quadrillion" | ./kang
+
echo "full spelling of an English cardinal numeral less than a quadrillion" | ./kang
Try:
-
./try.sh # try various languages
+
./try.sh # try various languages
./en.sh # English 0 through 13
@@ -164,15 +165,15 @@ deal with it :-) It also breaks other words too and this happens only for one
letter change. With this one should hopefully be able to really appreciate the
subtlety of this entry even more.
Alternate build:
-
make alt
+
make alt
Alternate use:
-
echo "full spelling of an English cardinal numeral less than a quadrillion" | ./kang.alt
+
echo "full spelling of an English cardinal numeral less than a quadrillion" | ./kang.alt
echo vier | ./kang.alt
echo uno | ./kang.alt
Alternate try:
-
./try.alt.sh # try various languages
+
./try.alt.sh # try various languages
./en.alt.sh # English 0 through 13
@@ -188,9 +189,9 @@ German, Italian, Russian, and Spanish numerals.
colloquial year numbers of the last millennium.
We’ve added a linefeed to the print format for convenience.
@@ -141,13 +142,13 @@ Location: US - United States of America
To build:
-
make
+
make
There is an alternate version that will read from the compiled file itself, in
case you don’t have a /dev/urandom file. There is also a version that should
theoretically work with Windows which distinguishes binary and text. See
alternate code below.
To use:
-
./nyaruko [seed.txt] < original.bin > output.c
+
./nyaruko [seed.txt] < original.bin > output.c
bash output.c > key.c
perl output.c > data.c
@@ -159,7 +160,7 @@ theoretically work with Windows which distinguishes binary and text. See
file or use the alternate version which reads in the compiled
binary itself.
Try:
-
./try.sh
+
./try.sh
The script try.sh will check if you have perl before trying to use the
perl parts of the script.
Alternate code:
@@ -171,14 +172,14 @@ is like the first except it also should theoretically work with Windows, setting
binary mode on stdin and stdout.
Alternate build:
For the first version:
-
make alt
+
make alt
For the second version:
-
make alt2
+
make alt2
Alternate use:
Use nyaruko.alt or nyaruko.alt2 as you would nyaruko above.
Alternate try:
For the first alternate version:
-
./try.alt.sh
+
./try.alt.sh
We have no way to test the second version, sorry (tm Canada :-) )!
Judges’ remarks:
The judges have nothing to add that has not already been written about in the
@@ -187,24 +188,24 @@ binary mode on stdin and stdout.
Usage
Nyaruko is a binary to text filter. Given some input on stdin,
Nyaruko will produce C code that reproduces this input on stdout:
Output is encrypted, but both key and data are included in the output.
To separate the key from the data, run these commands:
-
bash output.c > key.c
+
bash output.c > key.c
perl output.c > data.c
The key-less data.c still compiles, but produces a different message
on stdout instead of the original input. This message is a hint to
why the code is formatted the way it is.
To combine the key and data, concatenate them together in either
order:
By default, Nyaruko generates a unique random key for every message,
using /dev/urandom as the seed. If given an extra command line
argument, Nyaruko will seed using that file instead of /dev/urandom:
-
./nyaruko seed.txt < input.bin > output.c
+
./nyaruko seed.txt < input.bin > output.c
This makes the output key deterministic, allowing the same key to be shared
across different files. On operating systems that do not have /dev/urandom,
users should always specify this extra seed argument to avoid indeterministic
@@ -297,10 +298,10 @@ JavaScript.
Use ./tromp32 as you would ./tromp if on a 32-bit machine.
To use:
-
cat ascii-prog.blc data | ./tromp -b
+
cat ascii-prog.blc data | ./tromp -b
cat binary-prog.Blc data | ./tromp
Try:
-
./try.sh
+
./try.sh
Judges’ remarks:
The judges dare to say that the data files this entry is processing
are more obfuscated than the entry itself.
@@ -206,23 +207,23 @@ notation) which is the
identity function. When its encoding 0010 is fed into the universal machine,
it will simply copy the input to the output (well, not that simply, since each
byte is smashed to bits and rebuilt from scratch). Voila: a half byte cat:
-
$ echo " Hello, world" | ./tromp
+
$ echo " Hello, world" | ./tromp
Hello, world
Since the least significant 4 bits of the first byte are just arbitrary padding
that is ignored by the program, any character from ASCII 32 (space) through 47
(/) will do, e.g.:
-
$ echo "*Hello, world" | ./tromp
+
$ echo "*Hello, world" | ./tromp
Hello, world
Bad programs
If the input doesn’t start with a valid program, that is,
if the interpreter reaches end-of-file during program parsing,
it will crash in some way. E.g. the following might dump core:
-
echo -n "U" | ./tromp
+
echo -n "U" | ./tromp
Furthermore, the interpreter requires the initial encoded lambda term to be
closed, that is, variable n can only appear within at least n enclosing
lambdas. For instance, here the term \ 5 is not closed, causing the
interpreter to crash when looking into a null-pointer environment:
-
echo ">Hello, world" | ./tromp
+
echo ">Hello, world" | ./tromp
will likely dump core.
Since these properties can be checked when creating
BLC programs,
@@ -265,7 +266,7 @@ as a self interpreter in BLC it is downright minuscule at 232 bits (29 bytes):
0b7fb 00cf6
7bb03 91a1a
-
$ (cat uni8.Blc; echo " Ni hao") | ./tromp
+
$ (cat uni8.Blc; echo " Ni hao") | ./tromp
Ni hao
A prime number sieve
Even shorter than the self-interpreter is this prime number sieve in 167 bits
@@ -281,7 +282,7 @@ as a self interpreter in BLC it is downright minuscule at 232 bits (29 bytes):
0000110110
The nth bit in the output indicates whether n is prime:
For those who prefer to digest their primes in decimal, there is oddindices.Blc,
which will print the indices of all odd characters (with
@@ -308,7 +309,7 @@ separated by a given character:
60 8191a00167fb cbcfdf65f7c0 a20
It expects n arbitrary characters of input, and draws a space filling Hilbert
curve of order n:
-
$ (cat hilbert.Blc; echo -n "1") | ./tromp
+
$ (cat hilbert.Blc; echo -n "1") | ./tromp
_
| |
@@ -370,7 +371,7 @@ followed by a ], followed by the input for the Brainfuck program.
A BLC assembler
Writing BLC programs can be made slightly less painful with this parser that
translates single-letter-variable lambda calculus into BLC:
-
$ echo "\f\x f (f (f x))" > three
+
$ echo "\f\x f (f (f x))" > three
$ cat parse.Blc three | ./tromp
000001110011100111010
Converting between bits and bytes
@@ -378,21 +379,21 @@ translates single-letter-variable lambda calculus into BLC:
BLC and BLC8. If you assemble a byte oriented program, you’ll need to compact it
into BLC8:
So we could assemble an input reversing program as
-
echo "\a a ((\b b b) (\b \c \d \e d (b b) (\f f c e))) (\b \c c)" > reverse
+
echo "\a a ((\b b b) (\b \c \d \e d (b b) (\f f c e))) (\b \c c)" > reverse
cat parse.Blc reverse | ./tromp > reverse.blc
BLC8 program symbolic.Blc shows individual reduction steps on symbolic lambda terms.
Here it is used to show the calculation of 2^3 in Church numerals:
-
$ echo "(\f\x f (f (f x))) (\f\x f (f x))" > threetwo
+
$ echo "(\f\x f (f (f x))) (\f\x f (f x))" > threetwo
$ cat parse.Blc threetwo | ./tromp > threetwo.blc
$ cat symbolic.Blc threetwo.blc | ./tromp
(\a \b a (a (a b))) (\a \b a (a b))
@@ -415,11 +416,11 @@ numeral 8.
Taking only the first line of output gives us a sort of BLC disassembler, an
exact inverse of the above assembler. The prime number sieve disassembles as
follows:
-
$ cat symbolic.Blc primes.blc | ./tromp | head -1
+
$ cat symbolic.Blc primes.blc | ./tromp | head -1
\a (\b b (b ((\c c c) (\c \d \e e (\f \g g) ((\f c c f ((\g g g) (\g f (g g)))) (\f \g \h \i i g (h (d f))))) (\c \d \e b (e c))))) (\b \c c (\d \e d) b)
Hardly any less obfuscated…
The last line of
-
cat symbolic.Blc primes.blc | ./tromp | head -16
+
cat symbolic.Blc primes.blc | ./tromp | head -16
starts out as
\a \b b (\c \d c) (\c c (\d \e d) (\d d (\e \f f) (\e e (\f \g g) ((\f (\g \h \i
The \a is for ignoring the rest of the input (to which the universal machine
@@ -444,7 +445,7 @@ Syntax which relies on the highly optimized
Haskell runtime system for evaluation. Of course individual BLC programs running
under the interpreter perform much worse than that same program written in Haskell.
Our interpreter copes well with extra levels of interpretation:
-
$ time cat primes.blc | ./tromp -b | head -c 210 > /dev/null
+