-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathast.h
141 lines (127 loc) · 3.38 KB
/
ast.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
// ast.h: Contains the definition for the AST types die and pattern
#pragma once
#include "set.h"
#include "util.h"
#define NUL ((char)0)
/** non-utf8 char that marks an integer token */
#define INT ((char)-2)
/** non-utf8 char that marks a zero */
#define ZERO ((char)-3)
// equivalent to (char)-4
#define UPUP '\xFC'
// equivalent to (char)-5
#define __ '\xFB'
// equivalent to (char)-6
#define UP_BANG '\xFA'
// equivalent to (char)-7
#define LT_EQ '\xF9'
// equivalent to (char)-8
#define GT_EQ '\xF8'
// equivalent to (char)-9
#define NEQ '\xF7'
// equivalent to (char)-10
#define UP_DOLLAR '\xF6'
// equivalent to (char)-11
#define DOLLAR_UP '\xF5'
// equivalent to (char)-12
#define SLASH_SLASH '\xF4'
/** All valid relational operators (also binary operators) */
#define RELOPS "<>=\xF9\xF8\xF7"
/** All valid binary operators */
#define BIOPS "+-*x/?" RELOPS "\xFC\xFB\xF4"
/** All valid unary operators */
#define SELECT "^_\xFA\xF6\xF5"
/** All valid reroll operators */
#define REROLLS "~\\"
/** All valid unary operators */
#define UOPS SELECT REROLLS "!$d("
/** All valid values for `Die.op` */
#define OPS BIOPS UOPS "@[:"
/** represents a die expression as a syntax tree */
struct Die
{
char op;
union
{
// valid if op == ':'
struct { struct Die *cond, *then, *otherwise; } ternary;
// valid if op in BIOPS
struct { struct Die *l, *r; } biop;
// valid if op in SELECT
struct { struct Die *v; int sel, of, bust; } select;
/** valid if op in REROLLS*/
struct
{
/** The die to roll on */
struct Die *v;
/** The results to reroll */
struct Pattern *pat;
} reroll;
// valid if op is '$'
struct { struct Die *v; int rounds; } explode;
// valid if op is '['
struct {
struct Die *v;
/** The length of patterns and actions */
int cases;
/** The patterns that are matched against */
struct Pattern *patterns;
/** The dice rolled when the corresponding pattern matches.
May be NULL to indicate a pattern check rather than match. */
struct Die *actions;
} match;
// valid if op in UOPS
struct Die *unop;
// valid if op == INT
int constant;
};
};
/* Patterns are one of:
rel := '<' | '>' | '>=' | '<=' | '=' | '/=' ;
P := T
| F
| SET
| rel DIE
;
MATCHES := P DIE
| MATCHES ';' MATCHES
;
MATCH := '[' MATCHES ']' ;
*/
struct Pattern
{
/** The comparison operator, or 0 if this is a set pattern */
char op;
union
{
/** Valid if op is 0 */
struct SetPattern
{
/** Values to match against */
struct Set entries;
/** Whether this filter is negated */
bool negated;
/** Whether the special ranges `_` or `^` are included */
bool hasMin, hasMax;
} set;
/** A die to compare against, if op is in RELOPS */
struct Die die;
};
};
/** The ratio of crits needed to explode */
#define EXPLODE_RATIO 2
CLONE_SIG(d_clone, struct Die);
CLONE_SIG(pt_clone, struct Pattern)
/** Frees all resources used by a die expression. */
void d_free(struct Die die);
void d_freeP(struct Die *die);
/** Prints the given die expression, approximating the input format */
void d_print(const struct Die *d);
/** Prints the syntax tree of the given die expression
@param d a die expression
@param depth how deep the current expression should be indented, i.e. how many indirections were taken
*/
void d_printTree(const struct Die *d, int depth);
void pt_free(struct Pattern pt);
void pt_print(struct Pattern p);
void pt_freeP(struct Pattern *p);