libtool-commit
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[SCM] GNU Libtool branch, master, updated. v2.2.6-178-g080e088


From: Peter Rosin
Subject: [SCM] GNU Libtool branch, master, updated. v2.2.6-178-g080e088
Date: Thu, 21 Jan 2010 08:10:36 +0000

This is an automated email from the git hooks/post-receive script. It was
generated because a ref change was pushed to the repository containing
the project "GNU Libtool".

The branch, master has been updated
       via  080e088e42e230d458e18073fef82b6eab01837f (commit)
      from  16362c656aac5daf7337f2ed27aae1fe4838d03a (commit)

Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.

- Log -----------------------------------------------------------------
commit 080e088e42e230d458e18073fef82b6eab01837f
Author: Peter Rosin <address@hidden>
Date:   Thu Jan 21 08:42:12 2010 +0100

    Report proper errors from the loadlibrary loader.
    
    * libltdl/loaders/loadlibrary.c (loadlibraryerror): New
    helper function that returns the latest Windows error as a
    string, or the provided default string on failure to do so.
    (LOADLIB_SETERROR): New macro that wraps previous to make it
    easy to use.
    (vm_open, vm_close, vm_sym): Make use of previous.
    (LOCALFREE): New macro to help free the Windows error string.
    (vl_exit): Make use of previous.
    * tests/loadlibarry.at: New file, new test that makes sure
    the loadlibrary loader reports non-standard error messages.
    * Makefile.am (TESTSUITE_AT): Add above test.
    
    Signed-off-by: Peter Rosin <address@hidden>

-----------------------------------------------------------------------

Summary of changes:
 ChangeLog                     |   15 +++
 Makefile.am                   |    1 +
 libltdl/loaders/loadlibrary.c |   45 +++++++-
 tests/loadlibrary.at          |  251 +++++++++++++++++++++++++++++++++++++++++
 4 files changed, 308 insertions(+), 4 deletions(-)
 create mode 100644 tests/loadlibrary.at

diff --git a/ChangeLog b/ChangeLog
index 5f2518c..9dce6a8 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,18 @@
+2010-01-20  Peter Rosin  <address@hidden>
+
+       Report proper errors from the loadlibrary loader.
+       * libltdl/loaders/loadlibrary.c (loadlibraryerror): New
+       helper function that returns the latest Windows error as a
+       string, or the provided default string on failure to do so.
+       (LOADLIB_SETERROR): New macro that wraps previous to make it
+       easy to use.
+       (vm_open, vm_close, vm_sym): Make use of previous.
+       (LOCALFREE): New macro to help free the Windows error string.
+       (vl_exit): Make use of previous.
+       * tests/loadlibarry.at: New file, new test that makes sure
+       the loadlibrary loader reports non-standard error messages.
+       * Makefile.am (TESTSUITE_AT): Add above test.
+
 2010-01-02  Peter Rosin  <address@hidden>
 
        Use GetErrorMode if it is available.
diff --git a/Makefile.am b/Makefile.am
index 8d6682b..40a0138 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -485,6 +485,7 @@ TESTSUITE_AT        = tests/testsuite.at \
                  tests/lt_dlopen_a.at \
                  tests/lt_dlopenext.at \
                  tests/ltdl-api.at \
+                 tests/loadlibrary.at \
                  tests/lalib-syntax.at \
                  tests/resident.at \
                  tests/slist.at \
diff --git a/libltdl/loaders/loadlibrary.c b/libltdl/loaders/loadlibrary.c
index 40435fe..139851a 100644
--- a/libltdl/loaders/loadlibrary.c
+++ b/libltdl/loaders/loadlibrary.c
@@ -98,12 +98,19 @@ get_vtable (lt_user_data loader_data)
 
 #include <windows.h>
 
+#define LOCALFREE(mem)                                      LT_STMT_START { \
+       if (mem) { LocalFree ((void *)mem); mem = NULL; }    } LT_STMT_END
+#define LOADLIB__SETERROR(errmsg) LT__SETERRORSTR (loadlibraryerror (errmsg))
+#define LOADLIB_SETERROR(errcode) LOADLIB__SETERROR (LT__STRERROR (errcode))
+
+static const char *loadlibraryerror (const char *default_errmsg);
 static UINT WINAPI wrap_geterrormode (void);
 static UINT WINAPI fallback_geterrormode (void);
 
 typedef UINT (WINAPI geterrormode_type) (void);
 
 static geterrormode_type *geterrormode = wrap_geterrormode;
+static char *error_message = 0;
 
 
 /* A function called through the vtable when this loader is no
@@ -112,6 +119,7 @@ static int
 vl_exit (lt_user_data LT__UNUSED loader_data)
 {
   vtable = NULL;
+  LOCALFREE (error_message);
   return 0;
 }
 
@@ -213,7 +221,9 @@ vm_open (lt_user_data LT__UNUSED loader_data, const char 
*filename,
           }
       }
 
-    if (cur || !module)
+    if (!module)
+      LOADLIB_SETERROR (CANNOT_OPEN);
+    else if (cur)
       {
         LT__SETERROR (CANNOT_OPEN);
         module = 0;
@@ -231,9 +241,9 @@ vm_close (lt_user_data LT__UNUSED loader_data, lt_module 
module)
 {
   int errors = 0;
 
-  if (FreeLibrary((HMODULE) module) == 0)
+  if (FreeLibrary ((HMODULE) module) == 0)
     {
-      LT__SETERROR (CANNOT_CLOSE);
+      LOADLIB_SETERROR (CANNOT_CLOSE);
       ++errors;
     }
 
@@ -250,7 +260,7 @@ vm_sym (lt_user_data LT__UNUSED loader_data, lt_module 
module, const char *name)
 
   if (!address)
     {
-      LT__SETERROR (SYMBOL_NOT_FOUND);
+      LOADLIB_SETERROR (SYMBOL_NOT_FOUND);
     }
 
   return address;
@@ -261,6 +271,33 @@ vm_sym (lt_user_data LT__UNUSED loader_data, lt_module 
module, const char *name)
 /* --- HELPER FUNCTIONS --- */
 
 
+/* Return the windows error message, or the passed in error message on
+   failure. */
+static const char *
+loadlibraryerror (const char *default_errmsg)
+{
+  size_t len;
+  LOCALFREE (error_message);
+
+  FormatMessageA (FORMAT_MESSAGE_ALLOCATE_BUFFER |
+                  FORMAT_MESSAGE_FROM_SYSTEM |
+                  FORMAT_MESSAGE_IGNORE_INSERTS,
+                  NULL,
+                  GetLastError (),
+                  0,
+                  (char *) &error_message,
+                  0, NULL);
+
+  /* Remove trailing CRNL */
+  len = LT_STRLEN (error_message);
+  if (len && error_message[len - 1] == '\n')
+    error_message[--len] = LT_EOS_CHAR;
+  if (len && error_message[len - 1] == '\r')
+    error_message[--len] = LT_EOS_CHAR;
+
+  return len ? error_message : default_errmsg;
+}
+
 /* A function called through the geterrormode variable which checks
    if the system supports GetErrorMode and arranges for it or a
    fallback implementation to be called directly in the future. The
diff --git a/tests/loadlibrary.at b/tests/loadlibrary.at
new file mode 100644
index 0000000..8315a5d
--- /dev/null
+++ b/tests/loadlibrary.at
@@ -0,0 +1,251 @@
+# loadlibrary.at -- test loadlibrary functionality          -*- Autotest -*-
+#
+#   Copyright (C) 2010 Free Software Foundation, Inc.
+#   This file is part of GNU Libtool.
+#
+# GNU Libtool is free software; you can redistribute it and/or
+# modify it under the terms of the GNU General Public License as
+# published by the Free Software Foundation; either version 2 of
+# the License, or (at your option) any later version.
+#
+# GNU Libtool 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 for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with GNU Libtool; see the file COPYING.  If not, a copy
+# can be downloaded from  http://www.gnu.org/licenses/gpl.html,
+# or obtained by writing to the Free Software Foundation, Inc.,
+# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+####
+
+AT_SETUP([loadlibrary error messages])
+AT_KEYWORDS([libltdl])
+
+eval "`$LIBTOOL --config | $EGREP '^(objdir)='`"
+
+AT_DATA([main.c],
+[[#include <ltdl.h>
+#include <stdio.h>
+
+static int
+standard_error_message(const char *error)
+{
+  int error_number;
+
+  for (error_number = 0; error_number < LT_ERROR_MAX; ++error_number)
+    {
+      lt_dlseterror (error_number);
+      if (error == lt_dlerror ())
+       {
+         return 1;
+       }
+    }
+
+  lt_dlseterror (LT_ERROR_UNKNOWN);
+  return 0;
+}
+
+int
+main (int argc, char* argv[])
+{
+  int err = 0;
+  lt_dlhandle module = NULL;
+  const lt_dlvtable *loadlibrary;
+  const lt_dlvtable *preopen;
+  lt_dlloader *loader = NULL;
+  lt_dlloader *next;
+  const lt_dlvtable *vtable;
+  void *symbol;
+  const char *error;
+
+  if (argc < 2)
+    {
+      fprintf (stderr, "usage: %s plugin [symbol]\n", argv[0]);
+      return 1;
+    }
+
+  lt_dlinit ();
+
+  loadlibrary = lt_dlloader_find ("lt_loadlibrary");
+  if (!loadlibrary)
+    {
+      /* Skip if the loadlibrary loader isn't supported */
+      printf ("loadlibrary loader not found\n");
+      err = 77;
+      goto cleanup;
+    }
+
+  preopen = lt_dlloader_find ("lt_preopen");
+  if (!loadlibrary)
+    {
+      printf ("preopen loader not found\n");
+      err = 2;
+      goto cleanup;
+    }
+
+  /* Remove all loaders except the preopen and loadlibrary loaders. */
+  while (next = lt_dlloader_next (loader))
+    {
+      if (lt_dlloader_get (next) == loadlibrary)
+       {
+         loader = next;
+         continue;
+       }
+
+      if (lt_dlloader_get (next) == preopen)
+       {
+         loader = next;
+         continue;
+       }
+
+      lt_dlloader_remove (lt_dlloader_get (next)->name);
+    }
+
+  module = lt_dlopen (argv[1]);
+  error = lt_dlerror ();
+
+  if (module)
+    {
+      printf ("lt_dlopen: success!\n");
+
+      if (argc == 2)
+       {
+         /* But failure was the desired result... */
+         printf ("expected failure\n");
+         err = 2;
+         goto cleanup;
+       }
+    }
+  else if (argc > 2)
+    {
+      /* Didn't expect failure... */
+      printf ("lt_dlopen: failure: %s\n", error);
+      err = 2;
+      goto cleanup;
+    }
+  else if (standard_error_message (error))
+    {
+      /* Expected custom error message... */
+      printf ("lt_dlopen: standard error (bad): %s\n", error);
+      err = 1;
+      goto cleanup;
+    }
+  else
+    {
+      printf ("lt_dlopen: custom error (good): %s\n", error);
+      goto cleanup;
+    }
+
+  symbol = lt_dlsym (module, argv[2]);
+  error = lt_dlerror ();
+
+  if (symbol)
+    {
+      printf ("lt_dlsym: success!\n");
+    }
+  else if (standard_error_message (error))
+    {
+      /* Expected custom failure message... */
+      printf ("lt_dlsym: standard error (bad): %s\n", error);
+      err = 1;
+    }
+  else
+    {
+      printf ("lt_dlsym: custom error (good): %s\n", error);
+    }
+
+cleanup:
+  if (module)
+    {
+      lt_dlclose (module);
+    }
+  lt_dlexit ();
+  return err;
+}
+]])
+
+AT_DATA([foomod.c],
+[[
+int foosym (void);
+int
+foosym (void)
+{
+  return 0;
+}
+]])
+
+AT_DATA([bardep.c],
+[[
+int bardep (void);
+int
+bardep (void)
+{
+  return 0;
+}
+]])
+
+AT_DATA([barmod.c],
+[[
+int bardep (void);
+int barsym (void);
+int
+barsym (void)
+{
+  return bardep ();
+}
+]])
+
+: ${LTDLINCL="-I$abs_top_srcdir/libltdl"}
+: ${LIBLTDL="$abs_builddir/../libltdl/libltdlc.la"}
+
+CPPFLAGS="$LTDLINCL $CPPFLAGS"
+inst=`pwd`/inst
+libdir=$inst/lib
+
+AT_CHECK([$CC $CPPFLAGS $CFLAGS -c main.c], [], [ignore], [ignore])
+for file in foomod.c bardep.c barmod.c; do
+  AT_CHECK([$LIBTOOL --mode=compile $CC $CPPFLAGS $CFLAGS -c $file],
+          [], [ignore], [ignore])
+done
+AT_CHECK([$LIBTOOL --mode=link $CC $CFLAGS $LDFLAGS -o foomod.la ]dnl
+        [-rpath $libdir -module -avoid-version -no-undefined ]dnl
+        [foomod.lo],
+        [], [ignore], [ignore])
+AT_CHECK([$LIBTOOL --mode=link $CC $CFLAGS $LDFLAGS -o libbardep.la ]dnl
+        [-rpath $libdir -avoid-version -no-undefined ]dnl
+        [bardep.lo],
+        [], [ignore], [ignore])
+AT_CHECK([$LIBTOOL --mode=link $CC $CFLAGS $LDFLAGS -o barmod.la ]dnl
+        [-rpath $libdir -module -avoid-version -no-undefined ]dnl
+        [barmod.lo ./libbardep.la],
+        [], [ignore], [ignore])
+
+AT_CHECK([$LIBTOOL --mode=link $CC $CFLAGS $LDFLAGS -o main$EXEEXT ]dnl
+        [main.$OBJEXT $LIBLTDL],
+        [], [ignore], [ignore])
+
+. ./foomod.la
+AT_CHECK([test -n "$dlname" || (exit 77)])
+
+LT_AT_EXEC_CHECK([./main], [], [ignore], [ignore], [./foomod.la no_symbol])
+
+#   chmod -x doesn't appear to work in MSYS, and Wine can load no-exec dlls.
+dnl chmod -x $objdir/$dlname
+dnl LT_AT_EXEC_CHECK([./main], [], [ignore], [ignore], [./foomod.la])
+
+rm -f $objdir/$dlname
+LT_AT_EXEC_CHECK([./main], [], [ignore], [ignore], [./foomod.la])
+
+LT_AT_EXEC_CHECK([./main], [], [ignore], [ignore], [./barmod.la no_symbol])
+
+. ./libbardep.la
+#   chmod -x doesn't appear to work in MSYS, and Wine can load no-exec dlls.
+dnl chmod -x $objdir/$dlname
+dnl LT_AT_EXEC_CHECK([./main], [], [ignore], [ignore], [./barmod.la])
+
+rm -f $objdir/$dlname
+LT_AT_EXEC_CHECK([./main], [], [ignore], [ignore], [./barmod.la])
+
+AT_CLEANUP


hooks/post-receive
-- 
GNU Libtool




reply via email to

[Prev in Thread] Current Thread [Next in Thread]