build administrativa
[m6w6/ext-psi] / src / calc / bin.h
1 /*******************************************************************************
2 Copyright (c) 2016, Michael Wallner <mike@php.net>.
3 All rights reserved.
4
5 Redistribution and use in source and binary forms, with or without
6 modification, are permitted provided that the following conditions are met:
7
8 * Redistributions of source code must retain the above copyright notice,
9 this list of conditions and the following disclaimer.
10 * Redistributions in binary form must reproduce the above copyright
11 notice, this list of conditions and the following disclaimer in the
12 documentation and/or other materials provided with the distribution.
13
14 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15 AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
17 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE
18 FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
19 DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
20 SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
21 CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
22 OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
23 OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24 *******************************************************************************/
25
26 #include <assert.h>
27
28 #include "token.h"
29
30 static inline token_t psi_calc_bin_lshift(token_t t1, impl_val *v1, token_t t2, impl_val *v2, impl_val *res)
31 {
32 impl_val i1, i2;
33
34 switch (t1) {
35 case PSI_T_INT8:
36 i1.u64 = v1->i8;
37 break;
38
39 case PSI_T_UINT8:
40 i1.u64 = v1->u8;
41 break;
42
43 case PSI_T_INT16:
44 i1.u64 = v1->i16;
45 break;
46
47 case PSI_T_UINT16:
48 i1.u64 = v1->u16;
49 break;
50
51 case PSI_T_INT32:
52 i1.u64 = v1->i32;
53 break;
54
55 case PSI_T_UINT32:
56 i1.u64 = v1->u32;
57 break;
58
59 case PSI_T_INT64:
60 i1.u64 = v1->i64;
61 break;
62
63 case PSI_T_UINT64:
64 i1.u64 = v1->u64;
65 break;
66
67 #if HAVE_INT128
68 case PSI_T_INT128:
69 i1.u64 = v1->i128;
70 break;
71
72 #endif
73
74 #if HAVE_UINT128
75 case PSI_T_UINT128:
76 i1.u64 = v1->u128;
77 break;
78
79 #endif
80
81 case PSI_T_FLOAT:
82 i1.u64 = v1->fval;
83 break;
84
85 case PSI_T_DOUBLE:
86 i1.u64 = v1->dval;
87 break;
88
89 #if HAVE_LONG_DOUBLE
90 case PSI_T_LONG_DOUBLE:
91 i1.u64 = v1->ldval;
92 break;
93
94 #endif
95
96 default:
97 assert(0);
98 break;
99 }
100
101 switch (t2) {
102 case PSI_T_INT8:
103 i2.u64 = v2->i8;
104 break;
105 case PSI_T_UINT8:
106 i2.u64 = v2->u8;
107 break;
108 case PSI_T_INT16:
109 i2.u64 = v2->i16;
110 break;
111 case PSI_T_UINT16:
112 i2.u64 = v2->u16;
113 break;
114 case PSI_T_INT32:
115 i2.u64 = v2->i32;
116 break;
117 case PSI_T_UINT32:
118 i2.u64 = v2->u32;
119 break;
120 case PSI_T_INT64:
121 i2.u64 = v2->i64;
122 break;
123 case PSI_T_UINT64:
124 i2.u64 = v2->u64;
125 break;
126 #if HAVE_INT128
127 case PSI_T_INT128:
128 i2.u64 = v2->i128;
129 break;
130 #endif
131
132 #if HAVE_UINT128
133 case PSI_T_UINT128:
134 i2.u64 = v2->u128;
135 break;
136 #endif
137
138 case PSI_T_FLOAT:
139 i2.u64 = v2->fval;
140 break;
141 case PSI_T_DOUBLE:
142 i2.u64 = v2->dval;
143 break;
144 #if HAVE_LONG_DOUBLE
145 case PSI_T_LONG_DOUBLE:
146 i2.u64 = v2->ldval;
147 break;
148 #endif
149
150 default:
151 assert(0);
152 break;
153 }
154
155 res->u64 = i1.u64 << i2.u64;
156 return PSI_T_UINT64;
157 }
158
159 static inline token_t psi_calc_bin_rshift(token_t t1, impl_val *v1, token_t t2, impl_val *v2, impl_val *res)
160 {
161 impl_val i1, i2;
162
163 switch (t1) {
164 case PSI_T_INT8:
165 i1.u64 = v1->i8;
166 break;
167
168 case PSI_T_UINT8:
169 i1.u64 = v1->u8;
170 break;
171
172 case PSI_T_INT16:
173 i1.u64 = v1->i16;
174 break;
175
176 case PSI_T_UINT16:
177 i1.u64 = v1->u16;
178 break;
179
180 case PSI_T_INT32:
181 i1.u64 = v1->i32;
182 break;
183
184 case PSI_T_UINT32:
185 i1.u64 = v1->u32;
186 break;
187
188 case PSI_T_INT64:
189 i1.u64 = v1->i64;
190 break;
191
192 case PSI_T_UINT64:
193 i1.u64 = v1->u64;
194 break;
195
196 #if HAVE_INT128
197 case PSI_T_INT128:
198 i1.u64 = v1->i128;
199 break;
200
201 #endif
202
203 #if HAVE_UINT128
204 case PSI_T_UINT128:
205 i1.u64 = v1->u128;
206 break;
207
208 #endif
209
210 case PSI_T_FLOAT:
211 i1.u64 = v1->fval;
212 break;
213
214 case PSI_T_DOUBLE:
215 i1.u64 = v1->dval;
216 break;
217
218 #if HAVE_LONG_DOUBLE
219 case PSI_T_LONG_DOUBLE:
220 i1.u64 = v1->ldval;
221 break;
222
223 #endif
224
225 default:
226 assert(0);
227 break;
228 }
229
230 switch (t2) {
231 case PSI_T_INT8:
232 i2.u64 = v2->i8;
233 break;
234 case PSI_T_UINT8:
235 i2.u64 = v2->u8;
236 break;
237 case PSI_T_INT16:
238 i2.u64 = v2->i16;
239 break;
240 case PSI_T_UINT16:
241 i2.u64 = v2->u16;
242 break;
243 case PSI_T_INT32:
244 i2.u64 = v2->i32;
245 break;
246 case PSI_T_UINT32:
247 i2.u64 = v2->u32;
248 break;
249 case PSI_T_INT64:
250 i2.u64 = v2->i64;
251 break;
252 case PSI_T_UINT64:
253 i2.u64 = v2->u64;
254 break;
255 #if HAVE_INT128
256 case PSI_T_INT128:
257 i2.u64 = v2->i128;
258 break;
259 #endif
260
261 #if HAVE_UINT128
262 case PSI_T_UINT128:
263 i2.u64 = v2->u128;
264 break;
265 #endif
266
267 case PSI_T_FLOAT:
268 i2.u64 = v2->fval;
269 break;
270 case PSI_T_DOUBLE:
271 i2.u64 = v2->dval;
272 break;
273 #if HAVE_LONG_DOUBLE
274 case PSI_T_LONG_DOUBLE:
275 i2.u64 = v2->ldval;
276 break;
277 #endif
278
279 default:
280 assert(0);
281 break;
282 }
283
284 res->u64 = i1.u64 >> i2.u64;
285 return PSI_T_UINT64;
286 }
287
288 static inline token_t psi_calc_bin_and(token_t t1, impl_val *v1, token_t t2, impl_val *v2, impl_val *res)
289 {
290 impl_val i1, i2;
291
292 switch (t1) {
293 case PSI_T_INT8:
294 i1.u64 = v1->i8;
295 break;
296
297 case PSI_T_UINT8:
298 i1.u64 = v1->u8;
299 break;
300
301 case PSI_T_INT16:
302 i1.u64 = v1->i16;
303 break;
304
305 case PSI_T_UINT16:
306 i1.u64 = v1->u16;
307 break;
308
309 case PSI_T_INT32:
310 i1.u64 = v1->i32;
311 break;
312
313 case PSI_T_UINT32:
314 i1.u64 = v1->u32;
315 break;
316
317 case PSI_T_INT64:
318 i1.u64 = v1->i64;
319 break;
320
321 case PSI_T_UINT64:
322 i1.u64 = v1->u64;
323 break;
324
325 #if HAVE_INT128
326 case PSI_T_INT128:
327 i1.u64 = v1->i128;
328 break;
329
330 #endif
331
332 #if HAVE_UINT128
333 case PSI_T_UINT128:
334 i1.u64 = v1->u128;
335 break;
336
337 #endif
338
339 case PSI_T_FLOAT:
340 i1.u64 = v1->fval;
341 break;
342
343 case PSI_T_DOUBLE:
344 i1.u64 = v1->dval;
345 break;
346
347 #if HAVE_LONG_DOUBLE
348 case PSI_T_LONG_DOUBLE:
349 i1.u64 = v1->ldval;
350 break;
351
352 #endif
353
354 default:
355 assert(0);
356 break;
357 }
358
359 switch (t2) {
360 case PSI_T_INT8:
361 i2.u64 = v2->i8;
362 break;
363 case PSI_T_UINT8:
364 i2.u64 = v2->u8;
365 break;
366 case PSI_T_INT16:
367 i2.u64 = v2->i16;
368 break;
369 case PSI_T_UINT16:
370 i2.u64 = v2->u16;
371 break;
372 case PSI_T_INT32:
373 i2.u64 = v2->i32;
374 break;
375 case PSI_T_UINT32:
376 i2.u64 = v2->u32;
377 break;
378 case PSI_T_INT64:
379 i2.u64 = v2->i64;
380 break;
381 case PSI_T_UINT64:
382 i2.u64 = v2->u64;
383 break;
384 #if HAVE_INT128
385 case PSI_T_INT128:
386 i2.u64 = v2->i128;
387 break;
388 #endif
389
390 #if HAVE_UINT128
391 case PSI_T_UINT128:
392 i2.u64 = v2->u128;
393 break;
394 #endif
395
396 case PSI_T_FLOAT:
397 i2.u64 = v2->fval;
398 break;
399 case PSI_T_DOUBLE:
400 i2.u64 = v2->dval;
401 break;
402 #if HAVE_LONG_DOUBLE
403 case PSI_T_LONG_DOUBLE:
404 i2.u64 = v2->ldval;
405 break;
406 #endif
407
408 default:
409 assert(0);
410 break;
411 }
412
413 res->u64 = i1.u64 & i2.u64;
414 return PSI_T_UINT64;
415 }
416
417 static inline token_t psi_calc_bin_xor(token_t t1, impl_val *v1, token_t t2, impl_val *v2, impl_val *res)
418 {
419 impl_val i1, i2;
420
421 switch (t1) {
422 case PSI_T_INT8:
423 i1.u64 = v1->i8;
424 break;
425
426 case PSI_T_UINT8:
427 i1.u64 = v1->u8;
428 break;
429
430 case PSI_T_INT16:
431 i1.u64 = v1->i16;
432 break;
433
434 case PSI_T_UINT16:
435 i1.u64 = v1->u16;
436 break;
437
438 case PSI_T_INT32:
439 i1.u64 = v1->i32;
440 break;
441
442 case PSI_T_UINT32:
443 i1.u64 = v1->u32;
444 break;
445
446 case PSI_T_INT64:
447 i1.u64 = v1->i64;
448 break;
449
450 case PSI_T_UINT64:
451 i1.u64 = v1->u64;
452 break;
453
454 #if HAVE_INT128
455 case PSI_T_INT128:
456 i1.u64 = v1->i128;
457 break;
458
459 #endif
460
461 #if HAVE_UINT128
462 case PSI_T_UINT128:
463 i1.u64 = v1->u128;
464 break;
465
466 #endif
467
468 case PSI_T_FLOAT:
469 i1.u64 = v1->fval;
470 break;
471
472 case PSI_T_DOUBLE:
473 i1.u64 = v1->dval;
474 break;
475
476 #if HAVE_LONG_DOUBLE
477 case PSI_T_LONG_DOUBLE:
478 i1.u64 = v1->ldval;
479 break;
480
481 #endif
482
483 default:
484 assert(0);
485 break;
486 }
487
488 switch (t2) {
489 case PSI_T_INT8:
490 i2.u64 = v2->i8;
491 break;
492 case PSI_T_UINT8:
493 i2.u64 = v2->u8;
494 break;
495 case PSI_T_INT16:
496 i2.u64 = v2->i16;
497 break;
498 case PSI_T_UINT16:
499 i2.u64 = v2->u16;
500 break;
501 case PSI_T_INT32:
502 i2.u64 = v2->i32;
503 break;
504 case PSI_T_UINT32:
505 i2.u64 = v2->u32;
506 break;
507 case PSI_T_INT64:
508 i2.u64 = v2->i64;
509 break;
510 case PSI_T_UINT64:
511 i2.u64 = v2->u64;
512 break;
513 #if HAVE_INT128
514 case PSI_T_INT128:
515 i2.u64 = v2->i128;
516 break;
517 #endif
518
519 #if HAVE_UINT128
520 case PSI_T_UINT128:
521 i2.u64 = v2->u128;
522 break;
523 #endif
524
525 case PSI_T_FLOAT:
526 i2.u64 = v2->fval;
527 break;
528 case PSI_T_DOUBLE:
529 i2.u64 = v2->dval;
530 break;
531 #if HAVE_LONG_DOUBLE
532 case PSI_T_LONG_DOUBLE:
533 i2.u64 = v2->ldval;
534 break;
535 #endif
536
537 default:
538 assert(0);
539 break;
540 }
541
542 res->u64 = i1.u64 ^ i2.u64;
543 return PSI_T_UINT64;
544 }
545
546 static inline token_t psi_calc_bin_or(token_t t1, impl_val *v1, token_t t2, impl_val *v2, impl_val *res)
547 {
548 impl_val i1, i2;
549
550 switch (t1) {
551 case PSI_T_INT8:
552 i1.u64 = v1->i8;
553 break;
554
555 case PSI_T_UINT8:
556 i1.u64 = v1->u8;
557 break;
558
559 case PSI_T_INT16:
560 i1.u64 = v1->i16;
561 break;
562
563 case PSI_T_UINT16:
564 i1.u64 = v1->u16;
565 break;
566
567 case PSI_T_INT32:
568 i1.u64 = v1->i32;
569 break;
570
571 case PSI_T_UINT32:
572 i1.u64 = v1->u32;
573 break;
574
575 case PSI_T_INT64:
576 i1.u64 = v1->i64;
577 break;
578
579 case PSI_T_UINT64:
580 i1.u64 = v1->u64;
581 break;
582
583 #if HAVE_INT128
584 case PSI_T_INT128:
585 i1.u64 = v1->i128;
586 break;
587
588 #endif
589
590 #if HAVE_UINT128
591 case PSI_T_UINT128:
592 i1.u64 = v1->u128;
593 break;
594
595 #endif
596
597 case PSI_T_FLOAT:
598 i1.u64 = v1->fval;
599 break;
600
601 case PSI_T_DOUBLE:
602 i1.u64 = v1->dval;
603 break;
604
605 #if HAVE_LONG_DOUBLE
606 case PSI_T_LONG_DOUBLE:
607 i1.u64 = v1->ldval;
608 break;
609
610 #endif
611
612 default:
613 assert(0);
614 break;
615 }
616
617 switch (t2) {
618 case PSI_T_INT8:
619 i2.u64 = v2->i8;
620 break;
621 case PSI_T_UINT8:
622 i2.u64 = v2->u8;
623 break;
624 case PSI_T_INT16:
625 i2.u64 = v2->i16;
626 break;
627 case PSI_T_UINT16:
628 i2.u64 = v2->u16;
629 break;
630 case PSI_T_INT32:
631 i2.u64 = v2->i32;
632 break;
633 case PSI_T_UINT32:
634 i2.u64 = v2->u32;
635 break;
636 case PSI_T_INT64:
637 i2.u64 = v2->i64;
638 break;
639 case PSI_T_UINT64:
640 i2.u64 = v2->u64;
641 break;
642 #if HAVE_INT128
643 case PSI_T_INT128:
644 i2.u64 = v2->i128;
645 break;
646 #endif
647
648 #if HAVE_UINT128
649 case PSI_T_UINT128:
650 i2.u64 = v2->u128;
651 break;
652 #endif
653
654 case PSI_T_FLOAT:
655 i2.u64 = v2->fval;
656 break;
657 case PSI_T_DOUBLE:
658 i2.u64 = v2->dval;
659 break;
660 #if HAVE_LONG_DOUBLE
661 case PSI_T_LONG_DOUBLE:
662 i2.u64 = v2->ldval;
663 break;
664 #endif
665
666 default:
667 assert(0);
668 break;
669 }
670
671 res->u64 = i1.u64 | i2.u64;
672 return PSI_T_UINT64;
673 }