Mercurial > hg > release > icedtea6-1.2
changeset 863:33a90721ac50
2008-05-15 Matthias Klose <doko@ubuntu.com>
* patches/icedtea-sparc.patch: New.
* Makefile.am: Add the icedtea-sparc patch.
* acinclude.m4: Don't default to the zero port on sparc.
* Makefile.in, configure: Regenerated.
author | doko@ubuntu.com |
---|---|
date | Thu, 15 May 2008 11:51:53 +0200 |
parents | 493b2cd196e2 |
children | 4560c7ed0c62 |
files | ChangeLog Makefile.am Makefile.in acinclude.m4 configure patches/icedtea-sparc.patch |
diffstat | 6 files changed, 1830 insertions(+), 2 deletions(-) [+] |
line wrap: on
line diff
--- a/ChangeLog Wed May 14 14:13:02 2008 -0400 +++ b/ChangeLog Thu May 15 11:51:53 2008 +0200 @@ -1,3 +1,10 @@ +2008-05-15 Matthias Klose <doko@ubuntu.com> + + * patches/icedtea-sparc.patch: New. + * Makefile.am: Add the icedtea-sparc patch. + * acinclude.m4: Don't default to the zero port on sparc. + * Makefile.in, configure: Regenerated. + 2008-05-14 Joshua Sumali <jsumali@redhat.com> * rt/net/sourceforge/jnlp/security/CertsInfoPane.java: Fix certificate
--- a/Makefile.am Wed May 14 14:13:02 2008 -0400 +++ b/Makefile.am Thu May 15 11:51:53 2008 +0200 @@ -313,6 +313,7 @@ patches/icedtea-gervill.patch \ patches/icedtea-directaudio-close-trick.patch \ patches/icedtea-hat-spl-gpl.patch \ + patches/icedtea-sparc.patch \ $(GCC_PATCH) \ $(DISTRIBUTION_PATCHES)
--- a/Makefile.in Wed May 14 14:13:02 2008 -0400 +++ b/Makefile.in Thu May 15 11:51:53 2008 +0200 @@ -415,8 +415,8 @@ patches/icedtea-color-profiles.patch \ patches/icedtea-fonts.patch patches/icedtea-gervill.patch \ patches/icedtea-directaudio-close-trick.patch \ - patches/icedtea-hat-spl-gpl.patch $(GCC_PATCH) \ - $(DISTRIBUTION_PATCHES) $(am__append_7) + patches/icedtea-hat-spl-gpl.patch patches/icedtea-sparc.patch \ + $(GCC_PATCH) $(DISTRIBUTION_PATCHES) $(am__append_7) # Patch OpenJDK for plug replacements and ecj. ICEDTEA_ECJ_PATCH = patches/icedtea-ecj.patch
--- a/acinclude.m4 Wed May 14 14:13:02 2008 -0400 +++ b/acinclude.m4 Thu May 15 11:51:53 2008 +0200 @@ -542,6 +542,7 @@ [ case "${host}" in i?86-*-*) ;; + sparc*-*-*) ;; x86_64-*-*) ;; *) if test "x${CACAO}" != xno; then
--- a/configure Wed May 14 14:13:02 2008 -0400 +++ b/configure Thu May 15 11:51:53 2008 +0200 @@ -8659,6 +8659,7 @@ case "${host}" in i?86-*-*) ;; + sparc*-*-*) ;; x86_64-*-*) ;; *) if test "x${CACAO}" != xno; then
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/patches/icedtea-sparc.patch Thu May 15 11:51:53 2008 +0200 @@ -0,0 +1,1818 @@ + +# HG changeset patch +# User phh +# Date 1209064077 14400 +# Node ID 435e6450501506326c95d3374eb08b3406fa420c +# Parent ec73d88d5b43153e083db1fc57971def1e828ab3 +6693457: Open-source hotspot linux-sparc support +Summary: Move os_cpu/linux_sparc from closed to open +Reviewed-by: kamg + +#--- a/src/share/vm/oops/oop.inline.hpp Wed Apr 23 06:35:28 2008 -0400 +#+++ openjdk/hotspot/src/share/vm/oops/oop.inline.hpp Thu Apr 24 15:07:57 2008 -0400 +#@@ -135,7 +135,7 @@ inline narrowOop oopDesc::encode_heap_oo +# assert(!is_null(v), "oop value can never be zero"); +# address heap_base = Universe::heap_base(); +# uint64_t result = (uint64_t)(pointer_delta((void*)v, (void*)heap_base, 1) >> LogMinObjAlignmentInBytes); +#- assert((result & 0xffffffff00000000L) == 0, "narrow oop overflow"); +#+ assert((result & 0xffffffff00000000ULL) == 0, "narrow oop overflow"); +# return (narrowOop)result; +# } +# +--- /dev/null Thu Jan 01 00:00:00 1970 +0000 ++++ openjdk/hotspot/make/linux/platform_sparcv9 Thu Apr 24 15:07:57 2008 -0400 +@@ -0,0 +1,15 @@ ++os_family = linux ++ ++arch = sparc ++ ++arch_model = sparc ++ ++os_arch = linux_sparc ++ ++os_arch_model = linux_sparc ++ ++lib_arch = sparcv9 ++ ++compiler = gcc ++ ++sysdefs = -DLINUX -D_GNU_SOURCE -DSPARC +--- /dev/null Thu Jan 01 00:00:00 1970 +0000 ++++ openjdk/hotspot/src/os_cpu/linux_sparc/vm/assembler_linux_sparc.cpp Thu Apr 24 15:07:57 2008 -0400 +@@ -0,0 +1,51 @@ ++/* ++ * Copyright 1999-2006 Sun Microsystems, Inc. All Rights Reserved. ++ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. ++ * ++ * This code is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 only, as ++ * published by the Free Software Foundation. ++ * ++ * This code is distributed in the hope that it will be useful, but WITHOUT ++ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or ++ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ++ * version 2 for more details (a copy is included in the LICENSE file that ++ * accompanied this code). ++ * ++ * You should have received a copy of the GNU General Public License version ++ * 2 along with this work; if not, write to the Free Software Foundation, ++ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. ++ * ++ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, ++ * CA 95054 USA or visit www.sun.com if you need additional information or ++ * have any questions. ++ * ++ */ ++ ++#include "incls/_precompiled.incl" ++#include "incls/_assembler_linux_sparc.cpp.incl" ++ ++#include <asm-sparc/traps.h> ++ ++bool MacroAssembler::needs_explicit_null_check(intptr_t offset) { ++ // Since the linux kernel resides at the low end of ++ // user address space, no null pointer check is needed. ++ return offset < 0 || offset >= 0x100000; ++} ++ ++void MacroAssembler::read_ccr_trap(Register ccr_save) { ++ // No implementation ++ breakpoint_trap(); ++} ++ ++void MacroAssembler::write_ccr_trap(Register ccr_save, Register scratch1, Register scratch2) { ++ // No implementation ++ breakpoint_trap(); ++} ++ ++void MacroAssembler::flush_windows_trap() { trap(SP_TRAP_FWIN); } ++void MacroAssembler::clean_windows_trap() { trap(SP_TRAP_CWIN); } ++ ++// Use software breakpoint trap until we figure out how to do this on Linux ++void MacroAssembler::get_psr_trap() { trap(SP_TRAP_SBPT); } ++void MacroAssembler::set_psr_trap() { trap(SP_TRAP_SBPT); } +--- /dev/null Thu Jan 01 00:00:00 1970 +0000 ++++ openjdk/hotspot/src/os_cpu/linux_sparc/vm/atomic_linux_sparc.inline.hpp Thu Apr 24 15:07:57 2008 -0400 +@@ -0,0 +1,206 @@ ++/* ++ * Copyright 1999-2007 Sun Microsystems, Inc. All Rights Reserved. ++ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. ++ * ++ * This code is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 only, as ++ * published by the Free Software Foundation. ++ * ++ * This code is distributed in the hope that it will be useful, but WITHOUT ++ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or ++ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ++ * version 2 for more details (a copy is included in the LICENSE file that ++ * accompanied this code). ++ * ++ * You should have received a copy of the GNU General Public License version ++ * 2 along with this work; if not, write to the Free Software Foundation, ++ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. ++ * ++ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, ++ * CA 95054 USA or visit www.sun.com if you need additional information or ++ * have any questions. ++ * ++ */ ++ ++// Implementation of class atomic ++ ++inline void Atomic::store (jbyte store_value, jbyte* dest) { *dest = store_value; } ++inline void Atomic::store (jshort store_value, jshort* dest) { *dest = store_value; } ++inline void Atomic::store (jint store_value, jint* dest) { *dest = store_value; } ++inline void Atomic::store (jlong store_value, jlong* dest) { *dest = store_value; } ++inline void Atomic::store_ptr(intptr_t store_value, intptr_t* dest) { *dest = store_value; } ++inline void Atomic::store_ptr(void* store_value, void* dest) { *(void**)dest = store_value; } ++ ++inline void Atomic::store (jbyte store_value, volatile jbyte* dest) { *dest = store_value; } ++inline void Atomic::store (jshort store_value, volatile jshort* dest) { *dest = store_value; } ++inline void Atomic::store (jint store_value, volatile jint* dest) { *dest = store_value; } ++inline void Atomic::store (jlong store_value, volatile jlong* dest) { *dest = store_value; } ++inline void Atomic::store_ptr(intptr_t store_value, volatile intptr_t* dest) { *dest = store_value; } ++inline void Atomic::store_ptr(void* store_value, volatile void* dest) { *(void* volatile *)dest = store_value; } ++ ++inline void Atomic::inc (volatile jint* dest) { (void)add (1, dest); } ++inline void Atomic::inc_ptr(volatile intptr_t* dest) { (void)add_ptr(1, dest); } ++inline void Atomic::inc_ptr(volatile void* dest) { (void)add_ptr(1, dest); } ++ ++inline void Atomic::dec (volatile jint* dest) { (void)add (-1, dest); } ++inline void Atomic::dec_ptr(volatile intptr_t* dest) { (void)add_ptr(-1, dest); } ++inline void Atomic::dec_ptr(volatile void* dest) { (void)add_ptr(-1, dest); } ++ ++inline jint Atomic::add (jint add_value, volatile jint* dest) { ++ intptr_t rv; ++ __asm__ volatile( ++ "1: \n\t" ++ " ld [%2], %%o2\n\t" ++ " add %1, %%o2, %%o3\n\t" ++ " cas [%2], %%o2, %%o3\n\t" ++ " cmp %%o2, %%o3\n\t" ++ " bne 1b\n\t" ++ " nop\n\t" ++ " add %1, %%o2, %0\n\t" ++ : "=r" (rv) ++ : "r" (add_value), "r" (dest) ++ : "memory", "o2", "o3"); ++ return rv; ++} ++ ++inline intptr_t Atomic::add_ptr(intptr_t add_value, volatile intptr_t* dest) { ++ intptr_t rv; ++#ifdef _LP64 ++ __asm__ volatile( ++ "1: \n\t" ++ " ldx [%2], %%o2\n\t" ++ " add %0, %%o2, %%o3\n\t" ++ " casx [%2], %%o2, %%o3\n\t" ++ " cmp %%o2, %%o3\n\t" ++ " bne %%xcc, 1b\n\t" ++ " nop\n\t" ++ " add %0, %%o2, %0\n\t" ++ : "=r" (rv) ++ : "r" (add_value), "r" (dest) ++ : "memory", "o2", "o3"); ++#else ++ __asm__ volatile( ++ "1: \n\t" ++ " ld [%2], %%o2\n\t" ++ " add %1, %%o2, %%o3\n\t" ++ " cas [%2], %%o2, %%o3\n\t" ++ " cmp %%o2, %%o3\n\t" ++ " bne 1b\n\t" ++ " nop\n\t" ++ " add %1, %%o2, %0\n\t" ++ : "=r" (rv) ++ : "r" (add_value), "r" (dest) ++ : "memory", "o2", "o3"); ++#endif // _LP64 ++ return rv; ++} ++ ++inline void* Atomic::add_ptr(intptr_t add_value, volatile void* dest) { ++ return (void*)add_ptr((intptr_t)add_value, (volatile intptr_t*)dest); ++} ++ ++ ++inline jint Atomic::xchg (jint exchange_value, volatile jint* dest) { ++ intptr_t rv = exchange_value; ++ __asm__ volatile( ++ " swap [%2],%1\n\t" ++ : "=r" (rv) ++ : "0" (exchange_value) /* we use same register as for return value */, "r" (dest) ++ : "memory"); ++ return rv; ++} ++ ++inline intptr_t Atomic::xchg_ptr(intptr_t exchange_value, volatile intptr_t* dest) { ++ intptr_t rv = exchange_value; ++#ifdef _LP64 ++ __asm__ volatile( ++ "1:\n\t" ++ " mov %1, %%o3\n\t" ++ " ldx [%2], %%o2\n\t" ++ " casx [%2], %%o2, %%o3\n\t" ++ " cmp %%o2, %%o3\n\t" ++ " bne %%xcc, 1b\n\t" ++ " nop\n\t" ++ " mov %%o2, %0\n\t" ++ : "=r" (rv) ++ : "r" (exchange_value), "r" (dest) ++ : "memory", "o2", "o3"); ++#else ++ __asm__ volatile( ++ "swap [%2],%1\n\t" ++ : "=r" (rv) ++ : "0" (exchange_value) /* we use same register as for return value */, "r" (dest) ++ : "memory"); ++#endif // _LP64 ++ return rv; ++} ++ ++inline void* Atomic::xchg_ptr(void* exchange_value, volatile void* dest) { ++ return (void*)xchg_ptr((intptr_t)exchange_value, (volatile intptr_t*)dest); ++} ++ ++ ++inline jint Atomic::cmpxchg (jint exchange_value, volatile jint* dest, jint compare_value) { ++ jint rv; ++ __asm__ volatile( ++ " cas [%2], %3, %0" ++ : "=r" (rv) ++ : "0" (exchange_value), "r" (dest), "r" (compare_value) ++ : "memory"); ++ return rv; ++} ++ ++inline jlong Atomic::cmpxchg (jlong exchange_value, volatile jlong* dest, jlong compare_value) { ++#ifdef _LP64 ++ jlong rv; ++ __asm__ volatile( ++ " casx [%2], %3, %0" ++ : "=r" (rv) ++ : "0" (exchange_value), "r" (dest), "r" (compare_value) ++ : "memory"); ++ return rv; ++#else ++ assert(VM_Version::v9_instructions_work(), "cas only supported on v9"); ++ volatile jlong_accessor evl, cvl, rv; ++ evl.long_value = exchange_value; ++ cvl.long_value = compare_value; ++ ++ __asm__ volatile( ++ " sllx %2, 32, %2\n\t" ++ " srl %3, 0, %3\n\t" ++ " or %2, %3, %2\n\t" ++ " sllx %5, 32, %5\n\t" ++ " srl %6, 0, %6\n\t" ++ " or %5, %6, %5\n\t" ++ " casx [%4], %5, %2\n\t" ++ " srl %2, 0, %1\n\t" ++ " srlx %2, 32, %0\n\t" ++ : "=r" (rv.words[0]), "=r" (rv.words[1]) ++ : "r" (evl.words[0]), "r" (evl.words[1]), "r" (dest), "r" (cvl.words[0]), "r" (cvl.words[1]) ++ : "memory"); ++ ++ return rv.long_value; ++#endif ++} ++ ++inline intptr_t Atomic::cmpxchg_ptr(intptr_t exchange_value, volatile intptr_t* dest, intptr_t compare_value) { ++ intptr_t rv; ++#ifdef _LP64 ++ __asm__ volatile( ++ " casx [%2], %3, %0" ++ : "=r" (rv) ++ : "0" (exchange_value), "r" (dest), "r" (compare_value) ++ : "memory"); ++#else ++ __asm__ volatile( ++ " cas [%2], %3, %0" ++ : "=r" (rv) ++ : "0" (exchange_value), "r" (dest), "r" (compare_value) ++ : "memory"); ++#endif // _LP64 ++ return rv; ++} ++ ++inline void* Atomic::cmpxchg_ptr(void* exchange_value, volatile void* dest, void* compare_value) { ++ return (void*)cmpxchg_ptr((intptr_t)exchange_value, (volatile intptr_t*)dest, (intptr_t)compare_value); ++} +--- /dev/null Thu Jan 01 00:00:00 1970 +0000 ++++ openjdk/hotspot/src/os_cpu/linux_sparc/vm/globals_linux_sparc.hpp Thu Apr 24 15:07:57 2008 -0400 +@@ -0,0 +1,34 @@ ++/* ++ * Copyright 2000-2004 Sun Microsystems, Inc. All Rights Reserved. ++ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. ++ * ++ * This code is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 only, as ++ * published by the Free Software Foundation. ++ * ++ * This code is distributed in the hope that it will be useful, but WITHOUT ++ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or ++ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ++ * version 2 for more details (a copy is included in the LICENSE file that ++ * accompanied this code). ++ * ++ * You should have received a copy of the GNU General Public License version ++ * 2 along with this work; if not, write to the Free Software Foundation, ++ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. ++ * ++ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, ++ * CA 95054 USA or visit www.sun.com if you need additional information or ++ * have any questions. ++ * ++ */ ++ ++// ++// Sets the default values for platform dependent flags used by the ++// runtime system. (see globals.hpp) ++// ++ ++define_pd_global(uintx, JVMInvokeMethodSlack, 12288); ++define_pd_global(intx, CompilerThreadStackSize, 0); ++ ++// Only used on 64 bit Windows platforms ++define_pd_global(bool, UseVectoredExceptions, false); +--- /dev/null Thu Jan 01 00:00:00 1970 +0000 ++++ openjdk/hotspot/src/os_cpu/linux_sparc/vm/linux_sparc.ad Thu Apr 24 15:07:57 2008 -0400 +@@ -0,0 +1,27 @@ ++// ++// Copyright 1999-2007 Sun Microsystems, Inc. All Rights Reserved. ++// DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. ++// ++// This code is free software; you can redistribute it and/or modify it ++// under the terms of the GNU General Public License version 2 only, as ++// published by the Free Software Foundation. ++// ++// This code is distributed in the hope that it will be useful, but WITHOUT ++// ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or ++// FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ++// version 2 for more details (a copy is included in the LICENSE file that ++// accompanied this code). ++// ++// You should have received a copy of the GNU General Public License version ++// 2 along with this work; if not, write to the Free Software Foundation, ++// Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. ++// ++// Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, ++// CA 95054 USA or visit www.sun.com if you need additional information or ++// have any questions. ++// ++ ++// ++// ++ ++// SPARC Linux Architecture Description File +--- /dev/null Thu Jan 01 00:00:00 1970 +0000 ++++ openjdk/hotspot/src/os_cpu/linux_sparc/vm/linux_sparc.s Thu Apr 24 15:07:57 2008 -0400 +@@ -0,0 +1,105 @@ ++# ++# Copyright 2005-2007 Sun Microsystems, Inc. All Rights Reserved. ++# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. ++# ++# This code is free software; you can redistribute it and/or modify it ++# under the terms of the GNU General Public License version 2 only, as ++# published by the Free Software Foundation. ++# ++# This code is distributed in the hope that it will be useful, but WITHOUT ++# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or ++# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ++# version 2 for more details (a copy is included in the LICENSE file that ++# accompanied this code). ++# ++# You should have received a copy of the GNU General Public License version ++# 2 along with this work; if not, write to the Free Software Foundation, ++# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. ++# ++# Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, ++# CA 95054 USA or visit www.sun.com if you need additional information or ++# have any questions. ++# ++ ++ # Prototype: int SafeFetch32 (int * adr, int ErrValue) ++ # The "ld" at Fetch32 is potentially faulting instruction. ++ # If the instruction traps the trap handler will arrange ++ # for control to resume at Fetch32Resume. ++ # By convention with the trap handler we ensure there is a non-CTI ++ # instruction in the trap shadow. ++ ++ ++ .globl SafeFetch32, Fetch32PFI, Fetch32Resume ++ .globl SafeFetchN ++ .align 32 ++ .type SafeFetch32,@function ++SafeFetch32: ++ mov %o0, %g1 ++ mov %o1, %o0 ++Fetch32PFI: ++ # <-- Potentially faulting instruction ++ ld [%g1], %o0 ++Fetch32Resume: ++ nop ++ retl ++ nop ++ ++ .globl SafeFetchN, FetchNPFI, FetchNResume ++ .type SafeFetchN,@function ++ .align 32 ++SafeFetchN: ++ mov %o0, %g1 ++ mov %o1, %o0 ++FetchNPFI: ++ ldn [%g1], %o0 ++FetchNResume: ++ nop ++ retl ++ nop ++ ++ # Possibilities: ++ # -- membar ++ # -- CAS (SP + BIAS, G0, G0) ++ # -- wr %g0, %asi ++ ++ .globl SpinPause ++ .type SpinPause,@function ++ .align 32 ++SpinPause: ++ retl ++ mov %g0, %o0 ++ ++ .globl _Copy_conjoint_jlongs_atomic ++ .type _Copy_conjoint_jlongs_atomic,@function ++_Copy_conjoint_jlongs_atomic: ++ cmp %o0, %o1 ++ bleu 4f ++ sll %o2, 3, %o4 ++ ba 2f ++ 1: ++ subcc %o4, 8, %o4 ++ std %o2, [%o1] ++ add %o0, 8, %o0 ++ add %o1, 8, %o1 ++ 2: ++ bge,a 1b ++ ldd [%o0], %o2 ++ ba 5f ++ nop ++ 3: ++ std %o2, [%o1+%o4] ++ 4: ++ subcc %o4, 8, %o4 ++ bge,a 3b ++ ldd [%o0+%o4], %o2 ++ 5: ++ retl ++ nop ++ ++ ++ .globl _flush_reg_windows ++ .align 32 ++ _flush_reg_windows: ++ ta 0x03 ++ retl ++ mov %fp, %o0 +--- /dev/null Thu Jan 01 00:00:00 1970 +0000 ++++ openjdk/hotspot/src/os_cpu/linux_sparc/vm/orderAccess_linux_sparc.inline.hpp Thu Apr 24 15:07:57 2008 -0400 +@@ -0,0 +1,102 @@ ++/* ++ * Copyright 2003-2007 Sun Microsystems, Inc. All Rights Reserved. ++ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. ++ * ++ * This code is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 only, as ++ * published by the Free Software Foundation. ++ * ++ * This code is distributed in the hope that it will be useful, but WITHOUT ++ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or ++ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ++ * version 2 for more details (a copy is included in the LICENSE file that ++ * accompanied this code). ++ * ++ * You should have received a copy of the GNU General Public License version ++ * 2 along with this work; if not, write to the Free Software Foundation, ++ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. ++ * ++ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, ++ * CA 95054 USA or visit www.sun.com if you need additional information or ++ * have any questions. ++ * ++ */ ++ ++// Implementation of class OrderAccess. ++ ++// Assume TSO. ++ ++inline void OrderAccess::loadload() { acquire(); } ++inline void OrderAccess::storestore() { release(); } ++inline void OrderAccess::loadstore() { acquire(); } ++inline void OrderAccess::storeload() { fence(); } ++ ++inline void OrderAccess::acquire() { ++ __asm__ volatile ("nop" : : :); ++} ++ ++inline void OrderAccess::release() { ++ jint* dummy = (jint*)&dummy; ++ __asm__ volatile("stw %%g0, [%0]" : : "r" (dummy) : "memory"); ++} ++ ++inline void OrderAccess::fence() { ++ __asm__ volatile ("membar #StoreLoad" : : :); ++} ++ ++inline jbyte OrderAccess::load_acquire(volatile jbyte* p) { return *p; } ++inline jshort OrderAccess::load_acquire(volatile jshort* p) { return *p; } ++inline jint OrderAccess::load_acquire(volatile jint* p) { return *p; } ++inline jlong OrderAccess::load_acquire(volatile jlong* p) { return *p; } ++inline jubyte OrderAccess::load_acquire(volatile jubyte* p) { return *p; } ++inline jushort OrderAccess::load_acquire(volatile jushort* p) { return *p; } ++inline juint OrderAccess::load_acquire(volatile juint* p) { return *p; } ++inline julong OrderAccess::load_acquire(volatile julong* p) { return *p; } ++inline jfloat OrderAccess::load_acquire(volatile jfloat* p) { return *p; } ++inline jdouble OrderAccess::load_acquire(volatile jdouble* p) { return *p; } ++ ++inline intptr_t OrderAccess::load_ptr_acquire(volatile intptr_t* p) { return *p; } ++inline void* OrderAccess::load_ptr_acquire(volatile void* p) { return *(void* volatile *)p; } ++inline void* OrderAccess::load_ptr_acquire(const volatile void* p) { return *(void* const volatile *)p; } ++ ++inline void OrderAccess::release_store(volatile jbyte* p, jbyte v) { *p = v; } ++inline void OrderAccess::release_store(volatile jshort* p, jshort v) { *p = v; } ++inline void OrderAccess::release_store(volatile jint* p, jint v) { *p = v; } ++inline void OrderAccess::release_store(volatile jlong* p, jlong v) { *p = v; } ++inline void OrderAccess::release_store(volatile jubyte* p, jubyte v) { *p = v; } ++inline void OrderAccess::release_store(volatile jushort* p, jushort v) { *p = v; } ++inline void OrderAccess::release_store(volatile juint* p, juint v) { *p = v; } ++inline void OrderAccess::release_store(volatile julong* p, julong v) { *p = v; } ++inline void OrderAccess::release_store(volatile jfloat* p, jfloat v) { *p = v; } ++inline void OrderAccess::release_store(volatile jdouble* p, jdouble v) { *p = v; } ++ ++inline void OrderAccess::release_store_ptr(volatile intptr_t* p, intptr_t v) { *p = v; } ++inline void OrderAccess::release_store_ptr(volatile void* p, void* v) { *(void* volatile *)p = v; } ++ ++inline void OrderAccess::store_fence(jbyte* p, jbyte v) { *p = v; fence(); } ++inline void OrderAccess::store_fence(jshort* p, jshort v) { *p = v; fence(); } ++inline void OrderAccess::store_fence(jint* p, jint v) { *p = v; fence(); } ++inline void OrderAccess::store_fence(jlong* p, jlong v) { *p = v; fence(); } ++inline void OrderAccess::store_fence(jubyte* p, jubyte v) { *p = v; fence(); } ++inline void OrderAccess::store_fence(jushort* p, jushort v) { *p = v; fence(); } ++inline void OrderAccess::store_fence(juint* p, juint v) { *p = v; fence(); } ++inline void OrderAccess::store_fence(julong* p, julong v) { *p = v; fence(); } ++inline void OrderAccess::store_fence(jfloat* p, jfloat v) { *p = v; fence(); } ++inline void OrderAccess::store_fence(jdouble* p, jdouble v) { *p = v; fence(); } ++ ++inline void OrderAccess::store_ptr_fence(intptr_t* p, intptr_t v) { *p = v; fence(); } ++inline void OrderAccess::store_ptr_fence(void** p, void* v) { *p = v; fence(); } ++ ++inline void OrderAccess::release_store_fence(volatile jbyte* p, jbyte v) { *p = v; fence(); } ++inline void OrderAccess::release_store_fence(volatile jshort* p, jshort v) { *p = v; fence(); } ++inline void OrderAccess::release_store_fence(volatile jint* p, jint v) { *p = v; fence(); } ++inline void OrderAccess::release_store_fence(volatile jlong* p, jlong v) { *p = v; fence(); } ++inline void OrderAccess::release_store_fence(volatile jubyte* p, jubyte v) { *p = v; fence(); } ++inline void OrderAccess::release_store_fence(volatile jushort* p, jushort v) { *p = v; fence(); } ++inline void OrderAccess::release_store_fence(volatile juint* p, juint v) { *p = v; fence(); } ++inline void OrderAccess::release_store_fence(volatile julong* p, julong v) { *p = v; fence(); } ++inline void OrderAccess::release_store_fence(volatile jfloat* p, jfloat v) { *p = v; fence(); } ++inline void OrderAccess::release_store_fence(volatile jdouble* p, jdouble v) { *p = v; fence(); } ++ ++inline void OrderAccess::release_store_ptr_fence(volatile intptr_t* p, intptr_t v) { *p = v; fence(); } ++inline void OrderAccess::release_store_ptr_fence(volatile void* p, void* v) { *(void* volatile *)p = v; fence(); } +--- /dev/null Thu Jan 01 00:00:00 1970 +0000 ++++ openjdk/hotspot/src/os_cpu/linux_sparc/vm/os_linux_sparc.cpp Thu Apr 24 15:07:57 2008 -0400 +@@ -0,0 +1,648 @@ ++/* ++ * Copyright 1999-2007 Sun Microsystems, Inc. All Rights Reserved. ++ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. ++ * ++ * This code is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 only, as ++ * published by the Free Software Foundation. ++ * ++ * This code is distributed in the hope that it will be useful, but WITHOUT ++ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or ++ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ++ * version 2 for more details (a copy is included in the LICENSE file that ++ * accompanied this code). ++ * ++ * You should have received a copy of the GNU General Public License version ++ * 2 along with this work; if not, write to the Free Software Foundation, ++ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. ++ * ++ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, ++ * CA 95054 USA or visit www.sun.com if you need additional information or ++ * have any questions. ++ * ++ */ ++ ++// do not include precompiled header file ++ ++#include "incls/_os_linux_sparc.cpp.incl" ++ ++// Linux/Sparc has rather obscure naming of registers in sigcontext ++// different between 32 and 64 bits ++#ifdef _LP64 ++#define SIG_PC(x) ((x)->sigc_regs.tpc) ++#define SIG_NPC(x) ((x)->sigc_regs.tnpc) ++#define SIG_REGS(x) ((x)->sigc_regs) ++#else ++#define SIG_PC(x) ((x)->si_regs.pc) ++#define SIG_NPC(x) ((x)->si_regs.npc) ++#define SIG_REGS(x) ((x)->si_regs) ++#endif ++ ++// those are to reference registers in sigcontext ++enum { ++ CON_G0 = 0, ++ CON_G1, ++ CON_G2, ++ CON_G3, ++ CON_G4, ++ CON_G5, ++ CON_G6, ++ CON_G7, ++ CON_O0, ++ CON_O1, ++ CON_O2, ++ CON_O3, ++ CON_O4, ++ CON_O5, ++ CON_O6, ++ CON_O7, ++}; ++ ++static inline void set_cont_address(sigcontext* ctx, address addr) { ++ SIG_PC(ctx) = (intptr_t)addr; ++ SIG_NPC(ctx) = (intptr_t)(addr+4); ++} ++ ++// For Forte Analyzer AsyncGetCallTrace profiling support - thread is ++// currently interrupted by SIGPROF. ++// os::Solaris::fetch_frame_from_ucontext() tries to skip nested ++// signal frames. Currently we don't do that on Linux, so it's the ++// same as os::fetch_frame_from_context(). ++ExtendedPC os::Linux::fetch_frame_from_ucontext(Thread* thread, ++ ucontext_t* uc, ++ intptr_t** ret_sp, ++ intptr_t** ret_fp) { ++ assert(thread != NULL, "just checking"); ++ assert(ret_sp != NULL, "just checking"); ++ assert(ret_fp != NULL, "just checking"); ++ ++ return os::fetch_frame_from_context(uc, ret_sp, ret_fp); ++} ++ ++ExtendedPC os::fetch_frame_from_context(void* ucVoid, ++ intptr_t** ret_sp, ++ intptr_t** ret_fp) { ++ ucontext_t* uc = (ucontext_t*) ucVoid; ++ ExtendedPC epc; ++ ++ if (uc != NULL) { ++ epc = ExtendedPC(os::Linux::ucontext_get_pc(uc)); ++ if (ret_sp) { ++ *ret_sp = os::Linux::ucontext_get_sp(uc); ++ } ++ if (ret_fp) { ++ *ret_fp = os::Linux::ucontext_get_fp(uc); ++ } ++ } else { ++ // construct empty ExtendedPC for return value checking ++ epc = ExtendedPC(NULL); ++ if (ret_sp) { ++ *ret_sp = (intptr_t*) NULL; ++ } ++ if (ret_fp) { ++ *ret_fp = (intptr_t*) NULL; ++ } ++ } ++ ++ return epc; ++} ++ ++frame os::fetch_frame_from_context(void* ucVoid) { ++ intptr_t* sp; ++ intptr_t* fp; ++ ExtendedPC epc = fetch_frame_from_context(ucVoid, &sp, &fp); ++ return frame(sp, fp, epc.pc()); ++} ++ ++frame os::get_sender_for_C_frame(frame* fr) { ++ return frame(fr->sender_sp(), fr->link(), fr->sender_pc()); ++} ++ ++frame os::current_frame() { ++ fprintf(stderr, "current_frame()"); ++ ++ intptr_t* sp = StubRoutines::Sparc::flush_callers_register_windows_func()(); ++ frame myframe(sp, frame::unpatchable, ++ CAST_FROM_FN_PTR(address, os::current_frame)); ++ if (os::is_first_C_frame(&myframe)) { ++ // stack is not walkable ++ return frame(NULL, frame::unpatchable, NULL); ++ } else { ++ return os::get_sender_for_C_frame(&myframe); ++ } ++} ++ ++address os::current_stack_pointer() { ++ register void *sp __asm__ ("sp"); ++ return (address)sp; ++} ++ ++static void current_stack_region(address* bottom, size_t* size) { ++ if (os::Linux::is_initial_thread()) { ++ // initial thread needs special handling because pthread_getattr_np() ++ // may return bogus value. ++ *bottom = os::Linux::initial_thread_stack_bottom(); ++ *size = os::Linux::initial_thread_stack_size(); ++ } else { ++ pthread_attr_t attr; ++ ++ int rslt = pthread_getattr_np(pthread_self(), &attr); ++ ++ // JVM needs to know exact stack location, abort if it fails ++ if (rslt != 0) { ++ if (rslt == ENOMEM) { ++ vm_exit_out_of_memory(0, "pthread_getattr_np"); ++ } else { ++ fatal1("pthread_getattr_np failed with errno = %d", rslt); ++ } ++ } ++ ++ if (pthread_attr_getstack(&attr, (void**)bottom, size) != 0) { ++ fatal("Can not locate current stack attributes!"); ++ } ++ ++ pthread_attr_destroy(&attr); ++ } ++ assert(os::current_stack_pointer() >= *bottom && ++ os::current_stack_pointer() < *bottom + *size, "just checking"); ++} ++ ++address os::current_stack_base() { ++ address bottom; ++ size_t size; ++ current_stack_region(&bottom, &size); ++ return bottom + size; ++} ++ ++size_t os::current_stack_size() { ++ // stack size includes normal stack and HotSpot guard pages ++ address bottom; ++ size_t size; ++ current_stack_region(&bottom, &size); ++ return size; ++} ++ ++char* os::non_memory_address_word() { ++ // Must never look like an address returned by reserve_memory, ++ // even in its subfields (as defined by the CPU immediate fields, ++ // if the CPU splits constants across multiple instructions). ++ // On SPARC, 0 != %hi(any real address), because there is no ++ // allocation in the first 1Kb of the virtual address space. ++ return (char*) 0; ++} ++ ++void os::initialize_thread() {} ++ ++void os::print_context(outputStream *st, void *context) { ++ if (context == NULL) return; ++ ++ ucontext_t* uc = (ucontext_t*)context; ++ sigcontext* sc = (sigcontext*)context; ++ st->print_cr("Registers:"); ++ ++ st->print_cr(" O0=" INTPTR_FORMAT " O1=" INTPTR_FORMAT ++ " O2=" INTPTR_FORMAT " O3=" INTPTR_FORMAT, ++ SIG_REGS(sc).u_regs[CON_O0], ++ SIG_REGS(sc).u_regs[CON_O1], ++ SIG_REGS(sc).u_regs[CON_O2], ++ SIG_REGS(sc).u_regs[CON_O3]); ++ st->print_cr(" O4=" INTPTR_FORMAT " O5=" INTPTR_FORMAT ++ " O6=" INTPTR_FORMAT " O7=" INTPTR_FORMAT, ++ SIG_REGS(sc).u_regs[CON_O4], ++ SIG_REGS(sc).u_regs[CON_O5], ++ SIG_REGS(sc).u_regs[CON_O6], ++ SIG_REGS(sc).u_regs[CON_O7]); ++ ++ st->print_cr(" G1=" INTPTR_FORMAT " G2=" INTPTR_FORMAT ++ " G3=" INTPTR_FORMAT " G4=" INTPTR_FORMAT, ++ SIG_REGS(sc).u_regs[CON_G1], ++ SIG_REGS(sc).u_regs[CON_G2], ++ SIG_REGS(sc).u_regs[CON_G3], ++ SIG_REGS(sc).u_regs[CON_G4]); ++ st->print_cr(" G5=" INTPTR_FORMAT " G6=" INTPTR_FORMAT ++ " G7=" INTPTR_FORMAT " Y=" INTPTR_FORMAT, ++ SIG_REGS(sc).u_regs[CON_G5], ++ SIG_REGS(sc).u_regs[CON_G6], ++ SIG_REGS(sc).u_regs[CON_G7], ++ SIG_REGS(sc).y); ++ ++ st->print_cr(" PC=" INTPTR_FORMAT " nPC=" INTPTR_FORMAT, ++ SIG_PC(sc), ++ SIG_NPC(sc)); ++ st->cr(); ++ st->cr(); ++ ++ intptr_t *sp = (intptr_t *)os::Linux::ucontext_get_sp(uc); ++ st->print_cr("Top of Stack: (sp=" PTR_FORMAT ")", sp); ++ print_hex_dump(st, (address)sp, (address)(sp + 32), sizeof(intptr_t)); ++ st->cr(); ++ ++ // Note: it may be unsafe to inspect memory near pc. For example, pc may ++ // point to garbage if entry point in an nmethod is corrupted. Leave ++ // this at the end, and hope for the best. ++ address pc = os::Linux::ucontext_get_pc(uc); ++ st->print_cr("Instructions: (pc=" PTR_FORMAT ")", pc); ++ print_hex_dump(st, pc - 16, pc + 16, sizeof(char)); ++} ++ ++ ++address os::Linux::ucontext_get_pc(ucontext_t* uc) { ++ return (address) SIG_PC((sigcontext*)uc); ++} ++ ++intptr_t* os::Linux::ucontext_get_sp(ucontext_t *uc) { ++ return (intptr_t*) ++ ((intptr_t)SIG_REGS((sigcontext*)uc).u_regs[CON_O6] + STACK_BIAS); ++} ++ ++// not used on Sparc ++intptr_t* os::Linux::ucontext_get_fp(ucontext_t *uc) { ++ ShouldNotReachHere(); ++ return NULL; ++} ++ ++// Utility functions ++ ++extern "C" void Fetch32PFI(); ++extern "C" void Fetch32Resume(); ++extern "C" void FetchNPFI(); ++extern "C" void FetchNResume(); ++ ++inline static bool checkPrefetch(sigcontext* uc, address pc) { ++ if (pc == (address) Fetch32PFI) { ++ set_cont_address(uc, address(Fetch32Resume)); ++ return true; ++ } ++ if (pc == (address) FetchNPFI) { ++ set_cont_address(uc, address(FetchNResume)); ++ return true; ++ } ++ return false; ++} ++ ++inline static bool checkOverflow(sigcontext* uc, ++ address pc, ++ address addr, ++ JavaThread* thread, ++ address* stub) { ++ // check if fault address is within thread stack ++ if (addr < thread->stack_base() && ++ addr >= thread->stack_base() - thread->stack_size()) { ++ // stack overflow ++ if (thread->in_stack_yellow_zone(addr)) { ++ thread->disable_stack_yellow_zone(); ++ if (thread->thread_state() == _thread_in_Java) { ++ // Throw a stack overflow exception. Guard pages will be reenabled ++ // while unwinding the stack. ++ *stub = ++ SharedRuntime::continuation_for_implicit_exception(thread, ++ pc, ++ SharedRuntime::STACK_OVERFLOW); ++ } else { ++ // Thread was in the vm or native code. Return and try to finish. ++ return true; ++ } ++ } else if (thread->in_stack_red_zone(addr)) { ++ // Fatal red zone violation. Disable the guard pages and fall through ++ // to handle_unexpected_exception way down below. ++ thread->disable_stack_red_zone(); ++ tty->print_raw_cr("An irrecoverable stack overflow has occurred."); ++ } else { ++ // Accessing stack address below sp may cause SEGV if current ++ // thread has MAP_GROWSDOWN stack. This should only happen when ++ // current thread was created by user code with MAP_GROWSDOWN flag ++ // and then attached to VM. See notes in os_linux.cpp. ++ if (thread->osthread()->expanding_stack() == 0) { ++ thread->osthread()->set_expanding_stack(); ++ if (os::Linux::manually_expand_stack(thread, addr)) { ++ thread->osthread()->clear_expanding_stack(); ++ return true; ++ } ++ thread->osthread()->clear_expanding_stack(); ++ } else { ++ fatal("recursive segv. expanding stack."); ++ } ++ } ++ } ++ return false; ++} ++ ++inline static bool checkPollingPage(address pc, address fault, address* stub) { ++ if (fault == os::get_polling_page()) { ++ *stub = SharedRuntime::get_poll_stub(pc); ++ return true; ++ } ++ return false; ++} ++ ++inline static bool checkByteBuffer(address pc, address* stub) { ++ // BugId 4454115: A read from a MappedByteBuffer can fault ++ // here if the underlying file has been truncated. ++ // Do not crash the VM in such a case. ++ CodeBlob* cb = CodeCache::find_blob_unsafe(pc); ++ nmethod* nm = cb->is_nmethod() ? (nmethod*)cb : NULL; ++ if (nm != NULL && nm->has_unsafe_access()) { ++ *stub = StubRoutines::handler_for_unsafe_access(); ++ return true; ++ } ++ return false; ++} ++ ++inline static bool checkVerifyOops(address pc, address fault, address* stub) { ++ if (pc >= MacroAssembler::_verify_oop_implicit_branch[0] ++ && pc < MacroAssembler::_verify_oop_implicit_branch[1] ) { ++ *stub = MacroAssembler::_verify_oop_implicit_branch[2]; ++ warning("fixed up memory fault in +VerifyOops at address " ++ INTPTR_FORMAT, fault); ++ return true; ++ } ++ return false; ++} ++ ++inline static bool checkFPFault(address pc, int code, ++ JavaThread* thread, address* stub) { ++ if (code == FPE_INTDIV || code == FPE_FLTDIV) { ++ *stub = ++ SharedRuntime:: ++ continuation_for_implicit_exception(thread, ++ pc, ++ SharedRuntime::IMPLICIT_DIVIDE_BY_ZERO); ++ return true; ++ } ++ return false; ++} ++ ++inline static bool checkNullPointer(address pc, intptr_t fault, ++ JavaThread* thread, address* stub) { ++ if (!MacroAssembler::needs_explicit_null_check(fault)) { ++ // Determination of interpreter/vtable stub/compiled code null ++ // exception ++ *stub = ++ SharedRuntime:: ++ continuation_for_implicit_exception(thread, pc, ++ SharedRuntime::IMPLICIT_NULL); ++ return true; ++ } ++ return false; ++} ++ ++inline static bool checkFastJNIAccess(address pc, address* stub) { ++ address addr = JNI_FastGetField::find_slowcase_pc(pc); ++ if (addr != (address)-1) { ++ *stub = addr; ++ return true; ++ } ++ return false; ++} ++ ++inline static bool checkSerializePage(JavaThread* thread, address addr) { ++ return os::is_memory_serialize_page(thread, addr); ++} ++ ++inline static bool checkZombie(sigcontext* uc, address* pc, address* stub) { ++ if (nativeInstruction_at(*pc)->is_zombie()) { ++ // zombie method (ld [%g0],%o7 instruction) ++ *stub = SharedRuntime::get_handle_wrong_method_stub(); ++ ++ // At the stub it needs to look like a call from the caller of this ++ // method (not a call from the segv site). ++ *pc = (address)SIG_REGS(uc).u_regs[CON_O7]; ++ return true; ++ } ++ return false; ++} ++ ++inline static bool checkICMiss(sigcontext* uc, address* pc, address* stub) { ++#ifdef COMPILER2 ++ if (nativeInstruction_at(*pc)->is_ic_miss_trap()) { ++#ifdef ASSERT ++#ifdef TIERED ++ CodeBlob* cb = CodeCache::find_blob_unsafe(pc); ++ assert(cb->is_compiled_by_c2(), "Wrong compiler"); ++#endif // TIERED ++#endif // ASSERT ++ // Inline cache missed and user trap "Tne G0+ST_RESERVED_FOR_USER_0+2" taken. ++ *stub = SharedRuntime::get_ic_miss_stub(); ++ // At the stub it needs to look like a call from the caller of this ++ // method (not a call from the segv site). ++ *pc = (address)SIG_REGS(uc).u_regs[CON_O7]; ++ return true; ++ } ++#endif // COMPILER2 ++ return false; ++} ++ ++extern "C" int ++JVM_handle_linux_signal(int sig, ++ siginfo_t* info, ++ void* ucVoid, ++ int abort_if_unrecognized) { ++ // in fact this isn't ucontext_t* at all, but struct sigcontext* ++ // but Linux porting layer uses ucontext_t, so to minimize code change ++ // we cast as needed ++ ucontext_t* ucFake = (ucontext_t*) ucVoid; ++ sigcontext* uc = (sigcontext*)ucVoid; ++ ++ Thread* t = ThreadLocalStorage::get_thread_slow(); ++ ++ SignalHandlerMark shm(t); ++ ++ // Note: it's not uncommon that JNI code uses signal/sigset to install ++ // then restore certain signal handler (e.g. to temporarily block SIGPIPE, ++ // or have a SIGILL handler when detecting CPU type). When that happens, ++ // JVM_handle_linux_signal() might be invoked with junk info/ucVoid. To ++ // avoid unnecessary crash when libjsig is not preloaded, try handle signals ++ // that do not require siginfo/ucontext first. ++ ++ if (sig == SIGPIPE || sig == SIGXFSZ) { ++ // allow chained handler to go first ++ if (os::Linux::chained_handler(sig, info, ucVoid)) { ++ return true; ++ } else { ++ if (PrintMiscellaneous && (WizardMode || Verbose)) { ++ char buf[64]; ++ warning("Ignoring %s - see bugs 4229104 or 646499219", ++ os::exception_name(sig, buf, sizeof(buf))); ++ } ++ return true; ++ } ++ } ++ ++ JavaThread* thread = NULL; ++ VMThread* vmthread = NULL; ++ if (os::Linux::signal_handlers_are_installed) { ++ if (t != NULL ){ ++ if(t->is_Java_thread()) { ++ thread = (JavaThread*)t; ++ } ++ else if(t->is_VM_thread()){ ++ vmthread = (VMThread *)t; ++ } ++ } ++ } ++ ++ // decide if this trap can be handled by a stub ++ address stub = NULL; ++ address pc = NULL; ++ address npc = NULL; ++ ++ //%note os_trap_1 ++ if (info != NULL && uc != NULL && thread != NULL) { ++ pc = address(SIG_PC(uc)); ++ npc = address(SIG_NPC(uc)); ++ ++ // Check to see if we caught the safepoint code in the ++ // process of write protecting the memory serialization page. ++ // It write enables the page immediately after protecting it ++ // so we can just return to retry the write. ++ if ((sig == SIGSEGV) && checkSerializePage(thread, (address)info->si_addr)) { ++ // Block current thread until the memory serialize page permission restored. ++ os::block_on_serialize_page_trap(); ++ return 1; ++ } ++ ++ if (checkPrefetch(uc, pc)) { ++ return 1; ++ } ++ ++ // Handle ALL stack overflow variations here ++ if (sig == SIGSEGV) { ++ if (checkOverflow(uc, pc, (address)info->si_addr, thread, &stub)) { ++ return 1; ++ } ++ } ++ ++ if (sig == SIGBUS && ++ thread->thread_state() == _thread_in_vm && ++ thread->doing_unsafe_access()) { ++ stub = StubRoutines::handler_for_unsafe_access(); ++ } ++ ++ if (thread->thread_state() == _thread_in_Java) { ++ do { ++ // Java thread running in Java code => find exception handler if any ++ // a fault inside compiled code, the interpreter, or a stub ++ ++ if ((sig == SIGSEGV) && checkPollingPage(pc, (address)info->si_addr, &stub)) { ++ break; ++ } ++ ++ if ((sig == SIGBUS) && checkByteBuffer(pc, &stub)) { ++ break; ++ } ++ ++ if ((sig == SIGSEGV || sig == SIGBUS) && ++ checkVerifyOops(pc, (address)info->si_addr, &stub)) { ++ break; ++ } ++ ++ if ((sig == SIGSEGV) && checkZombie(uc, &pc, &stub)) { ++ break; ++ } ++ ++ if ((sig == SIGILL) && checkICMiss(uc, &pc, &stub)) { ++ break; ++ } ++ ++ if ((sig == SIGFPE) && checkFPFault(pc, info->si_code, thread, &stub)) { ++ break; ++ } ++ ++ if ((sig == SIGSEGV) && ++ checkNullPointer(pc, (intptr_t)info->si_addr, thread, &stub)) { ++ break; ++ } ++ } while (0); ++ ++ // jni_fast_Get<Primitive>Field can trap at certain pc's if a GC kicks in ++ // and the heap gets shrunk before the field access. ++ if ((sig == SIGSEGV) || (sig == SIGBUS)) { ++ checkFastJNIAccess(pc, &stub); ++ } ++ } ++ ++ if (stub != NULL) { ++ // save all thread context in case we need to restore it ++ thread->set_saved_exception_pc(pc); ++ thread->set_saved_exception_npc(npc); ++ set_cont_address(uc, stub); ++ return true; ++ } ++ } ++ ++ // signal-chaining ++ if (os::Linux::chained_handler(sig, info, ucVoid)) { ++ return true; ++ } ++ ++ if (!abort_if_unrecognized) { ++ // caller wants another chance, so give it to him ++ return false; ++ } ++ ++ if (pc == NULL && uc != NULL) { ++ pc = os::Linux::ucontext_get_pc((ucontext_t*)uc); ++ } ++ ++ // unmask current signal ++ sigset_t newset; ++ sigemptyset(&newset); ++ sigaddset(&newset, sig); ++ sigprocmask(SIG_UNBLOCK, &newset, NULL); ++ ++ VMError err(t, sig, pc, info, ucVoid); ++ err.report_and_die(); ++ ++ ShouldNotReachHere(); ++} ++ ++void os::Linux::init_thread_fpu_state(void) { ++ // Nothing to do ++} ++ ++int os::Linux::get_fpu_control_word() { ++ return 0; ++} ++ ++void os::Linux::set_fpu_control_word(int fpu) { ++ // nothing ++} ++ ++bool os::is_allocatable(size_t bytes) { ++#ifdef _LP64 ++ return true; ++#else ++ if (bytes < 2 * G) { ++ return true; ++ } ++ ++ char* addr = reserve_memory(bytes, NULL); ++ ++ if (addr != NULL) { ++ release_memory(addr, bytes); ++ } ++ ++ return addr != NULL; ++#endif // _LP64 ++} ++ ++/////////////////////////////////////////////////////////////////////////////// ++// thread stack ++ ++size_t os::Linux::min_stack_allowed = 128 * K; ++ ++// pthread on Ubuntu is always in floating stack mode ++bool os::Linux::supports_variable_stack_size() { return true; } ++ ++// return default stack size for thr_type ++size_t os::Linux::default_stack_size(os::ThreadType thr_type) { ++ // default stack size (compiler thread needs larger stack) ++ size_t s = (thr_type == os::compiler_thread ? 4 * M : 1 * M); ++ return s; ++} ++ ++size_t os::Linux::default_guard_size(os::ThreadType thr_type) { ++ // Creating guard page is very expensive. Java thread has HotSpot ++ // guard page, only enable glibc guard page for non-Java threads. ++ return (thr_type == java_thread ? 0 : page_size()); ++} +--- /dev/null Thu Jan 01 00:00:00 1970 +0000 ++++ openjdk/hotspot/src/os_cpu/linux_sparc/vm/os_linux_sparc.hpp Thu Apr 24 15:07:57 2008 -0400 +@@ -0,0 +1,46 @@ ++/* ++ * Copyright 1999-2004 Sun Microsystems, Inc. All Rights Reserved. ++ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. ++ * ++ * This code is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 only, as ++ * published by the Free Software Foundation. ++ * ++ * This code is distributed in the hope that it will be useful, but WITHOUT ++ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or ++ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ++ * version 2 for more details (a copy is included in the LICENSE file that ++ * accompanied this code). ++ * ++ * You should have received a copy of the GNU General Public License version ++ * 2 along with this work; if not, write to the Free Software Foundation, ++ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. ++ * ++ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, ++ * CA 95054 USA or visit www.sun.com if you need additional information or ++ * have any questions. ++ * ++ */ ++ ++ // ++ // NOTE: we are back in class os here, not Linux ++ // ++ static jint (*atomic_xchg_func) (jint, volatile jint*); ++ static jint (*atomic_cmpxchg_func) (jint, volatile jint*, jint); ++ static jlong (*atomic_cmpxchg_long_func)(jlong, volatile jlong*, jlong); ++ static jint (*atomic_add_func) (jint, volatile jint*); ++ static void (*fence_func) (); ++ ++ static jint atomic_xchg_bootstrap (jint, volatile jint*); ++ static jint atomic_cmpxchg_bootstrap (jint, volatile jint*, jint); ++ static jlong atomic_cmpxchg_long_bootstrap(jlong, volatile jlong*, jlong); ++ static jint atomic_add_bootstrap (jint, volatile jint*); ++ static void fence_bootstrap (); ++ ++ static void setup_fpu() {} ++ ++ static bool is_allocatable(size_t bytes); ++ ++ // Used to register dynamic code cache area with the OS ++ // Note: Currently only used in 64 bit Windows implementations ++ static bool register_code_area(char *low, char *high) { return true; } +--- /dev/null Thu Jan 01 00:00:00 1970 +0000 ++++ openjdk/hotspot/src/os_cpu/linux_sparc/vm/prefetch_linux_sparc.inline.hpp Thu Apr 24 15:07:57 2008 -0400 +@@ -0,0 +1,40 @@ ++/* ++ * Copyright 2003-2007 Sun Microsystems, Inc. All Rights Reserved. ++ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. ++ * ++ * This code is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 only, as ++ * published by the Free Software Foundation. ++ * ++ * This code is distributed in the hope that it will be useful, but WITHOUT ++ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or ++ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ++ * version 2 for more details (a copy is included in the LICENSE file that ++ * accompanied this code). ++ * ++ * You should have received a copy of the GNU General Public License version ++ * 2 along with this work; if not, write to the Free Software Foundation, ++ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. ++ * ++ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, ++ * CA 95054 USA or visit www.sun.com if you need additional information or ++ * have any questions. ++ * ++ */ ++ ++#if defined(COMPILER2) || defined(_LP64) ++ ++inline void Prefetch::read(void *loc, intx interval) { ++ __asm__ volatile("prefetch [%0+%1], 0" : : "r" (loc), "r" (interval) : "memory" ); ++} ++ ++inline void Prefetch::write(void *loc, intx interval) { ++ __asm__ volatile("prefetch [%0+%1], 2" : : "r" (loc), "r" (interval) : "memory" ); ++} ++ ++#else ++ ++inline void Prefetch::read (void *loc, intx interval) {} ++inline void Prefetch::write(void *loc, intx interval) {} ++ ++#endif +--- /dev/null Thu Jan 01 00:00:00 1970 +0000 ++++ openjdk/hotspot/src/os_cpu/linux_sparc/vm/threadLS_linux_sparc.cpp Thu Apr 24 15:07:57 2008 -0400 +@@ -0,0 +1,37 @@ ++/* ++ * Copyright 1998-2003 Sun Microsystems, Inc. All Rights Reserved. ++ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. ++ * ++ * This code is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 only, as ++ * published by the Free Software Foundation. ++ * ++ * This code is distributed in the hope that it will be useful, but WITHOUT ++ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or ++ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ++ * version 2 for more details (a copy is included in the LICENSE file that ++ * accompanied this code). ++ * ++ * You should have received a copy of the GNU General Public License version ++ * 2 along with this work; if not, write to the Free Software Foundation, ++ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. ++ * ++ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, ++ * CA 95054 USA or visit www.sun.com if you need additional information or ++ * have any questions. ++ * ++ */ ++ ++#include "incls/_precompiled.incl" ++#include "incls/_threadLS_linux_sparc.cpp.incl" ++ ++void ThreadLocalStorage::generate_code_for_get_thread() { ++} ++ ++void ThreadLocalStorage::pd_init() { ++ // Nothing to do ++} ++ ++void ThreadLocalStorage::pd_set_thread(Thread* thread) { ++ os::thread_local_storage_at_put(ThreadLocalStorage::thread_index(), thread); ++} +--- /dev/null Thu Jan 01 00:00:00 1970 +0000 ++++ openjdk/hotspot/src/os_cpu/linux_sparc/vm/threadLS_linux_sparc.hpp Thu Apr 24 15:07:57 2008 -0400 +@@ -0,0 +1,28 @@ ++/* ++ * Copyright 1998-2005 Sun Microsystems, Inc. All Rights Reserved. ++ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. ++ * ++ * This code is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 only, as ++ * published by the Free Software Foundation. ++ * ++ * This code is distributed in the hope that it will be useful, but WITHOUT ++ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or ++ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ++ * version 2 for more details (a copy is included in the LICENSE file that ++ * accompanied this code). ++ * ++ * You should have received a copy of the GNU General Public License version ++ * 2 along with this work; if not, write to the Free Software Foundation, ++ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. ++ * ++ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, ++ * CA 95054 USA or visit www.sun.com if you need additional information or ++ * have any questions. ++ * ++ */ ++ ++public: ++ static Thread* thread() { ++ return (Thread*) os::thread_local_storage_at(thread_index()); ++ } +--- /dev/null Thu Jan 01 00:00:00 1970 +0000 ++++ openjdk/hotspot/src/os_cpu/linux_sparc/vm/thread_linux_sparc.cpp Thu Apr 24 15:07:57 2008 -0400 +@@ -0,0 +1,107 @@ ++/* ++ * Copyright 2003-2004 Sun Microsystems, Inc. All Rights Reserved. ++ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. ++ * ++ * This code is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 only, as ++ * published by the Free Software Foundation. ++ * ++ * This code is distributed in the hope that it will be useful, but WITHOUT ++ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or ++ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ++ * version 2 for more details (a copy is included in the LICENSE file that ++ * accompanied this code). ++ * ++ * You should have received a copy of the GNU General Public License version ++ * 2 along with this work; if not, write to the Free Software Foundation, ++ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. ++ * ++ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, ++ * CA 95054 USA or visit www.sun.com if you need additional information or ++ * have any questions. ++ * ++ */ ++ ++#include "incls/_precompiled.incl" ++#include "incls/_thread_linux_sparc.cpp.incl" ++ ++// For Forte Analyzer AsyncGetCallTrace profiling support - thread is ++// currently interrupted by SIGPROF ++bool JavaThread::pd_get_top_frame_for_signal_handler(frame* fr_addr, ++ void* ucontext, ++ bool isInJava) { ++ assert(Thread::current() == this, "caller must be current thread"); ++ assert(this->is_Java_thread(), "must be JavaThread"); ++ ++ JavaThread* jt = (JavaThread *)this; ++ ++ if (!isInJava) { ++ // make_walkable flushes register windows and grabs last_Java_pc ++ // which can not be done if the ucontext sp matches last_Java_sp ++ // stack walking utilities assume last_Java_pc set if marked flushed ++ jt->frame_anchor()->make_walkable(jt); ++ } ++ ++ // If we have a walkable last_Java_frame, then we should use it ++ // even if isInJava == true. It should be more reliable than ++ // ucontext info. ++ if (jt->has_last_Java_frame() && jt->frame_anchor()->walkable()) { ++ *fr_addr = jt->pd_last_frame(); ++ return true; ++ } ++ ++ ucontext_t* uc = (ucontext_t*) ucontext; ++ ++ // At this point, we don't have a walkable last_Java_frame, so ++ // we try to glean some information out of the ucontext. ++ intptr_t* ret_sp; ++ ExtendedPC addr = ++ os::fetch_frame_from_context(uc, &ret_sp, ++ NULL /* ret_fp only used on X86 */); ++ if (addr.pc() == NULL || ret_sp == NULL) { ++ // ucontext wasn't useful ++ return false; ++ } ++ ++ // we were running Java code when SIGPROF came in ++ if (isInJava) { ++ // If we have a last_Java_sp, then the SIGPROF signal caught us ++ // right when we were transitioning from _thread_in_Java to a new ++ // JavaThreadState. We use last_Java_sp instead of the sp from ++ // the ucontext since it should be more reliable. ++ if (jt->has_last_Java_frame()) { ++ ret_sp = jt->last_Java_sp(); ++ } ++ // Implied else: we don't have a last_Java_sp so we use what we ++ // got from the ucontext. ++ ++ frame ret_frame(ret_sp, frame::unpatchable, addr.pc()); ++ if (!ret_frame.safe_for_sender(jt)) { ++ // nothing else to try if the frame isn't good ++ return false; ++ } ++ *fr_addr = ret_frame; ++ return true; ++ } ++ ++ // At this point, we know we weren't running Java code. We might ++ // have a last_Java_sp, but we don't have a walkable frame. ++ // However, we might still be able to construct something useful ++ // if the thread was running native code. ++ if (jt->has_last_Java_frame()) { ++ assert(!jt->frame_anchor()->walkable(), "case covered above"); ++ ++ if (jt->thread_state() == _thread_in_native) { ++ frame ret_frame(jt->last_Java_sp(), frame::unpatchable, addr.pc()); ++ if (!ret_frame.safe_for_sender(jt)) { ++ // nothing else to try if the frame isn't good ++ return false; ++ } ++ *fr_addr = ret_frame; ++ return true; ++ } ++ } ++ ++ // nothing else to try ++ return false; ++} +--- /dev/null Thu Jan 01 00:00:00 1970 +0000 ++++ openjdk/hotspot/src/os_cpu/linux_sparc/vm/thread_linux_sparc.hpp Thu Apr 24 15:07:57 2008 -0400 +@@ -0,0 +1,98 @@ ++/* ++ * Copyright 1998-2007 Sun Microsystems, Inc. All Rights Reserved. ++ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. ++ * ++ * This code is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 only, as ++ * published by the Free Software Foundation. ++ * ++ * This code is distributed in the hope that it will be useful, but WITHOUT ++ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or ++ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ++ * version 2 for more details (a copy is included in the LICENSE file that ++ * accompanied this code). ++ * ++ * You should have received a copy of the GNU General Public License version ++ * 2 along with this work; if not, write to the Free Software Foundation, ++ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. ++ * ++ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, ++ * CA 95054 USA or visit www.sun.com if you need additional information or ++ * have any questions. ++ * ++ */ ++ ++private: ++ ++ void pd_initialize() { ++ _anchor.clear(); ++ _base_of_stack_pointer = NULL; ++ } ++ ++ frame pd_last_frame() { ++ assert(has_last_Java_frame(), "must have last_Java_sp() when suspended"); ++ assert(_anchor.walkable(), "thread has not dumped its register windows yet"); ++ ++ assert(_anchor.last_Java_pc() != NULL, "Ack no pc!"); ++ return frame(last_Java_sp(), frame::unpatchable, _anchor.last_Java_pc()); ++ } ++ ++ // Sometimes the trap handler needs to record both PC and NPC. ++ // This is a SPARC-specific companion to Thread::set_saved_exception_pc. ++ address _saved_exception_npc; ++ ++ // In polling_page_safepoint_handler_blob(s) we have to tail call other ++ // blobs without blowing any registers. A tail call requires some ++ // register to jump with and we can't blow any registers, so it must ++ // be restored in the delay slot. 'restore' cannot be used as it ++ // will chop the heads off of 64-bit %o registers in the 32-bit ++ // build. Instead we reload the registers using G2_thread and this ++ // location. Must be 64bits in the 32-bit LION build. ++ jdouble _o_reg_temps[6]; ++ ++ // a stack pointer older than any java frame stack pointer. It is ++ // used to validate stack pointers in frame::next_younger_sp (it ++ // provides the upper bound in the range check). This is necessary ++ // on Solaris/SPARC since the ucontext passed to a signal handler is ++ // sometimes corrupt and we need a way to check the extracted sp. ++ intptr_t* _base_of_stack_pointer; ++ ++public: ++ ++ static int o_reg_temps_offset_in_bytes() { return offset_of(JavaThread, _o_reg_temps); } ++ ++#ifndef _LP64 ++ address o_reg_temps(int i) { return (address)&_o_reg_temps[i]; } ++#endif ++ ++ static int saved_exception_npc_offset_in_bytes() { return offset_of(JavaThread,_saved_exception_npc); } ++ ++ address saved_exception_npc() { return _saved_exception_npc; } ++ void set_saved_exception_npc(address a) { _saved_exception_npc = a; } ++ ++ ++public: ++ ++ intptr_t* base_of_stack_pointer() { return _base_of_stack_pointer; } ++ ++ void set_base_of_stack_pointer(intptr_t* base_sp) { ++ _base_of_stack_pointer = base_sp; ++ } ++ ++ void record_base_of_stack_pointer() { ++ intptr_t *sp = (intptr_t *)(((intptr_t)StubRoutines::Sparc::flush_callers_register_windows_func()())); ++ intptr_t *ysp; ++ while((ysp = (intptr_t*)sp[FP->sp_offset_in_saved_window()]) != NULL) { ++ sp = (intptr_t *)((intptr_t)ysp + STACK_BIAS); ++ } ++ _base_of_stack_pointer = sp; ++ } ++ ++ bool pd_get_top_frame_for_signal_handler(frame* fr_addr, void* ucontext, ++ bool isInJava); ++ ++ // These routines are only used on cpu architectures that ++ // have separate register stacks (Itanium). ++ static bool register_stack_overflow() { return false; } ++ static void enable_register_stack_guard() {} ++ static void disable_register_stack_guard() {} +--- /dev/null Thu Jan 01 00:00:00 1970 +0000 ++++ openjdk/hotspot/src/os_cpu/linux_sparc/vm/vmStructs_linux_sparc.hpp Thu Apr 24 15:07:57 2008 -0400 +@@ -0,0 +1,69 @@ ++/* ++ * Copyright 2000-2007 Sun Microsystems, Inc. All Rights Reserved. ++ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. ++ * ++ * This code is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 only, as ++ * published by the Free Software Foundation. ++ * ++ * This code is distributed in the hope that it will be useful, but WITHOUT ++ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or ++ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ++ * version 2 for more details (a copy is included in the LICENSE file that ++ * accompanied this code). ++ * ++ * You should have received a copy of the GNU General Public License version ++ * 2 along with this work; if not, write to the Free Software Foundation, ++ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. ++ * ++ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, ++ * CA 95054 USA or visit www.sun.com if you need additional information or ++ * have any questions. ++ * ++ */ ++ ++// These are the OS and CPU-specific fields, types and integer ++// constants required by the Serviceability Agent. This file is ++// referenced by vmStructs.cpp. ++ ++#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, last_entry) \ ++ \ ++ /******************************/ \ ++ /* Threads (NOTE: incomplete) */ \ ++ /******************************/ \ ++ \ ++ nonstatic_field(JavaThread, _base_of_stack_pointer, intptr_t*) \ ++ nonstatic_field(OSThread, _thread_id, pid_t) \ ++ nonstatic_field(OSThread, _pthread_id, pthread_t) \ ++ /* This must be the last entry, and must be present */ \ ++ last_entry() ++ ++ ++#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, last_entry) \ ++ \ ++ /**********************/ \ ++ /* POSIX Thread IDs */ \ ++ /**********************/ \ ++ \ ++ declare_integer_type(pid_t) \ ++ declare_unsigned_integer_type(pthread_t) \ ++ \ ++ /* This must be the last entry, and must be present */ \ ++ last_entry() ++ ++ ++#define VM_INT_CONSTANTS_OS_CPU(declare_constant, declare_preprocessor_constant, declare_c1_constant, declare_c2_constant, declare_c2_preprocessor_constant, last_entry) \ ++ \ ++ /************************/ \ ++ /* JavaThread constants */ \ ++ /************************/ \ ++ \ ++ declare_constant(JavaFrameAnchor::flushed) \ ++ \ ++ /* This must be the last entry, and must be present */ \ ++ last_entry() ++ ++#define VM_LONG_CONSTANTS_OS_CPU(declare_constant, declare_preprocessor_constant, declare_c1_constant, declare_c2_constant, declare_c2_preprocessor_constant, last_entry) \ ++ \ ++ /* This must be the last entry, and must be present */ \ ++ last_entry() +--- /dev/null Thu Jan 01 00:00:00 1970 +0000 ++++ openjdk/hotspot/src/os_cpu/linux_sparc/vm/vm_version_linux_sparc.cpp Thu Apr 24 15:07:57 2008 -0400 +@@ -0,0 +1,61 @@ ++/* ++ * Copyright 2006 Sun Microsystems, Inc. All Rights Reserved. ++ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. ++ * ++ * This code is free software; you can redistribute it and/or modify it ++ * under the terms of the GNU General Public License version 2 only, as ++ * published by the Free Software Foundation. ++ * ++ * This code is distributed in the hope that it will be useful, but WITHOUT ++ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or ++ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ++ * version 2 for more details (a copy is included in the LICENSE file that ++ * accompanied this code). ++ * ++ * You should have received a copy of the GNU General Public License version ++ * 2 along with this work; if not, write to the Free Software Foundation, ++ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. ++ * ++ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, ++ * CA 95054 USA or visit www.sun.com if you need additional information or ++ * have any questions. ++ * ++ */ ++ ++# include "incls/_precompiled.incl" ++# include "incls/_vm_version_linux_sparc.cpp.incl" ++ ++static bool detect_niagara() { ++ char cpu[128]; ++ bool rv = false; ++ ++ FILE* fp = fopen("/proc/cpuinfo", "r"); ++ if (fp == NULL) { ++ return rv; ++ } ++ ++ while (!feof(fp)) { ++ if (fscanf(fp, "cpu\t\t: %100[^\n]", &cpu) == 1) { ++ if (strstr(cpu, "Niagara") != NULL) { ++ rv = true; ++ } ++ break; ++ } ++ } ++ ++ fclose(fp); ++ ++ return rv; ++} ++ ++int VM_Version::platform_features(int features) { ++ // Default to generic v9 ++ features = generic_v9_m; ++ ++ if (detect_niagara()) { ++ NOT_PRODUCT(if (PrintMiscellaneous && Verbose) tty->print_cr("Detected Linux on Niagara");) ++ features = niagara1_m; ++ } ++ ++ return features; ++} + +diff -urN openjdk/hotspot/build/linux/makefiles/sparc.make openjdk/hotspot/build/linux/makefiles/sparc.make +--- openjdk/hotspot/build/linux/makefiles/sparc.make 1970-01-01 00:00:00.000000000 +0000 ++++ openjdk/hotspot/build/linux/makefiles/sparc.make 2008-05-13 19:08:58.000000000 +0000 +@@ -0,0 +1,27 @@ ++# ++# Copyright 1999-2005 Sun Microsystems, Inc. All Rights Reserved. ++# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. ++# ++# This code is free software; you can redistribute it and/or modify it ++# under the terms of the GNU General Public License version 2 only, as ++# published by the Free Software Foundation. ++# ++# This code is distributed in the hope that it will be useful, but WITHOUT ++# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or ++# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ++# version 2 for more details (a copy is included in the LICENSE file that ++# accompanied this code). ++# ++# You should have received a copy of the GNU General Public License version ++# 2 along with this work; if not, write to the Free Software Foundation, ++# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. ++# ++# Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara, ++# CA 95054 USA or visit www.sun.com if you need additional information or ++# have any questions. ++# ++# ++ ++# TLS helper, assembled from .s file ++# Not included in includeDB because it has no dependencies ++Obj_Files += linux_sparc.o +--- openjdk/hotspot/build/linux/makefiles/gcc.make.orig 2008-05-13 22:45:24.000000000 +0000 ++++ openjdk/hotspot/build/linux/makefiles/gcc.make 2008-05-13 22:46:34.000000000 +0000 +@@ -52,6 +52,10 @@ + PICFLAG = -fpic + endif + ++ifneq ($(filter sparc sparcv9,$(BUILDARCH)),) ++PICFLAG = -fPIC ++endif ++ + VM_PICFLAG/LIBJVM = $(PICFLAG) + VM_PICFLAG/AOUT = + +--- openjdk/hotspot/src/os_cpu/linux_sparc/vm/os_linux_sparc.cpp.orig 2008-05-13 22:48:33.000000000 +0000 ++++ openjdk/hotspot/src/os_cpu/linux_sparc/vm/os_linux_sparc.cpp 2008-05-14 06:58:25.000000000 +0000 +@@ -263,6 +263,16 @@ + + // Utility functions + ++julong os::allocatable_physical_memory(julong size) { ++ julong result = MIN2(size, (julong)3800*M); ++ if (!is_allocatable(result)) { ++ // See comments under solaris for alignment considerations ++ julong reasonable_size = (julong)2*G - 2 * os::vm_page_size(); ++ result = MIN2(size, reasonable_size); ++ } ++ return result; ++} ++ + extern "C" void Fetch32PFI(); + extern "C" void Fetch32Resume(); + extern "C" void FetchNPFI(); +--- openjdk/hotspot/build/linux/makefiles/defs.make.orig 2008-05-14 10:39:14.000000000 +0000 ++++ openjdk/hotspot/build/linux/makefiles/defs.make 2008-05-14 15:18:21.000000000 +0000 +@@ -59,7 +59,7 @@ + endif + + # sparc +-ifeq ($(ARCH), sparc64) ++ifneq (,$(filter $(ARCH), sparc sparc64)) + ifeq ($(ARCH_DATA_MODEL), 64) + ARCH_DATA_MODEL = 64 + MAKE_ARGS += LP64=1