Re: [sigc] test tarball: libsigc++ 2.0.6 (test1)



Hi!

To speed up things I had a go at the 'operator new/delete ()' solution myself. Please try again with the attached patch applied against the test tarball or current cvs!

Thanks,

 Martin


Am 09.10.2004 01:06:09 schrieb(en) Martin Schulze:
Am 08.10.2004 23:58:31 schrieb(en) Timothy M. Shead:
> Martin Schulze wrote:
>
> >> Do I understand correctly that allocating an object via new from
> >> within
> >> a DLL, then destroying it via delete within a different module
> (EXE
>  or
> >>
> >> DLL) is the problem?
> >
> >
> > This is what I have been told. James Lin (jameslin vmware com)
> brought
> > up the problem.
> >
> >> One item looks suspicious to me, I see that in sigc++/functors/
> slot.h,
> >>
> >> the template struct typed_slot_rep<> has a static member function
> >> "dup()" that is making a call to new, could this be a problem,
> since
> >> it's inline code?
> >
> >
> > Hm, note that 'typed_slot_rep<>::dup()' is only called from
> > 'slot_rep::dup()' (inline) via an indirect function call.
> > 'slot_rep::dup()' is in turn only invoked from non-inline code in
> > slot_base.cc.
> > On second thought, this probably means that the code containing
the
>
> > 'new' is in the EXE module (where the template instantiations lie)
> but
> > invoked from the DLL module!?
> > The corresponding 'delete' is in the DLL module
> (slot_base::~slot_base).
> >
> > Does this cause the problems? Then the solution would be to move
> the
>
> > 'delete' in the EXE module. Please apply the attached patch
> (against
>
> > the test tarball or cvs) and try again.
>
> Applied the patch, it doesn't seem to change the symptoms.

Strange - logic fails! Well, on the other hand this is MS ...

> For everyone's reference, here is a discussion of this issue:
>
> http://support.microsoft.com/default.aspx?scid=kb;en-us;122675
>
> They offer four workarounds, it looks to me like their second
> suggestion
> could be relatively elegant compared to
> SIGC_NEW_DELETE_IN_LIBRARY_ONLY
> - override operator new and operator delete for the problem classes,
> and
> call functions in the DLL to allocate/deallocate memory in their
> implementations.  I will poke at this and see what I come up with.

Go ahead.

> As an aside, I have verified that all tests pass if sigc++ is built

> as
> a
> static library.  If a DLL continues to be problematic, would you
> consider adopting a static build so gtkmm-2.4 on MSVC can go
forward?

Sure - we don't want to give up support for MSVC. However if others
can
solve this problem we should also be able to do so.

Regards,

  Martin


_______________________________________________
libsigc-list mailing list
libsigc-list gnome org
http://mail.gnome.org/mailman/listinfo/libsigc-list


? libsigc++-2.0.6
? stamp-h.in
? stamp-h1
? the_diff
? scripts/libtool.m4
? scripts/ltoptions.m4
? scripts/ltsugar.m4
? scripts/ltversion.m4
? sigc++/signal_base.loT
Index: sigc++/signal_base.cc
===================================================================
RCS file: /cvs/gnome/libsigc++2/sigc++/signal_base.cc,v
retrieving revision 1.3
diff -u -3 -r1.3 signal_base.cc
--- sigc++/signal_base.cc	2 Oct 2004 13:51:17 -0000	1.3
+++ sigc++/signal_base.cc	10 Oct 2004 11:03:34 -0000
@@ -26,10 +26,16 @@
 : ref_count_(0), exec_count_(0), deferred_(0)
 {}
 
-#ifdef SIGC_NEW_DELETE_IN_LIBRARY_ONLY // only defined for MSVC to keep ABI compatibility
-void signal_impl::destroy()
+// only MSVC needs this to guarantee that all new/delete are executed from the DLL module
+#ifdef SIGC_NEW_DELETE_IN_LIBRARY_ONLY
+void* signal_impl::operator new(size_t size_)
 {
-  delete this;
+  return malloc(size_);
+}
+
+void signal_impl::operator delete(void* p)
+{
+  free(p);
 }
 #endif
 
Index: sigc++/signal_base.h
===================================================================
RCS file: /cvs/gnome/libsigc++2/sigc++/signal_base.h,v
retrieving revision 1.6
diff -u -3 -r1.6 signal_base.h
--- sigc++/signal_base.h	2 Oct 2004 13:51:17 -0000	1.6
+++ sigc++/signal_base.h	10 Oct 2004 11:03:34 -0000
@@ -49,9 +49,10 @@
 
   signal_impl();
 
-#ifdef SIGC_NEW_DELETE_IN_LIBRARY_ONLY // only defined for MSVC to keep ABI compatibility
-  /// Destroys the object.
-  void destroy();
+  // only MSVC needs this to guarantee that all new/delete are executed from the DLL module
+#ifdef SIGC_NEW_DELETE_IN_LIBRARY_ONLY
+  void* operator new(size_t size_);
+  void operator delete(void* p);
 #endif
 
   /// Increments the reference counter.
@@ -66,11 +67,7 @@
    * The object is deleted when the reference counter reaches zero.
    */
   inline void unreference()
-#ifdef SIGC_NEW_DELETE_IN_LIBRARY_ONLY // only defined for MSVC to keep ABI compatibility
-    { if (!(--ref_count_)) destroy(); }
-#else
     { if (!(--ref_count_)) delete this; }
-#endif
 
   /** Decrements the reference and execution counter.
    * Invokes sweep() if the execution counter reaches zero and the
@@ -78,11 +75,7 @@
    */
   inline void unreference_exec()
     {
-#ifdef SIGC_NEW_DELETE_IN_LIBRARY_ONLY // only defined for MSVC to keep ABI compatibility
-      if (!(--ref_count_)) destroy();
-#else
       if (!(--ref_count_)) delete this;
-#endif
       else if (!(--exec_count_) && deferred_) sweep();
     }
 
Index: sigc++/functors/slot_base.cc
===================================================================
RCS file: /cvs/gnome/libsigc++2/sigc++/functors/slot_base.cc,v
retrieving revision 1.4
diff -u -3 -r1.4 slot_base.cc
--- sigc++/functors/slot_base.cc	2 Oct 2004 18:29:05 -0000	1.4
+++ sigc++/functors/slot_base.cc	10 Oct 2004 11:03:35 -0000
@@ -25,6 +25,19 @@
 
 namespace internal {
 
+// only MSVC needs this to guarantee that all new/delete are executed from the DLL module
+#ifdef SIGC_NEW_DELETE_IN_LIBRARY_ONLY
+void* slot_rep::operator new(size_t size_)
+{
+  return malloc(size_);
+}
+
+void slot_rep::operator delete(void* p)
+{
+  free(p);
+}
+#endif
+
 void slot_rep::disconnect()
 {
   if (parent_)
@@ -55,17 +68,10 @@
   blocked_(false)
 {}
 
-#ifdef SIGC_NEW_DELETE_IN_LIBRARY_ONLY // only defined for MSVC to keep ABI compatibility
-slot_base::slot_base(const rep_type& rep)
-: rep_(rep.dup()),
-  blocked_(false)
-{}
-#else
 slot_base::slot_base(rep_type* rep)
 : rep_(rep),
   blocked_(false)
 {}
-#endif
 
 slot_base::slot_base(const slot_base& src)
 : rep_(0),
@@ -157,4 +163,3 @@
 }*/
 
 } //namespace sigc
-
Index: sigc++/functors/slot_base.h
===================================================================
RCS file: /cvs/gnome/libsigc++2/sigc++/functors/slot_base.h,v
retrieving revision 1.6
diff -u -3 -r1.6 slot_base.h
--- sigc++/functors/slot_base.h	2 Oct 2004 18:29:05 -0000	1.6
+++ sigc++/functors/slot_base.h	10 Oct 2004 11:03:35 -0000
@@ -86,6 +86,12 @@
   inline ~slot_rep()
     { destroy(); }
 
+  // only MSVC needs this to guarantee that all new/delete are executed from the DLL module
+#ifdef SIGC_NEW_DELETE_IN_LIBRARY_ONLY
+  void* operator new(size_t size_);
+  void operator delete(void* p);
+#endif
+
   /** Destroys the slot_rep object (but doesn't delete it).
    */
   inline void destroy()
@@ -219,11 +225,7 @@
   /** Constructs a slot from an existing slot_rep object.
    * @param rep The slot_rep object this slot should contain.
    */
-#ifdef SIGC_NEW_DELETE_IN_LIBRARY_ONLY // only defined for MSVC to keep ABI compatibility
-  explicit slot_base(const rep_type& rep);
-#else
   explicit slot_base(rep_type* rep);
-#endif
 
   /** Constructs a slot, copying an existing one.
    * @param src The existing slot to copy.
Index: sigc++/functors/macros/slot.h.m4
===================================================================
RCS file: /cvs/gnome/libsigc++2/sigc++/functors/macros/slot.h.m4,v
retrieving revision 1.12
diff -u -3 -r1.12 slot.h.m4
--- sigc++/functors/macros/slot.h.m4	2 Oct 2004 18:29:05 -0000	1.12
+++ sigc++/functors/macros/slot.h.m4	10 Oct 2004 11:03:35 -0000
@@ -79,11 +79,7 @@
    */
   template <class T_functor>
   slot$1(const T_functor& _A_func)
-#ifdef SIGC_NEW_DELETE_IN_LIBRARY_ONLY // only defined for MSVC to keep ABI compatibility
-    : slot_base(internal::typed_slot_rep<T_functor>(_A_func))
-#else
     : slot_base(new internal::typed_slot_rep<T_functor>(_A_func))
-#endif
     { rep_->call_ = internal::slot_call$1<LIST(T_functor, T_return, LOOP(T_arg%1, $1))>::address(); }
 
   slot$1(const slot$1& src)



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