1 /* 2 * Copyright (c) 2000, 2014, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. 8 * 9 * This code is distributed in the hope that it will be useful, but WITHOUT 10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12 * version 2 for more details (a copy is included in the LICENSE file that 13 * accompanied this code). 14 * 15 * You should have received a copy of the GNU General Public License version 16 * 2 along with this work; if not, write to the Free Software Foundation, 17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 18 * 19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 20 * or visit www.oracle.com if you need additional information or have any 21 * questions. 22 * 23 */ 24 25 #ifndef SHARE_VM_ASM_REGISTER_HPP 26 #define SHARE_VM_ASM_REGISTER_HPP 27 28 #include "utilities/top.hpp" 29 30 // Use AbstractRegister as shortcut 31 class AbstractRegisterImpl; 32 typedef AbstractRegisterImpl* AbstractRegister; 33 34 35 // The super class for platform specific registers. Instead of using value objects, 36 // registers are implemented as pointers. Subclassing is used so all registers can 37 // use the debugging suport below. No virtual functions are used for efficiency. 38 // They are canonicalized; i.e., registers are equal if their pointers are equal, 39 // and vice versa. A concrete implementation may just map the register onto 'this'. 40 41 class AbstractRegisterImpl { 42 protected: 43 int value() const { return (int)(intx)this; } 44 }; 45 46 47 // 48 // Macros for use in defining Register instances. We'd like to be 49 // able to simply define const instances of the RegisterImpl* for each 50 // of the registers needed on a system in a header file. However many 51 // compilers don't handle this very well and end up producing a 52 // private definition in every file which includes the header file. 53 // Along with the static constructors necessary for initialization it 54 // can consume a significant amount of space in the result library. 55 // 56 // The following macros allow us to declare the instance in a .hpp and 57 // produce an enumeration value which has the same number. Then in a 58 // .cpp the the register instance can be defined using the enumeration 59 // value. This avoids the use of static constructors and multiple 60 // definitions per .cpp. In addition #defines for the register can be 61 // produced so that the constant registers can be inlined. These 62 // macros should not be used inside other macros, because you may get 63 // multiple evaluations of the macros which can give bad results. 64 // 65 // Here are some example uses and expansions. Note that the macro 66 // invocation is terminated with a ;. 67 // 68 // CONSTANT_REGISTER_DECLARATION(Register, G0, 0); 69 // 70 // extern const Register G0 ; 71 // enum { G0_RegisterEnumValue = 0 } ; 72 // 73 // REGISTER_DECLARATION(Register, Gmethod, G5); 74 // 75 // extern const Register Gmethod ; 76 // enum { Gmethod_RegisterEnumValue = G5_RegisterEnumValue } ; 77 // 78 // REGISTER_DEFINITION(Register, G0); 79 // 80 // const Register G0 = ( ( Register ) G0_RegisterEnumValue ) ; 81 // 82 83 #define AS_REGISTER(type,name) ((type)name##_##type##EnumValue) 84 85 #define CONSTANT_REGISTER_DECLARATION(type, name, value) \ 86 extern const type name; \ 87 enum { name##_##type##EnumValue = (value) } 88 89 #define REGISTER_DECLARATION(type, name, value) \ 90 extern const type name; \ 91 enum { name##_##type##EnumValue = value##_##type##EnumValue } 92 93 #define REGISTER_DEFINITION(type, name) \ 94 const type name = ((type)name##_##type##EnumValue) 95 96 #ifdef TARGET_ARCH_x86 97 # include "register_x86.hpp" 98 #endif 99 #ifdef TARGET_ARCH_sparc 100 # include "register_sparc.hpp" 101 #endif 102 #ifdef TARGET_ARCH_zero 103 # include "register_zero.hpp" 104 #endif 105 #ifdef TARGET_ARCH_arm 106 # include "register_arm.hpp" 107 #endif 108 #ifdef TARGET_ARCH_ppc 109 # include "register_ppc.hpp" 110 #endif 111 #ifdef TARGET_ARCH_aarch64 112 # include "register_aarch64.hpp" 113 #endif 114 115 116 // Debugging support 117 118 inline void assert_different_registers( 119 AbstractRegister a, 120 AbstractRegister b 121 ) { 122 assert( 123 a != b, 124 "registers must be different: a=" INTPTR_FORMAT ", b=" INTPTR_FORMAT "", p2i(a), p2i(b) 125 ); 126 } 127 128 129 inline void assert_different_registers( 130 AbstractRegister a, 131 AbstractRegister b, 132 AbstractRegister c 133 ) { 134 assert( 135 a != b && a != c 136 && b != c, 137 "registers must be different: a=" INTPTR_FORMAT ", b=" INTPTR_FORMAT 138 ", c=" INTPTR_FORMAT "", 139 p2i(a), p2i(b), p2i(c) 140 ); 141 } 142 143 144 inline void assert_different_registers( 145 AbstractRegister a, 146 AbstractRegister b, 147 AbstractRegister c, 148 AbstractRegister d 149 ) { 150 assert( 151 a != b && a != c && a != d 152 && b != c && b != d 153 && c != d, 154 "registers must be different: a=" INTPTR_FORMAT ", b=" INTPTR_FORMAT 155 ", c=" INTPTR_FORMAT ", d=" INTPTR_FORMAT "", 156 p2i(a), p2i(b), p2i(c), p2i(d) 157 ); 158 } 159 160 161 inline void assert_different_registers( 162 AbstractRegister a, 163 AbstractRegister b, 164 AbstractRegister c, 165 AbstractRegister d, 166 AbstractRegister e 167 ) { 168 assert( 169 a != b && a != c && a != d && a != e 170 && b != c && b != d && b != e 171 && c != d && c != e 172 && d != e, 173 "registers must be different: a=" INTPTR_FORMAT ", b=" INTPTR_FORMAT 174 ", c=" INTPTR_FORMAT ", d=" INTPTR_FORMAT ", e=" INTPTR_FORMAT "", 175 p2i(a), p2i(b), p2i(c), p2i(d), p2i(e) 176 ); 177 } 178 179 180 inline void assert_different_registers( 181 AbstractRegister a, 182 AbstractRegister b, 183 AbstractRegister c, 184 AbstractRegister d, 185 AbstractRegister e, 186 AbstractRegister f 187 ) { 188 assert( 189 a != b && a != c && a != d && a != e && a != f 190 && b != c && b != d && b != e && b != f 191 && c != d && c != e && c != f 192 && d != e && d != f 193 && e != f, 194 "registers must be different: a=" INTPTR_FORMAT ", b=" INTPTR_FORMAT 195 ", c=" INTPTR_FORMAT ", d=" INTPTR_FORMAT ", e=" INTPTR_FORMAT 196 ", f=" INTPTR_FORMAT "", 197 p2i(a), p2i(b), p2i(c), p2i(d), p2i(e), p2i(f) 198 ); 199 } 200 201 202 inline void assert_different_registers( 203 AbstractRegister a, 204 AbstractRegister b, 205 AbstractRegister c, 206 AbstractRegister d, 207 AbstractRegister e, 208 AbstractRegister f, 209 AbstractRegister g 210 ) { 211 assert( 212 a != b && a != c && a != d && a != e && a != f && a != g 213 && b != c && b != d && b != e && b != f && b != g 214 && c != d && c != e && c != f && c != g 215 && d != e && d != f && d != g 216 && e != f && e != g 217 && f != g, 218 "registers must be different: a=" INTPTR_FORMAT ", b=" INTPTR_FORMAT 219 ", c=" INTPTR_FORMAT ", d=" INTPTR_FORMAT ", e=" INTPTR_FORMAT 220 ", f=" INTPTR_FORMAT ", g=" INTPTR_FORMAT "", 221 p2i(a), p2i(b), p2i(c), p2i(d), p2i(e), p2i(f), p2i(g) 222 ); 223 } 224 225 226 inline void assert_different_registers( 227 AbstractRegister a, 228 AbstractRegister b, 229 AbstractRegister c, 230 AbstractRegister d, 231 AbstractRegister e, 232 AbstractRegister f, 233 AbstractRegister g, 234 AbstractRegister h 235 ) { 236 assert( 237 a != b && a != c && a != d && a != e && a != f && a != g && a != h 238 && b != c && b != d && b != e && b != f && b != g && b != h 239 && c != d && c != e && c != f && c != g && c != h 240 && d != e && d != f && d != g && d != h 241 && e != f && e != g && e != h 242 && f != g && f != h 243 && g != h, 244 "registers must be different: a=" INTPTR_FORMAT ", b=" INTPTR_FORMAT 245 ", c=" INTPTR_FORMAT ", d=" INTPTR_FORMAT ", e=" INTPTR_FORMAT 246 ", f=" INTPTR_FORMAT ", g=" INTPTR_FORMAT ", h=" INTPTR_FORMAT "", 247 p2i(a), p2i(b), p2i(c), p2i(d), p2i(e), p2i(f), p2i(g), p2i(h) 248 ); 249 } 250 251 252 inline void assert_different_registers( 253 AbstractRegister a, 254 AbstractRegister b, 255 AbstractRegister c, 256 AbstractRegister d, 257 AbstractRegister e, 258 AbstractRegister f, 259 AbstractRegister g, 260 AbstractRegister h, 261 AbstractRegister i 262 ) { 263 assert( 264 a != b && a != c && a != d && a != e && a != f && a != g && a != h && a != i 265 && b != c && b != d && b != e && b != f && b != g && b != h && b != i 266 && c != d && c != e && c != f && c != g && c != h && c != i 267 && d != e && d != f && d != g && d != h && d != i 268 && e != f && e != g && e != h && e != i 269 && f != g && f != h && f != i 270 && g != h && g != i 271 && h != i, 272 "registers must be different: a=" INTPTR_FORMAT ", b=" INTPTR_FORMAT 273 ", c=" INTPTR_FORMAT ", d=" INTPTR_FORMAT ", e=" INTPTR_FORMAT 274 ", f=" INTPTR_FORMAT ", g=" INTPTR_FORMAT ", h=" INTPTR_FORMAT 275 ", i=" INTPTR_FORMAT "", 276 p2i(a), p2i(b), p2i(c), p2i(d), p2i(e), p2i(f), p2i(g), p2i(h), p2i(i) 277 ); 278 } 279 280 inline void assert_different_registers( 281 AbstractRegister a, 282 AbstractRegister b, 283 AbstractRegister c, 284 AbstractRegister d, 285 AbstractRegister e, 286 AbstractRegister f, 287 AbstractRegister g, 288 AbstractRegister h, 289 AbstractRegister i, 290 AbstractRegister j 291 ) { 292 assert( 293 a != b && a != c && a != d && a != e && a != f && a != g && a != h && a != i && a != j 294 && b != c && b != d && b != e && b != f && b != g && b != h && b != i && b != j 295 && c != d && c != e && c != f && c != g && c != h && c != i && c != j 296 && d != e && d != f && d != g && d != h && d != i && d != j 297 && e != f && e != g && e != h && e != i && e != j 298 && f != g && f != h && f != i && f != j 299 && g != h && g != i && g != j 300 && h != i && h != j 301 && i != j, 302 "registers must be different: a=" INTPTR_FORMAT ", b=" INTPTR_FORMAT 303 ", c=" INTPTR_FORMAT ", d=" INTPTR_FORMAT ", e=" INTPTR_FORMAT 304 ", f=" INTPTR_FORMAT ", g=" INTPTR_FORMAT ", h=" INTPTR_FORMAT 305 ", i=" INTPTR_FORMAT ", j=" INTPTR_FORMAT "", 306 p2i(a), p2i(b), p2i(c), p2i(d), p2i(e), p2i(f), p2i(g), p2i(h), p2i(i), p2i(j) 307 ); 308 } 309 310 inline void assert_different_registers( 311 AbstractRegister a, 312 AbstractRegister b, 313 AbstractRegister c, 314 AbstractRegister d, 315 AbstractRegister e, 316 AbstractRegister f, 317 AbstractRegister g, 318 AbstractRegister h, 319 AbstractRegister i, 320 AbstractRegister j, 321 AbstractRegister k 322 ) { 323 assert( 324 a != b && a != c && a != d && a != e && a != f && a != g && a != h && a != i && a != j && a !=k 325 && b != c && b != d && b != e && b != f && b != g && b != h && b != i && b != j && b !=k 326 && c != d && c != e && c != f && c != g && c != h && c != i && c != j && c !=k 327 && d != e && d != f && d != g && d != h && d != i && d != j && d !=k 328 && e != f && e != g && e != h && e != i && e != j && e !=k 329 && f != g && f != h && f != i && f != j && f !=k 330 && g != h && g != i && g != j && g !=k 331 && h != i && h != j && h !=k 332 && i != j && i !=k 333 && j !=k, 334 "registers must be different: a=" INTPTR_FORMAT ", b=" INTPTR_FORMAT 335 ", c=" INTPTR_FORMAT ", d=" INTPTR_FORMAT ", e=" INTPTR_FORMAT 336 ", f=" INTPTR_FORMAT ", g=" INTPTR_FORMAT ", h=" INTPTR_FORMAT 337 ", i=" INTPTR_FORMAT ", j=" INTPTR_FORMAT ", k=" INTPTR_FORMAT "", 338 p2i(a), p2i(b), p2i(c), p2i(d), p2i(e), p2i(f), p2i(g), p2i(h), p2i(i), p2i(j), p2i(k) 339 ); 340 } 341 342 inline void assert_different_registers( 343 AbstractRegister a, 344 AbstractRegister b, 345 AbstractRegister c, 346 AbstractRegister d, 347 AbstractRegister e, 348 AbstractRegister f, 349 AbstractRegister g, 350 AbstractRegister h, 351 AbstractRegister i, 352 AbstractRegister j, 353 AbstractRegister k, 354 AbstractRegister l 355 ) { 356 assert( 357 a != b && a != c && a != d && a != e && a != f && a != g && a != h && a != i && a != j && a !=k && a !=l 358 && b != c && b != d && b != e && b != f && b != g && b != h && b != i && b != j && b !=k && b !=l 359 && c != d && c != e && c != f && c != g && c != h && c != i && c != j && c !=k && c !=l 360 && d != e && d != f && d != g && d != h && d != i && d != j && d !=k && d !=l 361 && e != f && e != g && e != h && e != i && e != j && e !=k && e !=l 362 && f != g && f != h && f != i && f != j && f !=k && f !=l 363 && g != h && g != i && g != j && g !=k && g !=l 364 && h != i && h != j && h !=k && h !=l 365 && i != j && i !=k && i !=l 366 && j !=k && j !=l 367 && k !=l, 368 "registers must be different: a=" INTPTR_FORMAT ", b=" INTPTR_FORMAT 369 ", c=" INTPTR_FORMAT ", d=" INTPTR_FORMAT ", e=" INTPTR_FORMAT 370 ", f=" INTPTR_FORMAT ", g=" INTPTR_FORMAT ", h=" INTPTR_FORMAT 371 ", i=" INTPTR_FORMAT ", j=" INTPTR_FORMAT ", k=" INTPTR_FORMAT 372 ", l=" INTPTR_FORMAT "", 373 p2i(a), p2i(b), p2i(c), p2i(d), p2i(e), p2i(f), p2i(g), p2i(h), p2i(i), p2i(j), p2i(k), p2i(l) 374 ); 375 } 376 377 #endif // SHARE_VM_ASM_REGISTER_HPP