Power bug fix
[dyninst.git] / dyninstAPI / src / inst-power.C
1 /*
2  * Copyright (c) 1996-2009 Barton P. Miller
3  * 
4  * We provide the Paradyn Parallel Performance Tools (below
5  * described as "Paradyn") on an AS IS basis, and do not warrant its
6  * validity or performance.  We reserve the right to update, modify,
7  * or discontinue this software at any time.  We shall have no
8  * obligation to supply such updates or modifications or any other
9  * form of support to you.
10  * 
11  * By your use of Paradyn, you understand and agree that we (or any
12  * other person or entity with proprietary rights in Paradyn) are
13  * under no obligation to provide either maintenance services,
14  * update services, notices of latent defects, or correction of
15  * defects for Paradyn.
16  * 
17  * This library is free software; you can redistribute it and/or
18  * modify it under the terms of the GNU Lesser General Public
19  * License as published by the Free Software Foundation; either
20  * version 2.1 of the License, or (at your option) any later version.
21  * 
22  * This library is distributed in the hope that it will be useful,
23  * but WITHOUT ANY WARRANTY; without even the implied warranty of
24  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
25  * Lesser General Public License for more details.
26  * 
27  * You should have received a copy of the GNU Lesser General Public
28  * License along with this library; if not, write to the Free Software
29  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
30  */
31
32 /*
33  * inst-power.C - Identify instrumentation points for a RS6000/PowerPCs
34  * $Id: inst-power.C,v 1.291 2008/06/19 22:13:42 jaw Exp $
35  */
36
37 #include "common/h/headers.h"
38 #include "dyninstAPI/h/BPatch_memoryAccess_NP.h"
39 #include "dyninstAPI/src/symtab.h"
40 #include "dyninstAPI/src/process.h"
41 #include "dyninstAPI/src/inst.h"
42 #include "dyninstAPI/src/instP.h"
43 #include "dyninstAPI/src/inst-power.h"
44 #include "common/h/arch.h"
45 #include "dyninstAPI/src/codegen.h"
46 #if defined(os_aix)
47 #include "dyninstAPI/src/aix.h"
48 #endif
49 #include "dyninstAPI/src/ast.h"
50 #include "dyninstAPI/src/util.h"
51 #include "common/h/stats.h"
52 #include "dyninstAPI/src/os.h"
53 #include "dyninstAPI/src/instPoint.h" // class instPoint
54 #include "dyninstAPI/src/debug.h"
55 #include "common/h/debugOstream.h"
56 #include "dyninstAPI/src/rpcMgr.h"
57 #include "dyninstAPI/src/baseTramp.h"
58 #include "dyninstAPI/src/multiTramp.h"
59 #include "dyninstAPI/src/miniTramp.h"
60 #include "dyninstAPI/h/BPatch.h"
61 #include "dyninstAPI/src/BPatch_collections.h"
62 #include "dyninstAPI/src/dyn_thread.h"
63 #include "dyninstAPI/src/registerSpace.h"
64 #include "dyninstAPI/src/binaryEdit.h"
65 #include "dyninstAPI/src/function.h"
66
67 #include "parseAPI/h/CFG.h"
68
69 #include "emitter.h"
70 #include "emit-power.h"
71
72 #include <sstream>
73
74 #include "dyninstAPI/h/BPatch_memoryAccess_NP.h"
75
76 extern bool isPowerOf2(int value, int &result);
77
78 #define DISTANCE(x,y)   ((x<y) ? (y-x) : (x-y))
79
80 Address getMaxBranch() {
81   return MAX_BRANCH;
82 }
83
84 const char *registerNames[] = { "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
85                         "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15",
86                         "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23",
87                         "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31"};
88
89 dictionary_hash<std::string, unsigned> funcFrequencyTable(::Dyninst::stringhash);
90
91 void initDefaultPointFrequencyTable()
92 {
93 #ifdef notdef
94     funcFrequencyTable[EXIT_NAME] = 1;
95
96     FILE *fp;
97     float value;
98     char name[512];
99
100     funcFrequencyTable["main"] = 1;
101     funcFrequencyTable["DYNINSTsampleValues"] = 1;
102     // try to read file.
103     fp = fopen("freq.input", "r");
104     if (!fp) {
105         bperr("no freq.input file\n");
106         return;
107     }
108     while (!feof(fp)) {
109         fscanf(fp, "%s %f\n", name, &value);
110         funcFrequencyTable[name] = (int) value;
111         bperr("adding %s %f\n", name, value);
112     }
113     fclose(fp);
114 #endif
115 }
116
117 /*
118  * Get an etimate of the frequency for the passed instPoint.  
119  *    This is not (always) the same as the function that contains the point.
120  * 
121  *  The function is selected as follows:
122  *
123  *  If the point is an entry or an exit return the function name.
124  *  If the point is a call and the callee can be determined, return the called
125  *     function.
126  *  else return the funcation containing the point.
127  *
128  *  WARNING: This code contins arbitray values for func frequency (both user 
129  *     and system).  This should be refined over time.
130  *
131  * Using 1000 calls sec to be one SD from the mean for most FPSPEC apps.
132  *      -- jkh 6/24/94
133  *
134  */
135 float getPointFrequency(instPoint *point)
136 {
137
138     int_function *func;
139
140     func = point->findCallee();
141     if (!func)
142         func = point->func();
143     
144     if (!funcFrequencyTable.defines(func->prettyName().c_str())) {
145         // Changing this value from 250 to 100 because predictedCost was
146         // too high - naim 07/18/96
147         return(100);
148     } else {
149         return (funcFrequencyTable[func->prettyName().c_str()]);
150     }
151 }
152
153
154 int instPoint::liveRegSize()
155 {
156   return maxGPR;
157 }
158
159 //
160 // return cost in cycles of executing at this point.  This is the cost
161 //   of the base tramp if it is the first at this point or 0 otherwise.
162 //
163 // We now have multiple versions of instrumentation... so, how does this work?
164 // We look for a local maximum.
165 int instPoint::getPointCost()
166 {
167   unsigned worstCost = 0;
168   for (unsigned i = 0; i < instances.size(); i++) {
169       if (instances[i]->multi()) {
170           if (instances[i]->multi()->usesTrap()) {
171               // Stop right here
172               // Actually, probably don't want this if the "always
173               // delivered" instrumentation happens
174               return 9000; // Estimated trap cost
175           }
176           else {
177               // How the heck does a base tramp only cost 35 cycles?
178               // -- bernat, 4OCT03
179               // 35 cycles for base tramp
180               // + 70 cyles for MT version (assuming 1 cycle per instruction)
181               worstCost = 105; // Magic constant from before time
182           }
183       }
184       else {
185           // No multiTramp, so still free (we're not instrumenting here).
186       }
187   }
188   return worstCost;
189 }
190
191 unsigned baseTramp::getBTCost() {
192     // Ummm... check this
193     return 105;
194 }
195
196 /*
197  * Given and instruction, relocate it to a new address, patching up
198  *   any relative addressing that is present.
199  *
200  */
201
202 unsigned relocatedInstruction::maxSizeRequired() {
203     return insn->spaceToRelocate();
204 }
205
206 Register floatingLiveRegList[] = {13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0 };
207 unsigned int floatingLiveRegListSize = 14;
208
209 // It appears as though 32-bit AIX and 32-bit Linux have compatible
210 // calling conventions, and thus we share the initialization code
211 // for both. 
212
213 // Note that while we have register definitions for r13..r31, we only
214 // use r0..r12 (well, r3..r12). I believe this is to reduce the number
215 // of saves that we execute. 
216
217
218 void registerSpace::initialize32() {
219     static bool done = false;
220     if (done) return;
221     done = true;
222
223     pdvector<registerSlot *> registers;
224
225     // At ABI boundary: R0 and R12 are dead, others are live.
226     // Also, define registers in reverse order - it helps with
227     // function calls
228     
229     registers.push_back(new registerSlot(r12,
230                                          "r12",
231                                          false,
232                                          registerSlot::deadABI,
233                                          registerSlot::GPR));
234     registers.push_back(new registerSlot(r11,
235                                          "r11",
236                                          false,
237                                          registerSlot::liveAlways,
238                                          registerSlot::GPR));
239     registers.push_back(new registerSlot(r10,
240                                          "r10",
241                                          false,
242                                          registerSlot::liveAlways,
243                                          registerSlot::GPR));
244     registers.push_back(new registerSlot(r9,
245                                          "r9",
246                                          false,
247                                          registerSlot::liveAlways,
248                                          registerSlot::GPR));
249     registers.push_back(new registerSlot(r8,
250                                          "r8",
251                                          false,
252                                          registerSlot::liveAlways,
253                                          registerSlot::GPR));
254     registers.push_back(new registerSlot(r7,
255                                          "r7",
256                                          false,
257                                          registerSlot::liveAlways,
258                                          registerSlot::GPR));
259     registers.push_back(new registerSlot(r6,
260                                          "r6",
261                                          false,
262                                          registerSlot::liveAlways,
263                                          registerSlot::GPR));
264     registers.push_back(new registerSlot(r5,
265                                          "r5",
266                                          false,
267                                          registerSlot::liveAlways,
268                                          registerSlot::GPR));
269     registers.push_back(new registerSlot(r4,
270                                          "r4",
271                                          false,
272                                          registerSlot::liveAlways,
273                                          registerSlot::GPR));
274     registers.push_back(new registerSlot(r3,
275                                          "r3",
276                                          false,
277                                          registerSlot::liveAlways,
278                                          registerSlot::GPR));
279     /// Aaaand the off-limits ones.
280
281     registers.push_back(new registerSlot(r0,
282                                          "r0",
283                                          true, // Don't use r0 - it has all sorts
284                                          // of implicit behavior.
285                                          registerSlot::deadABI,
286                                          registerSlot::GPR));
287     registers.push_back(new registerSlot(r1,
288                                          "r1",
289                                          true,
290                                          registerSlot::liveAlways,
291                                          registerSlot::GPR));
292     registers.push_back(new registerSlot(r2,
293                                          "r2",
294                                          true,
295                                          registerSlot::liveAlways,
296                                          registerSlot::GPR));
297
298     for (unsigned i = fpr0; i <= fpr13; i++) {
299         char buf[128];
300         sprintf(buf, "fpr%d", i - fpr0);
301         registers.push_back(new registerSlot(i,
302                                              buf,
303                                              false,
304                                              registerSlot::liveAlways,
305                                              registerSlot::FPR));
306     }
307     registers.push_back(new registerSlot(xer,
308                                          "xer",
309                                          true,
310                                          registerSlot::liveAlways,
311                                          registerSlot::SPR));
312  
313     registers.push_back(new registerSlot(lr,
314                                          "lr",
315                                          true,
316                                          registerSlot::liveAlways,
317                                          registerSlot::SPR));
318     registers.push_back(new registerSlot(cr,
319                                          "cr",
320                                          true,
321                                          registerSlot::liveAlways,
322                                          registerSlot::SPR));
323     registers.push_back(new registerSlot(ctr,
324                                          "ctr",
325                                          true,
326                                          registerSlot::liveAlways,
327                                          registerSlot::SPR));
328     registers.push_back(new registerSlot(mq,
329                                          "mq",
330                                          true,
331                                          registerSlot::liveAlways,
332                                          registerSlot::SPR));
333     registerSpace::createRegisterSpace(registers);
334
335     // Initialize the sets that encode which registers
336     // are used/defined by calls, returns, and syscalls. 
337     // These all assume the ABI, of course. 
338
339     // TODO: Linux/PPC needs these set as well.
340     
341 #if defined(cap_liveness)
342     returnRead_ = getBitArray();
343     // Return reads r3, r4, fpr1, fpr2
344     returnRead_[r3] = true;
345     returnRead_[r4] = true;
346     returnRead_[fpr1] = true;
347     returnRead_[fpr2] = true;
348
349     // Calls
350     callRead_ = getBitArray();
351     // Calls read r3 -> r10 (parameters), fpr1 -> fpr13 (volatile FPRs)
352     for (unsigned i = r3; i <= r10; i++) 
353         callRead_[i] = true;
354     for (unsigned i = fpr1; i <= fpr13; i++) 
355         callRead_[i] = true;
356     callWritten_ = getBitArray();
357     // Calls write to pretty much every register we use for code generation
358     callWritten_[r0] = true;
359     for (unsigned i = r3; i <= r12; i++)
360         callWritten_[i] = true;
361     // FPRs 0->13 are volatile
362     for (unsigned i = fpr0; i <= fpr13; i++)
363         callWritten_[i] = true;
364
365     // Syscall - assume the same as call
366     //syscallRead_ = getBitArray().set();
367     //syscallWritten_ = getBitArray().set();
368     syscallRead_ = callRead_;
369     syscallRead_[r0] = true;
370     syscallWritten_ = callWritten_;
371
372     allRegs_ = getBitArray().set();
373 #endif
374 }
375
376 void registerSpace::initialize64() {
377     static bool done = false;
378     if (done) return;
379     done = true;
380
381     pdvector<registerSlot *> registers;
382
383     // At ABI boundary: R0 and R12 are dead, others are live.
384     // Also, define registers in reverse order - it helps with
385     // function calls
386     
387     registers.push_back(new registerSlot(r12,
388                                          "r12",
389                                          false,
390                                          registerSlot::deadABI,
391                                          registerSlot::GPR));
392     registers.push_back(new registerSlot(r11,
393                                          "r11",
394                                          false,
395                                          registerSlot::liveAlways,
396                                          registerSlot::GPR));
397     registers.push_back(new registerSlot(r10,
398                                          "r10",
399                                          false,
400                                          registerSlot::liveAlways,
401                                          registerSlot::GPR));
402     registers.push_back(new registerSlot(r9,
403                                          "r9",
404                                          false,
405                                          registerSlot::liveAlways,
406                                          registerSlot::GPR));
407     registers.push_back(new registerSlot(r8,
408                                          "r8",
409                                          false,
410                                          registerSlot::liveAlways,
411                                          registerSlot::GPR));
412     registers.push_back(new registerSlot(r7,
413                                          "r7",
414                                          false,
415                                          registerSlot::liveAlways,
416                                          registerSlot::GPR));
417     registers.push_back(new registerSlot(r6,
418                                          "r6",
419                                          false,
420                                          registerSlot::liveAlways,
421                                          registerSlot::GPR));
422     registers.push_back(new registerSlot(r5,
423                                          "r5",
424                                          false,
425                                          registerSlot::liveAlways,
426                                          registerSlot::GPR));
427     registers.push_back(new registerSlot(r4,
428                                          "r4",
429                                          false,
430                                          registerSlot::liveAlways,
431                                          registerSlot::GPR));
432     registers.push_back(new registerSlot(r3,
433                                          "r3",
434                                          false,
435                                          registerSlot::liveAlways,
436                                          registerSlot::GPR));
437     /// Aaaand the off-limits ones.
438
439     registers.push_back(new registerSlot(r0,
440                                          "r0",
441                                          true, // Don't use r0 - it has all sorts
442                                          // of implicit behavior.
443                                          registerSlot::deadABI,
444                                          registerSlot::GPR));
445     registers.push_back(new registerSlot(r1,
446                                          "r1",
447                                          true,
448                                          registerSlot::liveAlways,
449                                          registerSlot::GPR));
450     registers.push_back(new registerSlot(r2,
451                                          "r2",
452                                          true,
453                                          registerSlot::liveAlways,
454                                          registerSlot::GPR));
455
456     for (unsigned i = fpr0; i <= fpr13; i++) {
457         char buf[128];
458         sprintf(buf, "fpr%d", i - fpr0);
459         registers.push_back(new registerSlot(i,
460                                              buf,
461                                              false,
462                                              registerSlot::liveAlways,
463                                              registerSlot::FPR));
464     }
465     registers.push_back(new registerSlot(xer,
466                                          "xer",
467                                          true,
468                                          registerSlot::liveAlways,
469                                          registerSlot::SPR));
470     registers.push_back(new registerSlot(lr,
471                                          "lr",
472                                          true,
473                                          registerSlot::liveAlways,
474                                          registerSlot::SPR));
475     registers.push_back(new registerSlot(cr,
476                                          "cr",
477                                          true,
478                                          registerSlot::liveAlways,
479                                          registerSlot::SPR));
480     registers.push_back(new registerSlot(ctr,
481                                          "ctr",
482                                          true,
483                                          registerSlot::liveAlways,
484                                          registerSlot::SPR));
485     registers.push_back(new registerSlot(mq,
486                                          "mq",
487                                          true,
488                                          registerSlot::liveAlways,
489                                          registerSlot::SPR));
490     registerSpace::createRegisterSpace64(registers);
491
492     // Initialize the sets that encode which registers
493     // are used/defined by calls, returns, and syscalls. 
494     // These all assume the ABI, of course. 
495
496     // TODO: Linux/PPC needs these set as well.
497     
498 #if defined(cap_liveness)
499     returnRead64_ = getBitArray();
500     // Return reads r3, r4, fpr1, fpr2
501     returnRead64_[r3] = true;
502     returnRead64_[r4] = true;
503     returnRead64_[fpr1] = true;
504     returnRead64_[fpr2] = true;
505
506     // Calls
507     callRead64_ = getBitArray();
508     // Calls read r3 -> r10 (parameters), fpr1 -> fpr13 (volatile FPRs)
509     for (unsigned i = r3; i <= r10; i++) 
510         callRead64_[i] = true;
511     for (unsigned i = fpr1; i <= fpr13; i++) 
512         callRead64_[i] = true;
513     callWritten64_ = getBitArray();
514     // Calls write to pretty much every register we use for code generation
515     callWritten64_[r0] = true;
516     for (unsigned i = r3; i <= r12; i++)
517         callWritten64_[i] = true;
518     // FPRs 0->13 are volatile
519     for (unsigned i = fpr0; i <= fpr13; i++)
520         callWritten64_[i] = true;
521
522     // Syscall - assume the same as call
523     syscallRead64_ = getBitArray().set();
524     syscallWritten64_ = getBitArray().set();
525
526     allRegs64_ = getBitArray().set();
527 #endif
528 }
529
530 void registerSpace::initialize() {
531     initialize32();
532     initialize64();
533 }
534
535 unsigned registerSpace::SPR(Register x) {
536     // Encodings from architecture manual
537     switch ((powerRegisters_t) x) {
538     case xer:
539         return SPR_XER;
540         break;
541     case lr:
542         return SPR_LR;
543         break;
544     case ctr:
545         return SPR_CTR;
546         break;
547     case mq:
548         return SPR_MQ;
549         break;
550     case cr:
551         fprintf(stderr, "Error: condition register has no encoding!\n");
552         return REG_NULL;
553         break;
554     default:
555         assert(0);
556         return REG_NULL;
557         break;
558     }
559 }
560             
561
562 /*
563  * Saving and restoring registers
564  * We create a new stack frame in the base tramp and save registers
565  * above it. Currently, the plan is this:
566  *          < 220 bytes as per system spec      > + 4 for 64-bit alignment
567  *          < 14 GPR slots @ 4 bytes each       >
568  *          < 14 FPR slots @ 8 bytes each       >
569  *          < 6 SPR slots @ 4 bytes each        >
570  *          < 1 FP SPR slot @ 8 bytes           >
571  *          < Space to save live regs at func call >
572  *          < Func call overflow area, 32 bytes > 
573  *          < Linkage area, 24 bytes            >
574  *
575  * Of course, change all the 4's to 8's for 64-bit mode.
576  */
577
578     ////////////////////////////////////////////////////////////////////
579     //Generates instructions to save a special purpose register onto
580     //the stack.
581     //  Returns the number of bytes needed to store the generated
582     //    instructions.
583     //  The instruction storage pointer is advanced the number of 
584     //    instructions generated.
585     //
586 // NOTE: the bit layout of the mfspr instruction is as follows:
587 // opcode:6 ; RT: 5 ; SPR: 10 ; const 339:10 ; Rc: 1
588 // However, the two 5-bit halves of the SPR field are reversed
589 // so just using the xfxform will not work
590 void saveSPR(codeGen &gen,     //Instruction storage pointer
591              Register    scratchReg, //Scratch register
592              int         sprnum,     //SPR number
593              int         stkOffset) //Offset from stack pointer
594 {
595     instruction insn;
596
597     // mfspr:  mflr scratchReg
598     insn.clear();
599     XFORM_OP_SET(insn, EXTop);
600     XFORM_RT_SET(insn, scratchReg);
601     XFORM_RA_SET(insn, sprnum & 0x1f);
602     XFORM_RB_SET(insn, (sprnum >> 5) & 0x1f);
603     XFORM_XO_SET(insn, MFSPRxop);
604     insnCodeGen::generate(gen,insn);
605
606     if (gen.addrSpace()->getAddressWidth() == 4) {
607         insnCodeGen::generateImm(gen, STop,
608                                  scratchReg, REG_SP, stkOffset);
609     } else /* gen.addrSpace()->getAddressWidth() == 8 */ {
610         insnCodeGen::generateMemAccess64(gen, STDop, STDxop,
611                                          scratchReg, REG_SP, stkOffset);
612     }
613 }
614
615     ////////////////////////////////////////////////////////////////////
616     //Generates instructions to restore a special purpose register from
617     //the stack.
618     //  Returns the number of bytes needed to store the generated
619     //    instructions.
620     //  The instruction storage pointer is advanced the number of 
621     //    instructions generated.
622     //
623 void restoreSPR(codeGen &gen,       //Instruction storage pointer
624                 Register      scratchReg, //Scratch register
625                 int           sprnum,     //SPR number
626                 int           stkOffset)  //Offset from stack pointer
627 {
628     if (gen.addrSpace()->getAddressWidth() == 4) {
629         insnCodeGen::generateImm(gen, Lop,
630                                  scratchReg, REG_SP, stkOffset);
631     } else /* gen.addrSpace()->getAddressWidth() == 8 */ {
632         insnCodeGen::generateMemAccess64(gen, LDop, LDxop,
633                                          scratchReg, REG_SP, stkOffset);
634     }
635
636     instruction insn;
637     insn.clear();
638
639     //mtspr:  mtlr scratchReg
640     XFORM_OP_SET(insn, EXTop);
641     XFORM_RT_SET(insn, scratchReg);
642     XFORM_RA_SET(insn, sprnum & 0x1f);
643     XFORM_RB_SET(insn, (sprnum >> 5) & 0x1f);
644     XFORM_XO_SET(insn, MTSPRxop);
645     insnCodeGen::generate(gen,insn);
646 }
647
648            ////////////////////////////////////////////////////////////////////
649            //Generates instructions to save link register onto stack.
650            //  Returns the number of bytes needed to store the generated
651            //    instructions.
652            //  The instruction storage pointer is advanced the number of 
653            //    instructions generated.
654 void saveLR(codeGen &gen,       //Instruction storage pointer
655             Register      scratchReg, //Scratch register
656             int           stkOffset)  //Offset from stack pointer
657 {
658     saveSPR(gen, scratchReg, SPR_LR, stkOffset);
659     gen.rs()->markSavedRegister(registerSpace::lr, stkOffset);
660 }
661
662            ////////////////////////////////////////////////////////////////////
663            //Generates instructions to restore link register from stack.
664            //  Returns the number of bytes needed to store the generated
665            //    instructions.
666            //  The instruction storage pointer is advanced the number of 
667            //    instructions generated.
668            //
669 void restoreLR(codeGen &gen,       //Instruction storage pointer
670                Register      scratchReg, //Scratch register
671                int           stkOffset)  //Offset from stack pointer
672 {
673     restoreSPR(gen, scratchReg, SPR_LR, stkOffset);
674 }
675
676            ////////////////////////////////////////////////////////////////////
677            //Generates instructions to place a given value into link register.
678            //  The entire instruction sequence consists of the generated
679            //    instructions followed by a given (tail) instruction.
680            //  Returns the number of bytes needed to store the entire
681            //    instruction sequence.
682            //  The instruction storage pointer is advanced the number of 
683            //    instructions in the sequence.
684            //
685 void setBRL(codeGen &gen,        //Instruction storage pointer
686             Register      scratchReg,  //Scratch register
687             long          val,         //Value to set link register to
688             instruction   ti)          //Tail instruction
689 {
690     insnCodeGen::loadImmIntoReg(gen, scratchReg, val);
691
692     instruction insn;
693
694     //mtspr:  mtlr scratchReg
695     insn.clear();
696     XFORM_OP_SET(insn, EXTop);
697     XFORM_RT_SET(insn, scratchReg);
698     XFORM_RA_SET(insn, SPR_LR);
699     XFORM_XO_SET(insn, MTSPRxop);
700     insnCodeGen::generate(gen,insn);
701
702     insn = ti;
703     insnCodeGen::generate(gen,insn);
704 }
705
706      //////////////////////////////////////////////////////////////////////////
707      //Writes out instructions to place a value into the link register.
708      //  If val == 0, then the instruction sequence is followed by a `nop'.
709      //  If val != 0, then the instruction sequence is followed by a `brl'.
710      //
711 void resetBRL(process  *p,   //Process to write instructions into
712               Address   loc, //Address in process to write into
713               unsigned  val) //Value to set link register
714 {
715     codeGen gen(10*instruction::size());
716     Register scratch = 10;
717     if (val) {
718         setBRL(gen, scratch, val, instruction(BRLraw));
719     }
720     else {
721         setBRL(gen, scratch, val, instruction(NOOPraw));
722     }
723     p->writeTextSpace((void *)loc, gen.used(), gen.start_ptr());
724 }
725
726     /////////////////////////////////////////////////////////////////////////
727     //Generates instructions to save the condition codes register onto stack.
728     //  Returns the number of bytes needed to store the generated
729     //    instructions.
730     //  The instruction storage pointer is advanced the number of 
731     //    instructions generated.
732     //
733 void saveCR(codeGen &gen,       //Instruction storage pointer
734             Register      scratchReg, //Scratch register
735             int           stkOffset)  //Offset from stack pointer
736 {
737     instruction insn;
738
739     //mfcr:  mflr scratchReg
740     insn.clear();
741     XFXFORM_OP_SET(insn, EXTop);
742     XFXFORM_RT_SET(insn, scratchReg);
743     XFXFORM_XO_SET(insn, MFCRxop);
744     insnCodeGen::generate(gen,insn);
745
746     if (gen.addrSpace()->getAddressWidth() == 4) {
747         insnCodeGen::generateImm(gen, STop,
748                                  scratchReg, REG_SP, stkOffset);
749     } else /* gen.addrSpace()->getAddressWidth() == 8 */ {
750         insnCodeGen::generateMemAccess64(gen, STDop, STDxop,
751                                          scratchReg, REG_SP, stkOffset);
752     }
753 }
754
755     ///////////////////////////////////////////////////////////////////////////
756     //Generates instructions to restore the condition codes register from stack.
757     //  Returns the number of bytes needed to store the generated
758     //    instructions.
759     //  The instruction storage pointer is advanced the number of 
760     //    instructions generated.
761     //
762 void restoreCR(codeGen &gen,       //Instruction storage pointer
763                Register      scratchReg, //Scratch register
764                int           stkOffset)  //Offset from stack pointer
765 {
766     instruction insn;
767
768     if (gen.addrSpace()->getAddressWidth() == 4) {
769         insnCodeGen::generateImm(gen, Lop,
770                                  scratchReg, REG_SP, stkOffset);
771     } else /* gen.addrSpace()->getAddressWidth() == 8 */ {
772         insnCodeGen::generateMemAccess64(gen, LDop, LDxop,
773                                          scratchReg, REG_SP, stkOffset);
774     }
775
776     //mtcrf:  scratchReg
777     insn.clear();
778     XFXFORM_OP_SET(insn, EXTop);
779     XFXFORM_RT_SET(insn, scratchReg);
780     XFXFORM_SPR_SET(insn, 0xff << 1);
781     XFXFORM_XO_SET(insn, MTCRFxop);
782     insnCodeGen::generate(gen,insn);
783 }
784
785     /////////////////////////////////////////////////////////////////////////
786     //Generates instructions to save the floating point status and control
787     //register on the stack.
788     //  Returns the number of bytes needed to store the generated
789     //    instructions.
790     //  The instruction storage pointer is advanced the number of 
791     //    instructions generated.
792     //
793 void saveFPSCR(codeGen &gen,       //Instruction storage pointer
794                Register      scratchReg, //Scratch fp register
795                int           stkOffset)  //Offset from stack pointer
796 {
797     instruction mffs;
798
799     //mffs scratchReg
800     mffs.clear();
801     XFORM_OP_SET(mffs, X_FP_EXTENDEDop);
802     XFORM_RT_SET(mffs, scratchReg);
803     XFORM_XO_SET(mffs, MFFSxop);
804     insnCodeGen::generate(gen,mffs);
805
806     //st:     st scratchReg, stkOffset(r1)
807     insnCodeGen::generateImm(gen, STFDop, scratchReg, REG_SP, stkOffset);
808 }
809
810     ///////////////////////////////////////////////////////////////////////////
811     //Generates instructions to restore the floating point status and control
812     //register from the stack.
813     //  Returns the number of bytes needed to store the generated
814     //    instructions.
815     //  The instruction storage pointer is advanced the number of 
816     //    instructions generated.
817     //
818 void restoreFPSCR(codeGen &gen,       //Instruction storage pointer
819                   Register      scratchReg, //Scratch fp register
820                   int           stkOffset)  //Offset from stack pointer
821 {
822     insnCodeGen::generateImm(gen, LFDop, scratchReg, REG_SP, stkOffset);
823
824     instruction mtfsf;
825
826     //mtfsf:  scratchReg
827     mtfsf.clear();
828     XFLFORM_OP_SET(mtfsf, X_FP_EXTENDEDop);
829     XFLFORM_FLM_SET(mtfsf, 0xff);
830     XFLFORM_FRB_SET(mtfsf, scratchReg);
831     XFLFORM_XO_SET(mtfsf, MTFSFxop);
832     insnCodeGen::generate(gen,mtfsf);
833 }
834
835      //////////////////////////////////////////////////////////////////////////
836      //Writes out a `br' instruction
837      //
838 void resetBR(process  *p,    //Process to write instruction into
839              Address   loc)  //Address in process to write into
840 {
841     instruction i = BRraw;
842
843     if (!p->writeDataSpace((void *)loc, instruction::size(), i.ptr()))
844         fprintf(stderr, "%s[%d]:  writeDataSpace failed\n", FILE__, __LINE__);
845 }
846
847 void saveRegisterAtOffset(codeGen &gen,
848                           Register reg,
849                           int save_off) {
850     if (gen.addrSpace()->getAddressWidth() == 4) {
851         insnCodeGen::generateImm(gen, STop,
852                                  reg, REG_SP, save_off);
853     } else /* gen.addrSpace()->getAddressWidth() == 8 */ {
854         insnCodeGen::generateMemAccess64(gen, STDop, STDxop,
855                                          reg, REG_SP, save_off);
856     }
857 }
858
859 // Dest != reg : optimizate away a load/move pair
860 void saveRegister(codeGen &gen,
861                   Register source,
862                   Register dest,
863                   int save_off)
864 {
865     saveRegisterAtOffset(gen, source, save_off + (dest * gen.addrSpace()->getAddressWidth()));
866     //  bperr("Saving reg %d at 0x%x off the stack\n", reg, offset + reg*GPRSIZE);
867 }
868
869 void saveRegister(codeGen &gen,
870                   Register reg,
871                   int save_off)
872 {
873     saveRegister(gen, reg, reg, save_off);
874 }
875
876 void restoreRegisterAtOffset(codeGen &gen,
877                              Register dest,
878                              int saved_off) {
879     if (gen.addrSpace()->getAddressWidth() == 4) {
880         insnCodeGen::generateImm(gen, Lop, 
881                                  dest, REG_SP, saved_off);
882     } else /* gen.addrSpace()->getAddressWidth() == 8 */ {
883         insnCodeGen::generateMemAccess64(gen, LDop, LDxop,
884                                          dest, REG_SP, saved_off);
885     }
886 }
887
888 // Dest != reg : optimizate away a load/move pair
889 void restoreRegister(codeGen &gen,
890                      Register source,
891                      Register dest, 
892                      int saved_off)
893 {
894     return restoreRegisterAtOffset(gen, dest, saved_off + (source * gen.addrSpace()->getAddressWidth()));
895     //bperr( "Loading reg %d (into reg %d) at 0x%x off the stack\n", 
896     //  reg, dest, offset + reg*GPRSIZE);
897 }
898
899 void restoreRegister(codeGen &gen,
900                      Register reg,
901                      int save_off)
902 {
903     restoreRegister(gen, reg, reg, save_off);
904 }
905
906 void saveFPRegister(codeGen &gen, 
907                     Register reg,
908                     int save_off)
909 {
910     insnCodeGen::generateImm(gen, STFDop, 
911                              reg, REG_SP, save_off + reg*FPRSIZE);
912     //bperr( "Saving FP reg %d at 0x%x off the stack\n", 
913     //  reg, offset + reg*FPRSIZE);
914 }
915
916 void restoreFPRegister(codeGen &gen,
917                        Register source,
918                        Register dest,
919                        int save_off)
920 {
921     insnCodeGen::generateImm(gen, LFDop, 
922                              dest, REG_SP, save_off + source*FPRSIZE);
923     //  bperr("Loading FP reg %d (into %d) at 0x%x off the stack\n", 
924     //  reg, dest, offset + reg*FPRSIZE);
925 }
926
927 void restoreFPRegister(codeGen &gen,
928                        Register reg,
929                        int save_off)
930 {
931     restoreFPRegister(gen, reg, reg, save_off);
932 }       
933
934 /*
935  * Emit code to push down the stack, AST-generate style
936  */
937 void pushStack(codeGen &gen)
938 {
939     if (gen.addrSpace()->getAddressWidth() == 4) {
940         insnCodeGen::generateImm(gen, STUop,
941                                  REG_SP, REG_SP, -TRAMP_FRAME_SIZE_32);
942     } else /* gen.addrSpace()->getAddressWidth() == 8 */ {
943         insnCodeGen::generateMemAccess64(gen, STDop, STDUxop,
944                                   REG_SP, REG_SP, -TRAMP_FRAME_SIZE_64);
945     }
946 }
947
948 void popStack(codeGen &gen)
949 {
950     if (gen.addrSpace()->getAddressWidth() == 4) {
951         insnCodeGen::generateImm(gen, CALop, 
952                                  REG_SP, REG_SP, TRAMP_FRAME_SIZE_32);
953
954     } else /* gen.addrSpace()->getAddressWidth() == 8 */ {
955         insnCodeGen::generateImm(gen, CALop,
956                                  REG_SP, REG_SP, TRAMP_FRAME_SIZE_64);
957     }
958 }
959
960 /*
961  * Save necessary registers on the stack
962  * insn, base: for code generation. Offset: regs saved at offset + reg
963  * Returns: number of registers saved.
964  * Side effects: instruction pointer and base param are shifted to 
965  *   next free slot.
966  */
967 unsigned saveGPRegisters(codeGen &gen,
968                          registerSpace *theRegSpace,
969                          int save_off, int numReqGPRs)
970 {
971     int numRegs = 0;
972     if (numReqGPRs == -1 ) numReqGPRs = theRegSpace->numGPRs();
973     for(int i = 0; i < theRegSpace->numGPRs(); i++) {
974         registerSlot *reg = theRegSpace->GPRs()[i];
975         if (reg->liveState == registerSlot::live) {
976             saveRegister(gen, reg->encoding(), save_off);
977             // saveRegister implicitly adds in (reg * word size)
978             // Do that by hand here.
979             
980             int actual_save_off = save_off;
981
982             actual_save_off += (reg->encoding() * gen.addrSpace()->getAddressWidth());
983
984             gen.rs()->markSavedRegister(reg->number, actual_save_off);
985             numRegs++;
986             if (numRegs == numReqGPRs) break;
987         }
988     }
989     return numRegs;
990 }
991
992 /*
993  * Restore necessary registers from the stack
994  * insn, base: for code generation. Offset: regs restored from offset + reg
995  * Returns: number of registers restored.
996  * Side effects: instruction pointer and base param are shifted to 
997  *   next free slot.
998  */
999
1000 unsigned restoreGPRegisters(codeGen &gen,
1001                             registerSpace *theRegSpace,
1002                             int save_off)
1003 {
1004     unsigned numRegs = 0;
1005     for(int i = 0; i < theRegSpace->numGPRs(); i++) {
1006         registerSlot *reg = theRegSpace->GPRs()[i];
1007         if (reg->liveState == registerSlot::spilled) {
1008             restoreRegister(gen, reg->encoding(), save_off);
1009             numRegs++;
1010         }
1011     }
1012
1013     return numRegs;
1014 }
1015
1016 /*
1017  * Save FPR registers on the stack. (0-13)
1018  * insn, base: for code generation. Offset: regs saved at offset + reg
1019  * Returns: number of regs saved.
1020  */
1021
1022 unsigned saveFPRegisters(codeGen &gen,
1023                          registerSpace * theRegSpace,
1024                          int save_off)
1025 {
1026   unsigned numRegs = 0;
1027   for(int i = 0; i < theRegSpace->numFPRs(); i++) {
1028       registerSlot *reg = theRegSpace->FPRs()[i];
1029       if (reg->liveState == registerSlot::live) {
1030           saveFPRegister(gen, reg->encoding(), save_off);
1031           reg->liveState = registerSlot::spilled;
1032           numRegs++;
1033       }
1034   }  
1035   
1036   return numRegs;
1037 }
1038
1039 /*
1040  * Restore FPR registers from the stack. (0-13)
1041  * insn, base: for code generation. Offset: regs restored from offset + reg
1042  * Returns: number of regs restored.
1043  */
1044
1045 unsigned restoreFPRegisters(codeGen &gen, 
1046                             registerSpace *theRegSpace,
1047                             int save_off)
1048 {
1049   
1050   unsigned numRegs = 0;
1051   for(int i = 0; i < theRegSpace->numFPRs(); i++) {
1052       registerSlot *reg = theRegSpace->FPRs()[i];
1053       if (reg->liveState == registerSlot::spilled) {
1054           restoreFPRegister(gen, reg->encoding(), save_off);
1055           numRegs++;
1056       }
1057   }
1058   
1059   return numRegs;
1060 }
1061
1062 /*
1063  * Save the special purpose registers (for Dyninst conservative tramp)
1064  * CTR, CR, XER, SPR0, FPSCR
1065  */
1066 unsigned saveSPRegisters(codeGen &gen,
1067                          registerSpace * 
1068 #if defined(os_aix)
1069                          theRegSpace
1070 #endif
1071                          , int save_off
1072                          , int force_save)
1073 {
1074     unsigned num_saved = 0;
1075     int cr_off, ctr_off, xer_off, spr0_off, fpscr_off;
1076     
1077     if (gen.addrSpace()->getAddressWidth() == 4) {
1078         cr_off    = STK_CR_32;
1079         ctr_off   = STK_CTR_32;
1080         xer_off   = STK_XER_32;
1081         fpscr_off = STK_FP_CR_32;
1082         spr0_off  = STK_SPR0_32;
1083     } else /* gen.addrSpace()->getAddressWidth() == 8 */ {
1084         cr_off    = STK_CR_64;
1085         ctr_off   = STK_CTR_64;
1086         xer_off   = STK_XER_64;
1087         fpscr_off = STK_FP_CR_64;
1088         spr0_off  = STK_SPR0_64;
1089     }
1090
1091     registerSlot *regCR = (*(gen.rs()))[registerSpace::cr]; 
1092     assert (regCR != NULL); 
1093     if (force_save || regCR->liveState == registerSlot::live) 
1094     {
1095     saveCR(gen, 10, save_off + cr_off); num_saved++;
1096     gen.rs()->markSavedRegister(registerSpace::cr, save_off + cr_off);
1097     }
1098     registerSlot *regCTR = (*(gen.rs()))[registerSpace::ctr]; 
1099     assert (regCTR != NULL); 
1100     if (force_save || regCTR->liveState == registerSlot::live) 
1101     {
1102     saveSPR(gen, 10, SPR_CTR, save_off + ctr_off); num_saved++;
1103     gen.rs()->markSavedRegister(registerSpace::ctr, save_off + ctr_off);
1104     }
1105
1106     registerSlot *regXER = (*(gen.rs()))[registerSpace::xer]; 
1107     assert (regXER != NULL); 
1108     if (force_save || regXER->liveState == registerSlot::live) 
1109    {
1110     saveSPR(gen, 10, SPR_XER, save_off + xer_off); num_saved++;
1111     gen.rs()->markSavedRegister(registerSpace::xer, save_off + xer_off);
1112     }
1113
1114     saveFPSCR(gen, 10, save_off + fpscr_off); num_saved++;
1115     
1116     // MQ only exists on POWER, not PowerPC. Right now that's correlated
1117     // to AIX vs Linux, but we _really_ should fix that...
1118     // We need to dynamically determine the CPU and emit code based on that.
1119     //
1120     // Apparently, AIX64 doesn't use the MQ register either.
1121     //
1122     // Well, if it isn't used, then it's dead, and we won't save it.
1123     // ARGH inferior RPCs...
1124 #if defined(os_aix) && !defined(arch_64bit)
1125     registerSlot *mq = ((*theRegSpace)[registerSpace::mq]);
1126     if (mq->liveState == registerSlot::live) {
1127         saveSPR(gen, 10, mq->encoding(), save_off + spr0_off); num_saved++;
1128         mq->liveState = registerSlot::spilled;
1129         gen.rs()->markSavedRegister(registerSpace::mq, save_off + spr0_off);
1130
1131     }
1132 #endif
1133
1134     return num_saved;
1135 }
1136
1137 /*
1138  * Restore the special purpose registers (for Dyninst conservative tramp)
1139  * CTR, CR, XER, SPR0, FPSCR
1140  */
1141
1142 unsigned restoreSPRegisters(codeGen &gen,
1143                             registerSpace *
1144 #if defined(os_aix)
1145                             theRegSpace
1146 #endif
1147                             , int save_off
1148                             , int force_save)
1149 {
1150     int cr_off, ctr_off, xer_off, spr0_off, fpscr_off;
1151     unsigned num_restored = 0;
1152
1153     if (gen.addrSpace()->getAddressWidth() == 4) {
1154         cr_off    = STK_CR_32;
1155         ctr_off   = STK_CTR_32;
1156         xer_off   = STK_XER_32;
1157         fpscr_off = STK_FP_CR_32;
1158         spr0_off  = STK_SPR0_32;
1159     } else /* gen.addrSpace()->getAddressWidth() == 8 */ {
1160         cr_off    = STK_CR_64;
1161         ctr_off   = STK_CTR_64;
1162         xer_off   = STK_XER_64;
1163         fpscr_off = STK_FP_CR_64;
1164         spr0_off  = STK_SPR0_64;
1165     }
1166
1167     registerSlot *regCR = (*(gen.rs()))[registerSpace::cr]; 
1168     assert (regCR != NULL); 
1169     if (force_save || regCR->liveState == registerSlot::spilled) 
1170     {
1171     restoreCR(gen, 10, save_off + cr_off); num_restored++;
1172     }
1173     registerSlot *regCTR = (*(gen.rs()))[registerSpace::ctr]; 
1174     assert (regCTR != NULL); 
1175     if (force_save || regCTR->liveState == registerSlot::spilled) 
1176     {
1177     restoreSPR(gen, 10, SPR_CTR, save_off + ctr_off); num_restored++;
1178     }
1179     registerSlot *regXER = (*(gen.rs()))[registerSpace::xer]; 
1180     assert (regXER != NULL); 
1181     if (force_save || regXER->liveState == registerSlot::spilled) 
1182     {
1183     restoreSPR(gen, 10, SPR_XER, save_off + xer_off); num_restored++;
1184     }
1185     restoreFPSCR(gen, 10, save_off + fpscr_off); num_restored++;
1186     
1187 #if defined(os_aix) && !defined(arch_64bit)
1188     // See comment in saveSPRegisters
1189     registerSlot *mq = ((*theRegSpace)[registerSpace::mq]);
1190     if (mq->liveState == registerSlot::spilled) {
1191         restoreSPR(gen, 10, mq->encoding(), save_off + spr0_off); num_restored++;
1192     }
1193 #endif
1194
1195     return num_restored;
1196 }
1197
1198
1199 bool baseTrampInstance::finalizeGuardBranch(codeGen &gen,
1200                                             int disp) {
1201     // Assumes that preCode is generated
1202     // and we're now finalizing the jump to go
1203     // past whatever miniTramps may have been.
1204
1205     // Note: must be a conditional jump
1206
1207     assert(disp > 0);
1208
1209     // Conditional jump if not equal.
1210     instruction jumpInsn;
1211
1212     jumpInsn.clear();
1213     BFORM_OP_SET(jumpInsn, BCop);
1214     BFORM_BO_SET(jumpInsn, BFALSEcond);
1215     BFORM_BI_SET(jumpInsn, EQcond);
1216     BFORM_BD_SET(jumpInsn, disp >> 2);
1217     BFORM_AA_SET(jumpInsn, 0);
1218     BFORM_LK_SET(jumpInsn, 0);
1219     insnCodeGen::generate(gen,jumpInsn);
1220
1221     return true;
1222 }
1223        
1224
1225 bool baseTramp::generateSaves(codeGen &gen,
1226                               registerSpace *,
1227                               baseTrampInstance *)
1228 {
1229     regalloc_printf("========== baseTramp::generateSaves\n");
1230     
1231     int gpr_off, fpr_off, ctr_off;
1232     if (gen.addrSpace()->getAddressWidth() == 4) {
1233         gpr_off = TRAMP_GPR_OFFSET_32;
1234         fpr_off = TRAMP_FPR_OFFSET_32;
1235         ctr_off = STK_CTR_32;
1236     } else /* gen.addrSpace()->getAddressWidth() == 8 */ {
1237         gpr_off = TRAMP_GPR_OFFSET_64;
1238         fpr_off = TRAMP_FPR_OFFSET_64;
1239         ctr_off = STK_CTR_64;
1240     }
1241
1242     // Make a stack frame.
1243     pushStack(gen);
1244
1245     // Save GPRs
1246     saveGPRegisters(gen, gen.rs(), gpr_off);
1247
1248     if(BPatch::bpatch->isSaveFPROn() ||  // Save FPRs
1249         BPatch::bpatch->isForceSaveFPROn() ) 
1250         saveFPRegisters(gen, gen.rs(), fpr_off);
1251
1252     // Save LR            
1253     saveLR(gen, REG_SCRATCH /* register to use */, TRAMP_SPR_OFFSET + STK_LR);
1254
1255     // No more cookie. FIX aix stackwalking.
1256     if (isConservative())
1257         saveSPRegisters(gen, gen.rs(), TRAMP_SPR_OFFSET, true);
1258     else 
1259         saveSPRegisters(gen, gen.rs(), TRAMP_SPR_OFFSET, false);
1260     
1261
1262     return true;
1263 }
1264
1265 bool baseTramp::generateRestores(codeGen &gen,
1266                                  registerSpace *,
1267                                  baseTrampInstance *)
1268 {
1269
1270     regalloc_printf("========== baseTramp::generateRestores\n");
1271
1272     int gpr_off, fpr_off, ctr_off;
1273     if (gen.addrSpace()->getAddressWidth() == 4) {
1274         gpr_off = TRAMP_GPR_OFFSET_32;
1275         fpr_off = TRAMP_FPR_OFFSET_32;
1276         ctr_off = STK_CTR_32;
1277     } else /* gen.addrSpace()->getAddressWidth() == 8 */ {
1278         gpr_off = TRAMP_GPR_OFFSET_64;
1279         fpr_off = TRAMP_FPR_OFFSET_64;
1280         ctr_off = STK_CTR_64;
1281     }
1282
1283     // Restore possible SPR saves
1284     if (isConservative())
1285         restoreSPRegisters(gen, gen.rs(), TRAMP_SPR_OFFSET, true);
1286     else 
1287         restoreSPRegisters(gen, gen.rs(), TRAMP_SPR_OFFSET, false);
1288
1289
1290     // LR
1291     restoreLR(gen, REG_SCRATCH, TRAMP_SPR_OFFSET + STK_LR);
1292
1293     if (BPatch::bpatch->isSaveFPROn() || // FPRs
1294         BPatch::bpatch->isForceSaveFPROn() ) 
1295         restoreFPRegisters(gen, gen.rs(), fpr_off);
1296
1297     // GPRs
1298     restoreGPRegisters(gen, gen.rs(), gpr_off);
1299
1300     /*
1301     // Multithread GPR -- always save
1302     restoreRegister(gen, REG_MT_POS, TRAMP_GPR_OFFSET);
1303     */
1304
1305     popStack(gen);
1306
1307     return true;
1308 }
1309
1310
1311 void emitImm(opCode op, Register src1, RegValue src2imm, Register dest, 
1312              codeGen &gen, bool noCost, registerSpace * /* rs */)
1313 {
1314         //bperr("emitImm(op=%d,src=%d,src2imm=%d,dest=%d)\n",
1315         //        op, src1, src2imm, dest);
1316     int iop=-1;
1317     int result=-1;
1318     switch (op) {
1319         // integer ops
1320     case plusOp:
1321         iop = CALop;
1322         insnCodeGen::generateImm(gen, iop, dest, src1, src2imm);
1323         return;
1324         break;
1325         
1326     case minusOp:
1327         iop = SIop;
1328         insnCodeGen::generateImm(gen, iop, dest, src1, src2imm);
1329         return;
1330         break;
1331         
1332     case timesOp:
1333        if (isPowerOf2(src2imm,result) && (result < (int) (gen.addrSpace()->getAddressWidth() * 8))) {
1334             insnCodeGen::generateLShift(gen, src1, result, dest);
1335             return;
1336         }
1337         else {
1338             Register dest2 = gen.rs()->getScratchRegister(gen, noCost);
1339             emitVload(loadConstOp, src2imm, dest2, dest2, gen, noCost);
1340             emitV(op, src1, dest2, dest, gen, noCost);
1341             return;
1342         }
1343         break;
1344         
1345     case divOp:
1346         if (isPowerOf2(src2imm,result) && (result < (int) (gen.addrSpace()->getAddressWidth() * 8))) {
1347             insnCodeGen::generateRShift(gen, src1, result, dest);
1348             return;
1349         }
1350         else {
1351             Register dest2 = gen.rs()->getScratchRegister(gen, noCost);
1352             emitVload(loadConstOp, src2imm, dest2, dest2, gen, noCost);
1353             emitV(op, src1, dest2, dest, gen, noCost);
1354             return;
1355         }
1356         break;
1357         
1358         // Bool ops
1359     case orOp:
1360         iop = ORILop;
1361         // For some reason, the destField is 2nd for ORILop and ANDILop
1362         insnCodeGen::generateImm(gen, iop, src1, dest, src2imm);
1363         return;
1364         break;
1365         
1366     case andOp:
1367         iop = ANDILop;
1368         // For some reason, the destField is 2nd for ORILop and ANDILop
1369         insnCodeGen::generateImm(gen, iop, src1, dest, src2imm);
1370         return;
1371         break;
1372     default:
1373         Register dest2 = gen.rs()->getScratchRegister(gen, noCost);
1374         emitVload(loadConstOp, src2imm, dest2, dest2, gen, noCost);
1375         emitV(op, src1, dest2, dest, gen, noCost);
1376         return;
1377         break;
1378     }
1379 }
1380
1381 void cleanUpAndExit(int status);
1382
1383 /* Recursive function that goes to where our instrumentation is calling
1384 to figure out what registers are clobbered there, and in any function
1385 that it calls, to a certain depth ... at which point we clobber everything
1386
1387 Update-12/06, njr, since we're going to a cached system we are just going to 
1388 look at the first level and not do recursive, since we would have to also
1389 store and reexamine every call out instead of doing it on the fly like before*/
1390 bool EmitterPOWER::clobberAllFuncCall( registerSpace *rs,
1391                                        int_function * callee)
1392                    
1393 {
1394   unsigned i;
1395   if (!callee) return true;
1396
1397   stats_codegen.startTimer(CODEGEN_LIVENESS_TIMER);
1398     
1399   /* usedRegs does calculations if not done before and returns
1400      whether or not the callee is a leaf function.
1401      if it is, we use the register info we gathered,
1402      otherwise, we punt and save everything */
1403   //     bool isLeafFunc = callee->ifunc()->usedRegs();
1404
1405   if (callee->ifunc()->isLeafFunc()) {
1406       std::set<Register> * gprs = callee->ifunc()->usedGPRs();
1407       std::set<Register>::iterator It = gprs->begin();
1408       for(i = 0; i < gprs->size(); i++) {
1409           //while (It != gprs->end()){
1410           rs->GPRs()[*(It++)]->beenUsed = true;
1411       }
1412       
1413       std::set<Register> * fprs = callee->ifunc()->usedFPRs();
1414       std::set<Register>::iterator It2 = fprs->begin();
1415       for(i = 0; i < fprs->size(); i++)
1416       {
1417           //while (It2 != fprs->end()){
1418           rs->FPRs()[*(It2++)]->beenUsed = true;
1419       }
1420     }
1421   else {
1422       for (int i = 0; i < rs->numGPRs(); i++) {
1423           rs->GPRs()[i]->beenUsed = true;
1424       }
1425       for (int i = 0; i < rs->numFPRs(); i++) {
1426           rs->FPRs()[i]->beenUsed = true;
1427       }
1428   }
1429   stats_codegen.stopTimer(CODEGEN_LIVENESS_TIMER);
1430   return false;
1431 }
1432
1433
1434 //
1435 // Author: Jeff Hollingsworth (3/26/96)
1436 //
1437 // Emit a function call.
1438 //   It saves registers as needed.
1439 //   copy the passed arguments into the canonical argument registers (r3-r10)
1440 //   AIX and 64-bit ELF Linux ONLY: 
1441 //     Locate the TOC entry of the callee module and copy it into R2
1442 //   generate a branch and link the destination
1443 //   AIX and 64-bit ELF Linux ONLY:
1444 //     Restore the original TOC into R2
1445 //   restore the saved registers.
1446 //
1447 // Parameters:
1448 //   op - unused parameter (to be compatible with sparc)
1449 //   srcs - vector of ints indicating the registers that contain the parameters
1450 //   dest - the destination address (should be Address not reg). 
1451 //   insn - pointer to the code we are generating
1452 //   based - offset into the code generated.
1453 //
1454
1455 Register emitFuncCall(opCode, codeGen &, pdvector<AstNodePtr> &, bool, Address) {
1456         assert(0);
1457         return 0;
1458 }
1459
1460 Register emitFuncCall(opCode op,
1461                       codeGen &gen,
1462                       pdvector<AstNodePtr> &operands, bool noCost,
1463                       int_function *callee) {
1464     return gen.emitter()->emitCall(op, gen, operands, noCost, callee);
1465 }
1466
1467 Register EmitterPOWERStat::emitCallReplacement(opCode /*ocode*/,
1468                                               codeGen &/*gen*/,
1469                                               bool /* noCost */,
1470                                               int_function * /*callee*/) {
1471         fprintf(stderr, "emitCallReplacement not implemented for binary rewriter \n");
1472         assert (0);
1473         return 0;
1474 }
1475  
1476 Register EmitterPOWERDyn::emitCallReplacement(opCode ocode,
1477                                               codeGen &gen,
1478                                               bool /* noCost */,
1479                                               int_function *callee) {
1480     // This takes care of the special case where we are replacing an existing
1481     // linking branch instruction.
1482     //
1483     // This code makes two crucial assumptions:
1484     // 1) LR is free: Linking branch instructions place pre-branch IP in LR.
1485     // 2) TOC (r2) is free: r2 should hold TOC of destination.  So use it
1486     //    as scratch, and set it to destination module's TOC upon return.
1487     //    This works for both the inter and intra module call cases.
1488     // In the 32-bit case where we can't use r2, stomp on r0 and pray...
1489
1490     //  Sanity check for opcode.
1491     assert(ocode == funcJumpOp);
1492
1493     Register freeReg = 0;
1494     instruction mtlr(MTLR0raw);
1495
1496     // 64-bit Mutatees
1497     if (gen.addrSpace()->proc()->getAddressWidth() == 8) {
1498         freeReg = 2;
1499         mtlr = instruction(MTLR2raw);
1500     }
1501
1502     // Load register with address.
1503     emitVload(loadConstOp, callee->getAddress(), freeReg, freeReg, gen, false);
1504
1505     // Move to link register.
1506     insnCodeGen::generate(gen,mtlr);
1507
1508     Address toc_new = gen.addrSpace()->proc()->getTOCoffsetInfo(callee);
1509     if (toc_new) {
1510         // Set up the new TOC value
1511         emitVload(loadConstOp, toc_new, freeReg, freeReg, gen, false);
1512     }
1513
1514     // blr - branch through the link reg.
1515     instruction blr(BRraw);
1516     insnCodeGen::generate(gen,blr);
1517
1518     int_function *caller = gen.point()->func();
1519     Address toc_orig = gen.addrSpace()->proc()->getTOCoffsetInfo(caller);
1520     if (toc_new) {
1521         // Restore the original TOC value.
1522         emitVload(loadConstOp, toc_orig, freeReg, freeReg, gen, false);
1523     }
1524
1525     // What to return here?
1526     return REG_NULL;
1527 }
1528
1529 // There are four "axes" going on here:
1530 // AIX vs Linux
1531 // 32 bit vs 64 bit  
1532 // Instrumentation vs function call replacement
1533 // Static vs. dynamic 
1534
1535 Register EmitterPOWER::emitCall(opCode ocode,
1536                                    codeGen &gen,
1537                                    const pdvector<AstNodePtr> &operands, bool noCost,
1538                                    int_function *callee) {
1539
1540     bool inInstrumentation = true;
1541
1542 // If inInstrumentation is true we're in instrumentation; if false we're in function call replacement
1543     if (gen.obj() && 
1544         dynamic_cast<replacedInstruction *>(gen.obj())) {
1545         inInstrumentation = false;
1546         inst_printf("In function replacement, not saving state\n");
1547     }
1548     
1549     if (ocode == funcJumpOp)
1550         return emitCallReplacement(ocode, gen, noCost, callee);
1551     
1552     //  Sanity check for NULL address argument
1553     if (!callee) {
1554         char msg[256];
1555         sprintf(msg, "%s[%d]:  internal error:  emitFuncCall called w/out"
1556                 "callee argument", __FILE__, __LINE__);
1557         showErrorCallback(80, msg);
1558         assert(0);
1559     }
1560
1561     // Now that we have the destination address (unique, hopefully) 
1562     // get the TOC anchor value for that function
1563     // The TOC offset is stored in the Object. 
1564     // file() -> pdmodule "parent"
1565     // exec() -> image "parent"
1566  
1567     Address toc_anchor = 0;
1568     Address caller_toc = 0;
1569     pdvector <Register> srcs;
1570
1571     // AIX, 32/64, static/dynamic, inst/replacement ; Linux, 64, static/dynamic, inst/repl
1572     //DYN
1573     if (gen.addrSpace()->proc()) {
1574         toc_anchor = gen.addrSpace()->proc()->getTOCoffsetInfo(callee);
1575         
1576         // Instead of saving the TOC (if we can't), just reset it afterwards.
1577         if (gen.func()) {
1578            caller_toc = gen.addrSpace()->proc()->getTOCoffsetInfo(gen.func());
1579         }
1580         else if (gen.point()) {
1581            caller_toc = gen.addrSpace()->proc()->getTOCoffsetInfo(gen.point()->func());
1582         }
1583         else {
1584            // Don't need it, and this might be an iRPC
1585         }
1586
1587         inst_printf("Caller TOC 0x%lx; callee 0x%lx\n",
1588             caller_toc, toc_anchor);
1589     }
1590     // ALL
1591     bool needToSaveLR = false;
1592     registerSlot *regLR = (*(gen.rs()))[registerSpace::lr];
1593     if (regLR && regLR->liveState == registerSlot::live) {
1594         needToSaveLR = true;
1595         inst_printf("... need to save LR\n");
1596     }
1597
1598     // Note: For 32-bit ELF PowerPC Linux (and other SYSV ABI followers)
1599     // r2 is described as "reserved for system use and is not to be 
1600     // changed by application code".
1601     // On these platforms, we return 0 when getTOCoffsetInfo is called.
1602
1603     pdvector<int> savedRegs;
1604
1605     //  Save the link register.
1606     // mflr r0
1607     // AIX/Linux, 32/64, stat/dynamic, instrumentation
1608     if (needToSaveLR) {
1609       if (!inInstrumentation) {
1610         // Debug output
1611         fprintf(stderr, "Error: instrumenting offset 0x%lx, function %s, from module %s; LR live at call replacement\n",
1612                 gen.point()->addr(), gen.func()->symTabName().c_str(), gen.func()->obj()->fileName().c_str());
1613       }
1614
1615         assert(inInstrumentation);
1616         insnCodeGen::generateMoveFromLR(gen, 0);
1617         saveRegister(gen, 0, FUNC_CALL_SAVE);
1618         savedRegs.push_back(0);
1619         inst_printf("saved LR in 0\n");
1620     }
1621
1622     if (inInstrumentation &&
1623         toc_anchor &&
1624         (toc_anchor != caller_toc)) {
1625         // Save register 2 (TOC)
1626         saveRegister(gen, 2, FUNC_CALL_SAVE);
1627         savedRegs.push_back(2);
1628     }
1629
1630     // see what others we need to save.
1631     for (int i = 0; i < gen.rs()->numGPRs(); i++) {
1632        registerSlot *reg = gen.rs()->GPRs()[i];
1633
1634        // We must save if:
1635        // refCount > 0 (and not a source register)
1636        // keptValue == true (keep over the call)
1637        // liveState == live (technically, only if not saved by the callee) 
1638        
1639        if (inInstrumentation &&
1640            ((reg->refCount > 0) || 
1641             reg->keptValue ||
1642             (reg->liveState == registerSlot::live))) {
1643           saveRegister(gen, reg->number, FUNC_CALL_SAVE);
1644           savedRegs.push_back(reg->number);
1645        }
1646     }
1647
1648     // Generate the code for all function parameters, and keep a list
1649     // of what registers they're in.
1650     for (unsigned u = 0; u < operands.size(); u++) {
1651     // Note: if we're in function replacement, we can assert operands.empty()
1652 /*
1653         if (operands[u]->getSize() == 8) {
1654             // What does this do?
1655             bperr( "in weird code\n");
1656             Register dummyReg = gen.rs()->allocateRegister(gen, noCost);
1657             srcs.push_back(dummyReg);
1658
1659             insnCodeGen::generateImm(gen, CALop, dummyReg, 0, 0);
1660         }
1661 */
1662         //Register src = REG_NULL;
1663         // Try to target the code generation
1664         
1665         Register reg = REG_NULL;
1666         // Try to allocate the correct parameter register
1667         if (gen.rs()->allocateSpecificRegister(gen, registerSpace::r3 + u, true))
1668             reg = registerSpace::r3 + u;
1669
1670         Address unused = ADDR_NULL;
1671         if (!operands[u]->generateCode_phase2( gen, false, unused, reg)) assert(0);
1672         assert(reg != REG_NULL);
1673         srcs.push_back(reg);
1674         //bperr( "Generated operand %d, base %d\n", u, base);
1675     }
1676   
1677     if(srcs.size() > 8) {
1678         // This is not necessarily true; more then 8 arguments could be passed,
1679         // the first 8 need to be in registers while the others need to be on
1680         // the stack, -- sec 3/1/97
1681        std::string msg = "Too many arguments to function call in instrumentation code:"
1682             " only 8 arguments can (currently) be passed on the POWER architecture.\n";
1683         bperr( msg.c_str());
1684         showErrorCallback(94,msg);
1685         cleanUpAndExit(-1);
1686     }
1687
1688     // If we got the wrong register, we may need to do a 3-way swap. 
1689
1690     int scratchRegs[8];
1691     for (int a = 0; a < 8; a++) {
1692         scratchRegs[a] = -1;
1693     }
1694
1695     // Now load the parameters into registers.
1696     for (unsigned u=0; u<srcs.size(); u++){
1697
1698         // Parameters start at register 3 - so we're already done
1699         // in this case
1700         if (srcs[u] == (registerSpace::r3+u)) {
1701             gen.rs()->freeRegister(srcs[u]);
1702             continue;
1703         }
1704
1705         int whichSource = -1;
1706         bool hasSourceBeenCopied = true;
1707         
1708
1709         // If the parameter we want exists in a scratch register...
1710         if (scratchRegs[u] != -1) {
1711             insnCodeGen::generateImm(gen, ORILop, scratchRegs[u], u+3, 0);
1712             gen.rs()->freeRegister(scratchRegs[u]);
1713             // We should check to make sure the one we want isn't occupied?
1714         } else {
1715             for (unsigned v=u; v < srcs.size(); v++) {
1716                 if (srcs[v] == u+3) {
1717                     // Okay, so the source we want is actuall in srcs[v]
1718                     hasSourceBeenCopied = false;
1719                     whichSource = v;
1720                     break;
1721                 }
1722             }
1723             // Ummm... we didn't find it? Ah, so copying us (since we're wrong)
1724             // into scratch.
1725             if (!hasSourceBeenCopied) {
1726                 Register scratch = gen.rs()->getScratchRegister(gen);
1727                 insnCodeGen::generateImm(gen, ORILop, u+3, scratch, 0);
1728                 gen.rs()->freeRegister(u+3);
1729                 scratchRegs[whichSource] = scratch;
1730                 hasSourceBeenCopied = true;
1731
1732                 insnCodeGen::generateImm(gen, ORILop, srcs[u], u+3, 0);
1733                 gen.rs()->freeRegister(srcs[u]);
1734
1735             } else {
1736                 insnCodeGen::generateImm(gen, ORILop, srcs[u], u+3, 0);
1737                 gen.rs()->freeRegister(srcs[u]);
1738                 // Not sure why this was needed
1739                 //gen.rs()->clobberRegister(u+3);
1740             }
1741         } 
1742     }
1743
1744     // Call generation time.
1745     bool setTOC = false;
1746
1747         // AIX, 32/64, stat/dyn, inst/repl; Linux, 64, stat/dyn, inst/repl
1748     if (toc_anchor &&
1749         (toc_anchor != caller_toc))
1750         setTOC = true;
1751
1752     
1753     emitCallInstruction(gen, callee, setTOC, toc_anchor);
1754     
1755     // ALL instrumentation
1756     Register retReg = REG_NULL;
1757     if (inInstrumentation) {
1758         // get a register to keep the return value in.
1759         retReg = gen.rs()->allocateRegister(gen, noCost);        
1760         // put the return value from register 3 to the newly allocated register.
1761         insnCodeGen::generateImm(gen, ORILop, 3, retReg, 0);
1762     }
1763
1764         
1765     // Otherwise we're replacing a call and so we don't want to move
1766     // anything. 
1767
1768     // restore saved registers.
1769     // If inInstrumentation == false then this vector should be empty...
1770         // ALL instrumentation
1771  
1772     if (!inInstrumentation) assert(savedRegs.size() == 0);
1773     for (u_int ui = 0; ui < savedRegs.size(); ui++) {
1774         restoreRegister(gen, savedRegs[ui], FUNC_CALL_SAVE);
1775     }
1776   
1777     // mtlr     0 (aka mtspr 8, rs) = 0x7c0803a6
1778     // Move to link register
1779     // Reused from above. instruction mtlr0(MTLR0raw);
1780     if (needToSaveLR) {
1781         // We only use register 0 to save LR. 
1782         insnCodeGen::generateMoveToLR(gen, 0);
1783     }
1784     
1785     if (!inInstrumentation && setTOC) {
1786         // Need to reset the TOC
1787         emitVload(loadConstOp, caller_toc, 2, 2, gen, false);
1788
1789         // Also store toc_orig [r2] into the TOC save area [40(r1)].
1790         // Subsequent code will look for it there.
1791         saveRegisterAtOffset(gen, 2, 40);
1792     }        
1793
1794     /*
1795       gen = (instruction *) gen;
1796       for (unsigned foo = initBase/4; foo < base/4; foo++)
1797       bperr( "0x%x,\n", gen[foo].raw);
1798     */ 
1799     // return value is the register with the return value from the called function
1800     return(retReg);
1801 }
1802
1803  
1804 codeBufIndex_t emitA(opCode op, Register src1, Register /*src2*/, Register dest,
1805               codeGen &gen, RegControl, bool /*noCost*/)
1806 {
1807     //bperr("emitA(op=%d,src1=%d,src2=XX,dest=%d)\n",op,src1,dest);
1808     codeBufIndex_t retval = 0;
1809     switch (op) {
1810       case ifOp: {
1811         // cmpi 0,0,src1,0
1812           instruction insn;
1813           insn.clear();
1814           DFORM_OP_SET(insn, CMPIop);
1815           DFORM_RA_SET(insn, src1);
1816           DFORM_SI_SET(insn, 0);
1817           insnCodeGen::generate(gen,insn);
1818           retval = gen.getIndex();
1819           
1820           // be 0, dest
1821           insn.clear();
1822           BFORM_OP_SET(insn, BCop);
1823           BFORM_BO_SET(insn, BTRUEcond);
1824           BFORM_BI_SET(insn, EQcond);
1825           BFORM_BD_SET(insn, dest/4);
1826           BFORM_AA_SET(insn, 0);
1827           BFORM_LK_SET(insn, 0);
1828           
1829           insnCodeGen::generate(gen,insn);
1830           break;
1831       }
1832     case branchOp: {
1833         retval = gen.getIndex();
1834         insnCodeGen::generateBranch(gen, dest);
1835         break;
1836     }
1837     case trampPreamble: {
1838         // nothing to do in this platform
1839         return(0);              // let's hope this is expected!
1840     }        
1841     default:
1842         assert(0);        // unexpected op for this emit!
1843     }
1844     return retval;
1845 }
1846
1847 Register emitR(opCode op, Register src1, Register src2, Register dest,
1848                codeGen &gen, bool /*noCost*/,
1849                const instPoint * /*location*/, bool /*for_MT*/)
1850 {
1851     //bperr("emitR(op=%d,src1=%d,src2=XX,dest=%d)\n",op,src1,dest);
1852
1853     registerSlot *regSlot = NULL;
1854     unsigned addrWidth = gen.addrSpace()->getAddressWidth();
1855
1856     switch (op) {
1857     case getRetValOp: {
1858         regSlot = (*(gen.rs()))[registerSpace::r3];
1859         break;
1860     }
1861
1862     case getParamOp: {
1863         // The first 8 parameters (0-7) are stored in registers (r3-r10) upon
1864         // entering the function and then saved above the stack upon entering
1865         // the trampoline; in emit functional call the stack pointer is moved
1866         // so the saved registers are not over-written the other parameters >
1867         // 8 are stored on the caller's stack at an offset.
1868         // 
1869         // src1 is the argument number 0..X, the first 8 are stored in regs
1870         // src2 (if not REG_NULL) holds the value to be written into src1
1871
1872         if(src1 < 8) {
1873             // src1 is 0..8 - it's a parameter number, not a register
1874             regSlot = (*(gen.rs()))[registerSpace::r3 + src1];
1875             break;
1876
1877         } else {
1878             // Registers from 11 (src = 8) and beyond are saved on the stack.
1879             // On AIX this is +56 bytes; for ELF it's something different.
1880
1881             int stkOffset;
1882             if (addrWidth == 4) {
1883                 stkOffset = TRAMP_FRAME_SIZE_32 +
1884                             (src1 - 8) * sizeof(int) +
1885                             PARAM_OFFSET(addrWidth);
1886             } else {
1887                 stkOffset = TRAMP_FRAME_SIZE_64 +
1888                             (src1 - 8) * sizeof(long) +
1889                             PARAM_OFFSET(addrWidth);
1890             }
1891
1892             if (src2 != REG_NULL) saveRegisterAtOffset(gen, src2, stkOffset);
1893             restoreRegisterAtOffset(gen, dest, stkOffset);
1894             return(dest);
1895       }
1896       break;
1897     }
1898
1899     default:
1900         assert(0);
1901         break;
1902     }
1903
1904     assert(regSlot);
1905     Register reg = regSlot->number;
1906
1907     switch(regSlot->liveState) {
1908     case registerSlot::spilled: {
1909         int offset;
1910         if (addrWidth == 4)
1911             offset = TRAMP_GPR_OFFSET_32;
1912         else /* addrWidth == 8 */
1913             offset = TRAMP_GPR_OFFSET_64;
1914
1915         // its on the stack so load it.
1916         if (src2 != REG_NULL) saveRegister(gen, src2, reg, offset);
1917         restoreRegister(gen, reg, dest, offset);
1918         return(dest);
1919     }
1920     case registerSlot::live: {
1921         // its still in a register so return the register it is in.
1922         
1923         return(reg);
1924     }
1925     case registerSlot::dead: {
1926         // Uhhh... wha?
1927         assert(0);
1928     }
1929     }
1930
1931     assert(0);
1932     return REG_NULL;
1933 }
1934
1935 void emitJmpMC(int /*condition*/, int /*offset*/, codeGen &)
1936 {
1937   // Not needed for memory instrumentation, otherwise TBD
1938 }
1939
1940
1941 // VG(11/16/01): Say if we have to restore a register to get its original value
1942 // VG(03/15/02): Sync'd with the new AIX tramp
1943 static inline bool needsRestore(Register x)
1944 {
1945   //return (x == 0) || ((x >= 3) && (x <= 12)) || (x == POWER_XER2531);
1946   return ((x <= 12) && !(x==2)) || (x == POWER_XER2531);
1947 }
1948
1949 // VG(03/15/02): Restore mutatee value of GPR reg to dest GPR
1950 static inline void restoreGPRtoGPR(codeGen &gen,
1951                                    Register reg, Register dest)
1952 {
1953     int frame_size, gpr_size, gpr_off;
1954     if (gen.addrSpace()->getAddressWidth() == 4) {
1955         frame_size = TRAMP_FRAME_SIZE_32;
1956         gpr_size   = GPRSIZE_32;
1957         gpr_off    = TRAMP_GPR_OFFSET_32;
1958     } else /* gen.addrSpace()->getAddressWidth() == 8 */ {
1959         frame_size = TRAMP_FRAME_SIZE_64;
1960         gpr_size   = GPRSIZE_64;
1961         gpr_off    = TRAMP_GPR_OFFSET_64;
1962     }
1963
1964     if (reg == 1) // SP is in a different place, but we don't need to
1965                   // restore it, just subtract the stack frame size
1966         insnCodeGen::generateImm(gen, CALop, dest, REG_SP, frame_size);
1967
1968     else if((reg == 0) || ((reg >= 3) && (reg <=12)))
1969         insnCodeGen::generateImm(gen, Lop, dest, REG_SP,
1970                                  gpr_off + reg*gpr_size);
1971     else {
1972         bperr( "GPR %d should not be restored...", reg);
1973         assert(0);
1974     }
1975     //bperr( "Loading reg %d (into reg %d) at 0x%x off the stack\n", 
1976     //  reg, dest, offset + reg*GPRSIZE);
1977 }
1978
1979 // VG(03/15/02): Restore mutatee value of XER to dest GPR
1980 static inline void restoreXERtoGPR(codeGen &gen, Register dest)
1981 {
1982     if (gen.addrSpace()->getAddressWidth() == 4) {
1983         insnCodeGen::generateImm(gen, Lop, dest, REG_SP,
1984                                  TRAMP_SPR_OFFSET + STK_XER_32);
1985     } else /* gen.addrSpace()->getAddressWidth() == 8 */ {
1986         insnCodeGen::generateMemAccess64(gen, LDop, LDxop, dest, REG_SP,
1987                                          TRAMP_SPR_OFFSET + STK_XER_64);
1988     }
1989 }
1990
1991 // VG(03/15/02): Move bits 25:31 of GPR reg to GPR dest
1992 static inline void moveGPR2531toGPR(codeGen &gen,
1993                                     Register reg, Register dest)
1994 {
1995   // keep only bits 32+25:32+31; extrdi dest, reg, 7 (n bits), 32+25 (start at b)
1996   // which is actually: rldicl dest, reg, 32+25+7 (b+n), 64-7 (64-n)
1997   // which is the same as: clrldi dest,reg,57 because 32+25+7 = 64
1998     instruction rld;
1999     rld.clear();
2000     MDFORM_OP_SET( rld, RLDop);
2001     MDFORM_RS_SET( rld, reg);
2002     MDFORM_RA_SET( rld, dest);
2003     MDFORM_SH_SET( rld, 0);  //(32+25+7) % 32;
2004     MDFORM_MB_SET( rld, (64-7) % 32);
2005     MDFORM_MB2_SET(rld, (64-7) / 32);
2006     MDFORM_XO_SET( rld, ICLxop);
2007     MDFORM_SH2_SET(rld, 0); //(32+25+7) / 32;
2008     MDFORM_RC_SET( rld, 0);
2009     insnCodeGen::generate(gen,rld);
2010 }
2011
2012 // VG(11/16/01): Emit code to add the original value of a register to
2013 // another. The original value may need to be restored from stack...
2014 // VG(03/15/02): Made functionality more obvious by adding the above functions
2015 static inline void emitAddOriginal(Register src, Register acc, 
2016                                    codeGen &gen, bool noCost)
2017 {
2018     bool nr = needsRestore(src);
2019     Register temp;
2020     
2021     if(nr) {
2022         // this needs gen because it uses emitV...
2023         temp = gen.rs()->allocateRegister(gen, noCost);
2024         
2025         // Emit code to restore the original ra register value in temp.
2026         // The offset compensates for the gap 0, 3, 4, ...
2027         // This writes at insn, and updates insn and base.
2028         
2029         if(src == POWER_XER2531) { // hack for XER_25:31
2030             //bperr( "XER_25:31\n");
2031             restoreXERtoGPR(gen, temp);
2032             moveGPR2531toGPR(gen, temp, temp);
2033         }
2034         else
2035             restoreGPRtoGPR(gen, src, temp);
2036     }
2037     else
2038         temp = src;
2039     
2040     // add temp to dest;
2041     // writes at gen+base and updates base, we must update insn...
2042     emitV(plusOp, temp, acc, acc, gen, noCost, 0);
2043     
2044     if(nr)
2045         gen.rs()->freeRegister(temp);
2046 }
2047
2048 // VG(11/07/01): Load in destination the effective address given
2049 // by the address descriptor. Used for memory access stuff.
2050 void emitASload(const BPatch_addrSpec_NP *as, Register dest, codeGen &gen,
2051                 bool noCost)
2052 {
2053   //instruction *insn = (instruction *) ((void*)&gen[base]);
2054   int imm = as->getImm();
2055   int ra  = as->getReg(0);
2056   int rb  = as->getReg(1);
2057   // TODO: optimize this to generate the minimum number of
2058   // instructions; think about schedule
2059
2060   // emit code to load the immediate (constant offset) into dest; this
2061   // writes at gen+base and updates base, we must update insn...
2062   emitVload(loadConstOp, (Address)imm, dest, dest, gen, noCost);
2063   
2064   // If ra is used in the address spec, allocate a temp register and
2065   // get the value of ra from stack into it
2066   if(ra > -1)
2067       emitAddOriginal(ra, dest, gen, noCost);
2068
2069   // If rb is used in the address spec, allocate a temp register and
2070   // get the value of ra from stack into it
2071   if(rb > -1)
2072     emitAddOriginal(rb, dest, gen, noCost);
2073
2074 }
2075
2076 void emitCSload(const BPatch_addrSpec_NP *as, Register dest, codeGen &gen,               
2077                 bool noCost)
2078 {
2079     emitASload(as, dest, gen, noCost);
2080 }
2081
2082 void emitVload(opCode op, Address src1, Register /*src2*/, Register dest,
2083                codeGen &gen, bool /*noCost*/, 
2084                registerSpace * /*rs*/, int size,
2085                const instPoint * /* location */, AddressSpace *proc)
2086 {
2087     if (op == loadConstOp) {
2088         insnCodeGen::loadImmIntoReg(gen, dest, (long)src1);
2089
2090     } else if (op == loadOp) {
2091         insnCodeGen::loadPartialImmIntoReg(gen, dest, (long)src1);
2092
2093         // really load dest, (dest)imm
2094         if (size == 1)
2095             insnCodeGen::generateImm(gen, LBZop, dest, dest, LOW(src1));
2096         else if (size == 2)
2097             insnCodeGen::generateImm(gen, LHZop, dest, dest, LOW(src1));
2098         else if ((size == 4) ||
2099                  (size == 8 && proc->getAddressWidth() == 4)) // Override bogus size
2100             insnCodeGen::generateImm(gen, Lop,   dest, dest, LOW(src1));
2101         else if (size == 8)
2102             insnCodeGen::generateMemAccess64(gen, LDop, LDxop,
2103                                              dest, dest, (int16_t)LOW(src1));
2104         else assert(0 && "Incompatible loadOp size");
2105
2106     } else if (op == loadFrameRelativeOp) {
2107         long offset = (long)src1;
2108         if (gen.addrSpace()->getAddressWidth() == 4)
2109             offset += TRAMP_FRAME_SIZE_32;
2110         else /* gen.addrSpace()->getAddressWidth() == 8 */
2111             offset += TRAMP_FRAME_SIZE_64;
2112
2113         // return the value that is FP offset from the original fp
2114         if (size == 1)
2115             insnCodeGen::generateImm(gen, LBZop, dest, REG_SP, offset);
2116         else if (size == 2)
2117             insnCodeGen::generateImm(gen, LHZop, dest, REG_SP, offset);
2118         else if ((size == 4) ||
2119                  (size == 8 && proc->getAddressWidth() == 4)) // Override bogus size
2120             insnCodeGen::generateImm(gen, Lop,   dest, REG_SP, offset);
2121         else if (size == 8)
2122             insnCodeGen::generateMemAccess64(gen, LDop, LDxop,
2123                                              dest, REG_SP, offset);
2124         else assert(0 && "Incompatible loadFrameRelativeOp size");
2125
2126     } else if (op == loadFrameAddr) {
2127         // offsets are signed!
2128         long offset = (long)src1;
2129         offset += (gen.addrSpace()->getAddressWidth() == 4 ? TRAMP_FRAME_SIZE_32
2130                                                       : TRAMP_FRAME_SIZE_64);
2131
2132         if (offset < MIN_IMM16 || MAX_IMM16 < offset) assert(0);
2133         insnCodeGen::generateImm(gen, CALop, dest, REG_SP, offset);
2134
2135     } else {
2136         assert(0);
2137     }
2138 }
2139
2140 void emitVstore(opCode op, Register src1, Register /*src2*/, Address dest,
2141                 codeGen &gen, bool noCost, 
2142                 registerSpace * /* rs */, int size,
2143                 const instPoint * /* location */, AddressSpace *proc)
2144 {
2145     if (op == storeOp) {
2146         // temp register to hold base address for store (added 6/26/96 jkh)
2147         Register temp = gen.rs()->getScratchRegister(gen, noCost);
2148
2149         insnCodeGen::loadPartialImmIntoReg(gen, temp, (long)dest);
2150         if (size == 1)
2151             insnCodeGen::generateImm(gen, STBop, src1, temp, LOW(dest));
2152         else if (size == 2)
2153             insnCodeGen::generateImm(gen, STHop, src1, temp, LOW(dest));
2154         else if ((size == 4) ||
2155                  (size == 8 && proc->getAddressWidth() == 4)) // Override bogus size
2156             insnCodeGen::generateImm(gen, STop,  src1, temp, LOW(dest));
2157         else if (size == 8)
2158             insnCodeGen::generateMemAccess64(gen, STDop, STDxop,
2159                                              src1, temp, (int16_t)BOT_LO(dest));
2160         else assert(0 && "Incompatible storeOp size");
2161
2162     } else if (op == storeFrameRelativeOp) {
2163         long offset = (long)dest;
2164         offset += (gen.addrSpace()->getAddressWidth() == 4
2165                    ? TRAMP_FRAME_SIZE_32
2166                    : TRAMP_FRAME_SIZE_64);
2167
2168         if (size == 1)
2169             insnCodeGen::generateImm(gen, STBop, src1, REG_SP, offset);
2170         else if (size == 2)
2171             insnCodeGen::generateImm(gen, STHop, src1, REG_SP, offset);
2172         else if ((size == 4) ||
2173                  (size == 8 || proc->getAddressWidth() == 4)) // Override bogus size
2174             insnCodeGen::generateImm(gen, STop,  src1, REG_SP, offset);
2175         else if (size == 8)
2176             insnCodeGen::generateMemAccess64(gen, STDop, STDxop, src1,
2177                                              REG_SP, offset);
2178         else assert(0 && "Incompatible storeFrameRelativeOp size");
2179
2180     } else assert(0 && "Unknown op passed to emitVstore");
2181 }
2182
2183 void emitV(opCode op, Register src1, Register src2, Register dest,
2184            codeGen &gen, bool /*noCost*/,
2185            registerSpace * /*rs*/, int size,
2186            const instPoint * /* location */, AddressSpace *proc)
2187 {
2188     //bperr("emitV(op=%d,src1=%d,src2=%d,dest=%d)\n",op,src1,src2,dest);
2189
2190     assert ((op!=branchOp) && (op!=ifOp) && 
2191             (op!=trampPreamble));         // !emitA
2192     assert ((op!=getRetValOp) && (op!=getParamOp));             // !emitR
2193     assert ((op!=loadOp) && (op!=loadConstOp));                 // !emitVload
2194     assert ((op!=storeOp));                                     // !emitVstore
2195     assert ((op!=updateCostOp));                                // !emitVupdate
2196
2197     instruction insn;
2198
2199     if (op == loadIndirOp) {
2200        // really load dest, (dest)imm
2201        assert(src2 == 0); // Since we don't use it.
2202        if (!size)
2203           size = proc->getAddressWidth();
2204        if (size == 1)
2205           insnCodeGen::generateImm(gen, LBZop, dest, src1, 0);
2206        else if (size == 2)
2207           insnCodeGen::generateImm(gen, LHZop, dest, src1, 0);
2208        else if ((size == 4) ||
2209                 (size == 8 && proc->getAddressWidth() == 4)) // Override bogus size
2210           insnCodeGen::generateImm(gen, Lop,   dest, src1, 0);
2211        else if (size == 8) {
2212           insnCodeGen::generateMemAccess64(gen, LDop, LDxop,
2213                                            dest, src1, 0);
2214        } 
2215        else 
2216           assert(0 && "Incompatible loadOp size");
2217     } else if (op == storeIndirOp) {
2218         // generate -- st src1, dest
2219         if (size == 1)
2220             insnCodeGen::generateImm(gen, STBop, src1, dest, 0);
2221         else if (size == 2)
2222             insnCodeGen::generateImm(gen, STHop, src1, dest, 0);
2223         else if ((size == 4) ||
2224                  (size == 8 && proc->getAddressWidth() == 4)) // Override bogus size
2225             insnCodeGen::generateImm(gen, STop,  src1, dest, 0);
2226         else if (size == 8)
2227             insnCodeGen::generateMemAccess64(gen, STDop, STDxop,
2228                                              src1, dest, 0);
2229         else assert(0 && "Incompatible storeOp size");
2230
2231     } else if (op == noOp) {
2232         insnCodeGen::generateNOOP(gen);
2233
2234     } else if (op == saveRegOp) {
2235         saveRegister(gen,src1,8);
2236
2237     } else {
2238         int instXop=-1;
2239         int instOp=-1;
2240         switch (op) {
2241             // integer ops
2242             case plusOp:
2243                 instOp = CAXop;
2244                 instXop = CAXxop;
2245                 break;
2246
2247             case minusOp:
2248                 Register temp;
2249                 // need to flip operands since this computes ra-rb not rb-ra
2250                 temp = src1;
2251                 src1 = src2;
2252                 src2 = temp;
2253                 instOp = SFop;
2254                 instXop = SFxop;
2255                 break;
2256
2257             case timesOp:
2258                 instOp = MULSop;
2259                 instXop = MULSxop;
2260                 break;
2261
2262             case divOp:
2263                 instOp = DIVSop;   // POWER divide instruction
2264                                    // Same as DIVWop for PowerPC
2265 #if defined(os_aix)                // Should use runtime CPU detection ...
2266                 if (gen.addrSpace()->getAddressWidth() == 8)
2267                     instXop = DIVWxop; // divs instruction deleted on 64-bit
2268                 else
2269                     instXop = DIVSxop;
2270 #else
2271                 instXop = DIVWxop; // PowerPC
2272 #endif
2273                 break;
2274
2275             // Bool ops
2276             case orOp:
2277                 //genSimple(gen, ORop, src1, src2, dest);
2278                 insn.clear();
2279                 XOFORM_OP_SET(insn, ORop);
2280                 // operation is ra <- rs | rb (or rs,ra,rb)
2281                 XOFORM_RA_SET(insn, dest);
2282                 XOFORM_RT_SET(insn, src1);
2283                 XOFORM_RB_SET(insn, src2);
2284                 XOFORM_XO_SET(insn, ORxop);
2285                 insnCodeGen::generate(gen,insn);
2286                 return;
2287                 break;
2288
2289             case andOp:
2290                 //genSimple(gen, ANDop, src1, src2, dest);
2291                 // This is a Boolean and with true == 1 so bitwise is OK
2292                 insn.clear();
2293                 XOFORM_OP_SET(insn, ANDop);
2294                 // operation is ra <- rs & rb (and rs,ra,rb)
2295                 XOFORM_RA_SET(insn, dest);
2296                 XOFORM_RT_SET(insn, src1);
2297                 XOFORM_RB_SET(insn, src2);
2298                 XOFORM_XO_SET(insn, ANDxop);
2299                 insnCodeGen::generate(gen,insn);
2300                 return;
2301                 break;
2302
2303             // rel ops
2304             case eqOp:
2305                 insnCodeGen::generateRelOp(gen, EQcond, BTRUEcond, src1, src2, dest);
2306                 return;
2307                 break;
2308
2309             case neOp:
2310                 insnCodeGen::generateRelOp(gen, EQcond, BFALSEcond, src1, src2, dest);
2311                 return;
2312                 break;
2313
2314             case lessOp:
2315                 insnCodeGen::generateRelOp(gen, LTcond, BTRUEcond, src1, src2, dest);
2316                 return;
2317                 break;
2318
2319             case greaterOp:
2320                 insnCodeGen::generateRelOp(gen, GTcond, BTRUEcond, src1, src2, dest);
2321                 return;
2322                 break;
2323
2324             case leOp:
2325                 insnCodeGen::generateRelOp(gen, GTcond, BFALSEcond, src1, src2, dest);
2326                 return;
2327                 break;
2328
2329             case geOp:
2330                 insnCodeGen::generateRelOp(gen, LTcond, BFALSEcond, src1, src2, dest);
2331                 return;
2332                 break;
2333
2334             default:
2335                 // internal error, invalid op.
2336                 bperr( "Invalid op passed to emit, instOp = %d\n", instOp);
2337                 assert(0 && "Invalid op passed to emit");
2338                 break;
2339         }
2340
2341         
2342         assert((instOp != -1) && (instXop != -1));
2343         insn.clear();
2344         XOFORM_OP_SET(insn, instOp);
2345         XOFORM_RT_SET(insn, dest);
2346         XOFORM_RA_SET(insn, src1);
2347         XOFORM_RB_SET(insn, src2);
2348         XOFORM_XO_SET(insn, instXop);
2349         insnCodeGen::generate(gen,insn);
2350     }
2351   return;
2352 }
2353
2354
2355 //
2356 // I don't know how to compute cycles for POWER instructions due to 
2357 //   multiple functional units.  However, we can compute the number of
2358 //   instructions and hope that is fairly close. - jkh 1/30/96
2359 //
2360 int getInsnCost(opCode op)
2361   {
2362     int cost = 0;
2363
2364     /* XXX Need to add branchOp */
2365     switch (op) {
2366       
2367     case noOp:
2368     case loadIndirOp:
2369     case saveRegOp:
2370
2371       // worse case is it is on the stack and takes one instruction.
2372     case getParamOp:
2373
2374       // integer ops
2375     case plusOp:
2376     case minusOp:
2377     case timesOp:
2378     case divOp:
2379       cost = 1;
2380       break;
2381
2382     case loadConstOp:
2383       // worse case is addi followed by ori
2384
2385     case loadOp:
2386       // addis, l
2387       
2388     case storeOp:
2389     case storeIndirOp:
2390       cost = 2;
2391       break;
2392
2393     case ifOp:
2394       // cmpi 0,0,src1,0
2395       // be 0, dest
2396       // nop
2397       cost = 3;
2398       break;
2399
2400       // rel ops
2401     case eqOp:
2402     case neOp:
2403     case lessOp:
2404     case greaterOp:
2405     case leOp:
2406     case geOp:
2407       cost = 4;
2408       break;
2409       
2410     case callOp:
2411       // mflr r0
2412       // st r0, (r1)
2413       cost += 2;
2414       
2415       // Should compute the cost to save registers here.  However, we lack 
2416       //   sufficient information to compute this value. We need to be 
2417       //   inside the code generator to know this amount.
2418       //
2419       // We know it is at *least* every live register (i.e. parameter reg)
2420       cost += 13;
2421       
2422       // clr r5
2423       // clr r6
2424       // decrement stack pointer -- STUop
2425       // load r0 with address, then move to link reg and branch and link.
2426       // ori dest,dest,LOW(src1)
2427       // mtlr   0 (aka mtspr 8, rs) = 0x7c0803a6
2428       // brl - branch and link through the link reg.
2429       cost += 7;
2430       
2431       // now cleanup.
2432       
2433       // increment stack pointer -- CALop
2434       // restore the saved register 0.
2435       cost += 2;
2436       
2437       // Should compute the cost to restore registers here.  However, we lack 
2438       //   sufficient information to compute this value. We need to be 
2439       //   inside the code generator to know this amount.
2440       //
2441       // We know it is at *least* every live register (i.e. parameter reg)
2442       cost += 13;
2443       
2444       // mtlr   0 
2445       cost++;
2446       break;
2447
2448     case updateCostOp:
2449       // In most cases this cost is 4, but if we can't use CALop because
2450       // the value is to large, then we'll need 2 additional operations to
2451       // load that value - naim
2452       // Why the +=? Isn't it equivalent to an = here? -- bernat
2453       cost += 4;
2454       break;
2455       
2456     case trampPreamble:
2457       // Generate code to update the observed cost.
2458       // generated code moved to the base trampoline.
2459       cost += 0;
2460       break;
2461
2462     default:
2463       cost = 0;
2464       break;
2465     }
2466     return (cost);
2467 }
2468
2469 #if 0
2470 // What does this do???
2471 void registerSpace::saveClobberInfo(const instPoint *location)
2472 {
2473   registerSlot *regSlot = NULL;
2474   registerSlot *regFPSlot = NULL;
2475   if (location == NULL)
2476     return;
2477   if (location->actualGPRLiveSet_ != NULL && location->actualFPRLiveSet_ != NULL)
2478     {
2479       
2480       // REG guard registers, if live, must be saved
2481       if (location->actualGPRLiveSet_[ REG_GUARD_ADDR ] == LIVE_REG)
2482         location->actualGPRLiveSet_[ REG_GUARD_ADDR ] = LIVE_CLOBBERED_REG;
2483       
2484       if (location->actualGPRLiveSet_[ REG_GUARD_OFFSET ] == LIVE_REG)
2485         location->actualGPRLiveSet_[ REG_GUARD_OFFSET ] = LIVE_CLOBBERED_REG;
2486
2487       // GPR and FPR scratch registers, if live, must be saved
2488       if (location->actualGPRLiveSet_[ REG_SCRATCH ] == LIVE_REG)
2489         location->actualGPRLiveSet_[ REG_SCRATCH ] = LIVE_CLOBBERED_REG;
2490
2491       if (location->actualFPRLiveSet_[ REG_SCRATCH ] == LIVE_REG)
2492         location->actualFPRLiveSet_[ REG_SCRATCH ] = LIVE_CLOBBERED_REG;
2493
2494       // Return func call register, since we make a call because
2495       // of multithreading (regardless if it's threaded) from BT
2496       // we must save return register
2497       if (location->actualGPRLiveSet_[ 3 ] == LIVE_REG)
2498         location->actualGPRLiveSet_[ 3 ] = LIVE_CLOBBERED_REG;
2499
2500     
2501       for (u_int i = 0; i < getRegisterCount(); i++)
2502         {
2503           regSlot = getRegSlot(i);
2504
2505           if (  location->actualGPRLiveSet_[ (int) registers[i].number ] == LIVE_REG )
2506             {
2507               if (!registers[i].beenClobbered)
2508                 location->actualGPRLiveSet_[ (int) registers[i].number ] = LIVE_UNCLOBBERED_REG;
2509               else
2510                 location->actualGPRLiveSet_[ (int) registers[i].number ] = LIVE_CLOBBERED_REG;
2511             }
2512
2513
2514           if (  location->actualGPRLiveSet_[ (int) registers[i].number ] == LIVE_UNCLOBBERED_REG ) 
2515             {
2516               if (registers[i].beenClobbered)
2517                 location->actualGPRLiveSet_[ (int) registers[i].number ] = LIVE_CLOBBERED_REG;
2518             }
2519         }
2520           
2521       for (u_int i = 0; i < getFPRegisterCount(); i++)
2522         {
2523           regFPSlot = getFPRegSlot(i);
2524           
2525           if (  location->actualFPRLiveSet_[ (int) fpRegisters[i].number ] == LIVE_REG )
2526             {
2527               if (!fpRegisters[i].beenClobbered)
2528                 location->actualFPRLiveSet_[ (int) fpRegisters[i].number ] = LIVE_UNCLOBBERED_REG;
2529               else
2530                 location->actualFPRLiveSet_[ (int) fpRegisters[i].number ] = LIVE_CLOBBERED_REG;
2531             }
2532           
2533           if (  location->actualFPRLiveSet_[ (int) fpRegisters[i].number ] == LIVE_UNCLOBBERED_REG )
2534             {
2535               if (fpRegisters[i].beenClobbered)
2536                 location->actualFPRLiveSet_[ (int) fpRegisters[i].number ] = LIVE_CLOBBERED_REG;
2537             }
2538         }
2539     }
2540 }
2541 #endif
2542
2543
2544 bool doNotOverflow(int value)
2545 {
2546   // we are assuming that we have 15 bits to store the immediate operand.
2547   if ( (value <= 32767) && (value >= -32768) ) return(true);
2548   else return(false);
2549 }
2550
2551 #if defined (os_aix)
2552 // hasBeenBound: returns false
2553 // On AIX (at least what we handle so far), all symbols are bound
2554 // at load time. This kind of obviates the need for a hasBeenBound
2555 // function: of _course_ the symbol has been bound. 
2556 // So the idea of having a relocation entry for the function doesn't
2557 // quite make sense. Given the target address, we can scan the function
2558 // lists until we find the desired function.
2559
2560 bool process::hasBeenBound(const SymtabAPI::relocationEntry &,int_function *&, Address ) {
2561   // What needs doing:
2562   // Locate call instruction
2563   // Decipher call instruction (static/dynamic call, global linkage code)
2564   // Locate target
2565   // Lookup target
2566   return false; // Haven't patched this up yet
2567 }
2568 #else
2569 // hasBeenBound: returns true if the runtime linker has bound the
2570 // function symbol corresponding to the relocation entry in at the address
2571 // specified by entry and base_addr.  If it has been bound, then the callee 
2572 // function is returned in "target_pdf", else it returns false.
2573 bool process::hasBeenBound(const SymtabAPI::relocationEntry &entry, 
2574                 int_function *&target_pdf, Address base_addr) 
2575 {
2576
2577         if (status() == exited) return false;
2578
2579         // if the relocationEntry has not been bound yet, then the value
2580         // at rel_addr is the address of the instruction immediately following
2581         // the first instruction in the PLT entry (which is at the target_addr) 
2582         // The PLT entries are never modified, instead they use an indirrect 
2583         // jump to an address stored in the _GLOBAL_OFFSET_TABLE_.  When the 
2584         // function symbol is bound by the runtime linker, it changes the address
2585         // in the _GLOBAL_OFFSET_TABLE_ corresponding to the PLT entry
2586
2587         Address got_entry = entry.rel_addr() + base_addr;
2588         Address bound_addr = 0;
2589         if (!readDataSpace((const void*)got_entry, sizeof(Address),
2590                                 &bound_addr, true)){
2591                 sprintf(errorLine, "read error in process::hasBeenBound addr 0x%x, pid=%d\n (readDataSpace returns 0)",(unsigned)got_entry,getPid());
2592                 logLine(errorLine);
2593                 //print_read_error_info(entry, target_pdf, base_addr);
2594                 fprintf(stderr, "%s[%d]: %s\n", FILE__, __LINE__, errorLine);
2595                 return false;
2596         }
2597
2598    //fprintf(stderr, "%s[%d]:  hasBeenBound:  %p ?= %p ?\n", FILE__, __LINE__, bound_addr, entry.target_addr() + 6 + base_addr);
2599         if ( !( bound_addr == (entry.target_addr()+6+base_addr)) ) {
2600                 // the callee function has been bound by the runtime linker
2601                 // find the function and return it
2602                 target_pdf = findFuncByAddr(bound_addr);
2603                 if(!target_pdf){
2604                         return false;
2605                 }
2606                 return true;
2607         }
2608         return false;
2609 }
2610
2611 #endif
2612
2613 // Emit code to jump to function CALLEE without linking.  (I.e., when
2614 // CALLEE returns, it returns to the current caller.)
2615
2616 void emitFuncJump(opCode             , 
2617                   codeGen            &gen,
2618                   int_function *func,
2619                   AddressSpace       *proc,
2620                   const instPoint    *point,
2621                   bool)
2622 {
2623     // POWER (for both Linux and AIX) is using the new instruction replacement
2624     // based method for replacing a function jump, and therefore we are 
2625     // *NOT* in a base tramp when this occurs.
2626
2627     assert(func);
2628     assert(point);
2629
2630     // Which means we don't need to unwind a baseTramp.
2631
2632     // We have two function call ABIs. 
2633     // 1) AIX (32/64), Linux (64)
2634     //   * GPR 2 is the TOC, which is module-specific.
2635     //   * The stack frame has two empty words at (SP + 3W) and (SP + 4W)
2636     //     where W = 4 or 8
2637     //   * We need to reset the TOC post-call, which means we need
2638     //     to _return_ to after the call. Thus the link register also
2639     //     needs to be saved.
2640     //
2641     // 2) Linux (32)
2642     //   * There is no TOC (r2 is a "system reserved register").
2643     //   * Thus we don't need to set or restore the TOC. 
2644     //   * Thus all we need to do is branch to the destination function.
2645
2646     bool is64 = false;
2647     if (gen.addrSpace()->getAddressWidth() == 8)
2648         is64 = true;
2649
2650     bool needToSetTOC = false;
2651     Address currentTOC = 0;
2652     Address replacementTOC = 0;
2653     if(proc->proc()) {
2654         currentTOC = proc->proc()->getTOCoffsetInfo(point->func());
2655         replacementTOC = proc->proc()->getTOCoffsetInfo(const_cast<int_function *>(func));
2656
2657         if (currentTOC &&
2658             (currentTOC != replacementTOC)) {
2659                 needToSetTOC = true;
2660         }
2661
2662     }
2663
2664     // If we either don't have a TOC (32-bit Linux, currentTOC == 0)
2665     // or the new TOC is the same as the current, just branch.
2666
2667     if (!needToSetTOC) {
2668         if (proc->proc()) {
2669         // Easy case, just branch.
2670         insnCodeGen::generateInterFunctionBranch(gen,
2671                                                  gen.currAddr(),
2672                                                  func->getAddress());
2673         } else  { // binary rewriter case       
2674     instPoint *point = gen.point();
2675     if (!point) {
2676         printf(" Point NOT AVAILABLE. We cannot instrument this point. skipping ...\n");
2677         return;
2678     }
2679     assert(point);
2680     bitArray liveRegs = point->liveRegisters(callPreInsn);
2681     if (liveRegs[registerSpace::ctr] == true)
2682     {
2683         printf(" COUNT REGISTER NOT AVAILABLE. We cannot instrument this point. skipping ...\n");
2684         return;
2685     }
2686
2687     if (gen.func()->obj() == func->obj()) {     
2688         inst_printf("same module name %s \n", gen.func()->obj()->fileName().c_str());
2689     insnCodeGen::loadImmIntoReg(gen, 0, func->getAddress());
2690     insnCodeGen::generateMoveToCR(gen, 0);
2691
2692     gen.bti()->baseT->generateRestores(gen, gen.rs(), NULL);
2693     // And branch to CTR
2694     instruction btctr(BCTRraw);
2695     insnCodeGen::generate(gen,btctr);
2696
2697         } else {
2698                 Register scratchPCReg = gen.rs()->getScratchRegister(gen, true);
2699                 assert (scratchPCReg != REG_NULL);
2700                 insnCodeGen::generateBranch(gen, gen.currAddr(),  gen.currAddr()+4, true); // blrl
2701                 insnCodeGen::generateMoveFromLR(gen, scratchPCReg); // mflr
2702
2703                 pdvector<Register> excludeReg;
2704                 excludeReg.push_back(scratchPCReg);
2705                 Register scratchReg = gen.rs()->getScratchRegister(gen, excludeReg, true);      
2706                 assert (scratchReg != REG_NULL);
2707
2708                 Address dest = gen.codeEmitter()->getInterModuleFuncAddr(func, gen);
2709                 Address varOffset = dest - gen.currAddr()+4;
2710
2711                 inst_printf("diff module names %s %s dest 0x%lx offset 0x%lx\n", gen.func()->obj()->fileName().c_str(), func->obj()->fileName().c_str(), dest, varOffset);
2712
2713                 insnCodeGen::generateImm (gen, CAUop, scratchReg, 0, BOT_HI (varOffset));
2714                 insnCodeGen::generateImm (gen, ORILop, scratchReg, scratchReg, BOT_LO (varOffset));
2715                 insnCodeGen::generateLoadReg (gen, LXop, scratchReg, scratchReg, scratchPCReg);
2716                 //insnCodeGen::generateAddReg (gen, CAXop, scratchReg, scratchReg, scratchPCReg);
2717                 insnCodeGen::generateMoveToCR(gen, scratchReg);
2718
2719                 // Make sure we do not "restore" Count Register
2720                 gen.bti()->baseT->generateRestores(gen, gen.rs(), NULL);
2721                 instruction btctr(BCTRraw);
2722                 insnCodeGen::generate(gen,btctr);
2723         }
2724
2725         }
2726         return;
2727     }
2728     
2729     // Hard case...
2730     // 
2731     // Sketch of operations:
2732     //   Save current TOC at SP + 3W
2733     //   Save current LR at SP + 4W
2734     //   Set up new branch target in LR
2735     //   Set up new TOC
2736     //   Call
2737     //   Restore TOC
2738     //   Restore LR
2739
2740     // Save TOC
2741     saveRegisterAtOffset(gen, 2, 3*gen.addrSpace()->getAddressWidth());
2742     
2743     // Use TOC to access and save LR
2744     insnCodeGen::generateMoveFromLR(gen, 2);
2745     saveRegisterAtOffset(gen, 2, 4*gen.addrSpace()->getAddressWidth());
2746
2747     // Assign new LR for branch. 
2748     emitVload(loadConstOp, func->getAddress(), 2, 2, gen, false);
2749     insnCodeGen::generateMoveToLR(gen, 2);
2750
2751     // Assign new TOC
2752     emitVload(loadConstOp, replacementTOC, 2, 2, gen, false);
2753
2754     // Call
2755     instruction brl(BRLraw);
2756     insnCodeGen::generate(gen,brl);
2757
2758     // We're done with the replacement function, so restore TOC, LR, return
2759     
2760     // Load LR from SP + 4W to TOC
2761     restoreRegisterAtOffset(gen, 2, 4*gen.addrSpace()->getAddressWidth());
2762     insnCodeGen::generateMoveToLR(gen, 2);
2763     
2764     // Load TOC from SP + 3W
2765     restoreRegisterAtOffset(gen, 2, 3*gen.addrSpace()->getAddressWidth());
2766
2767     // Make sure we do not "restore" Count Register
2768     gen.bti()->baseT->generateRestores(gen, gen.rs(), NULL);
2769
2770     // Return...
2771     instruction br(BRraw);
2772     insnCodeGen::generate(gen,br);
2773     
2774     // Should be done.
2775     return;
2776 }
2777
2778 void emitLoadPreviousStackFrameRegister(Address register_num, 
2779                                         Register dest,
2780                                         codeGen &gen,
2781                                         int /*size*/,
2782                                         bool noCost)
2783 {
2784     // As of 10/24/2007, the size parameter is still incorrect.
2785     // Luckily, we know implicitly what size they actually want.
2786
2787     // Offset if needed
2788     int offset;
2789     // Unused, 3OCT03
2790     //instruction *insn_ptr = (instruction *)insn;
2791     // We need values to define special registers.
2792
2793     switch ( (int) register_num) {
2794     case registerSpace::lr:
2795         // LR is saved on the stack
2796         // Note: this is only valid for non-function entry/exit instru. 
2797         // Once we've entered a function, the LR is stomped to point
2798         // at the exit tramp!
2799         offset = TRAMP_SPR_OFFSET + STK_LR; 
2800
2801         // Get address (SP + offset) and stick in register dest.
2802         emitImm(plusOp ,(Register) REG_SP, (RegValue) offset, dest,
2803                 gen, noCost, gen.rs());
2804         // Load LR into register dest
2805         emitV(loadIndirOp, dest, 0, dest, gen, noCost, gen.rs(),
2806               gen.addrSpace()->getAddressWidth(), gen.point(), gen.addrSpace());
2807         break;
2808
2809     case registerSpace::ctr:
2810         // CTR is saved down the stack
2811         if (gen.addrSpace()->getAddressWidth() == 4)
2812             offset = TRAMP_SPR_OFFSET + STK_CTR_32;
2813         else
2814             offset = TRAMP_SPR_OFFSET + STK_CTR_64;
2815
2816         // Get address (SP + offset) and stick in register dest.
2817         emitImm(plusOp ,(Register) REG_SP, (RegValue) offset, dest,
2818                 gen, noCost, gen.rs());
2819         // Load LR into register dest
2820         emitV(loadIndirOp, dest, 0, dest, gen, noCost, gen.rs(),
2821               gen.addrSpace()->getAddressWidth(), gen.point(), gen.addrSpace());
2822       break;
2823
2824     default:
2825         cerr << "Fallthrough in emitLoadPreviousStackFrameRegister" << endl;
2826         cerr << "Unexpected register " << register_num << endl;
2827         assert(0);
2828         break;
2829     }
2830 }
2831
2832 void emitStorePreviousStackFrameRegister(Address,
2833                                          Register,
2834                                          codeGen &,
2835                                          int,
2836                                          bool) {
2837     assert(0);
2838 }
2839
2840 using namespace Dyninst::InstructionAPI; 
2841 bool AddressSpace::getDynamicCallSiteArgs(instPoint *callSite,
2842                                     pdvector<AstNodePtr> &args)
2843 {
2844
2845     const Instruction::Ptr i = callSite->insn();
2846     Register branch_target = registerSpace::ignored;
2847
2848     // Is this a branch conditional link register (BCLR)
2849     // BCLR uses the xlform (6,5,5,5,10,1)
2850     for(Instruction::cftConstIter curCFT = i->cft_begin();
2851         curCFT != i->cft_end();
2852         ++curCFT)
2853     {
2854         if(*(curCFT->target) == RegisterAST(ppc32::ctr))
2855         {
2856             branch_target = registerSpace::ctr;
2857             break;
2858         }
2859         else if(*(curCFT->target) == RegisterAST(ppc32::lr))
2860         {
2861             branch_target = registerSpace::lr;
2862             break;
2863         }
2864     }
2865     if(branch_target != registerSpace::ignored)
2866     {
2867         // Where we're jumping to (link register, count register)
2868         args.push_back( AstNode::operandNode(AstNode::origRegister,
2869                         (void *) branch_target));
2870
2871         // Where we are now
2872         args.push_back( AstNode::operandNode(AstNode::Constant,
2873                         (void *) callSite->addr()));
2874
2875         return true;
2876     }
2877     else
2878     {
2879         return false;
2880     }
2881 }
2882
2883 bool writeFunctionPtr(AddressSpace *p, Address addr, int_function *f)
2884 {
2885 #if defined(os_aix)
2886     Address buffer[3];
2887     Address val_to_write = f->getAddress();
2888     Address toc = p->proc()->getTOCoffsetInfo(val_to_write);
2889     buffer[0] = val_to_write;
2890     buffer[1] = toc;
2891     buffer[2] = 0x0;
2892
2893     if (!p->writeDataSpace((void *) addr, sizeof(buffer), buffer))
2894         fprintf(stderr, "%s[%d]:  writeDataSpace failed\n", FILE__, __LINE__);
2895     return true;
2896 #else
2897     // 64-bit ELF PowerPC Linux uses r2 (same as AIX) for TOC base register
2898     if (p->getAddressWidth() == sizeof(uint64_t)) {
2899         Address buffer[3];
2900         Address val_to_write = f->getAddress();
2901         // Use function descriptor address, if available.
2902         if (f->getPtrAddress()) val_to_write = f->getPtrAddress();
2903         assert(p->proc());
2904         Address toc = p->proc()->getTOCoffsetInfo(val_to_write);
2905         buffer[0] = val_to_write;
2906         buffer[1] = toc;
2907         buffer[2] = 0x0;
2908
2909         if (!p->writeDataSpace((void *) addr, sizeof(buffer), buffer))
2910             fprintf(stderr, "%s[%d]:  writeDataSpace failed\n",
2911                             FILE__, __LINE__);
2912         return true;
2913     }
2914     else {
2915         // Originally copied from inst-x86.C
2916         // 32-bit ELF PowerPC Linux mutatee
2917         uint32_t val_to_write = (uint32_t)f->getAddress();
2918         return p->writeDataSpace((void *) addr,
2919                                  sizeof(val_to_write), &val_to_write);
2920     }
2921 #endif
2922 }
2923
2924 Emitter *AddressSpace::getEmitter() 
2925 {
2926     static EmitterPOWER32Dyn emitter32Dyn;
2927     static EmitterPOWER64Dyn emitter64Dyn;
2928     static EmitterPOWER32Stat emitter32Stat;
2929     static EmitterPOWER64Stat emitter64Stat;
2930
2931     if (getAddressWidth() == 8) {
2932         if (proc()) {
2933             return &emitter64Dyn;
2934         }
2935         else return &emitter64Stat;
2936     }
2937     if (proc())
2938         return &emitter32Dyn;
2939     else
2940         return &emitter32Stat;
2941
2942     assert(0);
2943     return NULL;
2944 }
2945
2946 #define GET_IP      0x429f0005
2947 #define MFLR_30     0x7fc802a6
2948 #define ADDIS_30_30 0x3fde0000
2949 #define ADDI_30_30  0x3bde0000
2950 #define LWZ_11_30   0x817e0000
2951 #define ADDIS_11_30 0x3d7e0000
2952
2953 /*
2954  * If the target stub_addr is a glink stub, try to determine the actual
2955  * function called (through the GOT) and fill in that information.
2956  *
2957  * The function at stub_addr may not have been created when this method
2958  * is called.
2959  *
2960  * XXX Is this a candidate to move into general parsing code, or is
2961  *     this properly a Dyninst-only technique?
2962  */
2963 bool image::updatePltFunc(image_func *caller_func, Address stub_addr)
2964 {
2965     unsigned int *stub;
2966     Address got2 = 0;
2967
2968     if(!getPltFuncs())
2969         return false;
2970
2971     // If we're calling an empty glink stub.
2972     if ( pltFuncs->defines(stub_addr) && (*pltFuncs)[stub_addr] == "@plt") 
2973     {
2974         int state = 0;
2975
2976         // Find GOT2 value
2977         ParseAPI::Function::blocklist & bl = caller_func->blocks();
2978         ParseAPI::Function::blocklist::iterator bit = bl.begin();
2979         for( ; bit != bl.end(); ++bit) {
2980           ParseAPI::Block * b = *bit;
2981           for(Address addr = b->start(); addr < b->end();
2982               addr += instruction::size()) // XXX 4
2983           {
2984             unsigned int * caller_insn = 
2985                 (unsigned int *)caller_func->isrc()->getPtrToInstruction(addr);
2986
2987             if (state == 0 && *caller_insn == GET_IP) {
2988                 got2 = addr + instruction::size();
2989                 ++state;
2990             } else if (state == 1 && *caller_insn == MFLR_30) {
2991                 ++state;
2992             } else if (state == 4) {
2993                 break;
2994             } 
2995             else if (state >= 2 && (*caller_insn & 0xffff0000) == ADDIS_30_30)
2996             {
2997                 got2 += ((signed short)(*caller_insn & 0x0000ffff)) << 16;
2998                 ++state;
2999             } 
3000             else if (state >= 2 && (*caller_insn & 0xffff0000) == ADDI_30_30)
3001             {
3002                 got2 += (signed short)(*caller_insn & 0x0000ffff);
3003                 ++state;
3004             }
3005           }
3006         }
3007         if (state != 4) return false;
3008
3009         // Find stub offset
3010         stub = (unsigned int *)
3011             caller_func->isrc()->getPtrToInstruction(stub_addr);
3012         int offset = 0;
3013         if ( (stub[0] & 0xffff0000) == LWZ_11_30) {
3014             offset = (signed short)(stub[0] & 0x0000ffff);
3015         } else if ( (stub[0] & 0xffff0000) == ADDIS_11_30) {
3016             offset &= (stub[0] & 0x0000ffff) << 16;
3017             offset &= (stub[1] & 0x0000ffff);
3018         }
3019
3020         // Update all PLT based structures
3021         Address plt_addr = got2 + offset;
3022         (*pltFuncs)[stub_addr] = (*pltFuncs)[plt_addr];
3023         getObject()->updateFuncBindingTable(stub_addr, plt_addr);
3024     }
3025     return true;
3026 }
3027
3028 bool EmitterPOWER::emitCallRelative(Register dest, Address offset, Register base, codeGen &gen){
3029     // Loads a saved register from the stack. 
3030     int imm = offset;
3031     if (gen.addrSpace()->getAddressWidth() == 4) {
3032       if (((signed)MIN_IMM16 <= (signed)imm) && ((signed)imm <= (signed)MAX_IMM16))
3033         {
3034           insnCodeGen::generateImm (gen, CALop, dest, base, imm);
3035
3036         }
3037       else if (((signed)MIN_IMM32 <= (signed)imm) && ((signed)imm <= (signed)MAX_IMM32))
3038         {
3039           insnCodeGen::generateImm (gen, CAUop, dest, 0, BOT_HI (offset));
3040           insnCodeGen::generateImm (gen, ORILop, dest, dest, BOT_LO (offset));
3041           insnCodeGen::generateAddReg (gen, CAXop, dest, dest, base);
3042         }
3043         else {
3044                 assert(0);
3045         }
3046         
3047     }
3048     else {
3049 /*        insnCodeGen::generateMemAccess64(gen, LDop, LDxop,
3050                                          dest,
3051                                          base,
3052                                          offset);
3053 */
3054     }
3055     return true;
3056 }
3057
3058 bool EmitterPOWER::emitLoadRelative(Register dest, Address offset, Register base, int size, codeGen &gen){
3059     // Loads a saved register from the stack. 
3060     int imm = offset;
3061     if (gen.addrSpace()->getAddressWidth() == 4) {
3062       if (((signed)MIN_IMM16 <= (signed)imm) && ((signed)imm <= (signed)MAX_IMM16))
3063         {
3064           int ocode = Lop;
3065           switch (size) {
3066           case 1:
3067                 ocode = LBZop;
3068                 break;
3069           case 2:
3070                 ocode = LHZop;
3071                 break;
3072           case 4:
3073                 ocode = Lop;
3074                 break;
3075           default:
3076                 printf(" Unrecognized size for load operation(%d). Assuming size of 4 \n", size);
3077                 break;
3078           }
3079           insnCodeGen::generateImm (gen, ocode, dest, base, imm);
3080
3081         }
3082       else if (((signed)MIN_IMM32 <= (signed)imm) && ((signed)imm <= (signed)MAX_IMM32))
3083         {
3084           insnCodeGen::generateImm (gen, CAUop, dest, 0, BOT_HI (offset));
3085           insnCodeGen::generateImm (gen, ORILop, dest, dest, BOT_LO (offset));
3086           insnCodeGen::generateLoadReg (gen, LXop, dest, dest, base);
3087         }
3088         else {
3089                 assert(0);
3090         }
3091         
3092     }
3093     else {
3094         insnCodeGen::generateMemAccess64(gen, LDop, LDxop,
3095                                          dest,
3096                                          base,
3097                                          offset);
3098     }
3099     return true;
3100 }
3101
3102 void EmitterPOWER::emitStoreRelative(Register source, Address offset, Register base, int size, codeGen &gen){
3103     int imm = offset;
3104     if (gen.addrSpace()->getAddressWidth() == 4) {
3105       if (((signed)MIN_IMM16 <= (signed)imm) && ((signed)imm <= (signed)MAX_IMM16))
3106         {
3107           int ocode = STop;
3108           switch (size) {
3109           case 1:
3110                 ocode = STBop;
3111                 break;
3112           case 2:
3113                 ocode = STHop;
3114                 break;
3115           case 4:
3116                 ocode = STop;
3117                 break;
3118           default:
3119                 printf(" Unrecognized size for store operation(%d). Assuming size of 4 \n", size);
3120                 break;
3121           }
3122           insnCodeGen::generateImm (gen, ocode, source, base, imm);
3123
3124         }
3125       else if (((signed)MIN_IMM32 <= (signed)imm) && ((signed)imm <= (signed)MAX_IMM32))
3126         {
3127           insnCodeGen::generateImm (gen, CAUop, source, 0, BOT_HI (offset));
3128           insnCodeGen::generateImm (gen, ORILop, source, source, BOT_LO (offset));
3129           insnCodeGen::generateStoreReg (gen, STXop, source, source, base);
3130         }
3131         else {
3132                 assert(0);
3133         }
3134         
3135     }
3136     else {
3137         insnCodeGen::generateMemAccess64(gen, STDop, STDxop,
3138                                          source,
3139                                          base,
3140                                          offset);
3141     }
3142
3143 }
3144
3145 bool EmitterPOWER::emitMoveRegToReg(registerSlot *src, 
3146                                     registerSlot *dest, 
3147                                     codeGen &gen) {
3148     assert(dest->type == registerSlot::GPR);
3149
3150     switch (src->type) {
3151     case registerSlot::GPR:
3152         insnCodeGen::generateImm(gen, ORILop, src->encoding(), dest->encoding(), 0);
3153         break;
3154     case registerSlot::SPR: {
3155         instruction insn;
3156         
3157         switch (src->number) {
3158         case registerSpace::lr:
3159         case registerSpace::xer:
3160         case registerSpace::ctr:
3161         case registerSpace::mq:
3162             insn.clear();
3163             XFORM_OP_SET(insn, EXTop);
3164             XFORM_RT_SET(insn, dest->encoding());
3165             XFORM_RA_SET(insn, src->encoding() & 0x1f);
3166             XFORM_RB_SET(insn, (src->encoding() >> 5) & 0x1f);
3167             XFORM_XO_SET(insn, MFSPRxop);
3168             insnCodeGen::generate(gen,insn);
3169             break;
3170         case registerSpace::cr:
3171             insn.clear();                    //mtcrf:  scratchReg
3172             XFXFORM_OP_SET(insn, EXTop);
3173             XFXFORM_RT_SET(insn, dest->encoding());
3174             XFXFORM_XO_SET(insn, MFCRxop);
3175             insnCodeGen::generate(gen,insn);
3176             break;
3177         default:
3178             assert(0);
3179             break;
3180         }
3181         break;
3182     }
3183
3184     default:
3185         assert(0);
3186         break;
3187     }
3188     return true;
3189 }
3190
3191 /*
3192 bool EmitterPOWER32Stat::emitPIC(codeGen& gen, Address origAddr, Address relocAddr) {
3193
3194       Register scratchPCReg = gen.rs()->getScratchRegister(gen, true);
3195       pdvector<Register> excludeReg;
3196       excludeReg.push_back(scratchPCReg);
3197       Register scratchReg = gen.rs()->getScratchRegister(gen, excludeReg, true);
3198       bool newStackFrame = false;
3199       int stack_size = 0;
3200       int gpr_off, fpr_off, ctr_off;
3201       //fprintf(stderr, " emitPIC origAddr 0x%lx reloc 0x%lx Registers PC %d scratch %d \n", origAddr, relocAddr, scratchPCReg, scratchReg);
3202       if ((scratchPCReg == REG_NULL) || (scratchReg == REG_NULL)) {
3203                 //fprintf(stderr, " Creating new stack frame for 0x%lx to 0x%lx \n", origAddr, relocAddr);
3204
3205                 newStackFrame = true;
3206                 //create new stack frame
3207                 gpr_off = TRAMP_GPR_OFFSET_32;
3208                 fpr_off = TRAMP_FPR_OFFSET_32;
3209                 ctr_off = STK_CTR_32;
3210
3211                 // Make a stack frame.
3212                 pushStack(gen);
3213
3214                 // Save GPRs
3215               stack_size = saveGPRegisters(gen, gen.rs(), gpr_off, 2);
3216
3217               scratchPCReg = gen.rs()->getScratchRegister(gen, true);
3218               assert(scratchPCReg != REG_NULL);
3219               excludeReg.clear();
3220               excludeReg.push_back(scratchPCReg);
3221               scratchReg = gen.rs()->getScratchRegister(gen, excludeReg, true);
3222               assert(scratchReg != REG_NULL);
3223               // relocaAddr has moved since we added instructions to setup a new stack frame
3224               relocAddr = relocAddr + ((stack_size + 1)*(gen.addrSpace()->getAddressWidth()));
3225               //fprintf(stderr, " emitPIC origAddr 0x%lx reloc 0x%lx stack size %d Registers PC %d scratch %d \n", origAddr, relocAddr, stack_size, scratchPCReg, scratchReg);
3226
3227         } 
3228         emitMovPCToReg(scratchPCReg, gen);      
3229         Address varOffset = origAddr - relocAddr;
3230         emitCallRelative(scratchReg, varOffset, scratchPCReg, gen);
3231         insnCodeGen::generateMoveToLR(gen, scratchReg);
3232         if(newStackFrame) {
3233               // GPRs
3234               restoreGPRegisters(gen, gen.rs(), gpr_off);
3235               popStack(gen);
3236         }
3237
3238       return 0;
3239 }
3240
3241 bool EmitterPOWER64Stat::emitPIC(codeGen& gen, Address origAddr, Address relocAddr) {
3242         assert(0);
3243         return false;
3244 }
3245 bool EmitterPOWERDyn::emitPIC(codeGen &gen, Address origAddr, Address relocAddr) {
3246
3247         Address origRet = origAddr + 4;
3248         Register scratch = gen.rs()->getScratchRegister(gen, true);
3249         assert(scratch != REG_NULL);
3250         instruction::loadImmIntoReg(gen, scratch, origRet);
3251         insnCodeGen::generateMoveToLR(gen, scratch);
3252         return true;
3253
3254 }
3255 */
3256 bool EmitterPOWER32Stat::emitCallInstruction(codeGen& gen, int_function* callee, bool /* setTOC */, Address) {
3257 // 32 - No TOC 
3258 // if inter module, gen PIC code
3259
3260     Address dest;
3261     Register scratchPCReg = gen.rs()->getScratchRegister(gen, true);
3262     pdvector<Register> excludeReg;
3263     excludeReg.push_back(scratchPCReg);
3264     Register scratchReg = gen.rs()->getScratchRegister(gen, excludeReg, true);
3265     assert ((scratchPCReg != REG_NULL) && (scratchReg != REG_NULL)) ;
3266
3267     if (gen.func()->obj() != callee->obj()) {
3268         dest = getInterModuleFuncAddr(callee, gen);
3269 //      insnCodeGen::generateInterFunctionBranch(gen, gen.currAddr(), dest, true);
3270     } else {
3271         dest = callee->getAddress();
3272 //      insnCodeGen::generateBranch(gen, gen.currAddr(), dest, true);
3273     }
3274
3275     inst_printf("emitCallInstruction addr 0x%lx curr adress 0x%lx offset %ld 0x%lx\n",
3276                 dest, gen.currAddr(), dest - gen.currAddr()+4, dest - gen.currAddr()+4);
3277     // Use scratchReg to set destination of the call...
3278    
3279     emitMovPCToReg(scratchPCReg, gen);
3280     Address varOffset = dest - gen.currAddr()+4;
3281
3282     if (gen.func()->obj() != callee->obj()) 
3283         emitLoadRelative(scratchReg, varOffset, scratchPCReg, gen.addrSpace()->getAddressWidth(), gen);
3284     else
3285         emitCallRelative(scratchReg, varOffset, scratchPCReg, gen);
3286
3287     insnCodeGen::generateMoveToLR(gen, scratchReg);
3288      
3289     instruction brl(BRLraw);
3290     insnCodeGen::generate(gen,brl);
3291
3292   
3293     return true;
3294 }
3295
3296 /*
3297 bool EmitterPOWER32Stat::emitCallInstruction(codeGen& gen, int_function* callee, bool setTOC, Address) {
3298 // 32 - No TOC 
3299 // if inter module, gen PIC code
3300
3301     Address dest;
3302     if (gen.func()->obj() != callee->obj()) {
3303         dest = getInterModuleFuncAddr(callee, gen);
3304         insnCodeGen::generateInterFunctionBranch(gen, gen.currAddr(), dest, true);
3305     } else {
3306         dest = callee->getAddress();
3307         insnCodeGen::generateBranch(gen, gen.currAddr(), dest, true);
3308     }
3309
3310     return true;
3311 }
3312 */
3313 bool EmitterPOWER64Stat::emitCallInstruction(codeGen& /*gen*/, int_function* /*callee*/, bool /*setTOC*/, Address) {
3314    assert(0);
3315    return 0;
3316 }
3317
3318
3319 bool EmitterPOWERDyn::emitCallInstruction(codeGen &gen, int_function *callee, bool setTOC, Address toc_anchor) {
3320
3321     bool needLongBranch = false;
3322     if (gen.startAddr() == (Address) -1) { // Unset...
3323         needLongBranch = true;
3324         inst_printf("Unknown generation addr, long call required\n");
3325     }
3326     else {
3327         long displacement = callee->getAddress() - gen.currAddr();
3328         // Increase the displacement to be conservative. 
3329         // We use fewer than 6 instructions, too. But again,
3330         // conservative.
3331
3332         if ((ABS(displacement) + 6*instruction::size()) > MAX_BRANCH) {
3333             needLongBranch = true;
3334             inst_printf("Need long call to get from 0x%lx to 0x%lx\n",
3335                     gen.currAddr(), callee->getAddress());
3336         }
3337     }
3338
3339     // Need somewhere to put the destination calculation...
3340     int scratchReg = 0;
3341     if (needLongBranch) {
3342         // Use scratchReg to set destination of the call...
3343         emitVload(loadConstOp, callee->getAddress(), scratchReg, scratchReg, gen, false);
3344         insnCodeGen::generateMoveToLR(gen, scratchReg);
3345         inst_printf("Generated LR value in %d\n", scratchReg);
3346     }
3347
3348
3349     // AIX 32/64, etc; Linux 64
3350     if (setTOC) {
3351         // Set up the new TOC value
3352         emitVload(loadConstOp, toc_anchor, 2, 2, gen, false);
3353         //inst_printf("toc setup (%d)...");
3354         inst_printf("Set new TOC\n");
3355     }
3356
3357         // ALL dynamic; call instruction generation
3358     if (needLongBranch) {
3359         instruction brl(BRLraw);
3360         insnCodeGen::generate(gen,brl);
3361         inst_printf("Generated BRL\n");
3362     }
3363     else {
3364         insnCodeGen::generateCall(gen, gen.currAddr(), callee->getAddress());
3365         inst_printf("Generated short call from 0x%lx to 0x%lx\n",
3366                 gen.currAddr(), callee->getAddress());
3367     }
3368
3369     return true;
3370
3371 }
3372
3373 void EmitterPOWER::emitLoadShared(opCode op, Register dest, const image_variable* var, bool is_local, int size, codeGen &gen, Address offset)
3374 {
3375    // create or retrieve jump slot
3376    Address addr;
3377    int stackSize = 0;
3378
3379    if(var == NULL) {
3380       addr = offset;
3381    }
3382    else if(!is_local) {
3383       addr = getInterModuleVarAddr(var, gen);
3384    }
3385    else {
3386       addr = (Address)var->getOffset();
3387    }
3388
3389    // load register with address from jump slot
3390
3391    inst_printf("emitLoadrelative addr 0x%lx curr adress 0x%lx offset %ld 0x%lx size %d\n", 
3392         addr, gen.currAddr(), addr - gen.currAddr()+4, addr - gen.currAddr()+4, size);
3393    Register scratchReg = gen.rs()->getScratchRegister(gen, true);
3394    if (scratchReg == REG_NULL) {
3395         pdvector<Register> freeReg;
3396         pdvector<Register> excludeReg;
3397         stackSize = insnCodeGen::createStackFrame(gen, 1, freeReg, excludeReg);
3398         assert (stackSize == 1);
3399         scratchReg = freeReg[0];
3400         inst_printf("emitLoadrelative - after new stack frame - addr 0x%lx curr adress 0x%lx offset %ld 0x%lx size %d\n", 
3401                 addr, gen.currAddr(), addr - gen.currAddr()+4, addr - gen.currAddr()+4, size);
3402    }
3403
3404    emitMovPCToReg(scratchReg, gen);
3405    Address varOffset = addr - gen.currAddr()+4;
3406    
3407    if (op ==loadOp) {
3408         if(!is_local && (var != NULL)){
3409                 emitLoadRelative(scratchReg, varOffset, scratchReg, gen.addrSpace()->getAddressWidth(), gen);
3410                 // Deference the pointer to get the variable
3411                 emitLoadRelative(dest, 0, scratchReg, size, gen);
3412         } else {
3413                 emitLoadRelative(dest, varOffset, scratchReg, size, gen);
3414         }
3415    } else { //loadConstop
3416         if(!is_local && (var != NULL)){
3417                 emitLoadRelative(dest, varOffset, scratchReg, gen.addrSpace()->getAddressWidth(), gen);
3418         } else {
3419                 // Move address of the variable into the register - load effective address
3420                 //dest = effective address of pc+offset ;
3421                 insnCodeGen::generateImm (gen, CAUop, dest, 0, BOT_HI (varOffset));
3422                 insnCodeGen::generateImm (gen, ORILop, dest, dest, BOT_LO (varOffset));
3423                 insnCodeGen::generateAddReg (gen, CAXop, dest, dest, scratchReg);
3424         }
3425    }
3426
3427    if (stackSize > 0)
3428         insnCodeGen::removeStackFrame(gen);
3429
3430   return;
3431 }
3432
3433 void EmitterPOWER::emitStoreShared(Register source, const image_variable * var, bool is_local, int size, codeGen & gen)
3434 {
3435    // create or retrieve jump slot
3436    Address addr;