]> git.ipfire.org Git - thirdparty/dhcp.git/commitdiff
Fix handling of changing a connectiong from connecting to connected, avoiding
authorShawn Routhier <sar@isc.org>
Thu, 15 Oct 2009 18:39:49 +0000 (18:39 +0000)
committerShawn Routhier <sar@isc.org>
Thu, 15 Oct 2009 18:39:49 +0000 (18:39 +0000)
releasing the memory for the omapi io object.

RELNOTES
includes/omapip/omapip.h
omapip/connection.c
omapip/dispatch.c

index 3fd283550b7fdce3a05e6fe8d78593ddc5486cfb..2b609bd04a7436dfbb9334b9246dbaaa2c752d29 100644 (file)
--- a/RELNOTES
+++ b/RELNOTES
@@ -205,6 +205,11 @@ work on other platforms. Please report any problems and suggested fixes to
 - ./configure now checks to ensure the intX_t and u_intX_t types are defined,
   correcting a compilation failure when using Sun's compiler.
 
+- Modified the handling of a connection to avoid releasing the omapi io
+  object for the connection while it is still in use.  One symptom from
+  this error was a segfault when a failover secondary attempted to connect
+  to the failover primary if their clocks were not synchronized.
+
                        Changes since 4.1.0b1
 
 - A missing "else" in dhcrelay.c could have caused an interface not to
index 08a05c50e2113511aa03f8ce3fd7dcd63e6e3c95..732c6fe86284bf513d5156b2186dfd59e7e182db 100644 (file)
@@ -380,6 +380,12 @@ isc_result_t omapi_register_io_object (omapi_object_t *,
                                       isc_result_t (*)(omapi_object_t *),
                                       isc_result_t (*)(omapi_object_t *),
                                       isc_result_t (*)(omapi_object_t *));
+isc_result_t omapi_reregister_io_object (omapi_object_t *,
+                                        int (*)(omapi_object_t *),
+                                        int (*)(omapi_object_t *),
+                                        isc_result_t (*)(omapi_object_t *),
+                                        isc_result_t (*)(omapi_object_t *),
+                                        isc_result_t (*)(omapi_object_t *));
 isc_result_t omapi_unregister_io_object (omapi_object_t *);
 isc_result_t omapi_dispatch (struct timeval *);
 isc_result_t omapi_wait_for_completion (omapi_object_t *, struct timeval *);
index e95fd3f7824ce91e41826491acacbdafb849cdee..e9289643de66189ee0e1d8ddcaaef767f8ce03ec 100644 (file)
@@ -674,16 +674,16 @@ static isc_result_t omapi_connection_connect_internal (omapi_object_t *h)
                         (struct sockaddr *)&c -> local_addr, &sl) < 0) {
        }
 
-       /* Disconnect from I/O object, if any. */
-       if (h -> outer)
-               omapi_unregister_io_object (h);
-
-       status = omapi_register_io_object (h,
-                                          omapi_connection_readfd,
-                                          omapi_connection_writefd,
-                                          omapi_connection_reader,
-                                          omapi_connection_writer,
-                                          omapi_connection_reaper);
+       /* Reregister with the I/O object.  If we don't already have an
+          I/O object this turns into a register call, otherwise we simply
+          modify the pointers in the I/O object. */
+
+       status = omapi_reregister_io_object (h,
+                                            omapi_connection_readfd,
+                                            omapi_connection_writefd,
+                                            omapi_connection_reader,
+                                            omapi_connection_writer,
+                                            omapi_connection_reaper);
 
        if (status != ISC_R_SUCCESS) {
                omapi_disconnect (h, 1);
index 27eb46ed56ee309d88613331fb2fa740ae55b79b..9e3fb8ae0bf21e15d0d607ae8a5cce1b0c7535f1 100644 (file)
@@ -167,6 +167,50 @@ isc_result_t omapi_register_io_object (omapi_object_t *h,
        return ISC_R_SUCCESS;
 }
 
+/* ReRegister an I/O handle so that we can do asynchronous I/O on it.
+ * If the handle doesn't exist we call the register routine to build it.
+ * if it does exist we change the functions associated with it, and
+ * repoke the fd code to make it happy.  Neither the objects nor the
+ * fd are allowed to have changed. */
+
+isc_result_t omapi_reregister_io_object (omapi_object_t *h,
+                                        int (*readfd) (omapi_object_t *),
+                                        int (*writefd) (omapi_object_t *),
+                                        isc_result_t (*reader)
+                                               (omapi_object_t *),
+                                        isc_result_t (*writer)
+                                               (omapi_object_t *),
+                                        isc_result_t (*reaper)
+                                               (omapi_object_t *))
+{
+       omapi_io_object_t *obj;
+
+       if ((!h -> outer) || (h -> outer -> type != omapi_type_io_object)) {
+               /* If we don't have an object or if the type isn't what 
+                * we expect do the normal registration (which will overwrite
+                * an incorrect type, that's what we did historically, may
+                * want to change that)
+                */
+               return (omapi_register_io_object (h, readfd, writefd,
+                                                 reader, writer, reaper));
+       }
+
+       /* We have an io object of the correct type, try to update it */
+       /*sar*/
+       /* Should we validate that the fd matches the previous one?
+        * It's suppossed to, that's a requirement, don't bother yet */
+
+       obj = (omapi_io_object_t *)h->outer;
+
+       obj -> readfd = readfd;
+       obj -> writefd = writefd;
+       obj -> reader = reader;
+       obj -> writer = writer;
+       obj -> reaper = reaper;
+       
+       return (ISC_R_SUCCESS);
+}
+
 isc_result_t omapi_unregister_io_object (omapi_object_t *h)
 {
        omapi_io_object_t *p, *obj, *last, *ph;