Attempt to improve mingw-w64 support
author <shinichiro.hamaji@gmail.com> <>
Mon, 18 Feb 2013 10:56:53 +0000 (10:56 +0000)
committer <shinichiro.hamaji@gmail.com> <>
Mon, 18 Feb 2013 10:56:53 +0000 (10:56 +0000)
- Set -Isrc/windows for mingw
- Check existence of sigaction, pread, and pwrite
- Provide alternative implementation of pread and pwrite
- Eliminate symlink code for OS_WINDOWS
- Don't check /proc/self/fd if the OS isn't linux
- Don't use MSVC specific declarations in port.h for mingw

git-svn-id: https://google-glog.googlecode.com/svn/trunk@135 eb4d4688-79bd-11dd-afb4-1d65580434c0

Makefile.am
Makefile.in
configure
configure.ac
src/config.h.in
src/googletest.h
src/logging.cc
src/signalhandler.cc
src/utilities.cc
src/windows/config.h
src/windows/port.h

index cff3352..b598fa3 100644 (file)
@@ -51,7 +51,8 @@ lib_LTLIBRARIES =
 # The libraries libglog depends on.
 COMMON_LIBS = $(PTHREAD_LIBS) $(GFLAGS_LIBS) $(UNWIND_LIBS)
 # Compile switches for our unittest.
-TEST_CFLAGS = $(GTEST_CFLAGS) $(GMOCK_CFLAGS) $(GFLAGS_CFLAGS) $(AM_CXXFLAGS)
+TEST_CFLAGS = $(GTEST_CFLAGS) $(GMOCK_CFLAGS) $(GFLAGS_CFLAGS) \
+              $(MINGW_CFLAGS) $(AM_CXXFLAGS)
 # Libraries for our unittest.
 TEST_LIBS = $(GTEST_LIBS) $(GMOCK_LIBS) $(GFLAGS_LIBS)
 
@@ -195,7 +196,8 @@ libglog_la_SOURCES = $(gloginclude_HEADERS) \
                        src/base/commandlineflags.h src/googletest.h
 nodist_libglog_la_SOURCES = $(nodist_gloginclude_HEADERS)
 
-libglog_la_CXXFLAGS = $(PTRHEAD_CFLAGS) $(GFLAGS_CFLAGS) $(AM_CXXFLAGS) -DNDEBUG
+libglog_la_CXXFLAGS = $(PTRHEAD_CFLAGS) $(GFLAGS_CFLAGS) $(MINGW_CFLAGS) \
+                      $(AM_CXXFLAGS) -DNDEBUG
 libglog_la_LDFLAGS = $(PTRHEAD_CFLAGS) $(GFLAGS_LDFLAGS)
 libglog_la_LIBADD = $(COMMON_LIBS)
 
index 17856a8..a4ee668 100644 (file)
@@ -382,6 +382,7 @@ LN_S = @LN_S@
 LTLIBOBJS = @LTLIBOBJS@
 MAKEINFO = @MAKEINFO@
 MANIFEST_TOOL = @MANIFEST_TOOL@
+MINGW_CFLAGS = @MINGW_CFLAGS@
 MKDIR_P = @MKDIR_P@
 NM = @NM@
 NMEDIT = @NMEDIT@
@@ -499,7 +500,9 @@ lib_LTLIBRARIES = libglog.la
 # The libraries libglog depends on.
 COMMON_LIBS = $(PTHREAD_LIBS) $(GFLAGS_LIBS) $(UNWIND_LIBS)
 # Compile switches for our unittest.
-TEST_CFLAGS = $(GTEST_CFLAGS) $(GMOCK_CFLAGS) $(GFLAGS_CFLAGS) $(AM_CXXFLAGS)
+TEST_CFLAGS = $(GTEST_CFLAGS) $(GMOCK_CFLAGS) $(GFLAGS_CFLAGS) \
+              $(MINGW_CFLAGS) $(AM_CXXFLAGS)
+
 # Libraries for our unittest.
 TEST_LIBS = $(GTEST_LIBS) $(GMOCK_LIBS) $(GFLAGS_LIBS)
 TESTS_ENVIRONMENT = 
@@ -606,7 +609,9 @@ libglog_la_SOURCES = $(gloginclude_HEADERS) \
                        src/base/commandlineflags.h src/googletest.h
 
 nodist_libglog_la_SOURCES = $(nodist_gloginclude_HEADERS)
-libglog_la_CXXFLAGS = $(PTRHEAD_CFLAGS) $(GFLAGS_CFLAGS) $(AM_CXXFLAGS) -DNDEBUG
+libglog_la_CXXFLAGS = $(PTRHEAD_CFLAGS) $(GFLAGS_CFLAGS) $(MINGW_CFLAGS) \
+                      $(AM_CXXFLAGS) -DNDEBUG
+
 libglog_la_LDFLAGS = $(PTRHEAD_CFLAGS) $(GFLAGS_LDFLAGS)
 libglog_la_LIBADD = $(COMMON_LIBS)
 WINDOWS_PROJECTS = google-glog.sln vsprojects/libglog/libglog.vcproj \
index 6a77d35..6b74fce 100755 (executable)
--- a/configure
+++ b/configure
@@ -619,6 +619,7 @@ LIBOBJS
 GMOCK_LIBS
 GTEST_LIBS
 GFLAGS_LIBS
+MINGW_CFLAGS
 GMOCK_CFLAGS
 GTEST_CFLAGS
 GFLAGS_CFLAGS
 done
 
 
+ac_fn_cxx_check_header_mongrel "$LINENO" "windows.h" "ac_cv_header_windows_h" "$ac_includes_default"
+if test "x$ac_cv_header_windows_h" = xyes; then :
+  ac_cv_have_windows_h=1
+else
+  ac_cv_have_windows_h=0
+fi
+
+
+if test x"$ac_cv_have_windows_h" = x"1"; then
+  MINGW_CFLAGS=-Isrc/windows
+fi
+
 # The cast to long int works around a bug in the HP C Compiler
 # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects
 # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'.
@@ -15771,6 +15784,13 @@ $as_echo "#define HAVE_SIGALTSTACK 1" >>confdefs.h
 
 fi
 
+ac_fn_cxx_check_func "$LINENO" "sigaction" "ac_cv_func_sigaction"
+if test "x$ac_cv_func_sigaction" = xyes; then :
+
+$as_echo "#define HAVE_SIGACTION 1" >>confdefs.h
+
+fi
+
 ac_fn_cxx_check_func "$LINENO" "dladdr" "ac_cv_func_dladdr"
 if test "x$ac_cv_func_dladdr" = xyes; then :
 
@@ -15785,6 +15805,20 @@ $as_echo "#define HAVE_FCNTL 1" >>confdefs.h
 
 fi
 
+ac_fn_cxx_check_func "$LINENO" "pread" "ac_cv_func_pread"
+if test "x$ac_cv_func_pread" = xyes; then :
+
+$as_echo "#define HAVE_PREAD 1" >>confdefs.h
+
+fi
+
+ac_fn_cxx_check_func "$LINENO" "pwrite" "ac_cv_func_pwrite"
+if test "x$ac_cv_func_pwrite" = xyes; then :
+
+$as_echo "#define HAVE_PWRITE 1" >>confdefs.h
+
+fi
+
 
 
   { $as_echo "$as_me:${as_lineno-$LINENO}: checking for __attribute__" >&5
@@ -16650,7 +16684,41 @@ $as_echo "no" >&6; }
 fi
 
 
-if test x"$GTEST_CONFIG" = "xyes"; then
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for main in -lgtest" >&5
+$as_echo_n "checking for main in -lgtest... " >&6; }
+if ${ac_cv_lib_gtest_main+:} false; then :
+  $as_echo_n "(cached) " >&6
+else
+  ac_check_lib_save_LIBS=$LIBS
+LIBS="-lgtest  $LIBS"
+cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+
+
+int
+main ()
+{
+return main ();
+  ;
+  return 0;
+}
+_ACEOF
+if ac_fn_cxx_try_link "$LINENO"; then :
+  ac_cv_lib_gtest_main=yes
+else
+  ac_cv_lib_gtest_main=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+    conftest$ac_exeext conftest.$ac_ext
+LIBS=$ac_check_lib_save_LIBS
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_gtest_main" >&5
+$as_echo "$ac_cv_lib_gtest_main" >&6; }
+if test "x$ac_cv_lib_gtest_main" = xyes; then :
+  have_gtest_lib="yes"
+fi
+
+if test x"$GTEST_CONFIG" = "xyes" -a x"$have_gtest_lib" = "xyes"; then
   GTEST_CFLAGS=`gtest-config --cppflags --cxxflags`
   GTEST_LIBS=`gtest-config --ldflags --libs`
 
@@ -17180,6 +17248,7 @@ _ACEOF
 
 
 
+
 # Write generated configuration file
 ac_config_files="$ac_config_files Makefile src/glog/logging.h src/glog/raw_logging.h src/glog/vlog_is_on.h src/glog/stl_logging.h"
 
index 8b458fa..a07c562 100644 (file)
@@ -47,6 +47,11 @@ AC_CHECK_HEADERS(glob.h)
 # For backtrace with gcc.
 AC_CHECK_HEADERS(unwind.h)
 
+AC_CHECK_HEADER(windows.h, ac_cv_have_windows_h=1, ac_cv_have_windows_h=0)
+if test x"$ac_cv_have_windows_h" = x"1"; then
+  MINGW_CFLAGS=-Isrc/windows
+fi
+
 AC_CHECK_SIZEOF(void *)
 
 # These are the types I need.  We look for them in either stdint.h,
@@ -58,12 +63,21 @@ AC_CHECK_TYPE(__uint16, ac_cv_have___uint16=1, ac_cv_have___uint16=0)
 AC_CHECK_FUNC(sigaltstack,
               AC_DEFINE(HAVE_SIGALTSTACK, 1,
                         [Define if you have the `sigaltstack' function]))
+AC_CHECK_FUNC(sigaction,
+              AC_DEFINE(HAVE_SIGACTION, 1,
+                        [Define if you have the 'sigaction' function]))
 AC_CHECK_FUNC(dladdr,
               AC_DEFINE(HAVE_DLADDR, 1,
                         [Define if you have the `dladdr' function]))
 AC_CHECK_FUNC(fcntl,
               AC_DEFINE(HAVE_FCNTL, 1,
                         [Define if you have the `fcntl' function]))
+AC_CHECK_FUNC(pread,
+              AC_DEFINE(HAVE_PREAD, 1,
+                        [Define if you have the 'pread' function]))
+AC_CHECK_FUNC(pwrite,
+              AC_DEFINE(HAVE_PWRITE, 1,
+                        [Define if you have the 'pwrite' function]))
 
 AX_C___ATTRIBUTE__
 # We only care about these two attributes.
@@ -139,7 +153,8 @@ LIBS="$SAVE_LIBS"
 #               once the m4 macro of Google Mocking becomes ready.
 # Check if there is Google Test library installed.
 AC_CHECK_PROG(GTEST_CONFIG, gtest-config, "yes")
-if test x"$GTEST_CONFIG" = "xyes"; then
+AC_CHECK_LIB(gtest, main, have_gtest_lib="yes")
+if test x"$GTEST_CONFIG" = "xyes" -a x"$have_gtest_lib" = "xyes"; then
   GTEST_CFLAGS=`gtest-config --cppflags --cxxflags`
   GTEST_LIBS=`gtest-config --ldflags --libs`
   AC_DEFINE(HAVE_LIB_GTEST, 1, [define if you have google gtest library])
@@ -211,6 +226,7 @@ AC_SUBST(ac_cv_have_libgflags)
 AC_SUBST(GFLAGS_CFLAGS)
 AC_SUBST(GTEST_CFLAGS)
 AC_SUBST(GMOCK_CFLAGS)
+AC_SUBST(MINGW_CFLAGS)
 AC_SUBST(GFLAGS_LIBS)
 AC_SUBST(GTEST_LIBS)
 AC_SUBST(GMOCK_LIBS)
index 0c5e8b0..8190f23 100644 (file)
 /* define if the compiler implements namespaces */
 #undef HAVE_NAMESPACES
 
+/* Define if you have the 'pread' function */
+#undef HAVE_PREAD
+
 /* Define if you have POSIX threads libraries and header files. */
 #undef HAVE_PTHREAD
 
 /* Define to 1 if you have the <pwd.h> header file. */
 #undef HAVE_PWD_H
 
+/* Define if you have the 'pwrite' function */
+#undef HAVE_PWRITE
+
 /* define if the compiler implements pthread_rwlock_* */
 #undef HAVE_RWLOCK
 
+/* Define if you have the 'sigaction' function */
+#undef HAVE_SIGACTION
+
 /* Define if you have the `sigaltstack' function */
 #undef HAVE_SIGALTSTACK
 
index b3e26c4..21e4f64 100644 (file)
@@ -81,7 +81,7 @@ static inline string GetTempDir() {
 #endif
 }
 
-#ifdef OS_WINDOWS
+#if defined(OS_WINDOWS) && defined(_MSC_VER)
 // The test will run in glog/vsproject/<project name>
 // (e.g., glog/vsproject/logging_unittest).
 static const char TEST_SRC_DIR[] = "../..";
index ec334a9..12330b0 100644 (file)
@@ -179,6 +179,38 @@ GLOG_DEFINE_string(log_backtrace_at, "",
 // TODO(hamaji): consider windows
 #define PATH_SEPARATOR '/'
 
+#ifndef HAVE_PREAD
+static ssize_t pread(int fd, void* buf, size_t count, off_t offset) {
+  off_t orig_offset = lseek(fd, 0, SEEK_CUR);
+  if (orig_offset == (off_t)-1)
+    return -1;
+  if (lseek(fd, offset, SEEK_CUR) == (off_t)-1)
+    return -1;
+  ssize_t len = read(fd, buf, count);
+  if (len < 0)
+    return len;
+  if (lseek(fd, orig_offset, SEEK_SET) == (off_t)-1)
+    return -1;
+  return len;
+}
+#endif  // !HAVE_PREAD
+
+#ifndef HAVE_PWRITE
+static ssize_t pwrite(int fd, void* buf, size_t count, off_t offset) {
+  off_t orig_offset = lseek(fd, 0, SEEK_CUR);
+  if (orig_offset == (off_t)-1)
+    return -1;
+  if (lseek(fd, offset, SEEK_CUR) == (off_t)-1)
+    return -1;
+  ssize_t len = write(fd, buf, count);
+  if (len < 0)
+    return len;
+  if (lseek(fd, orig_offset, SEEK_SET) == (off_t)-1)
+    return -1;
+  return len;
+}
+#endif  // !HAVE_PWRITE
+
 static void GetHostName(string* hostname) {
 #if defined(HAVE_SYS_UTSNAME_H)
   struct utsname buf;
@@ -887,8 +919,10 @@ bool LogFileObject::CreateLogfile(const string& time_pid_string) {
     linkpath += linkname;
     unlink(linkpath.c_str());                    // delete old one if it exists
 
+#if defined(OS_WINDOWS)
+    // TODO(hamaji): Create lnk file on Windows?
+#elif defined(HAVE_UNISTD_H)
     // We must have unistd.h.
-#ifdef HAVE_UNISTD_H
     // Make the symlink be relative (in the same dir) so that if the
     // entire log directory gets relocated the link is still valid.
     const char *linkdest = slash ? (slash + 1) : filename;
@@ -1824,8 +1858,11 @@ void TruncateLogFile(const char *path, int64 limit, int64 keep) {
   int64 read_offset, write_offset;
   // Don't follow symlinks unless they're our own fd symlinks in /proc
   int flags = O_RDWR;
+  // TODO(hamaji): Support other environments.
+#ifdef OS_LINUX
   const char *procfd_prefix = "/proc/self/fd/";
   if (strncmp(procfd_prefix, path, strlen(procfd_prefix))) flags |= O_NOFOLLOW;
+#endif
 
   int fd = open(path, flags);
   if (fd == -1) {
index d6c203b..cccd800 100644 (file)
@@ -48,6 +48,9 @@
 
 _START_GOOGLE_NAMESPACE_
 
+// TOOD(hamaji): Use signal instead of sigaction?
+#ifdef HAVE_SIGACTION
+
 namespace {
 
 // We'll install the failure signal handler for these signals.  We could
@@ -330,7 +333,10 @@ void FailureSignalHandler(int signal_number,
 
 }  // namespace
 
+#endif  // HAVE_SIGACTION
+
 void InstallFailureSignalHandler() {
+#ifdef HAVE_SIGACTION
   // Build the sigaction struct.
   struct sigaction sig_action;
   memset(&sig_action, 0, sizeof(sig_action));
@@ -341,10 +347,13 @@ void InstallFailureSignalHandler() {
   for (size_t i = 0; i < ARRAYSIZE(kFailureSignals); ++i) {
     CHECK_ERR(sigaction(kFailureSignals[i].number, &sig_action, NULL));
   }
+#endif  // HAVE_SIGACTION
 }
 
 void InstallFailureWriter(void (*writer)(const char* data, int size)) {
+#ifdef HAVE_SIGACTION
   g_failure_writer = writer;
+#endif  // HAVE_SIGACTION
 }
 
 _END_GOOGLE_NAMESPACE_
index a6d1961..f31c7c7 100644 (file)
@@ -136,6 +136,8 @@ static void DumpStackTrace(int skip_count, DebugWriter *writerfn, void *arg) {
 static void DumpStackTraceAndExit() {
   DumpStackTrace(1, DebugWriteToStderr, NULL);
 
+  // TOOD(hamaji): Use signal instead of sigaction?
+#ifdef HAVE_SIGACTION
   // Set the default signal handler for SIGABRT, to avoid invoking our
   // own signal handler installed by InstallFailedSignalHandler().
   struct sigaction sig_action;
@@ -143,6 +145,7 @@ static void DumpStackTraceAndExit() {
   sigemptyset(&sig_action.sa_mask);
   sig_action.sa_handler = SIG_DFL;
   sigaction(SIGABRT, &sig_action, NULL);
+#endif  // HAVE_SIGACTION
 
   abort();
 }
index 114762e..2d23fb0 100755 (executable)
@@ -3,121 +3,6 @@
 /* Namespace for Google classes */
 #define GOOGLE_NAMESPACE google
 
-/* Define if you have the `dladdr' function */
-#undef HAVE_DLADDR
-
-/* Define to 1 if you have the <dlfcn.h> header file. */
-#undef HAVE_DLFCN_H
-
-/* Define to 1 if you have the <execinfo.h> header file. */
-#undef HAVE_EXECINFO_H
-
-/* Define to 1 if you have the <inttypes.h> header file. */
-#undef HAVE_INTTYPES_H
-
-/* Define to 1 if you have the <libunwind.h> header file. */
-#undef HAVE_LIBUNWIND_H
-
-/* define if you have google gflags library */
-#undef HAVE_LIB_GFLAGS
-
-/* define if you have libunwind */
-#undef HAVE_LIB_UNWIND
-
-/* Define to 1 if you have the <memory.h> header file. */
-#undef HAVE_MEMORY_H
-
-/* define if the compiler implements namespaces */
-#undef HAVE_NAMESPACES
-
-/* Define if you have POSIX threads libraries and header files. */
-#undef HAVE_PTHREAD
-
-/* define if the compiler implements pthread_rwlock_* */
-#undef HAVE_RWLOCK
-
-/* Define if you have the `sigaltstack' function */
-#undef HAVE_SIGALTSTACK
-
-/* Define to 1 if you have the <stdint.h> header file. */
-#undef HAVE_STDINT_H
-
-/* Define to 1 if you have the <stdlib.h> header file. */
-#undef HAVE_STDLIB_H
-
-/* Define to 1 if you have the <strings.h> header file. */
-#undef HAVE_STRINGS_H
-
-/* Define to 1 if you have the <string.h> header file. */
-#undef HAVE_STRING_H
-
-/* Define to 1 if you have the <syscall.h> header file. */
-#undef HAVE_SYSCALL_H
-
-/* Define to 1 if you have the <sys/stat.h> header file. */
-#undef HAVE_SYS_STAT_H
-
-/* Define to 1 if you have the <sys/syscall.h> header file. */
-#undef HAVE_SYS_SYSCALL_H
-
-/* Define to 1 if you have the <sys/types.h> header file. */
-#undef HAVE_SYS_TYPES_H
-
-/* Define to 1 if you have the <ucontext.h> header file. */
-#undef HAVE_UCONTEXT_H
-
-/* Define to 1 if you have the <unistd.h> header file. */
-#undef HAVE_UNISTD_H
-
-/* define if the compiler supports using expression for operator */
-#undef HAVE_USING_OPERATOR
-
-/* define if your compiler has __attribute__ */
-#undef HAVE___ATTRIBUTE__
-
-/* define if your compiler has __builtin_expect */
-#undef HAVE___BUILTIN_EXPECT
-
-/* define if your compiler has __sync_val_compare_and_swap */
-#undef HAVE___SYNC_VAL_COMPARE_AND_SWAP
-
-/* Name of package */
-#undef PACKAGE
-
-/* Define to the address where bug reports for this package should be sent. */
-#undef PACKAGE_BUGREPORT
-
-/* Define to the full name of this package. */
-#undef PACKAGE_NAME
-
-/* Define to the full name and version of this package. */
-#undef PACKAGE_STRING
-
-/* Define to the one symbol short name of this package. */
-#undef PACKAGE_TARNAME
-
-/* Define to the version of this package. */
-#undef PACKAGE_VERSION
-
-/* How to access the PC from a struct ucontext */
-#undef PC_FROM_UCONTEXT
-
-/* Define to necessary symbol if this constant uses a non-standard name on
-   your system. */
-#undef PTHREAD_CREATE_JOINABLE
-
-/* The size of `void *', as computed by sizeof. */
-#undef SIZEOF_VOID_P
-
-/* Define to 1 if you have the ANSI C header files. */
-#undef STDC_HEADERS
-
-/* the namespace where STL code like vector<> is defined */
-#undef STL_NAMESPACE
-
-/* Version number of package */
-#undef VERSION
-
 /* Stops putting the code inside the Google namespace */
 #define _END_GOOGLE_NAMESPACE_ }
 
index c9be748..24d7677 100755 (executable)
@@ -62,6 +62,8 @@
  * used by both C and C++ code, so we put all the C++ together.
  */
 
+#ifdef _MSC_VER
+
 /* 4244: otherwise we get problems when substracting two size_t's to an int
  * 4251: it's complaining about a private struct I've chosen not to dllexport
  * 4355: we use this in a constructor, but we do it safely
@@ -127,6 +129,8 @@ extern int safe_vsnprintf(char *str, size_t size,
 typedef int pid_t;
 #define getpid  _getpid
 
+#endif  // _MSC_VER
+
 // ----------------------------------- THREADS
 typedef DWORD pthread_t;
 typedef DWORD pthread_key_t;