001/*
002 * Copyright (c) 2012-2018 Institut National des Sciences Appliquées de Lyon (INSA Lyon) and others
003 *
004 * This program and the accompanying materials are made available under the
005 * terms of the Eclipse Public License 2.0 which is available at
006 * http://www.eclipse.org/legal/epl-2.0.
007 *
008 * SPDX-License-Identifier: EPL-2.0
009 */
010
011package org.eclipse.golo.runtime;
012
013import java.lang.invoke.*;
014import java.lang.invoke.MethodHandles.Lookup;
015import java.util.HashSet;
016import java.util.Set;
017import java.util.Objects;
018import java.math.BigDecimal;
019import java.math.BigInteger;
020
021import static java.lang.invoke.MethodHandles.*;
022import static java.lang.invoke.MethodType.methodType;
023import static gololang.Messages.message;
024
025public final class OperatorSupport {
026
027  private OperatorSupport() {
028    throw new UnsupportedOperationException("Don't instantiate invokedynamic bootstrap class");
029  }
030
031  static class MonomorphicInlineCache extends MutableCallSite {
032
033    final Lookup callerLookup;
034    final String name;
035    MethodHandle fallback;
036
037    MonomorphicInlineCache(Lookup callerLookup, String name, MethodType type) {
038      super(type);
039      this.callerLookup = callerLookup;
040      this.name = name;
041    }
042  }
043
044  private static final MethodHandle FALLBACK_1;
045
046  private static final MethodHandle GUARD_2;
047  private static final MethodHandle FALLBACK_2;
048
049  private static final Set<String> NO_GUARD_OPERATORS = new HashSet<String>() {
050    {
051      add("is");
052      add("isnt");
053      add("oftype");
054    }
055  };
056
057  static {
058    try {
059      Lookup lookup = MethodHandles.lookup();
060
061      FALLBACK_1 = lookup.findStatic(
062          OperatorSupport.class,
063          "fallback_1",
064          methodType(Object.class, MonomorphicInlineCache.class, Object[].class));
065
066      GUARD_2 = lookup.findStatic(
067          OperatorSupport.class,
068          "guard_2",
069          methodType(boolean.class, Class.class, Class.class, Object.class, Object.class));
070
071      FALLBACK_2 = lookup.findStatic(
072          OperatorSupport.class,
073          "fallback_2",
074          methodType(Object.class, MonomorphicInlineCache.class, Object[].class));
075    } catch (NoSuchMethodException | IllegalAccessException e) {
076      throw new Error("Could not bootstrap the required method handles", e);
077    }
078  }
079
080  public static boolean guard_2(Class<?> expected1, Class<?> expected2, Object arg1, Object arg2) {
081    Class<?> t1 = (arg1 == null) ? Object.class : arg1.getClass();
082    Class<?> t2 = (arg2 == null) ? Object.class : arg2.getClass();
083    return (t1 == expected1) && (t2 == expected2);
084  }
085
086  public static Object fallback_1(MonomorphicInlineCache inlineCache, Object[] args) throws Throwable {
087
088    Class<?> argClass = (args[0] == null) ? Object.class : args[0].getClass();
089    MethodHandle target;
090
091    try {
092      target = inlineCache.callerLookup.findStatic(
093          OperatorSupport.class, inlineCache.name, methodType(Object.class, argClass));
094    } catch (Throwable t1) {
095      try {
096        target = inlineCache.callerLookup.findStatic(
097            OperatorSupport.class, inlineCache.name + "_fallback", methodType(Object.class, Object.class));
098      } catch (Throwable t2) {
099        return reject(args[0], inlineCache.name);
100      }
101    }
102
103    target = target.asType(methodType(Object.class, Object.class));
104    target = catchException(target, ClassCastException.class, inlineCache.fallback);
105    inlineCache.setTarget(target);
106
107    return target.invokeWithArguments(args);
108  }
109
110  public static Object fallback_2(MonomorphicInlineCache inlineCache, Object[] args) throws Throwable {
111
112    Class<?> arg1Class = (args[0] == null) ? Object.class : args[0].getClass();
113    Class<?> arg2Class = (args[1] == null) ? Object.class : args[1].getClass();
114    MethodHandle target;
115
116    try {
117      target = inlineCache.callerLookup.findStatic(
118          OperatorSupport.class, inlineCache.name, methodType(Object.class, arg1Class, arg2Class));
119    } catch (Throwable t1) {
120      try {
121        target = inlineCache.callerLookup.findStatic(
122            OperatorSupport.class, inlineCache.name + "_fallback", methodType(Object.class, Object.class, Object.class));
123      } catch (Throwable t2) {
124        return reject(args[0], args[1], inlineCache.name);
125      }
126    }
127
128    target = target.asType(methodType(Object.class, Object.class, Object.class));
129    if (arg1Class == String.class || arg2Class == String.class) {
130      MethodHandle guard = insertArguments(GUARD_2, 0, arg1Class, arg2Class);
131      target = guardWithTest(guard, target, inlineCache.fallback);
132    } else {
133      target = catchException(target, ClassCastException.class, dropArguments(inlineCache.fallback, 0, ClassCastException.class));
134    }
135    inlineCache.setTarget(target);
136
137    return target.invokeWithArguments(args);
138  }
139
140  public static CallSite bootstrap(Lookup caller, String name, MethodType type, int arity) throws NoSuchMethodException, IllegalAccessException {
141
142    if (NO_GUARD_OPERATORS.contains(name)) {
143      MethodHandle target = caller.findStatic(OperatorSupport.class, name + "_noguard",
144          methodType(Object.class, Object.class, Object.class));
145      return new ConstantCallSite(target);
146    }
147
148    MonomorphicInlineCache callSite = new MonomorphicInlineCache(caller, name, type);
149    MethodHandle fallback;
150    if (arity == 2) {
151      fallback = FALLBACK_2;
152    } else {
153      fallback = FALLBACK_1;
154    }
155    MethodHandle fallbackHandle = fallback
156        .bindTo(callSite)
157        .asCollector(Object[].class, type.parameterCount())
158        .asType(type);
159    callSite.fallback = fallbackHandle;
160    callSite.setTarget(fallbackHandle);
161    return callSite;
162  }
163
164  // primitive specific arithmetic and comparisons (generated, use generate_math.rb) ......................................................................
165
166  // BEGIN GENERATED
167  public static Object plus(Character a, Character b) {
168    return ((char) a) + ((char) b);
169  }
170
171  public static Object minus(Character a, Character b) {
172    return ((char) a) - ((char) b);
173  }
174
175  public static Object divide(Character a, Character b) {
176    return ((char) a) / ((char) b);
177  }
178
179  public static Object times(Character a, Character b) {
180    return ((char) a) * ((char) b);
181  }
182
183  public static Object modulo(Character a, Character b) {
184    return ((char) a) % ((char) b);
185  }
186
187  public static Object equals(Character a, Character b) {
188    return ((char) a) == ((char) b);
189  }
190
191  public static Object notequals(Character a, Character b) {
192    return ((char) a) != ((char) b);
193  }
194
195  public static Object less(Character a, Character b) {
196    return ((char) a) < ((char) b);
197  }
198
199  public static Object lessorequals(Character a, Character b) {
200    return ((char) a) <= ((char) b);
201  }
202
203  public static Object more(Character a, Character b) {
204    return ((char) a) > ((char) b);
205  }
206
207  public static Object moreorequals(Character a, Character b) {
208    return ((char) a) >= ((char) b);
209  }
210
211  public static Object plus(Integer a, Integer b) {
212    return ((int) a) + ((int) b);
213  }
214
215  public static Object minus(Integer a, Integer b) {
216    return ((int) a) - ((int) b);
217  }
218
219  public static Object divide(Integer a, Integer b) {
220    return ((int) a) / ((int) b);
221  }
222
223  public static Object times(Integer a, Integer b) {
224    return ((int) a) * ((int) b);
225  }
226
227  public static Object modulo(Integer a, Integer b) {
228    return ((int) a) % ((int) b);
229  }
230
231  public static Object equals(Integer a, Integer b) {
232    return ((int) a) == ((int) b);
233  }
234
235  public static Object notequals(Integer a, Integer b) {
236    return ((int) a) != ((int) b);
237  }
238
239  public static Object less(Integer a, Integer b) {
240    return ((int) a) < ((int) b);
241  }
242
243  public static Object lessorequals(Integer a, Integer b) {
244    return ((int) a) <= ((int) b);
245  }
246
247  public static Object more(Integer a, Integer b) {
248    return ((int) a) > ((int) b);
249  }
250
251  public static Object moreorequals(Integer a, Integer b) {
252    return ((int) a) >= ((int) b);
253  }
254
255  public static Object plus(Long a, Long b) {
256    return ((long) a) + ((long) b);
257  }
258
259  public static Object minus(Long a, Long b) {
260    return ((long) a) - ((long) b);
261  }
262
263  public static Object divide(Long a, Long b) {
264    return ((long) a) / ((long) b);
265  }
266
267  public static Object times(Long a, Long b) {
268    return ((long) a) * ((long) b);
269  }
270
271  public static Object modulo(Long a, Long b) {
272    return ((long) a) % ((long) b);
273  }
274
275  public static Object equals(Long a, Long b) {
276    return ((long) a) == ((long) b);
277  }
278
279  public static Object notequals(Long a, Long b) {
280    return ((long) a) != ((long) b);
281  }
282
283  public static Object less(Long a, Long b) {
284    return ((long) a) < ((long) b);
285  }
286
287  public static Object lessorequals(Long a, Long b) {
288    return ((long) a) <= ((long) b);
289  }
290
291  public static Object more(Long a, Long b) {
292    return ((long) a) > ((long) b);
293  }
294
295  public static Object moreorequals(Long a, Long b) {
296    return ((long) a) >= ((long) b);
297  }
298
299  public static Object plus(Double a, Double b) {
300    return ((double) a) + ((double) b);
301  }
302
303  public static Object minus(Double a, Double b) {
304    return ((double) a) - ((double) b);
305  }
306
307  public static Object divide(Double a, Double b) {
308    return ((double) a) / ((double) b);
309  }
310
311  public static Object times(Double a, Double b) {
312    return ((double) a) * ((double) b);
313  }
314
315  public static Object modulo(Double a, Double b) {
316    return ((double) a) % ((double) b);
317  }
318
319  public static Object equals(Double a, Double b) {
320    return ((double) a) == ((double) b);
321  }
322
323  public static Object notequals(Double a, Double b) {
324    return ((double) a) != ((double) b);
325  }
326
327  public static Object less(Double a, Double b) {
328    return ((double) a) < ((double) b);
329  }
330
331  public static Object lessorequals(Double a, Double b) {
332    return ((double) a) <= ((double) b);
333  }
334
335  public static Object more(Double a, Double b) {
336    return ((double) a) > ((double) b);
337  }
338
339  public static Object moreorequals(Double a, Double b) {
340    return ((double) a) >= ((double) b);
341  }
342
343  public static Object plus(Float a, Float b) {
344    return ((float) a) + ((float) b);
345  }
346
347  public static Object minus(Float a, Float b) {
348    return ((float) a) - ((float) b);
349  }
350
351  public static Object divide(Float a, Float b) {
352    return ((float) a) / ((float) b);
353  }
354
355  public static Object times(Float a, Float b) {
356    return ((float) a) * ((float) b);
357  }
358
359  public static Object modulo(Float a, Float b) {
360    return ((float) a) % ((float) b);
361  }
362
363  public static Object equals(Float a, Float b) {
364    return ((float) a) == ((float) b);
365  }
366
367  public static Object notequals(Float a, Float b) {
368    return ((float) a) != ((float) b);
369  }
370
371  public static Object less(Float a, Float b) {
372    return ((float) a) < ((float) b);
373  }
374
375  public static Object lessorequals(Float a, Float b) {
376    return ((float) a) <= ((float) b);
377  }
378
379  public static Object more(Float a, Float b) {
380    return ((float) a) > ((float) b);
381  }
382
383  public static Object moreorequals(Float a, Float b) {
384    return ((float) a) >= ((float) b);
385  }
386
387  public static Object plus(Character a, Integer b) {
388    return ((int) a) + ((int) b);
389  }
390
391  public static Object minus(Character a, Integer b) {
392    return ((int) a) - ((int) b);
393  }
394
395  public static Object divide(Character a, Integer b) {
396    return ((int) a) / ((int) b);
397  }
398
399  public static Object times(Character a, Integer b) {
400    return ((int) a) * ((int) b);
401  }
402
403  public static Object modulo(Character a, Integer b) {
404    return ((int) a) % ((int) b);
405  }
406
407  public static Object equals(Character a, Integer b) {
408    return ((int) a) == ((int) b);
409  }
410
411  public static Object notequals(Character a, Integer b) {
412    return ((int) a) != ((int) b);
413  }
414
415  public static Object less(Character a, Integer b) {
416    return ((int) a) < ((int) b);
417  }
418
419  public static Object lessorequals(Character a, Integer b) {
420    return ((int) a) <= ((int) b);
421  }
422
423  public static Object more(Character a, Integer b) {
424    return ((int) a) > ((int) b);
425  }
426
427  public static Object moreorequals(Character a, Integer b) {
428    return ((int) a) >= ((int) b);
429  }
430
431  public static Object plus(Character a, Long b) {
432    return ((long) a) + ((long) b);
433  }
434
435  public static Object minus(Character a, Long b) {
436    return ((long) a) - ((long) b);
437  }
438
439  public static Object divide(Character a, Long b) {
440    return ((long) a) / ((long) b);
441  }
442
443  public static Object times(Character a, Long b) {
444    return ((long) a) * ((long) b);
445  }
446
447  public static Object modulo(Character a, Long b) {
448    return ((long) a) % ((long) b);
449  }
450
451  public static Object equals(Character a, Long b) {
452    return ((long) a) == ((long) b);
453  }
454
455  public static Object notequals(Character a, Long b) {
456    return ((long) a) != ((long) b);
457  }
458
459  public static Object less(Character a, Long b) {
460    return ((long) a) < ((long) b);
461  }
462
463  public static Object lessorequals(Character a, Long b) {
464    return ((long) a) <= ((long) b);
465  }
466
467  public static Object more(Character a, Long b) {
468    return ((long) a) > ((long) b);
469  }
470
471  public static Object moreorequals(Character a, Long b) {
472    return ((long) a) >= ((long) b);
473  }
474
475  public static Object plus(Character a, Double b) {
476    return ((double) a) + ((double) b);
477  }
478
479  public static Object minus(Character a, Double b) {
480    return ((double) a) - ((double) b);
481  }
482
483  public static Object divide(Character a, Double b) {
484    return ((double) a) / ((double) b);
485  }
486
487  public static Object times(Character a, Double b) {
488    return ((double) a) * ((double) b);
489  }
490
491  public static Object modulo(Character a, Double b) {
492    return ((double) a) % ((double) b);
493  }
494
495  public static Object equals(Character a, Double b) {
496    return ((double) a) == ((double) b);
497  }
498
499  public static Object notequals(Character a, Double b) {
500    return ((double) a) != ((double) b);
501  }
502
503  public static Object less(Character a, Double b) {
504    return ((double) a) < ((double) b);
505  }
506
507  public static Object lessorequals(Character a, Double b) {
508    return ((double) a) <= ((double) b);
509  }
510
511  public static Object more(Character a, Double b) {
512    return ((double) a) > ((double) b);
513  }
514
515  public static Object moreorequals(Character a, Double b) {
516    return ((double) a) >= ((double) b);
517  }
518
519  public static Object plus(Character a, Float b) {
520    return ((float) a) + ((float) b);
521  }
522
523  public static Object minus(Character a, Float b) {
524    return ((float) a) - ((float) b);
525  }
526
527  public static Object divide(Character a, Float b) {
528    return ((float) a) / ((float) b);
529  }
530
531  public static Object times(Character a, Float b) {
532    return ((float) a) * ((float) b);
533  }
534
535  public static Object modulo(Character a, Float b) {
536    return ((float) a) % ((float) b);
537  }
538
539  public static Object equals(Character a, Float b) {
540    return ((float) a) == ((float) b);
541  }
542
543  public static Object notequals(Character a, Float b) {
544    return ((float) a) != ((float) b);
545  }
546
547  public static Object less(Character a, Float b) {
548    return ((float) a) < ((float) b);
549  }
550
551  public static Object lessorequals(Character a, Float b) {
552    return ((float) a) <= ((float) b);
553  }
554
555  public static Object more(Character a, Float b) {
556    return ((float) a) > ((float) b);
557  }
558
559  public static Object moreorequals(Character a, Float b) {
560    return ((float) a) >= ((float) b);
561  }
562
563  public static Object plus(Integer a, Long b) {
564    return ((long) a) + ((long) b);
565  }
566
567  public static Object minus(Integer a, Long b) {
568    return ((long) a) - ((long) b);
569  }
570
571  public static Object divide(Integer a, Long b) {
572    return ((long) a) / ((long) b);
573  }
574
575  public static Object times(Integer a, Long b) {
576    return ((long) a) * ((long) b);
577  }
578
579  public static Object modulo(Integer a, Long b) {
580    return ((long) a) % ((long) b);
581  }
582
583  public static Object equals(Integer a, Long b) {
584    return ((long) a) == ((long) b);
585  }
586
587  public static Object notequals(Integer a, Long b) {
588    return ((long) a) != ((long) b);
589  }
590
591  public static Object less(Integer a, Long b) {
592    return ((long) a) < ((long) b);
593  }
594
595  public static Object lessorequals(Integer a, Long b) {
596    return ((long) a) <= ((long) b);
597  }
598
599  public static Object more(Integer a, Long b) {
600    return ((long) a) > ((long) b);
601  }
602
603  public static Object moreorequals(Integer a, Long b) {
604    return ((long) a) >= ((long) b);
605  }
606
607  public static Object plus(Integer a, Double b) {
608    return ((double) a) + ((double) b);
609  }
610
611  public static Object minus(Integer a, Double b) {
612    return ((double) a) - ((double) b);
613  }
614
615  public static Object divide(Integer a, Double b) {
616    return ((double) a) / ((double) b);
617  }
618
619  public static Object times(Integer a, Double b) {
620    return ((double) a) * ((double) b);
621  }
622
623  public static Object modulo(Integer a, Double b) {
624    return ((double) a) % ((double) b);
625  }
626
627  public static Object equals(Integer a, Double b) {
628    return ((double) a) == ((double) b);
629  }
630
631  public static Object notequals(Integer a, Double b) {
632    return ((double) a) != ((double) b);
633  }
634
635  public static Object less(Integer a, Double b) {
636    return ((double) a) < ((double) b);
637  }
638
639  public static Object lessorequals(Integer a, Double b) {
640    return ((double) a) <= ((double) b);
641  }
642
643  public static Object more(Integer a, Double b) {
644    return ((double) a) > ((double) b);
645  }
646
647  public static Object moreorequals(Integer a, Double b) {
648    return ((double) a) >= ((double) b);
649  }
650
651  public static Object plus(Integer a, Float b) {
652    return ((float) a) + ((float) b);
653  }
654
655  public static Object minus(Integer a, Float b) {
656    return ((float) a) - ((float) b);
657  }
658
659  public static Object divide(Integer a, Float b) {
660    return ((float) a) / ((float) b);
661  }
662
663  public static Object times(Integer a, Float b) {
664    return ((float) a) * ((float) b);
665  }
666
667  public static Object modulo(Integer a, Float b) {
668    return ((float) a) % ((float) b);
669  }
670
671  public static Object equals(Integer a, Float b) {
672    return ((float) a) == ((float) b);
673  }
674
675  public static Object notequals(Integer a, Float b) {
676    return ((float) a) != ((float) b);
677  }
678
679  public static Object less(Integer a, Float b) {
680    return ((float) a) < ((float) b);
681  }
682
683  public static Object lessorequals(Integer a, Float b) {
684    return ((float) a) <= ((float) b);
685  }
686
687  public static Object more(Integer a, Float b) {
688    return ((float) a) > ((float) b);
689  }
690
691  public static Object moreorequals(Integer a, Float b) {
692    return ((float) a) >= ((float) b);
693  }
694
695  public static Object plus(Long a, Double b) {
696    return ((double) a) + ((double) b);
697  }
698
699  public static Object minus(Long a, Double b) {
700    return ((double) a) - ((double) b);
701  }
702
703  public static Object divide(Long a, Double b) {
704    return ((double) a) / ((double) b);
705  }
706
707  public static Object times(Long a, Double b) {
708    return ((double) a) * ((double) b);
709  }
710
711  public static Object modulo(Long a, Double b) {
712    return ((double) a) % ((double) b);
713  }
714
715  public static Object equals(Long a, Double b) {
716    return ((double) a) == ((double) b);
717  }
718
719  public static Object notequals(Long a, Double b) {
720    return ((double) a) != ((double) b);
721  }
722
723  public static Object less(Long a, Double b) {
724    return ((double) a) < ((double) b);
725  }
726
727  public static Object lessorequals(Long a, Double b) {
728    return ((double) a) <= ((double) b);
729  }
730
731  public static Object more(Long a, Double b) {
732    return ((double) a) > ((double) b);
733  }
734
735  public static Object moreorequals(Long a, Double b) {
736    return ((double) a) >= ((double) b);
737  }
738
739  public static Object plus(Long a, Float b) {
740    return ((float) a) + ((float) b);
741  }
742
743  public static Object minus(Long a, Float b) {
744    return ((float) a) - ((float) b);
745  }
746
747  public static Object divide(Long a, Float b) {
748    return ((float) a) / ((float) b);
749  }
750
751  public static Object times(Long a, Float b) {
752    return ((float) a) * ((float) b);
753  }
754
755  public static Object modulo(Long a, Float b) {
756    return ((float) a) % ((float) b);
757  }
758
759  public static Object equals(Long a, Float b) {
760    return ((float) a) == ((float) b);
761  }
762
763  public static Object notequals(Long a, Float b) {
764    return ((float) a) != ((float) b);
765  }
766
767  public static Object less(Long a, Float b) {
768    return ((float) a) < ((float) b);
769  }
770
771  public static Object lessorequals(Long a, Float b) {
772    return ((float) a) <= ((float) b);
773  }
774
775  public static Object more(Long a, Float b) {
776    return ((float) a) > ((float) b);
777  }
778
779  public static Object moreorequals(Long a, Float b) {
780    return ((float) a) >= ((float) b);
781  }
782
783  public static Object plus(Double a, Float b) {
784    return ((double) a) + ((double) b);
785  }
786
787  public static Object minus(Double a, Float b) {
788    return ((double) a) - ((double) b);
789  }
790
791  public static Object divide(Double a, Float b) {
792    return ((double) a) / ((double) b);
793  }
794
795  public static Object times(Double a, Float b) {
796    return ((double) a) * ((double) b);
797  }
798
799  public static Object modulo(Double a, Float b) {
800    return ((double) a) % ((double) b);
801  }
802
803  public static Object equals(Double a, Float b) {
804    return ((double) a) == ((double) b);
805  }
806
807  public static Object notequals(Double a, Float b) {
808    return ((double) a) != ((double) b);
809  }
810
811  public static Object less(Double a, Float b) {
812    return ((double) a) < ((double) b);
813  }
814
815  public static Object lessorequals(Double a, Float b) {
816    return ((double) a) <= ((double) b);
817  }
818
819  public static Object more(Double a, Float b) {
820    return ((double) a) > ((double) b);
821  }
822
823  public static Object moreorequals(Double a, Float b) {
824    return ((double) a) >= ((double) b);
825  }
826
827  public static Object plus(Integer a, Character b) {
828    return ((int) a) + ((int) b);
829  }
830
831  public static Object minus(Integer a, Character b) {
832    return ((int) a) - ((int) b);
833  }
834
835  public static Object divide(Integer a, Character b) {
836    return ((int) a) / ((int) b);
837  }
838
839  public static Object times(Integer a, Character b) {
840    return ((int) a) * ((int) b);
841  }
842
843  public static Object modulo(Integer a, Character b) {
844    return ((int) a) % ((int) b);
845  }
846
847  public static Object equals(Integer a, Character b) {
848    return ((int) a) == ((int) b);
849  }
850
851  public static Object notequals(Integer a, Character b) {
852    return ((int) a) != ((int) b);
853  }
854
855  public static Object less(Integer a, Character b) {
856    return ((int) a) < ((int) b);
857  }
858
859  public static Object lessorequals(Integer a, Character b) {
860    return ((int) a) <= ((int) b);
861  }
862
863  public static Object more(Integer a, Character b) {
864    return ((int) a) > ((int) b);
865  }
866
867  public static Object moreorequals(Integer a, Character b) {
868    return ((int) a) >= ((int) b);
869  }
870
871  public static Object plus(Long a, Character b) {
872    return ((long) a) + ((long) b);
873  }
874
875  public static Object minus(Long a, Character b) {
876    return ((long) a) - ((long) b);
877  }
878
879  public static Object divide(Long a, Character b) {
880    return ((long) a) / ((long) b);
881  }
882
883  public static Object times(Long a, Character b) {
884    return ((long) a) * ((long) b);
885  }
886
887  public static Object modulo(Long a, Character b) {
888    return ((long) a) % ((long) b);
889  }
890
891  public static Object equals(Long a, Character b) {
892    return ((long) a) == ((long) b);
893  }
894
895  public static Object notequals(Long a, Character b) {
896    return ((long) a) != ((long) b);
897  }
898
899  public static Object less(Long a, Character b) {
900    return ((long) a) < ((long) b);
901  }
902
903  public static Object lessorequals(Long a, Character b) {
904    return ((long) a) <= ((long) b);
905  }
906
907  public static Object more(Long a, Character b) {
908    return ((long) a) > ((long) b);
909  }
910
911  public static Object moreorequals(Long a, Character b) {
912    return ((long) a) >= ((long) b);
913  }
914
915  public static Object plus(Double a, Character b) {
916    return ((double) a) + ((double) b);
917  }
918
919  public static Object minus(Double a, Character b) {
920    return ((double) a) - ((double) b);
921  }
922
923  public static Object divide(Double a, Character b) {
924    return ((double) a) / ((double) b);
925  }
926
927  public static Object times(Double a, Character b) {
928    return ((double) a) * ((double) b);
929  }
930
931  public static Object modulo(Double a, Character b) {
932    return ((double) a) % ((double) b);
933  }
934
935  public static Object equals(Double a, Character b) {
936    return ((double) a) == ((double) b);
937  }
938
939  public static Object notequals(Double a, Character b) {
940    return ((double) a) != ((double) b);
941  }
942
943  public static Object less(Double a, Character b) {
944    return ((double) a) < ((double) b);
945  }
946
947  public static Object lessorequals(Double a, Character b) {
948    return ((double) a) <= ((double) b);
949  }
950
951  public static Object more(Double a, Character b) {
952    return ((double) a) > ((double) b);
953  }
954
955  public static Object moreorequals(Double a, Character b) {
956    return ((double) a) >= ((double) b);
957  }
958
959  public static Object plus(Float a, Character b) {
960    return ((float) a) + ((float) b);
961  }
962
963  public static Object minus(Float a, Character b) {
964    return ((float) a) - ((float) b);
965  }
966
967  public static Object divide(Float a, Character b) {
968    return ((float) a) / ((float) b);
969  }
970
971  public static Object times(Float a, Character b) {
972    return ((float) a) * ((float) b);
973  }
974
975  public static Object modulo(Float a, Character b) {
976    return ((float) a) % ((float) b);
977  }
978
979  public static Object equals(Float a, Character b) {
980    return ((float) a) == ((float) b);
981  }
982
983  public static Object notequals(Float a, Character b) {
984    return ((float) a) != ((float) b);
985  }
986
987  public static Object less(Float a, Character b) {
988    return ((float) a) < ((float) b);
989  }
990
991  public static Object lessorequals(Float a, Character b) {
992    return ((float) a) <= ((float) b);
993  }
994
995  public static Object more(Float a, Character b) {
996    return ((float) a) > ((float) b);
997  }
998
999  public static Object moreorequals(Float a, Character b) {
1000    return ((float) a) >= ((float) b);
1001  }
1002
1003  public static Object plus(Long a, Integer b) {
1004    return ((long) a) + ((long) b);
1005  }
1006
1007  public static Object minus(Long a, Integer b) {
1008    return ((long) a) - ((long) b);
1009  }
1010
1011  public static Object divide(Long a, Integer b) {
1012    return ((long) a) / ((long) b);
1013  }
1014
1015  public static Object times(Long a, Integer b) {
1016    return ((long) a) * ((long) b);
1017  }
1018
1019  public static Object modulo(Long a, Integer b) {
1020    return ((long) a) % ((long) b);
1021  }
1022
1023  public static Object equals(Long a, Integer b) {
1024    return ((long) a) == ((long) b);
1025  }
1026
1027  public static Object notequals(Long a, Integer b) {
1028    return ((long) a) != ((long) b);
1029  }
1030
1031  public static Object less(Long a, Integer b) {
1032    return ((long) a) < ((long) b);
1033  }
1034
1035  public static Object lessorequals(Long a, Integer b) {
1036    return ((long) a) <= ((long) b);
1037  }
1038
1039  public static Object more(Long a, Integer b) {
1040    return ((long) a) > ((long) b);
1041  }
1042
1043  public static Object moreorequals(Long a, Integer b) {
1044    return ((long) a) >= ((long) b);
1045  }
1046
1047  public static Object plus(Double a, Integer b) {
1048    return ((double) a) + ((double) b);
1049  }
1050
1051  public static Object minus(Double a, Integer b) {
1052    return ((double) a) - ((double) b);
1053  }
1054
1055  public static Object divide(Double a, Integer b) {
1056    return ((double) a) / ((double) b);
1057  }
1058
1059  public static Object times(Double a, Integer b) {
1060    return ((double) a) * ((double) b);
1061  }
1062
1063  public static Object modulo(Double a, Integer b) {
1064    return ((double) a) % ((double) b);
1065  }
1066
1067  public static Object equals(Double a, Integer b) {
1068    return ((double) a) == ((double) b);
1069  }
1070
1071  public static Object notequals(Double a, Integer b) {
1072    return ((double) a) != ((double) b);
1073  }
1074
1075  public static Object less(Double a, Integer b) {
1076    return ((double) a) < ((double) b);
1077  }
1078
1079  public static Object lessorequals(Double a, Integer b) {
1080    return ((double) a) <= ((double) b);
1081  }
1082
1083  public static Object more(Double a, Integer b) {
1084    return ((double) a) > ((double) b);
1085  }
1086
1087  public static Object moreorequals(Double a, Integer b) {
1088    return ((double) a) >= ((double) b);
1089  }
1090
1091  public static Object plus(Float a, Integer b) {
1092    return ((float) a) + ((float) b);
1093  }
1094
1095  public static Object minus(Float a, Integer b) {
1096    return ((float) a) - ((float) b);
1097  }
1098
1099  public static Object divide(Float a, Integer b) {
1100    return ((float) a) / ((float) b);
1101  }
1102
1103  public static Object times(Float a, Integer b) {
1104    return ((float) a) * ((float) b);
1105  }
1106
1107  public static Object modulo(Float a, Integer b) {
1108    return ((float) a) % ((float) b);
1109  }
1110
1111  public static Object equals(Float a, Integer b) {
1112    return ((float) a) == ((float) b);
1113  }
1114
1115  public static Object notequals(Float a, Integer b) {
1116    return ((float) a) != ((float) b);
1117  }
1118
1119  public static Object less(Float a, Integer b) {
1120    return ((float) a) < ((float) b);
1121  }
1122
1123  public static Object lessorequals(Float a, Integer b) {
1124    return ((float) a) <= ((float) b);
1125  }
1126
1127  public static Object more(Float a, Integer b) {
1128    return ((float) a) > ((float) b);
1129  }
1130
1131  public static Object moreorequals(Float a, Integer b) {
1132    return ((float) a) >= ((float) b);
1133  }
1134
1135  public static Object plus(Double a, Long b) {
1136    return ((double) a) + ((double) b);
1137  }
1138
1139  public static Object minus(Double a, Long b) {
1140    return ((double) a) - ((double) b);
1141  }
1142
1143  public static Object divide(Double a, Long b) {
1144    return ((double) a) / ((double) b);
1145  }
1146
1147  public static Object times(Double a, Long b) {
1148    return ((double) a) * ((double) b);
1149  }
1150
1151  public static Object modulo(Double a, Long b) {
1152    return ((double) a) % ((double) b);
1153  }
1154
1155  public static Object equals(Double a, Long b) {
1156    return ((double) a) == ((double) b);
1157  }
1158
1159  public static Object notequals(Double a, Long b) {
1160    return ((double) a) != ((double) b);
1161  }
1162
1163  public static Object less(Double a, Long b) {
1164    return ((double) a) < ((double) b);
1165  }
1166
1167  public static Object lessorequals(Double a, Long b) {
1168    return ((double) a) <= ((double) b);
1169  }
1170
1171  public static Object more(Double a, Long b) {
1172    return ((double) a) > ((double) b);
1173  }
1174
1175  public static Object moreorequals(Double a, Long b) {
1176    return ((double) a) >= ((double) b);
1177  }
1178
1179  public static Object plus(Float a, Long b) {
1180    return ((float) a) + ((float) b);
1181  }
1182
1183  public static Object minus(Float a, Long b) {
1184    return ((float) a) - ((float) b);
1185  }
1186
1187  public static Object divide(Float a, Long b) {
1188    return ((float) a) / ((float) b);
1189  }
1190
1191  public static Object times(Float a, Long b) {
1192    return ((float) a) * ((float) b);
1193  }
1194
1195  public static Object modulo(Float a, Long b) {
1196    return ((float) a) % ((float) b);
1197  }
1198
1199  public static Object equals(Float a, Long b) {
1200    return ((float) a) == ((float) b);
1201  }
1202
1203  public static Object notequals(Float a, Long b) {
1204    return ((float) a) != ((float) b);
1205  }
1206
1207  public static Object less(Float a, Long b) {
1208    return ((float) a) < ((float) b);
1209  }
1210
1211  public static Object lessorequals(Float a, Long b) {
1212    return ((float) a) <= ((float) b);
1213  }
1214
1215  public static Object more(Float a, Long b) {
1216    return ((float) a) > ((float) b);
1217  }
1218
1219  public static Object moreorequals(Float a, Long b) {
1220    return ((float) a) >= ((float) b);
1221  }
1222
1223  public static Object plus(Float a, Double b) {
1224    return ((double) a) + ((double) b);
1225  }
1226
1227  public static Object minus(Float a, Double b) {
1228    return ((double) a) - ((double) b);
1229  }
1230
1231  public static Object divide(Float a, Double b) {
1232    return ((double) a) / ((double) b);
1233  }
1234
1235  public static Object times(Float a, Double b) {
1236    return ((double) a) * ((double) b);
1237  }
1238
1239  public static Object modulo(Float a, Double b) {
1240    return ((double) a) % ((double) b);
1241  }
1242
1243  public static Object equals(Float a, Double b) {
1244    return ((double) a) == ((double) b);
1245  }
1246
1247  public static Object notequals(Float a, Double b) {
1248    return ((double) a) != ((double) b);
1249  }
1250
1251  public static Object less(Float a, Double b) {
1252    return ((double) a) < ((double) b);
1253  }
1254
1255  public static Object lessorequals(Float a, Double b) {
1256    return ((double) a) <= ((double) b);
1257  }
1258
1259  public static Object more(Float a, Double b) {
1260    return ((double) a) > ((double) b);
1261  }
1262
1263  public static Object moreorequals(Float a, Double b) {
1264    return ((double) a) >= ((double) b);
1265  }
1266
1267  public static Object equals(BigDecimal a, Integer b) {
1268    return (a).compareTo(new BigDecimal(b)) == 0;
1269  }
1270
1271  public static Object equals(Integer a, BigDecimal b) {
1272    return (new BigDecimal(a)).compareTo(b) == 0;
1273  }
1274
1275  public static Object notequals(BigDecimal a, Integer b) {
1276    return (a).compareTo(new BigDecimal(b)) != 0;
1277  }
1278
1279  public static Object notequals(Integer a, BigDecimal b) {
1280    return (new BigDecimal(a)).compareTo(b) != 0;
1281  }
1282
1283  public static Object less(BigDecimal a, Integer b) {
1284    return (a).compareTo(new BigDecimal(b)) < 0;
1285  }
1286
1287  public static Object less(Integer a, BigDecimal b) {
1288    return (new BigDecimal(a)).compareTo(b) < 0;
1289  }
1290
1291  public static Object lessorequals(BigDecimal a, Integer b) {
1292    return (a).compareTo(new BigDecimal(b)) <= 0;
1293  }
1294
1295  public static Object lessorequals(Integer a, BigDecimal b) {
1296    return (new BigDecimal(a)).compareTo(b) <= 0;
1297  }
1298
1299  public static Object more(BigDecimal a, Integer b) {
1300    return (a).compareTo(new BigDecimal(b)) > 0;
1301  }
1302
1303  public static Object more(Integer a, BigDecimal b) {
1304    return (new BigDecimal(a)).compareTo(b) > 0;
1305  }
1306
1307  public static Object moreorequals(BigDecimal a, Integer b) {
1308    return (a).compareTo(new BigDecimal(b)) >= 0;
1309  }
1310
1311  public static Object moreorequals(Integer a, BigDecimal b) {
1312    return (new BigDecimal(a)).compareTo(b) >= 0;
1313  }
1314
1315  public static Object plus(BigDecimal a, Integer b) {
1316    return (a).add(new BigDecimal(b));
1317  }
1318
1319  public static Object plus(Integer a, BigDecimal b) {
1320    return (new BigDecimal(a)).add(b);
1321  }
1322
1323  public static Object minus(BigDecimal a, Integer b) {
1324    return (a).subtract(new BigDecimal(b));
1325  }
1326
1327  public static Object minus(Integer a, BigDecimal b) {
1328    return (new BigDecimal(a)).subtract(b);
1329  }
1330
1331  public static Object times(BigDecimal a, Integer b) {
1332    return (a).multiply(new BigDecimal(b));
1333  }
1334
1335  public static Object times(Integer a, BigDecimal b) {
1336    return (new BigDecimal(a)).multiply(b);
1337  }
1338
1339  public static Object divide(BigDecimal a, Integer b) {
1340    return (a).divide(new BigDecimal(b));
1341  }
1342
1343  public static Object divide(Integer a, BigDecimal b) {
1344    return (new BigDecimal(a)).divide(b);
1345  }
1346
1347  public static Object modulo(BigDecimal a, Integer b) {
1348    return (a).remainder(new BigDecimal(b));
1349  }
1350
1351  public static Object modulo(Integer a, BigDecimal b) {
1352    return (new BigDecimal(a)).remainder(b);
1353  }
1354
1355  public static Object equals(BigDecimal a, Long b) {
1356    return (a).compareTo(new BigDecimal(b)) == 0;
1357  }
1358
1359  public static Object equals(Long a, BigDecimal b) {
1360    return (new BigDecimal(a)).compareTo(b) == 0;
1361  }
1362
1363  public static Object notequals(BigDecimal a, Long b) {
1364    return (a).compareTo(new BigDecimal(b)) != 0;
1365  }
1366
1367  public static Object notequals(Long a, BigDecimal b) {
1368    return (new BigDecimal(a)).compareTo(b) != 0;
1369  }
1370
1371  public static Object less(BigDecimal a, Long b) {
1372    return (a).compareTo(new BigDecimal(b)) < 0;
1373  }
1374
1375  public static Object less(Long a, BigDecimal b) {
1376    return (new BigDecimal(a)).compareTo(b) < 0;
1377  }
1378
1379  public static Object lessorequals(BigDecimal a, Long b) {
1380    return (a).compareTo(new BigDecimal(b)) <= 0;
1381  }
1382
1383  public static Object lessorequals(Long a, BigDecimal b) {
1384    return (new BigDecimal(a)).compareTo(b) <= 0;
1385  }
1386
1387  public static Object more(BigDecimal a, Long b) {
1388    return (a).compareTo(new BigDecimal(b)) > 0;
1389  }
1390
1391  public static Object more(Long a, BigDecimal b) {
1392    return (new BigDecimal(a)).compareTo(b) > 0;
1393  }
1394
1395  public static Object moreorequals(BigDecimal a, Long b) {
1396    return (a).compareTo(new BigDecimal(b)) >= 0;
1397  }
1398
1399  public static Object moreorequals(Long a, BigDecimal b) {
1400    return (new BigDecimal(a)).compareTo(b) >= 0;
1401  }
1402
1403  public static Object plus(BigDecimal a, Long b) {
1404    return (a).add(new BigDecimal(b));
1405  }
1406
1407  public static Object plus(Long a, BigDecimal b) {
1408    return (new BigDecimal(a)).add(b);
1409  }
1410
1411  public static Object minus(BigDecimal a, Long b) {
1412    return (a).subtract(new BigDecimal(b));
1413  }
1414
1415  public static Object minus(Long a, BigDecimal b) {
1416    return (new BigDecimal(a)).subtract(b);
1417  }
1418
1419  public static Object times(BigDecimal a, Long b) {
1420    return (a).multiply(new BigDecimal(b));
1421  }
1422
1423  public static Object times(Long a, BigDecimal b) {
1424    return (new BigDecimal(a)).multiply(b);
1425  }
1426
1427  public static Object divide(BigDecimal a, Long b) {
1428    return (a).divide(new BigDecimal(b));
1429  }
1430
1431  public static Object divide(Long a, BigDecimal b) {
1432    return (new BigDecimal(a)).divide(b);
1433  }
1434
1435  public static Object modulo(BigDecimal a, Long b) {
1436    return (a).remainder(new BigDecimal(b));
1437  }
1438
1439  public static Object modulo(Long a, BigDecimal b) {
1440    return (new BigDecimal(a)).remainder(b);
1441  }
1442
1443  public static Object equals(BigDecimal a, BigInteger b) {
1444    return (a).compareTo(new BigDecimal(b)) == 0;
1445  }
1446
1447  public static Object equals(BigInteger a, BigDecimal b) {
1448    return (new BigDecimal(a)).compareTo(b) == 0;
1449  }
1450
1451  public static Object notequals(BigDecimal a, BigInteger b) {
1452    return (a).compareTo(new BigDecimal(b)) != 0;
1453  }
1454
1455  public static Object notequals(BigInteger a, BigDecimal b) {
1456    return (new BigDecimal(a)).compareTo(b) != 0;
1457  }
1458
1459  public static Object less(BigDecimal a, BigInteger b) {
1460    return (a).compareTo(new BigDecimal(b)) < 0;
1461  }
1462
1463  public static Object less(BigInteger a, BigDecimal b) {
1464    return (new BigDecimal(a)).compareTo(b) < 0;
1465  }
1466
1467  public static Object lessorequals(BigDecimal a, BigInteger b) {
1468    return (a).compareTo(new BigDecimal(b)) <= 0;
1469  }
1470
1471  public static Object lessorequals(BigInteger a, BigDecimal b) {
1472    return (new BigDecimal(a)).compareTo(b) <= 0;
1473  }
1474
1475  public static Object more(BigDecimal a, BigInteger b) {
1476    return (a).compareTo(new BigDecimal(b)) > 0;
1477  }
1478
1479  public static Object more(BigInteger a, BigDecimal b) {
1480    return (new BigDecimal(a)).compareTo(b) > 0;
1481  }
1482
1483  public static Object moreorequals(BigDecimal a, BigInteger b) {
1484    return (a).compareTo(new BigDecimal(b)) >= 0;
1485  }
1486
1487  public static Object moreorequals(BigInteger a, BigDecimal b) {
1488    return (new BigDecimal(a)).compareTo(b) >= 0;
1489  }
1490
1491  public static Object plus(BigDecimal a, BigInteger b) {
1492    return (a).add(new BigDecimal(b));
1493  }
1494
1495  public static Object plus(BigInteger a, BigDecimal b) {
1496    return (new BigDecimal(a)).add(b);
1497  }
1498
1499  public static Object minus(BigDecimal a, BigInteger b) {
1500    return (a).subtract(new BigDecimal(b));
1501  }
1502
1503  public static Object minus(BigInteger a, BigDecimal b) {
1504    return (new BigDecimal(a)).subtract(b);
1505  }
1506
1507  public static Object times(BigDecimal a, BigInteger b) {
1508    return (a).multiply(new BigDecimal(b));
1509  }
1510
1511  public static Object times(BigInteger a, BigDecimal b) {
1512    return (new BigDecimal(a)).multiply(b);
1513  }
1514
1515  public static Object divide(BigDecimal a, BigInteger b) {
1516    return (a).divide(new BigDecimal(b));
1517  }
1518
1519  public static Object divide(BigInteger a, BigDecimal b) {
1520    return (new BigDecimal(a)).divide(b);
1521  }
1522
1523  public static Object modulo(BigDecimal a, BigInteger b) {
1524    return (a).remainder(new BigDecimal(b));
1525  }
1526
1527  public static Object modulo(BigInteger a, BigDecimal b) {
1528    return (new BigDecimal(a)).remainder(b);
1529  }
1530
1531  public static Object equals(BigDecimal a, Float b) {
1532    return (a).compareTo(new BigDecimal(b)) == 0;
1533  }
1534
1535  public static Object equals(Float a, BigDecimal b) {
1536    return (new BigDecimal(a)).compareTo(b) == 0;
1537  }
1538
1539  public static Object notequals(BigDecimal a, Float b) {
1540    return (a).compareTo(new BigDecimal(b)) != 0;
1541  }
1542
1543  public static Object notequals(Float a, BigDecimal b) {
1544    return (new BigDecimal(a)).compareTo(b) != 0;
1545  }
1546
1547  public static Object less(BigDecimal a, Float b) {
1548    return (a).compareTo(new BigDecimal(b)) < 0;
1549  }
1550
1551  public static Object less(Float a, BigDecimal b) {
1552    return (new BigDecimal(a)).compareTo(b) < 0;
1553  }
1554
1555  public static Object lessorequals(BigDecimal a, Float b) {
1556    return (a).compareTo(new BigDecimal(b)) <= 0;
1557  }
1558
1559  public static Object lessorequals(Float a, BigDecimal b) {
1560    return (new BigDecimal(a)).compareTo(b) <= 0;
1561  }
1562
1563  public static Object more(BigDecimal a, Float b) {
1564    return (a).compareTo(new BigDecimal(b)) > 0;
1565  }
1566
1567  public static Object more(Float a, BigDecimal b) {
1568    return (new BigDecimal(a)).compareTo(b) > 0;
1569  }
1570
1571  public static Object moreorequals(BigDecimal a, Float b) {
1572    return (a).compareTo(new BigDecimal(b)) >= 0;
1573  }
1574
1575  public static Object moreorequals(Float a, BigDecimal b) {
1576    return (new BigDecimal(a)).compareTo(b) >= 0;
1577  }
1578
1579  public static Object plus(BigDecimal a, Float b) {
1580    return (a).add(new BigDecimal(b));
1581  }
1582
1583  public static Object plus(Float a, BigDecimal b) {
1584    return (new BigDecimal(a)).add(b);
1585  }
1586
1587  public static Object minus(BigDecimal a, Float b) {
1588    return (a).subtract(new BigDecimal(b));
1589  }
1590
1591  public static Object minus(Float a, BigDecimal b) {
1592    return (new BigDecimal(a)).subtract(b);
1593  }
1594
1595  public static Object times(BigDecimal a, Float b) {
1596    return (a).multiply(new BigDecimal(b));
1597  }
1598
1599  public static Object times(Float a, BigDecimal b) {
1600    return (new BigDecimal(a)).multiply(b);
1601  }
1602
1603  public static Object divide(BigDecimal a, Float b) {
1604    return (a).divide(new BigDecimal(b));
1605  }
1606
1607  public static Object divide(Float a, BigDecimal b) {
1608    return (new BigDecimal(a)).divide(b);
1609  }
1610
1611  public static Object modulo(BigDecimal a, Float b) {
1612    return (a).remainder(new BigDecimal(b));
1613  }
1614
1615  public static Object modulo(Float a, BigDecimal b) {
1616    return (new BigDecimal(a)).remainder(b);
1617  }
1618
1619  public static Object equals(BigDecimal a, Double b) {
1620    return (a).compareTo(new BigDecimal(b)) == 0;
1621  }
1622
1623  public static Object equals(Double a, BigDecimal b) {
1624    return (new BigDecimal(a)).compareTo(b) == 0;
1625  }
1626
1627  public static Object notequals(BigDecimal a, Double b) {
1628    return (a).compareTo(new BigDecimal(b)) != 0;
1629  }
1630
1631  public static Object notequals(Double a, BigDecimal b) {
1632    return (new BigDecimal(a)).compareTo(b) != 0;
1633  }
1634
1635  public static Object less(BigDecimal a, Double b) {
1636    return (a).compareTo(new BigDecimal(b)) < 0;
1637  }
1638
1639  public static Object less(Double a, BigDecimal b) {
1640    return (new BigDecimal(a)).compareTo(b) < 0;
1641  }
1642
1643  public static Object lessorequals(BigDecimal a, Double b) {
1644    return (a).compareTo(new BigDecimal(b)) <= 0;
1645  }
1646
1647  public static Object lessorequals(Double a, BigDecimal b) {
1648    return (new BigDecimal(a)).compareTo(b) <= 0;
1649  }
1650
1651  public static Object more(BigDecimal a, Double b) {
1652    return (a).compareTo(new BigDecimal(b)) > 0;
1653  }
1654
1655  public static Object more(Double a, BigDecimal b) {
1656    return (new BigDecimal(a)).compareTo(b) > 0;
1657  }
1658
1659  public static Object moreorequals(BigDecimal a, Double b) {
1660    return (a).compareTo(new BigDecimal(b)) >= 0;
1661  }
1662
1663  public static Object moreorequals(Double a, BigDecimal b) {
1664    return (new BigDecimal(a)).compareTo(b) >= 0;
1665  }
1666
1667  public static Object plus(BigDecimal a, Double b) {
1668    return (a).add(new BigDecimal(b));
1669  }
1670
1671  public static Object plus(Double a, BigDecimal b) {
1672    return (new BigDecimal(a)).add(b);
1673  }
1674
1675  public static Object minus(BigDecimal a, Double b) {
1676    return (a).subtract(new BigDecimal(b));
1677  }
1678
1679  public static Object minus(Double a, BigDecimal b) {
1680    return (new BigDecimal(a)).subtract(b);
1681  }
1682
1683  public static Object times(BigDecimal a, Double b) {
1684    return (a).multiply(new BigDecimal(b));
1685  }
1686
1687  public static Object times(Double a, BigDecimal b) {
1688    return (new BigDecimal(a)).multiply(b);
1689  }
1690
1691  public static Object divide(BigDecimal a, Double b) {
1692    return (a).divide(new BigDecimal(b));
1693  }
1694
1695  public static Object divide(Double a, BigDecimal b) {
1696    return (new BigDecimal(a)).divide(b);
1697  }
1698
1699  public static Object modulo(BigDecimal a, Double b) {
1700    return (a).remainder(new BigDecimal(b));
1701  }
1702
1703  public static Object modulo(Double a, BigDecimal b) {
1704    return (new BigDecimal(a)).remainder(b);
1705  }
1706
1707  public static Object equals(BigDecimal a, BigDecimal b) {
1708    return (a).compareTo(b) == 0;
1709  }
1710
1711  public static Object notequals(BigDecimal a, BigDecimal b) {
1712    return (a).compareTo(b) != 0;
1713  }
1714
1715  public static Object less(BigDecimal a, BigDecimal b) {
1716    return (a).compareTo(b) < 0;
1717  }
1718
1719  public static Object lessorequals(BigDecimal a, BigDecimal b) {
1720    return (a).compareTo(b) <= 0;
1721  }
1722
1723  public static Object more(BigDecimal a, BigDecimal b) {
1724    return (a).compareTo(b) > 0;
1725  }
1726
1727  public static Object moreorequals(BigDecimal a, BigDecimal b) {
1728    return (a).compareTo(b) >= 0;
1729  }
1730
1731  public static Object plus(BigDecimal a, BigDecimal b) {
1732    return (a).add(b);
1733  }
1734
1735  public static Object minus(BigDecimal a, BigDecimal b) {
1736    return (a).subtract(b);
1737  }
1738
1739  public static Object times(BigDecimal a, BigDecimal b) {
1740    return (a).multiply(b);
1741  }
1742
1743  public static Object divide(BigDecimal a, BigDecimal b) {
1744    return (a).divide(b);
1745  }
1746
1747  public static Object modulo(BigDecimal a, BigDecimal b) {
1748    return (a).remainder(b);
1749  }
1750
1751  public static Object equals(BigInteger a, Integer b) {
1752    return (a).compareTo(BigInteger.valueOf(b.longValue())) == 0;
1753  }
1754
1755  public static Object equals(Integer a, BigInteger b) {
1756    return (BigInteger.valueOf(a.longValue())).compareTo(b) == 0;
1757  }
1758
1759  public static Object notequals(BigInteger a, Integer b) {
1760    return (a).compareTo(BigInteger.valueOf(b.longValue())) != 0;
1761  }
1762
1763  public static Object notequals(Integer a, BigInteger b) {
1764    return (BigInteger.valueOf(a.longValue())).compareTo(b) != 0;
1765  }
1766
1767  public static Object less(BigInteger a, Integer b) {
1768    return (a).compareTo(BigInteger.valueOf(b.longValue())) < 0;
1769  }
1770
1771  public static Object less(Integer a, BigInteger b) {
1772    return (BigInteger.valueOf(a.longValue())).compareTo(b) < 0;
1773  }
1774
1775  public static Object lessorequals(BigInteger a, Integer b) {
1776    return (a).compareTo(BigInteger.valueOf(b.longValue())) <= 0;
1777  }
1778
1779  public static Object lessorequals(Integer a, BigInteger b) {
1780    return (BigInteger.valueOf(a.longValue())).compareTo(b) <= 0;
1781  }
1782
1783  public static Object more(BigInteger a, Integer b) {
1784    return (a).compareTo(BigInteger.valueOf(b.longValue())) > 0;
1785  }
1786
1787  public static Object more(Integer a, BigInteger b) {
1788    return (BigInteger.valueOf(a.longValue())).compareTo(b) > 0;
1789  }
1790
1791  public static Object moreorequals(BigInteger a, Integer b) {
1792    return (a).compareTo(BigInteger.valueOf(b.longValue())) >= 0;
1793  }
1794
1795  public static Object moreorequals(Integer a, BigInteger b) {
1796    return (BigInteger.valueOf(a.longValue())).compareTo(b) >= 0;
1797  }
1798
1799  public static Object plus(BigInteger a, Integer b) {
1800    return (a).add(BigInteger.valueOf(b.longValue()));
1801  }
1802
1803  public static Object plus(Integer a, BigInteger b) {
1804    return (BigInteger.valueOf(a.longValue())).add(b);
1805  }
1806
1807  public static Object minus(BigInteger a, Integer b) {
1808    return (a).subtract(BigInteger.valueOf(b.longValue()));
1809  }
1810
1811  public static Object minus(Integer a, BigInteger b) {
1812    return (BigInteger.valueOf(a.longValue())).subtract(b);
1813  }
1814
1815  public static Object times(BigInteger a, Integer b) {
1816    return (a).multiply(BigInteger.valueOf(b.longValue()));
1817  }
1818
1819  public static Object times(Integer a, BigInteger b) {
1820    return (BigInteger.valueOf(a.longValue())).multiply(b);
1821  }
1822
1823  public static Object divide(BigInteger a, Integer b) {
1824    return (a).divide(BigInteger.valueOf(b.longValue()));
1825  }
1826
1827  public static Object divide(Integer a, BigInteger b) {
1828    return (BigInteger.valueOf(a.longValue())).divide(b);
1829  }
1830
1831  public static Object modulo(BigInteger a, Integer b) {
1832    return (a).remainder(BigInteger.valueOf(b.longValue()));
1833  }
1834
1835  public static Object modulo(Integer a, BigInteger b) {
1836    return (BigInteger.valueOf(a.longValue())).remainder(b);
1837  }
1838
1839  public static Object equals(BigInteger a, Long b) {
1840    return (a).compareTo(BigInteger.valueOf(b.longValue())) == 0;
1841  }
1842
1843  public static Object equals(Long a, BigInteger b) {
1844    return (BigInteger.valueOf(a.longValue())).compareTo(b) == 0;
1845  }
1846
1847  public static Object notequals(BigInteger a, Long b) {
1848    return (a).compareTo(BigInteger.valueOf(b.longValue())) != 0;
1849  }
1850
1851  public static Object notequals(Long a, BigInteger b) {
1852    return (BigInteger.valueOf(a.longValue())).compareTo(b) != 0;
1853  }
1854
1855  public static Object less(BigInteger a, Long b) {
1856    return (a).compareTo(BigInteger.valueOf(b.longValue())) < 0;
1857  }
1858
1859  public static Object less(Long a, BigInteger b) {
1860    return (BigInteger.valueOf(a.longValue())).compareTo(b) < 0;
1861  }
1862
1863  public static Object lessorequals(BigInteger a, Long b) {
1864    return (a).compareTo(BigInteger.valueOf(b.longValue())) <= 0;
1865  }
1866
1867  public static Object lessorequals(Long a, BigInteger b) {
1868    return (BigInteger.valueOf(a.longValue())).compareTo(b) <= 0;
1869  }
1870
1871  public static Object more(BigInteger a, Long b) {
1872    return (a).compareTo(BigInteger.valueOf(b.longValue())) > 0;
1873  }
1874
1875  public static Object more(Long a, BigInteger b) {
1876    return (BigInteger.valueOf(a.longValue())).compareTo(b) > 0;
1877  }
1878
1879  public static Object moreorequals(BigInteger a, Long b) {
1880    return (a).compareTo(BigInteger.valueOf(b.longValue())) >= 0;
1881  }
1882
1883  public static Object moreorequals(Long a, BigInteger b) {
1884    return (BigInteger.valueOf(a.longValue())).compareTo(b) >= 0;
1885  }
1886
1887  public static Object plus(BigInteger a, Long b) {
1888    return (a).add(BigInteger.valueOf(b.longValue()));
1889  }
1890
1891  public static Object plus(Long a, BigInteger b) {
1892    return (BigInteger.valueOf(a.longValue())).add(b);
1893  }
1894
1895  public static Object minus(BigInteger a, Long b) {
1896    return (a).subtract(BigInteger.valueOf(b.longValue()));
1897  }
1898
1899  public static Object minus(Long a, BigInteger b) {
1900    return (BigInteger.valueOf(a.longValue())).subtract(b);
1901  }
1902
1903  public static Object times(BigInteger a, Long b) {
1904    return (a).multiply(BigInteger.valueOf(b.longValue()));
1905  }
1906
1907  public static Object times(Long a, BigInteger b) {
1908    return (BigInteger.valueOf(a.longValue())).multiply(b);
1909  }
1910
1911  public static Object divide(BigInteger a, Long b) {
1912    return (a).divide(BigInteger.valueOf(b.longValue()));
1913  }
1914
1915  public static Object divide(Long a, BigInteger b) {
1916    return (BigInteger.valueOf(a.longValue())).divide(b);
1917  }
1918
1919  public static Object modulo(BigInteger a, Long b) {
1920    return (a).remainder(BigInteger.valueOf(b.longValue()));
1921  }
1922
1923  public static Object modulo(Long a, BigInteger b) {
1924    return (BigInteger.valueOf(a.longValue())).remainder(b);
1925  }
1926
1927  public static Object equals(BigInteger a, BigInteger b) {
1928    return (a).compareTo(b) == 0;
1929  }
1930
1931  public static Object notequals(BigInteger a, BigInteger b) {
1932    return (a).compareTo(b) != 0;
1933  }
1934
1935  public static Object less(BigInteger a, BigInteger b) {
1936    return (a).compareTo(b) < 0;
1937  }
1938
1939  public static Object lessorequals(BigInteger a, BigInteger b) {
1940    return (a).compareTo(b) <= 0;
1941  }
1942
1943  public static Object more(BigInteger a, BigInteger b) {
1944    return (a).compareTo(b) > 0;
1945  }
1946
1947  public static Object moreorequals(BigInteger a, BigInteger b) {
1948    return (a).compareTo(b) >= 0;
1949  }
1950
1951  public static Object plus(BigInteger a, BigInteger b) {
1952    return (a).add(b);
1953  }
1954
1955  public static Object minus(BigInteger a, BigInteger b) {
1956    return (a).subtract(b);
1957  }
1958
1959  public static Object times(BigInteger a, BigInteger b) {
1960    return (a).multiply(b);
1961  }
1962
1963  public static Object divide(BigInteger a, BigInteger b) {
1964    return (a).divide(b);
1965  }
1966
1967  public static Object modulo(BigInteger a, BigInteger b) {
1968    return (a).remainder(b);
1969  }
1970
1971  public static Object equals(BigInteger a, Float b) {
1972    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) == 0;
1973  }
1974
1975  public static Object equals(Float a, BigInteger b) {
1976    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) == 0;
1977  }
1978
1979  public static Object notequals(BigInteger a, Float b) {
1980    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) != 0;
1981  }
1982
1983  public static Object notequals(Float a, BigInteger b) {
1984    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) != 0;
1985  }
1986
1987  public static Object less(BigInteger a, Float b) {
1988    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) < 0;
1989  }
1990
1991  public static Object less(Float a, BigInteger b) {
1992    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) < 0;
1993  }
1994
1995  public static Object lessorequals(BigInteger a, Float b) {
1996    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) <= 0;
1997  }
1998
1999  public static Object lessorequals(Float a, BigInteger b) {
2000    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) <= 0;
2001  }
2002
2003  public static Object more(BigInteger a, Float b) {
2004    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) > 0;
2005  }
2006
2007  public static Object more(Float a, BigInteger b) {
2008    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) > 0;
2009  }
2010
2011  public static Object moreorequals(BigInteger a, Float b) {
2012    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) >= 0;
2013  }
2014
2015  public static Object moreorequals(Float a, BigInteger b) {
2016    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) >= 0;
2017  }
2018
2019  public static Object plus(BigInteger a, Float b) {
2020    return (new BigDecimal(a)).add(new BigDecimal(b));
2021  }
2022
2023  public static Object plus(Float a, BigInteger b) {
2024    return (new BigDecimal(a)).add(new BigDecimal(b));
2025  }
2026
2027  public static Object minus(BigInteger a, Float b) {
2028    return (new BigDecimal(a)).subtract(new BigDecimal(b));
2029  }
2030
2031  public static Object minus(Float a, BigInteger b) {
2032    return (new BigDecimal(a)).subtract(new BigDecimal(b));
2033  }
2034
2035  public static Object times(BigInteger a, Float b) {
2036    return (new BigDecimal(a)).multiply(new BigDecimal(b));
2037  }
2038
2039  public static Object times(Float a, BigInteger b) {
2040    return (new BigDecimal(a)).multiply(new BigDecimal(b));
2041  }
2042
2043  public static Object divide(BigInteger a, Float b) {
2044    return (new BigDecimal(a)).divide(new BigDecimal(b));
2045  }
2046
2047  public static Object divide(Float a, BigInteger b) {
2048    return (new BigDecimal(a)).divide(new BigDecimal(b));
2049  }
2050
2051  public static Object modulo(BigInteger a, Float b) {
2052    return (new BigDecimal(a)).remainder(new BigDecimal(b));
2053  }
2054
2055  public static Object modulo(Float a, BigInteger b) {
2056    return (new BigDecimal(a)).remainder(new BigDecimal(b));
2057  }
2058
2059  public static Object equals(BigInteger a, Double b) {
2060    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) == 0;
2061  }
2062
2063  public static Object equals(Double a, BigInteger b) {
2064    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) == 0;
2065  }
2066
2067  public static Object notequals(BigInteger a, Double b) {
2068    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) != 0;
2069  }
2070
2071  public static Object notequals(Double a, BigInteger b) {
2072    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) != 0;
2073  }
2074
2075  public static Object less(BigInteger a, Double b) {
2076    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) < 0;
2077  }
2078
2079  public static Object less(Double a, BigInteger b) {
2080    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) < 0;
2081  }
2082
2083  public static Object lessorequals(BigInteger a, Double b) {
2084    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) <= 0;
2085  }
2086
2087  public static Object lessorequals(Double a, BigInteger b) {
2088    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) <= 0;
2089  }
2090
2091  public static Object more(BigInteger a, Double b) {
2092    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) > 0;
2093  }
2094
2095  public static Object more(Double a, BigInteger b) {
2096    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) > 0;
2097  }
2098
2099  public static Object moreorequals(BigInteger a, Double b) {
2100    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) >= 0;
2101  }
2102
2103  public static Object moreorequals(Double a, BigInteger b) {
2104    return (new BigDecimal(a)).compareTo(new BigDecimal(b)) >= 0;
2105  }
2106
2107  public static Object plus(BigInteger a, Double b) {
2108    return (new BigDecimal(a)).add(new BigDecimal(b));
2109  }
2110
2111  public static Object plus(Double a, BigInteger b) {
2112    return (new BigDecimal(a)).add(new BigDecimal(b));
2113  }
2114
2115  public static Object minus(BigInteger a, Double b) {
2116    return (new BigDecimal(a)).subtract(new BigDecimal(b));
2117  }
2118
2119  public static Object minus(Double a, BigInteger b) {
2120    return (new BigDecimal(a)).subtract(new BigDecimal(b));
2121  }
2122
2123  public static Object times(BigInteger a, Double b) {
2124    return (new BigDecimal(a)).multiply(new BigDecimal(b));
2125  }
2126
2127  public static Object times(Double a, BigInteger b) {
2128    return (new BigDecimal(a)).multiply(new BigDecimal(b));
2129  }
2130
2131  public static Object divide(BigInteger a, Double b) {
2132    return (new BigDecimal(a)).divide(new BigDecimal(b));
2133  }
2134
2135  public static Object divide(Double a, BigInteger b) {
2136    return (new BigDecimal(a)).divide(new BigDecimal(b));
2137  }
2138
2139  public static Object modulo(BigInteger a, Double b) {
2140    return (new BigDecimal(a)).remainder(new BigDecimal(b));
2141  }
2142
2143  public static Object modulo(Double a, BigInteger b) {
2144    return (new BigDecimal(a)).remainder(new BigDecimal(b));
2145  }
2146
2147  // END GENERATED
2148
2149  // arithmetic fallbacks .............................................................................................
2150
2151  public static Object plus(String a, String b) {
2152    return a + b;
2153  }
2154
2155  public static Object plus_fallback(Object a, Object b) {
2156    if (isNotNullAndString(a) || isNotNullAndString(b)) {
2157      return String.valueOf(a) + b;
2158    }
2159    return reject(a, b, "+");
2160  }
2161
2162  public static Object times_fallback(Object a, Object b) {
2163    if (isInteger(a) && isString(b)) {
2164      return repeat((String) b, (Integer) a);
2165    }
2166    if (isString(a) && isInteger(b)) {
2167      return repeat((String) a, (Integer) b);
2168    }
2169    return reject(a, b, "*");
2170  }
2171
2172  private static String repeat(String string, int n) {
2173    StringBuilder builder = new StringBuilder();
2174    for (int i = 0; i < n; i++) {
2175      builder.append(string);
2176    }
2177    return builder.toString();
2178  }
2179
2180  // comparisons fallback .............................................................................................
2181
2182  public static Object equals_fallback(Object a, Object b) {
2183    return Objects.equals(a, b);
2184  }
2185
2186  public static Object notequals_fallback(Object a, Object b) {
2187    return !Objects.equals(a, b);
2188  }
2189
2190  @SuppressWarnings("unchecked")
2191  public static Object less_fallback(Object a, Object b) {
2192    if (bothNotNull(a, b) && isComparable(a) && isComparable(b)) {
2193      return ((Comparable) a).compareTo(b) < 0;
2194    }
2195    return reject(a, b, "<");
2196  }
2197
2198  @SuppressWarnings("unchecked")
2199  public static Object lessorequals_fallback(Object a, Object b) {
2200    if (bothNotNull(a, b) && isComparable(a) && isComparable(b)) {
2201      return ((Comparable) a).compareTo(b) <= 0;
2202    }
2203    return reject(a, b, "<=");
2204  }
2205
2206  @SuppressWarnings("unchecked")
2207  public static Object more_fallback(Object a, Object b) {
2208    if (bothNotNull(a, b) && isComparable(a) && isComparable(b)) {
2209      return ((Comparable) a).compareTo(b) > 0;
2210    }
2211    return reject(a, b, ">");
2212  }
2213
2214  @SuppressWarnings("unchecked")
2215  public static Object moreorequals_fallback(Object a, Object b) {
2216    if (bothNotNull(a, b) && isComparable(a) && isComparable(b)) {
2217      return ((Comparable) a).compareTo(b) >= 0;
2218    }
2219    return reject(a, b, ">=");
2220  }
2221
2222  // logic ............................................................................................................
2223
2224  public static Object not(Boolean a) {
2225    return !a;
2226  }
2227
2228  public static Object oftype_noguard(Object a, Object b) {
2229    if (isClass(b)) {
2230      return ((Class<?>) b).isInstance(a);
2231    }
2232    return reject(a, b, "oftype");
2233  }
2234
2235  public static Object is_noguard(Object a, Object b) {
2236    return a == b;
2237  }
2238
2239  public static Object isnt_noguard(Object a, Object b) {
2240    return a != b;
2241  }
2242
2243  // helpers ..........................................................................................................
2244
2245  private static boolean isNotNullAndString(Object obj) {
2246    return (obj != null) && (obj.getClass() == String.class);
2247  }
2248
2249  private static boolean bothNotNull(Object a, Object b) {
2250    return (a != null) && (b != null);
2251  }
2252
2253  private static boolean isString(Object obj) {
2254    return obj.getClass() == String.class;
2255  }
2256
2257  private static boolean isInteger(Object obj) {
2258    return obj.getClass() == Integer.class;
2259  }
2260
2261  private static boolean isComparable(Object obj) {
2262    return obj instanceof Comparable<?>;
2263  }
2264
2265  private static boolean isClass(Object obj) {
2266    return (obj != null) && (obj.getClass() == Class.class);
2267  }
2268
2269  private static Object reject(Object a, String symbol) throws IllegalArgumentException {
2270    throw new IllegalArgumentException(
2271        message("invalid_unary_operator", symbol, a.getClass().getName()));
2272  }
2273
2274  private static Object reject(Object a, Object b, String symbol) throws IllegalArgumentException {
2275    throw new IllegalArgumentException(
2276        message("invalid_binary_operator", symbol, a.getClass().getName(), b.getClass().getName()));
2277  }
2278}