IOCC 2015 not winning entries 25/03/2020
Sometimes you win sometimes you NOT. One year after my 2014 Winning entries i have participated another times to the IOCCC contest without winning nothing. But here they are ALL of the programs that i have created for the nerdy contest!
SOUNDOFPI
OVERVIEW
This is a song generator. The generated song is based on an obscure sequence of numbers. Who can understand what is this sequence?
BUILD
$(CC) prog.c -o prog
RUN
./prog 1000 > song.wav
FEATURES
This program generate a 44100Hz 16bit mono audio file. The length and duration of the file depends on the argument given to the program. You can try with these values:
./prog 200
./prog 1000
./prog 6000
The more the number is great, the more the length of the file will be big.
SIERPINSKI
OVERVIEW
This is a fractals generator. It generates a fractal like the Sierpinski Carpet but little different.
BUILD
$(CC) prog.c -o prog
RUN
echo 27 | ./prog > image.ppm
To view the generate image you can use GIMP or ImageMagick to convert the image
convert image.ppm image.jpg
FEATURES
This program reads a number N from stdin and generates a PPM image with resolution NxN
SIERPINSKI CARPET in 149 bytes
This is the standard Sierpinski Carpet fractal, if you don't want my fractal:
a,b,c,x,y;main(){scanf("%d",&a);printf("P5 %d %d 1 ",a,a);for(;b!=a*a;b++){x=b%a;y=b/a;c=1;while(c&&x||y){c&=!(x%3&1&&y%3&1);x/=3;y/=3;}putchar(c);}}
PACMAN
OVERVIEW
This is not a pizza. Obviously this is a tribute to the famous PAC MAN game.
BUILD
$(CC) prog.c -lSDL -o prog
RUN
cat level-ioccc | ./prog && echo YOU WIN!
Or
cat level-classic | ./prog && echo YOU WIN!
The program return zero if you win, not-zero if you are a loser.
FEATURES
This simple program is a partial implementation of the original PAC MAN . The gameplay is a bit ' different : Ghosts , once eaten , never become two eyes and never return ghosts . This difference made the game easier.
The program does not count the lives or points . Just wait until the player dies or wins ( by collecting all points / coins ) .
The program does not implement a traditional pathfinding algorithm , but use one that I wrote specifically for the event ( see chapter Pathfinding ) .
The description of the level is read from stdin so you can customize what you want . You can add ghosts , walls and dots .
The game sprites are contained in a single bitmap that you can change, if you like.
LEVEL DESCRIPTION
Each line must be 21 characters long.
These are the supported characters:
- SPACE mean empty cell
- ! is the position of PAC MAN
- & is the first ghost
- ' is the second ghost
- ( is the third ghost
- ) is the forth ghost
- * is one dot
- + is one pearl. When PAC MAN eat the pearl the ghosts become eatable for some seconds. When the ghosts are eatable they try to reach the safe zone where only ghosts can enter
- / is a wall that only ghosts can walk throught (the pink wall)
- 0 is the first type of wall
- 1 is the second type of wall
- 3,4,5 and following characters are different types of walls. If you modify the image, you can add more sprites, with the limit of 68 walls.
PATHFINDING
Instead of implementing one of the standard pathfinding algorithms i've decided to write a cooperative pathfinding algorithm that use a single weighted map for all ghosts. The code is small and seems to do the job.
The algorithm follow these three rules:
-
every time the player moves, the global weighted table is computed using this formula:
cell.weight = manhattan_distance(cell.pos, pacman.pos)
If the cell is a wall its weight is infinitely great.
- each ghost moves to one of its nearest cells (up, down, left, right), choosing the one with the lowest weight
- when a ghost leaves a cell, the cell weight is multiplied by two
NOTES
The program will not terminate until the player win or dies. Press ESCAPE to quit.
Two examples of levels build for this awesome and clearly clean program:
CHIP8
OVERVIEW
As you can see , it is an emulator CHIP8. CHIP8 is an old virtual machine used in the 70s and 80s. It was used inside the VIP COSMAC , TELMAC 1800 and in some other microcomputer.
CHIP8 virtual machine has this features:
- 4K of RAM
- 16 8bit registers
- call stack
- single audio tone generation
- 2 programmable timers: one for sounds and one for delays
- 64x32 screen monochromatic
- 16 keys for keyboard input. This is the keyboard layout:
1 2 3 C 4 5 6 D 7 8 9 E A 0 B F
BUILD
$(CC) prog.c -lSDL -o prog
RUN
cat BRIX | ./prog
You can try one of these games (downloaded from here):
- 15PUZZLE the game of 15
- BLINKY a Pac Man clone
- BRIX a Breakout clone
- INVADERS a Space Invaders clone
- MAZE a maze generator
- TICTAC a Tic Tac Toe game
- TETRIS a Tetris clone
(DE)OBFUSCATION
The main obfuscation tricks is to encode the instruction set inside the V string:
*V="`__m__`__mm________`_____a_____b___`_c___`ad___a_e___`_f___"
"`ag___aag__`aag__aaag__baag__caag__daag__eaag__faag__maah_"
"__a_i_____j_____k___`_l___bbm_hmabm_i`abn__fabn__iabn_`dab"
"n_`gabn_`mabn_ahabn_bbabn_ddabn_eda"
This string is a simple sequence encoded in base16. If you decodes it correctly you obtain this:
*V="100E00100EE000000001000002000003000104000125000206000107000"
"12800022800122800222800322800422800522800622800722800E2290"
"0020A00000B00000C00010D00033E09E23E0A123F00723F00A23F01523"
"F01823F01E23F02923F03323F05523F0652"
Each subsequence of 6 characters contain these informations:
1 00E0 0
| |__| |
| | +-- instruction parameters format (0=_NNN,
| | 1=_XNN,
| | 2=_XY_,
| | 3=_XYN)
| |
| +---- instruction opcode
|
+--------- instruction mask (0=1111000000000000,
1=1111111111111111,
2=1111000000001111,
3=1111000011111111)
With these informations is pretty simple to recognize each one of the 35 instructions of the CHIP8, by searching a match inside the V string. This solution is obviously really slow but the resulting code is pretty fun. This is the main switch used to decode one instruction, rewritten using the _ macro:
#define _ ;}else if(((o=0),(c=*n++-95),\
k(12),k(8),k(4),k(0),\
(f=*n++-95),1)&&(q&r[c])==o){\
s[f]();
void instruction_set_switch() {
if (0) {
_ _ _ _ _
_ _ _ _ _
_ _ _ _ _
_ _ _ _ _
_ _ _ _ _
_ _ _ _ _
}
}
From here you can de obfuscate the rest of the program. It's pretty simple to do... don't you think? :D
NOTES
You can slow down the emulator by increasing the parameter of
SDL_Delay(3);
You can change the zoom factor of the screen by editing this variable
I=4
SUBLEQ
Some INFO extracted from the official DOCS
OVERVIEW
This is a simple SUBLEQ emulator. It also embeds a SUBLEQ interpreter writen in SUBLEQ.
SUBLEQ is a simple OISC machine: A one instruction set computer (OISC), sometimes called an ultimate reduced instruction set computer (URISC), is an abstract machine that uses only one instruction [...] an OISC is capable of being a universal computer in the same manner as traditional computers that have multiple instructions.
SUBLEQ instruction is defined like this:
The subleq instruction ("SUbtract and Branch if Less than or EQual to zero") subtracts the contents at address A from the contents at address B, stores the result at address B, and then, if the result is not positive, transfers control to address C (if the result is positive, execution proceeds to the next instruction in sequence)
A SUBLEQ instruciton looks like this:
A B C
This emulator execute its input until the program jump to the address -1 (C==-1).
This emulator can also read values from stdin, write to stdout and allocate some memory. To do that i've overloaded the original meaning of the SUBLEQ instruction by adding two special memory addresses: -1 and -2. These addresses must be used like that:
-
A -1 C
write the number stored in A to stdout and jump to C.
-
A -2 C
Write the character code stored in A to the stdout and jump to C
-
-1 B C
Read a number from stdin, save it to B and jump to C
-
-2 B C
Allocate 1000 bytes of memory, save the address of the allocated memory to B and jump to C
To terminate the sourcecode of your program you must use the magic number:
-65535
Your programs cannot be greater than 64 kilobytes of RAM.