Hi All,
I have made PostgreSQL to compile on linux using sun studio with
spinlock support. The patch is attached. Here is the explanation of
changes I made:
I renamed the following files
solaris_x86.s
solaris_sparch.s
to
sunstudio_x86.s
sunstudio_sparch.s
because the code is used on linux as well and is not related to solaris
but sunstudio.
I added the detection of Sun Studio to configure script, changed the
template for linux, so it gives same settings for sun studio as for solaris.
Finally, I changed the #ifdef of __sun macro to __SUNPRO_C macro in
s_lock.h. Macro __sun is defined on solaris by both gcc and sun studio
and it is not defined on linux. Macro __SUNPRO_C is defined on linux as
well as solaris by sun studio and is never defined by gcc.
I tested the patch (build process & make check) without any problems on:
x86, solaris nevada build 79; gcc 3.4.3 (csl-sol210-3_4-20050802)
x86, solaris nevada build 79; sun studio 12
x86, debian etch, gcc 4.1.2 (20061115)
x86, debian etch, sun studio 12
sparc, solaris 10U3, gcc 3.4.3 (csl-sol210-3_4-branch+sol_rpath)
sparc, solaris 10U3, sun studio 12
I do not have an access to linux sparc machine.
Thanks for your comments.
Cheers
Julo
Index: configure
--- configure
+++ configure
@@ -682,6 +682,7 @@
ac_ct_CC
EXEEXT
OBJEXT
+SSCC
CPP
GCC
TAS
@@ -3353,6 +3354,54 @@
rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+# Check if it's Sun Studio compiler. We assume that
+# __SUNPRO_C will be defined for Sun Studio compilers
+cat >conftest.$ac_ext <<_ACEOF
+/* confdefs.h. */
+_ACEOF
+cat confdefs.h >>conftest.$ac_ext
+cat >>conftest.$ac_ext <<_ACEOF
+/* end confdefs.h. */
+
+int
+main ()
+{
+#ifndef __SUNPRO_C
+choke me
+#endif
+ ;
+ return 0;
+}
+_ACEOF
+rm -f conftest.$ac_objext
+if { (ac_try="$ac_compile"
+case "(($ac_try" in
+ *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;;
+ *) ac_try_echo=$ac_try;;
+esac
+eval "echo \"\$as_me:$LINENO: $ac_try_echo\"") >&5
+ (eval "$ac_compile") 2>conftest.er1
+ ac_status=$?
+ grep -v '^ *+' conftest.er1 >conftest.err
+ rm -f conftest.er1
+ cat conftest.err >&5
+ echo "$as_me:$LINENO: \$? = $ac_status" >&5
+ (exit $ac_status); } && {
+ test -z "$ac_c_werror_flag" ||
+ test ! -s conftest.err
+ } && test -s conftest.$ac_objext; then
+ SSCC=yes
+else
+ echo "$as_me: failed program was:" >&5
+sed 's/^/| /' conftest.$ac_ext >&5
+
+ SSCC=no
+fi
+
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
+
+
+
unset CFLAGS
#
@@ -25545,6 +25594,7 @@
ac_ct_CC!$ac_ct_CC$ac_delim
EXEEXT!$EXEEXT$ac_delim
OBJEXT!$OBJEXT$ac_delim
+SSCC!$SSCC$ac_delim
CPP!$CPP$ac_delim
GCC!$GCC$ac_delim
TAS!$TAS$ac_delim
@@ -25577,7 +25627,6 @@
RANLIB!$RANLIB$ac_delim
STRIP!$STRIP$ac_delim
STRIP_STATIC_LIB!$STRIP_STATIC_LIB$ac_delim
-STRIP_SHARED_LIB!$STRIP_SHARED_LIB$ac_delim
_ACEOF
if test `sed -n "s/.*$ac_delim\$/X/p" conf$$subs.sed | grep -c X` = 97; then
@@ -25619,6 +25668,7 @@
ac_delim='%!_!# '
for ac_last_try in false false false false false :; do
cat >conf$$subs.sed <<_ACEOF
+STRIP_SHARED_LIB!$STRIP_SHARED_LIB$ac_delim
TAR!$TAR$ac_delim
LN_S!$LN_S$ac_delim
AWK!$AWK$ac_delim
@@ -25669,7 +25719,7 @@
LTLIBOBJS!$LTLIBOBJS$ac_delim
_ACEOF
- if test `sed -n "s/.*$ac_delim\$/X/p" conf$$subs.sed | grep -c X` = 48; then
+ if test `sed -n "s/.*$ac_delim\$/X/p" conf$$subs.sed | grep -c X` = 49; then
break
elif $ac_last_try; then
{ { echo "$as_me:$LINENO: error: could not make $CONFIG_STATUS" >&5
Index: configure.in
--- configure.in
+++ configure.in
@@ -241,6 +241,14 @@
choke me
@%:@endif], [ICC=[yes]], [ICC=[no]])
+# Check if it's Sun Studio compiler. We assume that
+# __SUNPRO_C will be defined for Sun Studio compilers
+AC_TRY_COMPILE([], [@%:@ifndef __SUNPRO_C
+choke me
+@%:@endif], [SSCC=[yes]], [SSCC=[no]])
+
+AC_SUBST(SSCC)
+
unset CFLAGS
#
Index: src/Makefile.global.in
--- src/Makefile.global.in
+++ src/Makefile.global.in
@@ -304,6 +304,7 @@
# Name of the "template"
PORTNAME= @PORTNAME@
+SUN_STUDIO_COMPILER = @SSCC@
host_tuple = @host@
host_os = @host_os@
Index: src/backend/port/Makefile
--- src/backend/port/Makefile
+++ src/backend/port/Makefile
@@ -33,12 +33,14 @@
include $(top_srcdir)/src/backend/common.mk
tas.o: tas.s
-ifeq ($(PORTNAME), solaris)
+ifeq ($(SUN_STUDIO_COMPILER), yes)
# preprocess assembler file with cpp, used by x86
+ echo YES.
$(CC) $(CFLAGS) -c -P $<
mv $*.i $*_cpp.s
$(CC) $(CFLAGS) -c $*_cpp.s -o $@
else
+ echo NO.
$(CC) $(CFLAGS) -c $<
endif
Index: src/backend/port/tas/solaris_sparc.s
--- src/backend/port/tas/solaris_sparc.s
+++ src/backend/port/tas/solaris_sparc.s
@@ -1,42 +0,0 @@
-!=======================================================================
-! solaris_sparc.s -- compare and swap for solaris_sparc
-!=======================================================================
-
-! Fortunately the Sun compiler can process cpp conditionals with -P
-
-! '/' is the comment for x86, while '!' is the comment for Sparc
-
-#if defined(__sparcv9) || defined(__sparc)
-
- .section ".text"
- .align 8
- .skip 24
- .align 4
-
- .global pg_atomic_cas
-pg_atomic_cas:
-
- ! "cas" only works on sparcv9 and sparcv8plus chips, and
- ! requies a compiler targeting these CPUs. It will fail
- ! on a compiler targeting sparcv8, and of course will not
- ! be understood by a sparcv8 CPU. gcc continues to use
- ! "ldstub" because it targets sparcv7.
- !
- ! There is actually a trick for embedding "cas" in a
- ! sparcv8-targeted compiler, but it can only be run
- ! on a sparcv8plus/v9 cpus:
- !
- ! http://cvs.opensolaris.org/source/xref/on/usr/src/lib/libc/sparc/threads/sparc.il
- !
-
-#if defined(__sparcv9) || defined(__sparcv8plus)
- cas [%o0],%o2,%o1
-#else
- ldstub [%o0],%o1
-#endif
- mov %o1,%o0
- retl
- nop
- .type pg_atomic_cas,2
- .size pg_atomic_cas,(.-pg_atomic_cas)
-#endif
Index: src/backend/port/tas/solaris_x86.s
--- src/backend/port/tas/solaris_x86.s
+++ src/backend/port/tas/solaris_x86.s
@@ -1,34 +0,0 @@
-/=======================================================================
-/ solaris_i386.s -- compare and swap for solaris_i386
-/=======================================================================
-
-/ Fortunately the Sun compiler can process cpp conditionals with -P
-
-/ '/' is the comment for x86, while '!' is the comment for Sparc
-
- .file "tas.s"
-
-#if defined(__amd64)
- .code64
-#endif
-
- .globl pg_atomic_cas
- .type pg_atomic_cas, @function
-
- .section .text, "ax"
- .align 16
-
-pg_atomic_cas:
-#if defined(__amd64)
- movl %edx,%eax
- lock
- cmpxchgl %esi,(%rdi)
-#else
- movl 4(%esp), %edx
- movl 8(%esp), %ecx
- movl 12(%esp), %eax
- lock
- cmpxchgl %ecx, (%edx)
-#endif
- ret
- .size pg_atomic_cas, . - pg_atomic_cas
Index: src/backend/port/tas/sunstudio_sparc.s
--- /dev/null
+++ src/backend/port/tas/sunstudio_sparc.s
@@ -0,0 +1,42 @@
+!=======================================================================
+! solaris_sparc.s -- compare and swap for solaris_sparc
+!=======================================================================
+
+! Fortunately the Sun compiler can process cpp conditionals with -P
+
+! '/' is the comment for x86, while '!' is the comment for Sparc
+
+#if defined(__sparcv9) || defined(__sparc)
+
+ .section ".text"
+ .align 8
+ .skip 24
+ .align 4
+
+ .global pg_atomic_cas
+pg_atomic_cas:
+
+ ! "cas" only works on sparcv9 and sparcv8plus chips, and
+ ! requies a compiler targeting these CPUs. It will fail
+ ! on a compiler targeting sparcv8, and of course will not
+ ! be understood by a sparcv8 CPU. gcc continues to use
+ ! "ldstub" because it targets sparcv7.
+ !
+ ! There is actually a trick for embedding "cas" in a
+ ! sparcv8-targeted compiler, but it can only be run
+ ! on a sparcv8plus/v9 cpus:
+ !
+ ! http://cvs.opensolaris.org/source/xref/on/usr/src/lib/libc/sparc/threads/sparc.il
+ !
+
+#if defined(__sparcv9) || defined(__sparcv8plus)
+ cas [%o0],%o2,%o1
+#else
+ ldstub [%o0],%o1
+#endif
+ mov %o1,%o0
+ retl
+ nop
+ .type pg_atomic_cas,2
+ .size pg_atomic_cas,(.-pg_atomic_cas)
+#endif
Index: src/backend/port/tas/sunstudio_x86.s
--- /dev/null
+++ src/backend/port/tas/sunstudio_x86.s
@@ -0,0 +1,34 @@
+/=======================================================================
+/ solaris_i386.s -- compare and swap for solaris_i386
+/=======================================================================
+
+/ Fortunately the Sun compiler can process cpp conditionals with -P
+
+/ '/' is the comment for x86, while '!' is the comment for Sparc
+
+ .file "tas.s"
+
+#if defined(__amd64)
+ .code64
+#endif
+
+ .globl pg_atomic_cas
+ .type pg_atomic_cas, @function
+
+ .section .text, "ax"
+ .align 16
+
+pg_atomic_cas:
+#if defined(__amd64)
+ movl %edx,%eax
+ lock
+ cmpxchgl %esi,(%rdi)
+#else
+ movl 4(%esp), %edx
+ movl 8(%esp), %ecx
+ movl 12(%esp), %eax
+ lock
+ cmpxchgl %ecx, (%edx)
+#endif
+ ret
+ .size pg_atomic_cas, . - pg_atomic_cas
Index: src/include/storage/s_lock.h
--- src/include/storage/s_lock.h
+++ src/include/storage/s_lock.h
@@ -578,7 +578,7 @@
#endif
-#endif /* __GNUC__ */
+#endif /* defined(__GNUC__) || defined(__INTEL_COMPILER) */
@@ -782,7 +782,7 @@
#endif
-#if defined(__sun) && (defined(__i386) || defined(__x86_64__) || defined(__sparc__) || defined(__sparc))
+#if defined(__SUNPRO_C) && (defined(__i386) || defined(__x86_64__) || defined(__sparc__) || defined(__sparc))
#define HAS_TEST_AND_SET
#if defined(__i386) || defined(__x86_64__) || defined(__sparcv9) || defined(__sparcv8plus)
Index: src/template/linux
--- src/template/linux
+++ src/template/linux
@@ -1,7 +1,31 @@
# $PostgreSQL: pgsql/src/template/linux,v 1.30 2007/09/21 02:33:46 tgl Exp $
-# Force _GNU_SOURCE on; plperl is broken with Perl 5.8.0 otherwise
-CPPFLAGS="$CPPFLAGS -D_GNU_SOURCE"
+if test "$SSCC" != "yes" ; then
+ # Force _GNU_SOURCE on; plperl is broken with Perl 5.8.0 otherwise
+ CPPFLAGS="$CPPFLAGS -D_GNU_SOURCE"
-# If --enable-profiling is specified, we need -DLINUX_PROFILE
-PLATFORM_PROFILE_FLAGS="-DLINUX_PROFILE"
+ # If --enable-profiling is specified, we need -DLINUX_PROFILE
+ PLATFORM_PROFILE_FLAGS="-DLINUX_PROFILE"
+else
+ # fiif test "$GCC" != yes ; then
+ CC="$CC -Xa" # relaxed ISO C mode
+ CFLAGS="-v -DSUNOS4_CC" # -v is like gcc -Wall
+ if test "$enable_debug" != yes; then
+ CFLAGS="$CFLAGS -O" # any optimization breaks debug
+ fi
+
+ # Pick the right test-and-set (TAS) code for the Sun compiler.
+ # We would like to use in-line assembler, but the compiler
+ # requires *.il files to be on every compile line, making
+ # the build system too fragile.
+ case $host in
+ sparc-*-linux*)
+ need_tas=yes
+ tas_file=sunstudio_sparc.s
+ ;;
+ i?86-*-linux*)
+ need_tas=yes
+ tas_file=sunstudio_x86.s
+ ;;
+ esac
+fi
Index: src/template/solaris
--- src/template/solaris
+++ src/template/solaris
@@ -12,11 +12,11 @@
case $host in
sparc-*-solaris*)
need_tas=yes
- tas_file=solaris_sparc.s
+ tas_file=sunstudio_sparc.s
;;
i?86-*-solaris*)
need_tas=yes
- tas_file=solaris_x86.s
+ tas_file=sunstudio_x86.s
;;
esac
fi