8032045: Enable compiler and linker safety switches for debug builds
authormduigou
Thu, 12 Jun 2014 16:31:07 -0700
changeset 24955 fbde9efb7b56
parent 24954 9bd47e3d7c69
child 24956 208e807ef3b0
8032045: Enable compiler and linker safety switches for debug builds Summary: Enable GCC linker protections, runtime bounds checks and stack protection. Reviewed-by: dholmes, kvn, coleenp
hotspot/make/bsd/makefiles/fastdebug.make
hotspot/make/bsd/makefiles/gcc.make
hotspot/make/linux/makefiles/fastdebug.make
hotspot/make/linux/makefiles/gcc.make
hotspot/make/solaris/makefiles/gcc.make
--- a/hotspot/make/bsd/makefiles/fastdebug.make	Thu Jun 12 10:15:43 2014 -0700
+++ b/hotspot/make/bsd/makefiles/fastdebug.make	Thu Jun 12 16:31:07 2014 -0700
@@ -24,37 +24,30 @@
 
 # Sets make macros for making debug version of VM
 
+# Compiler specific DEBUG_CFLAGS are passed in from gcc.make, sparcWorks.make
+# They may also specify FASTDEBUG_CFLAGS, but it defaults to DEBUG_CFLAGS.
+
+FASTDEBUG_CFLAGS$(FASTDEBUG_CFLAGS) = $(DEBUG_CFLAGS)
+
 # Compiler specific OPT_CFLAGS are passed in from gcc.make, sparcWorks.make
 OPT_CFLAGS/DEFAULT= $(OPT_CFLAGS)
 OPT_CFLAGS/BYFILE = $(OPT_CFLAGS/$@)$(OPT_CFLAGS/DEFAULT$(OPT_CFLAGS/$@))
 
 # (OPT_CFLAGS/SLOWER is also available, to alter compilation of buggy files)
 
-ifeq ($(BUILDARCH), ia64)
-  # Bug in GCC, causes hang.  -O1 will override the -O3 specified earlier
-  OPT_CFLAGS/callGenerator.o += -O1
-  OPT_CFLAGS/ciTypeFlow.o += -O1
-  OPT_CFLAGS/compile.o += -O1
-  OPT_CFLAGS/concurrentMarkSweepGeneration.o += -O1
-  OPT_CFLAGS/doCall.o += -O1
-  OPT_CFLAGS/generateOopMap.o += -O1
-  OPT_CFLAGS/generateOptoStub.o += -O1
-  OPT_CFLAGS/graphKit.o += -O1
-  OPT_CFLAGS/instanceKlass.o += -O1
-  OPT_CFLAGS/interpreterRT_ia64.o += -O1
-  OPT_CFLAGS/output.o += -O1
-  OPT_CFLAGS/parse1.o += -O1
-  OPT_CFLAGS/runtime.o += -O1
-  OPT_CFLAGS/synchronizer.o += -O1
-endif
-
-
 # If you set HOTSPARC_GENERIC=yes, you disable all OPT_CFLAGS settings
 CFLAGS$(HOTSPARC_GENERIC) += $(OPT_CFLAGS/BYFILE)
 
 # Set the environment variable HOTSPARC_GENERIC to "true"
 # to inhibit the effect of the previous line on CFLAGS.
 
+# The following lines are copied from debug.make, except that we
+# consult FASTDEBUG_CFLAGS instead of DEBUG_CFLAGS.
+# Compiler specific DEBUG_CFLAGS are passed in from gcc.make, sparcWorks.make
+DEBUG_CFLAGS/DEFAULT= $(FASTDEBUG_CFLAGS)
+DEBUG_CFLAGS/BYFILE = $(DEBUG_CFLAGS/$@)$(DEBUG_CFLAGS/DEFAULT$(DEBUG_CFLAGS/$@))
+CFLAGS += $(DEBUG_CFLAGS/BYFILE)
+
 # Linker mapfile
 MAPFILE = $(GAMMADIR)/make/bsd/makefiles/mapfile-vers-debug
 ifeq ($(OS_VENDOR), Darwin)
--- a/hotspot/make/bsd/makefiles/gcc.make	Thu Jun 12 10:15:43 2014 -0700
+++ b/hotspot/make/bsd/makefiles/gcc.make	Thu Jun 12 16:31:07 2014 -0700
@@ -19,7 +19,7 @@
 # Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 # or visit www.oracle.com if you need additional information or have any
 # questions.
-#  
+#
 #
 
 OS_VENDOR = $(shell uname -s)
@@ -80,7 +80,7 @@
     HOSTCC  = $(CC)
   endif
 
-  AS   = $(CC) -c 
+  AS  = $(CC) -c
 endif
 
 ifeq ($(OS_VENDOR), Darwin)
@@ -100,7 +100,7 @@
 endif
 
 ifeq ($(USE_CLANG), true)
-  # clang has precompiled headers support by default, but the user can switch
+  # Clang has precompiled headers support by default, but the user can switch
   # it off by using 'USE_PRECOMPILED_HEADER=0'.
   ifdef LP64
     ifeq ($(USE_PRECOMPILED_HEADER),)
@@ -112,29 +112,29 @@
     # Clang produces an error if the PCH file was compiled with other options than the actual compilation unit.
     USE_PRECOMPILED_HEADER=0
   endif
-  
+
   ifeq ($(USE_PRECOMPILED_HEADER),1)
-  
+
     ifndef LP64
       $(error " Precompiled Headers only supported on 64-bit platforms!")
     endif
-  
+
     PRECOMPILED_HEADER_DIR=.
     PRECOMPILED_HEADER_SRC=$(GAMMADIR)/src/share/vm/precompiled/precompiled.hpp
     PRECOMPILED_HEADER=$(PRECOMPILED_HEADER_DIR)/precompiled.hpp.pch
-  
+
     PCH_FLAG = -include precompiled.hpp
     PCH_FLAG/DEFAULT = $(PCH_FLAG)
     PCH_FLAG/NO_PCH = -DNO_PCH
     PCH_FLAG/BY_FILE = $(PCH_FLAG/$@)$(PCH_FLAG/DEFAULT$(PCH_FLAG/$@))
-  
+
     VM_PCH_FLAG/LIBJVM = $(PCH_FLAG/BY_FILE)
     VM_PCH_FLAG/AOUT =
     VM_PCH_FLAG = $(VM_PCH_FLAG/$(LINK_INTO))
-  
+
     # We only use precompiled headers for the JVM build
     CFLAGS += $(VM_PCH_FLAG)
- 
+
     # The following files are compiled at various optimization
     # levels due to optimization issues encountered at the
     # 'OPT_CFLAGS_DEFAULT' level. The Clang compiler issues a compile
@@ -149,7 +149,7 @@
     PCH_FLAG/sharedRuntimeTrig.o = $(PCH_FLAG/NO_PCH)
     PCH_FLAG/sharedRuntimeTrans.o = $(PCH_FLAG/NO_PCH)
     PCH_FLAG/unsafe.o = $(PCH_FLAG/NO_PCH)
-  
+
   endif
 else # ($(USE_CLANG), true)
   # check for precompiled headers support
@@ -272,21 +272,24 @@
 
 CFLAGS_WARN/DEFAULT = $(WARNINGS_ARE_ERRORS) $(WARNING_FLAGS)
 # Special cases
-CFLAGS_WARN/BYFILE = $(CFLAGS_WARN/$@)$(CFLAGS_WARN/DEFAULT$(CFLAGS_WARN/$@)) 
+CFLAGS_WARN/BYFILE = $(CFLAGS_WARN/$@)$(CFLAGS_WARN/DEFAULT$(CFLAGS_WARN/$@))
 # XXXDARWIN: for _dyld_bind_fully_image_containing_address
 ifeq ($(OS_VENDOR), Darwin)
   CFLAGS_WARN/os_bsd.o = $(CFLAGS_WARN/DEFAULT) -Wno-deprecated-declarations
 endif
 
+# optimization control flags (Used by fastdebug and release variants)
+OPT_CFLAGS/NOOPT=-O0
+ifeq "$(shell expr \( $(CC_VER_MAJOR) \> 4 \) \| \( \( $(CC_VER_MAJOR) = 4 \) \& \( $(CC_VER_MINOR) \>= 8 \) \))" "1"
+  # Allow basic optimizations which don't distrupt debugging. (Principally dead code elimination)
+  OPT_CFLAGS/DEBUG=-Og
+else
+  # Allow no optimizations.
+ OPT_CFLAGS/DEBUG=-O0
+endif
 OPT_CFLAGS/SIZE=-Os
 OPT_CFLAGS/SPEED=-O3
 
-# Hotspot uses very unstrict aliasing turn this optimization off
-# This option is added to CFLAGS rather than OPT_CFLAGS
-# so that OPT_CFLAGS overrides get this option too.
-CFLAGS += -fno-strict-aliasing
-
-# The flags to use for an Optimized g++ build
 ifeq ($(OS_VENDOR), Darwin)
   # use -Os by default, unless -O3 can be proved to be worth the cost, as per policy
   # <https://wiki.openjdk.java.net/display/MacOSXPort/Compiler+Errata>
@@ -295,6 +298,11 @@
   OPT_CFLAGS_DEFAULT ?= SPEED
 endif
 
+# Hotspot uses very unstrict aliasing turn this optimization off
+# This option is added to CFLAGS rather than OPT_CFLAGS
+# so that OPT_CFLAGS overrides get this option too.
+CFLAGS += -fno-strict-aliasing
+
 ifdef OPT_CFLAGS
   ifneq ("$(origin OPT_CFLAGS)", "command line")
     $(error " Use OPT_EXTRAS instead of OPT_CFLAGS to add extra flags to OPT_CFLAGS.")
@@ -309,8 +317,6 @@
 OPT_CFLAGS += -fno-expensive-optimizations
 endif
 
-OPT_CFLAGS/NOOPT=-O0
-
 # Work around some compiler bugs.
 ifeq ($(USE_CLANG), true)
   ifeq ($(shell expr $(CC_VER_MAJOR) = 4 \& $(CC_VER_MINOR) = 2), 1)
@@ -338,7 +344,7 @@
 endif
 
 ifeq ($(OS_VENDOR), Darwin)
-  # Setting these parameters makes it an error to link to macosx APIs that are 
+  # Setting these parameters makes it an error to link to macosx APIs that are
   # newer than the given OS version and makes the linked binaries compatible even
   # if built on a newer version of the OS.
   # The expected format is X.Y.Z
@@ -371,10 +377,22 @@
 
 ifeq ($(USE_CLANG),)
   # statically link libgcc and/or libgcc_s, libgcc does not exist before gcc-3.x.
-  ifneq ("${CC_VER_MAJOR}", "2")
+  ifneq ($(CC_VER_MAJOR), 2)
     STATIC_LIBGCC += -static-libgcc
   endif
 
+  ifneq ($(OS_VENDOR), Darwin)
+    ifneq (, findstring(debug,$(BUILD_FLAVOR)))
+      # for relocations read-only
+      LFLAGS += -Xlinker -z -Xlinker relro
+
+      ifeq ($(BUILD_FLAVOR), debug)
+        # disable incremental relocations linking
+        LFLAGS += -Xlinker -z -Xlinker now
+      endif
+    endif
+  endif
+
   ifeq ($(BUILDARCH), ia64)
     LFLAGS += -Wl,-relax
   endif
@@ -425,6 +443,14 @@
   CFLAGS += -flimit-debug-info
 endif
 
+ifeq "$(shell expr \( $(CC_VER_MAJOR) \> 4 \) \| \( \( $(CC_VER_MAJOR) = 4 \) \& \( $(CC_VER_MINOR) \>= 8 \) \))" "1"
+  # Allow basic optimizations which don't distrupt debugging. (Principally dead code elimination)
+  DEBUG_CFLAGS=-Og
+else
+  # Allow no optimizations.
+  DEBUG_CFLAGS=-O0
+endif
+
 # DEBUG_BINARIES uses full -g debug information for all configs
 ifeq ($(DEBUG_BINARIES), true)
   CFLAGS += -g
@@ -441,9 +467,14 @@
   DEBUG_CFLAGS/ppc   = -g
   DEBUG_CFLAGS += $(DEBUG_CFLAGS/$(BUILDARCH))
   ifeq ($(DEBUG_CFLAGS/$(BUILDARCH)),)
-  DEBUG_CFLAGS += -gstabs
+      ifeq ($(USE_CLANG), true)
+        # Clang doesn't understand -gstabs
+        DEBUG_CFLAGS += -g
+      else
+        DEBUG_CFLAGS += -gstabs
+      endif
   endif
-  
+
   ifeq ($(ENABLE_FULL_DEBUG_SYMBOLS),1)
     FASTDEBUG_CFLAGS/ia64  = -g
     FASTDEBUG_CFLAGS/amd64 = -g
@@ -458,7 +489,7 @@
         FASTDEBUG_CFLAGS += -gstabs
       endif
     endif
-  
+
     OPT_CFLAGS/ia64  = -g
     OPT_CFLAGS/amd64 = -g
     OPT_CFLAGS/arm   = -g
@@ -475,6 +506,18 @@
   endif
 endif
 
+ifeq ($(USE_CLANG),)
+  # Enable bounds checking.
+  # _FORTIFY_SOURCE appears in GCC 4.0+
+  ifeq "$(shell expr \( $(CC_VER_MAJOR) \> 3 \) )" "1"
+    # compile time size bounds checks
+    FASTDEBUG_CFLAGS += -U_FORTIFY_SOURCE -D_FORTIFY_SOURCE=1
+
+    # and runtime size bounds checks and paranoid stack smashing checks.
+    DEBUG_CFLAGS += -U_FORTIFY_SOURCE -D_FORTIFY_SOURCE=2 -fstack-protector-all --param ssp-buffer-size=1
+  endif
+endif
+
 # If we are building HEADLESS, pass on to VM
 # so it can set the java.awt.headless property
 ifdef HEADLESS
--- a/hotspot/make/linux/makefiles/fastdebug.make	Thu Jun 12 10:15:43 2014 -0700
+++ b/hotspot/make/linux/makefiles/fastdebug.make	Thu Jun 12 16:31:07 2014 -0700
@@ -24,6 +24,11 @@
 
 # Sets make macros for making debug version of VM
 
+# Compiler specific DEBUG_CFLAGS are passed in from gcc.make, sparcWorks.make
+# They may also specify FASTDEBUG_CFLAGS, but it defaults to DEBUG_CFLAGS.
+
+FASTDEBUG_CFLAGS$(FASTDEBUG_CFLAGS) = $(DEBUG_CFLAGS)
+
 # Compiler specific OPT_CFLAGS are passed in from gcc.make, sparcWorks.make
 OPT_CFLAGS/DEFAULT= $(OPT_CFLAGS)
 OPT_CFLAGS/BYFILE = $(OPT_CFLAGS/$@)$(OPT_CFLAGS/DEFAULT$(OPT_CFLAGS/$@))
@@ -54,6 +59,12 @@
 
 # Set the environment variable HOTSPARC_GENERIC to "true"
 # to inhibit the effect of the previous line on CFLAGS.
+# The following lines are copied from debug.make, except that we
+# consult FASTDEBUG_CFLAGS instead of DEBUG_CFLAGS.
+# Compiler specific DEBUG_CFLAGS are passed in from gcc.make, sparcWorks.make
+DEBUG_CFLAGS/DEFAULT= $(FASTDEBUG_CFLAGS)
+DEBUG_CFLAGS/BYFILE = $(DEBUG_CFLAGS/$@)$(DEBUG_CFLAGS/DEFAULT$(DEBUG_CFLAGS/$@))
+CFLAGS += $(DEBUG_CFLAGS/BYFILE)
 
 # Linker mapfile
 MAPFILE = $(GAMMADIR)/make/linux/makefiles/mapfile-vers-debug
--- a/hotspot/make/linux/makefiles/gcc.make	Thu Jun 12 10:15:43 2014 -0700
+++ b/hotspot/make/linux/makefiles/gcc.make	Thu Jun 12 16:31:07 2014 -0700
@@ -19,7 +19,7 @@
 # Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 # or visit www.oracle.com if you need additional information or have any
 # questions.
-#  
+#
 #
 
 #------------------------------------------------------------------------
@@ -62,7 +62,6 @@
   CC_VER_MINOR := $(shell $(CC) -dumpversion | sed 's/egcs-//' | cut -d'.' -f2)
 endif
 
-
 ifeq ($(USE_CLANG), true)
   # Clang has precompiled headers support by default, but the user can switch
   # it off by using 'USE_PRECOMPILED_HEADER=0'.
@@ -104,7 +103,7 @@
     # But Clang doesn't support a precompiled header which was compiled with -O3
     # to be used in a compilation unit which uses '-O0'. We could also prepare an
     # extra '-O0' PCH file for the opt build and use it here, but it's probably
-    # not worth the effoert as long as only two files need this special handling.
+    # not worth the effort as long as only two files need this special handling.
     PCH_FLAG/loopTransform.o = $(PCH_FLAG/NO_PCH)
     PCH_FLAG/sharedRuntimeTrig.o = $(PCH_FLAG/NO_PCH)
     PCH_FLAG/sharedRuntimeTrans.o = $(PCH_FLAG/NO_PCH)
@@ -226,19 +225,28 @@
 endif
 
 CFLAGS_WARN/DEFAULT = $(WARNINGS_ARE_ERRORS) $(WARNING_FLAGS)
+
 # Special cases
-CFLAGS_WARN/BYFILE = $(CFLAGS_WARN/$@)$(CFLAGS_WARN/DEFAULT$(CFLAGS_WARN/$@)) 
+CFLAGS_WARN/BYFILE = $(CFLAGS_WARN/$@)$(CFLAGS_WARN/DEFAULT$(CFLAGS_WARN/$@))
 
-# The flags to use for an Optimized g++ build
+# optimization control flags (Used by fastdebug and release variants)
+OPT_CFLAGS/NOOPT=-O0
+ifeq "$(shell expr \( $(CC_VER_MAJOR) \> 4 \) \| \( \( $(CC_VER_MAJOR) = 4 \) \& \( $(CC_VER_MINOR) \>= 8 \) \))" "1"
+  # Allow basic optimizations which don't distrupt debugging. (Principally dead code elimination)
+  OPT_CFLAGS/DEBUG=-Og
+else
+  # Allow no optimizations.
+  OPT_CFLAGS/DEBUG=-O0
+endif
 OPT_CFLAGS/SIZE=-Os
 OPT_CFLAGS/SPEED=-O3
 
+OPT_CFLAGS_DEFAULT ?= SPEED
+
 # Hotspot uses very unstrict aliasing turn this optimization off
 # This option is added to CFLAGS rather than OPT_CFLAGS
 # so that OPT_CFLAGS overrides get this option too.
-CFLAGS += -fno-strict-aliasing 
-
-OPT_CFLAGS_DEFAULT ?= SPEED
+CFLAGS += -fno-strict-aliasing
 
 ifdef OPT_CFLAGS
   ifneq ("$(origin OPT_CFLAGS)", "command line")
@@ -248,14 +256,12 @@
 
 OPT_CFLAGS = $(OPT_CFLAGS/$(OPT_CFLAGS_DEFAULT)) $(OPT_EXTRAS)
 
-# The gcc compiler segv's on ia64 when compiling bytecodeInterpreter.cpp 
+# The gcc compiler segv's on ia64 when compiling bytecodeInterpreter.cpp
 # if we use expensive-optimizations
 ifeq ($(BUILDARCH), ia64)
 OPT_CFLAGS += -fno-expensive-optimizations
 endif
 
-OPT_CFLAGS/NOOPT=-O0
-
 # Work around some compiler bugs.
 ifeq ($(USE_CLANG), true)
   ifeq ($(shell expr $(CC_VER_MAJOR) = 4 \& $(CC_VER_MINOR) = 2), 1)
@@ -271,7 +277,7 @@
 # Flags for generating make dependency flags.
 DEPFLAGS = -MMD -MP -MF $(DEP_DIR)/$(@:%=%.d)
 ifeq ($(USE_CLANG),)
-  ifneq ("${CC_VER_MAJOR}", "2")
+  ifneq ($(CC_VER_MAJOR), 2)
     DEPFLAGS += -fpch-deps
   endif
 endif
@@ -282,21 +288,26 @@
 # statically link libstdc++.so, work with gcc but ignored by g++
 STATIC_STDCXX = -Wl,-Bstatic -lstdc++ -Wl,-Bdynamic
 
+# Enable linker optimization
+LFLAGS += -Xlinker -O1
+
 ifeq ($(USE_CLANG),)
-  # statically link libgcc and/or libgcc_s, libgcc does not exist before gcc-3.x.
-  ifneq ("${CC_VER_MAJOR}", "2")
-    STATIC_LIBGCC += -static-libgcc
+  STATIC_LIBGCC += -static-libgcc
+
+  ifneq (, findstring(debug,$(BUILD_FLAVOR)))
+    # for relocations read-only
+    LFLAGS += -Xlinker -z -Xlinker relro
+
+    ifeq ($(BUILD_FLAVOR), debug)
+      # disable incremental relocations linking
+      LFLAGS += -Xlinker -z -Xlinker now
+    endif
   endif
 
   ifeq ($(BUILDARCH), ia64)
     LFLAGS += -Wl,-relax
   endif
-endif
 
-# Enable linker optimization
-LFLAGS += -Xlinker -O1
-
-ifeq ($(USE_CLANG),)
   # If this is a --hash-style=gnu system, use --hash-style=both
   #   The gnu .hash section won't work on some Linux systems like SuSE 10.
   _HAS_HASH_STYLE_GNU:=$(shell $(CC) -dumpspecs | grep -- '--hash-style=gnu')
@@ -333,6 +344,14 @@
   CFLAGS += -flimit-debug-info
 endif
 
+ifeq "$(shell expr \( $(CC_VER_MAJOR) \> 4 \) \| \( \( $(CC_VER_MAJOR) = 4 \) \& \( $(CC_VER_MINOR) \>= 8 \) \))" "1"
+  # Allow basic optimizations which don't distrupt debugging. (Principally dead code elimination)
+  DEBUG_CFLAGS=-Og
+else
+  # Allow no optimizations.
+  DEBUG_CFLAGS=-O0
+endif
+
 # DEBUG_BINARIES uses full -g debug information for all configs
 ifeq ($(DEBUG_BINARIES), true)
   CFLAGS += -g
@@ -355,6 +374,18 @@
   endif
 endif
 
+ifeq ($(USE_CLANG),)
+  # Enable bounds checking.
+  # _FORTIFY_SOURCE appears in GCC 4.0+
+  ifeq "$(shell expr \( $(CC_VER_MAJOR) \> 3 \) )" "1"
+    # compile time size bounds checks
+    FASTDEBUG_CFLAGS += -U_FORTIFY_SOURCE -D_FORTIFY_SOURCE=1
+
+    # and runtime size bounds checks and paranoid stack smashing checks.
+    DEBUG_CFLAGS += -U_FORTIFY_SOURCE -D_FORTIFY_SOURCE=2 -fstack-protector-all --param ssp-buffer-size=1
+  endif
+endif
+
 # If we are building HEADLESS, pass on to VM
 # so it can set the java.awt.headless property
 ifdef HEADLESS
--- a/hotspot/make/solaris/makefiles/gcc.make	Thu Jun 12 10:15:43 2014 -0700
+++ b/hotspot/make/solaris/makefiles/gcc.make	Thu Jun 12 16:31:07 2014 -0700
@@ -19,7 +19,7 @@
 # Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 # or visit www.oracle.com if you need additional information or have any
 # questions.
-#  
+#
 #
 
 #------------------------------------------------------------------------
@@ -40,7 +40,7 @@
 CC_VER_MAJOR := $(shell $(CC) -dumpversion | sed 's/egcs-//' | cut -d'.' -f1)
 CC_VER_MINOR := $(shell $(CC) -dumpversion | sed 's/egcs-//' | cut -d'.' -f2)
 
-# Check for the versions of C++ and C compilers ($CXX and $CC) used. 
+# Check for the versions of C++ and C compilers ($CXX and $CC) used.
 
 # Get the last thing on the line that looks like x.x+ (x is a digit).
 COMPILER_REV := \
@@ -98,7 +98,7 @@
 
 ifeq ($(BUILDARCH), amd64)
 ASFLAGS += -march=k8  -march=amd64
-LFLAGS += -march=k8 
+LFLAGS += -march=k8
 endif
 
 
@@ -115,21 +115,44 @@
 endif
 
 
-# Compiler warnings are treated as errors 
-WARNINGS_ARE_ERRORS = -Werror 
+# Compiler warnings are treated as errors
+WARNINGS_ARE_ERRORS = -Werror
+
 # Enable these warnings. See 'info gcc' about details on these options
 WARNING_FLAGS = -Wpointer-arith -Wconversion -Wsign-compare -Wundef -Wformat=2
 CFLAGS_WARN/DEFAULT = $(WARNINGS_ARE_ERRORS) $(WARNING_FLAGS)
-# Special cases 
-CFLAGS_WARN/BYFILE = $(CFLAGS_WARN/$@)$(CFLAGS_WARN/DEFAULT$(CFLAGS_WARN/$@))  
+
+# Special cases
+CFLAGS_WARN/BYFILE = $(CFLAGS_WARN/$@)$(CFLAGS_WARN/DEFAULT$(CFLAGS_WARN/$@))
 
-# The flags to use for an Optimized g++ build
-OPT_CFLAGS += -O3
+# optimization control flags (Used by fastdebug and release variants)
+OPT_CFLAGS/NOOPT=-O0
+ifeq "$(shell expr \( $(CC_VER_MAJOR) \> 4 \) \| \( \( $(CC_VER_MAJOR) = 4 \) \& \( $(CC_VER_MINOR) \>= 8 \) \))" "1"
+  # Allow basic optimizations which don't distrupt debugging. (Principally dead code elimination)
+  OPT_CFLAGS/DEBUG=-Og
++else
+  # Allow no optimizations.
+  OPT_CFLAGS/DEBUG=-O0
+endif
+OPT_CFLAGS/SIZE=-Os
+OPT_CFLAGS/SPEED=-O3
+
+OPT_CFLAGS_DEFAULT ?= SPEED
 
 # Hotspot uses very unstrict aliasing turn this optimization off
-OPT_CFLAGS += -fno-strict-aliasing
+# This option is added to CFLAGS rather than OPT_CFLAGS
+# so that OPT_CFLAGS overrides get this option too.
+CFLAGS += -fno-strict-aliasing
 
-# The gcc compiler segv's on ia64 when compiling bytecodeInterpreter.cpp 
+ifdef OPT_CFLAGS
+  ifneq ("$(origin OPT_CFLAGS)", "command line")
+    $(error " Use OPT_EXTRAS instead of OPT_CFLAGS to add extra flags to OPT_CFLAGS.")
+  endif
+endif
+
+OPT_CFLAGS = $(OPT_CFLAGS/$(OPT_CFLAGS_DEFAULT)) $(OPT_EXTRAS)
+
+# The gcc compiler segv's on ia64 when compiling bytecodeInterpreter.cpp
 # if we use expensive-optimizations
 # Note: all ia64 setting reflect the ones for linux
 # No actial testing was performed: there is no Solaris on ia64 presently
@@ -137,10 +160,20 @@
 OPT_CFLAGS/bytecodeInterpreter.o += -fno-expensive-optimizations
 endif
 
-OPT_CFLAGS/NOOPT=-O0
+# Work around some compiler bugs.
+ifeq ($(USE_CLANG), true)
+  ifeq ($(shell expr $(CC_VER_MAJOR) = 4 \& $(CC_VER_MINOR) = 2), 1)
+    OPT_CFLAGS/loopTransform.o += $(OPT_CFLAGS/NOOPT)
+  endif
+else
+  # 6835796. Problem in GCC 4.3.0 with mulnode.o optimized compilation.
+  ifeq ($(shell expr $(CC_VER_MAJOR) = 4 \& $(CC_VER_MINOR) = 3), 1)
+    OPT_CFLAGS/mulnode.o += $(OPT_CFLAGS/NOOPT)
+  endif
+endif
 
 # Flags for generating make dependency flags.
-ifneq ("${CC_VER_MAJOR}", "2")
+ifneq ($(CC_VER_MAJOR), 2)
 DEPFLAGS = -fpch-deps -MMD -MP -MF $(DEP_DIR)/$(@:%=%.d)
 endif
 
@@ -155,26 +188,37 @@
 # statically link libstdc++.so, work with gcc but ignored by g++
 STATIC_STDCXX = -Wl,-Bstatic -lstdc++ -Wl,-Bdynamic
 
-# statically link libgcc and/or libgcc_s, libgcc does not exist before gcc-3.x.
-ifneq ("${CC_VER_MAJOR}", "2")
-STATIC_LIBGCC += -static-libgcc
-endif
-
-ifeq ($(BUILDARCH), ia64)
-# Note: all ia64 setting reflect the ones for linux
-# No actial testing was performed: there is no Solaris on ia64 presently
-LFLAGS += -Wl,-relax
-endif
 
 ifdef USE_GNULD
-# Enable linker optimization
-LFLAGS += -Xlinker -O1
+  # statically link libgcc and/or libgcc_s, libgcc does not exist before gcc-3.x.
+  ifneq ($(CC_VER_MAJOR), 2)
+    STATIC_LIBGCC += -static-libgcc
+  endif
+
+  # Enable linker optimization
+  LFLAGS += -Xlinker -O1
+
+  ifneq (, findstring(debug,$(BUILD_FLAVOR)))
+    # for relocations read-only
+    LFLAGS += -Xlinker -z -Xlinker relro
 
-# Use $(MAPFLAG:FILENAME=real_file_name) to specify a map file.
-MAPFLAG = -Xlinker --version-script=FILENAME 
-else 
-MAPFLAG = -Xlinker -M -Xlinker FILENAME 
-endif 
+    ifeq ($(BUILD_FLAVOR), debug)
+      # disable incremental relocations linking
+      LFLAGS += -Xlinker -z -Xlinker now
+    endif
+  endif
+
+  ifeq ($(BUILDARCH), ia64)
+    # Note: all ia64 setting reflect the ones for linux
+    # No actual testing was performed: there is no Solaris on ia64 presently
+    LFLAGS += -Wl,-relax
+  endif
+
+  # Use $(MAPFLAG:FILENAME=real_file_name) to specify a map file.
+  MAPFLAG = -Xlinker --version-script=FILENAME
+else
+  MAPFLAG = -Xlinker -M -Xlinker FILENAME
+endif
 
 # Use $(SONAMEFLAG:SONAME=soname) to specify the intrinsic name of a shared obj
 SONAMEFLAG = -Xlinker -soname=SONAME
@@ -185,15 +229,34 @@
 #------------------------------------------------------------------------
 # Debug flags
 
-# Use the stabs format for debugging information (this is the default 
-# on gcc-2.91). It's good enough, has all the information about line 
-# numbers and local variables, and libjvm.so is only about 16M. 
-# Change this back to "-g" if you want the most expressive format. 
-# (warning: that could easily inflate libjvm.so to 150M!) 
-# Note: The Itanium gcc compiler crashes when using -gstabs. 
-DEBUG_CFLAGS/ia64  = -g 
-DEBUG_CFLAGS/amd64 = -g 
-DEBUG_CFLAGS += $(DEBUG_CFLAGS/$(BUILDARCH)) 
-ifeq ($(DEBUG_CFLAGS/$(BUILDARCH)),) 
-DEBUG_CFLAGS += -gstabs 
-endif 
+ifeq "$(shell expr \( $(CC_VER_MAJOR) \> 4 \) \| \( \( $(CC_VER_MAJOR) = 4 \) \& \( $(CC_VER_MINOR) \>= 8 \) \))" "1"
+  # Allow basic optimizations which don't distrupt debugging. (Principally dead code elimination)
+  DEBUG_CFLAGS=-Og
+else
+  # Allow no optimizations.
+  DEBUG_CFLAGS=-O0
+endif
+
+
+# Use the stabs format for debugging information (this is the default
+# on gcc-2.91). It's good enough, has all the information about line
+# numbers and local variables, and libjvm.so is only about 16M.
+# Change this back to "-g" if you want the most expressive format.
+# (warning: that could easily inflate libjvm.so to 150M!)
+# Note: The Itanium gcc compiler crashes when using -gstabs.
+DEBUG_CFLAGS/ia64  = -g
+DEBUG_CFLAGS/amd64 = -g
+DEBUG_CFLAGS += $(DEBUG_CFLAGS/$(BUILDARCH))
+ifeq ($(DEBUG_CFLAGS/$(BUILDARCH)),)
+  DEBUG_CFLAGS += -gstabs
+endif
+
+# Enable bounds checking.
+# _FORTIFY_SOURCE appears in GCC 4.0+
+ifeq "$(shell expr \( $(CC_VER_MAJOR) \> 3 \) )" "1"
+  # compile time size bounds checks
+  FASTDEBUG_CFLAGS += -U_FORTIFY_SOURCE -D_FORTIFY_SOURCE=1
+
+  # and runtime size bounds checks and paranoid stack smashing checks.
+  DEBUG_CFLAGS += -U_FORTIFY_SOURCE -D_FORTIFY_SOURCE=2 -fstack-protector-all --param ssp-buffer-size=1
+endif