1 diff -urN /tmp/a/assembler_solaris_x86.cpp b/src/hotspot/os_cpu/solaris_x86/assembler_solaris_x86.cpp
2 --- /tmp/a/assembler_solaris_x86.cpp 1970-01-01 01:00:00.000000000 +0100
3 +++ b/src/hotspot/os_cpu/solaris_x86/assembler_solaris_x86.cpp 2024-09-16 14:41:33.968469417 +0100
6 + * Copyright (c) 1999, 2015, Oracle and/or its affiliates. All rights reserved.
7 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
9 + * This code is free software; you can redistribute it and/or modify it
10 + * under the terms of the GNU General Public License version 2 only, as
11 + * published by the Free Software Foundation.
13 + * This code is distributed in the hope that it will be useful, but WITHOUT
14 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
15 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
16 + * version 2 for more details (a copy is included in the LICENSE file that
17 + * accompanied this code).
19 + * You should have received a copy of the GNU General Public License version
20 + * 2 along with this work; if not, write to the Free Software Foundation,
21 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
23 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
24 + * or visit www.oracle.com if you need additional information or have any
29 +#include "precompiled.hpp"
30 +#include "asm/macroAssembler.inline.hpp"
31 +#include "runtime/os.hpp"
33 +void MacroAssembler::int3() {
37 + call(RuntimeAddress(CAST_FROM_FN_PTR(address, os::breakpoint)));
42 diff -urN /tmp/a/atomic_solaris_x86.hpp b/src/hotspot/os_cpu/solaris_x86/atomic_solaris_x86.hpp
43 --- /tmp/a/atomic_solaris_x86.hpp 1970-01-01 01:00:00.000000000 +0100
44 +++ b/src/hotspot/os_cpu/solaris_x86/atomic_solaris_x86.hpp 2024-09-16 14:41:33.968592045 +0100
47 + * Copyright (c) 1999, 2019, Oracle and/or its affiliates. All rights reserved.
48 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
50 + * This code is free software; you can redistribute it and/or modify it
51 + * under the terms of the GNU General Public License version 2 only, as
52 + * published by the Free Software Foundation.
54 + * This code is distributed in the hope that it will be useful, but WITHOUT
55 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
56 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
57 + * version 2 for more details (a copy is included in the LICENSE file that
58 + * accompanied this code).
60 + * You should have received a copy of the GNU General Public License version
61 + * 2 along with this work; if not, write to the Free Software Foundation,
62 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
64 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
65 + * or visit www.oracle.com if you need additional information or have any
70 +#ifndef OS_CPU_SOLARIS_X86_ATOMIC_SOLARIS_X86_HPP
71 +#define OS_CPU_SOLARIS_X86_ATOMIC_SOLARIS_X86_HPP
73 +inline int32_t _Atomic_add(int32_t add_value, volatile int32_t* dest) {
74 + int32_t rv = add_value;
75 + __asm__ volatile ("lock xaddl %0,(%2)"
77 + : "0" (rv), "r" (dest)
79 + return rv + add_value;
81 +inline int64_t _Atomic_add_long(int64_t add_value, volatile int64_t* dest) {
82 + int64_t rv = add_value;
83 + __asm__ volatile ("lock xaddq %0,(%2)"
85 + : "0" (rv), "r" (dest)
87 + return rv + add_value;
89 +inline int32_t _Atomic_xchg(int32_t exchange_value, volatile int32_t* dest) {
90 + __asm__ __volatile__ ("xchgl (%2),%0"
91 + : "=r" (exchange_value)
92 + : "0" (exchange_value), "r" (dest)
94 + return exchange_value;
96 +inline int64_t _Atomic_xchg_long(int64_t exchange_value, volatile int64_t* dest) {
97 + __asm__ __volatile__ ("xchgq (%2),%0"
98 + : "=r" (exchange_value)
99 + : "0" (exchange_value), "r" (dest)
101 + return exchange_value;
103 +inline int8_t _Atomic_cmpxchg_byte(int8_t exchange_value, volatile int8_t* dest, int8_t compare_value) {
104 + __asm__ volatile ("lock cmpxchgb %1,(%3)"
105 + : "=a" (exchange_value)
106 + : "q" (exchange_value), "a" (compare_value), "r" (dest)
108 + return exchange_value;
110 +inline int32_t _Atomic_cmpxchg(int32_t exchange_value, volatile int32_t* dest, int32_t compare_value) {
111 + __asm__ volatile ("lock cmpxchgl %1,(%3)"
112 + : "=a" (exchange_value)
113 + : "q" (exchange_value), "a" (compare_value), "r" (dest)
115 + return exchange_value;
117 +inline int64_t _Atomic_cmpxchg_long(int64_t exchange_value, volatile int64_t* dest, int64_t compare_value) {
118 + __asm__ volatile ("lock cmpxchgq %1,(%3)"
119 + : "=a" (exchange_value)
120 + : "q" (exchange_value), "a" (compare_value), "r" (dest)
122 + return exchange_value;
125 +template<size_t byte_size>
126 +struct Atomic::PlatformAdd {
127 + template<typename D, typename I>
128 + D add_then_fetch(D volatile* dest, I add_value, atomic_memory_order order) const;
130 + template<typename D, typename I>
131 + D fetch_then_add(D volatile* dest, I add_value, atomic_memory_order order) const {
132 + return add_then_fetch(dest, add_value, order) - add_value;
136 +// Not using add_using_helper; see comment for cmpxchg.
138 +template<typename D, typename I>
139 +inline D Atomic::PlatformAdd<4>::add_then_fetch(D volatile* dest, I add_value,
140 + atomic_memory_order order) const {
141 + STATIC_ASSERT(4 == sizeof(I));
142 + STATIC_ASSERT(4 == sizeof(D));
143 + return PrimitiveConversions::cast<D>(
144 + _Atomic_add(PrimitiveConversions::cast<int32_t>(add_value),
145 + reinterpret_cast<int32_t volatile*>(dest)));
148 +// Not using add_using_helper; see comment for cmpxchg.
150 +template<typename D, typename I>
151 +inline D Atomic::PlatformAdd<8>::add_then_fetch(D volatile* dest, I add_value,
152 + atomic_memory_order order) const {
153 + STATIC_ASSERT(8 == sizeof(I));
154 + STATIC_ASSERT(8 == sizeof(D));
155 + return PrimitiveConversions::cast<D>(
156 + _Atomic_add_long(PrimitiveConversions::cast<int64_t>(add_value),
157 + reinterpret_cast<int64_t volatile*>(dest)));
161 +template<typename T>
162 +inline T Atomic::PlatformXchg<4>::operator()(T volatile* dest,
164 + atomic_memory_order order) const {
165 + STATIC_ASSERT(4 == sizeof(T));
166 + return PrimitiveConversions::cast<T>(
167 + _Atomic_xchg(PrimitiveConversions::cast<int32_t>(exchange_value),
168 + reinterpret_cast<int32_t volatile*>(dest)));
172 +template<typename T>
173 +inline T Atomic::PlatformXchg<8>::operator()(T volatile* dest,
175 + atomic_memory_order order) const {
176 + STATIC_ASSERT(8 == sizeof(T));
177 + return PrimitiveConversions::cast<T>(
178 + _Atomic_xchg_long(PrimitiveConversions::cast<int64_t>(exchange_value),
179 + reinterpret_cast<int64_t volatile*>(dest)));
182 +// Not using cmpxchg_using_helper here, because some configurations of
183 +// Solaris compiler don't deal well with passing a "defined in .il"
184 +// function as an argument. We *should* switch to using gcc-style
185 +// inline assembly, but attempting to do so with Studio 12.4 ran into
189 +template<typename T>
190 +inline T Atomic::PlatformCmpxchg<1>::operator()(T volatile* dest,
193 + atomic_memory_order order) const {
194 + STATIC_ASSERT(1 == sizeof(T));
195 + return PrimitiveConversions::cast<T>(
196 + _Atomic_cmpxchg_byte(PrimitiveConversions::cast<int8_t>(exchange_value),
197 + reinterpret_cast<int8_t volatile*>(dest),
198 + PrimitiveConversions::cast<int8_t>(compare_value)));
202 +template<typename T>
203 +inline T Atomic::PlatformCmpxchg<4>::operator()(T volatile* dest,
206 + atomic_memory_order order) const {
207 + STATIC_ASSERT(4 == sizeof(T));
208 + return PrimitiveConversions::cast<T>(
209 + _Atomic_cmpxchg(PrimitiveConversions::cast<int32_t>(exchange_value),
210 + reinterpret_cast<int32_t volatile*>(dest),
211 + PrimitiveConversions::cast<int32_t>(compare_value)));
215 +template<typename T>
216 +inline T Atomic::PlatformCmpxchg<8>::operator()(T volatile* dest,
219 + atomic_memory_order order) const {
220 + STATIC_ASSERT(8 == sizeof(T));
221 + return PrimitiveConversions::cast<T>(
222 + _Atomic_cmpxchg_long(PrimitiveConversions::cast<int64_t>(exchange_value),
223 + reinterpret_cast<int64_t volatile*>(dest),
224 + PrimitiveConversions::cast<int64_t>(compare_value)));
227 +#endif // OS_CPU_SOLARIS_X86_ATOMIC_SOLARIS_X86_HPP
228 diff -urN /tmp/a/bytes_solaris_x86.hpp b/src/hotspot/os_cpu/solaris_x86/bytes_solaris_x86.hpp
229 --- /tmp/a/bytes_solaris_x86.hpp 1970-01-01 01:00:00.000000000 +0100
230 +++ b/src/hotspot/os_cpu/solaris_x86/bytes_solaris_x86.hpp 2024-09-16 14:41:33.968672682 +0100
233 + * Copyright (c) 1998, 2019, Oracle and/or its affiliates. All rights reserved.
234 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
236 + * This code is free software; you can redistribute it and/or modify it
237 + * under the terms of the GNU General Public License version 2 only, as
238 + * published by the Free Software Foundation.
240 + * This code is distributed in the hope that it will be useful, but WITHOUT
241 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
242 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
243 + * version 2 for more details (a copy is included in the LICENSE file that
244 + * accompanied this code).
246 + * You should have received a copy of the GNU General Public License version
247 + * 2 along with this work; if not, write to the Free Software Foundation,
248 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
250 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
251 + * or visit www.oracle.com if you need additional information or have any
256 +#ifndef OS_CPU_SOLARIS_X86_BYTES_SOLARIS_X86_HPP
257 +#define OS_CPU_SOLARIS_X86_BYTES_SOLARIS_X86_HPP
260 + inline u2 _raw_swap_u2(u2 x) {
261 + unsigned short int __dest;
262 + __asm__ ("rorw $8, %w0": "=r" (__dest): "0" (x): "cc");
265 + inline u4 _raw_swap_u4(u4 x) {
266 + unsigned int __dest;
267 + __asm__ ("bswap %0" : "=r" (__dest) : "0" (x));
270 + inline u8 _raw_swap_u8(u8 x) {
271 + unsigned long __dest;
272 + __asm__ ("bswap %q0" : "=r" (__dest) : "0" (x));
277 +// Efficient swapping of data bytes from Java byte
278 +// ordering to native byte ordering and vice versa.
279 +inline u2 Bytes::swap_u2(u2 x) {
280 + return _raw_swap_u2(x);
283 +inline u4 Bytes::swap_u4(u4 x) {
284 + return _raw_swap_u4(x);
287 +inline u8 Bytes::swap_u8(u8 x) {
288 + return _raw_swap_u8(x);
291 +#endif // OS_CPU_SOLARIS_X86_BYTES_SOLARIS_X86_HPP
292 diff -urN /tmp/a/copy_solaris_x86.hpp b/src/hotspot/os_cpu/solaris_x86/copy_solaris_x86.hpp
293 --- /tmp/a/copy_solaris_x86.hpp 1970-01-01 01:00:00.000000000 +0100
294 +++ b/src/hotspot/os_cpu/solaris_x86/copy_solaris_x86.hpp 2024-09-16 14:41:33.968746196 +0100
297 + * Copyright (c) 2003, 2019, Oracle and/or its affiliates. All rights reserved.
298 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
300 + * This code is free software; you can redistribute it and/or modify it
301 + * under the terms of the GNU General Public License version 2 only, as
302 + * published by the Free Software Foundation.
304 + * This code is distributed in the hope that it will be useful, but WITHOUT
305 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
306 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
307 + * version 2 for more details (a copy is included in the LICENSE file that
308 + * accompanied this code).
310 + * You should have received a copy of the GNU General Public License version
311 + * 2 along with this work; if not, write to the Free Software Foundation,
312 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
314 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
315 + * or visit www.oracle.com if you need additional information or have any
320 +#ifndef OS_CPU_SOLARIS_X86_COPY_SOLARIS_X86_HPP
321 +#define OS_CPU_SOLARIS_X86_COPY_SOLARIS_X86_HPP
323 +// now in central copy_x86.hpp
325 +#endif // OS_CPU_SOLARIS_X86_COPY_SOLARIS_X86_HPP
326 diff -urN /tmp/a/globals_solaris_x86.hpp b/src/hotspot/os_cpu/solaris_x86/globals_solaris_x86.hpp
327 --- /tmp/a/globals_solaris_x86.hpp 1970-01-01 01:00:00.000000000 +0100
328 +++ b/src/hotspot/os_cpu/solaris_x86/globals_solaris_x86.hpp 2024-09-16 14:41:33.968829858 +0100
331 + * Copyright (c) 2000, 2019, Oracle and/or its affiliates. All rights reserved.
332 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
334 + * This code is free software; you can redistribute it and/or modify it
335 + * under the terms of the GNU General Public License version 2 only, as
336 + * published by the Free Software Foundation.
338 + * This code is distributed in the hope that it will be useful, but WITHOUT
339 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
340 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
341 + * version 2 for more details (a copy is included in the LICENSE file that
342 + * accompanied this code).
344 + * You should have received a copy of the GNU General Public License version
345 + * 2 along with this work; if not, write to the Free Software Foundation,
346 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
348 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
349 + * or visit www.oracle.com if you need additional information or have any
354 +#ifndef OS_CPU_SOLARIS_X86_GLOBALS_SOLARIS_X86_HPP
355 +#define OS_CPU_SOLARIS_X86_GLOBALS_SOLARIS_X86_HPP
357 +// Sets the default values for platform dependent flags used by the runtime system.
358 +// (see globals.hpp)
360 +define_pd_global(intx, CompilerThreadStackSize, 1024);
361 +define_pd_global(intx, ThreadStackSize, 1024); // 0 => use system default
362 +define_pd_global(intx, VMThreadStackSize, 1024);
363 +define_pd_global(size_t, JVMInvokeMethodSlack, 8*K);
365 +// Used on 64 bit platforms for UseCompressedOops base address
366 +define_pd_global(size_t, HeapBaseMinAddress, 2*G);
368 +#endif // OS_CPU_SOLARIS_X86_GLOBALS_SOLARIS_X86_HPP
369 diff -urN /tmp/a/javaThread_solaris_x86.cpp b/src/hotspot/os_cpu/solaris_x86/javaThread_solaris_x86.cpp
370 --- /tmp/a/javaThread_solaris_x86.cpp 1970-01-01 01:00:00.000000000 +0100
371 +++ b/src/hotspot/os_cpu/solaris_x86/javaThread_solaris_x86.cpp 2024-09-16 14:41:33.969654354 +0100
374 + * Copyright (c) 2003, 2020, Oracle and/or its affiliates. All rights reserved.
375 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
377 + * This code is free software; you can redistribute it and/or modify it
378 + * under the terms of the GNU General Public License version 2 only, as
379 + * published by the Free Software Foundation.
381 + * This code is distributed in the hope that it will be useful, but WITHOUT
382 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
383 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
384 + * version 2 for more details (a copy is included in the LICENSE file that
385 + * accompanied this code).
387 + * You should have received a copy of the GNU General Public License version
388 + * 2 along with this work; if not, write to the Free Software Foundation,
389 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
391 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
392 + * or visit www.oracle.com if you need additional information or have any
397 +#include "precompiled.hpp"
398 +#include "runtime/frame.inline.hpp"
399 +#include "runtime/javaThread.hpp"
401 +frame JavaThread::pd_last_frame() {
402 + assert(has_last_Java_frame(), "must have last_Java_sp() when suspended");
403 + vmassert(_anchor.last_Java_pc() != NULL, "not walkable");
404 + return frame(_anchor.last_Java_sp(), _anchor.last_Java_fp(), _anchor.last_Java_pc());
407 +// For Forte Analyzer AsyncGetCallTrace profiling support - thread is
408 +// currently interrupted by SIGPROF
409 +bool JavaThread::pd_get_top_frame_for_signal_handler(frame* fr_addr,
410 + void* ucontext, bool isInJava) {
411 + assert(Thread::current() == this, "caller must be current thread");
412 + return pd_get_top_frame(fr_addr, ucontext, isInJava);
415 +bool JavaThread::pd_get_top_frame_for_profiling(frame* fr_addr,
416 + void* ucontext, bool isInJava) {
417 + return pd_get_top_frame(fr_addr, ucontext, isInJava);
420 +bool JavaThread::pd_get_top_frame(frame* fr_addr,
421 + void* ucontext, bool isInJava) {
422 + assert(this->is_Java_thread(), "must be JavaThread");
423 + JavaThread* jt = (JavaThread *)this;
425 + // There is small window where last_Java_frame is not walkable or safe
426 + if (jt->has_last_Java_frame() && jt->frame_anchor()->walkable()) {
427 + *fr_addr = jt->pd_last_frame();
431 + ucontext_t* uc = (ucontext_t*) ucontext;
433 + // We always want to use the initial frame we create from the ucontext as
434 + // it certainly signals where we currently are. However that frame may not
435 + // be safe for calling sender. In that case if we have a last_Java_frame
436 + // then the forte walker will switch to that frame as the virtual sender
437 + // for the frame we create here which is not sender safe.
441 + address addr = os::fetch_frame_from_context(uc, &ret_sp, &ret_fp);
443 + // Something would really have to be screwed up to get a NULL pc
445 + if (addr == NULL) {
446 + // ucontext wasn't useful
450 + // If sp and fp are nonsense just leave them out
452 + if (!jt->is_in_full_stack((address)ret_sp)) {
456 + // sp is reasonable is fp reasonable?
457 + if (!jt->is_in_stack_range_incl((address)ret_fp, (address)ret_sp)) {
462 + frame ret_frame(ret_sp, ret_fp, addr);
464 + *fr_addr = ret_frame;
469 +void JavaThread::cache_global_variables() { }
470 diff -urN /tmp/a/javaThread_solaris_x86.hpp b/src/hotspot/os_cpu/solaris_x86/javaThread_solaris_x86.hpp
471 --- /tmp/a/javaThread_solaris_x86.hpp 1970-01-01 01:00:00.000000000 +0100
472 +++ b/src/hotspot/os_cpu/solaris_x86/javaThread_solaris_x86.hpp 2024-09-16 14:41:33.969734465 +0100
475 + * Copyright (c) 1999, 2019, Oracle and/or its affiliates. All rights reserved.
476 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
478 + * This code is free software; you can redistribute it and/or modify it
479 + * under the terms of the GNU General Public License version 2 only, as
480 + * published by the Free Software Foundation.
482 + * This code is distributed in the hope that it will be useful, but WITHOUT
483 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
484 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
485 + * version 2 for more details (a copy is included in the LICENSE file that
486 + * accompanied this code).
488 + * You should have received a copy of the GNU General Public License version
489 + * 2 along with this work; if not, write to the Free Software Foundation,
490 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
492 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
493 + * or visit www.oracle.com if you need additional information or have any
498 +#ifndef OS_CPU_SOLARIS_X86_JAVATHREAD_SOLARIS_X86_HPP
499 +#define OS_CPU_SOLARIS_X86_JAVATHREAD_SOLARIS_X86_HPP
502 + void pd_initialize() { _anchor.clear(); }
504 + frame pd_last_frame();
508 + void set_base_of_stack_pointer(intptr_t* base_sp) {}
510 + static ByteSize last_Java_fp_offset() {
511 + return byte_offset_of(JavaThread, _anchor) + JavaFrameAnchor::last_Java_fp_offset();
514 + intptr_t* base_of_stack_pointer() { return NULL; }
515 + void record_base_of_stack_pointer() {}
517 + bool pd_get_top_frame_for_signal_handler(frame* fr_addr, void* ucontext,
519 + bool pd_get_top_frame_for_profiling(frame* fr_addr, void* ucontext,
522 + bool pd_get_top_frame(frame* fr_addr, void* ucontext,
526 + // These routines are only used on cpu architectures that
527 + // have separate register stacks (Itanium).
528 + static bool register_stack_overflow() { return false; }
529 + static void enable_register_stack_guard() {}
530 + static void disable_register_stack_guard() {}
532 +#endif // OS_CPU_SOLARIS_X86_JAVATHREAD_SOLARIS_X86_HPP
533 diff -urN /tmp/a/orderAccess_solaris_x86.hpp b/src/hotspot/os_cpu/solaris_x86/orderAccess_solaris_x86.hpp
534 --- /tmp/a/orderAccess_solaris_x86.hpp 1970-01-01 01:00:00.000000000 +0100
535 +++ b/src/hotspot/os_cpu/solaris_x86/orderAccess_solaris_x86.hpp 2024-09-16 14:41:33.968909114 +0100
538 + * Copyright (c) 2003, 2019, Oracle and/or its affiliates. All rights reserved.
539 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
541 + * This code is free software; you can redistribute it and/or modify it
542 + * under the terms of the GNU General Public License version 2 only, as
543 + * published by the Free Software Foundation.
545 + * This code is distributed in the hope that it will be useful, but WITHOUT
546 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
547 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
548 + * version 2 for more details (a copy is included in the LICENSE file that
549 + * accompanied this code).
551 + * You should have received a copy of the GNU General Public License version
552 + * 2 along with this work; if not, write to the Free Software Foundation,
553 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
555 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
556 + * or visit www.oracle.com if you need additional information or have any
561 +#ifndef OS_CPU_SOLARIS_X86_ORDERACCESS_SOLARIS_X86_HPP
562 +#define OS_CPU_SOLARIS_X86_ORDERACCESS_SOLARIS_X86_HPP
564 +// Included in orderAccess.hpp header file.
566 +// Compiler version last used for testing: solaris studio 12u3
567 +// Please update this information when this file changes
569 +// Implementation of class OrderAccess.
571 +// A compiler barrier, forcing the C++ compiler to invalidate all memory assumptions
572 +inline void compiler_barrier() {
573 + __asm__ volatile ("" : : : "memory");
576 +inline void OrderAccess::loadload() { compiler_barrier(); }
577 +inline void OrderAccess::storestore() { compiler_barrier(); }
578 +inline void OrderAccess::loadstore() { compiler_barrier(); }
579 +inline void OrderAccess::storeload() { fence(); }
581 +inline void OrderAccess::acquire() { compiler_barrier(); }
582 +inline void OrderAccess::release() { compiler_barrier(); }
584 +inline void OrderAccess::fence() {
585 + __asm__ volatile ("lock; addl $0,0(%%rsp)" : : : "cc", "memory");
586 + compiler_barrier();
589 +inline void OrderAccess::cross_modify_fence_impl() {
591 + __asm__ volatile ("cpuid " : "+a" (idx) : : "ebx", "ecx", "edx", "memory");
594 +#endif // OS_CPU_SOLARIS_X86_ORDERACCESS_SOLARIS_X86_HPP
595 diff -urN /tmp/a/os_solaris_x86.cpp b/src/hotspot/os_cpu/solaris_x86/os_solaris_x86.cpp
596 --- /tmp/a/os_solaris_x86.cpp 1970-01-01 01:00:00.000000000 +0100
597 +++ b/src/hotspot/os_cpu/solaris_x86/os_solaris_x86.cpp 2024-09-16 14:41:34.008006119 +0100
600 + * Copyright (c) 1999, 2020, Oracle and/or its affiliates. All rights reserved.
601 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
603 + * This code is free software; you can redistribute it and/or modify it
604 + * under the terms of the GNU General Public License version 2 only, as
605 + * published by the Free Software Foundation.
607 + * This code is distributed in the hope that it will be useful, but WITHOUT
608 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
609 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
610 + * version 2 for more details (a copy is included in the LICENSE file that
611 + * accompanied this code).
613 + * You should have received a copy of the GNU General Public License version
614 + * 2 along with this work; if not, write to the Free Software Foundation,
615 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
617 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
618 + * or visit www.oracle.com if you need additional information or have any
623 +// no precompiled headers
625 +#include "asm/macroAssembler.hpp"
626 +#include "classfile/classLoader.hpp"
627 +#include "classfile/systemDictionary.hpp"
628 +#include "classfile/vmSymbols.hpp"
629 +#include "code/codeCache.hpp"
630 +#include "code/vtableStubs.hpp"
631 +#include "interpreter/interpreter.hpp"
632 +#include "logging/log.hpp"
633 +#include "memory/allocation.inline.hpp"
634 +#include "os_solaris.hpp"
635 +#include "os_posix.hpp"
636 +#include "prims/jniFastGetField.hpp"
637 +#include "prims/jvm_misc.hpp"
638 +#include "runtime/arguments.hpp"
639 +#include "runtime/frame.inline.hpp"
640 +#include "runtime/interfaceSupport.inline.hpp"
641 +#include "runtime/java.hpp"
642 +#include "runtime/javaCalls.hpp"
643 +#include "runtime/mutexLocker.hpp"
644 +#include "runtime/osThread.hpp"
645 +#include "runtime/safepointMechanism.hpp"
646 +#include "runtime/sharedRuntime.hpp"
647 +#include "runtime/stubRoutines.hpp"
648 +#include "runtime/thread.inline.hpp"
649 +#include "runtime/timer.hpp"
650 +#include "signals_posix.hpp"
651 +#include "utilities/align.hpp"
652 +#include "utilities/events.hpp"
653 +#include "utilities/vmError.hpp"
655 +// put OS-includes here
656 +# include <sys/types.h>
657 +# include <sys/mman.h>
658 +# include <pthread.h>
659 +# include <signal.h>
660 +# include <setjmp.h>
664 +# include <unistd.h>
665 +# include <sys/resource.h>
666 +# include <thread.h>
667 +# include <sys/stat.h>
668 +# include <sys/time.h>
669 +# include <sys/filio.h>
670 +# include <sys/utsname.h>
671 +# include <sys/systeminfo.h>
672 +# include <sys/socket.h>
673 +# include <sys/trap.h>
674 +# include <sys/lwp.h>
676 +# include <sys/lwp.h>
677 +# include <procfs.h>
680 +#define MAX_PATH (2 * K)
682 +// Minimum usable stack sizes required to get to user code. Space for
683 +// HotSpot guard pages is added later.
685 +// The adlc generated method 'State::MachNodeGenerator(int)' used by the C2 compiler
686 +// threads requires a large stack with the Solaris Studio C++ compiler version 5.13
687 +// and product VM builds (debug builds require significantly less stack space).
688 +size_t os::_compiler_thread_min_stack_allowed = 325 * K;
689 +size_t os::_java_thread_min_stack_allowed = 48 * K;
690 +size_t os::_vm_internal_thread_min_stack_allowed = 224 * K;
692 +size_t os::_compiler_thread_min_stack_allowed = 32 * K;
693 +size_t os::_java_thread_min_stack_allowed = 32 * K;
694 +size_t os::_vm_internal_thread_min_stack_allowed = 64 * K;
698 +#define REG_SP REG_RSP
699 +#define REG_PC REG_RIP
700 +#define REG_FP REG_RBP
705 +// 4900493 counter to prevent runaway LDTR refresh attempt
707 +static volatile int ldtr_refresh = 0;
708 +// the libthread instruction that faults because of the stale LDTR
710 +static const unsigned char movlfs[] = { 0x8e, 0xe0 // movl %eax,%fs
714 +char* os::non_memory_address_word() {
715 + // Must never look like an address returned by reserve_memory,
716 + // even in its subfields (as defined by the CPU immediate fields,
717 + // if the CPU splits constants across multiple instructions).
722 +// Validate a ucontext retrieved from walking a uc_link of a ucontext.
723 +// There are issues with libthread giving out uc_links for different threads
724 +// on the same uc_link chain and bad or circular links.
726 +bool os::Solaris::valid_ucontext(Thread* thread, const ucontext_t* valid, const ucontext_t* suspect) {
727 + if (valid >= suspect ||
728 + valid->uc_stack.ss_flags != suspect->uc_stack.ss_flags ||
729 + valid->uc_stack.ss_sp != suspect->uc_stack.ss_sp ||
730 + valid->uc_stack.ss_size != suspect->uc_stack.ss_size) {
731 + DEBUG_ONLY(tty->print_cr("valid_ucontext: failed test 1");)
735 + if (thread->is_Java_thread()) {
736 + if (!thread->is_in_full_stack_checked((address)suspect)) {
737 + DEBUG_ONLY(tty->print_cr("valid_ucontext: uc_link not in thread stack");)
740 + if (!thread->is_in_full_stack_checked((address) suspect->uc_mcontext.gregs[REG_SP])) {
741 + DEBUG_ONLY(tty->print_cr("valid_ucontext: stackpointer not in thread stack");)
748 +// We will only follow one level of uc_link since there are libthread
749 +// issues with ucontext linking and it is better to be safe and just
750 +// let caller retry later.
751 +const ucontext_t* os::Solaris::get_valid_uc_in_signal_handler(Thread *thread,
752 + const ucontext_t *uc) {
754 + const ucontext_t *retuc = NULL;
757 + if (uc->uc_link == NULL) {
758 + // cannot validate without uc_link so accept current ucontext
760 + } else if (os::Solaris::valid_ucontext(thread, uc, uc->uc_link)) {
761 + // first ucontext is valid so try the next one
763 + if (uc->uc_link == NULL) {
764 + // cannot validate without uc_link so accept current ucontext
766 + } else if (os::Solaris::valid_ucontext(thread, uc, uc->uc_link)) {
767 + // the ucontext one level down is also valid so return it
775 +void os::Posix::ucontext_set_pc(ucontext_t* uc, address pc) {
776 + uc->uc_mcontext.gregs [REG_PC] = (greg_t) pc;
779 +// Assumes ucontext is valid
780 +intptr_t* os::Solaris::ucontext_get_sp(const ucontext_t *uc) {
781 + return (intptr_t*)uc->uc_mcontext.gregs[REG_SP];
784 +// Assumes ucontext is valid
785 +intptr_t* os::Solaris::ucontext_get_fp(const ucontext_t *uc) {
786 + return (intptr_t*)uc->uc_mcontext.gregs[REG_FP];
789 +address os::Posix::ucontext_get_pc(const ucontext_t *uc) {
790 + return (address) uc->uc_mcontext.gregs[REG_PC];
793 +address os::fetch_frame_from_context(const void* ucVoid,
794 + intptr_t** ret_sp, intptr_t** ret_fp) {
797 + const ucontext_t *uc = (const ucontext_t*)ucVoid;
800 + epc = os::Posix::ucontext_get_pc(uc);
801 + if (ret_sp) *ret_sp = os::Solaris::ucontext_get_sp(uc);
802 + if (ret_fp) *ret_fp = os::Solaris::ucontext_get_fp(uc);
805 + if (ret_sp) *ret_sp = (intptr_t *)NULL;
806 + if (ret_fp) *ret_fp = (intptr_t *)NULL;
812 +frame os::fetch_frame_from_context(const void* ucVoid) {
815 + address epc = fetch_frame_from_context(ucVoid, &sp, &fp);
816 + return frame(sp, fp, epc);
819 +frame os::fetch_compiled_frame_from_context(const void* ucVoid) {
820 + const ucontext_t* uc = (const ucontext_t*)ucVoid;
821 + frame fr = os::fetch_frame_from_context(uc);
822 + // in compiled code, the stack banging is performed just after the return pc
823 + // has been pushed on the stack
824 + return frame(fr.sp() + 1, fr.fp(), (address)*(fr.sp()));
827 +frame os::get_sender_for_C_frame(frame* fr) {
828 + return frame(fr->sender_sp(), fr->link(), fr->sender_pc());
831 +extern "C" intptr_t *_get_current_sp() {
832 + register intptr_t *rsp __asm__ ("rsp");
836 +address os::current_stack_pointer() {
837 + return (address)_get_current_sp();
840 +extern "C" intptr_t *_get_current_fp() {
841 + register intptr_t **rbp __asm__ ("rbp");
842 + return (intptr_t*) *rbp;
845 +frame os::current_frame() {
846 + intptr_t* fp = _get_current_fp(); // it's inlined so want current fp
847 + // fp is for os::current_frame. We want the fp for our caller.
848 + frame myframe((intptr_t*)os::current_stack_pointer(),
850 + CAST_FROM_FN_PTR(address, os::current_frame));
851 + frame caller_frame = os::get_sender_for_C_frame(&myframe);
853 + if (os::is_first_C_frame(&caller_frame)) {
854 + // stack is not walkable
855 + frame ret; // This will be a null useless frame
858 + // return frame for our caller's caller
859 + return os::get_sender_for_C_frame(&caller_frame);
864 +juint os::cpu_microcode_revision() {
866 + // to implement this, look at the source for ucodeadm -v
870 +bool PosixSignals::pd_hotspot_signal_handler(int sig, siginfo_t* info,
871 + ucontext_t* uc, JavaThread* thread) {
873 + if (info == NULL || info->si_code <= 0 || info->si_code == SI_NOINFO) {
874 + // can't decode this kind of signal
877 + assert(sig == info->si_signo, "bad siginfo");
880 + // decide if this trap can be handled by a stub
881 + address stub = NULL;
886 + if (info != NULL && uc != NULL && thread != NULL) {
887 + // factor me: getPCfromContext
888 + pc = (address) uc->uc_mcontext.gregs[REG_PC];
890 + // Handle ALL stack overflow variations here
891 + if (sig == SIGSEGV && info->si_code == SEGV_ACCERR) {
892 + address addr = (address) info->si_addr;
893 + if (thread->is_in_full_stack(addr)) {
895 + if (os::Posix::handle_stack_overflow(thread, addr, pc, uc, &stub)) {
896 + return true; // continue
901 + if ((sig == SIGSEGV) && VM_Version::is_cpuinfo_segv_addr(pc)) {
902 + // Verify that OS save/restore AVX registers.
903 + stub = VM_Version::cpuinfo_cont_addr();
906 + if (thread->thread_state() == _thread_in_vm ||
907 + thread->thread_state() == _thread_in_native) {
908 + if (sig == SIGBUS && info->si_code == BUS_OBJERR && thread->doing_unsafe_access()) {
909 + address next_pc = Assembler::locate_next_instruction(pc);
910 + if (UnsafeMemoryAccess::contains_pc(pc)) {
911 + next_pc = UnsafeMemoryAccess::page_error_continue_pc(pc);
913 + stub = SharedRuntime::handle_unsafe_access(thread, next_pc);
917 + if (thread->thread_state() == _thread_in_Java) {
918 + // Support Safepoint Polling
919 + if ( sig == SIGSEGV && SafepointMechanism::is_poll_address((address)info->si_addr)) {
920 + stub = SharedRuntime::get_poll_stub(pc);
922 + else if (sig == SIGBUS && info->si_code == BUS_OBJERR) {
923 + // BugId 4454115: A read from a MappedByteBuffer can fault
924 + // here if the underlying file has been truncated.
925 + // Do not crash the VM in such a case.
926 + CodeBlob* cb = CodeCache::find_blob(pc);
928 + nmethod* nm = cb->as_nmethod_or_null();
929 + bool is_unsafe_memory_access = thread->doing_unsafe_access() && UnsafeMemoryAccess::contains_pc(pc);
930 + if ((nm != NULL && nm->has_unsafe_access()) || is_unsafe_memory_access) {
931 + address next_pc = Assembler::locate_next_instruction(pc);
932 + if (is_unsafe_memory_access) {
933 + next_pc = UnsafeMemoryAccess::page_error_continue_pc(pc);
935 + stub = SharedRuntime::handle_unsafe_access(thread, next_pc);
939 + if (sig == SIGFPE && info->si_code == FPE_INTDIV) {
940 + // integer divide by zero
941 + stub = SharedRuntime::continuation_for_implicit_exception(thread, pc, SharedRuntime::IMPLICIT_DIVIDE_BY_ZERO);
944 + else if (sig == SIGFPE && info->si_code == FPE_FLTDIV) {
945 + // floating-point divide by zero
946 + stub = SharedRuntime::continuation_for_implicit_exception(thread, pc, SharedRuntime::IMPLICIT_DIVIDE_BY_ZERO);
948 + else if (sig == SIGFPE && info->si_code == FPE_FLTINV) {
949 + // The encoding of D2I in i486.ad can cause an exception prior
950 + // to the fist instruction if there was an invalid operation
951 + // pending. We want to dismiss that exception. From the win_32
952 + // side it also seems that if it really was the fist causing
953 + // the exception that we do the d2i by hand with different
954 + // rounding. Seems kind of weird. QQQ TODO
955 + // Note that we take the exception at the NEXT floating point instruction.
956 + if (pc[0] == 0xDB) {
957 + assert(pc[0] == 0xDB, "not a FIST opcode");
958 + assert(pc[1] == 0x14, "not a FIST opcode");
959 + assert(pc[2] == 0x24, "not a FIST opcode");
962 + assert(pc[-3] == 0xDB, "not an flt invalid opcode");
963 + assert(pc[-2] == 0x14, "not an flt invalid opcode");
964 + assert(pc[-1] == 0x24, "not an flt invalid opcode");
967 + else if (sig == SIGFPE ) {
968 + tty->print_cr("caught SIGFPE, info 0x%x.", info->si_code);
972 + // QQQ It doesn't seem that we need to do this on x86 because we should be able
973 + // to return properly from the handler without this extra stuff on the back side.
975 + else if (sig == SIGSEGV && info->si_code > 0 &&
976 + MacroAssembler::uses_implicit_null_check(info->si_addr)) {
977 + // Determination of interpreter/vtable stub/compiled code null exception
978 + stub = SharedRuntime::continuation_for_implicit_exception(thread, pc, SharedRuntime::IMPLICIT_NULL);
982 + // jni_fast_Get<Primitive>Field can trap at certain pc's if a GC kicks in
983 + // and the heap gets shrunk before the field access.
984 + if ((sig == SIGSEGV) || (sig == SIGBUS)) {
985 + address addr = JNI_FastGetField::find_slowcase_pc(pc);
986 + if (addr != (address)-1) {
992 + // Execution protection violation
994 + // Preventative code for future versions of Solaris which may
995 + // enable execution protection when running the 32-bit VM on AMD64.
997 + // This should be kept as the last step in the triage. We don't
998 + // have a dedicated trap number for a no-execute fault, so be
999 + // conservative and allow other handlers the first shot.
1001 + // Note: We don't test that info->si_code == SEGV_ACCERR here.
1002 + // this si_code is so generic that it is almost meaningless; and
1003 + // the si_code for this condition may change in the future.
1004 + // Furthermore, a false-positive should be harmless.
1005 + if (UnguardOnExecutionViolation > 0 &&
1006 + (sig == SIGSEGV || sig == SIGBUS) &&
1007 + uc->uc_mcontext.gregs[TRAPNO] == T_PGFLT) { // page fault
1008 + int page_size = os::vm_page_size();
1009 + address addr = (address) info->si_addr;
1010 + address pc = (address) uc->uc_mcontext.gregs[REG_PC];
1011 + // Make sure the pc and the faulting address are sane.
1013 + // If an instruction spans a page boundary, and the page containing
1014 + // the beginning of the instruction is executable but the following
1015 + // page is not, the pc and the faulting address might be slightly
1016 + // different - we still want to unguard the 2nd page in this case.
1018 + // 15 bytes seems to be a (very) safe value for max instruction size.
1019 + bool pc_is_near_addr =
1020 + (pointer_delta((void*) addr, (void*) pc, sizeof(char)) < 15);
1021 + bool instr_spans_page_boundary =
1022 + (align_down((intptr_t) pc ^ (intptr_t) addr,
1023 + (intptr_t) page_size) > 0);
1025 + if (pc == addr || (pc_is_near_addr && instr_spans_page_boundary)) {
1026 + static volatile address last_addr =
1027 + (address) os::non_memory_address_word();
1029 + // In conservative mode, don't unguard unless the address is in the VM
1030 + if (addr != last_addr &&
1031 + (UnguardOnExecutionViolation > 1 || os::address_is_in_vm(addr))) {
1033 + // Make memory rwx and retry
1034 + address page_start = align_down(addr, page_size);
1035 + bool res = os::protect_memory((char*) page_start, page_size,
1036 + os::MEM_PROT_RWX);
1038 + log_debug(os)("Execution protection violation "
1039 + "at " INTPTR_FORMAT
1040 + ", unguarding " INTPTR_FORMAT ": %s, errno=%d", p2i(addr),
1041 + p2i(page_start), (res ? "success" : "failed"), errno);
1044 + // Set last_addr so if we fault again at the same address, we don't end
1045 + // up in an endless loop.
1047 + // There are two potential complications here. Two threads trapping at
1048 + // the same address at the same time could cause one of the threads to
1049 + // think it already unguarded, and abort the VM. Likely very rare.
1051 + // The other race involves two threads alternately trapping at
1052 + // different addresses and failing to unguard the page, resulting in
1053 + // an endless loop. This condition is probably even more unlikely than
1056 + // Although both cases could be avoided by using locks or thread local
1057 + // last_addr, these solutions are unnecessary complication: this
1058 + // handler is a best-effort safety net, not a complete solution. It is
1059 + // disabled by default and should only be used as a workaround in case
1060 + // we missed any no-execute-unsafe VM code.
1067 + if (stub != NULL) {
1068 + // save all thread context in case we need to restore it
1070 + if (thread != NULL) thread->set_saved_exception_pc(pc);
1071 + // 12/02/99: On Sparc it appears that the full context is also saved
1072 + // but as yet, no one looks at or restores that saved context
1073 + os::Posix::ucontext_set_pc(uc, stub);
1080 +void os::print_context(outputStream *st, const void *context) {
1081 + if (context == NULL) return;
1083 + const ucontext_t *uc = (const ucontext_t*)context;
1084 + st->print_cr("Registers:");
1086 + st->print( "RAX=" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_RAX]);
1087 + st->print(", RBX=" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_RBX]);
1088 + st->print(", RCX=" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_RCX]);
1089 + st->print(", RDX=" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_RDX]);
1091 + st->print( "RSP=" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_RSP]);
1092 + st->print(", RBP=" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_RBP]);
1093 + st->print(", RSI=" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_RSI]);
1094 + st->print(", RDI=" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_RDI]);
1096 + st->print( "R8 =" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_R8]);
1097 + st->print(", R9 =" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_R9]);
1098 + st->print(", R10=" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_R10]);
1099 + st->print(", R11=" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_R11]);
1101 + st->print( "R12=" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_R12]);
1102 + st->print(", R13=" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_R13]);
1103 + st->print(", R14=" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_R14]);
1104 + st->print(", R15=" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_R15]);
1106 + st->print( "RIP=" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_RIP]);
1107 + st->print(", RFLAGS=" INTPTR_FORMAT, uc->uc_mcontext.gregs[REG_RFL]);
1109 + st->print( "EAX=" INTPTR_FORMAT, uc->uc_mcontext.gregs[EAX]);
1110 + st->print(", EBX=" INTPTR_FORMAT, uc->uc_mcontext.gregs[EBX]);
1111 + st->print(", ECX=" INTPTR_FORMAT, uc->uc_mcontext.gregs[ECX]);
1112 + st->print(", EDX=" INTPTR_FORMAT, uc->uc_mcontext.gregs[EDX]);
1114 + st->print( "ESP=" INTPTR_FORMAT, uc->uc_mcontext.gregs[UESP]);
1115 + st->print(", EBP=" INTPTR_FORMAT, uc->uc_mcontext.gregs[EBP]);
1116 + st->print(", ESI=" INTPTR_FORMAT, uc->uc_mcontext.gregs[ESI]);
1117 + st->print(", EDI=" INTPTR_FORMAT, uc->uc_mcontext.gregs[EDI]);
1119 + st->print( "EIP=" INTPTR_FORMAT, uc->uc_mcontext.gregs[EIP]);
1120 + st->print(", EFLAGS=" INTPTR_FORMAT, uc->uc_mcontext.gregs[EFL]);
1126 +void os::print_register_info(outputStream *st, const void *context, int& continuation) {
1127 + const int register_count = AMD64_ONLY(16) NOT_AMD64(8);
1128 + int n = continuation;
1129 + assert(n >= 0 && n <= register_count, "Invalid continuation value");
1130 + if (context == nullptr || n == register_count) {
1134 + const ucontext_t *uc = (const ucontext_t*)context;
1135 + while (n < register_count) {
1136 + // Update continuation with next index before printing location
1137 + continuation = n + 1;
1138 +# define CASE_PRINT_REG(n, str, id) case n: st->print(str); print_location(st, uc->uc_mcontext.gregs[REG_##id]);
1141 + CASE_PRINT_REG( 0, "RAX=", RAX); break;
1142 + CASE_PRINT_REG( 1, "RBX=", RBX); break;
1143 + CASE_PRINT_REG( 2, "RCX=", RCX); break;
1144 + CASE_PRINT_REG( 3, "RDX=", RDX); break;
1145 + CASE_PRINT_REG( 4, "RSP=", RSP); break;
1146 + CASE_PRINT_REG( 5, "RBP=", RBP); break;
1147 + CASE_PRINT_REG( 6, "RSI=", RSI); break;
1148 + CASE_PRINT_REG( 7, "RDI=", RDI); break;
1149 + CASE_PRINT_REG( 8, "R8 =", R8); break;
1150 + CASE_PRINT_REG( 9, "R9 =", R9); break;
1151 + CASE_PRINT_REG(10, "R10=", R10); break;
1152 + CASE_PRINT_REG(11, "R11=", R11); break;
1153 + CASE_PRINT_REG(12, "R12=", R12); break;
1154 + CASE_PRINT_REG(13, "R13=", R13); break;
1155 + CASE_PRINT_REG(14, "R14=", R14); break;
1156 + CASE_PRINT_REG(15, "R15=", R15); break;
1158 + CASE_PRINT_REG(0, "EAX=", EAX); break;
1159 + CASE_PRINT_REG(1, "EBX=", EBX); break;
1160 + CASE_PRINT_REG(2, "ECX=", ECX); break;
1161 + CASE_PRINT_REG(3, "EDX=", EDX); break;
1162 + CASE_PRINT_REG(4, "ESP=", ESP); break;
1163 + CASE_PRINT_REG(5, "EBP=", EBP); break;
1164 + CASE_PRINT_REG(6, "ESI=", ESI); break;
1165 + CASE_PRINT_REG(7, "EDI=", EDI); break;
1168 +# undef CASE_PRINT_REG
1174 +void os::Solaris::init_thread_fpu_state(void) {
1177 +void os::setup_fpu() {}
1180 +void os::verify_stack_alignment() {
1181 + assert(((intptr_t)os::current_stack_pointer() & (StackAlignmentInBytes-1)) == 0, "incorrect stack alignment");
1185 +int os::extra_bang_size_in_bytes() {
1186 + // JDK-8050147 requires the full cache line bang for x86.
1187 + return VM_Version::L1_line_size();
1189 diff -urN /tmp/a/os_solaris_x86.hpp b/src/hotspot/os_cpu/solaris_x86/os_solaris_x86.hpp
1190 --- /tmp/a/os_solaris_x86.hpp 1970-01-01 01:00:00.000000000 +0100
1191 +++ b/src/hotspot/os_cpu/solaris_x86/os_solaris_x86.hpp 2024-09-16 14:41:33.995588707 +0100
1194 + * Copyright (c) 1999, 2019, Oracle and/or its affiliates. All rights reserved.
1195 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
1197 + * This code is free software; you can redistribute it and/or modify it
1198 + * under the terms of the GNU General Public License version 2 only, as
1199 + * published by the Free Software Foundation.
1201 + * This code is distributed in the hope that it will be useful, but WITHOUT
1202 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
1203 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
1204 + * version 2 for more details (a copy is included in the LICENSE file that
1205 + * accompanied this code).
1207 + * You should have received a copy of the GNU General Public License version
1208 + * 2 along with this work; if not, write to the Free Software Foundation,
1209 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
1211 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
1212 + * or visit www.oracle.com if you need additional information or have any
1217 +#ifndef OS_CPU_SOLARIS_X86_OS_SOLARIS_X86_HPP
1218 +#define OS_CPU_SOLARIS_X86_OS_SOLARIS_X86_HPP
1221 + // NOTE: we are back in class os here, not Solaris
1224 + static void setup_fpu() {}
1226 + static int32_t (*atomic_xchg_func) (int32_t, volatile int32_t*);
1227 + static int32_t (*atomic_cmpxchg_func) (int32_t, volatile int32_t*, int32_t);
1228 + static int64_t (*atomic_cmpxchg_long_func)(int64_t, volatile int64_t*, int64_t);
1229 + static int32_t (*atomic_add_func) (int32_t, volatile int32_t*);
1231 + static int32_t atomic_xchg_bootstrap (int32_t, volatile int32_t*);
1232 + static int32_t atomic_cmpxchg_bootstrap (int32_t, volatile int32_t*, int32_t);
1233 + static int64_t atomic_cmpxchg_long_bootstrap(int64_t, volatile int64_t*, int64_t);
1234 + static int32_t atomic_add_bootstrap (int32_t, volatile int32_t*);
1236 + static void setup_fpu();
1239 + static juint cpu_microcode_revision();
1241 + static jlong rdtsc();
1243 + static bool is_allocatable(size_t bytes);
1245 + // Used to register dynamic code cache area with the OS
1246 + // Note: Currently only used in 64 bit Windows implementations
1247 + static bool register_code_area(char *low, char *high) { return true; }
1249 +#endif // OS_CPU_SOLARIS_X86_OS_SOLARIS_X86_HPP
1250 diff -urN /tmp/a/os_solaris_x86.inline.hpp b/src/hotspot/os_cpu/solaris_x86/os_solaris_x86.inline.hpp
1251 --- /tmp/a/os_solaris_x86.inline.hpp 1970-01-01 01:00:00.000000000 +0100
1252 +++ b/src/hotspot/os_cpu/solaris_x86/os_solaris_x86.inline.hpp 2024-09-16 14:41:33.969321179 +0100
1255 + * Copyright (c) 2011, 2019, Oracle and/or its affiliates. All rights reserved.
1256 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
1258 + * This code is free software; you can redistribute it and/or modify it
1259 + * under the terms of the GNU General Public License version 2 only, as
1260 + * published by the Free Software Foundation.
1262 + * This code is distributed in the hope that it will be useful, but WITHOUT
1263 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
1264 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
1265 + * version 2 for more details (a copy is included in the LICENSE file that
1266 + * accompanied this code).
1268 + * You should have received a copy of the GNU General Public License version
1269 + * 2 along with this work; if not, write to the Free Software Foundation,
1270 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
1272 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
1273 + * or visit www.oracle.com if you need additional information or have any
1278 +#ifndef OS_CPU_SOLARIS_X86_OS_SOLARIS_X86_INLINE_HPP
1279 +#define OS_CPU_SOLARIS_X86_OS_SOLARIS_X86_INLINE_HPP
1281 +#include "runtime/os.hpp"
1283 +// See http://www.technovelty.org/code/c/reading-rdtsc.htl for details
1284 +inline jlong os::rdtsc() {
1286 + uint32_t ts1, ts2;
1287 + __asm__ __volatile__ ("rdtsc" : "=a" (ts1), "=d" (ts2));
1288 + res = ((uint64_t)ts1 | (uint64_t)ts2 << 32);
1289 + return (jlong)res;
1292 +#endif // OS_CPU_SOLARIS_X86_OS_SOLARIS_X86_INLINE_HPP
1293 diff -urN /tmp/a/prefetch_solaris_x86.inline.hpp b/src/hotspot/os_cpu/solaris_x86/prefetch_solaris_x86.inline.hpp
1294 --- /tmp/a/prefetch_solaris_x86.inline.hpp 1970-01-01 01:00:00.000000000 +0100
1295 +++ b/src/hotspot/os_cpu/solaris_x86/prefetch_solaris_x86.inline.hpp 2024-09-16 14:41:33.969397130 +0100
1298 + * Copyright (c) 2003, 2019, Oracle and/or its affiliates. All rights reserved.
1299 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
1301 + * This code is free software; you can redistribute it and/or modify it
1302 + * under the terms of the GNU General Public License version 2 only, as
1303 + * published by the Free Software Foundation.
1305 + * This code is distributed in the hope that it will be useful, but WITHOUT
1306 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
1307 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
1308 + * version 2 for more details (a copy is included in the LICENSE file that
1309 + * accompanied this code).
1311 + * You should have received a copy of the GNU General Public License version
1312 + * 2 along with this work; if not, write to the Free Software Foundation,
1313 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
1315 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
1316 + * or visit www.oracle.com if you need additional information or have any
1321 +#ifndef OS_CPU_SOLARIS_X86_PREFETCH_SOLARIS_X86_INLINE_HPP
1322 +#define OS_CPU_SOLARIS_X86_PREFETCH_SOLARIS_X86_INLINE_HPP
1324 +#include "runtime/prefetch.hpp"
1326 +inline void Prefetch::read (const void *loc, intx interval) {
1328 + __asm__ ("prefetcht0 (%0,%1,1)" : : "r" (loc), "r" (interval));
1332 +inline void Prefetch::write(void *loc, intx interval) {
1334 + __asm__ ("prefetcht0 (%0,%1,1)" : : "r" (loc), "r" (interval));
1338 +#endif // OS_CPU_SOLARIS_X86_PREFETCH_SOLARIS_X86_INLINE_HPP
1339 diff -urN /tmp/a/safefetch_solaris_x86_64.S b/src/hotspot/os_cpu/solaris_x86/safefetch_solaris_x86_64.S
1340 --- /tmp/a/safefetch_solaris_x86_64.S 1970-01-01 01:00:00.000000000 +0100
1341 +++ b/src/hotspot/os_cpu/solaris_x86/safefetch_solaris_x86_64.S 2024-09-16 14:41:34.012179534 +0100
1344 +# Copyright (c) 2022 SAP SE. All rights reserved.
1345 +# Copyright (c) 2022, Oracle and/or its affiliates. All rights reserved.
1346 +# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
1348 +# This code is free software; you can redistribute it and/or modify it
1349 +# under the terms of the GNU General Public License version 2 only, as
1350 +# published by the Free Software Foundation.
1352 +# This code is distributed in the hope that it will be useful, but WITHOUT
1353 +# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
1354 +# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
1355 +# version 2 for more details (a copy is included in the LICENSE file that
1356 +# accompanied this code).
1358 +# You should have received a copy of the GNU General Public License version
1359 +# 2 along with this work; if not, write to the Free Software Foundation,
1360 +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
1362 +# Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
1363 +# or visit www.oracle.com if you need additional information or have any
1366 + .globl SafeFetch32_impl
1367 + .globl SafeFetchN_impl
1368 + .globl _SafeFetch32_fault
1369 + .globl _SafeFetchN_fault
1370 + .globl _SafeFetch32_continuation
1371 + .globl _SafeFetchN_continuation
1376 + # Support for int SafeFetch32(int* address, int defaultval);
1379 + # %esi : defaultval
1380 + .type SafeFetch32_impl,@function
1382 +_SafeFetch32_fault:
1383 + movl (%rdi), %eax # load target value, may fault
1385 +_SafeFetch32_continuation:
1386 + movl %esi, %eax # return default
1389 + # Support for intptr_t SafeFetchN(intptr_t* address, intptr_t defaultval);
1392 + # %rsi : defaultval
1393 + .type SafeFetchN_impl,@function
1396 + movq (%rdi), %rax # load target value, may fault
1398 +_SafeFetchN_continuation:
1399 + movq %rsi, %rax # return default
1401 diff -urN /tmp/a/solaris_x86_64.S b/src/hotspot/os_cpu/solaris_x86/solaris_x86_64.S
1402 --- /tmp/a/solaris_x86_64.S 1970-01-01 01:00:00.000000000 +0100
1403 +++ b/src/hotspot/os_cpu/solaris_x86/solaris_x86_64.S 2024-09-16 14:41:33.969557123 +0100
1406 +# Copyright (c) 2004, 2013, Oracle and/or its affiliates. All rights reserved.
1407 +# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
1409 +# This code is free software; you can redistribute it and/or modify it
1410 +# under the terms of the GNU General Public License version 2 only, as
1411 +# published by the Free Software Foundation.
1413 +# This code is distributed in the hope that it will be useful, but WITHOUT
1414 +# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
1415 +# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
1416 +# version 2 for more details (a copy is included in the LICENSE file that
1417 +# accompanied this code).
1419 +# You should have received a copy of the GNU General Public License version
1420 +# 2 along with this work; if not, write to the Free Software Foundation,
1421 +# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
1423 +# Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
1424 +# or visit www.oracle.com if you need additional information or have any
1431 + ## NOTE WELL! The _Copy functions are called directly
1432 + ## from server-compiler-generated code via CallLeafNoFP,
1433 + ## which means that they *must* either not use floating
1434 + ## point or use it in the same manner as does the server
1437 + .globl _Copy_arrayof_conjoint_bytes
1438 + .globl _Copy_conjoint_jshorts_atomic
1439 + .globl _Copy_arrayof_conjoint_jshorts
1440 + .globl _Copy_conjoint_jints_atomic
1441 + .globl _Copy_arrayof_conjoint_jints
1442 + .globl _Copy_conjoint_jlongs_atomic
1443 + .globl _Copy_arrayof_conjoint_jlongs
1445 + .section .text,"ax"
1447 + # Fast thread accessors, used by threadLS_solaris_amd64.cpp
1450 + movq %fs:(%rdi),%rax
1467 + # Support for void Copy::arrayof_conjoint_bytes(void* from,
1472 + # rdx - count, treated as ssize_t
1475 +_Copy_arrayof_conjoint_bytes:
1476 + movq %rdx,%r8 # byte count
1477 + shrq $3,%rdx # qword count
1479 + leaq -1(%rdi,%r8,1),%rax # from + bcount*1 - 1
1484 + leaq -8(%rdi,%rdx,8),%rax # from + qcount*8 - 8
1485 + leaq -8(%rsi,%rdx,8),%rcx # to + qcount*8 - 8
1489 +1: movq 8(%rax,%rdx,8),%rsi
1490 + movq %rsi,8(%rcx,%rdx,8)
1493 +2: testq $4,%r8 # check for trailing dword
1495 + movl 8(%rax),%esi # copy trailing dword
1498 + addq $4,%rcx # original %rsi is trashed, so we
1499 + # can't use it as a base register
1500 +3: testq $2,%r8 # check for trailing word
1502 + movw 8(%rax),%si # copy trailing word
1505 +4: testq $1,%r8 # check for trailing byte
1507 + movb -1(%rdi,%r8,1),%al # copy trailing byte
1511 +6: movq -24(%rax,%rdx,8),%rsi
1512 + movq %rsi,-24(%rcx,%rdx,8)
1513 + movq -16(%rax,%rdx,8),%rsi
1514 + movq %rsi,-16(%rcx,%rdx,8)
1515 + movq -8(%rax,%rdx,8),%rsi
1516 + movq %rsi,-8(%rcx,%rdx,8)
1517 + movq (%rax,%rdx,8),%rsi
1518 + movq %rsi,(%rcx,%rdx,8)
1525 + testq $1,%r8 # check for trailing byte
1527 + movb -1(%rdi,%r8,1),%cl # copy trailing byte
1528 + movb %cl,-1(%rsi,%r8,1)
1529 + subq $1,%r8 # adjust for possible trailing word
1530 +1: testq $2,%r8 # check for trailing word
1532 + movw -2(%rdi,%r8,1),%cx # copy trailing word
1533 + movw %cx,-2(%rsi,%r8,1)
1534 +2: testq $4,%r8 # check for trailing dword
1536 + movl (%rdi,%rdx,8),%ecx # copy trailing dword
1537 + movl %ecx,(%rsi,%rdx,8)
1540 +3: movq -8(%rdi,%rdx,8),%rcx
1541 + movq %rcx,-8(%rsi,%rdx,8)
1546 +4: movq 24(%rdi,%rdx,8),%rcx
1547 + movq %rcx,24(%rsi,%rdx,8)
1548 + movq 16(%rdi,%rdx,8),%rcx
1549 + movq %rcx,16(%rsi,%rdx,8)
1550 + movq 8(%rdi,%rdx,8),%rcx
1551 + movq %rcx,8(%rsi,%rdx,8)
1552 + movq (%rdi,%rdx,8),%rcx
1553 + movq %rcx,(%rsi,%rdx,8)
1560 + # Support for void Copy::arrayof_conjoint_jshorts(void* from,
1564 + # conjoint_jshorts_atomic
1566 + # If 'from' and/or 'to' are aligned on 4- or 2-byte boundaries, we
1567 + # let the hardware handle it. The tow or four words within dwords
1568 + # or qwords that span cache line boundaries will still be loaded
1569 + # and stored atomically.
1573 + # rdx - count, treated as ssize_t
1576 +_Copy_arrayof_conjoint_jshorts:
1577 +_Copy_conjoint_jshorts_atomic:
1578 + movq %rdx,%r8 # word count
1579 + shrq $2,%rdx # qword count
1581 + leaq -2(%rdi,%r8,2),%rax # from + wcount*2 - 2
1586 + leaq -8(%rdi,%rdx,8),%rax # from + qcount*8 - 8
1587 + leaq -8(%rsi,%rdx,8),%rcx # to + qcount*8 - 8
1590 +1: movq 8(%rax,%rdx,8),%rsi
1591 + movq %rsi,8(%rcx,%rdx,8)
1594 +2: testq $2,%r8 # check for trailing dword
1596 + movl 8(%rax),%esi # copy trailing dword
1598 + addq $4,%rcx # original %rsi is trashed, so we
1599 + # can't use it as a base register
1600 +3: testq $1,%r8 # check for trailing word
1602 + movw -2(%rdi,%r8,2),%si # copy trailing word
1606 +5: movq -24(%rax,%rdx,8),%rsi
1607 + movq %rsi,-24(%rcx,%rdx,8)
1608 + movq -16(%rax,%rdx,8),%rsi
1609 + movq %rsi,-16(%rcx,%rdx,8)
1610 + movq -8(%rax,%rdx,8),%rsi
1611 + movq %rsi,-8(%rcx,%rdx,8)
1612 + movq (%rax,%rdx,8),%rsi
1613 + movq %rsi,(%rcx,%rdx,8)
1620 + testq $1,%r8 # check for trailing word
1622 + movw -2(%rdi,%r8,2),%cx # copy trailing word
1623 + movw %cx,-2(%rsi,%r8,2)
1624 +1: testq $2,%r8 # check for trailing dword
1626 + movl (%rdi,%rdx,8),%ecx # copy trailing dword
1627 + movl %ecx,(%rsi,%rdx,8)
1629 +2: movq -8(%rdi,%rdx,8),%rcx
1630 + movq %rcx,-8(%rsi,%rdx,8)
1635 +3: movq 24(%rdi,%rdx,8),%rcx
1636 + movq %rcx,24(%rsi,%rdx,8)
1637 + movq 16(%rdi,%rdx,8),%rcx
1638 + movq %rcx,16(%rsi,%rdx,8)
1639 + movq 8(%rdi,%rdx,8),%rcx
1640 + movq %rcx,8(%rsi,%rdx,8)
1641 + movq (%rdi,%rdx,8),%rcx
1642 + movq %rcx,(%rsi,%rdx,8)
1649 + # Support for void Copy::arrayof_conjoint_jints(jint* from,
1653 + # conjoint_jints_atomic
1655 + # If 'from' and/or 'to' are aligned on 4-byte boundaries, we let
1656 + # the hardware handle it. The two dwords within qwords that span
1657 + # cache line boundaries will still be loaded and stored atomically.
1661 + # rdx - count, treated as ssize_t
1664 +_Copy_arrayof_conjoint_jints:
1665 +_Copy_conjoint_jints_atomic:
1666 + movq %rdx,%r8 # dword count
1667 + shrq %rdx # qword count
1669 + leaq -4(%rdi,%r8,4),%rax # from + dcount*4 - 4
1674 + leaq -8(%rdi,%rdx,8),%rax # from + qcount*8 - 8
1675 + leaq -8(%rsi,%rdx,8),%rcx # to + qcount*8 - 8
1679 +1: movq 8(%rax,%rdx,8),%rsi
1680 + movq %rsi,8(%rcx,%rdx,8)
1683 +2: testq $1,%r8 # check for trailing dword
1685 + movl 8(%rax),%esi # copy trailing dword
1689 +4: movq -24(%rax,%rdx,8),%rsi
1690 + movq %rsi,-24(%rcx,%rdx,8)
1691 + movq -16(%rax,%rdx,8),%rsi
1692 + movq %rsi,-16(%rcx,%rdx,8)
1693 + movq -8(%rax,%rdx,8),%rsi
1694 + movq %rsi,-8(%rcx,%rdx,8)
1695 + movq (%rax,%rdx,8),%rsi
1696 + movq %rsi,(%rcx,%rdx,8)
1703 + testq $1,%r8 # check for trailing dword
1705 + movl -4(%rdi,%r8,4),%ecx # copy trailing dword
1706 + movl %ecx,-4(%rsi,%r8,4)
1708 +1: movq -8(%rdi,%rdx,8),%rcx
1709 + movq %rcx,-8(%rsi,%rdx,8)
1714 +2: movq 24(%rdi,%rdx,8),%rcx
1715 + movq %rcx,24(%rsi,%rdx,8)
1716 + movq 16(%rdi,%rdx,8),%rcx
1717 + movq %rcx,16(%rsi,%rdx,8)
1718 + movq 8(%rdi,%rdx,8),%rcx
1719 + movq %rcx,8(%rsi,%rdx,8)
1720 + movq (%rdi,%rdx,8),%rcx
1721 + movq %rcx,(%rsi,%rdx,8)
1728 + # Support for void Copy::arrayof_conjoint_jlongs(jlong* from,
1732 + # conjoint_jlongs_atomic
1733 + # arrayof_conjoint_oops
1734 + # conjoint_oops_atomic
1738 + # rdx - count, treated as ssize_t
1741 +_Copy_arrayof_conjoint_jlongs:
1742 +_Copy_conjoint_jlongs_atomic:
1744 + leaq -8(%rdi,%rdx,8),%rax # from + count*8 - 8
1749 + leaq -8(%rsi,%rdx,8),%rcx # to + count*8 - 8
1752 +1: movq 8(%rax,%rdx,8),%rsi
1753 + movq %rsi,8(%rcx,%rdx,8)
1758 +2: movq -24(%rax,%rdx,8),%rsi
1759 + movq %rsi,-24(%rcx,%rdx,8)
1760 + movq -16(%rax,%rdx,8),%rsi
1761 + movq %rsi,-16(%rcx,%rdx,8)
1762 + movq -8(%rax,%rdx,8),%rsi
1763 + movq %rsi,-8(%rcx,%rdx,8)
1764 + movq (%rax,%rdx,8),%rsi
1765 + movq %rsi,(%rcx,%rdx,8)
1771 +4: movq -8(%rdi,%rdx,8),%rcx
1772 + movq %rcx,-8(%rsi,%rdx,8)
1777 +5: movq 24(%rdi,%rdx,8),%rcx
1778 + movq %rcx,24(%rsi,%rdx,8)
1779 + movq 16(%rdi,%rdx,8),%rcx
1780 + movq %rcx,16(%rsi,%rdx,8)
1781 + movq 8(%rdi,%rdx,8),%rcx
1782 + movq %rcx,8(%rsi,%rdx,8)
1783 + movq (%rdi,%rdx,8),%rcx
1784 + movq %rcx,(%rsi,%rdx,8)
1791 diff -urN /tmp/a/vmStructs_solaris_x86.hpp b/src/hotspot/os_cpu/solaris_x86/vmStructs_solaris_x86.hpp
1792 --- /tmp/a/vmStructs_solaris_x86.hpp 1970-01-01 01:00:00.000000000 +0100
1793 +++ b/src/hotspot/os_cpu/solaris_x86/vmStructs_solaris_x86.hpp 2024-09-16 14:41:33.969811478 +0100
1796 + * Copyright (c) 2000, 2019, Oracle and/or its affiliates. All rights reserved.
1797 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
1799 + * This code is free software; you can redistribute it and/or modify it
1800 + * under the terms of the GNU General Public License version 2 only, as
1801 + * published by the Free Software Foundation.
1803 + * This code is distributed in the hope that it will be useful, but WITHOUT
1804 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
1805 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
1806 + * version 2 for more details (a copy is included in the LICENSE file that
1807 + * accompanied this code).
1809 + * You should have received a copy of the GNU General Public License version
1810 + * 2 along with this work; if not, write to the Free Software Foundation,
1811 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
1813 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
1814 + * or visit www.oracle.com if you need additional information or have any
1819 +#ifndef OS_CPU_SOLARIS_X86_VMSTRUCTS_SOLARIS_X86_HPP
1820 +#define OS_CPU_SOLARIS_X86_VMSTRUCTS_SOLARIS_X86_HPP
1822 +// These are the OS and CPU-specific fields, types and integer
1823 +// constants required by the Serviceability Agent. This file is
1824 +// referenced by vmStructs.cpp.
1826 +#define VM_STRUCTS_OS_CPU(nonstatic_field, static_field, unchecked_nonstatic_field, volatile_nonstatic_field, nonproduct_nonstatic_field, c2_nonstatic_field, unchecked_c1_static_field, unchecked_c2_static_field)
1828 +#define VM_TYPES_OS_CPU(declare_type, declare_toplevel_type, declare_oop_type, declare_integer_type, declare_unsigned_integer_type, declare_c1_toplevel_type, declare_c2_type, declare_c2_toplevel_type)
1830 +#define VM_INT_CONSTANTS_OS_CPU(declare_constant, declare_preprocessor_constant, declare_c1_constant, declare_c2_constant, declare_c2_preprocessor_constant)
1832 +#define VM_LONG_CONSTANTS_OS_CPU(declare_constant, declare_preprocessor_constant, declare_c1_constant, declare_c2_constant, declare_c2_preprocessor_constant)
1834 +#endif // OS_CPU_SOLARIS_X86_VMSTRUCTS_SOLARIS_X86_HPP
1835 diff -urN /tmp/a/vm_version_solaris_x86.cpp b/src/hotspot/os_cpu/solaris_x86/vm_version_solaris_x86.cpp
1836 --- /tmp/a/vm_version_solaris_x86.cpp 1970-01-01 01:00:00.000000000 +0100
1837 +++ b/src/hotspot/os_cpu/solaris_x86/vm_version_solaris_x86.cpp 2024-09-16 14:41:33.969882961 +0100
1840 + * Copyright (c) 2006, 2019, Oracle and/or its affiliates. All rights reserved.
1841 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
1843 + * This code is free software; you can redistribute it and/or modify it
1844 + * under the terms of the GNU General Public License version 2 only, as
1845 + * published by the Free Software Foundation.
1847 + * This code is distributed in the hope that it will be useful, but WITHOUT
1848 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
1849 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
1850 + * version 2 for more details (a copy is included in the LICENSE file that
1851 + * accompanied this code).
1853 + * You should have received a copy of the GNU General Public License version
1854 + * 2 along with this work; if not, write to the Free Software Foundation,
1855 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
1857 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
1858 + * or visit www.oracle.com if you need additional information or have any
1863 +#include "precompiled.hpp"
1864 +#include "runtime/os.hpp"
1865 +#include "runtime/vm_version.hpp"