asar coverage - build #100


src/asar/
File: src/asar/assembleblock.cpp
Date: 2024-01-19 20:26:51
Lines:
1348/1460
92.3%
Functions:
41/41
100.0%
Branches:
1995/3237
61.6%

Line Branch Exec Source
1 #include "addr2line.h"
2 #include "asar.h"
3 #include "assembleblock.h"
4 #include "asar_math.h"
5 #include "macro.h"
6 #include "platform/file-helpers.h"
7 #include "table.h"
8 #include "unicode.h"
9 #include <cinttypes>
10
11 #include "interface-shared.h"
12 #include "arch-shared.h"
13
14 int arch=arch_65816;
15
16 bool snespos_valid = false;
17 int snespos;
18 int realsnespos;
19 int startpos;
20 int realstartpos;
21
22 bool mapper_set = false;
23 bool warn_endwhile = true;
24 int label_counter = 0;
25
26 static int old_snespos;
27 static int old_startpos;
28 static int old_optimizeforbank;
29 static bool old_snespos_valid;
30 static int struct_base;
31 static string struct_name;
32 static string struct_parent;
33 static bool in_struct = false;
34 static bool in_sub_struct = false;
35 static bool static_struct = false;
36 static bool in_spcblock = false;
37
38 assocarr<snes_struct> structs;
39
40 static bool movinglabelspossible = false;
41
42 static bool disable_bank_cross_errors = false;
43 static bool check_half_banks_crossed = false;
44
45 int bytes;
46 static int freespaceuse=0;
47
48 static enum {
49 ratsmeta_ban,
50 ratsmeta_allow,
51 ratsmeta_used,
52 } ratsmetastate=ratsmeta_ban;
53
54 enum spcblock_type{
55 spcblock_nspc,
56 spcblock_custom
57 };
58
59 struct spcblock_data{
60 unsigned int destination;
61 spcblock_type type;
62 string macro_name;
63
64 unsigned int execute_address;
65 unsigned int size_address;
66 mapper_t old_mapper;
67 }spcblock;
68
69 1062 int snestopc_pick(int addr)
70 {
71 1062 return snestopc(addr);
72 }
73
74 1308732 inline void verifysnespos()
75 {
76
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 1308732 times.
1308732 if (!snespos_valid)
77 {
78 asar_throw_error(0, error_type_block, error_id_missing_org);
79 snespos=0x008000;
80 realsnespos=0x008000;
81 startpos=0x008000;
82 realstartpos=0x008000;
83 snespos_valid = true;
84 }
85 1308732 }
86
87 1656 static int fixsnespos(int inaddr, int step)
88 {
89 // randomdude999: turns out it wasn't very reliable at all.
90 /* // RPG Hacker: No idea how reliable this is.
91 // Might not work with some of the more exotic mappers.
92 return pctosnes(snestopc(inaddr) + step); */
93
2/2
✓ Branch 0 taken 288 times.
✓ Branch 1 taken 1368 times.
1656 if (mapper == lorom) {
94
2/2
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 252 times.
288 if ((inaddr&0xFFFF)+step > 0xFFFF) {
95 // bank crossed
96 36 return inaddr+step+0x8000;
97 }
98 252 return inaddr+step;
99
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 1368 times.
1368 } else if (mapper == hirom) {
100 if ((inaddr&0x400000) == 0) {
101 // system pages, need to account for low pages and stuff
102 if ((inaddr&0xFFFF)+step > 0xFFFF) {
103 return inaddr+step+0x8000;
104 }
105 }
106 return inaddr+step;
107
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 1368 times.
1368 } else if (mapper == exlorom) {
108 // exlorom has no mirroring so this should work fine
109 return pctosnes(snestopc(inaddr)+step);
110
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 1368 times.
1368 } else if (mapper == exhirom) {
111 // apparently exhirom is pretty similar to hirom after all
112 if ((inaddr&0x400000) == 0) {
113 // system pages, need to account for low pages and stuff
114 if ((inaddr&0xFFFF)+step > 0xFFFF) {
115 return inaddr+step+0x8000;
116 }
117 }
118 return inaddr+step;
119
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 1368 times.
1368 } else if (mapper == sa1rom) {
120 if((inaddr&0x400000) == 0) {
121 // lorom area
122 if ((inaddr&0xFFFF)+step > 0xFFFF) {
123 return inaddr+step+0x8000;
124 }
125 return inaddr+step;
126 } else {
127 // hirom area
128 return inaddr+step;
129 }
130
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 1368 times.
1368 } else if (mapper == sfxrom) {
131 if ((inaddr&0x400000) == 0) {
132 // lorom area
133 if ((inaddr&0xFFFF)+step > 0xFFFF) {
134 return inaddr+step+0x8000;
135 }
136 } else {
137 // hirom area
138 return inaddr+step;
139 }
140
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 1368 times.
1368 } else if (mapper == bigsa1rom) {
141 // no mirrors here, so this should work
142 return pctosnes(snestopc(inaddr)+step);
143
1/2
✓ Branch 0 taken 1368 times.
✗ Branch 1 not taken.
1368 } else if (mapper == norom) {
144 1368 return inaddr+step;
145 }
146 return -1;
147 }
148
149 1307721 inline void step(int num)
150 {
151
2/2
✓ Branch 0 taken 828 times.
✓ Branch 1 taken 1306893 times.
1307721 if (disable_bank_cross_errors)
152 {
153 828 snespos = fixsnespos(snespos, num);
154 828 realsnespos = fixsnespos(realsnespos, num);
155
156 // RPG Hacker: Not adjusting startpos here will eventually throw
157 // an error in checkbankcross() if we set warn bankcross on again.
158 // As far as I can tell, those are pretty much just used for
159 // checking bank crossing, anyways, so it's hopefully save to just
160 // adjust them here.
161 828 startpos = snespos;
162 828 realstartpos = realsnespos;
163 }
164 else
165 {
166 1306893 snespos += num;
167 1306893 realsnespos += num;
168 }
169 1307721 bytes+=num;
170 1307721 }
171
172 1305921 inline void write1_65816(unsigned int num)
173 {
174 1305921 verifysnespos();
175
2/2
✓ Branch 0 taken 435215 times.
✓ Branch 1 taken 870706 times.
1305921 if (pass==2)
176 {
177 435215 int pcpos=snestopc(realsnespos&0xFFFFFF);
178
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 435215 times.
435215 if (pcpos<0)
179 {
180 movinglabelspossible=true;
181 asar_throw_error(2, error_type_block, error_id_snes_address_doesnt_map_to_rom, hex((unsigned int)realsnespos, 6).data());
182 }
183 435215 writeromdata_byte(pcpos, (unsigned char)num);
184
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 435215 times.
435215 if (pcpos>=romlen) romlen=pcpos+1;
185 }
186
4/4
✓ Branch 0 taken 435335 times.
✓ Branch 1 taken 870586 times.
✓ Branch 2 taken 26507 times.
✓ Branch 3 taken 408828 times.
1305921 if(pass == 1 && freespaceid == 0) {
187 26507 int pcpos = snestopc(realsnespos & 0xFFFFFF);
188
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 26507 times.
26507 if(pcpos < 0) asar_throw_error(pass, error_type_fatal, error_id_internal_error, "invalid pos in pass 1");
189 26507 addromwrite(pcpos, 1);
190
2/2
✓ Branch 0 taken 25910 times.
✓ Branch 1 taken 597 times.
26507 if (pcpos>=romlen) romlen=pcpos+1;
191 }
192 1305921 step(1);
193 1305921 ratsmetastate=ratsmeta_ban;
194 1305921 }
195
196 int recent_opcode_num = 0;
197
198 1305921 void write1_pick(unsigned int num)
199 {
200 1305921 write1_65816(num);
201 1305921 }
202
203 78186 static bool asblock_pick(char** word, int numwords)
204 {
205 78186 recent_opcode_num = 1;
206
207
2/2
✓ Branch 0 taken 60114 times.
✓ Branch 1 taken 18072 times.
78186 if (arch==arch_65816) return asblock_65816(word, numwords);
208
2/2
✓ Branch 0 taken 7110 times.
✓ Branch 1 taken 10962 times.
18072 if (arch==arch_spc700) return asblock_spc700(word, numwords);
209
1/2
✓ Branch 0 taken 10962 times.
✗ Branch 1 not taken.
10962 if (arch==arch_superfx) return asblock_superfx(word, numwords);
210 return true;
211 }
212
213 #define write1 write1_pick
214 #define snestopc snestopc_pick
215
216 22644 const char * safedequote(char * str)
217 {
218 22644 const char * tmp=dequote(str);
219
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 22644 times.
22644 if (!tmp) asar_throw_error(0, error_type_block, error_id_garbage_near_quoted_string);
220 22644 return tmp;
221 }
222
223 extern char romtitle[30];
224 extern bool stdlib;
225
226 5184 void write2(unsigned int num)
227 {
228 5184 write1(num);
229 5184 write1(num/256);
230 5184 }
231
232 3108 void write3(unsigned int num)
233 {
234 3108 write1(num);
235 3108 write1(num/256);
236 3108 write1(num/65536);
237 3108 }
238
239 342 void write4(unsigned int num)
240 {
241 342 write1(num);
242 342 write1(num/256);
243 342 write1(num/65536);
244 342 write1(num/16777216);
245 342 }
246
247 //these are NOT used by the math parser - see math.cpp for that
248 90 int read2(int insnespos)
249 {
250 90 int addr=snestopc(insnespos);
251
3/4
✓ Branch 0 taken 72 times.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 72 times.
90 if (addr<0 || addr+2>romlen_r) return -1;
252 return
253 72 romdata_r[addr ] |
254 72 (romdata_r[addr+1]<< 8);
255 }
256
257 198 int read3(int insnespos)
258 {
259 198 int addr=snestopc(insnespos);
260
2/4
✓ Branch 0 taken 198 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 198 times.
198 if (addr<0 || addr+3>romlen_r) return -1;
261 return
262 198 romdata_r[addr ] |
263 198 (romdata_r[addr+1]<< 8)|
264 198 (romdata_r[addr+2]<<16);
265 }
266
267 4266 int getlenfromchar(char c)
268 {
269 4266 c=(char)to_lower(c);
270
2/2
✓ Branch 0 taken 1980 times.
✓ Branch 1 taken 2286 times.
4266 if (c=='b') return 1;
271
2/2
✓ Branch 0 taken 1980 times.
✓ Branch 1 taken 306 times.
2286 if (c=='w') return 2;
272
2/2
✓ Branch 0 taken 288 times.
✓ Branch 1 taken 18 times.
306 if (c=='l') return 3;
273 18 asar_throw_error(0, error_type_block, error_id_invalid_opcode_length);
274 return -1;
275 }
276
277 assocarr<snes_label> labels;
278 static autoarray<int> poslabels;
279 static autoarray<int> neglabels;
280
281 autoarray<int>* macroposlabels;
282 autoarray<int>* macroneglabels;
283
284 autoarray<string> sublabels;
285 autoarray<string>* macrosublabels;
286
287 // randomdude999: ns is still the string to prefix to all labels, it's calculated whenever namespace_list is changed
288 string ns;
289 string ns_backup;
290 autoarray<string> namespace_list;
291
292 //bool fastrom=false;
293
294 autoarray<string> includeonce;
295
296 // data necessary for one freespace block
297 struct freespace_data {
298 // snespos of the start of the freespace block. set to the found freespace
299 // block during the `freespace` command in pass 1.
300 int pos;
301 // length of the freespace block
302 int len;
303 // whether this freespace is leaked (no autocleans pointing at it)
304 bool leaked;
305 // position of the previous version of this freespace
306 int orgpos;
307 // length of previous version
308 int orglen;
309 // whether this freespace is static, i.e. can't be relocated when reinserting
310 bool is_static;
311 // what byte to use when searching for freespace, and clearing out previous rats tags
312 unsigned char cleanbyte;
313
314 // options only used for finding freespace:
315
316 // if this freespace is pinned to another one, this holds the name of the label of the target.
317 // we can't resolve this into a freespace number earlier since it could be a forward reference.
318 // we also need to keep the current namespace around since this is necessary for resolving label references.
319 string pin_target;
320 string pin_target_ns;
321 // computed at the end of pass 0. this is the freespace id of the final pin
322 // target, in case of multiple "nested" pins or whatnot.
323 int pin_target_id;
324 // what address to start searching for freespace at
325 int search_start;
326 // what bank to search for freespace in: -1 for any bank, -2 for banks with
327 // code mirrors, positive for specific bank
328 int bank;
329 bool write_rats;
330 // should rework this...
331 bool flag_align;
332 // pinned freespaces: how much space is actually needed for this freespace
333 int total_len;
334 // pinned freespaces: how much of this block we've already used
335 int used_len;
336 };
337 static autoarray<freespace_data> freespaces;
338
339 // id of the next unused freespace.
340 static int freespaceidnext;
341 // id of the current freespace, or 0 if not in freespace.
342 int freespaceid;
343 // start address of the current freespace, used for computing the length of the
344 // current freespace.
345 static int freespacestart;
346
347
348 7323 bool confirmname(const char * name)
349 {
350
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 7323 times.
7323 if (!name[0]) return false;
351
2/2
✓ Branch 0 taken 1836 times.
✓ Branch 1 taken 5487 times.
7323 if (is_digit(name[0])) return false;
352
2/2
✓ Branch 0 taken 45885 times.
✓ Branch 1 taken 5469 times.
51354 for (int i=0;name[i];i++)
353 {
354
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 45867 times.
45885 if (!is_ualnum(name[i])) return false;
355 }
356 5469 return true;
357 }
358
359 155646 string posneglabelname(const char ** input, bool define)
360 {
361 155646 const char* label = *input;
362
363 155646 string output;
364
365 155646 int depth = 0;
366 155646 bool ismacro = false;
367
368
2/2
✓ Branch 0 taken 138 times.
✓ Branch 1 taken 155508 times.
155646 if (label[0] == '?')
369 {
370 138 ismacro = true;
371 138 label++;
372 }
373
4/4
✓ Branch 0 taken 155483 times.
✓ Branch 1 taken 163 times.
✓ Branch 2 taken 583 times.
✓ Branch 3 taken 154900 times.
155646 if (label[0] == '-' || label[0] == '+')
374 {
375 746 char first = label[0];
376
4/4
✓ Branch 0 taken 926 times.
✓ Branch 1 taken 566 times.
✓ Branch 2 taken 746 times.
✓ Branch 3 taken 180 times.
1492 for (depth = 0; label[0] && label[0] == first; depth++) label++;
377
378
2/2
✓ Branch 0 taken 698 times.
✓ Branch 1 taken 48 times.
746 if (!ismacro)
379 {
380
2/2
✓ Branch 0 taken 559 times.
✓ Branch 1 taken 139 times.
698 if (first == '+')
381 {
382 559 *input = label;
383
8/16
✓ Branch 0 taken 559 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 559 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 559 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 559 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 559 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 559 times.
✗ Branch 11 not taken.
✓ Branch 12 taken 559 times.
✗ Branch 13 not taken.
✓ Branch 14 taken 559 times.
✗ Branch 15 not taken.
559 output = STR":pos_" + dec(depth) + "_" + dec(poslabels[depth]);
384
3/4
✓ Branch 0 taken 309 times.
✓ Branch 1 taken 250 times.
✓ Branch 2 taken 309 times.
✗ Branch 3 not taken.
559 if (define) poslabels[depth]++;
385 }
386 else
387 {
388 139 *input = label;
389
3/4
✓ Branch 0 taken 21 times.
✓ Branch 1 taken 118 times.
✓ Branch 2 taken 21 times.
✗ Branch 3 not taken.
139 if (define) neglabels[depth]++;
390
8/16
✓ Branch 0 taken 139 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 139 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 139 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 139 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 139 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 139 times.
✗ Branch 11 not taken.
✓ Branch 12 taken 139 times.
✗ Branch 13 not taken.
✓ Branch 14 taken 139 times.
✗ Branch 15 not taken.
139 output = STR":neg_" + dec(depth) + "_" + dec(neglabels[depth]);
391 }
392 }
393 else
394 {
395
3/6
✓ Branch 0 taken 48 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 48 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 48 times.
48 if (macrorecursion == 0 || macroposlabels == nullptr || macroneglabels == nullptr)
396 {
397 if (!macrorecursion) asar_throw_error(0, error_type_block, error_id_macro_label_outside_of_macro);
398 }
399 else
400 {
401
2/2
✓ Branch 0 taken 24 times.
✓ Branch 1 taken 24 times.
48 if (first == '+')
402 {
403 24 *input = label;
404
11/22
✓ Branch 0 taken 24 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 24 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 24 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 24 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 24 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 24 times.
✗ Branch 11 not taken.
✓ Branch 12 taken 24 times.
✗ Branch 13 not taken.
✓ Branch 14 taken 24 times.
✗ Branch 15 not taken.
✓ Branch 16 taken 24 times.
✗ Branch 17 not taken.
✓ Branch 18 taken 24 times.
✗ Branch 19 not taken.
✓ Branch 20 taken 24 times.
✗ Branch 21 not taken.
24 output = STR":macro_" + dec(calledmacros) + "_pos_" + dec(depth) + "_" + dec((*macroposlabels)[depth]);
405
3/4
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 6 times.
✓ Branch 2 taken 18 times.
✗ Branch 3 not taken.
24 if (define) (*macroposlabels)[depth]++;
406 }
407 else
408 {
409 24 *input = label;
410
3/4
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 6 times.
✓ Branch 2 taken 18 times.
✗ Branch 3 not taken.
24 if (define) (*macroneglabels)[depth]++;
411
11/22
✓ Branch 0 taken 24 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 24 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 24 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 24 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 24 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 24 times.
✗ Branch 11 not taken.
✓ Branch 12 taken 24 times.
✗ Branch 13 not taken.
✓ Branch 14 taken 24 times.
✗ Branch 15 not taken.
✓ Branch 16 taken 24 times.
✗ Branch 17 not taken.
✓ Branch 18 taken 24 times.
✗ Branch 19 not taken.
✓ Branch 20 taken 24 times.
✗ Branch 21 not taken.
24 output = STR":macro_" + dec(calledmacros) + "_neg_" + dec(depth) + "_" + dec((*macroneglabels)[depth]);
412 }
413 }
414 }
415 }
416
417 155646 return output;
418 }
419
420 6217 static string labelname(const char ** rawname, bool define=false)
421 {
422 #define deref_rawname (*rawname)
423 6217 autoarray<string>* sublabellist = &sublabels;
424
425 6217 bool ismacro = (deref_rawname[0] == '?');
426 6217 bool issublabel = false;
427
428
2/2
✓ Branch 0 taken 72 times.
✓ Branch 1 taken 6145 times.
6217 if (ismacro)
429 {
430 72 deref_rawname++;
431 72 sublabellist = macrosublabels;
432 }
433
434 6217 string name;
435 6217 int i=-1;
436
437
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 6217 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
6217 if (is_digit(*deref_rawname)) asar_throw_error(1, error_type_block, error_id_invalid_label_name);
438
2/2
✓ Branch 0 taken 210 times.
✓ Branch 1 taken 6007 times.
6217 if (*deref_rawname ==':')
439 {
440 210 deref_rawname++;
441
1/2
✓ Branch 0 taken 210 times.
✗ Branch 1 not taken.
210 name=":";
442 }
443
4/4
✓ Branch 0 taken 5413 times.
✓ Branch 1 taken 594 times.
✓ Branch 2 taken 5341 times.
✓ Branch 3 taken 72 times.
6007 else if (!in_struct && !in_sub_struct)
444 {
445
2/2
✓ Branch 0 taken 285 times.
✓ Branch 1 taken 5341 times.
5626 for (i=0;(*deref_rawname =='.');i++) deref_rawname++;
446
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 5341 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
5341 if (!is_ualnum(*deref_rawname)) asar_throw_error(1, error_type_block, error_id_invalid_label_name);
447
2/2
✓ Branch 0 taken 267 times.
✓ Branch 1 taken 5074 times.
5341 if (i)
448 {
449
5/12
✓ Branch 0 taken 267 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 267 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 267 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 267 times.
✗ Branch 8 not taken.
✓ Branch 9 taken 267 times.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
267 if (!sublabellist || !(*sublabellist)[i - 1]) asar_throw_error(1, error_type_block, error_id_label_missing_parent);
450
4/8
✓ Branch 0 taken 267 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 267 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 267 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 267 times.
✗ Branch 7 not taken.
267 name+=STR(*sublabellist)[i-1]+"_";
451 267 issublabel = true;
452 }
453 }
454
455
4/4
✓ Branch 0 taken 72 times.
✓ Branch 1 taken 6145 times.
✓ Branch 2 taken 48 times.
✓ Branch 3 taken 24 times.
6217 if (ismacro && !issublabel)
456 {
457 // RPG Hacker: Don't add the prefix for sublabels, because they already inherit it from
458 // their parents' names.
459
4/6
✓ Branch 0 taken 30 times.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 30 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 18 times.
48 if (!macrorecursion || macrosublabels == nullptr) asar_throw_error(1, error_type_block, error_id_macro_label_outside_of_macro);
460
6/12
✓ Branch 0 taken 30 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 30 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 30 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 30 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 30 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 30 times.
✗ Branch 11 not taken.
30 name = STR":macro_" + dec(calledmacros) + "_" + name;
461 }
462
463
464
4/4
✓ Branch 0 taken 5605 times.
✓ Branch 1 taken 594 times.
✓ Branch 2 taken 72 times.
✓ Branch 3 taken 5533 times.
6199 if (in_struct || in_sub_struct)
465 {
466
2/2
✓ Branch 0 taken 72 times.
✓ Branch 1 taken 594 times.
666 if(in_sub_struct)
467 {
468
2/4
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 72 times.
✗ Branch 3 not taken.
72 name += struct_parent + ".";
469 }
470
1/2
✓ Branch 0 taken 666 times.
✗ Branch 1 not taken.
666 name += struct_name;
471
1/2
✓ Branch 0 taken 666 times.
✗ Branch 1 not taken.
666 name += '.';
472
3/4
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 648 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 18 times.
666 if(*deref_rawname != '.') asar_throw_error(1, error_type_block, error_id_invalid_label_name); //probably should be a better error. TODO!!!
473 648 deref_rawname++;
474 }
475
476
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 6181 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
6181 if (!is_ualnum(*deref_rawname)) asar_throw_error(1, error_type_block, error_id_invalid_label_name);
477
478
6/6
✓ Branch 0 taken 6667 times.
✓ Branch 1 taken 43806 times.
✓ Branch 2 taken 486 times.
✓ Branch 3 taken 6181 times.
✓ Branch 4 taken 44292 times.
✓ Branch 5 taken 6181 times.
50473 while (is_ualnum(*deref_rawname) || *deref_rawname == '.')
479 {
480
1/2
✓ Branch 0 taken 44292 times.
✗ Branch 1 not taken.
44292 name+=*(deref_rawname++);
481 }
482
483
4/4
✓ Branch 0 taken 3736 times.
✓ Branch 1 taken 2445 times.
✓ Branch 2 taken 168 times.
✓ Branch 3 taken 3568 times.
6181 if(!define && *deref_rawname == '[')
484 {
485
3/4
✓ Branch 0 taken 552 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 384 times.
✓ Branch 3 taken 168 times.
552 while (*deref_rawname && *deref_rawname != ']') deref_rawname++;
486
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 168 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
168 if(*deref_rawname != ']') asar_throw_error(1, error_type_block, error_id_invalid_label_missing_closer);
487 168 deref_rawname++;
488
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 168 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
168 if(*deref_rawname != '.') asar_throw_error(1, error_type_block, error_id_invalid_label_name);
489 }
490
491
6/6
✓ Branch 0 taken 6349 times.
✓ Branch 1 taken 672 times.
✓ Branch 2 taken 168 times.
✓ Branch 3 taken 6181 times.
✓ Branch 4 taken 840 times.
✓ Branch 5 taken 6181 times.
7021 while (is_ualnum(*deref_rawname) || *deref_rawname == '.')
492 {
493
1/2
✓ Branch 0 taken 840 times.
✗ Branch 1 not taken.
840 name+=*(deref_rawname++);
494 }
495
496
3/4
✓ Branch 0 taken 72 times.
✓ Branch 1 taken 6109 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 72 times.
6181 if(*deref_rawname == '[') asar_throw_error(2, error_type_block, error_id_invalid_subscript);
497
498
4/4
✓ Branch 0 taken 2373 times.
✓ Branch 1 taken 3736 times.
✓ Branch 2 taken 1743 times.
✓ Branch 3 taken 630 times.
6109 if (define && i>=0)
499 {
500
1/2
✓ Branch 0 taken 1743 times.
✗ Branch 1 not taken.
1743 (*sublabellist).reset(i);
501
2/4
✓ Branch 0 taken 1743 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 1743 times.
✗ Branch 3 not taken.
1743 (*sublabellist)[i]=name;
502 }
503 6109 return name;
504 #undef deref_rawname
505 108 }
506
507 3592 inline bool labelvalcore(const char ** rawname, snes_label * rval, bool define, bool shouldthrow)
508 {
509
1/2
✓ Branch 0 taken 3592 times.
✗ Branch 1 not taken.
3592 string name=labelname(rawname, define);
510
13/20
✓ Branch 0 taken 3592 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 182 times.
✓ Branch 3 taken 3410 times.
✓ Branch 4 taken 182 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 182 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 96 times.
✓ Branch 9 taken 86 times.
✓ Branch 10 taken 182 times.
✓ Branch 11 taken 3410 times.
✓ Branch 12 taken 96 times.
✓ Branch 13 taken 3496 times.
✓ Branch 14 taken 96 times.
✗ Branch 15 not taken.
✓ Branch 16 taken 96 times.
✗ Branch 17 not taken.
✗ Branch 18 not taken.
✗ Branch 19 not taken.
3592 if (ns && labels.exists(ns+name)) {*rval = labels.find(ns+name);}
511
4/6
✓ Branch 0 taken 3496 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 3075 times.
✓ Branch 3 taken 421 times.
✓ Branch 4 taken 3075 times.
✗ Branch 5 not taken.
3496 else if (labels.exists(name)) {*rval = labels.find(name);}
512 else
513 {
514
4/4
✓ Branch 0 taken 127 times.
✓ Branch 1 taken 294 times.
✓ Branch 2 taken 7 times.
✓ Branch 3 taken 120 times.
421 if (shouldthrow && pass)
515 {
516
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 7 times.
7 asar_throw_error(2, error_type_block, error_id_label_not_found, name.data());
517 }
518 414 rval->pos = (unsigned int)-1;
519 414 rval->freespace_id = 0;
520 414 rval->is_static = false;
521 414 return false;
522 }
523 3171 return true;
524 3592 }
525
526 1750 snes_label labelval(const char ** rawname, bool define)
527 {
528 1750 snes_label rval;
529
2/2
✓ Branch 0 taken 872 times.
✓ Branch 1 taken 4 times.
1750 labelvalcore(rawname, &rval, define, true);
530 1743 return rval;
531 }
532
533 134 snes_label labelval(string name, bool define)
534 {
535 134 const char * rawname=name;
536 134 snes_label rval;
537
1/2
✓ Branch 0 taken 134 times.
✗ Branch 1 not taken.
134 labelvalcore(&rawname, &rval, define, true);
538 200 return rval;
539 }
540
541 1536 bool labelval(const char ** rawname, snes_label * rval, bool define)
542 {
543 1536 return labelvalcore(rawname, rval, define, false);
544 }
545
546 172 bool labelval(string name, snes_label * rval, bool define)
547 {
548 172 const char * str=name;
549
1/2
✓ Branch 0 taken 172 times.
✗ Branch 1 not taken.
344 return labelvalcore(&str, rval, define, false);
550 }
551
552 3279 static void setlabel(string name, int loc=-1, bool is_static=false, int freespace_id = -1)
553 {
554
2/2
✓ Branch 0 taken 2793 times.
✓ Branch 1 taken 486 times.
3279 if (loc==-1)
555 {
556
1/2
✓ Branch 0 taken 2793 times.
✗ Branch 1 not taken.
2793 verifysnespos();
557 2793 loc=snespos;
558 }
559
560 3279 snes_label label_data;
561 3279 label_data.pos = (unsigned int)loc;
562 3279 label_data.is_static = is_static;
563
1/2
✓ Branch 0 taken 3279 times.
✗ Branch 1 not taken.
3279 label_data.freespace_id = freespace_id == -1 ? freespaceid : freespace_id;
564
565 unsigned int labelpos;
566
2/2
✓ Branch 0 taken 1093 times.
✓ Branch 1 taken 2186 times.
3279 if (pass==0)
567 {
568
3/4
✓ Branch 0 taken 1093 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 6 times.
✓ Branch 3 taken 1087 times.
1093 if (labels.exists(name))
569 {
570 6 movinglabelspossible=true;
571
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6 times.
6 asar_throw_error(0, error_type_block, error_id_label_redefined, name.data());
572 }
573
1/2
✓ Branch 0 taken 1087 times.
✗ Branch 1 not taken.
1087 labels.create(name) = label_data;
574 }
575
2/2
✓ Branch 0 taken 1093 times.
✓ Branch 1 taken 1093 times.
2186 else if (pass==1)
576 {
577
1/2
✓ Branch 0 taken 1093 times.
✗ Branch 1 not taken.
1093 labels.create(name) = label_data;
578 }
579
1/2
✓ Branch 0 taken 1093 times.
✗ Branch 1 not taken.
1093 else if (pass==2)
580 {
581 //all label locations are known at this point, add a sanity check
582
2/6
✓ Branch 0 taken 1093 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 1093 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
1093 if (!labels.exists(name)) asar_throw_error(2, error_type_block, error_id_label_on_third_pass);
583
1/2
✓ Branch 0 taken 1093 times.
✗ Branch 1 not taken.
1093 labelpos = labels.find(name).pos;
584
3/4
✓ Branch 0 taken 12 times.
✓ Branch 1 taken 1081 times.
✓ Branch 2 taken 12 times.
✗ Branch 3 not taken.
1093 if ((int)labelpos != loc && !movinglabelspossible)
585 {
586
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 12 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
12 if((unsigned int)loc>>16 != labelpos>>16) asar_throw_error(2, error_type_block, error_id_label_ambiguous, name.raw());
587
3/4
✓ Branch 0 taken 6 times.
✓ Branch 1 taken 6 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 6 times.
12 else if(labelpos == (dp_base + 0xFFu)) asar_throw_error(2, error_type_block, error_id_label_ambiguous, name.raw());
588
1/2
✓ Branch 0 taken 6 times.
✗ Branch 1 not taken.
6 else if(errored) return;
589 else asar_throw_error(2, error_type_block, error_id_label_moving);
590 }
591 }
592 }
593
594 table thetable;
595 static autoarray<table> tablestack;
596
597 2124 static void cleartable()
598 {
599
2/4
✓ Branch 0 taken 2124 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2124 times.
✗ Branch 3 not taken.
2124 thetable = table();
600 2124 }
601
602 struct pushable {
603 int arch;
604 int snespos;
605 int snesstart;
606 int snesposreal;
607 int snesstartreal;
608 int freeid;
609 int freest;
610 int arch1;
611 int arch2;
612 int arch3;
613 int arch4;
614 };
615 static autoarray<pushable> pushpc;
616 static int pushpcnum;
617
618 static autoarray<int> basestack;
619 static int basestacknum;
620
621 struct ns_pushable {
622 string ns;
623 autoarray<string> namespace_list;
624 bool nested_namespaces;
625 };
626
627 static autoarray<ns_pushable> pushns;
628 static int pushnsnum;
629
630
631 static unsigned char fillbyte[12];
632 static unsigned char padbyte[12];
633
634 static bool nested_namespaces = false;
635
636 4374 static int getfreespaceid()
637 {
638 /*static const int max_num_freespaces = 125;
639 if (freespaceidnext > max_num_freespaces) asar_throw_error(pass, error_type_fatal, error_id_freespace_limit_reached, max_num_freespaces);*/
640 4374 int newid = freespaceidnext++;
641
2/2
✓ Branch 0 taken 1458 times.
✓ Branch 1 taken 2916 times.
4374 if(newid >= freespaces.count) {
642 1458 freespaces[newid].leaked = true;
643 1458 freespaces[newid].orgpos = -2;
644 1458 freespaces[newid].orglen = -1;
645 1458 freespaces[newid].cleanbyte = 0x00;
646 }
647 4374 return newid;
648 }
649
650 132534 void checkbankcross()
651 {
652
2/2
✓ Branch 0 taken 25671 times.
✓ Branch 1 taken 106863 times.
132534 if (!snespos_valid) return;
653
2/2
✓ Branch 0 taken 1134 times.
✓ Branch 1 taken 105729 times.
106863 if (disable_bank_cross_errors) return;
654
2/2
✓ Branch 0 taken 876 times.
✓ Branch 1 taken 104853 times.
105729 unsigned int mask = 0x7FFF0000 | (check_half_banks_crossed ? 0x8000 : 0);
655
4/4
✓ Branch 0 taken 1713 times.
✓ Branch 1 taken 104016 times.
✓ Branch 2 taken 12 times.
✓ Branch 3 taken 1701 times.
105729 if (((snespos^startpos) & mask) && (((snespos - 1) ^ startpos) & mask))
656 {
657 12 asar_throw_error(pass, error_type_fatal, error_id_bank_border_crossed, snespos);
658 }
659 // don't verify realsnespos when using norom. this allows making custom mappers where the file layout doesn't follow bank borders
660
5/6
✓ Branch 0 taken 104841 times.
✓ Branch 1 taken 876 times.
✓ Branch 2 taken 1701 times.
✓ Branch 3 taken 103140 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 1701 times.
105717 else if (mapper != norom && ((realsnespos^realstartpos) & mask) && (((realsnespos - 1) ^ realstartpos) & mask))
661 {
662 asar_throw_error(pass, error_type_fatal, error_id_bank_border_crossed, realsnespos);
663 }
664 }
665
666 8832 static void freespaceend()
667 {
668
2/2
✓ Branch 0 taken 4392 times.
✓ Branch 1 taken 4440 times.
8832 if (freespaceid > 0)
669 {
670 4392 freespaces[freespaceid].len = snespos-freespacestart;
671 4392 snespos=(int)0xFFFFFFFF;
672 4392 snespos_valid = false;
673 }
674 8832 freespaceid = 0;
675 8832 }
676
677 int numopcodes;
678
679 19408 static void adddefine(const string & key, string & value)
680 {
681
1/2
✓ Branch 0 taken 19408 times.
✗ Branch 1 not taken.
19408 if (!defines.exists(key)) defines.create(key) = value;
682 19408 }
683
684 2106 void initstuff()
685 {
686
2/2
✓ Branch 0 taken 722 times.
✓ Branch 1 taken 1384 times.
2106 if (pass==0)
687 {
688 722 freespaces.reset();
689 722 movinglabelspossible = false;
690 722 found_rats_tags_initialized = false;
691 722 found_rats_tags.clear();
692 }
693 2106 arch=arch_65816;
694 2106 mapper=lorom;
695 2106 mapper_set = false;
696 2106 calledmacros = 0;
697 2106 reallycalledmacros = 0;
698 2106 macrorecursion = 0;
699 2106 defines.reset();
700 2106 builtindefines.each(adddefine);
701 2106 clidefines.each(adddefine);
702 2106 ns="";
703 2106 namespace_list.reset();
704 2106 sublabels.reset();
705 2106 poslabels.reset();
706 2106 neglabels.reset();
707 2106 macroposlabels = nullptr;
708 2106 macroneglabels = nullptr;
709 2106 macrosublabels = nullptr;
710 2106 cleartable();
711 2106 pushpc.reset();
712 2106 pushpcnum=0;
713 2106 pushns.reset();
714 2106 pushnsnum = 0;
715 2106 bytes=0;
716 2106 freespaceuse=0;
717 2106 memset(fillbyte, 0, sizeof(fillbyte));
718 2106 memset(padbyte, 0, sizeof(padbyte));
719 2106 snespos_valid = false;
720 2106 snespos=(int)0xFFFFFFFF;
721 2106 realsnespos= (int)0xFFFFFFFF;
722 2106 startpos= (int)0xFFFFFFFF;
723 2106 realstartpos= (int)0xFFFFFFFF;
724 //fastrom=false;
725 2106 freespaceidnext=1;
726 2106 freespaceid=0;
727 2106 numopcodes=0;
728 2106 incsrcdepth = 0;
729
730 2106 optimizeforbank = -1;
731 2106 optimize_dp = optimize_dp_flag::NONE;
732 2106 dp_base = 0;
733 2106 optimize_address = optimize_address_flag::DEFAULT;
734
735 2106 in_struct = false;
736 2106 in_sub_struct = false;
737 2106 in_spcblock = false;
738
739
1/2
✓ Branch 0 taken 2106 times.
✗ Branch 1 not taken.
2106 if (arch==arch_65816) asinit_65816();
740
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 2106 times.
2106 if (arch==arch_spc700) asinit_spc700();
741
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 2106 times.
2106 if (arch==arch_superfx) asinit_superfx();
742
743 2106 disable_bank_cross_errors = false;
744 2106 check_half_banks_crossed = false;
745 2106 nested_namespaces = false;
746
747 2106 includeonce.reset();
748
749 extern AddressToLineMapping addressToLineMapping;
750 2106 addressToLineMapping.reset();
751
752 2106 push_warnings(false);
753
754 2106 initmathcore();
755
756 2106 callstack.reset();
757 #if defined(_WIN32) || !defined(NO_USE_THREADS)
758 2106 init_stack_use_check();
759 #endif
760 2106 }
761
762 1482 int get_freespace_pin_target(int target_id) {
763 // union-find algorithm
764
2/2
✓ Branch 0 taken 12 times.
✓ Branch 1 taken 1482 times.
1494 while(freespaces[target_id].pin_target_id != target_id) {
765 // i love programming
766 24 freespaces[target_id].pin_target_id =
767 12 freespaces[freespaces[target_id].pin_target_id].pin_target_id;
768 12 target_id = freespaces[target_id].pin_target_id;
769 }
770 1482 return target_id;
771 }
772
773 692 void resolve_pinned_freespaces() {
774
2/2
✓ Branch 0 taken 1458 times.
✓ Branch 1 taken 692 times.
2150 for(int i = 1; i < freespaces.count; i++)
775 // default to everyone being in a separate component
776 1458 freespaces[i].pin_target_id = i;
777
2/2
✓ Branch 0 taken 1458 times.
✓ Branch 1 taken 692 times.
2150 for(int i = 1; i < freespaces.count; i++) {
778
1/2
✓ Branch 0 taken 1458 times.
✗ Branch 1 not taken.
1458 freespace_data& fs = freespaces[i];
779
2/2
✓ Branch 0 taken 1434 times.
✓ Branch 1 taken 24 times.
1458 if(fs.pin_target == "") continue;
780 24 snes_label value;
781
4/16
✓ Branch 0 taken 24 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 24 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 24 times.
✗ Branch 12 not taken.
✓ Branch 13 taken 24 times.
✗ Branch 14 not taken.
✗ Branch 15 not taken.
24 if(fs.pin_target_ns && labels.exists(fs.pin_target_ns + fs.pin_target))
782 value = labels.find(fs.pin_target_ns + fs.pin_target);
783
2/4
✓ Branch 0 taken 24 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 24 times.
✗ Branch 3 not taken.
24 else if(labels.exists(fs.pin_target))
784
1/2
✓ Branch 0 taken 24 times.
✗ Branch 1 not taken.
24 value = labels.find(fs.pin_target);
785 else continue; // the error for this is thrown in the freespace command during pass 2
786
1/2
✓ Branch 0 taken 24 times.
✗ Branch 1 not taken.
24 fs.pin_target_id = get_freespace_pin_target(value.freespace_id);
787 24 fs.len = 0;
788 }
789 692 }
790
791 692 void allocate_freespaces() {
792 // compute real size of all pinned freespace blocks
793
2/2
✓ Branch 0 taken 1458 times.
✓ Branch 1 taken 692 times.
2150 for(int i = 1; i < freespaces.count; i++) {
794 1458 freespace_data& fs = freespaces[i];
795 // just in case the pin target changed again or something
796 1458 fs.pin_target_id = get_freespace_pin_target(fs.pin_target_id);
797 1458 freespace_data& target = freespaces[fs.pin_target_id];
798 1458 target.total_len += fs.len;
799 1458 target.search_start = std::max(fs.search_start, target.search_start);
800 }
801
802
2/2
✓ Branch 0 taken 1458 times.
✓ Branch 1 taken 692 times.
2150 for(int i = 1; i < freespaces.count; i++) {
803 1458 freespace_data& fs = freespaces[i];
804
4/4
✓ Branch 0 taken 12 times.
✓ Branch 1 taken 1446 times.
✓ Branch 2 taken 6 times.
✓ Branch 3 taken 6 times.
1458 if(fs.is_static && fs.orgpos > 0) {
805 6 fs.pos = fs.orgpos;
806 6 continue;
807 }
808 // if this freespace is pinned to another one, set it later
809
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 1434 times.
1452 if(fs.pin_target_id != i) continue;
810 // TODO: possibly fancier align
811 1434 fs.pos = getsnesfreespace(fs.total_len, fs.bank, true, true, fs.flag_align, fs.cleanbyte, fs.write_rats, fs.search_start);
812 1434 fs.used_len = fs.len;
813 }
814 // set pos for all pinned freespaces
815
2/2
✓ Branch 0 taken 1458 times.
✓ Branch 1 taken 692 times.
2150 for(int i = 1; i < freespaces.count; i++) {
816 1458 freespace_data& fs = freespaces[i];
817
2/2
✓ Branch 0 taken 1440 times.
✓ Branch 1 taken 18 times.
1458 if(fs.pin_target_id == i) continue;
818 18 freespace_data& tgt = freespaces[fs.pin_target_id];
819 18 fs.pos = tgt.pos + tgt.used_len;
820 18 tgt.used_len += fs.len;
821 }
822
823 // relocate all labels that were in freespace to point them to their real location
824 692 labels.each([](const char * key, snes_label & val) {
825
2/2
✓ Branch 0 taken 168 times.
✓ Branch 1 taken 919 times.
1087 if(val.freespace_id != 0) {
826 168 val.pos += freespaces[val.freespace_id].pos;
827 }
828 1087 });
829 692 }
830
831 //void nerf(const string& left, string& right){puts(S left+" = "+right);}
832
833 2076 void finishpass()
834 {
835 2076 verify_warnings();
836 2076 pull_warnings(false);
837
838 //defines.traverse(nerf);
839
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 2076 times.
2076 if(in_spcblock) asar_throw_error(0, error_type_block, error_id_missing_endspcblock);
840
2/4
✓ Branch 0 taken 2076 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2076 times.
2076 if (in_struct || in_sub_struct) asar_throw_error(pass, error_type_null, error_id_struct_without_endstruct);
841
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 2076 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
2076 else if (pushpcnum && pass == 0) asar_throw_error(pass, error_type_null, error_id_pushpc_without_pullpc);
842
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 2076 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
2076 else if (pushnsnum && pass == 0) asar_throw_error(pass, error_type_null, error_id_pushns_without_pullns);
843 2076 freespaceend();
844
2/2
✓ Branch 0 taken 1950 times.
✓ Branch 1 taken 126 times.
2076 if (arch==arch_65816) asend_65816();
845
2/2
✓ Branch 0 taken 90 times.
✓ Branch 1 taken 1986 times.
2076 if (arch==arch_spc700) asend_spc700();
846
2/2
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 2040 times.
2076 if (arch==arch_superfx) asend_superfx();
847
848 2076 deinitmathcore();
849
2/2
✓ Branch 0 taken 692 times.
✓ Branch 1 taken 1384 times.
2076 if(pass == 0) {
850 692 resolve_pinned_freespaces();
851
2/2
✓ Branch 0 taken 692 times.
✓ Branch 1 taken 692 times.
1384 } else if(pass == 1) {
852 692 allocate_freespaces();
853 692 handle_cleared_rats_tags();
854 }
855 #if defined(_WIN32) || !defined(NO_USE_THREADS)
856 2076 deinit_stack_use_check();
857 #endif
858 2076 }
859
860 139896 static bool addlabel(const char * label, int pos=-1, bool global_label = false)
861 {
862
3/4
✓ Branch 0 taken 94797 times.
✓ Branch 1 taken 45099 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 94797 times.
139896 if (!label[0] || label[0]==':') return false;//colons are reserved for special labels
863
864 94797 const char* posneglabel = label;
865
1/2
✓ Branch 0 taken 94797 times.
✗ Branch 1 not taken.
94797 string posnegname = posneglabelname(&posneglabel, true);
866
867
3/4
✓ Branch 0 taken 94797 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 366 times.
✓ Branch 3 taken 94431 times.
94797 if (posnegname.length() > 0)
868 {
869
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 366 times.
366 if (global_label) return false;
870
3/6
✓ Branch 0 taken 72 times.
✓ Branch 1 taken 294 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 72 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
366 if (*posneglabel != '\0' && *posneglabel != ':') asar_throw_error(0, error_type_block, error_id_broken_label_definition);
871
2/4
✓ Branch 0 taken 366 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 366 times.
✗ Branch 3 not taken.
366 setlabel(posnegname, pos);
872 366 return true;
873 }
874
7/8
✓ Branch 0 taken 92025 times.
✓ Branch 1 taken 2406 times.
✓ Branch 2 taken 91842 times.
✓ Branch 3 taken 183 times.
✓ Branch 4 taken 91824 times.
✓ Branch 5 taken 18 times.
✗ Branch 6 not taken.
✓ Branch 7 taken 91824 times.
94431 if (label[strlen(label)-1]==':' || label[0]=='.' || label[0]=='?' || label[0] == '#')
875 {
876
2/2
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 2571 times.
2607 if (!label[1]) return false;
877
6/8
✓ Branch 0 taken 126 times.
✓ Branch 1 taken 2445 times.
✓ Branch 2 taken 126 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 126 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 18 times.
✓ Branch 7 taken 108 times.
2571 if(global_label && (in_struct || in_sub_struct || label[0]=='?')) return false;
878
879 2553 bool define = true;
880
881
2/2
✓ Branch 0 taken 72 times.
✓ Branch 1 taken 2481 times.
2553 if (label[0] == '#')
882 {
883 72 define = false;
884 72 label++;
885 }
886
887 // RPG Hacker: Also checking label[1] now, since it might be a macro sublabel.
888 // Also, apparently this here doesn't account for main labels. I guess because
889 // we don't even get here in the first place if they don't include a colon?
890
7/8
✓ Branch 0 taken 1668 times.
✓ Branch 1 taken 885 times.
✓ Branch 2 taken 1650 times.
✓ Branch 3 taken 18 times.
✓ Branch 4 taken 1632 times.
✓ Branch 5 taken 18 times.
✗ Branch 6 not taken.
✓ Branch 7 taken 1632 times.
2553 bool requirecolon = (label[0] != '.' && label[1] != '.') && (in_struct || in_sub_struct);
891
2/2
✓ Branch 0 taken 2445 times.
✓ Branch 1 taken 108 times.
2553 string name=labelname(&label, define);
892
2/2
✓ Branch 0 taken 2316 times.
✓ Branch 1 taken 129 times.
2445 if (label[0]==':') label++;
893
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 129 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
129 else if (requirecolon) asar_throw_error(0, error_type_block, error_id_broken_label_definition);
894
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 111 times.
129 else if (global_label) return false;
895
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 2427 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
2427 if (label[0]) asar_throw_error(0, error_type_block, error_id_broken_label_definition);
896
9/12
✓ Branch 0 taken 2427 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 327 times.
✓ Branch 3 taken 2100 times.
✓ Branch 4 taken 291 times.
✓ Branch 5 taken 36 times.
✓ Branch 6 taken 291 times.
✓ Branch 7 taken 2136 times.
✓ Branch 8 taken 291 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 291 times.
✗ Branch 11 not taken.
2427 if (ns && !global_label) name=ns+name;
897
9/10
✓ Branch 0 taken 1869 times.
✓ Branch 1 taken 558 times.
✓ Branch 2 taken 72 times.
✓ Branch 3 taken 1797 times.
✓ Branch 4 taken 450 times.
✓ Branch 5 taken 180 times.
✓ Branch 6 taken 2427 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2415 times.
✓ Branch 9 taken 12 times.
2439 setlabel(name, pos, ((in_struct || in_sub_struct) && static_struct));
898 2415 return true;
899 2445 }
900 91824 return false;
901 94797 }
902
903 44643 static void add_addr_to_line(int pos)
904 {
905
2/2
✓ Branch 0 taken 15775 times.
✓ Branch 1 taken 28868 times.
44643 if (pass == 2)
906 15775 addressToLineMapping.includeMapping(get_current_file_name(), get_current_line() + 1, pos);
907 44643 }
908
909 static autoarray<bool> elsestatus;
910 int numtrue=0;//if 1 -> increase both
911 int numif = 0; //if 0 or inside if 0 -> increase only numif
912
913 autoarray<whiletracker> whilestatus;
914 int single_line_for_tracker;
915
916
917 270 static void push_pc()
918 {
919 270 pushpc[pushpcnum].arch=arch;
920 270 pushpc[pushpcnum].snespos=snespos;
921 270 pushpc[pushpcnum].snesstart=startpos;
922 270 pushpc[pushpcnum].snesposreal=realsnespos;
923 270 pushpc[pushpcnum].snesstartreal=realstartpos;
924 270 pushpc[pushpcnum].freeid=freespaceid;
925 270 pushpc[pushpcnum].freest=freespacestart;
926 270 pushpcnum++;
927 270 }
928
929 270 static void pop_pc()
930 {
931 270 pushpcnum--;
932 270 snespos=pushpc[pushpcnum].snespos;
933 270 startpos=pushpc[pushpcnum].snesstart;
934 270 realsnespos=pushpc[pushpcnum].snesposreal;
935 270 realstartpos=pushpc[pushpcnum].snesstartreal;
936 270 freespaceid=pushpc[pushpcnum].freeid;
937 270 freespacestart=pushpc[pushpcnum].freest;
938 270 }
939
940
941 984 string handle_print(char* input)
942 {
943 984 string out;
944
1/2
✓ Branch 0 taken 984 times.
✗ Branch 1 not taken.
984 autoptr<char**> pars = qpsplit(input, ',');
945
1/2
✓ Branch 0 taken 984 times.
✗ Branch 1 not taken.
984 verify_paren(pars);
946
2/2
✓ Branch 0 taken 1659 times.
✓ Branch 1 taken 966 times.
2625 for (int i = 0; pars[i]; i++)
947 {
948 if (0);
949
4/6
✓ Branch 0 taken 1218 times.
✓ Branch 1 taken 441 times.
✓ Branch 2 taken 1218 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 1218 times.
✗ Branch 5 not taken.
1659 else if (pars[i][0] == '"') out += safedequote(pars[i]);
950
6/8
✓ Branch 0 taken 234 times.
✓ Branch 1 taken 207 times.
✓ Branch 2 taken 36 times.
✓ Branch 3 taken 198 times.
✓ Branch 4 taken 36 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 18 times.
✗ Branch 7 not taken.
441 else if (!stricmp(pars[i], "bytes")) out += dec(bytes);
951
6/8
✓ Branch 0 taken 207 times.
✓ Branch 1 taken 198 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 189 times.
✓ Branch 4 taken 18 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 9 times.
✗ Branch 7 not taken.
405 else if (!stricmp(pars[i], "freespaceuse")) out += dec(freespaceuse);
952
3/8
✓ Branch 0 taken 189 times.
✓ Branch 1 taken 198 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 189 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
387 else if (!stricmp(pars[i], "pc")) out += hex((unsigned int)(snespos & 0xFFFFFF), 6);
953
1/2
✓ Branch 0 taken 189 times.
✗ Branch 1 not taken.
387 else if (!strncasecmp(pars[i], "bin(", strlen("bin(")) ||
954
4/4
✓ Branch 0 taken 258 times.
✓ Branch 1 taken 39 times.
✓ Branch 2 taken 108 times.
✓ Branch 3 taken 36 times.
297 !strncasecmp(pars[i], "dec(", strlen("dec(")) ||
955
8/8
✓ Branch 0 taken 297 times.
✓ Branch 1 taken 90 times.
✓ Branch 2 taken 180 times.
✓ Branch 3 taken 42 times.
✓ Branch 4 taken 261 times.
✓ Branch 5 taken 45 times.
✓ Branch 6 taken 180 times.
✓ Branch 7 taken 9 times.
828 !strncasecmp(pars[i], "hex(", strlen("hex(")) ||
956
4/4
✓ Branch 0 taken 135 times.
✓ Branch 1 taken 9 times.
✓ Branch 2 taken 63 times.
✓ Branch 3 taken 9 times.
144 !strncasecmp(pars[i], "double(", strlen("double(")))
957 {
958 369 char * arg1pos = strchr(pars[i], '(') + 1;
959 369 char * endpos = strchr(arg1pos, '\0');
960
3/4
✗ Branch 0 not taken.
✓ Branch 1 taken 738 times.
✓ Branch 2 taken 369 times.
✓ Branch 3 taken 369 times.
738 while (*endpos == ' ' || *endpos == '\0') endpos--;
961
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 369 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
369 if (*endpos != ')') asar_throw_error(0, error_type_block, error_id_invalid_print_function_syntax);
962
1/2
✓ Branch 0 taken 369 times.
✗ Branch 1 not taken.
369 string paramstr = string(arg1pos, (int)(endpos - arg1pos));
963
964 int numargs;
965
1/2
✓ Branch 0 taken 369 times.
✗ Branch 1 not taken.
369 autoptr<char**> params = qpsplit(paramstr.temp_raw(), ',', &numargs);
966
1/2
✓ Branch 0 taken 369 times.
✗ Branch 1 not taken.
369 verify_paren(params);
967
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 369 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
369 if (numargs > 2) asar_throw_error(0, error_type_block, error_id_wrong_num_parameters);
968 369 int precision = 0;
969 369 bool hasprec = numargs == 2;
970
2/2
✓ Branch 0 taken 234 times.
✓ Branch 1 taken 135 times.
369 if (hasprec)
971 {
972
1/2
✓ Branch 0 taken 234 times.
✗ Branch 1 not taken.
234 precision = getnum(params[1]);
973
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 234 times.
234 if (precision < 0) precision = 0;
974
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 234 times.
234 if (precision > 64) precision = 64;
975 }
976 369 *(arg1pos - 1) = '\0'; // allows more convenient comparsion functions
977
4/4
✓ Branch 0 taken 225 times.
✓ Branch 1 taken 144 times.
✓ Branch 2 taken 45 times.
✓ Branch 3 taken 135 times.
369 if (!stricmp(pars[i], "bin"))
978 {
979 // sadly printf doesn't have binary, so let's roll our own
980
1/2
✓ Branch 0 taken 90 times.
✗ Branch 1 not taken.
90 int64_t value = getnum(params[0]);
981 char buffer[65];
982
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 72 times.
90 if (value < 0) {
983
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 out += '-';
984 18 value = -value;
985 // decrement precision because we've output one char already
986 18 precision -= 1;
987
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 if (precision<0) precision = 0;
988 }
989
2/2
✓ Branch 0 taken 5760 times.
✓ Branch 1 taken 90 times.
5850 for (int j = 0; j < 64; j++) {
990 5760 buffer[63 - j] = '0' + ((value & (1ull << j)) >> j);
991 }
992 90 buffer[64] = 0;
993 90 int startidx = 0;
994
4/4
✓ Branch 0 taken 5184 times.
✓ Branch 1 taken 72 times.
✓ Branch 2 taken 5166 times.
✓ Branch 3 taken 18 times.
5256 while (startidx < 64 - precision && buffer[startidx] == '0') startidx++;
995
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 90 times.
90 if (startidx == 64) startidx--; // always want to print at least one digit
996
1/2
✓ Branch 0 taken 90 times.
✗ Branch 1 not taken.
90 out += buffer + startidx;
997 }
998
4/4
✓ Branch 0 taken 174 times.
✓ Branch 1 taken 105 times.
✓ Branch 2 taken 36 times.
✓ Branch 3 taken 99 times.
279 else if (!stricmp(pars[i], "dec"))
999 {
1000
1/2
✓ Branch 0 taken 75 times.
✗ Branch 1 not taken.
75 int64_t value = getnum(params[0]);
1001 char buffer[65];
1002
1/2
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
75 snprintf(buffer, 65, "%0*" PRId64, precision, value);
1003
1/2
✓ Branch 0 taken 75 times.
✗ Branch 1 not taken.
75 out += buffer;
1004 }
1005
4/4
✓ Branch 0 taken 141 times.
✓ Branch 1 taken 63 times.
✓ Branch 2 taken 36 times.
✓ Branch 3 taken 63 times.
204 else if (!stricmp(pars[i], "hex"))
1006 {
1007
1/2
✓ Branch 0 taken 78 times.
✗ Branch 1 not taken.
78 int64_t value = getnum(params[0]);
1008 char buffer[65];
1009
1/2
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
78 snprintf(buffer, 65, "%0*" PRIX64, precision, value);
1010
1/2
✓ Branch 0 taken 78 times.
✗ Branch 1 not taken.
78 out += buffer;
1011 }
1012
2/4
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 63 times.
✗ Branch 3 not taken.
126 else if (!stricmp(pars[i], "double"))
1013 {
1014
2/2
✓ Branch 0 taken 108 times.
✓ Branch 1 taken 18 times.
126 if (!hasprec) precision = 5;
1015
3/6
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 126 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 126 times.
✗ Branch 5 not taken.
126 out += ftostrvar(getnumdouble(params[0]), precision);
1016 }
1017 369 }
1018
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
18 else asar_throw_error(2, error_type_block, error_id_unknown_variable);
1019 }
1020 1932 return out;
1021 1002 }
1022
1023 // single_line_for_tracker is:
1024 // 0 if not in first block of line, not in (single-line) for loop
1025 // 1 if first block of line
1026 // 2 if in single-line for loop
1027 // 3 if after endfor (of a single-line loop)
1028 150318 void assembleblock(const char * block, int& single_line_for_tracker)
1029 {
1030 #define is(test) (!stricmpwithlower(word[0], test))
1031 #define is0(test) (numwords==1 && !stricmpwithlower(word[0], test))
1032 #define is1(test) (numwords==2 && !stricmpwithlower(word[0], test))
1033 #define is2(test) (numwords==3 && !stricmpwithlower(word[0], test))
1034 #define is3(test) (numwords==4 && !stricmpwithlower(word[0], test))
1035 #define par word[1]
1036
1037
1/2
✓ Branch 0 taken 150318 times.
✗ Branch 1 not taken.
150318 callstack_push cs_push(callstack_entry_type::BLOCK, block);
1038
1039 int numwords;
1040
1/2
✓ Branch 0 taken 150318 times.
✗ Branch 1 not taken.
150318 string splitblock = block;
1041
1/2
✓ Branch 0 taken 150318 times.
✗ Branch 1 not taken.
150318 char ** word = qsplit(splitblock.temp_raw(), ' ', &numwords);
1042 150318 autoptr<char **> scope_word = word;
1043 // when writing out the data for the addrToLine mapping,
1044 // we want to write out the snespos we had before writing opcodes
1045 150318 int addrToLinePos = realsnespos & 0xFFFFFF;
1046
1047
14/14
✓ Branch 0 taken 143325 times.
✓ Branch 1 taken 9684 times.
✓ Branch 2 taken 141210 times.
✓ Branch 3 taken 2115 times.
✓ Branch 4 taken 79299 times.
✓ Branch 5 taken 61911 times.
✓ Branch 6 taken 77859 times.
✓ Branch 7 taken 1440 times.
✓ Branch 8 taken 139650 times.
✓ Branch 9 taken 120 times.
✓ Branch 10 taken 2691 times.
✓ Branch 11 taken 136959 times.
✓ Branch 12 taken 2691 times.
✓ Branch 13 taken 150198 times.
153009 while (numif==numtrue && word[0] && (!word[1] || strcmp(word[1], "=")) && addlabel(word[0]))
1048 {
1049 2691 word++;
1050 2691 numwords--;
1051 }
1052
4/4
✓ Branch 0 taken 148083 times.
✓ Branch 1 taken 2115 times.
✓ Branch 2 taken 45891 times.
✓ Branch 3 taken 102192 times.
150198 if (!word[0] || !word[0][0]) return;
1053
12/12
✓ Branch 0 taken 100548 times.
✓ Branch 1 taken 1644 times.
✓ Branch 2 taken 99558 times.
✓ Branch 3 taken 990 times.
✓ Branch 4 taken 99468 times.
✓ Branch 5 taken 90 times.
✓ Branch 6 taken 93690 times.
✓ Branch 7 taken 5778 times.
✓ Branch 8 taken 1044 times.
✓ Branch 9 taken 92646 times.
✓ Branch 10 taken 9546 times.
✓ Branch 11 taken 92646 times.
102192 if (is("if") || is("elseif") || is("assert") || is("while") || is("for"))
1054 {
1055 9546 string errmsg;
1056 9546 whiletracker wstatus;
1057
1/2
✓ Branch 0 taken 9546 times.
✗ Branch 1 not taken.
9546 wstatus.startline = get_current_line();
1058 9546 wstatus.iswhile = is("while");
1059 9546 wstatus.cond = false;
1060 9546 wstatus.is_for = false;
1061 9546 wstatus.for_start = wstatus.for_end = wstatus.for_cur = 0;
1062 9546 wstatus.for_has_var_backup = false;
1063
2/2
✓ Branch 0 taken 1044 times.
✓ Branch 1 taken 8502 times.
9546 if(is("for")) wstatus.is_for = true;
1064
1065 9546 bool is_for_cont = false;
1066 // if this is a for loop and a whilestatus entry already exists at this level,
1067 // and the for loop isn't finished, this is a continuation of the for loop
1068
5/6
✓ Branch 0 taken 1042 times.
✓ Branch 1 taken 2 times.
✓ Branch 2 taken 1042 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 996 times.
✓ Branch 5 taken 46 times.
10590 if (is("for") && whilestatus.count > numif && whilestatus[numif].is_for
1069
8/10
✓ Branch 0 taken 1044 times.
✓ Branch 1 taken 8502 times.
✓ Branch 2 taken 996 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 996 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 738 times.
✓ Branch 7 taken 258 times.
✓ Branch 8 taken 738 times.
✓ Branch 9 taken 8808 times.
10590 && whilestatus[numif].for_cur < whilestatus[numif].for_end)
1070 738 is_for_cont = true;
1071
5/8
✓ Branch 0 taken 738 times.
✓ Branch 1 taken 8808 times.
✓ Branch 2 taken 738 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 8808 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 8808 times.
✗ Branch 7 not taken.
9546 whiletracker& addedwstatus = is_for_cont ? whilestatus[numif] : (whilestatus[numif] = wstatus);
1072
2/2
✓ Branch 0 taken 90 times.
✓ Branch 1 taken 9456 times.
9546 if (is("assert"))
1073 {
1074
1/2
✓ Branch 0 taken 90 times.
✗ Branch 1 not taken.
90 autoptr<char**> tokens = qpsplit(word[numwords - 1], ',');
1075
1/2
✓ Branch 0 taken 90 times.
✗ Branch 1 not taken.
90 verify_paren(tokens);
1076
5/6
✓ Branch 0 taken 90 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 36 times.
✓ Branch 3 taken 54 times.
✓ Branch 4 taken 36 times.
✓ Branch 5 taken 54 times.
90 if (tokens[0] != NULL && tokens[1] != NULL)
1077 {
1078 36 string rawerrmsg;
1079 36 size_t pos = 1;
1080
2/2
✓ Branch 0 taken 126 times.
✓ Branch 1 taken 36 times.
162 while (tokens[pos])
1081 {
1082
1/2
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
126 rawerrmsg += tokens[pos];
1083
2/2
✓ Branch 0 taken 90 times.
✓ Branch 1 taken 36 times.
126 if (tokens[pos + 1] != NULL)
1084 {
1085
1/2
✓ Branch 0 taken 90 times.
✗ Branch 1 not taken.
90 rawerrmsg += ",";
1086 }
1087 126 pos++;
1088 }
1089
1090
2/4
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 36 times.
✗ Branch 3 not taken.
36 errmsg = handle_print(rawerrmsg.raw());
1091 36 }
1092 90 }
1093
1094 //handle nested if statements
1095
8/8
✓ Branch 0 taken 1008 times.
✓ Branch 1 taken 8538 times.
✓ Branch 2 taken 666 times.
✓ Branch 3 taken 342 times.
✓ Branch 4 taken 144 times.
✓ Branch 5 taken 522 times.
✓ Branch 6 taken 486 times.
✓ Branch 7 taken 9060 times.
9546 if (numtrue!=numif && !(is("elseif") && numtrue+1==numif))
1096 {
1097
8/8
✓ Branch 0 taken 342 times.
✓ Branch 1 taken 144 times.
✓ Branch 2 taken 198 times.
✓ Branch 3 taken 144 times.
✓ Branch 4 taken 54 times.
✓ Branch 5 taken 144 times.
✓ Branch 6 taken 342 times.
✓ Branch 7 taken 144 times.
486 if ((is("if") || is("while") || is("for"))) numif++;
1098 486 return;
1099 }
1100
8/8
✓ Branch 0 taken 7560 times.
✓ Branch 1 taken 1500 times.
✓ Branch 2 taken 1926 times.
✓ Branch 3 taken 5634 times.
✓ Branch 4 taken 990 times.
✓ Branch 5 taken 936 times.
✓ Branch 6 taken 8124 times.
✓ Branch 7 taken 936 times.
9060 if ((is("if") || is("while") || is("for"))) numif++;
1101
1102
2/2
✓ Branch 0 taken 15912 times.
✓ Branch 1 taken 9060 times.
24972 for(int i = 1; i < numwords - 1; i++)
1103 {
1104 15912 word[i][strlen(word[i])] = ' ';
1105 }
1106 9060 numwords = 2;
1107
1108 bool cond;
1109
2/2
✓ Branch 0 taken 8070 times.
✓ Branch 1 taken 990 times.
9060 if(!is("for"))
1110 {
1111
1/2
✓ Branch 0 taken 8070 times.
✗ Branch 1 not taken.
8070 cond = getnum(word[1]);
1112
8/10
✓ Branch 0 taken 180 times.
✓ Branch 1 taken 7890 times.
✓ Branch 2 taken 90 times.
✓ Branch 3 taken 90 times.
✓ Branch 4 taken 90 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 90 times.
✓ Branch 7 taken 7980 times.
✗ Branch 8 not taken.
✓ Branch 9 taken 90 times.
8070 if (foundlabel && !foundlabel_static && !is("assert")) asar_throw_error(1, error_type_block, error_id_label_in_conditional, word[0]);
1113 }
1114
1115
2/2
✓ Branch 0 taken 990 times.
✓ Branch 1 taken 7980 times.
8970 if (is("for"))
1116 {
1117
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 990 times.
990 if(single_line_for_tracker != 1)
1118 {
1119 numif--;
1120 asar_throw_error(0, error_type_line, error_id_bad_single_line_for);
1121 }
1122
1123
2/2
✓ Branch 0 taken 252 times.
✓ Branch 1 taken 738 times.
990 if(!is_for_cont)
1124 {
1125 252 char* past_eq = strchr(word[1], '=');
1126
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 252 times.
252 if(!past_eq)
1127 asar_throw_error(0, error_type_block, error_id_broken_for_loop, "missing loop range");
1128
1129
1/2
✓ Branch 0 taken 252 times.
✗ Branch 1 not taken.
252 string varname(word[1], past_eq - word[1]);
1130 252 past_eq += 1;
1131
1/2
✓ Branch 0 taken 252 times.
✗ Branch 1 not taken.
252 strip_whitespace(varname);
1132
2/4
✓ Branch 0 taken 252 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 252 times.
252 if(!validatedefinename(varname))
1133 asar_throw_error(0, error_type_block, error_id_broken_for_loop, "invalid define name");
1134
1135
1/2
✓ Branch 0 taken 252 times.
✗ Branch 1 not taken.
252 char* range_sep = strqpstr(past_eq, "..");
1136
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 252 times.
252 if(!range_sep)
1137 asar_throw_error(0, error_type_block, error_id_broken_for_loop, "invalid loop range");
1138
1139
1/2
✓ Branch 0 taken 252 times.
✗ Branch 1 not taken.
252 string for_start(past_eq, range_sep - past_eq);
1140
1/2
✓ Branch 0 taken 252 times.
✗ Branch 1 not taken.
252 strip_whitespace(for_start);
1141
1/2
✓ Branch 0 taken 252 times.
✗ Branch 1 not taken.
252 string for_end(range_sep+2);
1142
1/2
✓ Branch 0 taken 252 times.
✗ Branch 1 not taken.
252 strip_whitespace(for_end);
1143
1144
1/2
✓ Branch 0 taken 252 times.
✗ Branch 1 not taken.
252 addedwstatus.for_start = getnum(for_start);
1145
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 252 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
252 if(foundlabel && !foundlabel_static)
1146 asar_throw_error(0, error_type_block, error_id_label_in_conditional, "for");
1147
1/2
✓ Branch 0 taken 252 times.
✗ Branch 1 not taken.
252 addedwstatus.for_end = getnum(for_end);
1148
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 252 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
252 if(foundlabel && !foundlabel_static)
1149 asar_throw_error(0, error_type_block, error_id_label_in_conditional, "for");
1150
1151
1/2
✓ Branch 0 taken 252 times.
✗ Branch 1 not taken.
252 addedwstatus.for_variable = varname;
1152 252 addedwstatus.for_cur = addedwstatus.for_start;
1153 252 }
1154 738 else addedwstatus.for_cur++;
1155
1156 990 addedwstatus.cond = addedwstatus.for_cur < addedwstatus.for_end;
1157 990 single_line_for_tracker = 2;
1158
2/2
✓ Branch 0 taken 738 times.
✓ Branch 1 taken 252 times.
990 if(addedwstatus.cond)
1159 {
1160 738 numtrue++;
1161
3/4
✓ Branch 0 taken 738 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 576 times.
✓ Branch 3 taken 162 times.
738 if(defines.exists(addedwstatus.for_variable))
1162 {
1163 576 addedwstatus.for_has_var_backup = true;
1164
2/4
✓ Branch 0 taken 576 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 576 times.
✗ Branch 3 not taken.
576 addedwstatus.for_var_backup = defines.find(addedwstatus.for_variable);
1165 }
1166
3/6
✓ Branch 0 taken 738 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 738 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 738 times.
✗ Branch 5 not taken.
738 defines.create(addedwstatus.for_variable) = ftostr(addedwstatus.for_cur);
1167 }
1168 }
1169
6/6
✓ Branch 0 taken 6570 times.
✓ Branch 1 taken 1410 times.
✓ Branch 2 taken 5634 times.
✓ Branch 3 taken 936 times.
✓ Branch 4 taken 7044 times.
✓ Branch 5 taken 936 times.
7980 else if (is("if") || is("while"))
1170 {
1171 if(0);
1172
2/2
✓ Branch 0 taken 5754 times.
✓ Branch 1 taken 1290 times.
7044 else if (cond)
1173 {
1174 5754 numtrue++;
1175
1/2
✓ Branch 0 taken 5754 times.
✗ Branch 1 not taken.
5754 elsestatus[numif]=true;
1176 }
1177
1/2
✓ Branch 0 taken 1290 times.
✗ Branch 1 not taken.
1290 else if (!cond)
1178 {
1179
1/2
✓ Branch 0 taken 1290 times.
✗ Branch 1 not taken.
1290 elsestatus[numif]=false;
1180 }
1181 7044 addedwstatus.cond = cond;
1182 }
1183
2/2
✓ Branch 0 taken 846 times.
✓ Branch 1 taken 90 times.
936 else if (is("elseif"))
1184 {
1185
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 846 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
846 if (!numif) asar_throw_error(1, error_type_block, error_id_misplaced_elseif);
1186
2/6
✓ Branch 0 taken 846 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 846 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
846 if (whilestatus[numif - 1].iswhile) asar_throw_error(1, error_type_block, error_id_elseif_in_while);
1187
2/2
✓ Branch 0 taken 324 times.
✓ Branch 1 taken 522 times.
846 if (numif==numtrue) numtrue--;
1188
7/8
✓ Branch 0 taken 324 times.
✓ Branch 1 taken 522 times.
✓ Branch 2 taken 324 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 234 times.
✓ Branch 5 taken 90 times.
✓ Branch 6 taken 234 times.
✓ Branch 7 taken 612 times.
846 if (cond && !elsestatus[numif])
1189 {
1190 234 numtrue++;
1191
1/2
✓ Branch 0 taken 234 times.
✗ Branch 1 not taken.
234 elsestatus[numif]=true;
1192 }
1193 }
1194 // otherwise, must be assert command
1195
4/4
✓ Branch 0 taken 30 times.
✓ Branch 1 taken 60 times.
✓ Branch 2 taken 24 times.
✓ Branch 3 taken 6 times.
90 else if (pass == 2 && !cond)
1196 {
1197
6/10
✓ Branch 0 taken 24 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 12 times.
✓ Branch 3 taken 12 times.
✓ Branch 4 taken 12 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 12 times.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✓ Branch 9 taken 12 times.
48 if (errmsg) asar_throw_error(2, error_type_block, error_id_assertion_failed, (string(": ") + errmsg).data());
1198
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 12 times.
12 else asar_throw_error(2, error_type_block, error_id_assertion_failed, ".");
1199 }
1200
4/4
✓ Branch 0 taken 8946 times.
✓ Branch 1 taken 486 times.
✓ Branch 2 taken 8946 times.
✓ Branch 3 taken 486 times.
10146 }
1201
14/14
✓ Branch 0 taken 18405 times.
✓ Branch 1 taken 74241 times.
✓ Branch 2 taken 16761 times.
✓ Branch 3 taken 1644 times.
✓ Branch 4 taken 16761 times.
✓ Branch 5 taken 74241 times.
✓ Branch 6 taken 10983 times.
✓ Branch 7 taken 5778 times.
✓ Branch 8 taken 10983 times.
✓ Branch 9 taken 74241 times.
✓ Branch 10 taken 1044 times.
✓ Branch 11 taken 9939 times.
✓ Branch 12 taken 8466 times.
✓ Branch 13 taken 84180 times.
92646 else if (is0("endif") || is0("endwhile") || is0("endfor"))
1202 {
1203
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 8466 times.
8466 if (!numif)
1204 asar_throw_error(1, error_type_block, error_id_misplaced_endif);
1205
1/2
✓ Branch 0 taken 8466 times.
✗ Branch 1 not taken.
8466 whiletracker& thisws = whilestatus[numif - 1];
1206
1207
3/4
✓ Branch 0 taken 1644 times.
✓ Branch 1 taken 5778 times.
✓ Branch 2 taken 1644 times.
✗ Branch 3 not taken.
7422 if((!thisws.is_for && !thisws.iswhile && !is("endif")) ||
1208
6/8
✓ Branch 0 taken 7422 times.
✓ Branch 1 taken 1044 times.
✓ Branch 2 taken 5778 times.
✓ Branch 3 taken 2688 times.
✓ Branch 4 taken 5778 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 8466 times.
24354 (thisws.iswhile && !is("endwhile")) ||
1209
3/4
✓ Branch 0 taken 1044 times.
✓ Branch 1 taken 7422 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 1044 times.
8466 (thisws.is_for && !is("endfor")))
1210 asar_throw_error(1, error_type_block, error_id_misplaced_endif);
1211
1212
2/2
✓ Branch 0 taken 6258 times.
✓ Branch 1 taken 2208 times.
8466 if (numif==numtrue) numtrue--;
1213 8466 numif--;
1214
1215
2/2
✓ Branch 0 taken 1044 times.
✓ Branch 1 taken 7422 times.
8466 if(thisws.is_for)
1216 {
1217
2/2
✓ Branch 0 taken 180 times.
✓ Branch 1 taken 864 times.
1044 if(single_line_for_tracker == 2) single_line_for_tracker = 3;
1218
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 1044 times.
1044 if(moreonline)
1219 {
1220 // sabotage the whilestatus to prevent the loop running again
1221 // and spamming more of the same error
1222 thisws.for_cur = thisws.for_end;
1223 thisws.cond = false;
1224 asar_throw_error(0, error_type_block, error_id_bad_single_line_for);
1225 }
1226
1227
2/2
✓ Branch 0 taken 738 times.
✓ Branch 1 taken 306 times.
1044 if(thisws.cond)
1228 {
1229
2/2
✓ Branch 0 taken 576 times.
✓ Branch 1 taken 162 times.
738 if(thisws.for_has_var_backup)
1230
2/4
✓ Branch 0 taken 576 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 576 times.
✗ Branch 3 not taken.
576 defines.create(thisws.for_variable) = thisws.for_var_backup;
1231 else
1232
1/2
✓ Branch 0 taken 162 times.
✗ Branch 1 not taken.
162 defines.remove(thisws.for_variable);
1233 }
1234 }
1235 }
1236
6/6
✓ Branch 0 taken 9939 times.
✓ Branch 1 taken 74241 times.
✓ Branch 2 taken 798 times.
✓ Branch 3 taken 9141 times.
✓ Branch 4 taken 798 times.
✓ Branch 5 taken 83382 times.
84180 else if (is0("else"))
1237 {
1238
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 798 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
798 if (!numif) asar_throw_error(1, error_type_block, error_id_misplaced_else);
1239
5/12
✓ Branch 0 taken 798 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 798 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 798 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 798 times.
✗ Branch 8 not taken.
✓ Branch 9 taken 798 times.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
798 if (whilestatus[numif - 1].iswhile || whilestatus[numif - 1].is_for) asar_throw_error(1, error_type_block, error_id_else_in_while_loop);
1240
2/2
✓ Branch 0 taken 318 times.
✓ Branch 1 taken 480 times.
798 else if (numif==numtrue) numtrue--;
1241
7/8
✓ Branch 0 taken 444 times.
✓ Branch 1 taken 36 times.
✓ Branch 2 taken 444 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 174 times.
✓ Branch 5 taken 270 times.
✓ Branch 6 taken 174 times.
✓ Branch 7 taken 306 times.
480 else if (numif==numtrue+1 && !elsestatus[numif])
1242 {
1243 174 numtrue++;
1244
1/2
✓ Branch 0 taken 174 times.
✗ Branch 1 not taken.
174 elsestatus[numif]=true;
1245 }
1246 }
1247
2/2
✓ Branch 0 taken 5196 times.
✓ Branch 1 taken 78186 times.
83382 else if (numif!=numtrue) return;
1248
4/4
✓ Branch 0 taken 78156 times.
✓ Branch 1 taken 30 times.
✓ Branch 2 taken 28959 times.
✓ Branch 3 taken 49197 times.
78186 else if (asblock_pick(word, numwords))
1249 {
1250
1/2
✓ Branch 0 taken 28959 times.
✗ Branch 1 not taken.
28959 add_addr_to_line(addrToLinePos);
1251 28959 numopcodes += recent_opcode_num;
1252 }
1253
12/12
✓ Branch 0 taken 45768 times.
✓ Branch 1 taken 3429 times.
✓ Branch 2 taken 34170 times.
✓ Branch 3 taken 11598 times.
✓ Branch 4 taken 34026 times.
✓ Branch 5 taken 144 times.
✓ Branch 6 taken 32238 times.
✓ Branch 7 taken 1788 times.
✓ Branch 8 taken 288 times.
✓ Branch 9 taken 31950 times.
✓ Branch 10 taken 13818 times.
✓ Branch 11 taken 35379 times.
49197 else if (numwords > 1 && (is("db") || is("dw") || is("dl") || is("dd")))
1254 {
1255 13818 string line;
1256
2/2
✓ Branch 0 taken 13818 times.
✓ Branch 1 taken 13818 times.
27636 for(int i = 1; i < numwords; i++){
1257
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 13818 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
13818 if(i > 1) line += " ";
1258
1/2
✓ Branch 0 taken 13818 times.
✗ Branch 1 not taken.
13818 line += word[i];
1259 }
1260
1/2
✓ Branch 0 taken 13818 times.
✗ Branch 1 not taken.
13818 autoptr<char**> pars=qpsplit(line.temp_raw(), ',');
1261
1/2
✓ Branch 0 taken 13818 times.
✗ Branch 1 not taken.
13818 verify_paren(pars);
1262
1263 void (*do_write)(unsigned int);
1264 13818 char first = to_lower(word[0][1]);
1265
2/2
✓ Branch 0 taken 11598 times.
✓ Branch 1 taken 2220 times.
13818 if (first == 'b') do_write = &write1;
1266
2/2
✓ Branch 0 taken 144 times.
✓ Branch 1 taken 2076 times.
2220 else if (first == 'w') do_write = &write2;
1267
2/2
✓ Branch 0 taken 1788 times.
✓ Branch 1 taken 288 times.
2076 else if (first == 'l') do_write = &write3;
1268 288 else do_write = &write4;
1269
1270
2/2
✓ Branch 0 taken 16308 times.
✓ Branch 1 taken 13752 times.
30060 for (int i=0;pars[i];i++)
1271 {
1272
2/2
✓ Branch 0 taken 669 times.
✓ Branch 1 taken 15639 times.
16308 if (pars[i][0]=='"')
1273 {
1274
1/2
✓ Branch 0 taken 669 times.
✗ Branch 1 not taken.
669 char * str=const_cast<char*>(safedequote(pars[i]));
1275 669 int codepoint = 0u;
1276
1/2
✓ Branch 0 taken 669 times.
✗ Branch 1 not taken.
669 str += utf8_val(&codepoint, str);
1277
3/4
✓ Branch 0 taken 2718 times.
✓ Branch 1 taken 669 times.
✓ Branch 2 taken 2718 times.
✗ Branch 3 not taken.
3387 while ( codepoint != 0 && codepoint != -1 )
1278 {
1279
2/4
✓ Branch 0 taken 2718 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2718 times.
✗ Branch 3 not taken.
2718 do_write(thetable.get_val(codepoint));
1280
1/2
✓ Branch 0 taken 2718 times.
✗ Branch 1 not taken.
2718 str += utf8_val(&codepoint, str);
1281 }
1282
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 669 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
669 if (codepoint == -1) asar_throw_error(0, error_type_block, error_id_invalid_utf8);
1283 }
1284 else
1285 {
1286
5/6
✓ Branch 0 taken 5207 times.
✓ Branch 1 taken 10432 times.
✓ Branch 2 taken 5141 times.
✓ Branch 3 taken 66 times.
✓ Branch 4 taken 15573 times.
✗ Branch 5 not taken.
15639 do_write((pass==2)?getnum(pars[i]):0);
1287 }
1288 }
1289
1/2
✓ Branch 0 taken 13752 times.
✗ Branch 1 not taken.
13752 add_addr_to_line(addrToLinePos);
1290 13884 }
1291
2/2
✓ Branch 0 taken 1566 times.
✓ Branch 1 taken 33813 times.
35379 else if(word[0][0]=='%')
1292 {
1293
2/2
✓ Branch 0 taken 1530 times.
✓ Branch 1 taken 36 times.
1566 callmacro(strchr(block, '%')+1);
1294 }
1295
6/6
✓ Branch 0 taken 29310 times.
✓ Branch 1 taken 4503 times.
✓ Branch 2 taken 360 times.
✓ Branch 3 taken 28950 times.
✓ Branch 4 taken 360 times.
✓ Branch 5 taken 33453 times.
33813 else if (is1("undef"))
1296 {
1297
2/4
✓ Branch 0 taken 360 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 360 times.
✗ Branch 3 not taken.
360 string def = safedequote(par);
1298
1299
3/4
✓ Branch 0 taken 360 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 342 times.
✓ Branch 3 taken 18 times.
360 if (defines.exists(def))
1300 {
1301
1/2
✓ Branch 0 taken 342 times.
✗ Branch 1 not taken.
342 defines.remove(def);
1302 }
1303 else
1304 {
1305
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
18 asar_throw_error(0, error_type_block, error_id_define_not_found, def.data());
1306 }
1307 360 }
1308
6/6
✓ Branch 0 taken 1881 times.
✓ Branch 1 taken 31572 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 1863 times.
✓ Branch 4 taken 18 times.
✓ Branch 5 taken 33435 times.
33453 else if (is0("error"))
1309 {
1310
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
18 asar_throw_error(0, error_type_block, error_id_error_command, ".");
1311 }
1312
6/6
✓ Branch 0 taken 1863 times.
✓ Branch 1 taken 31572 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 1845 times.
✓ Branch 4 taken 18 times.
✓ Branch 5 taken 33417 times.
33435 else if (is0("warn"))
1313 {
1314
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 asar_throw_warning(2, warning_id_warn_command, ".");
1315 }
1316
6/6
✓ Branch 0 taken 28950 times.
✓ Branch 1 taken 4467 times.
✓ Branch 2 taken 39 times.
✓ Branch 3 taken 28911 times.
✓ Branch 4 taken 39 times.
✓ Branch 5 taken 33378 times.
33417 else if (is1("error"))
1317 {
1318
1/2
✓ Branch 0 taken 39 times.
✗ Branch 1 not taken.
39 string out = handle_print(par);
1319 // RPG Hacker: This used to be on pass 0, which had its merits (you don't want to miss a potentially critical
1320 // user-generated error, just because a bazillion other errors are thrown in passes before it). However, I
1321 // don't see how to support print functions with this without moving it to pass 2. Suggestions are welcome.
1322
3/6
✓ Branch 0 taken 39 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 39 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 39 times.
117 asar_throw_error(2, error_type_block, error_id_error_command, (string(": ") + out).data());
1323 39 }
1324
6/6
✓ Branch 0 taken 28911 times.
✓ Branch 1 taken 4467 times.
✓ Branch 2 taken 39 times.
✓ Branch 3 taken 28872 times.
✓ Branch 4 taken 39 times.
✓ Branch 5 taken 33339 times.
33378 else if (is1("warn"))
1325 {
1326
1/2
✓ Branch 0 taken 39 times.
✗ Branch 1 not taken.
39 string out = handle_print(par);
1327
3/6
✓ Branch 0 taken 39 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 39 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 39 times.
✗ Branch 5 not taken.
39 asar_throw_warning(2, warning_id_warn_command, (string(": ") + out).data());
1328 39 }
1329
6/6
✓ Branch 0 taken 28872 times.
✓ Branch 1 taken 4467 times.
✓ Branch 2 taken 144 times.
✓ Branch 3 taken 28728 times.
✓ Branch 4 taken 144 times.
✓ Branch 5 taken 33195 times.
33339 else if (is1("warnings"))
1330 {
1331
4/4
✓ Branch 0 taken 108 times.
✓ Branch 1 taken 36 times.
✓ Branch 2 taken 36 times.
✓ Branch 3 taken 36 times.
144 if (stricmp(word[1], "push") == 0)
1332 {
1333
1/2
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
72 push_warnings();
1334 }
1335
2/4
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 36 times.
✗ Branch 3 not taken.
72 else if (stricmp(word[1], "pull") == 0)
1336 {
1337
2/2
✓ Branch 0 taken 54 times.
✓ Branch 1 taken 18 times.
72 pull_warnings();
1338 }
1339 else
1340 {
1341 asar_throw_error(0, error_type_block, error_id_broken_command, "warnings", "Unknown parameter");
1342 }
1343 }
1344
6/6
✓ Branch 0 taken 2424 times.
✓ Branch 1 taken 30771 times.
✓ Branch 2 taken 252 times.
✓ Branch 3 taken 2172 times.
✓ Branch 4 taken 252 times.
✓ Branch 5 taken 32943 times.
33195 else if (is2("warnings"))
1345 {
1346
4/4
✓ Branch 0 taken 153 times.
✓ Branch 1 taken 99 times.
✓ Branch 2 taken 27 times.
✓ Branch 3 taken 99 times.
252 if (stricmp(word[1], "enable") == 0)
1347 {
1348
1/2
✓ Branch 0 taken 54 times.
✗ Branch 1 not taken.
54 asar_warning_id warnid = parse_warning_id_from_string(word[2]);
1349
1350
2/2
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 18 times.
54 if (warnid != warning_id_end)
1351 {
1352
1/2
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
36 set_warning_enabled(warnid, true);
1353 }
1354 else
1355 {
1356
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
18 asar_throw_error(0, error_type_block, error_id_invalid_warning_id, word[2], "warnings enable");
1357 }
1358 }
1359
2/4
✓ Branch 0 taken 198 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 99 times.
✗ Branch 3 not taken.
198 else if (stricmp(word[1], "disable") == 0)
1360 {
1361
1/2
✓ Branch 0 taken 198 times.
✗ Branch 1 not taken.
198 asar_warning_id warnid = parse_warning_id_from_string(word[2]);
1362
1363
2/2
✓ Branch 0 taken 162 times.
✓ Branch 1 taken 36 times.
198 if (warnid != warning_id_end)
1364 {
1365
1/2
✓ Branch 0 taken 162 times.
✗ Branch 1 not taken.
162 set_warning_enabled(warnid, false);
1366 }
1367 else
1368 {
1369
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 36 times.
36 asar_throw_error(0, error_type_block, error_id_invalid_warning_id, word[2], "warnings disable");
1370 }
1371 }
1372 else
1373 {
1374 asar_throw_error(0, error_type_block, error_id_broken_command, "warnings", "Unknown parameter");
1375 }
1376 }
1377
6/6
✓ Branch 0 taken 28728 times.
✓ Branch 1 taken 4215 times.
✓ Branch 2 taken 126 times.
✓ Branch 3 taken 28602 times.
✓ Branch 4 taken 126 times.
✓ Branch 5 taken 32817 times.
32943 else if(is1("global"))
1378 {
1379
3/4
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 36 times.
✓ Branch 3 taken 90 times.
126 if (!addlabel(word[1], -1, true))
1380 {
1381
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 36 times.
36 asar_throw_error(1, error_type_block, error_id_invalid_global_label, word[1]);
1382 }
1383 }
1384
6/6
✓ Branch 0 taken 2172 times.
✓ Branch 1 taken 30645 times.
✓ Branch 2 taken 210 times.
✓ Branch 3 taken 1962 times.
✓ Branch 4 taken 210 times.
✓ Branch 5 taken 32607 times.
32817 else if (is2("check"))
1385 {
1386
4/4
✓ Branch 0 taken 114 times.
✓ Branch 1 taken 96 times.
✓ Branch 2 taken 9 times.
✓ Branch 3 taken 96 times.
210 if (stricmp(word[1], "title") == 0)
1387 {
1388 // RPG Hacker: Removed trimming for now - I think requiring an exact match is probably
1389 // better here (not sure, though, it's worth discussing)
1390
2/4
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 18 times.
✗ Branch 3 not taken.
18 string expected_title = safedequote(word[2]);
1391 // randomdude999: this also removes leading spaces because itrim gets stuck in an endless
1392 // loop when multi is true and one argument is empty
1393 // in hirom the rom needs to be an entire bank for it to have a title, other modes only need 0x8000 bytes
1394
3/6
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 18 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 18 times.
18 if (romlen < ((mapper == hirom || mapper == exhirom) ? 0x10000 : 0x8000)) // too short
1395 {
1396 if (!ignoretitleerrors) // title errors shouldn't be ignored
1397 asar_throw_error(0, error_type_block, error_id_rom_too_short, expected_title.data());
1398 else // title errors should be ignored, throw a warning anyways
1399 asar_throw_warning(0, warning_id_rom_too_short, expected_title.data());
1400 }
1401 else {
1402 18 string actual_title;
1403 18 string actual_display_title;
1404
2/2
✓ Branch 0 taken 378 times.
✓ Branch 1 taken 18 times.
396 for (int i = 0;i < 21;i++)
1405 {
1406
1/2
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
378 unsigned char c = romdata[snestopc(0x00FFC0 + i)];
1407
1/2
✓ Branch 0 taken 378 times.
✗ Branch 1 not taken.
378 actual_title += (char)c;
1408 // the replacements are from interface-cli.cpp
1409
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 378 times.
378 if (c == 7) c = 14;
1410
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 378 times.
378 if (c == 8) c = 27;
1411
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 378 times.
378 if (c == 9) c = 26;
1412
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 378 times.
378 if (c == '\r') c = 17;
1413
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 378 times.
378 if (c == '\n') c = 25;
1414
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 378 times.
378 if (c == '\0') c = 155;
1415
1/2
✓ Branch 0 taken 378 times.
✗ Branch 1 not taken.
378 actual_display_title += (char)c;
1416 }
1417
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
18 if (strncmp(expected_title, actual_title, 21) != 0)
1418 {
1419 if (!ignoretitleerrors) // title errors shouldn't be ignored
1420 asar_throw_error(0, error_type_block, error_id_rom_title_incorrect, expected_title.data(), actual_display_title.data());
1421 else // title errors should be ignored, throw a warning anyways
1422 asar_throw_warning(0, warning_id_rom_title_incorrect, expected_title.data(), actual_display_title.data());
1423 }
1424 18 }
1425 18 }
1426
2/4
✓ Branch 0 taken 192 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 96 times.
✗ Branch 3 not taken.
192 else if (stricmp(word[1], "bankcross") == 0)
1427 {
1428 if (0);
1429
4/4
✓ Branch 0 taken 141 times.
✓ Branch 1 taken 51 times.
✓ Branch 2 taken 45 times.
✓ Branch 3 taken 51 times.
192 else if (!stricmp(word[2], "off"))
1430 {
1431 90 disable_bank_cross_errors = true;
1432 }
1433
4/4
✓ Branch 0 taken 99 times.
✓ Branch 1 taken 3 times.
✓ Branch 2 taken 48 times.
✓ Branch 3 taken 3 times.
102 else if (!stricmp(word[2], "half"))
1434 {
1435 96 disable_bank_cross_errors = false;
1436 96 check_half_banks_crossed = true;
1437 }
1438
2/4
✓ Branch 0 taken 6 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 3 times.
✗ Branch 3 not taken.
6 else if (!stricmp(word[2], "full"))
1439 {
1440 6 disable_bank_cross_errors = false;
1441 6 check_half_banks_crossed = false;
1442 }
1443 else asar_throw_error(0, error_type_block, error_id_invalid_check);
1444
1445 }
1446 else
1447 {
1448 asar_throw_error(0, error_type_block, error_id_invalid_check);
1449 }
1450 }
1451
9/10
✓ Branch 0 taken 1845 times.
✓ Branch 1 taken 30762 times.
✓ Branch 2 taken 1845 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 28602 times.
✓ Branch 5 taken 4005 times.
✓ Branch 6 taken 108 times.
✓ Branch 7 taken 28494 times.
✓ Branch 8 taken 108 times.
✓ Branch 9 taken 32499 times.
32607 else if (is0("asar") || is1("asar"))
1452 {
1453
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 108 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
108 if (!asarverallowed) asar_throw_error(0, error_type_block, error_id_start_of_file);
1454
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 108 times.
198 if (!par) return;
1455 108 int dots=0;
1456 108 int dig=0;
1457
2/2
✓ Branch 0 taken 450 times.
✓ Branch 1 taken 108 times.
558 for (int i=0;par[i];i++)
1458 {
1459
2/2
✓ Branch 0 taken 126 times.
✓ Branch 1 taken 324 times.
450 if (par[i]=='.')
1460 {
1461
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 126 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
126 if (!dig) asar_throw_error(0, error_type_block, error_id_invalid_version_number);
1462 126 dig=0;
1463 126 dots++;
1464 }
1465
1/2
✓ Branch 0 taken 324 times.
✗ Branch 1 not taken.
324 else if (is_digit(par[i])) dig++;
1466 else asar_throw_error(0, error_type_block, error_id_invalid_version_number);
1467 }
1468
3/8
✓ Branch 0 taken 108 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 108 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 108 times.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
108 if (!dig || !dots || dots>2) asar_throw_error(0, error_type_block, error_id_invalid_version_number);
1469
1/2
✓ Branch 0 taken 108 times.
✗ Branch 1 not taken.
108 autoptr<char**> vers=split(par, '.');
1470 108 int vermaj=atoi(vers[0]);
1471
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 108 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
108 if (vermaj > asarver_maj) asar_throw_error(pass, error_type_fatal, error_id_asar_too_old);
1472
2/2
✓ Branch 0 taken 90 times.
✓ Branch 1 taken 18 times.
108 if (vermaj<asarver_maj) return;
1473
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
18 if (dots==1)
1474 {
1475 if (strlen(vers[1])!=2) asar_throw_error(0, error_type_block, error_id_invalid_version_number);
1476 //if (asarver_min<10 && asarver_bug<10 && strlen(vers[1])>2) error(0, "This version of Asar is too old for this patch.");
1477 int verminbug=atoi(vers[1]);
1478 int tmpver=asarver_bug;
1479 if (tmpver>9) tmpver=9;
1480 if (asarver_min*10+tmpver<verminbug) asar_throw_error(pass, error_type_fatal, error_id_asar_too_old);
1481 }
1482 else
1483 {
1484 18 int vermin=atoi(vers[1]);
1485
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
18 if (vermin>asarver_min) asar_throw_error(pass, error_type_fatal, error_id_asar_too_old);
1486 18 int verbug=atoi(vers[2]);
1487
2/6
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 18 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
18 if (vermin==asarver_min && verbug>asarver_bug) asar_throw_error(pass, error_type_fatal, error_id_asar_too_old);
1488 }
1489
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 90 times.
108 }
1490
10/10
✓ Branch 0 taken 1845 times.
✓ Branch 1 taken 30654 times.
✓ Branch 2 taken 1839 times.
✓ Branch 3 taken 6 times.
✓ Branch 4 taken 28494 times.
✓ Branch 5 taken 3999 times.
✓ Branch 6 taken 18 times.
✓ Branch 7 taken 28476 times.
✓ Branch 8 taken 24 times.
✓ Branch 9 taken 32475 times.
32499 else if (is0("include") || is1("includefrom"))
1491 {
1492
3/4
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 6 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 18 times.
24 if (!asarverallowed) asar_throw_error(0, error_type_block, error_id_start_of_file);
1493
2/4
✓ Branch 0 taken 6 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 6 times.
✗ Branch 3 not taken.
6 if (in_top_level_file())
1494 {
1495
1/10
✗ Branch 0 not taken.
✓ Branch 1 taken 6 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
6 if (par) asar_throw_error(pass, error_type_fatal, error_id_cant_be_main_file, (string(" The main file is '") + par + "'.").data());
1496
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6 times.
6 else asar_throw_error(pass, error_type_fatal, error_id_cant_be_main_file, "");
1497 }
1498 }
1499
6/6
✓ Branch 0 taken 1839 times.
✓ Branch 1 taken 30636 times.
✓ Branch 2 taken 90 times.
✓ Branch 3 taken 1749 times.
✓ Branch 4 taken 90 times.
✓ Branch 5 taken 32385 times.
32475 else if (is0("includeonce"))
1500 {
1501
1/2
✓ Branch 0 taken 90 times.
✗ Branch 1 not taken.
90 const char* current_file = get_current_file_name();
1502
2/4
✓ Branch 0 taken 90 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 90 times.
✗ Branch 3 not taken.
90 if (!file_included_once(current_file))
1503 {
1504
2/4
✓ Branch 0 taken 90 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 90 times.
✗ Branch 3 not taken.
90 includeonce.append(current_file);
1505 }
1506 }
1507
8/8
✓ Branch 0 taken 1962 times.
✓ Branch 1 taken 30423 times.
✓ Branch 2 taken 1701 times.
✓ Branch 3 taken 261 times.
✓ Branch 4 taken 720 times.
✓ Branch 5 taken 261 times.
✓ Branch 6 taken 720 times.
✓ Branch 7 taken 15378 times.
32385 else if (numwords==3 && !stricmp(word[1], "="))
1508 {
1509
3/4
✓ Branch 0 taken 1206 times.
✓ Branch 1 taken 234 times.
✓ Branch 2 taken 1206 times.
✗ Branch 3 not taken.
1440 if(word[0][0] == '\'' && word[0][1])
1510 {
1511 int codepoint;
1512 1206 const char* char_start = word[0]+1;
1513
1/2
✓ Branch 0 taken 1206 times.
✗ Branch 1 not taken.
1206 const char* after = char_start + utf8_val(&codepoint, char_start);
1514
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 1206 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
1206 if (codepoint == -1) asar_throw_error(0, error_type_block, error_id_invalid_utf8);
1515
2/4
✓ Branch 0 taken 1206 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 1206 times.
✗ Branch 3 not taken.
1206 if(after[0] == '\'' && after[1] == '\0') {
1516
3/4
✓ Branch 0 taken 1188 times.
✓ Branch 1 taken 18 times.
✓ Branch 2 taken 1188 times.
✗ Branch 3 not taken.
1206 thetable.set_val(codepoint, getnum(word[2]));
1517
3/6
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 1170 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 18 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
1188 if (foundlabel && !foundlabel_static) asar_throw_error(0, error_type_block, error_id_no_labels_here);
1518 1188 return;
1519 } // todo: error checking here
1520 }
1521 // randomdude999: int cast b/c i'm too lazy to also mess with making setlabel()
1522 // unsigned, besides it wouldn't matter anyways.
1523
1/2
✓ Branch 0 taken 234 times.
✗ Branch 1 not taken.
234 int num=(int)getnum(word[2]);
1524
5/6
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 198 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 18 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 18 times.
234 if (foundlabel && !foundlabel_static) asar_throw_error(0, error_type_block, error_id_label_cross_assignment);
1525
1526 216 const char* newlabelname = word[0];
1527 216 bool ismacro = false;
1528
1529
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 198 times.
216 if (newlabelname[0] == '?')
1530 {
1531 18 ismacro = true;
1532 18 newlabelname++;
1533 }
1534
1535
3/4
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 198 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 18 times.
216 if (ismacro && macrorecursion == 0)
1536 {
1537 asar_throw_error(0, error_type_block, error_id_macro_label_outside_of_macro);
1538 }
1539
1540
3/7
✓ Branch 0 taken 72 times.
✓ Branch 1 taken 144 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 72 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
216 if (!confirmname(newlabelname)) asar_throw_error(0, error_type_block, error_id_invalid_label_name);
1541
1542 216 string completename;
1543
1544
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 198 times.
216 if (ismacro)
1545 {
1546
5/10
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 18 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 18 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 18 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 18 times.
✗ Branch 9 not taken.
18 completename += STR":macro_" + dec(calledmacros) + "_";
1547 }
1548
1549
1/2
✓ Branch 0 taken 216 times.
✗ Branch 1 not taken.
216 completename += newlabelname;
1550
1551
2/4
✓ Branch 0 taken 216 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 216 times.
✗ Branch 3 not taken.
216 setlabel(ns + completename, num, true);
1552 216 }
1553
3/4
✓ Branch 0 taken 30945 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 30240 times.
✓ Branch 3 taken 705 times.
30945 else if (assemblemapper(word, numwords)) {}
1554
6/6
✓ Branch 0 taken 28419 times.
✓ Branch 1 taken 1821 times.
✓ Branch 2 taken 2364 times.
✓ Branch 3 taken 26055 times.
✓ Branch 4 taken 2364 times.
✓ Branch 5 taken 27876 times.
30240 else if (is1("org"))
1555 {
1556
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 2364 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
2364 if(in_spcblock) asar_throw_error(0, error_type_block, error_id_feature_unavaliable_in_spcblock);
1557
1/2
✓ Branch 0 taken 2364 times.
✗ Branch 1 not taken.
2364 freespaceend();
1558
1/2
✓ Branch 0 taken 2364 times.
✗ Branch 1 not taken.
2364 unsigned int num=getnum(par);
1559
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 2364 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
2364 if (forwardlabel) asar_throw_error(0, error_type_block, error_id_org_label_forward);
1560
1/6
✗ Branch 0 not taken.
✓ Branch 1 taken 2364 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
2364 if (num&~0xFFFFFF) asar_throw_error(1, error_type_block, error_id_snes_address_out_of_bounds, hex(num, 6).data());
1561
5/10
✓ Branch 0 taken 813 times.
✓ Branch 1 taken 1551 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 795 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 1569 times.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
2364 if ((mapper==lorom || mapper==exlorom) && (num&0x408000)==0x400000 && (num&0x700000)!=0x700000) asar_throw_warning(0, warning_id_set_middle_byte);
1562 //if (fastrom) num|=0x800000;
1563 2364 snespos=(int)num;
1564 2364 realsnespos=(int)num;
1565 2364 startpos=(int)num;
1566 2364 realstartpos=(int)num;
1567 2364 snespos_valid = true;
1568 }
1569 #define ret_error(errid) { asar_throw_error(0, error_type_block, errid); return; }
1570 #define ret_error_params(errid, ...) { asar_throw_error(0, error_type_block, errid, __VA_ARGS__); return; }
1571
2/2
✓ Branch 0 taken 270 times.
✓ Branch 1 taken 27606 times.
27876 else if (is("struct"))
1572 {
1573 //verifysnespos();
1574
2/6
✓ Branch 0 taken 270 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 270 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
270 if (in_struct || in_sub_struct) ret_error(error_id_nested_struct);
1575
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 270 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
270 if (numwords < 2) ret_error(error_id_missing_struct_params);
1576
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 270 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
270 if (numwords > 4) ret_error(error_id_too_many_struct_params);
1577
3/7
✓ Branch 0 taken 90 times.
✓ Branch 1 taken 180 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 90 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
270 if (!confirmname(word[1])) ret_error(error_id_invalid_struct_name);
1578
1579
5/10
✓ Branch 0 taken 270 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 132 times.
✓ Branch 3 taken 138 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 132 times.
✗ Branch 6 not taken.
✓ Branch 7 taken 270 times.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
270 if (structs.exists(word[1]) && pass == 0) ret_error_params(error_id_struct_redefined, word[1]);
1580
1581 270 static_struct = false;
1582 270 old_snespos = snespos;
1583 270 old_startpos = startpos;
1584 270 old_optimizeforbank = optimizeforbank;
1585 270 old_snespos_valid = snespos_valid;
1586 270 unsigned int base = 0;
1587
2/2
✓ Branch 0 taken 90 times.
✓ Branch 1 taken 180 times.
270 if (numwords == 3)
1588 {
1589 90 static_struct = true;
1590
1/2
✓ Branch 0 taken 90 times.
✗ Branch 1 not taken.
90 base = getnum(word[2]);
1591
1592
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 90 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
90 if (foundlabel && !foundlabel_static) static_struct = false;
1593 }
1594
1595 270 bool old_in_struct = in_struct;
1596 270 bool old_in_sub_struct = in_sub_struct;
1597
4/4
✓ Branch 0 taken 162 times.
✓ Branch 1 taken 108 times.
✓ Branch 2 taken 90 times.
✓ Branch 3 taken 72 times.
270 in_struct = numwords == 2 || numwords == 3;
1598 270 in_sub_struct = numwords == 4;
1599
1600 #define ret_error_cleanup(errid) { in_struct = old_in_struct; in_sub_struct = old_in_sub_struct; asar_throw_error(0, error_type_block, errid); return; }
1601 #define ret_error_params_cleanup(errid, ...) { in_struct = old_in_struct; in_sub_struct = old_in_sub_struct; asar_throw_error(0, error_type_block, errid, __VA_ARGS__); return; }
1602
1603
2/2
✓ Branch 0 taken 90 times.
✓ Branch 1 taken 180 times.
270 if (numwords == 3)
1604 {
1605
1/6
✗ Branch 0 not taken.
✓ Branch 1 taken 90 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
90 if (base&~0xFFFFFF) ret_error_params_cleanup(error_id_snes_address_out_of_bounds, hex((unsigned int)base, 6).data());
1606 90 snespos = (int)base;
1607 90 startpos = (int)base;
1608 }
1609
2/2
✓ Branch 0 taken 72 times.
✓ Branch 1 taken 108 times.
180 else if (numwords == 4)
1610 {
1611
3/6
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 36 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 36 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
72 if (strcasecmp(word[2], "extends")) ret_error_cleanup(error_id_missing_extends);
1612
3/7
✓ Branch 0 taken 24 times.
✓ Branch 1 taken 48 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 24 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
72 if (!confirmname(word[3])) ret_error_cleanup(error_id_struct_invalid_parent_name);
1613
1/2
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
72 string tmp_struct_parent = word[3];
1614
1615
2/6
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 72 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
72 if (!structs.exists(tmp_struct_parent)) ret_error_params_cleanup(error_id_struct_not_found, tmp_struct_parent.data());
1616
2/4
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 72 times.
✗ Branch 3 not taken.
72 snes_struct structure = structs.find(tmp_struct_parent);
1617
1618 72 static_struct = structure.is_static;
1619
1/2
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
72 struct_parent = tmp_struct_parent;
1620 72 snespos = structure.base_end;
1621 72 startpos = structure.base_end;
1622
1/2
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
72 }
1623
1624
1/2
✓ Branch 0 taken 270 times.
✗ Branch 1 not taken.
270 push_pc();
1625
1626 270 optimizeforbank = -1;
1627
1628
1/2
✓ Branch 0 taken 270 times.
✗ Branch 1 not taken.
270 struct_name = word[1];
1629 270 struct_base = snespos;
1630 270 realsnespos = 0;
1631 270 realstartpos = 0;
1632 270 snespos_valid = true;
1633
1634
2/4
✓ Branch 0 taken 270 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 270 times.
✗ Branch 3 not taken.
270 setlabel(ns + struct_name, snespos, static_struct);
1635
1636 #undef ret_error_cleanup
1637 #undef ret_error_params_cleanup
1638 }
1639
2/2
✓ Branch 0 taken 270 times.
✓ Branch 1 taken 27336 times.
27606 else if (is("endstruct"))
1640 {
1641
3/6
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 252 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 18 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
270 if (numwords != 1 && numwords != 3) ret_error(error_id_invalid_endstruct_count);
1642
6/10
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 252 times.
✓ Branch 2 taken 9 times.
✓ Branch 3 taken 9 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 9 times.
✗ Branch 6 not taken.
✓ Branch 7 taken 135 times.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
270 if (numwords == 3 && strcasecmp(word[1], "align")) ret_error(error_id_expected_align);
1643
3/6
✓ Branch 0 taken 72 times.
✓ Branch 1 taken 198 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 72 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
270 if (!in_struct && !in_sub_struct) ret_error(error_id_endstruct_without_struct);
1644
1645
3/4
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 252 times.
✓ Branch 2 taken 18 times.
✗ Branch 3 not taken.
270 int alignment = numwords == 3 ? (int)getnum(word[2]) : 1;
1646
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 270 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
270 if (alignment < 1) ret_error(error_id_alignment_too_small);
1647
1648 270 snes_struct structure;
1649 270 structure.base_end = snespos;
1650 270 structure.struct_size = alignment * ((snespos - struct_base + alignment - 1) / alignment);
1651 270 structure.object_size = structure.struct_size;
1652 270 structure.is_static = static_struct;
1653
1654
2/2
✓ Branch 0 taken 198 times.
✓ Branch 1 taken 72 times.
270 if (in_struct)
1655 {
1656
2/4
✓ Branch 0 taken 198 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 198 times.
✗ Branch 3 not taken.
198 structs.create(struct_name) = structure;
1657 }
1658
1/2
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
72 else if (in_sub_struct)
1659 {
1660 72 snes_struct parent;
1661
2/4
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 72 times.
✗ Branch 3 not taken.
72 parent = structs.find(struct_parent);
1662
1663
1/2
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
72 if (parent.object_size < parent.struct_size + structure.struct_size) {
1664 72 parent.object_size = parent.struct_size + structure.struct_size;
1665 }
1666
1667
4/8
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 72 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 72 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 72 times.
✗ Branch 7 not taken.
72 structs.create(struct_parent + "." + struct_name) = structure;
1668
2/4
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 72 times.
✗ Branch 3 not taken.
72 structs.create(struct_parent) = parent;
1669 72 }
1670
1671
1/2
✓ Branch 0 taken 270 times.
✗ Branch 1 not taken.
270 pop_pc();
1672 270 in_struct = false;
1673 270 in_sub_struct = false;
1674 270 snespos = old_snespos;
1675 270 startpos = old_startpos;
1676 270 optimizeforbank = old_optimizeforbank;
1677 270 snespos_valid = old_snespos_valid;
1678 270 static_struct = false;
1679 270 }
1680 #undef ret_error
1681
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 27318 times.
27336 else if(is("spcblock"))
1682 {
1683 //banned features when active: org, freespace(and variants), arch, mapper,namespace,pushns
1684
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
18 if(arch != arch_spc700) asar_throw_error(0, error_type_block, error_id_spcblock_bad_arch);
1685
2/6
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 18 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
18 if(in_struct || in_sub_struct) asar_throw_error(0, error_type_block, error_id_spcblock_inside_struct);
1686
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
18 if(numwords < 2) asar_throw_error(0, error_type_block, error_id_spcblock_too_few_args);
1687
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
18 if(numwords > 4) asar_throw_error(0, error_type_block, error_id_spcblock_too_many_args);
1688
1689
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 spcblock.destination = getnum(par);
1690 18 spcblock.type = spcblock_nspc;
1691
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 spcblock.macro_name = "";
1692
1693
1/6
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
18 if (spcblock.destination&~0xFFFF) asar_throw_error(0, error_type_block, error_id_snes_address_out_of_bounds, hex(spcblock.destination, 6).data());
1694
1695
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
18 if(numwords == 3)
1696 {
1697 if(!stricmp(word[2], "nspc")) spcblock.type = spcblock_nspc;
1698 else if(!stricmp(word[2], "custom")) asar_throw_error(0, error_type_block, error_id_custom_spcblock_missing_macro);
1699 else asar_throw_error(0, error_type_block, error_id_unknown_spcblock_type);
1700 }
1701
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
18 else if(numwords == 4)
1702 {
1703 if(!stricmp(word[2], "custom")) spcblock.type = spcblock_custom;
1704 else asar_throw_error(0, error_type_block, error_id_extra_spcblock_arg_for_type);
1705
1706 if(macros.exists(word[3]))
1707 {
1708 macrodata *macro = macros.find(word[3]);
1709 if(!macro->variadic) asar_throw_error(0, error_type_block, error_id_spcblock_macro_must_be_varadic);
1710 if(macro->numargs != 3) asar_throw_error(0, error_type_block, error_id_spcblock_macro_invalid_static_args);
1711 spcblock.macro_name = word[3];
1712 }
1713 else asar_throw_error(0, error_type_block, error_id_spcblock_macro_doesnt_exist);
1714 }
1715
1716
1/3
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
18 switch(spcblock.type)
1717 {
1718 18 case spcblock_nspc:
1719 18 spcblock.size_address=realsnespos;
1720
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 write2(0x0000);
1721
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 write2(spcblock.destination);
1722 18 snespos=(int)spcblock.destination;
1723 18 startpos=(int)spcblock.destination;
1724 18 spcblock.execute_address = -1u;
1725
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 add_addr_to_line(addrToLinePos);
1726 18 break;
1727 case spcblock_custom:
1728 //this is a todo that probably won't be ready for 1.9
1729 //mostly so we can leverage some cleanups we make in 2.0 for practicality
1730 asar_throw_error(0, error_type_block, error_id_spcblock_custom_types_incomplete);
1731 push_pc();
1732 spcblock.old_mapper = mapper;
1733 mapper = norom;
1734 break;
1735 default:
1736 asar_throw_error(0, error_type_fatal, error_id_internal_error, "invalid spcblock type");
1737 }
1738
1739
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 ns_backup = ns;
1740
3/6
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 18 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 18 times.
✗ Branch 5 not taken.
18 ns = STR":SPCBLOCK:_" + ns_backup;
1741 18 in_spcblock = true;
1742 }
1743
6/6
✓ Branch 0 taken 849 times.
✓ Branch 1 taken 26469 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 831 times.
✓ Branch 4 taken 18 times.
✓ Branch 5 taken 27300 times.
27318 else if(is0("endspcblock"))
1744 {
1745
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
18 if(!in_spcblock) asar_throw_error(0, error_type_block, error_id_endspcblock_without_spcblock);
1746
1747
1/3
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
18 switch(spcblock.type)
1748 {
1749 18 case spcblock_nspc:
1750
2/2
✓ Branch 0 taken 6 times.
✓ Branch 1 taken 12 times.
18 if (pass==2)
1751 {
1752
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
6 int pcpos=snestopc(spcblock.size_address&0xFFFFFF);
1753
1/6
✗ Branch 0 not taken.
✓ Branch 1 taken 6 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
6 if (pcpos<0) asar_throw_error(2, error_type_block, error_id_snes_address_doesnt_map_to_rom, hex((unsigned int)realsnespos, 6).data());
1754 6 int num=snespos-startpos;
1755
1/2
✓ Branch 0 taken 6 times.
✗ Branch 1 not taken.
6 writeromdata_byte(pcpos, (unsigned char)num);
1756
1/2
✓ Branch 0 taken 6 times.
✗ Branch 1 not taken.
6 writeromdata_byte(pcpos+1, (unsigned char)(num >> 8));
1757 }
1758
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 if(spcblock.execute_address != -1u)
1759 {
1760
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 write2(0x0000);
1761
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 write2((unsigned int)spcblock.execute_address);
1762 }
1763 18 break;
1764 case spcblock_custom:
1765 mapper = spcblock.old_mapper;
1766 pop_pc();
1767 break;
1768 default:
1769 asar_throw_error(0, error_type_fatal, error_id_internal_error, "invalid spcblock type");
1770 }
1771
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 ns = ns_backup;
1772 18 in_spcblock = false;
1773 }
1774
6/6
✓ Branch 0 taken 25929 times.
✓ Branch 1 taken 1371 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 25911 times.
✓ Branch 4 taken 18 times.
✓ Branch 5 taken 27282 times.
27300 else if (is1("startpos"))
1775 {
1776
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
18 if(!in_spcblock) asar_throw_error(0, error_type_block, error_id_startpos_without_spcblock);
1777
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 spcblock.execute_address=getnum(par);
1778 }
1779
6/6
✓ Branch 0 taken 25911 times.
✓ Branch 1 taken 1371 times.
✓ Branch 2 taken 270 times.
✓ Branch 3 taken 25641 times.
✓ Branch 4 taken 270 times.
✓ Branch 5 taken 27012 times.
27282 else if (is1("base"))
1780 {
1781
4/4
✓ Branch 0 taken 180 times.
✓ Branch 1 taken 90 times.
✓ Branch 2 taken 45 times.
✓ Branch 3 taken 90 times.
270 if (!stricmp(par, "off"))
1782 {
1783 90 snespos=realsnespos;
1784 90 startpos=realstartpos;
1785 90 snespos_valid = realsnespos >= 0;
1786 90 return;
1787 }
1788
1/2
✓ Branch 0 taken 180 times.
✗ Branch 1 not taken.
180 unsigned int num=getnum(par);
1789
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 180 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
180 if (forwardlabel) asar_throw_error(0, error_type_block, error_id_base_label_invalid);
1790
1/6
✗ Branch 0 not taken.
✓ Branch 1 taken 180 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
180 if (num&~0xFFFFFF) asar_throw_error(1, error_type_block, error_id_snes_address_out_of_bounds, hex((unsigned int)num).data());
1791 180 snespos=(int)num;
1792 180 startpos=(int)num;
1793 180 optimizeforbank=-1;
1794 180 snespos_valid = realsnespos >= 0;
1795 }
1796
6/6
✓ Branch 0 taken 25641 times.
✓ Branch 1 taken 1371 times.
✓ Branch 2 taken 36 times.
✓ Branch 3 taken 25605 times.
✓ Branch 4 taken 36 times.
✓ Branch 5 taken 26976 times.
27012 else if (is1("dpbase"))
1797 {
1798
1/2
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
36 unsigned int num=(int)getnum(par);
1799
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 36 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
36 if (forwardlabel) asar_throw_error(0, error_type_block, error_id_base_label_invalid);
1800
1/6
✗ Branch 0 not taken.
✓ Branch 1 taken 36 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
36 if (num&~0xFF00) asar_throw_error(1, error_type_block, error_id_bad_dp_base, hex((unsigned int)num, 6).data());
1801 36 dp_base = (int)num;
1802 }
1803
6/6
✓ Branch 0 taken 414 times.
✓ Branch 1 taken 26562 times.
✓ Branch 2 taken 108 times.
✓ Branch 3 taken 306 times.
✓ Branch 4 taken 108 times.
✓ Branch 5 taken 26868 times.
26976 else if (is2("optimize"))
1804 {
1805
4/4
✓ Branch 0 taken 90 times.
✓ Branch 1 taken 18 times.
✓ Branch 2 taken 36 times.
✓ Branch 3 taken 18 times.
108 if (!stricmp(par, "dp"))
1806 {
1807
4/4
✓ Branch 0 taken 45 times.
✓ Branch 1 taken 27 times.
✓ Branch 2 taken 9 times.
✓ Branch 3 taken 27 times.
72 if (!stricmp(word[2], "none"))
1808 {
1809 18 optimize_dp = optimize_dp_flag::NONE;
1810 18 return;
1811 }
1812
4/4
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 18 times.
✓ Branch 2 taken 9 times.
✓ Branch 3 taken 18 times.
54 if (!stricmp(word[2], "ram"))
1813 {
1814 18 optimize_dp = optimize_dp_flag::RAM;
1815 18 return;
1816 }
1817
2/4
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 18 times.
✗ Branch 3 not taken.
36 if (!stricmp(word[2], "always"))
1818 {
1819 36 optimize_dp = optimize_dp_flag::ALWAYS;
1820 36 return;
1821 }
1822 asar_throw_error(1, error_type_block, error_id_bad_dp_optimize, word[2]);
1823 }
1824
2/4
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 18 times.
✗ Branch 3 not taken.
36 if (!stricmp(par, "address"))
1825 {
1826
3/4
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 18 times.
36 if (!stricmp(word[2], "default"))
1827 {
1828 optimize_address = optimize_address_flag::DEFAULT;
1829 return;
1830 }
1831
4/4
✓ Branch 0 taken 27 times.
✓ Branch 1 taken 9 times.
✓ Branch 2 taken 9 times.
✓ Branch 3 taken 9 times.
36 if (!stricmp(word[2], "ram"))
1832 {
1833 18 optimize_address = optimize_address_flag::RAM;
1834 18 return;
1835 }
1836
2/4
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 9 times.
✗ Branch 3 not taken.
18 if (!stricmp(word[2], "mirrors"))
1837 {
1838 18 optimize_address = optimize_address_flag::MIRRORS;
1839 18 return;
1840 }
1841 asar_throw_error(1, error_type_block, error_id_bad_address_optimize, word[2]);
1842 }
1843 asar_throw_error(1, error_type_block, error_id_bad_optimize, par);
1844 }
1845
6/6
✓ Branch 0 taken 25605 times.
✓ Branch 1 taken 1263 times.
✓ Branch 2 taken 54 times.
✓ Branch 3 taken 25551 times.
✓ Branch 4 taken 54 times.
✓ Branch 5 taken 26814 times.
26868 else if (is1("bank"))
1846 {
1847
4/4
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 18 times.
✓ Branch 2 taken 9 times.
✓ Branch 3 taken 18 times.
54 if (!stricmp(par, "auto"))
1848 {
1849 18 optimizeforbank=-1;
1850 18 return;
1851 }
1852
4/4
✓ Branch 0 taken 27 times.
✓ Branch 1 taken 9 times.
✓ Branch 2 taken 9 times.
✓ Branch 3 taken 9 times.
36 if (!stricmp(par, "noassume"))
1853 {
1854 18 optimizeforbank=0x100;
1855 18 return;
1856 }
1857
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 unsigned int num=getnum(par);
1858 //if (forwardlabel) error(0, "bank Label is not valid");
1859 //if (foundlabel) num>>=16;
1860
1/6
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
18 if (num&~0x0000FF) asar_throw_error(1, error_type_block, error_id_snes_address_out_of_bounds, hex((unsigned int)num, 6).data());
1861 18 optimizeforbank=(int)num;
1862 }
1863
10/10
✓ Branch 0 taken 26796 times.
✓ Branch 1 taken 18 times.
✓ Branch 2 taken 23592 times.
✓ Branch 3 taken 3204 times.
✓ Branch 4 taken 22710 times.
✓ Branch 5 taken 882 times.
✓ Branch 6 taken 270 times.
✓ Branch 7 taken 22440 times.
✓ Branch 8 taken 4374 times.
✓ Branch 9 taken 22440 times.
26814 else if (is("freespace") || is("freecode") || is("freedata") || is("segment"))
1864 {
1865
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 4374 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
4374 if(in_spcblock) asar_throw_error(0, error_type_block, error_id_feature_unavaliable_in_spcblock);
1866 4374 string parstr;
1867
3/4
✓ Branch 0 taken 378 times.
✓ Branch 1 taken 3996 times.
✓ Branch 2 taken 378 times.
✗ Branch 3 not taken.
4374 if (numwords==1) parstr="\n";//crappy hack: impossible character to cut out extra commas
1868
2/4
✓ Branch 0 taken 3996 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 3996 times.
✗ Branch 3 not taken.
3996 else if (numwords==2) parstr=word[1];
1869 else asar_throw_error(0, error_type_block, error_id_invalid_freespace_request);
1870
5/8
✓ Branch 0 taken 3204 times.
✓ Branch 1 taken 1170 times.
✓ Branch 2 taken 3204 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 3204 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 3204 times.
✗ Branch 7 not taken.
4374 if (is("freecode")) parstr=STR"ram,"+parstr;
1871
5/8
✓ Branch 0 taken 882 times.
✓ Branch 1 taken 3492 times.
✓ Branch 2 taken 882 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 882 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 882 times.
✗ Branch 7 not taken.
4374 if (is("freedata")) parstr=STR"noram,"+parstr;
1872
5/8
✓ Branch 0 taken 270 times.
✓ Branch 1 taken 4104 times.
✓ Branch 2 taken 270 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 270 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 270 times.
✗ Branch 7 not taken.
4374 if (is("segment")) parstr = STR "norats," + parstr;
1873
1/2
✓ Branch 0 taken 4374 times.
✗ Branch 1 not taken.
4374 autoptr<char**> pars=split(parstr.temp_raw(), ',');
1874 4374 unsigned char fsbyte = 0x00;
1875 4374 bool fixedpos=false;
1876 4374 bool align=false;
1877 4374 bool leakwarn=true;
1878 4374 bool write_rats=true;
1879 4374 int target_bank = -3;
1880
1/2
✓ Branch 0 taken 4374 times.
✗ Branch 1 not taken.
4374 string pin_to_freespace = "";
1881 4374 int search_start_pos = -1;
1882
1883
2/2
✓ Branch 0 taken 8766 times.
✓ Branch 1 taken 4374 times.
13140 for (int i=0;pars[i];i++)
1884 {
1885
2/2
✓ Branch 0 taken 8388 times.
✓ Branch 1 taken 378 times.
8766 if (pars[i][0]=='\n') {}
1886
4/4
✓ Branch 0 taken 5796 times.
✓ Branch 1 taken 2592 times.
✓ Branch 2 taken 1602 times.
✓ Branch 3 taken 2592 times.
8388 else if (!stricmp(pars[i], "ram"))
1887 {
1888
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 3204 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
3204 if (target_bank!=-3) asar_throw_error(0, error_type_block, error_id_invalid_freespace_request);
1889 3204 target_bank = -2;
1890 }
1891
4/4
✓ Branch 0 taken 3033 times.
✓ Branch 1 taken 2151 times.
✓ Branch 2 taken 441 times.
✓ Branch 3 taken 2151 times.
5184 else if (!stricmp(pars[i], "noram"))
1892 {
1893
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 882 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
882 if (target_bank!=-3) asar_throw_error(0, error_type_block, error_id_invalid_freespace_request);
1894 882 target_bank = -1;
1895 }
1896
4/4
✓ Branch 0 taken 2169 times.
✓ Branch 1 taken 2133 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 2133 times.
4302 else if (!stricmp(pars[i], "static"))
1897 {
1898
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 36 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
36 if (fixedpos) asar_throw_error(0, error_type_block, error_id_invalid_freespace_request);
1899 36 fixedpos=true;
1900 }
1901
4/4
✓ Branch 0 taken 2151 times.
✓ Branch 1 taken 2115 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 2115 times.
4266 else if (!stricmp(pars[i], "align"))
1902 {
1903
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 36 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
36 if (align) asar_throw_error(0, error_type_block, error_id_invalid_freespace_request);
1904 36 align=true;
1905 }
1906
4/4
✓ Branch 0 taken 3996 times.
✓ Branch 1 taken 234 times.
✓ Branch 2 taken 1881 times.
✓ Branch 3 taken 234 times.
4230 else if (!stricmp(pars[i], "cleaned"))
1907 {
1908
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 3762 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
3762 if (!leakwarn) asar_throw_error(0, error_type_block, error_id_invalid_freespace_request);
1909 3762 leakwarn=false;
1910 }
1911
4/4
✓ Branch 0 taken 369 times.
✓ Branch 1 taken 99 times.
✓ Branch 2 taken 135 times.
✓ Branch 3 taken 99 times.
468 else if (!stricmp(pars[i], "norats"))
1912 {
1913 270 write_rats=false;
1914 }
1915
2/2
✓ Branch 0 taken 90 times.
✓ Branch 1 taken 108 times.
198 else if (stribegin(pars[i], "bank="))
1916 {
1917
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 90 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
90 if(target_bank != -3) asar_throw_error(0, error_type_block, error_id_invalid_freespace_request);
1918
1/2
✓ Branch 0 taken 90 times.
✗ Branch 1 not taken.
90 target_bank = getnum(pars[i] + 5);
1919
1/6
✗ Branch 0 not taken.
✓ Branch 1 taken 90 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
90 if(foundlabel && !foundlabel_static) asar_throw_error(0, error_type_block, error_id_no_labels_here);
1920 }
1921
2/2
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 72 times.
108 else if (stribegin(pars[i], "start="))
1922 {
1923
1/2
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
36 search_start_pos = getnum(pars[i] + 6);
1924
1/6
✗ Branch 0 not taken.
✓ Branch 1 taken 36 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
36 if(foundlabel && !foundlabel_static) asar_throw_error(0, error_type_block, error_id_no_labels_here);
1925 }
1926
1/2
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
72 else if (stribegin(pars[i], "pin="))
1927 {
1928 // TODO: should we handle posneg labels here too?
1929
1/2
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
72 string pin_to = pars[i] + 4;
1930 72 const char* pin_to_c = pin_to.data();
1931
2/4
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 72 times.
✗ Branch 3 not taken.
72 pin_to_freespace = labelname(&pin_to_c);
1932
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 72 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
72 if(*pin_to_c) asar_throw_error(0, error_type_block, error_id_invalid_label_name);
1933 // this is to throw an "undefined label" error with the proper callstack
1934
4/6
✓ Branch 0 taken 48 times.
✓ Branch 1 taken 24 times.
✓ Branch 2 taken 48 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 48 times.
✗ Branch 5 not taken.
72 if(pass) labelval(pin_to);
1935 72 }
1936 else if (stribegin(pars[i], "cleanbyte="))
1937 {
1938 fsbyte = getnum(pars[i] + strlen("cleanbyte="));
1939 if(foundlabel && !foundlabel_static) asar_throw_error(0, error_type_block, error_id_no_labels_here);
1940 }
1941 else
1942 {
1943 // for backwards compat i guess
1944 fsbyte = (unsigned char)getnum(pars[i]);
1945 }
1946 }
1947
3/4
✓ Branch 0 taken 198 times.
✓ Branch 1 taken 4176 times.
✓ Branch 2 taken 198 times.
✗ Branch 3 not taken.
4374 if(target_bank == -3 && !write_rats) target_bank = -1;
1948
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 4374 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
4374 if(target_bank == -3) asar_throw_error(0, error_type_block, error_id_invalid_freespace_request);
1949 // no point specifying anything about cleaning when not writing a rats tag
1950
4/8
✓ Branch 0 taken 270 times.
✓ Branch 1 taken 4104 times.
✓ Branch 2 taken 270 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 270 times.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
4374 if(!write_rats && (!leakwarn || fixedpos)) asar_throw_error(0, error_type_block, error_id_invalid_freespace_request);
1951
2/2
✓ Branch 0 taken 270 times.
✓ Branch 1 taken 4104 times.
4374 if(!write_rats) leakwarn = false;
1952
1/2
✓ Branch 0 taken 4374 times.
✗ Branch 1 not taken.
4374 freespaceend();
1953
1/2
✓ Branch 0 taken 4374 times.
✗ Branch 1 not taken.
4374 freespaceid=getfreespaceid();
1954
1/2
✓ Branch 0 taken 4374 times.
✗ Branch 1 not taken.
4374 freespace_data& thisfs = freespaces[freespaceid];
1955 4374 thisfs.cleanbyte = fsbyte;
1956
1957
1/2
✓ Branch 0 taken 4374 times.
✗ Branch 1 not taken.
4374 thisfs.pin_target = pin_to_freespace;
1958
4/6
✓ Branch 0 taken 4374 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 72 times.
✓ Branch 3 taken 4302 times.
✓ Branch 4 taken 72 times.
✗ Branch 5 not taken.
4374 if(pin_to_freespace) thisfs.pin_target_ns = ns;
1959 4374 thisfs.write_rats = write_rats;
1960 4374 thisfs.search_start = search_start_pos;
1961 4374 thisfs.bank = target_bank;
1962 4374 thisfs.flag_align = align;
1963
1964
2/2
✓ Branch 0 taken 1458 times.
✓ Branch 1 taken 2916 times.
4374 if (pass==0) snespos=0;
1965
2/2
✓ Branch 0 taken 1458 times.
✓ Branch 1 taken 2916 times.
4374 if (pass==1)
1966 {
1967
3/4
✓ Branch 0 taken 12 times.
✓ Branch 1 taken 1446 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 12 times.
1458 if (fixedpos && thisfs.orgpos<0)
1968 {
1969 thisfs.pos = 0;
1970 thisfs.leaked = false;//mute some other errors
1971 asar_throw_error(1, error_type_block, error_id_static_freespace_autoclean);
1972 }
1973 1458 snespos = 0;
1974 }
1975
2/2
✓ Branch 0 taken 1458 times.
✓ Branch 1 taken 2916 times.
4374 if (pass==2)
1976 {
1977
3/4
✓ Branch 0 taken 12 times.
✓ Branch 1 taken 1446 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 12 times.
1458 if (fixedpos && thisfs.orgpos == -1) return;//to kill some errors
1978 1458 snespos=thisfs.pos;
1979
3/6
✓ Branch 0 taken 1338 times.
✓ Branch 1 taken 120 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 1338 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
1458 if (thisfs.leaked && leakwarn) asar_throw_warning(2, warning_id_freespace_leaked);
1980
2/2
✓ Branch 0 taken 1368 times.
✓ Branch 1 taken 90 times.
1458 freespaceuse += (write_rats ? 8 : 0) + thisfs.len;
1981
1982 // add a mapping for the start of the rats tag
1983
3/4
✓ Branch 0 taken 1368 times.
✓ Branch 1 taken 90 times.
✓ Branch 2 taken 1368 times.
✗ Branch 3 not taken.
1458 if (write_rats) add_addr_to_line(snespos-8);
1984 }
1985 4374 thisfs.is_static = fixedpos;
1986
1/8
✗ Branch 0 not taken.
✓ Branch 1 taken 4374 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
4374 if (snespos < 0 && mapper == sa1rom) asar_throw_error(pass, error_type_fatal, error_id_no_freespace_in_mapped_banks, dec(thisfs.len).data());
1987
1/6
✗ Branch 0 not taken.
✓ Branch 1 taken 4374 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
4374 if (snespos < 0) asar_throw_error(pass, error_type_fatal, error_id_no_freespace, dec(thisfs.len).data());
1988
2/2
✓ Branch 0 taken 4104 times.
✓ Branch 1 taken 270 times.
4374 bytes+=write_rats ? 8 : 0;
1989 4374 freespacestart=snespos;
1990 4374 startpos=snespos;
1991 4374 realstartpos=snespos;
1992 4374 realsnespos=snespos;
1993 4374 optimizeforbank=-1;
1994
2/2
✓ Branch 0 taken 4104 times.
✓ Branch 1 taken 270 times.
4374 ratsmetastate=write_rats ? ratsmeta_allow : ratsmeta_ban;
1995 4374 snespos_valid = true;
1996 // check this at the very end so that snespos gets set properly, to
1997 // prevent spurious errors later
1998 //...i guess this can still cause bankcross errors if the old freespace
1999 //happened to be very close to the end of a bank or something, but
2000 //whatever
2001
7/8
✓ Branch 0 taken 1458 times.
✓ Branch 1 taken 2916 times.
✓ Branch 2 taken 12 times.
✓ Branch 3 taken 1446 times.
✓ Branch 4 taken 6 times.
✓ Branch 5 taken 6 times.
✓ Branch 6 taken 6 times.
✗ Branch 7 not taken.
4374 if (pass == 2 && fixedpos && thisfs.orgpos > 0 && thisfs.len > thisfs.orglen)
2002
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 6 times.
6 asar_throw_error(2, error_type_block, error_id_static_freespace_growing);
2003
3/6
✓ Branch 0 taken 4368 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 4368 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 4368 times.
✗ Branch 5 not taken.
4386 }
2004
6/6
✓ Branch 0 taken 21555 times.
✓ Branch 1 taken 885 times.
✓ Branch 2 taken 126 times.
✓ Branch 3 taken 21429 times.
✓ Branch 4 taken 126 times.
✓ Branch 5 taken 22314 times.
22440 else if (is1("prot"))
2005 {
2006
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 126 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
126 if(in_spcblock) asar_throw_error(0, error_type_block, error_id_feature_unavaliable_in_spcblock);
2007
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 126 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
126 if (!ratsmetastate) asar_throw_error(2, error_type_block, error_id_prot_not_at_freespace_start);
2008
2/2
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 90 times.
126 if (ratsmetastate==ratsmeta_used) step(-5);
2009 int num;
2010
1/2
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
126 autoptr<char**> pars=qpsplit(par, ',', &num);
2011
1/2
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
126 verify_paren(pars);
2012
1/2
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
126 write1('P');
2013
1/2
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
126 write1('R');
2014
1/2
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
126 write1('O');
2015
1/2
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
126 write1('T');
2016
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 126 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
126 if (num * 3 > 255) asar_throw_error(0, error_type_block, error_id_prot_too_many_entries);
2017
1/2
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
126 write1((unsigned int)(num*3));
2018
2/2
✓ Branch 0 taken 162 times.
✓ Branch 1 taken 126 times.
288 for (int i=0;i<num;i++)
2019 {
2020 //int num=getnum(pars[i]);
2021 162 const char * labeltest=pars[i];
2022
1/2
✓ Branch 0 taken 162 times.
✗ Branch 1 not taken.
162 string testlabel = labeltest;
2023
1/2
✓ Branch 0 taken 162 times.
✗ Branch 1 not taken.
162 snes_label lblval = labelval(&labeltest);
2024
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 162 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
162 if (*labeltest) asar_throw_error(0, error_type_block, error_id_label_not_found, testlabel.data());
2025
1/2
✓ Branch 0 taken 162 times.
✗ Branch 1 not taken.
162 write3(lblval.pos);
2026
3/4
✓ Branch 0 taken 54 times.
✓ Branch 1 taken 108 times.
✓ Branch 2 taken 54 times.
✗ Branch 3 not taken.
162 if (pass==1) freespaces[lblval.freespace_id].leaked = false;
2027 162 }
2028
1/2
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
126 write1('S');
2029
1/2
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
126 write1('T');
2030
1/2
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
126 write1('O');
2031
1/2
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
126 write1('P');
2032
1/2
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
126 write1(0);
2033 126 ratsmetastate=ratsmeta_used;
2034
2035
1/2
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
126 add_addr_to_line(addrToLinePos);
2036 126 }
2037
9/10
✓ Branch 0 taken 21429 times.
✓ Branch 1 taken 885 times.
✓ Branch 2 taken 21429 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 306 times.
✓ Branch 5 taken 22008 times.
✓ Branch 6 taken 198 times.
✓ Branch 7 taken 108 times.
✓ Branch 8 taken 198 times.
✓ Branch 9 taken 22116 times.
22314 else if (is1("autoclean") || is2("autoclean"))
2038 {
2039
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 198 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
198 if(in_spcblock) asar_throw_error(0, error_type_block, error_id_feature_unavaliable_in_spcblock);
2040
1/2
✓ Branch 0 taken 198 times.
✗ Branch 1 not taken.
198 if (numwords==3)
2041 {
2042
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 198 times.
198 if(freespaceid > 0)
2043 asar_throw_error(0, error_type_block, error_id_autoclean_in_freespace);
2044 198 const char * labeltest = word[2];
2045
1/2
✓ Branch 0 taken 198 times.
✗ Branch 1 not taken.
198 string testlabel = labeltest;
2046
1/2
✓ Branch 0 taken 198 times.
✗ Branch 1 not taken.
198 snes_label lblval = labelval(&labeltest);
2047
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 198 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
198 if (*labeltest) asar_throw_error(0, error_type_block, error_id_label_not_found, testlabel.data());
2048 198 int targetid= lblval.freespace_id;
2049
3/4
✓ Branch 0 taken 66 times.
✓ Branch 1 taken 132 times.
✓ Branch 2 taken 66 times.
✗ Branch 3 not taken.
198 if (pass==1) freespaces[targetid].leaked = false;
2050 198 int num = lblval.pos;
2051
2/8
✗ Branch 0 not taken.
✓ Branch 1 taken 198 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 99 times.
198 if (strlen(par)>3 && !stricmp(par+3, ".l")) par[3]=0;
2052
9/10
✓ Branch 0 taken 153 times.
✓ Branch 1 taken 45 times.
✓ Branch 2 taken 99 times.
✓ Branch 3 taken 54 times.
✓ Branch 4 taken 54 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 45 times.
✓ Branch 7 taken 9 times.
✓ Branch 8 taken 90 times.
✓ Branch 9 taken 9 times.
198 if (!stricmp(par, "JSL") || !stricmp(par, "JML"))
2053 {
2054
1/2
✓ Branch 0 taken 60 times.
✗ Branch 1 not taken.
180 int orgpos=read3(snespos+1);
2055
1/2
✓ Branch 0 taken 180 times.
✗ Branch 1 not taken.
180 int ratsloc=freespaces[targetid].orgpos;
2056
4/4
✓ Branch 0 taken 135 times.
✓ Branch 1 taken 45 times.
✓ Branch 2 taken 45 times.
✓ Branch 3 taken 45 times.
180 int firstbyte = ((!stricmp(par, "JSL")) ? 0x22 : 0x5C);
2057
1/2
✓ Branch 0 taken 60 times.
✗ Branch 1 not taken.
180 int pcpos=snestopc(snespos);
2058
4/6
✓ Branch 0 taken 180 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 180 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 72 times.
✓ Branch 5 taken 108 times.
180 if (/*pass==1 && */pcpos>=0 && pcpos<romlen_r && romdata_r[pcpos]==firstbyte)
2059 {
2060
1/2
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
72 ratsloc=ratsstart(orgpos)+8;
2061
3/5
✓ Branch 0 taken 60 times.
✓ Branch 1 taken 12 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 24 times.
✗ Branch 4 not taken.
72 freespaces[targetid].orglen=read2(ratsloc-4)+1;
2062
9/12
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 60 times.
✓ Branch 3 taken 12 times.
✓ Branch 4 taken 18 times.
✓ Branch 5 taken 42 times.
✓ Branch 6 taken 18 times.
✓ Branch 7 taken 54 times.
✓ Branch 8 taken 18 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 18 times.
✗ Branch 11 not taken.
72 if (!freespaces[targetid].is_static && pass==1) removerats(orgpos, freespaces[targetid].cleanbyte);
2063 }
2064
2/2
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 72 times.
108 else if (ratsloc<0) ratsloc=0;
2065
1/2
✓ Branch 0 taken 180 times.
✗ Branch 1 not taken.
180 write1((unsigned int)firstbyte);
2066
1/2
✓ Branch 0 taken 180 times.
✗ Branch 1 not taken.
180 write3((unsigned int)num);
2067
2/2
✓ Branch 0 taken 60 times.
✓ Branch 1 taken 120 times.
180 if (pass==2)
2068 {
2069
1/2
✓ Branch 0 taken 60 times.
✗ Branch 1 not taken.
60 int start=ratsstart(num);
2070
2/4
✓ Branch 0 taken 60 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 60 times.
60 if (start>=num || start<0)
2071 {
2072 asar_throw_error(2, error_type_block, error_id_autoclean_label_at_freespace_end);
2073 }
2074
2075
1/2
✓ Branch 0 taken 60 times.
✗ Branch 1 not taken.
60 add_addr_to_line(addrToLinePos);
2076 }
2077 //freespaceorglen[targetid]=read2(ratsloc-4)+1;
2078
1/2
✓ Branch 0 taken 180 times.
✗ Branch 1 not taken.
180 freespaces[targetid].orgpos = ratsloc;
2079 90 }
2080
2/4
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 9 times.
✗ Branch 3 not taken.
18 else if (!stricmp(par, "dl"))
2081 {
2082
1/2
✓ Branch 0 taken 6 times.
✗ Branch 1 not taken.
18 int orgpos=read3(snespos);
2083
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 int ratsloc=freespaces[targetid].orgpos;
2084
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 int start=ratsstart(num);
2085
3/4
✓ Branch 0 taken 6 times.
✓ Branch 1 taken 12 times.
✓ Branch 2 taken 6 times.
✗ Branch 3 not taken.
18 if (pass==1 && num>=0)
2086 {
2087
1/2
✓ Branch 0 taken 6 times.
✗ Branch 1 not taken.
6 ratsloc=ratsstart(orgpos)+8;
2088
4/8
✓ Branch 0 taken 6 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 6 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 6 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 6 times.
✗ Branch 7 not taken.
6 if (!freespaces[targetid].is_static) removerats(orgpos, freespaces[targetid].cleanbyte);
2089 }
2090
2/2
✓ Branch 0 taken 6 times.
✓ Branch 1 taken 6 times.
12 else if (!ratsloc) ratsloc=0;
2091
5/6
✓ Branch 0 taken 12 times.
✓ Branch 1 taken 6 times.
✓ Branch 2 taken 6 times.
✓ Branch 3 taken 6 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 12 times.
18 if ((start==num || start<0) && pass==2)
2092 asar_throw_error(2, error_type_block, error_id_autoclean_label_at_freespace_end);
2093
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 write3((unsigned int)num);
2094
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 freespaces[targetid].orgpos = ratsloc;
2095
3/5
✓ Branch 0 taken 15 times.
✓ Branch 1 taken 3 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 6 times.
✗ Branch 4 not taken.
18 freespaces[targetid].orglen = read2(ratsloc-4)+1;
2096
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 add_addr_to_line(addrToLinePos);
2097 }
2098 else asar_throw_error(0, error_type_block, error_id_broken_autoclean);
2099 198 }
2100 // weird gotcha: we don't know the freespace id here, so we don't know what clean_byte to use
2101 else if (pass==0) removerats((int)getnum(word[1]), 0x00);
2102 }
2103
6/6
✓ Branch 0 taken 453 times.
✓ Branch 1 taken 21663 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 435 times.
✓ Branch 4 taken 18 times.
✓ Branch 5 taken 22098 times.
22116 else if (is0("pushpc"))
2104 {
2105
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 verifysnespos();
2106
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 pushpc[pushpcnum].arch=arch;
2107
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 pushpc[pushpcnum].snespos=snespos;
2108
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 pushpc[pushpcnum].snesstart=startpos;
2109
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 pushpc[pushpcnum].snesposreal=realsnespos;
2110
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 pushpc[pushpcnum].snesstartreal=realstartpos;
2111
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 pushpc[pushpcnum].freeid=freespaceid;
2112
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 pushpc[pushpcnum].freest=freespacestart;
2113 18 pushpcnum++;
2114 18 snespos=(int)0xFFFFFFFF;
2115 18 startpos= (int)0xFFFFFFFF;
2116 18 realsnespos= (int)0xFFFFFFFF;
2117 18 realstartpos= (int)0xFFFFFFFF;
2118 18 snespos_valid = false;
2119 }
2120
6/6
✓ Branch 0 taken 435 times.
✓ Branch 1 taken 21663 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 417 times.
✓ Branch 4 taken 18 times.
✓ Branch 5 taken 22080 times.
22098 else if (is0("pullpc"))
2121 {
2122
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
18 if (!pushpcnum) asar_throw_error(0, error_type_block, error_id_pullpc_without_pushpc);
2123 18 pushpcnum--;
2124
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 freespaceend();
2125
2/6
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 18 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
18 if (arch != pushpc[pushpcnum].arch) asar_throw_error(0, error_type_block, error_id_pullpc_different_arch);
2126
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 snespos=pushpc[pushpcnum].snespos;
2127
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 startpos=pushpc[pushpcnum].snesstart;
2128
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 realsnespos=pushpc[pushpcnum].snesposreal;
2129
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 realstartpos=pushpc[pushpcnum].snesstartreal;
2130
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 freespaceid=pushpc[pushpcnum].freeid;
2131
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 freespacestart=pushpc[pushpcnum].freest;
2132 18 snespos_valid = true;
2133 }
2134
6/6
✓ Branch 0 taken 417 times.
✓ Branch 1 taken 21663 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 399 times.
✓ Branch 4 taken 18 times.
✓ Branch 5 taken 22062 times.
22080 else if (is0("pushbase"))
2135 {
2136
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 basestack[basestacknum] = snespos;
2137 18 basestacknum++;
2138 }
2139
6/6
✓ Branch 0 taken 399 times.
✓ Branch 1 taken 21663 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 381 times.
✓ Branch 4 taken 18 times.
✓ Branch 5 taken 22044 times.
22062 else if (is0("pullbase"))
2140 {
2141
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
18 if (!basestacknum) asar_throw_error(0, error_type_block, error_id_pullbase_without_pushbase);
2142 18 basestacknum--;
2143
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 snespos = basestack[basestacknum];
2144
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 startpos = basestack[basestacknum];
2145
2146
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 if (snespos != realstartpos)
2147 {
2148 18 optimizeforbank = -1;
2149 }
2150 }
2151
6/6
✓ Branch 0 taken 381 times.
✓ Branch 1 taken 21663 times.
✓ Branch 2 taken 36 times.
✓ Branch 3 taken 345 times.
✓ Branch 4 taken 36 times.
✓ Branch 5 taken 22008 times.
22044 else if (is0("pushns"))
2152 {
2153
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 36 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
36 if(in_spcblock) asar_throw_error(0, error_type_block, error_id_feature_unavaliable_in_spcblock);
2154
2/4
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 36 times.
✗ Branch 3 not taken.
36 pushns[pushnsnum].ns = ns;
2155
2/2
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 36 times.
72 for(int i = 0; i < namespace_list.count; i++)
2156 {
2157
3/6
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 36 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 36 times.
✗ Branch 5 not taken.
36 pushns[pushnsnum].namespace_list.append(namespace_list[i]);
2158 }
2159
1/2
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
36 pushns[pushnsnum].nested_namespaces = nested_namespaces;
2160 36 pushnsnum++;
2161
2162
1/2
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
36 namespace_list.reset();
2163
1/2
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
36 ns = "";
2164 36 nested_namespaces = false;
2165 }
2166
6/6
✓ Branch 0 taken 345 times.
✓ Branch 1 taken 21663 times.
✓ Branch 2 taken 36 times.
✓ Branch 3 taken 309 times.
✓ Branch 4 taken 36 times.
✓ Branch 5 taken 21972 times.
22008 else if (is0("pullns"))
2167 {
2168
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 36 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
36 if(in_spcblock) asar_throw_error(0, error_type_block, error_id_feature_unavaliable_in_spcblock);
2169
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 36 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
36 if (!pushnsnum) asar_throw_error(0, error_type_block, error_id_pullns_without_pushns);
2170 36 pushnsnum--;
2171
2/4
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 36 times.
✗ Branch 3 not taken.
36 ns = pushns[pushnsnum].ns;
2172
1/2
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
36 nested_namespaces = pushns[pushnsnum].nested_namespaces;
2173
1/2
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
36 namespace_list.reset();
2174
3/4
✓ Branch 0 taken 108 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 72 times.
✓ Branch 3 taken 36 times.
108 for(int i = 0; i < pushns[pushnsnum].namespace_list.count; i++)
2175 {
2176
3/6
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 72 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 72 times.
✗ Branch 5 not taken.
72 namespace_list.append(pushns[pushnsnum].namespace_list[i]);
2177 }
2178 }
2179
9/10
✓ Branch 0 taken 21429 times.
✓ Branch 1 taken 543 times.
✓ Branch 2 taken 21048 times.
✓ Branch 3 taken 381 times.
✓ Branch 4 taken 108 times.
✓ Branch 5 taken 21483 times.
✓ Branch 6 taken 108 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 489 times.
✓ Branch 9 taken 21483 times.
21972 else if (is1("namespace") || is2("namespace"))
2180 {
2181
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 489 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
489 if(in_spcblock) asar_throw_error(0, error_type_block, error_id_feature_unavaliable_in_spcblock);
2182 489 bool leave = false;
2183
1/2
✓ Branch 0 taken 489 times.
✗ Branch 1 not taken.
489 if (par)
2184 {
2185
4/4
✓ Branch 0 taken 315 times.
✓ Branch 1 taken 174 times.
✓ Branch 2 taken 72 times.
✓ Branch 3 taken 171 times.
489 if (!stricmp(par, "off"))
2186 {
2187
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 144 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
144 if (word[2]) asar_throw_error(0, error_type_block, error_id_invalid_namespace_use);
2188 144 leave = true;
2189 }
2190
4/4
✓ Branch 0 taken 225 times.
✓ Branch 1 taken 120 times.
✓ Branch 2 taken 54 times.
✓ Branch 3 taken 117 times.
345 else if (!stricmp(par, "nested"))
2191 {
2192
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 108 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
108 if (!word[2]) asar_throw_error(0, error_type_block, error_id_invalid_namespace_use);
2193
4/4
✓ Branch 0 taken 81 times.
✓ Branch 1 taken 27 times.
✓ Branch 2 taken 27 times.
✓ Branch 3 taken 27 times.
108 else if (!stricmp(word[2], "on")) nested_namespaces = true;
2194
2/4
✓ Branch 0 taken 54 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 27 times.
✗ Branch 3 not taken.
54 else if (!stricmp(word[2], "off")) nested_namespaces = false;
2195 }
2196 else
2197 {
2198
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 237 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
237 if (word[2]) asar_throw_error(0, error_type_block, error_id_invalid_namespace_use);
2199
1/2
✓ Branch 0 taken 237 times.
✗ Branch 1 not taken.
237 const char * tmpstr= safedequote(par);
2200
3/7
✓ Branch 0 taken 81 times.
✓ Branch 1 taken 156 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 81 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
237 if (!confirmname(tmpstr)) asar_throw_error(0, error_type_block, error_id_invalid_namespace_name);
2201
2/2
✓ Branch 0 taken 93 times.
✓ Branch 1 taken 144 times.
237 if (!nested_namespaces)
2202 {
2203
1/2
✓ Branch 0 taken 93 times.
✗ Branch 1 not taken.
93 namespace_list.reset();
2204 }
2205
2/4
✓ Branch 0 taken 237 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 237 times.
✗ Branch 3 not taken.
237 namespace_list.append(tmpstr);
2206 }
2207 }
2208 else
2209 {
2210 leave = true;
2211 }
2212
2213
2/2
✓ Branch 0 taken 144 times.
✓ Branch 1 taken 345 times.
489 if (leave)
2214 {
2215
2/2
✓ Branch 0 taken 108 times.
✓ Branch 1 taken 36 times.
144 if (nested_namespaces)
2216 {
2217
1/2
✓ Branch 0 taken 108 times.
✗ Branch 1 not taken.
108 namespace_list.remove(namespace_list.count - 1);
2218 }
2219 else
2220 {
2221
1/2
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
36 namespace_list.reset();
2222 }
2223 }
2224
2225 // recompute ns
2226
1/2
✓ Branch 0 taken 489 times.
✗ Branch 1 not taken.
489 ns = "";
2227
2/2
✓ Branch 0 taken 579 times.
✓ Branch 1 taken 489 times.
1068 for (int i = 0; i < namespace_list.count; i++)
2228 {
2229
2/4
✓ Branch 0 taken 579 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 579 times.
✗ Branch 3 not taken.
579 ns += namespace_list[i];
2230
1/2
✓ Branch 0 taken 579 times.
✗ Branch 1 not taken.
579 ns += "_";
2231 }
2232 }
2233
6/6
✓ Branch 0 taken 21048 times.
✓ Branch 1 taken 435 times.
✓ Branch 2 taken 72 times.
✓ Branch 3 taken 20976 times.
✓ Branch 4 taken 72 times.
✓ Branch 5 taken 21411 times.
21483 else if (is1("warnpc"))
2234 {
2235
1/2
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
72 unsigned int maxpos=getnum(par);
2236
3/4
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 54 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 18 times.
72 if (freespaceid > 0) asar_throw_error(0, error_type_block, error_id_warnpc_in_freespace);
2237
3/4
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 36 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 18 times.
54 if ((unsigned int)maxpos & 0xFF000000) asar_throw_error(0, error_type_block, error_id_warnpc_broken_param);
2238
5/8
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 18 times.
✓ Branch 2 taken 18 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 18 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 18 times.
72 if ((unsigned int)snespos > maxpos) asar_throw_error(0, error_type_block, error_id_warnpc_failed, hex((unsigned int)snespos).data(), hex((unsigned int)maxpos, 6).data());
2239 }
2240 #ifdef SANDBOX
2241 else if (is("incsrc") || is("incbin") || is("table"))
2242 {
2243 asar_throw_error(0, error_type_block, error_id_command_disabled);
2244 }
2245 #endif
2246
6/6
✓ Branch 0 taken 20976 times.
✓ Branch 1 taken 435 times.
✓ Branch 2 taken 17370 times.
✓ Branch 3 taken 3606 times.
✓ Branch 4 taken 17370 times.
✓ Branch 5 taken 4041 times.
21411 else if (is1("incsrc"))
2247 {
2248 17370 string name;
2249 // RPG Hacker: Should this also throw on absolute paths?
2250 // E.g., on something starting with C:/ or whatever.
2251
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 17352 times.
17370 if (strchr(par, '\\'))
2252 {
2253
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
18 asar_throw_error(0, error_type_block, error_id_platform_paths);
2254 }
2255
2/4
✓ Branch 0 taken 17352 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 17352 times.
✗ Branch 3 not taken.
17352 name=safedequote(par);
2256
2/2
✓ Branch 0 taken 474 times.
✓ Branch 1 taken 16878 times.
17352 assemblefile(name);
2257 17370 }
2258
6/6
✓ Branch 0 taken 3606 times.
✓ Branch 1 taken 435 times.
✓ Branch 2 taken 216 times.
✓ Branch 3 taken 3390 times.
✓ Branch 4 taken 216 times.
✓ Branch 5 taken 3825 times.
4041 else if (is1("incbin"))
2259 {
2260 int len;
2261 216 int start=0;
2262 216 int end=0;
2263
2/2
✓ Branch 0 taken 126 times.
✓ Branch 1 taken 90 times.
216 if (strqchr(par, ':'))
2264 {
2265 126 char * lengths=strqchr(par, ':');
2266 126 *lengths=0;
2267 126 lengths++;
2268
2269
1/2
✓ Branch 0 taken 126 times.
✗ Branch 1 not taken.
126 char* split = strqpstr(lengths, "..");
2270
3/4
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 108 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 18 times.
126 if(!split) asar_throw_error(0, error_type_block, error_id_broken_incbin);
2271
1/2
✓ Branch 0 taken 108 times.
✗ Branch 1 not taken.
108 string start_str(lengths, split-lengths);
2272
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 108 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
108 if(start_str == "") asar_throw_error(0, error_type_block, error_id_broken_incbin);
2273
1/2
✓ Branch 0 taken 108 times.
✗ Branch 1 not taken.
108 start = getnum(start_str);
2274
5/6
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 72 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 18 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 18 times.
108 if (foundlabel && !foundlabel_static) asar_throw_error(0, error_type_block, error_id_no_labels_here);
2275
1/2
✓ Branch 0 taken 90 times.
✗ Branch 1 not taken.
90 string end_str(split+2);
2276
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 90 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
90 if(end_str == "") asar_throw_error(0, error_type_block, error_id_broken_incbin);
2277
1/2
✓ Branch 0 taken 90 times.
✗ Branch 1 not taken.
90 end = getnum(end_str);
2278
5/6
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 54 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 18 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 18 times.
90 if (foundlabel && !foundlabel_static) asar_throw_error(0, error_type_block, error_id_no_labels_here);
2279 126 }
2280
1/2
✓ Branch 0 taken 162 times.
✗ Branch 1 not taken.
162 const char* current_file = get_current_file_name();
2281 162 string name;
2282 // RPG Hacker: Should this also throw on absolute paths?
2283 // E.g., on something starting with C:/ or whatever.
2284
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 144 times.
162 if (strchr(par, '\\'))
2285 {
2286
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
18 asar_throw_error(0, error_type_block, error_id_platform_paths);
2287 }
2288
2/4
✓ Branch 0 taken 144 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 144 times.
✗ Branch 3 not taken.
144 name = safedequote(par);
2289 char * data;//I couldn't find a way to get this into an autoptr
2290
6/10
✓ Branch 0 taken 144 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 36 times.
✓ Branch 3 taken 108 times.
✓ Branch 4 taken 36 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 36 times.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✓ Branch 9 taken 36 times.
144 if (!readfile(name, current_file, &data, &len)) asar_throw_error(0, error_type_block, vfile_error_to_error_id(asar_get_last_io_error()), name.data());
2291 108 autoptr<char*> datacopy=data;
2292
2/2
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 72 times.
108 if (!end) end=len;
2293
1/6
✗ Branch 0 not taken.
✓ Branch 1 taken 108 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
108 if(start < 0) asar_throw_error(0, error_type_block, error_id_file_offset_out_of_bounds, dec(start).data(), name.data());
2294
3/10
✓ Branch 0 taken 108 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 108 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 108 times.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
108 if (end < start || end > len || end < 0) asar_throw_error(0, error_type_block, error_id_file_offset_out_of_bounds, dec(end).data(), name.data());
2295
2296
3/4
✓ Branch 0 taken 198 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 198 times.
✓ Branch 3 taken 108 times.
306 for (int i=start;i<end;i++) write1((unsigned int)data[i]);
2297
1/2
✓ Branch 0 taken 108 times.
✗ Branch 1 not taken.
108 add_addr_to_line(addrToLinePos);
2298 162 }
2299
6/6
✓ Branch 0 taken 2061 times.
✓ Branch 1 taken 1764 times.
✓ Branch 2 taken 216 times.
✓ Branch 3 taken 1845 times.
✓ Branch 4 taken 1980 times.
✓ Branch 5 taken 1845 times.
3825 else if (is("skip") || is("fill"))
2300 {
2301
4/8
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 1962 times.
✓ Branch 2 taken 18 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 18 times.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
1980 if(numwords != 2 && numwords != 3 && numwords != 5) asar_throw_error(0, error_type_block, error_id_unknown_command);
2302
6/10
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 1962 times.
✓ Branch 2 taken 9 times.
✓ Branch 3 taken 9 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 9 times.
✗ Branch 6 not taken.
✓ Branch 7 taken 990 times.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
1980 if(numwords > 2 && stricmp(word[1], "align")) asar_throw_error(0, error_type_block, error_id_unknown_command);
2303
6/10
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 1962 times.
✓ Branch 2 taken 9 times.
✓ Branch 3 taken 9 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 9 times.
✗ Branch 6 not taken.
✓ Branch 7 taken 990 times.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
1980 if(numwords == 5 && stricmp(word[3], "offset")) asar_throw_error(0, error_type_block, error_id_unknown_command);
2304 int amount;
2305
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 1962 times.
1980 if(numwords > 2)
2306 {
2307
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 int alignment = getnum(word[2]);
2308
1/6
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
18 if(foundlabel && !foundlabel_static) asar_throw_error(0, error_type_block, error_id_no_labels_here);
2309 18 int offset = 0;
2310
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 if(numwords==5)
2311 {
2312
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 offset = getnum(word[4]);
2313
1/6
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
18 if(foundlabel && !foundlabel_static) asar_throw_error(0, error_type_block, error_id_no_labels_here);
2314 }
2315
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
18 if(alignment > 0x800000) asar_throw_error(0, error_type_block, error_id_alignment_too_big);
2316
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
18 if(alignment < 1) asar_throw_error(0, error_type_block, error_id_alignment_too_small);
2317
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
18 if(alignment & (alignment-1)) asar_throw_error(0, error_type_block, error_id_invalid_alignment);
2318 // i just guessed this formula but it seems to work
2319 18 amount = (alignment - ((snespos - offset) & (alignment-1))) & (alignment-1);
2320 }
2321 else
2322 {
2323
1/2
✓ Branch 0 taken 1962 times.
✗ Branch 1 not taken.
1962 amount = (int)getnum(par);
2324
5/6
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 1926 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 18 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 18 times.
1962 if (foundlabel && !foundlabel_static) asar_throw_error(0, error_type_block, error_id_no_labels_here);
2325 }
2326
2/2
✓ Branch 0 taken 1764 times.
✓ Branch 1 taken 198 times.
1962 if(is("skip")) step(amount);
2327 else
2328 {
2329
3/4
✓ Branch 0 taken 1221210 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 1221210 times.
✓ Branch 3 taken 198 times.
1221408 for(int i=0; i < amount; i++) write1(fillbyte[i%12]);
2330
1/2
✓ Branch 0 taken 198 times.
✗ Branch 1 not taken.
198 add_addr_to_line(addrToLinePos);
2331 }
2332
2333 }
2334
6/6
✓ Branch 0 taken 309 times.
✓ Branch 1 taken 1536 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 291 times.
✓ Branch 4 taken 18 times.
✓ Branch 5 taken 1827 times.
1845 else if (is0("cleartable"))
2335 {
2336
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 cleartable();
2337 }
2338
6/6
✓ Branch 0 taken 291 times.
✓ Branch 1 taken 1536 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 273 times.
✓ Branch 4 taken 18 times.
✓ Branch 5 taken 1809 times.
1827 else if (is0("pushtable"))
2339 {
2340
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 tablestack.append(thetable);
2341 }
2342
6/6
✓ Branch 0 taken 273 times.
✓ Branch 1 taken 1536 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 255 times.
✓ Branch 4 taken 18 times.
✓ Branch 5 taken 1791 times.
1809 else if (is0("pulltable"))
2343 {
2344
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 18 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
18 if (tablestack.count <= 0) asar_throw_error(0, error_type_block, error_id_pulltable_without_table);
2345
2/4
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 18 times.
✗ Branch 3 not taken.
18 thetable=tablestack[tablestack.count-1];
2346
1/2
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
18 tablestack.remove(tablestack.count-1);
2347 }
2348
5/6
✓ Branch 0 taken 108 times.
✓ Branch 1 taken 1683 times.
✓ Branch 2 taken 108 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 108 times.
✓ Branch 5 taken 1683 times.
1791 else if (is("function") && numwords >= 3)
2349 {
2350
3/6
✓ Branch 0 taken 54 times.
✓ Branch 1 taken 54 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 54 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
108 if (stricmp(word[2], "=")) asar_throw_error(0, error_type_block, error_id_broken_function_declaration);
2351
2/6
✓ Branch 0 taken 108 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 108 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
108 if (!confirmqpar(word[1])) asar_throw_error(0, error_type_block, error_id_broken_function_declaration);
2352
1/2
✓ Branch 0 taken 108 times.
✗ Branch 1 not taken.
108 string line=word[1];
2353
1/2
✓ Branch 0 taken 108 times.
✗ Branch 1 not taken.
108 line.qnormalize();
2354 108 char * startpar=strqchr(line.data(), '(');
2355
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 108 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
108 if (!startpar) asar_throw_error(0, error_type_block, error_id_broken_function_declaration);
2356 108 *startpar=0;
2357 108 startpar++;
2358
3/7
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 72 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 36 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
108 if (!confirmname(line)) asar_throw_error(0, error_type_block, error_id_invalid_function_name);
2359 108 char * endpar=strqchr(startpar, ')');
2360 //confirmqpar requires that all parentheses are matched, and a starting one exists, therefore it is harmless to not check for nulls
2361
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 108 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
108 if (endpar[1]) asar_throw_error(0, error_type_block, error_id_broken_function_declaration);
2362 108 *endpar=0;
2363
2364 108 string pars;
2365
2/2
✓ Branch 0 taken 108 times.
✓ Branch 1 taken 108 times.
216 for(int i = 3; i < numwords; i++){
2366
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 108 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
108 if(i > 3) pars += " ";
2367
1/2
✓ Branch 0 taken 108 times.
✗ Branch 1 not taken.
108 pars += word[i];
2368 }
2369
2370
1/2
✓ Branch 0 taken 108 times.
✗ Branch 1 not taken.
108 createuserfunc(line, startpar, pars.data());
2371 108 }
2372
6/6
✓ Branch 0 taken 1428 times.
✓ Branch 1 taken 255 times.
✓ Branch 2 taken 870 times.
✓ Branch 3 taken 558 times.
✓ Branch 4 taken 870 times.
✓ Branch 5 taken 813 times.
1683 else if (is1("print"))
2373 {
2374
2/2
✓ Branch 0 taken 852 times.
✓ Branch 1 taken 18 times.
870 string out = handle_print(par);
2375
3/4
✓ Branch 0 taken 284 times.
✓ Branch 1 taken 568 times.
✓ Branch 2 taken 284 times.
✗ Branch 3 not taken.
852 if (pass==2) print(out);
2376 852 }
2377
6/6
✓ Branch 0 taken 558 times.
✓ Branch 1 taken 255 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 540 times.
✓ Branch 4 taken 18 times.
✓ Branch 5 taken 795 times.
813 else if (is1("reset"))
2378 {
2379 if(0);
2380
2/4
✓ Branch 0 taken 18 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 9 times.
✗ Branch 3 not taken.
18 else if (!stricmp(par, "bytes")) bytes=0;
2381 else if (!stricmp(par, "freespaceuse")) freespaceuse=0;
2382 else asar_throw_error(2, error_type_block, error_id_unknown_variable);
2383 }
2384
15/18
✓ Branch 0 taken 540 times.
✓ Branch 1 taken 255 times.
✓ Branch 2 taken 486 times.
✓ Branch 3 taken 54 times.
✓ Branch 4 taken 486 times.
✓ Branch 5 taken 255 times.
✓ Branch 6 taken 486 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 486 times.
✓ Branch 9 taken 255 times.
✓ Branch 10 taken 486 times.
✗ Branch 11 not taken.
✓ Branch 12 taken 486 times.
✓ Branch 13 taken 255 times.
✗ Branch 14 not taken.
✓ Branch 15 taken 486 times.
✓ Branch 16 taken 54 times.
✓ Branch 17 taken 741 times.
795 else if (is1("padbyte") || is1("padword") || is1("padlong") || is1("paddword"))
2385 {
2386 54 int len = 0;
2387
1/2
✓ Branch 0 taken 54 times.
✗ Branch 1 not taken.
54 if (is("padbyte")) len=1;
2388
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 54 times.
54 if (is("padword")) len=2;
2389
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 54 times.
54 if (is("padlong")) len=3;
2390
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 54 times.
54 if (is("paddword")) len=4;
2391
1/2
✓ Branch 0 taken 54 times.
✗ Branch 1 not taken.
54 unsigned int val=getnum(par);
2392
5/6
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 18 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 18 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 18 times.
54 if (foundlabel && !foundlabel_static) asar_throw_error(0, error_type_block, error_id_no_labels_here);
2393
2/2
✓ Branch 0 taken 432 times.
✓ Branch 1 taken 36 times.
468 for (int i=0;i<12;i+=len)
2394 {
2395 432 unsigned int tmpval=val;
2396
2/2
✓ Branch 0 taken 432 times.
✓ Branch 1 taken 432 times.
864 for (int j=0;j<len;j++)
2397 {
2398 432 padbyte[i+j]=(unsigned char)tmpval;
2399 432 tmpval>>=8;
2400 }
2401 }
2402 }
2403
6/6
✓ Branch 0 taken 486 times.
✓ Branch 1 taken 255 times.
✓ Branch 2 taken 54 times.
✓ Branch 3 taken 432 times.
✓ Branch 4 taken 54 times.
✓ Branch 5 taken 687 times.
741 else if (is1("pad"))
2404 {
2405
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 54 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
54 if (freespaceid > 0) asar_throw_error(0, error_type_block, error_id_pad_in_freespace);
2406
1/2
✓ Branch 0 taken 54 times.
✗ Branch 1 not taken.
54 int num=(int)getnum(par);
2407
1/6
✗ Branch 0 not taken.
✓ Branch 1 taken 54 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
54 if ((unsigned int)num & 0xFF000000) asar_throw_error(0, error_type_block, error_id_snes_address_doesnt_map_to_rom, hex((unsigned int)num, 6).data());
2408
2/2
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 18 times.
54 if (num>realsnespos)
2409 {
2410
1/2
✓ Branch 0 taken 12 times.
✗ Branch 1 not taken.
36 int end=snestopc(num);
2411
1/2
✓ Branch 0 taken 12 times.
✗ Branch 1 not taken.
36 int start=snestopc(realsnespos);
2412 36 int len=end-start;
2413
3/4
✓ Branch 0 taken 180 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 180 times.
✓ Branch 3 taken 36 times.
216 for (int i=0;i<len;i++) write1(padbyte[i%12]);
2414
1/2
✓ Branch 0 taken 36 times.
✗ Branch 1 not taken.
36 add_addr_to_line(addrToLinePos);
2415 }
2416 }
2417
18/18
✓ Branch 0 taken 432 times.
✓ Branch 1 taken 255 times.
✓ Branch 2 taken 342 times.
✓ Branch 3 taken 90 times.
✓ Branch 4 taken 342 times.
✓ Branch 5 taken 255 times.
✓ Branch 6 taken 324 times.
✓ Branch 7 taken 18 times.
✓ Branch 8 taken 324 times.
✓ Branch 9 taken 255 times.
✓ Branch 10 taken 306 times.
✓ Branch 11 taken 18 times.
✓ Branch 12 taken 306 times.
✓ Branch 13 taken 255 times.
✓ Branch 14 taken 18 times.
✓ Branch 15 taken 288 times.
✓ Branch 16 taken 144 times.
✓ Branch 17 taken 543 times.
687 else if (is1("fillbyte") || is1("fillword") || is1("filllong") || is1("filldword"))
2418 {
2419 144 int len = 0;
2420
2/2
✓ Branch 0 taken 90 times.
✓ Branch 1 taken 54 times.
144 if (is("fillbyte")) len=1;
2421
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 126 times.
144 if (is("fillword")) len=2;
2422
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 126 times.
144 if (is("filllong")) len=3;
2423
2/2
✓ Branch 0 taken 18 times.
✓ Branch 1 taken 126 times.
144 if (is("filldword")) len=4;
2424
1/2
✓ Branch 0 taken 144 times.
✗ Branch 1 not taken.
144 unsigned int val= getnum(par);
2425
5/6
✓ Branch 0 taken 36 times.
✓ Branch 1 taken 108 times.
✓ Branch 2 taken 18 times.
✓ Branch 3 taken 18 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 18 times.
144 if (foundlabel && !foundlabel_static) asar_throw_error(0, error_type_block, error_id_no_labels_here);
2426
2/2
✓ Branch 0 taken 1098 times.
✓ Branch 1 taken 126 times.
1224 for (int i=0;i<12;i+=len)
2427 {
2428 1098 unsigned int tmpval=val;
2429
2/2
✓ Branch 0 taken 1512 times.
✓ Branch 1 taken 1098 times.
2610 for (int j=0;j<len;j++)
2430 {
2431 1512 fillbyte[i+j]=(unsigned char)tmpval;
2432 1512 tmpval>>=8;
2433 }
2434 }
2435 }
2436
5/6
✓ Branch 0 taken 288 times.
✓ Branch 1 taken 255 times.
✓ Branch 2 taken 288 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 288 times.
✓ Branch 5 taken 255 times.
543 else if (is1("arch"))
2437 {
2438
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 288 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
288 if(in_spcblock) asar_throw_error(0, error_type_block, error_id_feature_unavaliable_in_spcblock);
2439
4/4
✓ Branch 0 taken 180 times.
✓ Branch 1 taken 108 times.
✓ Branch 2 taken 36 times.
✓ Branch 3 taken 108 times.
288 if (!stricmp(par, "65816")) { arch=arch_65816; return; }
2440
4/4
✓ Branch 0 taken 180 times.
✓ Branch 1 taken 36 times.
✓ Branch 2 taken 72 times.
✓ Branch 3 taken 36 times.
216 if (!stricmp(par, "spc700")) { arch=arch_spc700; return; }
2441
2/4
✓ Branch 0 taken 72 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 36 times.
✗ Branch 3 not taken.
72 if (!stricmp(par, "superfx")) { arch=arch_superfx; return; }
2442 asar_throw_error(0, error_type_block, error_id_broken_command, "arch", "Invalid architecture, expected one of 65816, spc700, superfx");
2443 }
2444
8/10
✓ Branch 0 taken 255 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 147 times.
✓ Branch 3 taken 108 times.
✓ Branch 4 taken 147 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 108 times.
✓ Branch 7 taken 39 times.
✓ Branch 8 taken 39 times.
✓ Branch 9 taken 216 times.
255 else if (is0("{") || is0("}")) {}
2445 else
2446 {
2447
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 39 times.
39 asar_throw_error(1, error_type_block, error_id_unknown_command);
2448 }
2449
2450
6/6
✓ Branch 0 taken 77046 times.
✓ Branch 1 taken 55488 times.
✓ Branch 2 taken 77046 times.
✓ Branch 3 taken 55488 times.
✓ Branch 4 taken 77046 times.
✓ Branch 5 taken 55488 times.
296862 }
2451
2452 41907 bool assemblemapper(char** word, int numwords)
2453 {
2454 41907 auto previous_mapper = mapper;
2455 if(0);
2456
6/6
✓ Branch 0 taken 2379 times.
✓ Branch 1 taken 39528 times.
✓ Branch 2 taken 291 times.
✓ Branch 3 taken 2088 times.
✓ Branch 4 taken 291 times.
✓ Branch 5 taken 41616 times.
41907 else if (is0("lorom"))
2457 {
2458 //this also makes xkas set snespos to $008000 for some reason
2459 291 mapper=lorom;
2460 }
2461
6/6
✓ Branch 0 taken 2088 times.
✓ Branch 1 taken 39528 times.
✓ Branch 2 taken 123 times.
✓ Branch 3 taken 1965 times.
✓ Branch 4 taken 123 times.
✓ Branch 5 taken 41493 times.
41616 else if (is0("hirom"))
2462 {
2463 //xkas makes this point to $C00000
2464 123 mapper=hirom;
2465 }
2466
6/6
✓ Branch 0 taken 1965 times.
✓ Branch 1 taken 39528 times.
✓ Branch 2 taken 21 times.
✓ Branch 3 taken 1944 times.
✓ Branch 4 taken 21 times.
✓ Branch 5 taken 41472 times.
41493 else if (is0("exlorom"))
2467 {
2468 21 mapper = exlorom;
2469 }
2470
6/6
✓ Branch 0 taken 1944 times.
✓ Branch 1 taken 39528 times.
✓ Branch 2 taken 21 times.
✓ Branch 3 taken 1923 times.
✓ Branch 4 taken 21 times.
✓ Branch 5 taken 41451 times.
41472 else if (is0("exhirom"))
2471 {
2472 21 mapper=exhirom;
2473 }
2474
6/6
✓ Branch 0 taken 1923 times.
✓ Branch 1 taken 39528 times.
✓ Branch 2 taken 39 times.
✓ Branch 3 taken 1884 times.
✓ Branch 4 taken 39 times.
✓ Branch 5 taken 41412 times.
41451 else if (is0("sfxrom"))
2475 {
2476 39 mapper=sfxrom;
2477 //fastrom=false;
2478 }
2479
6/6
✓ Branch 0 taken 1884 times.
✓ Branch 1 taken 39528 times.
✓ Branch 2 taken 114 times.
✓ Branch 3 taken 1770 times.
✓ Branch 4 taken 114 times.
✓ Branch 5 taken 41298 times.
41412 else if (is0("norom"))
2480 {
2481 //$000000 would be the best snespos for this, but I don't care
2482 114 mapper=norom;
2483 //fastrom=false;
2484
2/2
✓ Branch 0 taken 78 times.
✓ Branch 1 taken 36 times.
114 if(!force_checksum_fix)
2485 78 checksum_fix_enabled = false;//we don't know where the header is, so don't set the checksum
2486 }
2487
6/6
✓ Branch 0 taken 1770 times.
✓ Branch 1 taken 39528 times.
✓ Branch 2 taken 21 times.
✓ Branch 3 taken 1749 times.
✓ Branch 4 taken 21 times.
✓ Branch 5 taken 41277 times.
41298 else if (is0("fullsa1rom"))
2488 {
2489 21 mapper=bigsa1rom;
2490 //fastrom=false;
2491 }
2492
2/2
✓ Branch 0 taken 75 times.
✓ Branch 1 taken 41202 times.
41277 else if (is("sa1rom"))
2493 {
2494 //fastrom=false;
2495
2/2
✓ Branch 0 taken 57 times.
✓ Branch 1 taken 18 times.
75 if (par)
2496 {
2497
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 57 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
57 if (word[2]) asar_throw_error(0, error_type_block, error_id_invalid_mapper);
2498
1/2
✓ Branch 0 taken 57 times.
✗ Branch 1 not taken.
114 if (!is_digit(par[0]) || par[1]!=',' ||
2499
2/4
✓ Branch 0 taken 57 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 57 times.
✗ Branch 3 not taken.
57 !is_digit(par[2]) || par[3]!=',' ||
2500
2/4
✓ Branch 0 taken 57 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 57 times.
✗ Branch 3 not taken.
57 !is_digit(par[4]) || par[5]!=',' ||
2501
4/10
✓ Branch 0 taken 57 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 57 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 57 times.
✗ Branch 6 not taken.
✓ Branch 7 taken 57 times.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
114 !is_digit(par[6]) || par[7]) asar_throw_error(0, error_type_block, error_id_invalid_mapper);
2502 int len;
2503
1/2
✓ Branch 0 taken 57 times.
✗ Branch 1 not taken.
57 autoptr<char**> pars=qpsplit(par, ',', &len);
2504
1/2
✓ Branch 0 taken 57 times.
✗ Branch 1 not taken.
57 verify_paren(pars);
2505
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 57 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
57 if (len!=4) asar_throw_error(0, error_type_block, error_id_invalid_mapper);
2506 57 sa1banks[0]=(par[0]-'0')<<20;
2507 57 sa1banks[1]=(par[2]-'0')<<20;
2508 57 sa1banks[4]=(par[4]-'0')<<20;
2509 57 sa1banks[5]=(par[6]-'0')<<20;
2510 57 }
2511 else
2512 {
2513 18 sa1banks[0]=0<<20;
2514 18 sa1banks[1]=1<<20;
2515 18 sa1banks[4]=2<<20;
2516 18 sa1banks[5]=3<<20;
2517 }
2518 75 mapper=sa1rom;
2519 }
2520 41202 else return false;
2521
2522
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 705 times.
705 if(in_spcblock) asar_throw_error(0, error_type_block, error_id_feature_unavaliable_in_spcblock);
2523
2/2
✓ Branch 0 taken 435 times.
✓ Branch 1 taken 270 times.
705 if(!mapper_set){
2524 435 mapper_set = true;
2525
2/2
✓ Branch 0 taken 234 times.
✓ Branch 1 taken 36 times.
270 }else if(previous_mapper != mapper){
2526 234 asar_throw_warning(1, warning_id_mapper_already_set);
2527 }
2528 705 return true;
2529 }
2530