comparison src/cpu/ppc/vm/vm_version_ppc.cpp @ 17803:31e80afe3fed

8035647: PPC64: Support for elf v2 abi. Summary: ELFv2 ABI used by the little endian PowerPC64 on Linux. Reviewed-by: kvn Contributed-by: asmundak@google.com
author goetz
date Thu, 06 Mar 2014 10:55:28 -0800
parents 67fa91961822
children 92aa6797d639 71a71b0bc844
comparison
equal deleted inserted replaced
17802:7c462558a08a 17803:31e80afe3fed
22 * questions. 22 * questions.
23 * 23 *
24 */ 24 */
25 25
26 #include "precompiled.hpp" 26 #include "precompiled.hpp"
27 #include "assembler_ppc.inline.hpp" 27 #include "asm/assembler.inline.hpp"
28 #include "asm/macroAssembler.inline.hpp"
28 #include "compiler/disassembler.hpp" 29 #include "compiler/disassembler.hpp"
29 #include "memory/resourceArea.hpp" 30 #include "memory/resourceArea.hpp"
30 #include "runtime/java.hpp" 31 #include "runtime/java.hpp"
31 #include "runtime/stubCodeGenerator.hpp" 32 #include "runtime/stubCodeGenerator.hpp"
32 #include "utilities/defaultStream.hpp" 33 #include "utilities/defaultStream.hpp"
166 CodeBuffer cb("detect_section_size", code_size, 0); 167 CodeBuffer cb("detect_section_size", code_size, 0);
167 MacroAssembler* a = new MacroAssembler(&cb); 168 MacroAssembler* a = new MacroAssembler(&cb);
168 169
169 uint32_t *code = (uint32_t *)a->pc(); 170 uint32_t *code = (uint32_t *)a->pc();
170 // Emit code. 171 // Emit code.
171 void (*test1)() = (void(*)())(void *)a->emit_fd(); 172 void (*test1)() = (void(*)())(void *)a->function_entry();
172 173
173 Label l1; 174 Label l1;
174 175
175 a->li(R4, 1); 176 a->li(R4, 1);
176 a->sldi(R4, R4, 28); 177 a->sldi(R4, R4, 28);
240 a->cmpdi(CCR0, R4, unroll); // 33 241 a->cmpdi(CCR0, R4, unroll); // 33
241 a->bge(CCR0, l1); // 34 242 a->bge(CCR0, l1); // 34
242 a->blr(); 243 a->blr();
243 244
244 // Emit code. 245 // Emit code.
245 void (*test2)() = (void(*)())(void *)a->emit_fd(); 246 void (*test2)() = (void(*)())(void *)a->function_entry();
246 // uint32_t *code = (uint32_t *)a->pc(); 247 // uint32_t *code = (uint32_t *)a->pc();
247 248
248 Label l2; 249 Label l2;
249 250
250 a->li(R4, 1); 251 a->li(R4, 1);
381 if (UsePower6SchedulerPPC64) Unimplemented(); 382 if (UsePower6SchedulerPPC64) Unimplemented();
382 } 383 }
383 #endif // COMPILER2 384 #endif // COMPILER2
384 385
385 void VM_Version::determine_features() { 386 void VM_Version::determine_features() {
387 #if defined(ABI_ELFv2)
388 const int code_size = (num_features+1+2*7)*BytesPerInstWord; // TODO(asmundak): calculation is incorrect.
389 #else
386 // 7 InstWords for each call (function descriptor + blr instruction). 390 // 7 InstWords for each call (function descriptor + blr instruction).
387 const int code_size = (num_features+1+2*7)*BytesPerInstWord; 391 const int code_size = (num_features+1+2*7)*BytesPerInstWord;
392 #endif
388 int features = 0; 393 int features = 0;
389 394
390 // create test area 395 // create test area
391 enum { BUFFER_SIZE = 2*4*K }; // Needs to be >=2* max cache line size (cache line size can't exceed min page size). 396 enum { BUFFER_SIZE = 2*4*K }; // Needs to be >=2* max cache line size (cache line size can't exceed min page size).
392 char test_area[BUFFER_SIZE]; 397 char test_area[BUFFER_SIZE];
396 ResourceMark rm; 401 ResourceMark rm;
397 CodeBuffer cb("detect_cpu_features", code_size, 0); 402 CodeBuffer cb("detect_cpu_features", code_size, 0);
398 MacroAssembler* a = new MacroAssembler(&cb); 403 MacroAssembler* a = new MacroAssembler(&cb);
399 404
400 // Emit code. 405 // Emit code.
401 void (*test)(address addr, uint64_t offset)=(void(*)(address addr, uint64_t offset))(void *)a->emit_fd(); 406 void (*test)(address addr, uint64_t offset)=(void(*)(address addr, uint64_t offset))(void *)a->function_entry();
402 uint32_t *code = (uint32_t *)a->pc(); 407 uint32_t *code = (uint32_t *)a->pc();
403 // Don't use R0 in ldarx. 408 // Don't use R0 in ldarx.
404 // Keep R3_ARG1 unmodified, it contains &field (see below). 409 // Keep R3_ARG1 unmodified, it contains &field (see below).
405 // Keep R4_ARG2 unmodified, it contains offset = 0 (see below). 410 // Keep R4_ARG2 unmodified, it contains offset = 0 (see below).
406 a->fsqrt(F3, F4); // code[0] -> fsqrt_m 411 a->fsqrt(F3, F4); // code[0] -> fsqrt_m
413 a->fcfids(F3, F4); // code[7] -> fcfids 418 a->fcfids(F3, F4); // code[7] -> fcfids
414 a->vand(VR0, VR0, VR0); // code[8] -> vand 419 a->vand(VR0, VR0, VR0); // code[8] -> vand
415 a->blr(); 420 a->blr();
416 421
417 // Emit function to set one cache line to zero. Emit function descriptor and get pointer to it. 422 // Emit function to set one cache line to zero. Emit function descriptor and get pointer to it.
418 void (*zero_cacheline_func_ptr)(char*) = (void(*)(char*))(void *)a->emit_fd(); 423 void (*zero_cacheline_func_ptr)(char*) = (void(*)(char*))(void *)a->function_entry();
419 a->dcbz(R3_ARG1); // R3_ARG1 = addr 424 a->dcbz(R3_ARG1); // R3_ARG1 = addr
420 a->blr(); 425 a->blr();
421 426
422 uint32_t *code_end = (uint32_t *)a->pc(); 427 uint32_t *code_end = (uint32_t *)a->pc();
423 a->flush(); 428 a->flush();