A little reshuffling and improving of READMEs and notes.
Chris Pressey
3 years ago
2 | 2 |
|
3 | 3 |
_Version 0.21. Work-in-progress, everything is subject to change._
|
4 | 4 |
|
|
5 |
**SixtyPical** brings [extended static checking][] to the [6502][].
|
|
6 |
|
5 | 7 |
**SixtyPical** is a [low-level](#low-level) programming language
|
6 | |
supporting a sophisticated [static analysis](#static-analysis).
|
|
8 |
supporting some advanced [static analysis](#static-analysis) methods.
|
7 | 9 |
Its reference compiler can generate [efficient code](#efficient-code) for
|
8 | 10 |
several 6502-based [target platforms](#target-platforms) while catching many
|
9 | 11 |
common mistakes at compile-time, reducing the time spent in debugging.
|
|
123 | 125 |
* [Output formats supported by `sixtypical`](doc/Output%20Formats.md)
|
124 | 126 |
* [TODO](TODO.md)
|
125 | 127 |
|
|
128 |
[6502]: https://en.wikipedia.org/wiki/MOS_Technology_6502
|
126 | 129 |
[MOS Technology 6502]: https://en.wikipedia.org/wiki/MOS_Technology_6502
|
|
130 |
[extended static checking]: https://en.wikipedia.org/wiki/Extended_static_checking
|
127 | 131 |
[effect system]: https://en.wikipedia.org/wiki/Effect_system
|
128 | 132 |
[abstractly interprets]: https://en.wikipedia.org/wiki/Abstract_interpretation
|
129 | 133 |
[calling conventions]: https://en.wikipedia.org/wiki/Calling_convention
|
54 | 54 |
constraints might be violated in this case. We should probably disallow
|
55 | 55 |
recursion by default. (Which means assembling the callgraph in all cases.)
|
56 | 56 |
|
|
57 |
However note, it's okay for a routine to goto itself. It's a common
|
|
58 |
pattern for implementing a state machine, for a routine to tail-goto a
|
|
59 |
vector, which might contain the address of the same routine.
|
|
60 |
|
|
61 |
The problems only come up, I think, when a routine calls itself re-entrantly.
|
|
62 |
|
|
63 |
So the callgraph would need to distinguish between these two cases.
|
|
64 |
|
57 | 65 |
### Analyze memory usage
|
58 | 66 |
|
59 | 67 |
If you define two variables that occupy the same address, an analysis error ought
|
|
82 | 90 |
For analysis errors, there is a line number, but it's the line of the routine
|
83 | 91 |
after the routine in which the analysis error occurred. Fix this.
|
84 | 92 |
|
|
93 |
### Better selection of options
|
|
94 |
|
|
95 |
`-O` should turn on the standard optimizations.
|
|
96 |
|
|
97 |
There should maybe be a flag to turn off tail-call optimization.
|
|
98 |
|
|
99 |
Some options should automatically add the appropriate architecture include
|
|
100 |
directory to the path.
|
|
101 |
|
|
102 |
Distribution
|
|
103 |
------------
|
|
104 |
|
|
105 |
### Demo game
|
|
106 |
|
|
107 |
Seems you're not be able to get killed unless you go off the top or bottom of
|
|
108 |
the screen? In particular, you cannot collide with a bar?
|
|
109 |
|
85 | 110 |
Blue-skying
|
86 | 111 |
-----------
|
87 | 112 |
|
12 | 12 |
In the [c64](c64/) directory are programs that run on the Commodore 64.
|
13 | 13 |
The directory itself contains some simple demos, for example
|
14 | 14 |
[hearts.60p](c64/hearts.60p), while there are subdirectories for more
|
15 | |
elaborate demos:
|
16 | |
|
17 | |
* [demo-game](c64/demo-game/): a little game-like program written as a
|
18 | |
"can we write something you'd see in practice?" test case for SixtyPical.
|
19 | |
|
20 | |
* [ribos](c64/ribos/): a well-commented example of a C64 raster interrupt
|
21 | |
routine. Originally written with the P65 assembler (which has since
|
22 | |
been reborn as [Ophis][]).
|
23 | |
|
24 | |
The second version of Ribos has been translated to SixtyPical.
|
25 | |
|
26 | |
* [petulant](c64/petulant/): "The PETulant Cursor", a tiny (44 bytes)
|
27 | |
"display hack". Originally written in the late 80's. Rewritten with
|
28 | |
the P65 assembler (now Ophis) and re-released on April 1st, 2008 (a
|
29 | |
hint as to its nature).
|
30 | |
|
31 | |
Translated to SixtyPical (in 2018), after adding some optimizations
|
32 | |
to the SixtyPical compiler, the resulting executable is still 44 bytes!
|
|
15 |
elaborate demos, like the flagship demo game. See
|
|
16 |
[the README in that directory](c64/README.md) for details.
|
33 | 17 |
|
34 | 18 |
### vic20
|
35 | 19 |
|
0 | 0 |
This directory contains SixtyPical example programs
|
1 | 1 |
specifically for the Commodore 64.
|
2 | 2 |
|
3 | |
See the [README in the parent directory](../README.md) for
|
4 | |
more information on these example programs.
|
|
3 |
There are subdirectories for more elaborate demos:
|
|
4 |
|
|
5 |
* [demo-game](demo-game/): a little game-like program written as a
|
|
6 |
"can we write something you'd see in practice?" test case for SixtyPical.
|
|
7 |
|
|
8 |
* [ribos](ribos/): a well-commented example of a C64 raster interrupt
|
|
9 |
routine. Originally written with the P65 assembler (which has since
|
|
10 |
been reborn as [Ophis][]).
|
|
11 |
|
|
12 |
The second version of Ribos has been translated to SixtyPical.
|
|
13 |
|
|
14 |
* [petulant](petulant/): "The PETulant Cursor", a tiny (44 bytes)
|
|
15 |
"display hack". Originally written in the late 80's. Rewritten with
|
|
16 |
the P65 assembler (now Ophis) and re-released on April 1st, 2008 (a
|
|
17 |
hint as to its nature).
|
|
18 |
|
|
19 |
Translated to SixtyPical (in 2018), after adding some optimizations
|
|
20 |
to the SixtyPical compiler, the resulting executable is still 44 bytes!
|
|
21 |
|
|
22 |
[Ophis]: http://michaelcmartin.github.io/Ophis/
|
1 | 1 |
// * Demo Game for SixtyPical *
|
2 | 2 |
// ****************************
|
3 | 3 |
|
4 | |
include "joy2delta.60p"
|
|
4 |
include "joystick.60p"
|
5 | 5 |
|
6 | 6 |
// ----------------------------------------------------------------
|
7 | 7 |
// Type Definitions
|
|
102 | 102 |
// Utility Routines
|
103 | 103 |
// ----------------------------------------------------------------
|
104 | 104 |
|
105 | |
// You can repeatedly (i.e. as part of actor logic or an IRQ handler)
|
106 | |
// call this routine.
|
107 | |
// Upon return, if carry is set, the button was pressed then released.
|
108 | |
|
109 | |
define check_button routine
|
110 | |
inputs joy2
|
111 | |
outputs c
|
112 | |
trashes a, z, n
|
113 | |
static byte button_down : 0
|
114 | |
{
|
115 | |
ld a, button_down
|
116 | |
if z {
|
117 | |
ld a, joy2
|
118 | |
and a, $10
|
119 | |
if z {
|
120 | |
ld a, 1
|
121 | |
st a, button_down
|
122 | |
}
|
123 | |
st off, c
|
124 | |
} else {
|
125 | |
ld a, joy2
|
126 | |
and a, $10
|
127 | |
if not z {
|
128 | |
ld a, 0
|
129 | |
st a, button_down
|
130 | |
st on, c
|
131 | |
} else {
|
132 | |
st off, c
|
133 | |
}
|
134 | |
}
|
135 | |
}
|
136 | |
|
137 | 105 |
define clear_screen routine
|
138 | 106 |
outputs screen, colormap
|
139 | 107 |
trashes a, y, c, n, z
|
|
0 |
#!/bin/sh
|
|
1 |
|
|
2 |
# This script builds and runs the demo game. You need
|
|
3 |
# the VICE emulatore installed, in particular VICE's x64.
|
|
4 |
|
|
5 |
# You might want a `vicerc` file like the following:
|
|
6 |
# [C64]
|
|
7 |
# VICIIDoubleScan=0
|
|
8 |
# VICIIDoubleSize=0
|
|
9 |
# KeySet1NorthWest=0
|
|
10 |
# KeySet1North=273
|
|
11 |
# KeySet1NorthEast=0
|
|
12 |
# KeySet1East=275
|
|
13 |
# KeySet1SouthEast=0
|
|
14 |
# KeySet1South=274
|
|
15 |
# KeySet1SouthWest=0
|
|
16 |
# KeySet1West=276
|
|
17 |
# KeySet1Fire=306
|
|
18 |
# KeySetEnable=1
|
|
19 |
# JoyDevice1=0
|
|
20 |
# JoyDevice2=2
|
|
21 |
|
|
22 |
../../../bin/sixtypical --run-on x64 -I ../../../include/c64/ demo-game.60p
|
|
0 |
include "joystick.60p"
|
|
1 |
|
|
2 |
word screen @ 1024
|
|
3 |
|
|
4 |
define main routine
|
|
5 |
inputs joy2
|
|
6 |
outputs delta
|
|
7 |
trashes a, x, z, n, screen
|
|
8 |
{
|
|
9 |
repeat {
|
|
10 |
call read_stick
|
|
11 |
copy delta, screen
|
|
12 |
ld a, 1
|
|
13 |
} until z
|
|
14 |
}
|
0 | |
include "joy2delta.60p"
|
1 | |
|
2 | |
word screen @ 1024
|
3 | |
|
4 | |
define main routine
|
5 | |
inputs joy2
|
6 | |
outputs delta
|
7 | |
trashes a, x, z, n, screen
|
8 | |
{
|
9 | |
repeat {
|
10 | |
call read_stick
|
11 | |
copy delta, screen
|
12 | |
ld a, 1
|
13 | |
} until z
|
14 | |
}
|
0 | |
byte joy2 @ $dc00
|
1 | |
|
2 | |
word delta
|
3 | |
|
4 | |
define read_stick routine
|
5 | |
inputs joy2
|
6 | |
outputs delta
|
7 | |
trashes a, x, z, n
|
8 | |
{
|
9 | |
ld x, joy2
|
10 | |
ld a, x
|
11 | |
and a, 1 // up
|
12 | |
if z {
|
13 | |
copy $ffd8, delta // -40
|
14 | |
} else {
|
15 | |
ld a, x
|
16 | |
and a, 2 // down
|
17 | |
if z {
|
18 | |
copy word 40, delta
|
19 | |
} else {
|
20 | |
ld a, x
|
21 | |
and a, 4 // left
|
22 | |
if z {
|
23 | |
copy $ffff, delta // -1
|
24 | |
} else {
|
25 | |
ld a, x
|
26 | |
and a, 8 // right
|
27 | |
if z {
|
28 | |
copy word 1, delta
|
29 | |
} else {
|
30 | |
copy word 0, delta
|
31 | |
}
|
32 | |
}
|
33 | |
}
|
34 | |
}
|
35 | |
}
|
|
0 |
byte joy2 @ $dc00
|
|
1 |
|
|
2 |
word delta
|
|
3 |
|
|
4 |
// Read the joystick and compute the delta it represents
|
|
5 |
// in a row-based 40-column grid like the C64's screen.
|
|
6 |
|
|
7 |
define read_stick routine
|
|
8 |
inputs joy2
|
|
9 |
outputs delta
|
|
10 |
trashes a, x, z, n
|
|
11 |
{
|
|
12 |
ld x, joy2
|
|
13 |
ld a, x
|
|
14 |
and a, 1 // up
|
|
15 |
if z {
|
|
16 |
copy $ffd8, delta // -40
|
|
17 |
} else {
|
|
18 |
ld a, x
|
|
19 |
and a, 2 // down
|
|
20 |
if z {
|
|
21 |
copy word 40, delta
|
|
22 |
} else {
|
|
23 |
ld a, x
|
|
24 |
and a, 4 // left
|
|
25 |
if z {
|
|
26 |
copy $ffff, delta // -1
|
|
27 |
} else {
|
|
28 |
ld a, x
|
|
29 |
and a, 8 // right
|
|
30 |
if z {
|
|
31 |
copy word 1, delta
|
|
32 |
} else {
|
|
33 |
copy word 0, delta
|
|
34 |
}
|
|
35 |
}
|
|
36 |
}
|
|
37 |
}
|
|
38 |
}
|
|
39 |
|
|
40 |
// You can repeatedly (i.e. as part of actor logic or an IRQ handler)
|
|
41 |
// call this routine.
|
|
42 |
// Upon return, if carry is set, the button was pressed then released.
|
|
43 |
|
|
44 |
define check_button routine
|
|
45 |
inputs joy2
|
|
46 |
outputs c
|
|
47 |
trashes a, z, n
|
|
48 |
static byte button_down : 0
|
|
49 |
{
|
|
50 |
ld a, button_down
|
|
51 |
if z {
|
|
52 |
ld a, joy2
|
|
53 |
and a, $10
|
|
54 |
if z {
|
|
55 |
ld a, 1
|
|
56 |
st a, button_down
|
|
57 |
}
|
|
58 |
st off, c
|
|
59 |
} else {
|
|
60 |
ld a, joy2
|
|
61 |
and a, $10
|
|
62 |
if not z {
|
|
63 |
ld a, 0
|
|
64 |
st a, button_down
|
|
65 |
st on, c
|
|
66 |
} else {
|
|
67 |
st off, c
|
|
68 |
}
|
|
69 |
}
|
|
70 |
}
|