001    /*
002     *  This file is part of the Jikes RVM project (http://jikesrvm.org).
003     *
004     *  This file is licensed to You under the Eclipse Public License (EPL);
005     *  You may not use this file except in compliance with the License. You
006     *  may obtain a copy of the License at
007     *
008     *      http://www.opensource.org/licenses/eclipse-1.0.php
009     *
010     *  See the COPYRIGHT.txt file distributed with this work for information
011     *  regarding copyright ownership.
012     */
013    package org.jikesrvm.compilers.baseline;
014    
015    import org.jikesrvm.ArchitectureSpecific.Assembler;
016    import org.jikesrvm.ArchitectureSpecific.MachineCode;
017    import org.jikesrvm.ArchitectureSpecific.StackframeLayoutConstants;
018    import org.jikesrvm.VM;
019    import org.jikesrvm.Services;
020    import org.jikesrvm.SizeConstants;
021    import org.jikesrvm.classloader.ClassLoaderConstants;
022    import org.jikesrvm.classloader.RVMArray;
023    import org.jikesrvm.classloader.BytecodeConstants;
024    import org.jikesrvm.classloader.BytecodeStream;
025    import org.jikesrvm.classloader.RVMClass;
026    import org.jikesrvm.classloader.FieldReference;
027    import org.jikesrvm.classloader.RVMMethod;
028    import org.jikesrvm.classloader.MethodReference;
029    import org.jikesrvm.classloader.NormalMethod;
030    import org.jikesrvm.classloader.RVMType;
031    import org.jikesrvm.classloader.TypeReference;
032    import org.jikesrvm.compilers.common.CompiledMethod;
033    import org.jikesrvm.compilers.common.CompiledMethods;
034    import org.jikesrvm.compilers.common.assembler.ForwardReference;
035    import org.jikesrvm.osr.bytecodes.InvokeStatic;
036    import org.jikesrvm.runtime.Statics;
037    import org.jikesrvm.scheduler.RVMThread;
038    import org.vmmagic.pragma.NoInline;
039    import org.vmmagic.unboxed.Offset;
040    
041    /**
042     * Framework compiler - platform independent code.
043     * This compiler provides the structure for a very simple compiler --
044     * one that generates code as each bytecode in the class file is
045     * seen. It is the common base class of the base compiler.
046     */
047    public abstract class TemplateCompilerFramework
048        implements BytecodeConstants, ClassLoaderConstants, SizeConstants, StackframeLayoutConstants {
049    
050      /**
051       * has fullyBootedVM been called by VM.boot?
052       */
053      protected static boolean fullyBootedVM = false;
054    
055      /**
056       * The method being compiled
057       */
058      protected final NormalMethod method;
059    
060      /**
061       * The declaring class of the method being compiled
062       */
063      protected final RVMClass klass;
064    
065      /**
066       * The bytecodes of the method being compiled
067       */
068      protected final BytecodeStream bcodes;
069    
070      /**
071       * Mapping from bytecodes to machine code offsets
072       */
073      protected final int[] bytecodeMap;
074    
075      /**
076       * bi at the start of a bytecode
077       */
078      protected int biStart;
079    
080      /**
081       * The Assembler being used for this compilation
082       */
083      public Assembler asm;
084    
085      /**
086       * The compiledMethod assigned to this compilation of method
087       */
088      protected final CompiledMethod compiledMethod;
089    
090      /**
091       * The height of the expression stack at the start of each bytecode.
092       * Only saved for some architectures, on others this field will be null.
093       * See the BaselineCompilerImpl constructor.
094       */
095      protected int[] stackHeights;
096    
097      /**
098       * machine code offset at which the lock is acquired in the prologue of a synchronized method.
099       */
100      protected int lockOffset;
101    
102      /**
103       * Should we print the machine code we generate?
104       */
105      protected boolean shouldPrint = false;
106    
107      /**
108       * Is the method currently being compiled interruptible?
109       */
110      protected final boolean isInterruptible;
111      /**
112       * Does this method do checkstore?
113       */
114      protected final boolean doesCheckStore;
115    
116      /**
117       * Is the method currently being compiled uninterruptible?
118       */
119      protected final boolean isUninterruptible;
120    
121      /**
122       * Is the method currently being compiled unpreemptible?
123       */
124      protected final boolean isUnpreemptible;
125    
126      /**
127       * Construct a BaselineCompilerImpl
128       */
129      protected TemplateCompilerFramework(CompiledMethod cm) {
130        compiledMethod = cm;
131        method = (NormalMethod) cm.getMethod();
132    
133        klass = method.getDeclaringClass();
134    
135        // new synthesized bytecodes for OSR
136        if (method.isForOsrSpecialization()) {
137          bcodes = method.getOsrSynthesizedBytecodes();
138        } else {
139          bcodes = method.getBytecodes();
140        }
141    
142        bytecodeMap = new int[bcodes.length() + 1];
143        isInterruptible = method.isInterruptible();
144        if (isInterruptible) {
145          isUninterruptible = false;
146          isUnpreemptible = false;
147        } else {
148          isUninterruptible = method.isUninterruptible();
149          isUnpreemptible = method.isUnpreemptible();
150        }
151        doesCheckStore = !method.hasNoCheckStoreAnnotation();
152    
153        // Double check logically uninterruptible methods have been annotated as
154        // uninterruptible
155        // TODO: remove logically uninterruptible annotations (see RVM-115).
156        if (VM.VerifyAssertions && method.hasLogicallyUninterruptibleAnnotation()) {
157          VM._assert(isUninterruptible, "LogicallyUninterruptible but not Uninterruptible method: ",
158            method.toString());
159        }
160      }
161    
162      final int[] getBytecodeMap() {
163        return bytecodeMap;
164      }
165    
166      /**
167       * Print a message to mark the start of machine code printing for a method
168       * @param method
169       */
170      protected final void printStartHeader(RVMMethod method) {
171        VM.sysWrite(getCompilerName());
172        VM.sysWrite(" Start: Final machine code for method ");
173        VM.sysWrite(method.getDeclaringClass().toString());
174        VM.sysWrite(" ");
175        VM.sysWrite(method.getName());
176        VM.sysWrite(" ");
177        VM.sysWrite(method.getDescriptor());
178        VM.sysWrite("\n");
179      }
180    
181      /**
182       * Print a message to mark the end of machine code printing for a method
183       * @param method
184       */
185      protected final void printEndHeader(RVMMethod method) {
186        VM.sysWrite(getCompilerName());
187        VM.sysWrite(" End: Final machine code for method ");
188        VM.sysWrite(method.getDeclaringClass().toString());
189        VM.sysWrite(" ");
190        VM.sysWrite(method.getName());
191        VM.sysWrite(" ");
192        VM.sysWrite(method.getDescriptor());
193        VM.sysWrite("\n");
194      }
195    
196      /**
197       * Print a message of a method name
198       */
199      protected final void printMethodMessage() {
200        String compilerName = getCompilerName();
201    
202        // It's tempting to use Character.toUpperCase here, but Character
203        // isn't fully initialized early in booting, so don't do it!
204        if (compilerName.equals("baseline")) {
205          VM.sysWrite("-methodBaseline ");
206        } else if (VM.VerifyAssertions) {
207          VM._assert(VM.NOT_REACHED, "Unknown compiler");
208        }
209        VM.sysWrite(method.getDeclaringClass().toString());
210        VM.sysWrite(" ");
211        VM.sysWrite(method.getName());
212        VM.sysWrite(" ");
213        VM.sysWrite(method.getDescriptor());
214        VM.sysWrite(" \n");
215      }
216    
217      /**
218       * Main code generation loop.
219       */
220      protected final MachineCode genCode() {
221    
222        emit_prologue();
223        while (bcodes.hasMoreBytecodes()) {
224          biStart = bcodes.index();
225          bytecodeMap[biStart] = asm.getMachineCodeIndex();
226          asm.resolveForwardReferences(biStart);
227          starting_bytecode();
228          int code = bcodes.nextInstruction();
229          switch (code) {
230            case JBC_nop: {
231              if (shouldPrint) asm.noteBytecode(biStart, "nop");
232              break;
233            }
234    
235            case JBC_aconst_null: {
236              if (shouldPrint) asm.noteBytecode(biStart, "aconst_null");
237              emit_aconst_null();
238              break;
239            }
240    
241            case JBC_iconst_m1: {
242              if (shouldPrint) asm.noteBytecode(biStart, "iconst_m1");
243              emit_iconst(-1);
244              break;
245            }
246    
247            case JBC_iconst_0: {
248              if (shouldPrint) asm.noteBytecode(biStart, "iconst_0");
249              emit_iconst(0);
250              break;
251            }
252    
253            case JBC_iconst_1: {
254              if (shouldPrint) asm.noteBytecode(biStart, "iconst_1");
255              emit_iconst(1);
256              break;
257            }
258    
259            case JBC_iconst_2: {
260              if (shouldPrint) asm.noteBytecode(biStart, "iconst_2");
261              emit_iconst(2);
262              break;
263            }
264    
265            case JBC_iconst_3: {
266              if (shouldPrint) asm.noteBytecode(biStart, "iconst_3");
267              emit_iconst(3);
268              break;
269            }
270    
271            case JBC_iconst_4: {
272              if (shouldPrint) asm.noteBytecode(biStart, "iconst_4");
273              emit_iconst(4);
274              break;
275            }
276    
277            case JBC_iconst_5: {
278              if (shouldPrint) asm.noteBytecode(biStart, "iconst_5");
279              emit_iconst(5);
280              break;
281            }
282    
283            case JBC_lconst_0: {
284              if (shouldPrint) asm.noteBytecode(biStart, "lconst_0");  // floating-point 0 is long 0
285              emit_lconst(0);
286              break;
287            }
288    
289            case JBC_lconst_1: {
290              if (shouldPrint) asm.noteBytecode(biStart, "lconst_1");
291              emit_lconst(1);
292              break;
293            }
294    
295            case JBC_fconst_0: {
296              if (shouldPrint) asm.noteBytecode(biStart, "fconst_0");
297              emit_fconst_0();
298              break;
299            }
300    
301            case JBC_fconst_1: {
302              if (shouldPrint) asm.noteBytecode(biStart, "fconst_1");
303              emit_fconst_1();
304              break;
305            }
306    
307            case JBC_fconst_2: {
308              if (shouldPrint) asm.noteBytecode(biStart, "fconst_2");
309              emit_fconst_2();
310              break;
311            }
312    
313            case JBC_dconst_0: {
314              if (shouldPrint) asm.noteBytecode(biStart, "dconst_0");
315              emit_dconst_0();
316              break;
317            }
318    
319            case JBC_dconst_1: {
320              if (shouldPrint) asm.noteBytecode(biStart, "dconst_1");
321              emit_dconst_1();
322              break;
323            }
324    
325            case JBC_bipush: {
326              int val = bcodes.getByteValue();
327              if (shouldPrint) asm.noteBytecode(biStart, "bipush", val);
328              emit_iconst(val);
329              break;
330            }
331    
332            case JBC_sipush: {
333              int val = bcodes.getShortValue();
334              if (shouldPrint) asm.noteBytecode(biStart, "sipush", val);
335              emit_iconst(val);
336              break;
337            }
338    
339            case JBC_ldc: {
340              int index = bcodes.getConstantIndex();
341              if (shouldPrint) asm.noteBytecode(biStart, "ldc", index);
342              Offset offset = klass.getLiteralOffset(index);
343              byte type = klass.getLiteralDescription(index);
344              emit_ldc(offset, type);
345              break;
346            }
347    
348            case JBC_ldc_w: {
349              int index = bcodes.getWideConstantIndex();
350              if (shouldPrint) asm.noteBytecode(biStart, "ldc_w", index);
351              Offset offset = klass.getLiteralOffset(index);
352              byte type = klass.getLiteralDescription(index);
353              emit_ldc(offset, type);
354              break;
355            }
356    
357            case JBC_ldc2_w: {
358              int index = bcodes.getWideConstantIndex();
359              if (shouldPrint) asm.noteBytecode(biStart, "ldc2_w", index);
360              Offset offset = klass.getLiteralOffset(index);
361              byte type = klass.getLiteralDescription(index);
362              emit_ldc2(offset, type);
363              break;
364            }
365    
366            case JBC_iload: {
367              int index = bcodes.getLocalNumber();
368              if (shouldPrint) asm.noteBytecode(biStart, "iload", index);
369              emit_iload(index);
370              break;
371            }
372    
373            case JBC_lload: {
374              int index = bcodes.getLocalNumber();
375              if (shouldPrint) asm.noteBytecode(biStart, "lload", index);
376              emit_lload(index);
377              break;
378            }
379    
380            case JBC_fload: {
381              int index = bcodes.getLocalNumber();
382              if (shouldPrint) asm.noteBytecode(biStart, "fload", index);
383              emit_fload(index);
384              break;
385            }
386    
387            case JBC_dload: {
388              int index = bcodes.getLocalNumber();
389              if (shouldPrint) asm.noteBytecode(biStart, "dload", index);
390              emit_dload(index);
391              break;
392            }
393    
394            case JBC_aload: {
395              int index = bcodes.getLocalNumber();
396              if (shouldPrint) asm.noteBytecode(biStart, "aload", index);
397              emit_aload(index);
398              break;
399            }
400    
401            case JBC_iload_0: {
402              if (shouldPrint) asm.noteBytecode(biStart, "iload_0");
403              emit_iload(0);
404              break;
405            }
406    
407            case JBC_iload_1: {
408              if (shouldPrint) asm.noteBytecode(biStart, "iload_1");
409              emit_iload(1);
410              break;
411            }
412    
413            case JBC_iload_2: {
414              if (shouldPrint) asm.noteBytecode(biStart, "iload_2");
415              emit_iload(2);
416              break;
417            }
418    
419            case JBC_iload_3: {
420              if (shouldPrint) asm.noteBytecode(biStart, "iload_3");
421              emit_iload(3);
422              break;
423            }
424    
425            case JBC_lload_0: {
426              if (shouldPrint) asm.noteBytecode(biStart, "lload_0");
427              emit_lload(0);
428              break;
429            }
430    
431            case JBC_lload_1: {
432              if (shouldPrint) asm.noteBytecode(biStart, "lload_1");
433              emit_lload(1);
434              break;
435            }
436    
437            case JBC_lload_2: {
438              if (shouldPrint) asm.noteBytecode(biStart, "lload_2");
439              emit_lload(2);
440              break;
441            }
442    
443            case JBC_lload_3: {
444              if (shouldPrint) asm.noteBytecode(biStart, "lload_3");
445              emit_lload(3);
446              break;
447            }
448    
449            case JBC_fload_0: {
450              if (shouldPrint) asm.noteBytecode(biStart, "fload_0");
451              emit_fload(0);
452              break;
453            }
454    
455            case JBC_fload_1: {
456              if (shouldPrint) asm.noteBytecode(biStart, "fload_1");
457              emit_fload(1);
458              break;
459            }
460    
461            case JBC_fload_2: {
462              if (shouldPrint) asm.noteBytecode(biStart, "fload_2");
463              emit_fload(2);
464              break;
465            }
466    
467            case JBC_fload_3: {
468              if (shouldPrint) asm.noteBytecode(biStart, "fload_3");
469              emit_fload(3);
470              break;
471            }
472    
473            case JBC_dload_0: {
474              if (shouldPrint) asm.noteBytecode(biStart, "dload_0");
475              emit_dload(0);
476              break;
477            }
478    
479            case JBC_dload_1: {
480              if (shouldPrint) asm.noteBytecode(biStart, "dload_1");
481              emit_dload(1);
482              break;
483            }
484    
485            case JBC_dload_2: {
486              if (shouldPrint) asm.noteBytecode(biStart, "dload_2");
487              emit_dload(2);
488              break;
489            }
490    
491            case JBC_dload_3: {
492              if (shouldPrint) asm.noteBytecode(biStart, "dload_3");
493              emit_dload(3);
494              break;
495            }
496    
497            case JBC_aload_0: {
498              if (shouldPrint) asm.noteBytecode(biStart, "aload_0");
499              emit_aload(0);
500              break;
501            }
502    
503            case JBC_aload_1: {
504              if (shouldPrint) asm.noteBytecode(biStart, "aload_1");
505              emit_aload(1);
506              break;
507            }
508    
509            case JBC_aload_2: {
510              if (shouldPrint) asm.noteBytecode(biStart, "aload_2");
511              emit_aload(2);
512              break;
513            }
514    
515            case JBC_aload_3: {
516              if (shouldPrint) asm.noteBytecode(biStart, "aload_3");
517              emit_aload(3);
518              break;
519            }
520    
521            case JBC_iaload: {
522              if (shouldPrint) asm.noteBytecode(biStart, "iaload");
523              emit_iaload();
524              break;
525            }
526    
527            case JBC_laload: {
528              if (shouldPrint) asm.noteBytecode(biStart, "laload");
529              emit_laload();
530              break;
531            }
532    
533            case JBC_faload: {
534              if (shouldPrint) asm.noteBytecode(biStart, "faload");
535              emit_faload();
536              break;
537            }
538    
539            case JBC_daload: {
540              if (shouldPrint) asm.noteBytecode(biStart, "daload");
541              emit_daload();
542              break;
543            }
544    
545            case JBC_aaload: {
546              if (shouldPrint) asm.noteBytecode(biStart, "aaload");
547              emit_aaload();
548              break;
549            }
550    
551            case JBC_baload: {
552              if (shouldPrint) asm.noteBytecode(biStart, "baload");
553              emit_baload();
554              break;
555            }
556    
557            case JBC_caload: {
558              if (shouldPrint) asm.noteBytecode(biStart, "caload");
559              emit_caload();
560              break;
561            }
562    
563            case JBC_saload: {
564              if (shouldPrint) asm.noteBytecode(biStart, "saload");
565              emit_saload();
566              break;
567            }
568    
569            case JBC_istore: {
570              int index = bcodes.getLocalNumber();
571              if (shouldPrint) asm.noteBytecode(biStart, "istore", index);
572              emit_istore(index);
573              break;
574            }
575    
576            case JBC_lstore: {
577              int index = bcodes.getLocalNumber();
578              if (shouldPrint) asm.noteBytecode(biStart, "lstore", index);
579              emit_lstore(index);
580              break;
581            }
582    
583            case JBC_fstore: {
584              int index = bcodes.getLocalNumber();
585              if (shouldPrint) asm.noteBytecode(biStart, "fstore", index);
586              emit_fstore(index);
587              break;
588            }
589    
590            case JBC_dstore: {
591              int index = bcodes.getLocalNumber();
592              if (shouldPrint) asm.noteBytecode(biStart, "dstore", index);
593              emit_dstore(index);
594              break;
595            }
596    
597            case JBC_astore: {
598              int index = bcodes.getLocalNumber();
599              if (shouldPrint) asm.noteBytecode(biStart, "astore", index);
600              emit_astore(index);
601              break;
602            }
603    
604            case JBC_istore_0: {
605              if (shouldPrint) asm.noteBytecode(biStart, "istore_0");
606              emit_istore(0);
607              break;
608            }
609    
610            case JBC_istore_1: {
611              if (shouldPrint) asm.noteBytecode(biStart, "istore_1");
612              emit_istore(1);
613              break;
614            }
615    
616            case JBC_istore_2: {
617              if (shouldPrint) asm.noteBytecode(biStart, "istore_2");
618              emit_istore(2);
619              break;
620            }
621    
622            case JBC_istore_3: {
623              if (shouldPrint) asm.noteBytecode(biStart, "istore_3");
624              emit_istore(3);
625              break;
626            }
627    
628            case JBC_lstore_0: {
629              if (shouldPrint) asm.noteBytecode(biStart, "lstore_0");
630              emit_lstore(0);
631              break;
632            }
633    
634            case JBC_lstore_1: {
635              if (shouldPrint) asm.noteBytecode(biStart, "lstore_1");
636              emit_lstore(1);
637              break;
638            }
639    
640            case JBC_lstore_2: {
641              if (shouldPrint) asm.noteBytecode(biStart, "lstore_2");
642              emit_lstore(2);
643              break;
644            }
645    
646            case JBC_lstore_3: {
647              if (shouldPrint) asm.noteBytecode(biStart, "lstore_3");
648              emit_lstore(3);
649              break;
650            }
651    
652            case JBC_fstore_0: {
653              if (shouldPrint) asm.noteBytecode(biStart, "fstore_0");
654              emit_fstore(0);
655              break;
656            }
657    
658            case JBC_fstore_1: {
659              if (shouldPrint) asm.noteBytecode(biStart, "fstore_1");
660              emit_fstore(1);
661              break;
662            }
663    
664            case JBC_fstore_2: {
665              if (shouldPrint) asm.noteBytecode(biStart, "fstore_2");
666              emit_fstore(2);
667              break;
668            }
669    
670            case JBC_fstore_3: {
671              if (shouldPrint) asm.noteBytecode(biStart, "fstore_3");
672              emit_fstore(3);
673              break;
674            }
675    
676            case JBC_dstore_0: {
677              if (shouldPrint) asm.noteBytecode(biStart, "dstore_0");
678              emit_dstore(0);
679              break;
680            }
681    
682            case JBC_dstore_1: {
683              if (shouldPrint) asm.noteBytecode(biStart, "dstore_1");
684              emit_dstore(1);
685              break;
686            }
687    
688            case JBC_dstore_2: {
689              if (shouldPrint) asm.noteBytecode(biStart, "dstore_2");
690              emit_dstore(2);
691              break;
692            }
693    
694            case JBC_dstore_3: {
695              if (shouldPrint) asm.noteBytecode(biStart, "dstore_3");
696              emit_dstore(3);
697              break;
698            }
699    
700            case JBC_astore_0: {
701              if (shouldPrint) asm.noteBytecode(biStart, "astore_0");
702              emit_astore(0);
703              break;
704            }
705    
706            case JBC_astore_1: {
707              if (shouldPrint) asm.noteBytecode(biStart, "astore_1");
708              emit_astore(1);
709              break;
710            }
711    
712            case JBC_astore_2: {
713              if (shouldPrint) asm.noteBytecode(biStart, "astore_2");
714              emit_astore(2);
715              break;
716            }
717    
718            case JBC_astore_3: {
719              if (shouldPrint) asm.noteBytecode(biStart, "astore_3");
720              emit_astore(3);
721              break;
722            }
723    
724            case JBC_iastore: {
725              if (shouldPrint) asm.noteBytecode(biStart, "iastore");
726              emit_iastore();
727              break;
728            }
729    
730            case JBC_lastore: {
731              if (shouldPrint) asm.noteBytecode(biStart, "lastore");
732              emit_lastore();
733              break;
734            }
735    
736            case JBC_fastore: {
737              if (shouldPrint) asm.noteBytecode(biStart, "fastore");
738              emit_fastore();
739              break;
740            }
741    
742            case JBC_dastore: {
743              if (shouldPrint) asm.noteBytecode(biStart, "dastore");
744              emit_dastore();
745              break;
746            }
747    
748            case JBC_aastore: {
749              if (shouldPrint) asm.noteBytecode(biStart, "aastore");
750              // Forbidden from uninterruptible code as may cause an {@link
751              // ArrayStoreException}
752              if (VM.VerifyUnint && isUninterruptible && doesCheckStore) forbiddenBytecode("aastore", bcodes.index());
753              emit_aastore();
754              break;
755            }
756    
757            case JBC_bastore: {
758              if (shouldPrint) asm.noteBytecode(biStart, "bastore");
759              emit_bastore();
760              break;
761            }
762    
763            case JBC_castore: {
764              if (shouldPrint) asm.noteBytecode(biStart, "castore");
765              emit_castore();
766              break;
767            }
768    
769            case JBC_sastore: {
770              if (shouldPrint) asm.noteBytecode(biStart, "sastore");
771              emit_sastore();
772              break;
773            }
774    
775            case JBC_pop: {
776              if (shouldPrint) asm.noteBytecode(biStart, "pop");
777              emit_pop();
778              break;
779            }
780    
781            case JBC_pop2: {
782              if (shouldPrint) asm.noteBytecode(biStart, "pop2");
783              emit_pop2();
784              break;
785            }
786    
787            case JBC_dup: {
788              if (shouldPrint) asm.noteBytecode(biStart, "dup");
789              emit_dup();
790              break;
791            }
792    
793            case JBC_dup_x1: {
794              if (shouldPrint) asm.noteBytecode(biStart, "dup_x1");
795              emit_dup_x1();
796              break;
797            }
798    
799            case JBC_dup_x2: {
800              if (shouldPrint) asm.noteBytecode(biStart, "dup_x2");
801              emit_dup_x2();
802              break;
803            }
804    
805            case JBC_dup2: {
806              if (shouldPrint) asm.noteBytecode(biStart, "dup2");
807              emit_dup2();
808              break;
809            }
810    
811            case JBC_dup2_x1: {
812              if (shouldPrint) asm.noteBytecode(biStart, "dup2_x1");
813              emit_dup2_x1();
814              break;
815            }
816    
817            case JBC_dup2_x2: {
818              if (shouldPrint) asm.noteBytecode(biStart, "dup2_x2");
819              emit_dup2_x2();
820              break;
821            }
822    
823            case JBC_swap: {
824              if (shouldPrint) asm.noteBytecode(biStart, "swap");
825              emit_swap();
826              break;
827            }
828    
829            case JBC_iadd: {
830              if (shouldPrint) asm.noteBytecode(biStart, "iadd");
831              emit_iadd();
832              break;
833            }
834    
835            case JBC_ladd: {
836              if (shouldPrint) asm.noteBytecode(biStart, "ladd");
837              emit_ladd();
838              break;
839            }
840    
841            case JBC_fadd: {
842              if (shouldPrint) asm.noteBytecode(biStart, "fadd");
843              emit_fadd();
844              break;
845            }
846    
847            case JBC_dadd: {
848              if (shouldPrint) asm.noteBytecode(biStart, "dadd");
849              emit_dadd();
850              break;
851            }
852    
853            case JBC_isub: {
854              if (shouldPrint) asm.noteBytecode(biStart, "isub");
855              emit_isub();
856              break;
857            }
858    
859            case JBC_lsub: {
860              if (shouldPrint) asm.noteBytecode(biStart, "lsub");
861              emit_lsub();
862              break;
863            }
864    
865            case JBC_fsub: {
866              if (shouldPrint) asm.noteBytecode(biStart, "fsub");
867              emit_fsub();
868              break;
869            }
870    
871            case JBC_dsub: {
872              if (shouldPrint) asm.noteBytecode(biStart, "dsub");
873              emit_dsub();
874              break;
875            }
876    
877            case JBC_imul: {
878              if (shouldPrint) asm.noteBytecode(biStart, "imul");
879              emit_imul();
880              break;
881            }
882    
883            case JBC_lmul: {
884              if (shouldPrint) asm.noteBytecode(biStart, "lmul");
885              emit_lmul();
886              break;
887            }
888    
889            case JBC_fmul: {
890              if (shouldPrint) asm.noteBytecode(biStart, "fmul");
891              emit_fmul();
892              break;
893            }
894    
895            case JBC_dmul: {
896              if (shouldPrint) asm.noteBytecode(biStart, "dmul");
897              emit_dmul();
898              break;
899            }
900    
901            case JBC_idiv: {
902              if (shouldPrint) asm.noteBytecode(biStart, "idiv");
903              emit_idiv();
904              break;
905            }
906    
907            case JBC_ldiv: {
908              if (shouldPrint) asm.noteBytecode(biStart, "ldiv");
909              emit_ldiv();
910              break;
911            }
912    
913            case JBC_fdiv: {
914              if (shouldPrint) asm.noteBytecode(biStart, "fdiv");
915              emit_fdiv();
916              break;
917            }
918    
919            case JBC_ddiv: {
920              if (shouldPrint) asm.noteBytecode(biStart, "ddiv");
921              emit_ddiv();
922              break;
923            }
924    
925            case JBC_irem: {
926              if (shouldPrint) asm.noteBytecode(biStart, "irem");
927              emit_irem();
928              break;
929            }
930    
931            case JBC_lrem: {
932              if (shouldPrint) asm.noteBytecode(biStart, "lrem");
933              emit_lrem();
934              break;
935            }
936    
937            case JBC_frem: {
938              if (shouldPrint) asm.noteBytecode(biStart, "frem");
939              emit_frem();
940              break;
941            }
942    
943            case JBC_drem: {
944              if (shouldPrint) asm.noteBytecode(biStart, "drem");
945              emit_drem();
946              break;
947            }
948    
949            case JBC_ineg: {
950              if (shouldPrint) asm.noteBytecode(biStart, "ineg");
951              emit_ineg();
952              break;
953            }
954    
955            case JBC_lneg: {
956              if (shouldPrint) asm.noteBytecode(biStart, "lneg");
957              emit_lneg();
958              break;
959            }
960    
961            case JBC_fneg: {
962              if (shouldPrint) asm.noteBytecode(biStart, "fneg");
963              emit_fneg();
964              break;
965            }
966    
967            case JBC_dneg: {
968              if (shouldPrint) asm.noteBytecode(biStart, "dneg");
969              emit_dneg();
970              break;
971            }
972    
973            case JBC_ishl: {
974              if (shouldPrint) asm.noteBytecode(biStart, "ishl");
975              emit_ishl();
976              break;
977            }
978    
979            case JBC_lshl: {
980              if (shouldPrint) asm.noteBytecode(biStart, "lshl");    // l >> n
981              emit_lshl();
982              break;
983            }
984    
985            case JBC_ishr: {
986              if (shouldPrint) asm.noteBytecode(biStart, "ishr");
987              emit_ishr();
988              break;
989            }
990    
991            case JBC_lshr: {
992              if (shouldPrint) asm.noteBytecode(biStart, "lshr");
993              emit_lshr();
994              break;
995            }
996    
997            case JBC_iushr: {
998              if (shouldPrint) asm.noteBytecode(biStart, "iushr");
999              emit_iushr();
1000              break;
1001            }
1002    
1003            case JBC_lushr: {
1004              if (shouldPrint) asm.noteBytecode(biStart, "lushr");
1005              emit_lushr();
1006              break;
1007            }
1008    
1009            case JBC_iand: {
1010              if (shouldPrint) asm.noteBytecode(biStart, "iand");
1011              emit_iand();
1012              break;
1013            }
1014    
1015            case JBC_land: {
1016              if (shouldPrint) asm.noteBytecode(biStart, "land");
1017              emit_land();
1018              break;
1019            }
1020    
1021            case JBC_ior: {
1022              if (shouldPrint) asm.noteBytecode(biStart, "ior");
1023              emit_ior();
1024              break;
1025            }
1026    
1027            case JBC_lor: {
1028              if (shouldPrint) asm.noteBytecode(biStart, "lor");
1029              emit_lor();
1030              break;
1031            }
1032    
1033            case JBC_ixor: {
1034              if (shouldPrint) asm.noteBytecode(biStart, "ixor");
1035              emit_ixor();
1036              break;
1037            }
1038    
1039            case JBC_lxor: {
1040              if (shouldPrint) asm.noteBytecode(biStart, "lxor");
1041              emit_lxor();
1042              break;
1043            }
1044    
1045            case JBC_iinc: {
1046              int index = bcodes.getLocalNumber();
1047              int val = bcodes.getIncrement();
1048              if (shouldPrint) asm.noteBytecode(biStart, "iinc", index, val);
1049              emit_iinc(index, val);
1050              break;
1051            }
1052    
1053            case JBC_i2l: {
1054              if (shouldPrint) asm.noteBytecode(biStart, "i2l");
1055              emit_i2l();
1056              break;
1057            }
1058    
1059            case JBC_i2f: {
1060              if (shouldPrint) asm.noteBytecode(biStart, "i2f");
1061              emit_i2f();
1062              break;
1063            }
1064    
1065            case JBC_i2d: {
1066              if (shouldPrint) asm.noteBytecode(biStart, "i2d");
1067              emit_i2d();
1068              break;
1069            }
1070    
1071            case JBC_l2i: {
1072              if (shouldPrint) asm.noteBytecode(biStart, "l2i");
1073              emit_l2i();
1074              break;
1075            }
1076    
1077            case JBC_l2f: {
1078              if (shouldPrint) asm.noteBytecode(biStart, "l2f");
1079              emit_l2f();
1080              break;
1081            }
1082    
1083            case JBC_l2d: {
1084              if (shouldPrint) asm.noteBytecode(biStart, "l2d");
1085              emit_l2d();
1086              break;
1087            }
1088    
1089            case JBC_f2i: {
1090              if (shouldPrint) asm.noteBytecode(biStart, "f2i");
1091              emit_f2i();
1092              break;
1093            }
1094    
1095            case JBC_f2l: {
1096              if (shouldPrint) asm.noteBytecode(biStart, "f2l");
1097              emit_f2l();
1098              break;
1099            }
1100    
1101            case JBC_f2d: {
1102              if (shouldPrint) asm.noteBytecode(biStart, "f2d");
1103              emit_f2d();
1104              break;
1105            }
1106    
1107            case JBC_d2i: {
1108              if (shouldPrint) asm.noteBytecode(biStart, "d2i");
1109              emit_d2i();
1110              break;
1111            }
1112    
1113            case JBC_d2l: {
1114              if (shouldPrint) asm.noteBytecode(biStart, "d2l");
1115              emit_d2l();
1116              break;
1117            }
1118    
1119            case JBC_d2f: {
1120              if (shouldPrint) asm.noteBytecode(biStart, "d2f");
1121              emit_d2f();
1122              break;
1123            }
1124    
1125            case JBC_int2byte: {
1126              if (shouldPrint) asm.noteBytecode(biStart, "i2b");
1127              emit_i2b();
1128              break;
1129            }
1130    
1131            case JBC_int2char: {
1132              if (shouldPrint) asm.noteBytecode(biStart, "i2c");
1133              emit_i2c();
1134              break;
1135            }
1136    
1137            case JBC_int2short: {
1138              if (shouldPrint) asm.noteBytecode(biStart, "i2s");
1139              emit_i2s();
1140              break;
1141            }
1142    
1143            case JBC_lcmp: {
1144              if (shouldPrint) asm.noteBytecode(biStart, "lcmp");  // a ? b
1145              emit_lcmp();
1146              break;
1147            }
1148    
1149            case JBC_fcmpl: {
1150              if (shouldPrint) asm.noteBytecode(biStart, "fcmpl");
1151              emit_fcmpl();
1152              break;
1153            }
1154    
1155            case JBC_fcmpg: {
1156              if (shouldPrint) asm.noteBytecode(biStart, "fcmpg");
1157              emit_fcmpg();
1158              break;
1159            }
1160    
1161            case JBC_dcmpl: {
1162              if (shouldPrint) asm.noteBytecode(biStart, "dcmpl");
1163              emit_dcmpl();
1164              break;
1165            }
1166    
1167            case JBC_dcmpg: {
1168              if (shouldPrint) asm.noteBytecode(biStart, "dcmpg");
1169              emit_dcmpg();
1170              break;
1171            }
1172    
1173            case JBC_ifeq: {
1174              int offset = bcodes.getBranchOffset();
1175              int bTarget = biStart + offset;
1176              if (shouldPrint) asm.noteBranchBytecode(biStart, "ifeq", offset, bTarget);
1177              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1178              emit_ifeq(bTarget);
1179              break;
1180            }
1181    
1182            case JBC_ifne: {
1183              int offset = bcodes.getBranchOffset();
1184              int bTarget = biStart + offset;
1185              if (shouldPrint) asm.noteBranchBytecode(biStart, "ifne", offset, bTarget);
1186              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1187              emit_ifne(bTarget);
1188              break;
1189            }
1190    
1191            case JBC_iflt: {
1192              int offset = bcodes.getBranchOffset();
1193              int bTarget = biStart + offset;
1194              if (shouldPrint) asm.noteBranchBytecode(biStart, "iflt", offset, bTarget);
1195              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1196              emit_iflt(bTarget);
1197              break;
1198            }
1199    
1200            case JBC_ifge: {
1201              int offset = bcodes.getBranchOffset();
1202              int bTarget = biStart + offset;
1203              if (shouldPrint) asm.noteBranchBytecode(biStart, "ifge", offset, bTarget);
1204              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1205              emit_ifge(bTarget);
1206              break;
1207            }
1208    
1209            case JBC_ifgt: {
1210              int offset = bcodes.getBranchOffset();
1211              int bTarget = biStart + offset;
1212              if (shouldPrint) asm.noteBranchBytecode(biStart, "ifgt", offset, bTarget);
1213              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1214              emit_ifgt(bTarget);
1215              break;
1216            }
1217    
1218            case JBC_ifle: {
1219              int offset = bcodes.getBranchOffset();
1220              int bTarget = biStart + offset;
1221              if (shouldPrint) asm.noteBranchBytecode(biStart, "ifle", offset, bTarget);
1222              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1223              emit_ifle(bTarget);
1224              break;
1225            }
1226    
1227            case JBC_if_icmpeq: {
1228              int offset = bcodes.getBranchOffset();
1229              int bTarget = biStart + offset;
1230              if (shouldPrint) asm.noteBranchBytecode(biStart, "if_icmpeq", offset, bTarget);
1231              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1232              emit_if_icmpeq(bTarget);
1233              break;
1234            }
1235    
1236            case JBC_if_icmpne: {
1237              int offset = bcodes.getBranchOffset();
1238              int bTarget = biStart + offset;
1239              if (shouldPrint) asm.noteBranchBytecode(biStart, "if_icmpne", offset, bTarget);
1240              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1241              emit_if_icmpne(bTarget);
1242              break;
1243            }
1244    
1245            case JBC_if_icmplt: {
1246              int offset = bcodes.getBranchOffset();
1247              int bTarget = biStart + offset;
1248              if (shouldPrint) asm.noteBranchBytecode(biStart, "if_icmplt", offset, bTarget);
1249              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1250              emit_if_icmplt(bTarget);
1251              break;
1252            }
1253    
1254            case JBC_if_icmpge: {
1255              int offset = bcodes.getBranchOffset();
1256              int bTarget = biStart + offset;
1257              if (shouldPrint) asm.noteBranchBytecode(biStart, "if_icmpge", offset, bTarget);
1258              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1259              emit_if_icmpge(bTarget);
1260              break;
1261            }
1262    
1263            case JBC_if_icmpgt: {
1264              int offset = bcodes.getBranchOffset();
1265              int bTarget = biStart + offset;
1266              if (shouldPrint) asm.noteBranchBytecode(biStart, "if_icmpgt", offset, bTarget);
1267              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1268              emit_if_icmpgt(bTarget);
1269              break;
1270            }
1271    
1272            case JBC_if_icmple: {
1273              int offset = bcodes.getBranchOffset();
1274              int bTarget = biStart + offset;
1275              if (shouldPrint) asm.noteBranchBytecode(biStart, "if_icmple", offset, bTarget);
1276              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1277              emit_if_icmple(bTarget);
1278              break;
1279            }
1280    
1281            case JBC_if_acmpeq: {
1282              int offset = bcodes.getBranchOffset();
1283              int bTarget = biStart + offset;
1284              if (shouldPrint) asm.noteBranchBytecode(biStart, "if_acmpeq", offset, bTarget);
1285              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1286              emit_if_acmpeq(bTarget);
1287              break;
1288            }
1289    
1290            case JBC_if_acmpne: {
1291              int offset = bcodes.getBranchOffset();
1292              int bTarget = biStart + offset;
1293              if (shouldPrint) asm.noteBranchBytecode(biStart, "if_acmpne", offset, bTarget);
1294              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1295              emit_if_acmpne(bTarget);
1296              break;
1297            }
1298    
1299            case JBC_goto: {
1300              int offset = bcodes.getBranchOffset();
1301              int bTarget = biStart + offset; // bi has been bumped by 3 already
1302              if (shouldPrint) asm.noteBranchBytecode(biStart, "goto", offset, bTarget);
1303              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1304              emit_goto(bTarget);
1305              break;
1306            }
1307    
1308            case JBC_jsr: {
1309              int offset = bcodes.getBranchOffset();
1310              int bTarget = biStart + offset;
1311              if (shouldPrint) asm.noteBranchBytecode(biStart, "jsr", offset, bTarget);
1312              emit_jsr(bTarget);
1313              break;
1314            }
1315    
1316            case JBC_ret: {
1317              int index = bcodes.getLocalNumber();
1318              if (shouldPrint) asm.noteBytecode(biStart, "ret ", index);
1319              emit_ret(index);
1320              break;
1321            }
1322    
1323            case JBC_tableswitch: {
1324              bcodes.alignSwitch();
1325              int defaultval = bcodes.getDefaultSwitchOffset();
1326              int low = bcodes.getLowSwitchValue();
1327              int high = bcodes.getHighSwitchValue();
1328              if (shouldPrint) asm.noteTableswitchBytecode(biStart, low, high, defaultval);
1329              emit_tableswitch(defaultval, low, high);
1330              break;
1331            }
1332    
1333            case JBC_lookupswitch: {
1334              bcodes.alignSwitch();
1335              int defaultval = bcodes.getDefaultSwitchOffset();
1336              int npairs = bcodes.getSwitchLength();
1337              if (shouldPrint) asm.noteLookupswitchBytecode(biStart, npairs, defaultval);
1338              emit_lookupswitch(defaultval, npairs);
1339              break;
1340            }
1341    
1342            case JBC_ireturn: {
1343              if (shouldPrint) asm.noteBytecode(biStart, "ireturn");
1344              if (VM.UseEpilogueYieldPoints) emit_threadSwitchTest(RVMThread.EPILOGUE);
1345              emit_ireturn();
1346              break;
1347            }
1348    
1349            case JBC_lreturn: {
1350              if (shouldPrint) asm.noteBytecode(biStart, "lreturn");
1351              if (VM.UseEpilogueYieldPoints) emit_threadSwitchTest(RVMThread.EPILOGUE);
1352              emit_lreturn();
1353              break;
1354            }
1355    
1356            case JBC_freturn: {
1357              if (shouldPrint) asm.noteBytecode(biStart, "freturn");
1358              if (VM.UseEpilogueYieldPoints) emit_threadSwitchTest(RVMThread.EPILOGUE);
1359              emit_freturn();
1360              break;
1361            }
1362    
1363            case JBC_dreturn: {
1364              if (shouldPrint) asm.noteBytecode(biStart, "dreturn");
1365              if (VM.UseEpilogueYieldPoints) emit_threadSwitchTest(RVMThread.EPILOGUE);
1366              emit_dreturn();
1367              break;
1368            }
1369    
1370            case JBC_areturn: {
1371              if (shouldPrint) asm.noteBytecode(biStart, "areturn");
1372              if (VM.UseEpilogueYieldPoints) emit_threadSwitchTest(RVMThread.EPILOGUE);
1373              emit_areturn();
1374              break;
1375            }
1376    
1377            case JBC_return: {
1378              if (shouldPrint) asm.noteBytecode(biStart, "return");
1379              if (VM.UseEpilogueYieldPoints) emit_threadSwitchTest(RVMThread.EPILOGUE);
1380              emit_return();
1381              break;
1382            }
1383    
1384            case JBC_getstatic: {
1385              FieldReference fieldRef = bcodes.getFieldReference();
1386              if (shouldPrint) asm.noteBytecode(biStart, "getstatic", fieldRef);
1387              if (fieldRef.needsDynamicLink(method)) {
1388                // Forbidden from uninterruptible code as dynamic linking can cause
1389                // interruptions
1390                if (VM.VerifyUnint && !isInterruptible) forbiddenBytecode("unresolved getstatic ", fieldRef, bcodes.index());
1391                emit_unresolved_getstatic(fieldRef);
1392              } else {
1393                emit_resolved_getstatic(fieldRef);
1394              }
1395              break;
1396            }
1397    
1398            case JBC_putstatic: {
1399              FieldReference fieldRef = bcodes.getFieldReference();
1400              if (shouldPrint) asm.noteBytecode(biStart, "putstatic", fieldRef);
1401              if (fieldRef.needsDynamicLink(method)) {
1402                // Forbidden from uninterruptible code as dynamic linking can cause
1403                // interruptions
1404                if (VM.VerifyUnint && !isInterruptible) forbiddenBytecode("unresolved putstatic ", fieldRef, bcodes.index());
1405                emit_unresolved_putstatic(fieldRef);
1406              } else {
1407                emit_resolved_putstatic(fieldRef);
1408              }
1409              break;
1410            }
1411    
1412            case JBC_getfield: {
1413              FieldReference fieldRef = bcodes.getFieldReference();
1414              if (shouldPrint) asm.noteBytecode(biStart, "getfield", fieldRef);
1415              if (fieldRef.needsDynamicLink(method)) {
1416                // Forbidden from uninterruptible code as dynamic linking can cause
1417                // interruptions
1418                if (VM.VerifyUnint && !isInterruptible) forbiddenBytecode("unresolved getfield ", fieldRef, bcodes.index());
1419                emit_unresolved_getfield(fieldRef);
1420              } else {
1421                emit_resolved_getfield(fieldRef);
1422              }
1423              break;
1424            }
1425    
1426            case JBC_putfield: {
1427              FieldReference fieldRef = bcodes.getFieldReference();
1428              if (shouldPrint) asm.noteBytecode(biStart, "putfield", fieldRef);
1429              if (fieldRef.needsDynamicLink(method)) {
1430                // Forbidden from uninterruptible code as dynamic linking can cause
1431                // interruptions
1432                if (VM.VerifyUnint && !isInterruptible) forbiddenBytecode("unresolved putfield ", fieldRef, bcodes.index());
1433                emit_unresolved_putfield(fieldRef);
1434              } else {
1435                emit_resolved_putfield(fieldRef);
1436              }
1437              break;
1438            }
1439    
1440            case JBC_invokevirtual: {
1441              ForwardReference xx = null;
1442              if (biStart == this.pendingIdx) {
1443                ForwardReference x = emit_pending_goto(0);  // goto X
1444                this.pendingRef.resolve(asm);          // pendingIdx:     (target of pending goto in prologue)
1445                CompiledMethod cm = CompiledMethods.getCompiledMethod(this.pendingCMID);
1446                if (VM.VerifyAssertions) VM._assert(cm.isSpecialForOSR());
1447                emit_invoke_compiledmethod(cm);  //  invoke_cmid
1448                xx = emit_pending_goto(0);                     // goto XX
1449                x.resolve(asm);                       //  X:
1450              }
1451    
1452              MethodReference methodRef = bcodes.getMethodReference();
1453              if (shouldPrint) asm.noteBytecode(biStart, "invokevirtual", methodRef);
1454              if (methodRef.getType().isMagicType()) {
1455                if (emit_Magic(methodRef)) {
1456                  break;
1457                }
1458              }
1459    
1460              if (methodRef.isMiranda()) {
1461                /* Special case of abstract interface method should generate
1462                 * an invokeinterface, despite the compiler claiming it should
1463                 * be invokevirtual.
1464                 */
1465                if (shouldPrint) asm.noteBytecode(biStart, "invokeinterface", methodRef);
1466                // Forbidden from uninterruptible code as interface invocation
1467                // causes runtime checks that can be interrupted
1468                if (VM.VerifyUnint && !isInterruptible) forbiddenBytecode("invokeinterface ", methodRef, bcodes.index());
1469                emit_invokeinterface(methodRef);
1470              } else {
1471                if (methodRef.needsDynamicLink(method)) {
1472                  // Forbidden from uninterruptible code as dynamic linking can
1473                  // cause interruptions
1474                  if (VM.VerifyUnint && !isInterruptible) forbiddenBytecode("unresolved invokevirtual ", methodRef, bcodes.index());
1475                  emit_unresolved_invokevirtual(methodRef);
1476                } else {
1477                  if (VM.VerifyUnint && !isInterruptible) checkTarget(methodRef.peekResolvedMethod(), bcodes.index());
1478                  emit_resolved_invokevirtual(methodRef);
1479                }
1480              }
1481    
1482              if (xx != null) {
1483                xx.resolve(asm);                     // XX:
1484              }
1485              break;
1486            }
1487    
1488            case JBC_invokespecial: {
1489              ForwardReference xx = null;
1490              if (biStart == this.pendingIdx) {
1491                ForwardReference x = emit_pending_goto(0);  // goto X
1492                this.pendingRef.resolve(asm);          // pendingIdx:     (target of pending goto in prologue)
1493                CompiledMethod cm = CompiledMethods.getCompiledMethod(this.pendingCMID);
1494                if (VM.VerifyAssertions) VM._assert(cm.isSpecialForOSR());
1495                emit_invoke_compiledmethod(cm);  //  invoke_cmid
1496                xx = emit_pending_goto(0);                     // goto XX
1497                x.resolve(asm);                       //  X:
1498              }
1499              MethodReference methodRef = bcodes.getMethodReference();
1500              if (shouldPrint) asm.noteBytecode(biStart, "invokespecial", methodRef);
1501              RVMMethod target = methodRef.resolveInvokeSpecial();
1502              if (target != null) {
1503                if (VM.VerifyUnint && !isInterruptible) checkTarget(target, bcodes.index());
1504                emit_resolved_invokespecial(methodRef, target);
1505              } else {
1506                emit_unresolved_invokespecial(methodRef);
1507              }
1508    
1509              if (xx != null) {
1510                xx.resolve(asm);                     // XX:
1511              }
1512    
1513              break;
1514            }
1515    
1516            case JBC_invokestatic: {
1517              ForwardReference xx = null;
1518              if (biStart == this.pendingIdx) {
1519                ForwardReference x = emit_pending_goto(0);  // goto X
1520                this.pendingRef.resolve(asm);          // pendingIdx:     (target of pending goto in prologue)
1521                CompiledMethod cm = CompiledMethods.getCompiledMethod(this.pendingCMID);
1522                if (VM.VerifyAssertions) VM._assert(cm.isSpecialForOSR());
1523                emit_invoke_compiledmethod(cm);  //  invoke_cmid
1524                xx = emit_pending_goto(0);                     // goto XX
1525                x.resolve(asm);                       //  X:
1526              }
1527    
1528              MethodReference methodRef = bcodes.getMethodReference();
1529              if (shouldPrint) asm.noteBytecode(biStart, "invokestatic", methodRef);
1530              if (methodRef.isMagic()) {
1531                if (emit_Magic(methodRef)) {
1532                  break;
1533                }
1534              }
1535              if (methodRef.needsDynamicLink(method)) {
1536                // Forbidden from uninterruptible code as dynamic linking can
1537                // cause interruptions
1538                if (VM.VerifyUnint && !isInterruptible) forbiddenBytecode("unresolved invokestatic ", methodRef, bcodes.index());
1539                emit_unresolved_invokestatic(methodRef);
1540              } else {
1541                if (VM.VerifyUnint && !isInterruptible) checkTarget(methodRef.peekResolvedMethod(), bcodes.index());
1542                emit_resolved_invokestatic(methodRef);
1543              }
1544    
1545              if (xx != null) {
1546                xx.resolve(asm);                     // XX:
1547              }
1548    
1549              break;
1550            }
1551    
1552            case JBC_invokeinterface: {
1553              ForwardReference xx = null;
1554              if (biStart == this.pendingIdx) {
1555                ForwardReference x = emit_pending_goto(0);  // goto X
1556                this.pendingRef.resolve(asm);          // pendingIdx:     (target of pending goto in prologue)
1557                CompiledMethod cm = CompiledMethods.getCompiledMethod(this.pendingCMID);
1558                if (VM.VerifyAssertions) VM._assert(cm.isSpecialForOSR());
1559                emit_invoke_compiledmethod(cm);  //  invoke_cmid
1560                xx = emit_pending_goto(0);                     // goto XX
1561                x.resolve(asm);                       //  X:
1562              }
1563    
1564              MethodReference methodRef = bcodes.getMethodReference();
1565              bcodes.alignInvokeInterface();
1566              if (shouldPrint) asm.noteBytecode(biStart, "invokeinterface", methodRef);
1567              // Forbidden from uninterruptible code as interface invocation
1568              // causes runtime checks that can be interrupted
1569              if (VM.VerifyUnint && !isInterruptible) forbiddenBytecode("invokeinterface ", methodRef, bcodes.index());
1570              emit_invokeinterface(methodRef);
1571    
1572              if (xx != null) {
1573                xx.resolve(asm);                     // XX:
1574              }
1575    
1576              break;
1577            }
1578    
1579            case JBC_xxxunusedxxx: {
1580              if (shouldPrint) asm.noteBytecode(biStart, "unused");
1581              if (VM.VerifyAssertions) VM._assert(VM.NOT_REACHED);
1582              break;
1583            }
1584    
1585            case JBC_new: {
1586              TypeReference typeRef = bcodes.getTypeReference();
1587              if (shouldPrint) asm.noteBytecode(biStart, "new", typeRef);
1588              // Forbidden from uninterruptible code as new causes calls into MMTk
1589              // that are interruptible
1590              if (VM.VerifyUnint && isUninterruptible) forbiddenBytecode("new ", typeRef, bcodes.index());
1591              RVMType type = typeRef.peekType();
1592              if (type != null && (type.isInitialized() || type.isInBootImage())) {
1593                emit_resolved_new(type.asClass());
1594              } else {
1595                if (VM.VerifyUnint && isUnpreemptible) forbiddenBytecode("unresolved new ", typeRef, bcodes.index());
1596                emit_unresolved_new(typeRef);
1597              }
1598              break;
1599            }
1600    
1601            case JBC_newarray: {
1602              int atype = bcodes.getArrayElementType();
1603              RVMArray array = RVMArray.getPrimitiveArrayType(atype);
1604              if (VM.VerifyAssertions) VM._assert(array.isResolved());
1605              // Forbidden from uninterruptible code as new causes calls into MMTk
1606              // that are interruptible
1607              if (shouldPrint) asm.noteBytecode(biStart, "newarray", array.getTypeRef());
1608              if (VM.VerifyUnint && isUninterruptible) forbiddenBytecode("newarray ", array, bcodes.index());
1609              emit_resolved_newarray(array);
1610              break;
1611            }
1612    
1613            case JBC_anewarray: {
1614              TypeReference elementTypeRef = bcodes.getTypeReference();
1615              TypeReference arrayRef = elementTypeRef.getArrayTypeForElementType();
1616    
1617              if (shouldPrint) asm.noteBytecode(biStart, "anewarray new", arrayRef);
1618              // Forbidden from uninterruptible code as new causes calls into MMTk
1619              // that are interruptible
1620              if (VM.VerifyUnint && !isInterruptible) forbiddenBytecode("anewarray ", arrayRef, bcodes.index());
1621    
1622              if (VM.VerifyAssertions && elementTypeRef.isUnboxedType()) {
1623                VM._assert(VM.NOT_REACHED,
1624                           "During compilation of " +
1625                           method +
1626                           " found an anewarray of " +
1627                           elementTypeRef +
1628                           "\n" +
1629                           "You must use the 'create' function to create an array of this type");
1630              }
1631    
1632              RVMArray array = (RVMArray) arrayRef.peekType();
1633              if (RVMType.JavaLangObjectType.isInstantiated()) {
1634                // If we've already instantiated java.lang.Object, then we can
1635                // forcibly fully instantiate the array type as long as the element type is
1636                // either already initialized or is in the bootimage.
1637                // Note: The test against java.lang.Object is required only for the baseline compiler
1638                //       and is not present in the opt compiler version of anewarray (BC2IR) because of the way
1639                //       we handle recursive invocations of the compiler (can be caused by instantiate()).
1640                //       We need Object to be instantiated because we are going to mine it's TIB to get entries for array methods...
1641                if (array == null || !(array.isInitialized() || array.isInBootImage())) {
1642                  RVMType elementType = elementTypeRef.peekType();
1643                  if (elementType != null && (elementType.isInitialized() || elementType.isInBootImage())) {
1644                    if (array == null) {
1645                      array = (RVMArray)arrayRef.resolve();
1646                    }
1647                    array.resolve();
1648                    array.instantiate();
1649                  }
1650                }
1651              }
1652              if (array != null && (array.isInitialized() || array.isInBootImage())) {
1653                emit_resolved_newarray(array);
1654              } else {
1655                emit_unresolved_newarray(arrayRef);
1656              }
1657              break;
1658            }
1659    
1660            case JBC_arraylength: {
1661              if (shouldPrint) asm.noteBytecode(biStart, "arraylength");
1662              emit_arraylength();
1663              break;
1664            }
1665    
1666            case JBC_athrow: {
1667              if (shouldPrint) asm.noteBytecode(biStart, "athrow");
1668              if (VM.UseEpilogueYieldPoints) emit_threadSwitchTest(RVMThread.EPILOGUE);
1669              // Forbidden from uninterruptible code as athrow causes calls into runtime
1670              // that are interruptible
1671              if (VM.VerifyUnint && isUninterruptible) forbiddenBytecode("athrow", bcodes.index());
1672              emit_athrow();
1673              break;
1674            }
1675    
1676            case JBC_checkcast: {
1677              TypeReference typeRef = bcodes.getTypeReference();
1678              if (shouldPrint) asm.noteBytecode(biStart, "checkcast", typeRef);
1679              RVMType type = typeRef.peekType();
1680              if (type != null) {
1681                if (type.isClassType()) {
1682                  RVMClass cType = type.asClass();
1683                  if (cType.isFinal()) {
1684                    emit_checkcast_final(cType);
1685                    break;
1686                  } else if (cType.isResolved()) {
1687                    if (cType.isInterface()) {
1688                      emit_checkcast_resolvedInterface(cType);
1689                    } else {
1690                      emit_checkcast_resolvedClass(cType);
1691                    }
1692                    break;
1693                  } // else fall through to emit_checkcast
1694                } else if (type.isArrayType()) {
1695                  RVMType elemType = type.asArray().getElementType();
1696                  if (elemType.isPrimitiveType() || elemType.isUnboxedType() ||
1697                      (elemType.isClassType() && elemType.asClass().isFinal())) {
1698                    emit_checkcast_final(type);
1699                    break;
1700                  } // else fall through to emit_checkcast
1701                } else {
1702                  // checkcast to a primitive. Must be a word type.
1703                  if (VM.VerifyAssertions) VM._assert(type.getTypeRef().isUnboxedType());
1704                  break;
1705                }
1706              }
1707              // Forbidden from uninterruptible code as it may throw an exception
1708              // that executes via interruptible code
1709              if (VM.VerifyUnint && !isInterruptible) forbiddenBytecode("checkcast ", typeRef, bcodes.index());
1710              emit_checkcast(typeRef);
1711              break;
1712            }
1713    
1714            case JBC_instanceof: {
1715              TypeReference typeRef = bcodes.getTypeReference();
1716              if (shouldPrint) asm.noteBytecode(biStart, "instanceof", typeRef);
1717              RVMType type = typeRef.peekType();
1718              if (type != null) {
1719                if (type.isClassType()) {
1720                  RVMClass cType = type.asClass();
1721                  if (cType.isFinal()) {
1722                    emit_instanceof_final(type);
1723                    break;
1724                  } else if (cType.isResolved()) {
1725                    if (cType.isInterface()) {
1726                      emit_instanceof_resolvedInterface(cType);
1727                    } else {
1728                      emit_instanceof_resolvedClass(cType);
1729                    }
1730                    break;
1731                  }
1732                } else if (type.isArrayType()) {
1733                  RVMType elemType = type.asArray().getElementType();
1734                  if (elemType.isPrimitiveType() || elemType.isUnboxedType() ||
1735                      (elemType.isClassType() && elemType.asClass().isFinal())) {
1736                    emit_instanceof_final(type);
1737                    break;
1738                  }
1739                }
1740              }
1741              // Forbidden from uninterruptible code as calls interruptible runtime
1742              // for its implementation
1743              if (VM.VerifyUnint && !isInterruptible) forbiddenBytecode("instanceof ", typeRef, bcodes.index());
1744              emit_instanceof(typeRef);
1745              break;
1746            }
1747    
1748            case JBC_monitorenter: {
1749              if (shouldPrint) asm.noteBytecode(biStart, "monitorenter");
1750              // Forbidden from uninterruptible code as calls interruptible object model
1751              // for its implementation
1752              if (VM.VerifyUnint && isUninterruptible) forbiddenBytecode("monitorenter", bcodes.index());
1753              emit_monitorenter();
1754              break;
1755            }
1756    
1757            case JBC_monitorexit: {
1758              if (shouldPrint) asm.noteBytecode(biStart, "monitorexit");
1759              // Forbidden from uninterruptible code as calls interruptible object model
1760              // for its implementation
1761              if (VM.VerifyUnint && isUninterruptible) forbiddenBytecode("monitorexit", bcodes.index());
1762              emit_monitorexit();
1763              break;
1764            }
1765    
1766            case JBC_wide: {
1767              int widecode = bcodes.getWideOpcode();
1768              int index = bcodes.getWideLocalNumber();
1769              switch (widecode) {
1770                case JBC_iload: {
1771                  if (shouldPrint) asm.noteBytecode(biStart, "wide iload", index);
1772                  emit_iload(index);
1773                  break;
1774                }
1775                case JBC_lload: {
1776                  if (shouldPrint) asm.noteBytecode(biStart, "wide lload", index);
1777                  emit_lload(index);
1778                  break;
1779                }
1780                case JBC_fload: {
1781                  if (shouldPrint) asm.noteBytecode(biStart, "wide fload", index);
1782                  emit_fload(index);
1783                  break;
1784                }
1785                case JBC_dload: {
1786                  if (shouldPrint) asm.noteBytecode(biStart, "wide dload", index);
1787                  emit_dload(index);
1788                  break;
1789                }
1790                case JBC_aload: {
1791                  if (shouldPrint) asm.noteBytecode(biStart, "wide aload", index);
1792                  emit_aload(index);
1793                  break;
1794                }
1795                case JBC_istore: {
1796                  if (shouldPrint) asm.noteBytecode(biStart, "wide istore", index);
1797                  emit_istore(index);
1798                  break;
1799                }
1800                case JBC_lstore: {
1801                  if (shouldPrint) asm.noteBytecode(biStart, "wide lstore", index);
1802                  emit_lstore(index);
1803                  break;
1804                }
1805                case JBC_fstore: {
1806                  if (shouldPrint) asm.noteBytecode(biStart, "wide fstore", index);
1807                  emit_fstore(index);
1808                  break;
1809                }
1810                case JBC_dstore: {
1811                  if (shouldPrint) asm.noteBytecode(biStart, "wide dstore", index);
1812                  emit_dstore(index);
1813                  break;
1814                }
1815                case JBC_astore: {
1816                  if (shouldPrint) asm.noteBytecode(biStart, "wide astore", index);
1817                  emit_astore(index);
1818                  break;
1819                }
1820                case JBC_iinc: {
1821                  int val = bcodes.getWideIncrement();
1822                  if (shouldPrint) asm.noteBytecode(biStart, "wide inc", index, val);
1823                  emit_iinc(index, val);
1824                  break;
1825                }
1826                case JBC_ret: {
1827                  if (shouldPrint) asm.noteBytecode(biStart, "wide ret", index);
1828                  emit_ret(index);
1829                  break;
1830                }
1831                default:
1832                  if (VM.VerifyAssertions) VM._assert(VM.NOT_REACHED);
1833              }
1834              break;
1835            }
1836    
1837            case JBC_multianewarray: {
1838              TypeReference typeRef = bcodes.getTypeReference();
1839              int dimensions = bcodes.getArrayDimension();
1840              if (shouldPrint) asm.noteBytecode(biStart, "multianewarray", typeRef);
1841              // Forbidden from uninterruptible code as new causes calls into MMTk
1842              // that are interruptible
1843              if (VM.VerifyUnint && !isInterruptible) forbiddenBytecode("multianewarray", bcodes.index());
1844              emit_multianewarray(typeRef, dimensions);
1845              break;
1846            }
1847    
1848            case JBC_ifnull: {
1849              int offset = bcodes.getBranchOffset();
1850              int bTarget = biStart + offset;
1851              if (shouldPrint) asm.noteBranchBytecode(biStart, "ifnull", offset, bTarget);
1852              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1853              emit_ifnull(bTarget);
1854              break;
1855            }
1856    
1857            case JBC_ifnonnull: {
1858              int offset = bcodes.getBranchOffset();
1859              int bTarget = biStart + offset;
1860              if (shouldPrint) asm.noteBranchBytecode(biStart, "ifnonnull", offset, bTarget);
1861              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1862              emit_ifnonnull(bTarget);
1863              break;
1864            }
1865    
1866            case JBC_goto_w: {
1867              int offset = bcodes.getWideBranchOffset();
1868              int bTarget = biStart + offset;
1869              if (shouldPrint) asm.noteBranchBytecode(biStart, "goto_w", offset, bTarget);
1870              if (offset <= 0) emit_threadSwitchTest(RVMThread.BACKEDGE);
1871              emit_goto(bTarget);
1872              break;
1873            }
1874    
1875            case JBC_jsr_w: {
1876              int offset = bcodes.getWideBranchOffset();
1877              int bTarget = biStart + offset;
1878              if (shouldPrint) asm.noteBranchBytecode(biStart, "jsr_w", offset, bTarget);
1879              emit_jsr(bTarget);
1880              break;
1881            }
1882    
1883            /* CAUTION: cannot use JBC_impdep1, which is 0xfffffffe (signed),
1884             * this is not consistent with OPT compiler.
1885             */
1886            case JBC_impdep1: /* --- pseudo bytecode --- */ {
1887              if (VM.BuildForAdaptiveSystem) {
1888                int pseudo_opcode = bcodes.nextPseudoInstruction();
1889                // pseudo instruction
1890                switch (pseudo_opcode) {
1891                  case org.jikesrvm.osr.OSRConstants.PSEUDO_LoadIntConst: {
1892                    int value = bcodes.readIntConst();
1893    
1894                    if (shouldPrint) asm.noteBytecode(biStart, "pseudo_load_int", value);
1895    
1896                    Offset offset = Offset.fromIntSignExtend(Statics.findOrCreateIntSizeLiteral(value));
1897                    emit_ldc(offset, CP_INT);
1898    
1899                    break;
1900                  }
1901                  case org.jikesrvm.osr.OSRConstants.PSEUDO_LoadLongConst: {
1902                    long value = bcodes.readLongConst();  // fetch8BytesUnsigned();
1903    
1904                    if (shouldPrint) asm.noteBytecode(biStart, "pseudo_load_long", value);
1905    
1906                    Offset offset = Offset.fromIntSignExtend(Statics.findOrCreateLongSizeLiteral(value));
1907                    emit_ldc2(offset, CP_LONG);
1908    
1909                    break;
1910                  }
1911                  case org.jikesrvm.osr.OSRConstants.PSEUDO_LoadWordConst: {
1912                    if (VM.BuildFor32Addr) {
1913                      int value = bcodes.readIntConst();
1914    
1915                      if (shouldPrint) asm.noteBytecode(biStart, "pseudo_load_word " + Integer.toHexString(value));
1916    
1917                      Offset offset = Offset.fromIntSignExtend(Statics.findOrCreateIntSizeLiteral(value));
1918                      emit_ldc(offset, CP_INT);
1919                    } else {
1920                      long value = bcodes.readLongConst();
1921    
1922                      if (shouldPrint) asm.noteBytecode(biStart, "pseudo_load_word " + Long.toHexString(value));
1923    
1924                      Offset offset = Offset.fromIntSignExtend(Statics.findOrCreateLongSizeLiteral(value));
1925                      emit_ldc2(offset, CP_LONG);
1926                      emit_l2i(); //dirty hack
1927                    }
1928                    break;
1929                  }
1930                  case org.jikesrvm.osr.OSRConstants.PSEUDO_LoadFloatConst: {
1931                    int ibits = bcodes.readIntConst(); // fetch4BytesSigned();
1932    
1933                    if (shouldPrint) asm.noteBytecode(biStart, "pseudo_load_float", ibits);
1934    
1935                    Offset offset = Offset.fromIntSignExtend(Statics.findOrCreateIntSizeLiteral(ibits));
1936                    emit_ldc(offset, CP_FLOAT);
1937    
1938                    break;
1939                  }
1940                  case org.jikesrvm.osr.OSRConstants.PSEUDO_LoadDoubleConst: {
1941                    long lbits = bcodes.readLongConst(); // fetch8BytesUnsigned();
1942    
1943                    if (shouldPrint) asm.noteBytecode(biStart, "pseudo_load_double", lbits);
1944    
1945                    Offset offset = Offset.fromIntSignExtend(Statics.findOrCreateLongSizeLiteral(lbits));
1946                    emit_ldc2(offset, CP_DOUBLE);
1947    
1948                    break;
1949                  }
1950                  case org.jikesrvm.osr.OSRConstants.PSEUDO_LoadRetAddrConst: {
1951                    int bcIndex = bcodes.readIntConst(); // fetch4BytesSigned();
1952    
1953                    if (shouldPrint) asm.noteBytecode(biStart, "pseudo_load_retaddr", bcIndex);
1954                    // for bytecode to get future bytecode's address
1955                    // we register it and patch it later.
1956                    emit_loadretaddrconst(bcIndex);
1957    
1958                    break;
1959                  }
1960                  case org.jikesrvm.osr.OSRConstants.PSEUDO_InvokeStatic: {
1961                    int targetidx = bcodes.readIntConst(); // fetch4BytesSigned();
1962                    RVMMethod methodRef = InvokeStatic.targetMethod(targetidx);
1963                    if (shouldPrint) asm.noteBytecode(biStart, "pseudo_invokestatic", methodRef);
1964                    emit_resolved_invokestatic(methodRef.getMemberRef().asMethodReference());
1965                    break;
1966                  }
1967                  /*
1968                    case org.jikesrvm.osr.OSRConstants.PSEUDO_CheckCast: {
1969    
1970                    if (shouldPrint) asm.noteBytecode(biStart, "pseudo_checkcast");
1971    
1972                    // fetch 4 byte type id
1973                    int tid = bcodes.readIntConst(); // fetch4BytesSigned();
1974                    // do nothing now
1975                    break;
1976                    }
1977                  */
1978                  case org.jikesrvm.osr.OSRConstants.PSEUDO_InvokeCompiledMethod: {
1979                    int cmid = bcodes.readIntConst(); // fetch4BytesSigned();    // callee's cmid
1980                    int origIdx =
1981                        bcodes.readIntConst(); // fetch4BytesSigned(); // orginal bytecode index of this call (for build gc map)
1982    
1983                    if (shouldPrint) asm.noteBytecode(biStart, "pseudo_invoke_cmid", cmid);
1984    
1985                    this.pendingCMID = cmid;
1986                    this.pendingIdx = origIdx + this.method.getOsrPrologueLength();
1987                    this.pendingRef = emit_pending_goto(this.pendingIdx);
1988                    /*
1989                      CompiledMethod cm = CompiledMethods.getCompiledMethod(cmid);
1990                      if (VM.VerifyAssertions) VM._assert(cm.isSpecialForOSR());
1991                      emit_invoke_compiledmethod(cm);
1992                    */
1993                    break;
1994                  }
1995                  case org.jikesrvm.osr.OSRConstants.PSEUDO_ParamInitEnd: {
1996                    if (shouldPrint) asm.noteBytecode(biStart, "pseudo_paraminitend");
1997                    // now we can inserted stack overflow check,
1998                    emit_deferred_prologue();
1999                    break;
2000                  }
2001                  default:
2002                    if (VM.TraceOnStackReplacement) {
2003                      VM.sysWrite("Unexpected PSEUDO code " + VM.intAsHexString(pseudo_opcode) + "\n");
2004                    }
2005                    if (VM.VerifyAssertions) VM._assert(VM.NOT_REACHED);
2006                    break;
2007                }
2008              } else {
2009                if (VM.VerifyAssertions) VM._assert(VM.NOT_REACHED);
2010              }
2011              break;
2012            }
2013    
2014            default:
2015              VM.sysWrite("BaselineCompilerImpl: unexpected bytecode: " + Services.getHexString(code, false) + "\n");
2016              if (VM.VerifyAssertions) VM._assert(VM.NOT_REACHED);
2017          }
2018          ending_bytecode();
2019        }
2020        bytecodeMap[bcodes.length()] = asm.getMachineCodeIndex();
2021        return asm.finalizeMachineCode(bytecodeMap);
2022      }
2023    
2024      /* for invoke compiled method, we have to fool GC map,
2025      * InvokeCompiledMethod has two parameters compiledMethodID
2026      * and originalBytecodeIndex of that call site
2027      *
2028      * we make the InvokeCompiledMethod pending until generating code
2029      * for the original call.
2030      * it looks like following instruction sequence:
2031      *    invokeCompiledMethod cmid, bc
2032      *
2033      *  ==>  forward (x)
2034      *
2035      *          bc:  forward(x')
2036      *             resolve (x):
2037      *               invoke cmid
2038      *               forward(x")
2039      *             resolve (x'):
2040      *               invoke xxxx
2041      *             resolve (x");
2042      * in this way, the instruction for invokeCompiledMethod is right before
2043      * the original call, and it uses the original call's GC map
2044      */
2045      private int pendingCMID = -1;
2046      private int pendingIdx = -1;
2047      private ForwardReference pendingRef = null;
2048    
2049      /**
2050       * Print a warning message whan we compile a bytecode that is forbidden in
2051       * Uninterruptible code.
2052       *
2053       * @param msg description of bytecode that is violating the invariant
2054       * @param obj object that provides further information
2055       * @param bci the index of the current bytecode
2056       */
2057      @NoInline
2058      protected final void forbiddenBytecode(String msg, Object obj, int bci) {
2059        forbiddenBytecode(msg + obj, bci);
2060      }
2061    
2062      /**
2063       * Print a warning message whan we compile a bytecode that is forbidden in
2064       * Uninterruptible code.
2065       *
2066       * @param msg description of bytecode that is violating the invariant
2067       * @param bci the index of the current bytecode
2068       */
2069      @NoInline
2070      protected final void forbiddenBytecode(String msg, int bci) {
2071        if (!VM.ParanoidVerifyUnint) {
2072          // Respect programmer overrides of uninterruptibility checking
2073          if (method.hasLogicallyUninterruptibleAnnotation()) return;
2074          if (method.hasUninterruptibleNoWarnAnnotation()) return;
2075          if (method.hasUnpreemptibleNoWarnAnnotation()) return;
2076        }
2077        // NB generate as a single string to avoid threads splitting output
2078        VM.sysWriteln("WARNING: UNINTERRUPTIBLE VIOLATION\n   "+ method + " at line " + method.getLineNumberForBCIndex(bci) +
2079        "\n   Uninterruptible methods may not contain the following forbidden bytecode\n   " + msg);
2080      }
2081    
2082      /**
2083       * Ensure that the callee method is safe to invoke from uninterruptible code
2084       *
2085       * @param target the target methodRef
2086       * @param bci the index of the current bytecode
2087       */
2088      protected final void checkTarget(RVMMethod target, int bci) {
2089        if (!VM.ParanoidVerifyUnint) {
2090          // Respect programmer overrides of uninterruptibility checking
2091          if (method.hasLogicallyUninterruptibleAnnotation()) return;
2092          if (method.hasUninterruptibleNoWarnAnnotation()) return;
2093          if (method.hasUnpreemptibleNoWarnAnnotation()) return;
2094        }
2095        if (isUninterruptible && !target.isUninterruptible()) {
2096          // NB generate as a single string to avoid threads splitting output
2097          VM.sysWrite("WARNING: UNINTERRUPTIBLE VIOLATION\n   "+ method + " at line " + method.getLineNumberForBCIndex(bci) +
2098          "\n   Uninterruptible method calls non-uninterruptible method " + target + "\n");
2099        }
2100        if (isUnpreemptible && target.isInterruptible()) {
2101          // NB generate as a single string to avoid threads splitting output
2102          VM.sysWrite("WARNING: UNPREEMPTIBLE VIOLATION\n   "+ method + " at line " + method.getLineNumberForBCIndex(bci) +
2103              "\n   Unpreemptible method calls interruptible method " + target + "\n");
2104        }
2105      }
2106    
2107      /*
2108       * The target-specific BaselineCompilerImpl class must implement the
2109       * following (lengthy) list of abstract methods.  Porting this
2110       * compiler to a new platform mainly entails implementing all of
2111       * these methods.
2112       */
2113    
2114      /*
2115      * Misc routines not directly tied to a particular bytecode
2116      */
2117    
2118      /**
2119       * Notify BaselineCompilerImpl that we are starting code gen for the bytecode biStart
2120       */
2121      protected abstract void starting_bytecode();
2122    
2123      /**
2124       * Notify BaselineCompilerImpl that we are ending code gen for the bytecode biStart
2125       */
2126      protected void ending_bytecode() {}
2127    
2128      /**
2129       * Emit the prologue for the method
2130       */
2131      protected abstract void emit_prologue();
2132    
2133      /**
2134       * Emit the code for a threadswitch tests (aka a yieldpoint).
2135       * @param whereFrom is this thread switch from a PROLOGUE, BACKEDGE, or EPILOGUE?
2136       */
2137      protected abstract void emit_threadSwitchTest(int whereFrom);
2138    
2139      protected abstract void emit_deferred_prologue();
2140    
2141      /**
2142       * Emit the code to implement the spcified magic.
2143       * @param magicMethod desired magic
2144       */
2145      protected abstract boolean emit_Magic(MethodReference magicMethod);
2146    
2147      /*
2148      * Loading constants
2149      */
2150    
2151      /**
2152       * Emit code to load the null constant.
2153       */
2154      protected abstract void emit_aconst_null();
2155    
2156      /**
2157       * Emit code to load an int constant.
2158       * @param val the int constant to load
2159       */
2160      protected abstract void emit_iconst(int val);
2161    
2162      /**
2163       * Emit code to load a long constant
2164       * @param val the lower 32 bits of long constant (upper32 are 0).
2165       */
2166      protected abstract void emit_lconst(int val);
2167    
2168      /**
2169       * Emit code to load 0.0f
2170       */
2171      protected abstract void emit_fconst_0();
2172    
2173      /**
2174       * Emit code to load 1.0f
2175       */
2176      protected abstract void emit_fconst_1();
2177    
2178      /**
2179       * Emit code to load 2.0f
2180       */
2181      protected abstract void emit_fconst_2();
2182    
2183      /**
2184       * Emit code to load 0.0d
2185       */
2186      protected abstract void emit_dconst_0();
2187    
2188      /**
2189       * Emit code to load 1.0d
2190       */
2191      protected abstract void emit_dconst_1();
2192    
2193      /**
2194       * Emit code to load a 32 bit constant
2195       * @param offset JTOC offset of the constant
2196       * @param type the type of the constant
2197       */
2198      protected abstract void emit_ldc(Offset offset, byte type);
2199    
2200      /**
2201       * Emit code to load a 64 bit constant
2202       * @param offset JTOC offset of the constant
2203       * @param type the type of the constant
2204       */
2205      protected abstract void emit_ldc2(Offset offset, byte type);
2206    
2207      /*
2208      * loading local variables
2209      */
2210    
2211      /**
2212       * Emit code to load an int local variable
2213       * @param index the local index to load
2214       */
2215      protected abstract void emit_iload(int index);
2216    
2217      /**
2218       * Emit code to load a long local variable
2219       * @param index the local index to load
2220       */
2221      protected abstract void emit_lload(int index);
2222    
2223      /**
2224       * Emit code to local a float local variable
2225       * @param index the local index to load
2226       */
2227      protected abstract void emit_fload(int index);
2228    
2229      /**
2230       * Emit code to load a double local variable
2231       * @param index the local index to load
2232       */
2233      protected abstract void emit_dload(int index);
2234    
2235      /**
2236       * Emit code to load a reference local variable
2237       * @param index the local index to load
2238       */
2239      protected abstract void emit_aload(int index);
2240    
2241      /*
2242      * storing local variables
2243      */
2244    
2245      /**
2246       * Emit code to store an int to a local variable
2247       * @param index the local index to load
2248       */
2249      protected abstract void emit_istore(int index);
2250    
2251      /**
2252       * Emit code to store a long to a local variable
2253       * @param index the local index to load
2254       */
2255      protected abstract void emit_lstore(int index);
2256    
2257      /**
2258       * Emit code to store a float to a local variable
2259       * @param index the local index to load
2260       */
2261      protected abstract void emit_fstore(int index);
2262    
2263      /**
2264       * Emit code to store an double  to a local variable
2265       * @param index the local index to load
2266       */
2267      protected abstract void emit_dstore(int index);
2268    
2269      /**
2270       * Emit code to store a reference to a local variable
2271       * @param index the local index to load
2272       */
2273      protected abstract void emit_astore(int index);
2274    
2275      /*
2276      * array loads
2277      */
2278    
2279      /**
2280       * Emit code to load from an int array
2281       */
2282      protected abstract void emit_iaload();
2283    
2284      /**
2285       * Emit code to load from a long array
2286       */
2287      protected abstract void emit_laload();
2288    
2289      /**
2290       * Emit code to load from a float array
2291       */
2292      protected abstract void emit_faload();
2293    
2294      /**
2295       * Emit code to load from a double array
2296       */
2297      protected abstract void emit_daload();
2298    
2299      /**
2300       * Emit code to load from a reference array
2301       */
2302      protected abstract void emit_aaload();
2303    
2304      /**
2305       * Emit code to load from a byte/boolean array
2306       */
2307      protected abstract void emit_baload();
2308    
2309      /**
2310       * Emit code to load from a char array
2311       */
2312      protected abstract void emit_caload();
2313    
2314      /**
2315       * Emit code to load from a short array
2316       */
2317      protected abstract void emit_saload();
2318    
2319      /*
2320      * array stores
2321      */
2322    
2323      /**
2324       * Emit code to store to an int array
2325       */
2326      protected abstract void emit_iastore();
2327    
2328      /**
2329       * Emit code to store to a long array
2330       */
2331      protected abstract void emit_lastore();
2332    
2333      /**
2334       * Emit code to store to a float array
2335       */
2336      protected abstract void emit_fastore();
2337    
2338      /**
2339       * Emit code to store to a double array
2340       */
2341      protected abstract void emit_dastore();
2342    
2343      /**
2344       * Emit code to store to a reference array
2345       */
2346      protected abstract void emit_aastore();
2347    
2348      /**
2349       * Emit code to store to a byte/boolean array
2350       */
2351      protected abstract void emit_bastore();
2352    
2353      /**
2354       * Emit code to store to a char array
2355       */
2356      protected abstract void emit_castore();
2357    
2358      /**
2359       * Emit code to store to a short array
2360       */
2361      protected abstract void emit_sastore();
2362    
2363      /*
2364      * expression stack manipulation
2365      */
2366    
2367      /**
2368       * Emit code to implement the pop bytecode
2369       */
2370      protected abstract void emit_pop();
2371    
2372      /**
2373       * Emit code to implement the pop2 bytecode
2374       */
2375      protected abstract void emit_pop2();
2376    
2377      /**
2378       * Emit code to implement the dup bytecode
2379       */
2380      protected abstract void emit_dup();
2381    
2382      /**
2383       * Emit code to implement the dup_x1 bytecode
2384       */
2385      protected abstract void emit_dup_x1();
2386    
2387      /**
2388       * Emit code to implement the dup_x2 bytecode
2389       */
2390      protected abstract void emit_dup_x2();
2391    
2392      /**
2393       * Emit code to implement the dup2 bytecode
2394       */
2395      protected abstract void emit_dup2();
2396    
2397      /**
2398       * Emit code to implement the dup2_x1 bytecode
2399       */
2400      protected abstract void emit_dup2_x1();
2401    
2402      /**
2403       * Emit code to implement the dup2_x2 bytecode
2404       */
2405      protected abstract void emit_dup2_x2();
2406    
2407      /**
2408       * Emit code to implement the swap bytecode
2409       */
2410      protected abstract void emit_swap();
2411    
2412      /*
2413      * int ALU
2414      */
2415    
2416      /**
2417       * Emit code to implement the iadd bytecode
2418       */
2419      protected abstract void emit_iadd();
2420    
2421      /**
2422       * Emit code to implement the isub bytecode
2423       */
2424      protected abstract void emit_isub();
2425    
2426      /**
2427       * Emit code to implement the imul bytecode
2428       */
2429      protected abstract void emit_imul();
2430    
2431      /**
2432       * Emit code to implement the idiv bytecode
2433       */
2434      protected abstract void emit_idiv();
2435    
2436      /**
2437       * Emit code to implement the irem bytecode
2438       */
2439      protected abstract void emit_irem();
2440    
2441      /**
2442       * Emit code to implement the ineg bytecode
2443       */
2444      protected abstract void emit_ineg();
2445    
2446      /**
2447       * Emit code to implement the ishl bytecode
2448       */
2449      protected abstract void emit_ishl();
2450    
2451      /**
2452       * Emit code to implement the ishr bytecode
2453       */
2454      protected abstract void emit_ishr();
2455    
2456      /**
2457       * Emit code to implement the iushr bytecode
2458       */
2459      protected abstract void emit_iushr();
2460    
2461      /**
2462       * Emit code to implement the iand bytecode
2463       */
2464      protected abstract void emit_iand();
2465    
2466      /**
2467       * Emit code to implement the ior bytecode
2468       */
2469      protected abstract void emit_ior();
2470    
2471      /**
2472       * Emit code to implement the ixor bytecode
2473       */
2474      protected abstract void emit_ixor();
2475    
2476      /**
2477       * Emit code to implement the iinc bytecode
2478       * @param index index of local
2479       * @param val value to increment it by
2480       */
2481      protected abstract void emit_iinc(int index, int val);
2482    
2483      /*
2484      * long ALU
2485      */
2486    
2487      /**
2488       * Emit code to implement the ladd bytecode
2489       */
2490      protected abstract void emit_ladd();
2491    
2492      /**
2493       * Emit code to implement the lsub bytecode
2494       */
2495      protected abstract void emit_lsub();
2496    
2497      /**
2498       * Emit code to implement the lmul bytecode
2499       */
2500      protected abstract void emit_lmul();
2501    
2502      /**
2503       * Emit code to implement the ldiv bytecode
2504       */
2505      protected abstract void emit_ldiv();
2506    
2507      /**
2508       * Emit code to implement the lrem bytecode
2509       */
2510      protected abstract void emit_lrem();
2511    
2512      /**
2513       * Emit code to implement the lneg bytecode
2514       */
2515      protected abstract void emit_lneg();
2516    
2517      /**
2518       * Emit code to implement the lshsl bytecode
2519       */
2520      protected abstract void emit_lshl();
2521    
2522      /**
2523       * Emit code to implement the lshr bytecode
2524       */
2525      protected abstract void emit_lshr();
2526    
2527      /**
2528       * Emit code to implement the lushr bytecode
2529       */
2530      protected abstract void emit_lushr();
2531    
2532      /**
2533       * Emit code to implement the land bytecode
2534       */
2535      protected abstract void emit_land();
2536    
2537      /**
2538       * Emit code to implement the lor bytecode
2539       */
2540      protected abstract void emit_lor();
2541    
2542      /**
2543       * Emit code to implement the lxor bytecode
2544       */
2545      protected abstract void emit_lxor();
2546    
2547      /*
2548      * float ALU
2549      */
2550    
2551      /**
2552       * Emit code to implement the fadd bytecode
2553       */
2554      protected abstract void emit_fadd();
2555    
2556      /**
2557       * Emit code to implement the fsub bytecode
2558       */
2559      protected abstract void emit_fsub();
2560    
2561      /**
2562       * Emit code to implement the fmul bytecode
2563       */
2564      protected abstract void emit_fmul();
2565    
2566      /**
2567       * Emit code to implement the fdiv bytecode
2568       */
2569      protected abstract void emit_fdiv();
2570    
2571      /**
2572       * Emit code to implement the frem bytecode
2573       */
2574      protected abstract void emit_frem();
2575    
2576      /**
2577       * Emit code to implement the fneg bytecode
2578       */
2579      protected abstract void emit_fneg();
2580    
2581      /*
2582      * double ALU
2583      */
2584    
2585      /**
2586       * Emit code to implement the dadd bytecode
2587       */
2588      protected abstract void emit_dadd();
2589    
2590      /**
2591       * Emit code to implement the dsub bytecode
2592       */
2593      protected abstract void emit_dsub();
2594    
2595      /**
2596       * Emit code to implement the dmul bytecode
2597       */
2598      protected abstract void emit_dmul();
2599    
2600      /**
2601       * Emit code to implement the ddiv bytecode
2602       */
2603      protected abstract void emit_ddiv();
2604    
2605      /**
2606       * Emit code to implement the drem bytecode
2607       */
2608      protected abstract void emit_drem();
2609    
2610      /**
2611       * Emit code to implement the dneg bytecode
2612       */
2613      protected abstract void emit_dneg();
2614    
2615      /*
2616      * conversion ops
2617      */
2618    
2619      /**
2620       * Emit code to implement the i2l bytecode
2621       */
2622      protected abstract void emit_i2l();
2623    
2624      /**
2625       * Emit code to implement the i2f bytecode
2626       */
2627      protected abstract void emit_i2f();
2628    
2629      /**
2630       * Emit code to implement the i2d bytecode
2631       */
2632      protected abstract void emit_i2d();
2633    
2634      /**
2635       * Emit code to implement the l2i bytecode
2636       */
2637      protected abstract void emit_l2i();
2638    
2639      /**
2640       * Emit code to implement the l2f bytecode
2641       */
2642      protected abstract void emit_l2f();
2643    
2644      /**
2645       * Emit code to implement the l2d bytecode
2646       */
2647      protected abstract void emit_l2d();
2648    
2649      /**
2650       * Emit code to implement the f2i bytecode
2651       */
2652      protected abstract void emit_f2i();
2653    
2654      /**
2655       * Emit code to implement the f2l bytecode
2656       */
2657      protected abstract void emit_f2l();
2658    
2659      /**
2660       * Emit code to implement the f2d bytecode
2661       */
2662      protected abstract void emit_f2d();
2663    
2664      /**
2665       * Emit code to implement the d2i bytecode
2666       */
2667      protected abstract void emit_d2i();
2668    
2669      /**
2670       * Emit code to implement the d2l bytecode
2671       */
2672      protected abstract void emit_d2l();
2673    
2674      /**
2675       * Emit code to implement the d2f bytecode
2676       */
2677      protected abstract void emit_d2f();
2678    
2679      /**
2680       * Emit code to implement the i2b bytecode
2681       */
2682      protected abstract void emit_i2b();
2683    
2684      /**
2685       * Emit code to implement the i2c bytecode
2686       */
2687      protected abstract void emit_i2c();
2688    
2689      /**
2690       * Emit code to implement the i2s bytecode
2691       */
2692      protected abstract void emit_i2s();
2693    
2694      /*
2695      * comparision ops
2696      */
2697    
2698      /**
2699       * Emit code to implement the lcmp bytecode
2700       */
2701      protected abstract void emit_lcmp();
2702    
2703      /**
2704       * Emit code to implement the fcmpl bytecode
2705       */
2706      protected abstract void emit_fcmpl();
2707    
2708      /**
2709       * Emit code to implement the fcmpg bytecode
2710       */
2711      protected abstract void emit_fcmpg();
2712    
2713      /**
2714       * Emit code to implement the dcmpl bytecode
2715       */
2716      protected abstract void emit_dcmpl();
2717    
2718      /**
2719       * Emit code to implement the dcmpg bytecode
2720       */
2721      protected abstract void emit_dcmpg();
2722    
2723      /*
2724      * branching
2725      */
2726    
2727      /**
2728       * Emit code to implement the ifeg bytecode
2729       * @param bTarget target bytecode of the branch
2730       */
2731      protected abstract void emit_ifeq(int bTarget);
2732    
2733      /**
2734       * Emit code to implement the ifne bytecode
2735       * @param bTarget target bytecode of the branch
2736       */
2737      protected abstract void emit_ifne(int bTarget);
2738    
2739      /**
2740       * Emit code to implement the iflt bytecode
2741       * @param bTarget target bytecode of the branch
2742       */
2743      protected abstract void emit_iflt(int bTarget);
2744    
2745      /**
2746       * Emit code to implement the ifge bytecode
2747       * @param bTarget target bytecode of the branch
2748       */
2749      protected abstract void emit_ifge(int bTarget);
2750    
2751      /**
2752       * Emit code to implement the ifgt bytecode
2753       * @param bTarget target bytecode of the branch
2754       */
2755      protected abstract void emit_ifgt(int bTarget);
2756    
2757      /**
2758       * Emit code to implement the ifle bytecode
2759       * @param bTarget target bytecode of the branch
2760       */
2761      protected abstract void emit_ifle(int bTarget);
2762    
2763      /**
2764       * Emit code to implement the if_icmpeq bytecode
2765       * @param bTarget target bytecode of the branch
2766       */
2767      protected abstract void emit_if_icmpeq(int bTarget);
2768    
2769      /**
2770       * Emit code to implement the if_icmpne bytecode
2771       * @param bTarget target bytecode of the branch
2772       */
2773      protected abstract void emit_if_icmpne(int bTarget);
2774    
2775      /**
2776       * Emit code to implement the if_icmplt bytecode
2777       * @param bTarget target bytecode of the branch
2778       */
2779      protected abstract void emit_if_icmplt(int bTarget);
2780    
2781      /**
2782       * Emit code to implement the if_icmpge bytecode
2783       * @param bTarget target bytecode of the branch
2784       */
2785      protected abstract void emit_if_icmpge(int bTarget);
2786    
2787      /**
2788       * Emit code to implement the if_icmpgt bytecode
2789       * @param bTarget target bytecode of the branch
2790       */
2791      protected abstract void emit_if_icmpgt(int bTarget);
2792    
2793      /**
2794       * Emit code to implement the if_icmple bytecode
2795       * @param bTarget target bytecode of the branch
2796       */
2797      protected abstract void emit_if_icmple(int bTarget);
2798    
2799      /**
2800       * Emit code to implement the if_acmpeq bytecode
2801       * @param bTarget target bytecode of the branch
2802       */
2803      protected abstract void emit_if_acmpeq(int bTarget);
2804    
2805      /**
2806       * Emit code to implement the if_acmpne bytecode
2807       * @param bTarget target bytecode of the branch
2808       */
2809      protected abstract void emit_if_acmpne(int bTarget);
2810    
2811      /**
2812       * Emit code to implement the ifnull bytecode
2813       * @param bTarget target bytecode of the branch
2814       */
2815      protected abstract void emit_ifnull(int bTarget);
2816    
2817      /**
2818       * Emit code to implement the ifnonnull bytecode
2819       * @param bTarget target bytecode of the branch
2820       */
2821      protected abstract void emit_ifnonnull(int bTarget);
2822    
2823      /**
2824       * Emit code to implement the goto and gotow bytecodes
2825       * @param bTarget target bytecode of the branch
2826       */
2827      protected abstract void emit_goto(int bTarget);
2828    
2829      /**
2830       * Emit code to implement the jsr and jsrw bytecode
2831       * @param bTarget target bytecode of the jsr
2832       */
2833      protected abstract void emit_jsr(int bTarget);
2834    
2835      /**
2836       * Emit code to implement the ret bytecode
2837       * @param index local variable containing the return address
2838       */
2839      protected abstract void emit_ret(int index);
2840    
2841      /**
2842       * Emit code to implement the tableswitch bytecode
2843       * @param defaultval bcIndex of the default target
2844       * @param low low value of switch
2845       * @param high high value of switch
2846       */
2847      protected abstract void emit_tableswitch(int defaultval, int low, int high);
2848    
2849      /**
2850       * Emit code to implement the lookupswitch bytecode
2851       * @param defaultval bcIndex of the default target
2852       * @param npairs number of pairs in the lookup switch
2853       */
2854      protected abstract void emit_lookupswitch(int defaultval, int npairs);
2855    
2856      /*
2857      * returns (from function; NOT ret)
2858      */
2859    
2860      /**
2861       * Emit code to implement the ireturn bytecode
2862       */
2863      protected abstract void emit_ireturn();
2864    
2865      /**
2866       * Emit code to implement the lreturn bytecode
2867       */
2868      protected abstract void emit_lreturn();
2869    
2870      /**
2871       * Emit code to implement the freturn bytecode
2872       */
2873      protected abstract void emit_freturn();
2874    
2875      /**
2876       * Emit code to implement the dreturn bytecode
2877       */
2878      protected abstract void emit_dreturn();
2879    
2880      /**
2881       * Emit code to implement the areturn bytecode
2882       */
2883      protected abstract void emit_areturn();
2884    
2885      /**
2886       * Emit code to implement the return bytecode
2887       */
2888      protected abstract void emit_return();
2889    
2890      /*
2891      * field access
2892      */
2893    
2894      /**
2895       * Emit code to implement a dynamically linked getstatic
2896       * @param fieldRef the referenced field
2897       */
2898      protected abstract void emit_unresolved_getstatic(FieldReference fieldRef);
2899    
2900      /**
2901       * Emit code to implement a getstatic
2902       * @param fieldRef the referenced field
2903       */
2904      protected abstract void emit_resolved_getstatic(FieldReference fieldRef);
2905    
2906      /**
2907       * Emit code to implement a dynamically linked putstatic
2908       * @param fieldRef the referenced field
2909       */
2910      protected abstract void emit_unresolved_putstatic(FieldReference fieldRef);
2911    
2912      /**
2913       * Emit code to implement a putstatic
2914       * @param fieldRef the referenced field
2915       */
2916      protected abstract void emit_resolved_putstatic(FieldReference fieldRef);
2917    
2918      /**
2919       * Emit code to implement a dynamically linked getfield
2920       * @param fieldRef the referenced field
2921       */
2922      protected abstract void emit_unresolved_getfield(FieldReference fieldRef);
2923    
2924      /**
2925       * Emit code to implement a getfield
2926       * @param fieldRef the referenced field
2927       */
2928      protected abstract void emit_resolved_getfield(FieldReference fieldRef);
2929    
2930      /**
2931       * Emit code to implement a dynamically linked putfield
2932       * @param fieldRef the referenced field
2933       */
2934      protected abstract void emit_unresolved_putfield(FieldReference fieldRef);
2935    
2936      /**
2937       * Emit code to implement a putfield
2938       * @param fieldRef the referenced field
2939       */
2940      protected abstract void emit_resolved_putfield(FieldReference fieldRef);
2941    
2942      /*
2943      * method invocation
2944      */
2945    
2946      /**
2947       * Emit code to implement a dynamically linked invokevirtual
2948       * @param methodRef the referenced method
2949       */
2950      protected abstract void emit_unresolved_invokevirtual(MethodReference methodRef);
2951    
2952      /**
2953       * Emit code to implement invokevirtual
2954       * @param methodRef the referenced method
2955       */
2956      protected abstract void emit_resolved_invokevirtual(MethodReference methodRef);
2957    
2958      /**
2959       * Emit code to implement a dynamically linked invokespecial
2960       * @param methodRef the referenced method
2961       * @param target the method to invoke
2962       */
2963      protected abstract void emit_resolved_invokespecial(MethodReference methodRef, RVMMethod target);
2964    
2965      /**
2966       * Emit code to implement invokespecial
2967       * @param methodRef the referenced method
2968       */
2969      protected abstract void emit_unresolved_invokespecial(MethodReference methodRef);
2970    
2971      /**
2972       * Emit code to implement a dynamically linked invokestatic
2973       * @param methodRef the referenced method
2974       */
2975      protected abstract void emit_unresolved_invokestatic(MethodReference methodRef);
2976    
2977      /**
2978       * Emit code to implement invokestatic
2979       * @param methodRef the referenced method
2980       */
2981      protected abstract void emit_resolved_invokestatic(MethodReference methodRef);
2982    
2983      // OSR only
2984      protected abstract void emit_invoke_compiledmethod(CompiledMethod cm);
2985    
2986      // OSR only
2987      protected abstract ForwardReference emit_pending_goto(int origidx);
2988    
2989      /**
2990       * Emit code to implement the invokeinterface bytecode
2991       * @param methodRef the referenced method
2992       */
2993      protected abstract void emit_invokeinterface(MethodReference methodRef);
2994    
2995      /*
2996      * other object model functions
2997      */
2998    
2999      /**
3000       * Emit code to allocate a scalar object
3001       *
3002       * @param typeRef  The {@link RVMClass} to instantiate
3003       */
3004      protected abstract void emit_resolved_new(RVMClass typeRef);
3005    
3006      /**
3007       * Emit code to dynamically link and allocate a scalar object
3008       * @param typeRef   {@link TypeReference} to dynamically link & instantiate
3009       */
3010      protected abstract void emit_unresolved_new(TypeReference typeRef);
3011    
3012      /**
3013       * Emit code to allocate an array
3014       * @param array the {@link RVMArray} to instantiate
3015       */
3016      protected abstract void emit_resolved_newarray(RVMArray array);
3017    
3018      /**
3019       * Emit code to dynamically link the element class and allocate an array
3020       * @param typeRef typeReference to dynamically link & instantiate
3021       */
3022      protected abstract void emit_unresolved_newarray(TypeReference typeRef);
3023    
3024      /**
3025       * Emit code to allocate a multi-dimensional array
3026       * @param typeRef typeReference to dynamically link & instantiate
3027       * @param dimensions the number of dimensions
3028       */
3029      protected abstract void emit_multianewarray(TypeReference typeRef, int dimensions);
3030    
3031      /**
3032       * Emit code to implement the arraylength bytecode
3033       */
3034      protected abstract void emit_arraylength();
3035    
3036      /**
3037       * Emit code to implement the athrow bytecode
3038       */
3039      protected abstract void emit_athrow();
3040    
3041      /**
3042       * Emit code to implement the checkcast bytecode
3043       * @param typeRef the LHS type
3044       */
3045      protected abstract void emit_checkcast(TypeReference typeRef);
3046    
3047      /**
3048       * Emit code to implement the checkcast bytecode
3049       * @param type the LHS type
3050       */
3051      protected abstract void emit_checkcast_resolvedInterface(RVMClass type);
3052      /**
3053       * Emit code to implement the checkcast bytecode
3054       * @param type the LHS type
3055       */
3056      protected abstract void emit_checkcast_resolvedClass(RVMClass type);
3057    
3058      /**
3059       * Emit code to implement the checkcast bytecode
3060       * @param type the LHS type
3061       */
3062      protected abstract void emit_checkcast_final(RVMType type);
3063    
3064      /**
3065       * Emit code to implement the instanceof bytecode
3066       * @param typeRef the LHS type
3067       */
3068      protected abstract void emit_instanceof(TypeReference typeRef);
3069    
3070      /**
3071       * Emit code to implement the instanceof bytecode
3072       * @param type the LHS type
3073       */
3074      protected abstract void emit_instanceof_resolvedInterface(RVMClass type);
3075    
3076      /**
3077       * Emit code to implement the instanceof bytecode
3078       * @param type the LHS type
3079       */
3080      protected abstract void emit_instanceof_resolvedClass(RVMClass type);
3081    
3082      /**
3083       * Emit code to implement the instanceof bytecode
3084       * @param type the LHS type
3085       */
3086      protected abstract void emit_instanceof_final(RVMType type);
3087    
3088      /**
3089       * Emit code to implement the monitorenter bytecode
3090       */
3091      protected abstract void emit_monitorenter();
3092    
3093      /**
3094       * Emit code to implement the monitorexit bytecode
3095       */
3096      protected abstract void emit_monitorexit();
3097    
3098      // OSR only
3099      protected abstract void emit_loadretaddrconst(int bcIndex);
3100    
3101      protected abstract String getCompilerName();
3102    }