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
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
|
#ifndef WP_PARSER_Y_H_
#define WP_PARSER_Y_H_
#include <AMReX_GpuQualifiers.H>
#include <AMReX_REAL.H>
#ifdef __cplusplus
#include <cstdlib>
extern "C" {
#else
#include <stdlib.h>
#endif
enum wp_f1_t { // Bulit-in functions with one argument
WP_SQRT = 1,
WP_EXP,
WP_LOG,
WP_LOG10,
WP_SIN,
WP_COS,
WP_TAN,
WP_ASIN,
WP_ACOS,
WP_ATAN,
WP_SINH,
WP_COSH,
WP_TANH,
WP_ABS,
WP_POW_M3,
WP_POW_M2,
WP_POW_M1,
WP_POW_P1,
WP_POW_P2,
WP_POW_P3
};
enum wp_f2_t { // Built-in functions with two arguments
WP_POW = 1,
WP_GT,
WP_LT,
WP_GEQ,
WP_LEQ,
WP_EQ,
WP_NEQ,
WP_AND,
WP_OR,
WP_HEAVISIDE,
WP_MIN,
WP_MAX
};
enum wp_node_t {
WP_NUMBER = 1,
WP_SYMBOL,
WP_ADD,
WP_SUB,
WP_MUL,
WP_DIV,
WP_NEG,
WP_F1,
WP_F2,
WP_ADD_VP, /* types below are generated by optimization */
WP_ADD_PP,
WP_SUB_VP,
WP_SUB_PP,
WP_MUL_VP,
WP_MUL_PP,
WP_DIV_VP,
WP_DIV_PP,
WP_NEG_P
};
/* In C, the address of the first member of a struct is the same as
* the address of the struct itself. Because of this, all struct wp_*
* pointers can be passed around as struct wp_node pointer and enum
* wp_node_t type can be safely checked to determine their real type.
*/
union wp_ip {
int i;
amrex_real* p;
};
union wp_vp {
amrex_real v;
union wp_ip ip;
};
struct wp_node {
enum wp_node_t type;
struct wp_node* l;
struct wp_node* r;
union wp_vp lvp; // After optimization, this may store left value/pointer.
union wp_ip rip; // this may store right pointer.
};
struct wp_number {
enum wp_node_t type;
amrex_real value;
};
struct wp_symbol {
enum wp_node_t type;
char* name;
union wp_ip ip;
};
struct wp_f1 { /* Builtin functions with one argument */
enum wp_node_t type;
struct wp_node* l;
enum wp_f1_t ftype;
};
struct wp_f2 { /* Builtin functions with two arguments */
enum wp_node_t type;
struct wp_node* l;
struct wp_node* r;
enum wp_f2_t ftype;
};
/*******************************************************************/
/* These functions are used in bison rules to generate the original
* AST. */
void wp_defexpr (struct wp_node* body);
struct wp_node* wp_newnumber (amrex_real d);
struct wp_symbol* wp_makesymbol (char* name);
struct wp_node* wp_newsymbol (struct wp_symbol* sym);
struct wp_node* wp_newnode (enum wp_node_t type, struct wp_node* l,
struct wp_node* r);
struct wp_node* wp_newf1 (enum wp_f1_t ftype, struct wp_node* l);
struct wp_node* wp_newf2 (enum wp_f2_t ftype, struct wp_node* l,
struct wp_node* r);
AMREX_GPU_HOST_DEVICE
void yyerror (char const *s, ...);
/*******************************************************************/
/* This is our struct for storing AST in a more packed way. The whole
* tree is stored in a contiguous chunk of memory starting from void*
* p_root with a size of sz_mempool.
*/
struct wp_parser {
void* p_root;
void* p_free;
struct wp_node* ast;
size_t sz_mempool;
};
struct wp_parser* wp_parser_new (void);
void wp_parser_delete (struct wp_parser* parser);
struct wp_parser* wp_parser_dup (struct wp_parser* source);
struct wp_node* wp_parser_ast_dup (struct wp_parser* parser, struct wp_node* src, int move);
void wp_parser_regvar (struct wp_parser* parser, char const* name, amrex_real* p);
void wp_parser_regvar_gpu (struct wp_parser* parser, char const* name, int i);
void wp_parser_setconst (struct wp_parser* parser, char const* name, amrex_real c);
/* We need to walk the tree in these functions */
void wp_ast_optimize (struct wp_node* node);
size_t wp_ast_size (struct wp_node* node);
void wp_ast_print (struct wp_node* node);
void wp_ast_regvar (struct wp_node* node, char const* name, amrex_real* p);
void wp_ast_regvar_gpu (struct wp_node* node, char const* name, int i);
void wp_ast_setconst (struct wp_node* node, char const* name, amrex_real c);
AMREX_GPU_HOST_DEVICE amrex_real wp_call_f1 (enum wp_f1_t type, amrex_real a);
AMREX_GPU_HOST_DEVICE amrex_real wp_call_f2 (enum wp_f2_t type, amrex_real a, amrex_real b);
#ifdef __cplusplus
}
#endif
#endif
|