RAPID_CodeGen.jrag 11.8 KB
Newer Older
1
2
3
4
5
6
7
8
9

aspect RAPID_env {
	public class RAPID_env {
		private String prefix;
		private StringBuilder types;
		private StringBuilder constants;
		private StringBuilder procedures;
		private PrintStream ps;

10
		public RAPID_env(PrintStream ps, String prefix)
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
		{
			this.types = new StringBuilder();
			this.constants = new StringBuilder();
			this.procedures = new StringBuilder();
			this.prefix = prefix;
			this.ps = ps;
		}

		public String prefix() { return this.prefix; }

		public String addRecord(String name, java.util.List<String> components)
		{
			String recordName = this.prefix + "_" + name;
			types.append("\tRECORD " + recordName);
			types.append("\n");
			for (String c : components) {
				types.append("\t\t" + c + "\n");
			}
			types.append("\tENDRECORD");
			types.append("\n\n");
			return recordName;
		}

		public void addConstant(String type, String name, String value) {
			this.constants.append("\tLOCAL CONST " + type + " " + name +
					" := " + value + ";\n");
		}

		public void addProc(String name, java.util.List<String> params,
					java.util.List<String> stmts)
		{
			this.procedures.append("\tLOCAL PROC " + name + "(");
			for (int i = 0; i < params.size(); i++) {
				this.procedures.append(params.get(i));
				if (i < params.size() - 1) {
					this.procedures.append(", ");
				}
			}
			this.procedures.append(")\n");
			for (String stmt : stmts) {
				this.procedures.append("\t\t" + stmt + "\n");
			}
			this.procedures.append("\tERROR\n\t\tRAISE ;\n\tENDPROC\n\n");
		}

		public void flush()
		{
			ps.println("MODULE " + prefix() + "(SYSMODULE)");
			ps.println();
			ps.print(types.toString());
			ps.println();
			ps.println("\tLOCAL CONST string prefix:=\"" + this.prefix + "\";");
			ps.print(constants.toString());
			ps.println();
			ps.print(procedures.toString());
			ps.println();
			ps.print("ENDMODULE");
		}
	}
}

aspect RAPID_CodeGen {

	public void ASTNode.RAPID_gen(RAPID_env env) {
		throw new UnsupportedOperationException();
	}

78
	public void Program.RAPID_gen(String file, String prefix)
79
80
81
			throws IOException
	{
		PrintStream ps = new PrintStream(new FileOutputStream(new File(file)));
82
		RAPID_env env = new RAPID_env(ps, prefix);
83
84
85
86
87
88
89
90
91
92
93
94
		RAPID_gen(env);
	}

	public void Program.RAPID_gen(RAPID_env env)
	{
		for (int i = 0; i < getNumDecl(); i++) {
			getDecl(i).RAPID_gen(env);
		}
		env.flush();
	}

	public void Decl.RAPID_gen(RAPID_env env) {
95
		throw new UnsupportedOperationException("RAPID code generation (currently) does not support "+getClass().getSimpleName());
96
97
	}

98
99
100
101
102
103
104
105
	public void TypeDecl.RAPID_gen(RAPID_env env) {
		System.out.println("***WARNING! TypeDecl.RapidGen(.) a NOP after sig reorganization.");
		System.out.println("            (Tell a developer to) remove this warning when tested");
	}

	public void Decl.RAPID_emitFlatSignature(RAPID_env env, String sig_len_name, String sig_name) {
		System.out.println("***WARNING! Code not tested after reorganization of signatures.");
		System.out.println("            (Tell a developer to) remove this warning when tested");
106
		SignatureList sig = flatSignature(2006);
107
108
109
110
111
		StringBuilder sb = new StringBuilder();
		sb.append("[");
		byte[] d = null;
		int sig_len = 0;
		for (int i = 0; i < sig.size(); i++) {
112
			d = sig.getData(i, 2006);
113
114
115
116
117
118
119
120
121
			for (int j = 0; d != null && j < d.length; j++) {
				sb.append(d[j] + ",");
				sig_len++;
			}
		}
		sb.delete(sb.length() - 1, sb.length());
		sb.append("]");
		env.addConstant("num", sig_len_name, "" + sig_len);
		env.addConstant("byte", sig_name + "{" + sig_len_name + "}",
122
123
124
125
126
127
128
129
130
131
132
133
		sb.toString());
	} 

	public void SampleDecl.RAPID_gen(RAPID_env env) {
		// Add type declarations
		String fullName = getType().RAPID_AddType(env, getName());
		// Add signature constants
		String sig_len_name = "signature_len_" + getName();
		String sig_name = "signature_" + getName();

		RAPID_emitFlatSignature(env, sig_len_name, sig_name);

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
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
		// Add decode procedures
		ArrayList<String> params = new ArrayList<String>();
		ArrayList<String> stmts = new ArrayList<String>();
		params.add("VAR LabComm_Decoder_Sample s");
		params.add("string handler");
		stmts.add("s.prefix := prefix;");
		stmts.add("s.name := \"" + getName() + "\";");
		stmts.add("s.handler := handler;");
		env.addProc("Dec_Reg_" + getName(), params, stmts);	

		params.clear();
		stmts.clear();
		params.add("VAR LabComm_Decoder_Sample s");
		params.add("VAR rawbytes sig");
		params.add("num user_id");
		stmts.add("VAR byte tmp_sig{" + sig_len_name + "};");
		stmts.add("IF RawBytesLen(sig)<>" + sig_len_name + " THEN");
		stmts.add("\tRETURN;");
		stmts.add("ENDIF");
		stmts.add("FOR i FROM 1 TO " + sig_len_name + " DO");
		stmts.add("\tUnpackRawBytes sig, i, tmp_sig{i}, \\Hex1;");
		stmts.add("ENDFOR");
		stmts.add("IF tmp_sig<>" + sig_name + " THEN");
		stmts.add("\tRETURN;");
		stmts.add("ENDIF");
		stmts.add("s.user_id := user_id;");
		env.addProc("Reg_If_Signature_Of_" + getName(), params, stmts);

		params.clear();
		stmts.clear();
		params.add("VAR Decoder d");
		params.add("VAR LabComm_Stream st");
		params.add("VAR LabComm_Decoder_Sample s");
		stmts.add("VAR " + fullName + " tmp;");
		getType().RAPID_AddDecodeInstr(env, stmts, "tmp", "st");
		stmts.add("% s.handler % tmp;");
		env.addProc("Decode_And_Handle_" + getName(), params, stmts);

		params.clear();
		stmts.clear();
		params.add("VAR Encoder e");
		params.add("VAR LabComm_Stream st");
		params.add("VAR LabComm_Encoder_Sample s");
		stmts.add("s.prefix := prefix;");
		stmts.add("s.name := \"" + getName() + "\";");
		stmts.add("Encoder_Register_Sample e, st, s;");
		env.addProc("Enc_Reg_" + getName(), params, stmts);

		params.clear();
		stmts.clear();
		params.add("VAR Encoder e");
		params.add("VAR LabComm_Stream s");
		stmts.add("VAR rawbytes buffer;");
		stmts.add("FOR i FROM 1 TO " + sig_len_name + " DO");
		stmts.add("\tPackRawBytes " + sig_name +
					"{i}, buffer, \\Network, i, \\Hex1;");
		stmts.add("ENDFOR");
		stmts.add("SocketSend s.soc, \\RawData:=buffer, \\NoOfBytes:=" +
					sig_len_name + ";");
		env.addProc("Encode_Signature_" + getName(), params, stmts);

		params.clear();
		stmts.clear();
		params.add("VAR Encoder e");
		params.add("VAR LabComm_Stream st");
		params.add("VAR LabComm_Encoder_Sample s");
		params.add("VAR " + fullName + " val");
		stmts.add("Encode_Packed st, s.user_id;");
		getType().RAPID_AddEncodeInstr(env, stmts, "val", "st");
		env.addProc("Encode_" + getName(), params, stmts);
	}

	public String Type.RAPID_AddType(RAPID_env env, String name) {
207
		throw new UnsupportedOperationException("RAPID code generation does (currently) not support "+getClass().getSimpleName());
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
	}

	public String StructType.RAPID_AddType(RAPID_env env, String name) {
		ArrayList<String> components = new ArrayList<String>();
		for (int i = 0; i < getNumField(); i++) {
			Field f = getField(i);
			components.add(
					f.getType().RAPID_AddType(env, name + "_" + f.getName()) +
					" " + f.getName() + ";");
		}
		String typeName = env.addRecord(name, components);
		return typeName;
	}

	public String FixedArrayType.RAPID_AddType(RAPID_env env, String name) {
		String typeName = getType().RAPID_AddType(env, name + "_e");
		if (getNumExp() > 1) {
225
			throw new UnsupportedOperationException("RAPID generation only (currently) supports one-dimensional arrays");
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
		}
		ArrayList<String> components = new ArrayList<String>();
		for (int i = 1; i <= getExp(0).RAPID_getValue(); i++) {
			components.add(typeName + " e" + i + ";");
		}
		String completeName = env.addRecord("list_" + name, components);
		return completeName;
	}

	public String PrimType.RAPID_AddType(RAPID_env env, String name) {
		if (getToken() == LABCOMM_SHORT ||
			getToken() == LABCOMM_FLOAT ||
			getToken() == LABCOMM_INT) {
			return "num";
		} else if (getToken() == LABCOMM_LONG) {
			return "dnum";
		} else if (getToken() == LABCOMM_STRING) {
			return "string";
		} else if (getToken() == LABCOMM_BOOLEAN) {
			return "bool";
		} else if (getToken() == LABCOMM_BYTE) {
			return "byte";
		}
249
		throw new UnsupportedOperationException("RAPID code generation does not (currently) support "+getName());
250
251
252
253
254
	}

	public void Type.RAPID_AddDecodeInstr(RAPID_env env,
			java.util.List<String> instrs,
			String var_name, String stream_name) {
255
		throw new UnsupportedOperationException("RAPID code generation does not (currently) support "+getClass().getSimpleName());
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
	}

	public void StructType.RAPID_AddDecodeInstr(RAPID_env env,
			java.util.List<String> instrs,
			String var_name, String stream_name) {
		for (int i = 0; i < getNumField(); i++) {
			getField(i).getType().RAPID_AddDecodeInstr(env, instrs,
					var_name + "." + getField(i).getName(), stream_name);
		}
	}

	public void FixedArrayType.RAPID_AddDecodeInstr(RAPID_env env,
			java.util.List<String> instrs,
			String var_name, String stream_name) {
		for (int i = 1; i <= getExp(0).RAPID_getValue(); i++) {
			getType().RAPID_AddDecodeInstr(env, instrs,
					var_name + ".e" + i, stream_name);
		}
	}

	public void PrimType.RAPID_AddDecodeInstr(RAPID_env env,
			java.util.List<String> instrs,
			String var_name, String stream_name) {
		switch(getToken()) {
			case LABCOMM_BYTE:
				instrs.add("Decode_Byte " + stream_name + "," + var_name + ";");
				break;
			case LABCOMM_BOOLEAN:
				instrs.add("Decode_Bool " + stream_name + "," + var_name + ";");
				break;
			case LABCOMM_SHORT:
				instrs.add("Decode_Short " + stream_name + "," + var_name + ";");
				break;
			case LABCOMM_INT:
				instrs.add("Decode_Int " + stream_name + "," + var_name + ";");
				break;
			case LABCOMM_LONG:
				instrs.add("Decode_Long " + stream_name + "," + var_name + ";");
				break;
			case LABCOMM_FLOAT:
				instrs.add("Decode_Float " + stream_name + "," + var_name + ";");
				break;
			case LABCOMM_STRING:
				instrs.add("Decode_String " + stream_name + "," + var_name + ";");
				break;
			default:
302
				throw new UnsupportedOperationException("RAPID code generation does not (currently) support "+getName());
303
304
305
306
307
308
		}
	}

	public void Type.RAPID_AddEncodeInstr(RAPID_env env,
			java.util.List<String> instrs,
			String var_name, String stream_name) {
309
		throw new UnsupportedOperationException("RAPID code generation does not (currently) support "+getClass().getSimpleName());
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
	}

	public void StructType.RAPID_AddEncodeInstr(RAPID_env env,
			java.util.List<String> instrs,
			String var_name, String stream_name) {
		for (int i = 0; i < getNumField(); i++) {
			getField(i).getType().RAPID_AddEncodeInstr(env, instrs,
					var_name + "." + getField(i).getName(), stream_name);
		}
	}

	public void FixedArrayType.RAPID_AddEncodeInstr(RAPID_env env,
			java.util.List<String> instrs,
			String var_name, String stream_name) {
		for (int i = 1; i <= getExp(0).RAPID_getValue(); i++) {
			getType().RAPID_AddEncodeInstr(env, instrs,
					var_name + ".e" + i, stream_name);
		}
	}

	public void PrimType.RAPID_AddEncodeInstr(RAPID_env env,
			java.util.List<String> instrs,
			String var_name, String stream_name) {
		switch(getToken()) {
			case LABCOMM_BYTE:
				instrs.add("Encode_Byte " + stream_name + "," + var_name + ";");
				break;
			case LABCOMM_BOOLEAN:
				instrs.add("Encode_Bool " + stream_name + "," + var_name + ";");
				break;
			case LABCOMM_SHORT:
				instrs.add("Encode_Short " + stream_name + "," + var_name + ";");
				break;
			case LABCOMM_INT:
				instrs.add("Encode_Int " + stream_name + "," + var_name + ";");
				break;
			case LABCOMM_LONG:
				instrs.add("Encode_Long " + stream_name + "," + var_name + ";");
				break;
			case LABCOMM_FLOAT:
				instrs.add("Encode_Float " + stream_name + "," + var_name + ";");
				break;
			case LABCOMM_STRING:
				instrs.add("Encode_String " + stream_name + "," + var_name + ";");
				break;
			default:
356
				throw new UnsupportedOperationException("RAPID code generation does not (currently) support "+getName());
357
358
359
360
		}
	}

	public int Exp.RAPID_getValue() {
361
		throw new UnsupportedOperationException("RAPID code generation does not (currently) support "+getClass().getSimpleName());
362
363
364
365
366
367
	}

	public int IntegerLiteral.RAPID_getValue() {
		return Integer.parseInt(getValue());
	}
}