Re: [gdome] Gdome providing free()



Luca,

Here's a second go-around for this patch.

In the saveDocToMemory* functions, it now wraps the libxml2 string
returned by xmlDocDumpFormatMemory into a GdomeDOMString.

Also, it adds a int * parameter to give the length of the buffer
to the caller.

I changed the logic in how the returned GdomeBoolean is determined.
It used to be 

       if ((mem == NULL) && (size > 0))
               return FALSE;
       else
               return TRUE;

but libxml2 already ensures the size = 0 if mem == 0.  So the new
code just checks if the memory has been allocated.

Best,
Blair
Index: ChangeLog
===================================================================
RCS file: /cvs/gnome/gdome2/ChangeLog,v
retrieving revision 1.104
diff -u -r1.104 ChangeLog
--- ChangeLog	10 Mar 2003 10:42:07 -0000	1.104
+++ ChangeLog	17 Mar 2003 23:12:06 -0000
@@ -1,4 +1,57 @@
-2003-04-10  Paolo Casarini <paolo casarini org>
+2003-03-17  Blair Zajac <blair orcaware com>
+	* libgdome/gdome.[ch]
+	(gdome_di_saveDocToMemory) Add a int *men_length pointer to get
+	  the length of the newly created memory buffer.  Change the char
+	  **mem to a GdomeDOMString **mem as this fixes a memory freeing
+	  issue.
+	(gdome_di_saveDocToMemoryEnc) Add a int *men_length pointer to get
+	  the length of the newly created memory buffer.  Change the char
+	  **mem to a GdomeDOMString **mem as this fixes a memory freeing
+	  issue.
+
+	* test/apigen/core.xml
+	(saveDocToMemory) Add a int *men_length pointer to get the length
+	  of the newly created memory buffer.  Change the char **mem to a
+	  GdomeDOMString **mem as this fixes a memory freeing issue.
+	(saveDocToMemoryEnc) Add a int *men_length pointer to get the
+	  length of the newly created memory buffer.  Change the char
+	  **mem to a GdomeDOMString **mem as this fixes a memory freeing
+	  issue.
+
+	* libgdome/gdomecore/gdome-xml-domimpl.[ch]
+	(gdome_xml_di_saveDocToMemory) Add a int *men_length pointer to
+	  get the length of the newly created memory buffer.  Change the
+	  char **mem to a GdomeDOMString **mem as this fixes a memory
+	  freeing issue.
+	(gdome_xml_di_saveDocToMemoryEnc)  Add a int *men_length pointer to
+	  get the length of the newly created memory buffer.  Change the
+	  char **mem to a GdomeDOMString **mem as this fixes a memory
+	  freeing issue.
+
+	* test/test-loadsave.c
+	Modified to test gdome_di_saveDocToMemmory and
+	gdome_di_saveDocToMemoryEnc with the new function arguments
+
+	* gtk-doc/gdome2-decl.txt
+	(gdome_xml_di_saveDocToMemory) Add a int *men_length pointer to
+	  get the length of the newly created memory buffer.  Change the
+	  char **mem to a GdomeDOMString **mem as this fixes a memory
+	  freeing issue.
+	(gdome_xml_di_saveDocToMemoryEnc) Add a int *men_length pointer to
+	  get the length of the newly created memory buffer.  Change the
+	  char **mem to a GdomeDOMString **mem as this fixes a memory
+	  freeing issue.
+
+	* test/apigen/core.xml
+	(saveDocToMemory) Add a int *men_length pointer to get the length
+	  of the newly created memory buffer.  Change the char **mem to a
+	  GdomeDOMString **mem as this fixes a memory freeing issue.
+	(saveDocToMemoryEnc) Add a int *men_length pointer to get the
+	  length of the newly created memory buffer.  Change the char
+	  **mem to a GdomeDOMString **mem as this fixes a memory freeing
+	  issue.
+
+2003-03-10  Paolo Casarini <paolo casarini org>
         * configure.in, README
 	Updated for 0.7.4 release
 
@@ -3277,5 +3330,3 @@
 	* ifgen.pl, DOM* : remove.
 
 	* gdome2/Makefile.am : cleanups. Remove code autogeneration.
-
-	
Index: gtk-doc/gdome2-decl.txt
===================================================================
RCS file: /cvs/gnome/gdome2/gtk-doc/gdome2-decl.txt,v
retrieving revision 1.10
diff -u -r1.10 gdome2-decl.txt
--- gtk-doc/gdome2-decl.txt	10 Mar 2003 10:42:10 -0000	1.10
+++ gtk-doc/gdome2-decl.txt	17 Mar 2003 23:12:14 -0000
@@ -1935,12 +1935,12 @@
 <FUNCTION>
 <NAME>gdome_di_saveDocToMemory</NAME>
 <RETURNS>GdomeBoolean  </RETURNS>
-GdomeDOMImplementation *self, GdomeDocument *doc, char **mem, GdomeSavingCode mode, GdomeException *exc
+GdomeDOMImplementation *self, GdomeDocument *doc, GdomeDOMString **mem, int *mem_length, GdomeSavingCode mode, GdomeException *exc
 </FUNCTION>
 <FUNCTION>
 <NAME>gdome_di_saveDocToMemoryEnc</NAME>
 <RETURNS>GdomeBoolean  </RETURNS>
-GdomeDOMImplementation *self, GdomeDocument *doc, char **mem, const char *encoding, GdomeSavingCode mode, GdomeException *exc
+GdomeDOMImplementation *self, GdomeDocument *doc, GdomeDOMString **mem, int *mem_length, const char *encoding, GdomeSavingCode mode, GdomeException *exc
 </FUNCTION>
 <FUNCTION>
 <NAME>gdome_doc_doctype</NAME>
Index: libgdome/gdome.c
===================================================================
RCS file: /cvs/gnome/gdome2/libgdome/gdome.c,v
retrieving revision 1.38
diff -u -r1.38 gdome.c
--- libgdome/gdome.c	23 May 2002 15:46:17 -0000	1.38
+++ libgdome/gdome.c	17 Mar 2003 23:12:48 -0000
@@ -557,47 +557,64 @@
  * gdome_di_saveDocToMemory:
  * @self:  DOMImplementation Object ref
  * @doc:  the Document of which the tree is wanted to be saved
- * @mem:  the memory pointer where the saved document is returned
+ * @mem: a newly allocated buffer that will contain the saved document
+ * @mem_length: the length of the string contained in @mem
  * @mode:  the indentation mode wanted
  * @exc:  Exception Object ref
  *
- * Save the DOM tree of the Document specified to a new allocated memory and
- * return it in the @mem pointer.
+ * Save the DOM tree of the Document specified to a newly allocated
+ * buffer and return it in @mem along with the length of the buffer in
+ * @mem_length.  @mem is dynamically allocated and should be free'd
+ * with gdome_str_unref.
  * Returns: %FALSE in case of failure, %TRUE otherwise.
  */
 GdomeBoolean
-gdome_di_saveDocToMemory (GdomeDOMImplementation *self, GdomeDocument *doc, char **mem, GdomeSavingCode mode, GdomeException *exc)
+gdome_di_saveDocToMemory (GdomeDOMImplementation *self,
+                          GdomeDocument *doc,
+                          GdomeDOMString **mem,
+                          int *mem_length,
+                          GdomeSavingCode mode,
+                          GdomeException *exc)
 {
 	if (self == NULL) {
 		*exc = GDOME_NULL_POINTER_ERR;
 		return FALSE;
 	}
 	*exc = 0;
-	return ((Gdome_xml_DOMImplementation *)self)->vtab->saveDocToMemory (self, doc, mem, mode, exc);
+	return ((Gdome_xml_DOMImplementation *)self)->vtab->saveDocToMemory (self, doc, mem, mem_length, mode, exc);
 }
 /**
  * gdome_di_saveDocToMemoryEnc:
  * @self:  DOMImplementation Object ref
  * @doc:  the Document of which the tree is wanted to be saved
- * @mem:  the memory pointer where the saved document is returned
+ * @mem: a newly allocated buffer that will contain the saved document
+ * @mem_length: the length of the string contained in @mem
  * @encoding:  character encoding to use when generating XML text
  * @mode:  the indentation mode wanted
  * @exc:  Exception Object ref
  *
- * Save the DOM tree of the Document specified using the specified character
- * encoding standard to a new allocated memory and return it in the @mem
- * pointer.
+ * Save the DOM tree of the Document specified using the specified
+ * character encoding standard to a newly allocated buffer and return
+ * it in @mem along with the length of the buffer in @mem_length.
+ * @mem is dynamically allocated and should be free'd with
+ * gdome_str_unref.
  * Returns: %FALSE in case of failure, %TRUE otherwise.
  */
 GdomeBoolean
-gdome_di_saveDocToMemoryEnc (GdomeDOMImplementation *self, GdomeDocument *doc, char **mem, const char *encoding, GdomeSavingCode mode, GdomeException *exc)
+gdome_di_saveDocToMemoryEnc (GdomeDOMImplementation *self,
+                             GdomeDocument *doc,
+                             GdomeDOMString **mem,
+                             int *mem_length,
+                             const char *encoding,
+                             GdomeSavingCode mode,
+                             GdomeException *exc)
 {
 	if (self == NULL) {
 		*exc = GDOME_NULL_POINTER_ERR;
 		return FALSE;
 	}
 	*exc = 0;
-	return ((Gdome_xml_DOMImplementation *)self)->vtab->saveDocToMemoryEnc (self, doc, mem, encoding, mode, exc);
+	return ((Gdome_xml_DOMImplementation *)self)->vtab->saveDocToMemoryEnc (self, doc, mem, mem_length, encoding, mode, exc);
 }
 
 /******************************************************************************
Index: libgdome/gdome.h
===================================================================
RCS file: /cvs/gnome/gdome2/libgdome/gdome.h,v
retrieving revision 1.52
diff -u -r1.52 gdome.h
--- libgdome/gdome.h	23 May 2002 15:46:18 -0000	1.52
+++ libgdome/gdome.h	17 Mar 2003 23:12:53 -0000
@@ -808,8 +808,8 @@
 GdomeDocument *gdome_di_createDocFromMemoryWithEntitiesTable (GdomeDOMImplementation *self, char *buffer, const GdomeEntitiesTableEntry entityTable[], unsigned int mode, GdomeException *exc);
 GdomeBoolean gdome_di_saveDocToFile (GdomeDOMImplementation *self, GdomeDocument *doc, const char *filename, GdomeSavingCode mode, GdomeException *exc);
 GdomeBoolean gdome_di_saveDocToFileEnc (GdomeDOMImplementation *self, GdomeDocument *doc, const char *filename, const char *encoding, GdomeSavingCode mode, GdomeException *exc);
-GdomeBoolean gdome_di_saveDocToMemory (GdomeDOMImplementation *self, GdomeDocument *doc, char **mem, GdomeSavingCode mode, GdomeException *exc);
-GdomeBoolean gdome_di_saveDocToMemoryEnc (GdomeDOMImplementation *self, GdomeDocument *doc, char **mem, const char *encoding, GdomeSavingCode mode, GdomeException *exc);
+GdomeBoolean gdome_di_saveDocToMemory (GdomeDOMImplementation *self, GdomeDocument *doc, GdomeDOMString **mem, int *mem_length, GdomeSavingCode mode, GdomeException *exc);
+GdomeBoolean gdome_di_saveDocToMemoryEnc (GdomeDOMImplementation *self, GdomeDocument *doc, GdomeDOMString **mem, int *mem_length, const char *encoding, GdomeSavingCode mode, GdomeException *exc);
 
 
 GdomeDocumentType *gdome_doc_doctype (GdomeDocument *self, GdomeException *exc);
Index: libgdome/gdomecore/gdome-xml-domimpl.c
===================================================================
RCS file: /cvs/gnome/gdome2/libgdome/gdomecore/gdome-xml-domimpl.c,v
retrieving revision 1.37
diff -u -r1.37 gdome-xml-domimpl.c
--- libgdome/gdomecore/gdome-xml-domimpl.c	23 May 2002 15:46:20 -0000	1.37
+++ libgdome/gdomecore/gdome-xml-domimpl.c	17 Mar 2003 23:12:55 -0000
@@ -36,6 +36,7 @@
 #include "gdome-xml-util.h"
 #include "gdome-xml-xmlutil.h"
 #include "gdome-xml-domimpl.h"
+#include "gdome-xml-str.h"
 
 Gdome_xml_DOMImplementation *gdome_xml_DOMImplementation = NULL;
 
@@ -780,67 +781,83 @@
  * gdome_xml_di_saveDocToMemory:
  * @self:  DOMImplementation Object ref
  * @doc:  the Document of which the tree is wanted to be saved
- * @mem:  the memory pointer where the saved document is returned
+ * @mem: a newly allocated buffer that will contain the saved document
+ * @mem_length: the length of the string contained in @mem
  * @mode:  the indentation mode wanted
  * @exc:  Exception Object ref
  *
- * Save the DOM tree of the Document specified to a new allocated memory and
- * return it in the @mem pointer.
+ * Save the DOM tree of the Document specified to a newly allocated
+ * buffer and return it in @mem along with the length of the buffer in
+ * @mem_length.  @mem is dynamically allocated and should be free'd
+ * with gdome_str_unref.
  * Returns: %FALSE in case of failure, %TRUE otherwise.
  */
 GdomeBoolean
 gdome_xml_di_saveDocToMemory (GdomeDOMImplementation *self, GdomeDocument *doc,
-															char **mem, GdomeSavingCode mode,
-															GdomeException *exc)
+                              GdomeDOMString **mem, int *mem_length,
+                              GdomeSavingCode mode, GdomeException *exc)
 {
 	Gdome_xml_Document *priv_doc = (Gdome_xml_Document *)doc;
-	int size = 0;
+	xmlChar *buffer;
 
 	g_return_val_if_fail (self != NULL, FALSE);
 	g_return_val_if_fail (doc != NULL, FALSE);
 	g_return_val_if_fail (mem != NULL, FALSE);
+	g_return_val_if_fail (mem_length != NULL, FALSE);
 	g_return_val_if_fail (exc != NULL, FALSE);
 	g_assert(self == (GdomeDOMImplementation *)gdome_xml_DOMImplementation);
 
-	xmlDocDumpFormatMemory(priv_doc->n, (xmlChar **)mem, &size, mode);
-	if ((mem == NULL) && (size > 0))
-		return FALSE;
-	else
+	xmlDocDumpFormatMemory(priv_doc->n, &buffer, mem_length, mode);
+	if (buffer) {
+		*mem = gdome_xml_str_mkref_xml(buffer);
 		return TRUE;
+	} else {
+		*mem = NULL;
+		return FALSE;
+	}
 }
 
 /**
  * gdome_xml_di_saveDocToMemoryEnc:
  * @self:  DOMImplementation Object ref
  * @doc:  the Document of which the tree is wanted to be saved
- * @mem:  the memory pointer where the saved document is returned
+ * @mem: a newly allocated buffer that will contain the saved document
+ * @mem_length: the length of the string contained in @mem
  * @encoding:  character encoding to use when generating XML text
  * @mode:  the indentation mode wanted
  * @exc:  Exception Object ref
  *
- * Save the DOM tree of the Document specified using the specified character
- * encoding standard to a new allocated memory and return it in the @mem
- * pointer.
+ * Save the DOM tree of the Document specified using the specified
+ * character encoding standard to a newly allocated buffer and return
+ * it in @mem along with the length of the buffer in @mem_length.
+ * @mem is dynamically allocated and should be free'd with
+ * gdome_str_unref.
  * Returns: %FALSE in case of failure, %TRUE otherwise.
  */
 GdomeBoolean
-gdome_xml_di_saveDocToMemoryEnc (GdomeDOMImplementation *self, GdomeDocument *doc,
-                                 char **mem, const char *encoding,
+gdome_xml_di_saveDocToMemoryEnc (GdomeDOMImplementation *self,
+																 GdomeDocument *doc,
+                                 GdomeDOMString **mem, int *mem_length,
+																 const char *encoding,
                                  GdomeSavingCode mode, GdomeException *exc)
 {
 	Gdome_xml_Document *priv_doc = (Gdome_xml_Document *)doc;
-	int size = 0;
+	xmlChar *buffer;
 
 	g_return_val_if_fail (self != NULL, FALSE);
 	g_return_val_if_fail (doc != NULL, FALSE);
 	g_return_val_if_fail (mem != NULL, FALSE);
+	g_return_val_if_fail (mem_length != NULL, FALSE);
 	g_return_val_if_fail (encoding != NULL, FALSE);
 	g_return_val_if_fail (exc != NULL, FALSE);
 	g_assert(self == (GdomeDOMImplementation *)gdome_xml_DOMImplementation);
 
-	xmlDocDumpFormatMemoryEnc(priv_doc->n, (xmlChar **)mem, &size, encoding, mode);
-	if ((mem == NULL) && (size > 0))
-		return FALSE;
-	else
+	xmlDocDumpFormatMemoryEnc(priv_doc->n, &buffer, mem_length, encoding, mode);
+	if (buffer) {
+		*mem = gdome_xml_str_mkref_xml(buffer);
 		return TRUE;
+	} else {
+		*mem = NULL;
+		return FALSE;
+	}
 }
Index: libgdome/gdomecore/gdome-xml-domimpl.h
===================================================================
RCS file: /cvs/gnome/gdome2/libgdome/gdomecore/gdome-xml-domimpl.h,v
retrieving revision 1.21
diff -u -r1.21 gdome-xml-domimpl.h
--- libgdome/gdomecore/gdome-xml-domimpl.h	23 May 2002 15:46:20 -0000	1.21
+++ libgdome/gdomecore/gdome-xml-domimpl.h	17 Mar 2003 23:12:56 -0000
@@ -41,9 +41,9 @@
   GdomeDocument *(*createDocFromURIWithEntitiesTable) (GdomeDOMImplementation *self, const char *uri, const GdomeEntitiesTableEntry entityTable[], unsigned int mode, GdomeException *exc);
   GdomeDocument *(*createDocFromMemoryWithEntitiesTable) (GdomeDOMImplementation *self, char *buffer, const GdomeEntitiesTableEntry entityTable[], unsigned int mode, GdomeException *exc);
   GdomeBoolean (*saveDocToFile) (GdomeDOMImplementation *self, GdomeDocument *doc, const char *filename, GdomeSavingCode mode, GdomeException *exc);
-  GdomeBoolean (*saveDocToMemory) (GdomeDOMImplementation *self, GdomeDocument *doc, char **mem, GdomeSavingCode mode, GdomeException *exc);
+  GdomeBoolean (*saveDocToMemory) (GdomeDOMImplementation *self, GdomeDocument *doc, GdomeDOMString **mem, int *mem_length, GdomeSavingCode mode, GdomeException *exc);
 	GdomeBoolean (*saveDocToFileEnc) (GdomeDOMImplementation *self, GdomeDocument *doc, const char *filename, const char *encoding, GdomeSavingCode mode, GdomeException *exc);
-  GdomeBoolean (*saveDocToMemoryEnc) (GdomeDOMImplementation *self, GdomeDocument *doc, char **mem, const char *encoding, GdomeSavingCode mode, GdomeException *exc);
+  GdomeBoolean (*saveDocToMemoryEnc) (GdomeDOMImplementation *self, GdomeDocument *doc, GdomeDOMString **mem, int *mem_length, const char *encoding, GdomeSavingCode mode, GdomeException *exc);
 };
 
 typedef struct _Gdome_xml_DOMImplementation Gdome_xml_DOMImplementation;
@@ -114,12 +114,14 @@
 																						GdomeException *exc);
 GdomeBoolean gdome_xml_di_saveDocToMemory (GdomeDOMImplementation *self,
                                            GdomeDocument *doc,
-                                           char **mem,
+                                           GdomeDOMString **mem,
+                                           int *mem_length,
                                            GdomeSavingCode mode,
                                            GdomeException *exc);
 GdomeBoolean gdome_xml_di_saveDocToMemoryEnc (GdomeDOMImplementation *self,
                                               GdomeDocument *doc,
-                                              char **mem,
+                                              GdomeDOMString **mem,
+                                              int *mem_length,
                                               const char *encoding,
                                               GdomeSavingCode mode,
                                               GdomeException *exc);
@@ -129,5 +131,3 @@
 
 
 #endif /* GDOME_DOMIMPL_FILE */
-
-
Index: test/test-loadsave.c
===================================================================
RCS file: /cvs/gnome/gdome2/test/test-loadsave.c,v
retrieving revision 1.6
diff -u -r1.6 test-loadsave.c
--- test/test-loadsave.c	23 May 2002 15:46:22 -0000	1.6
+++ test/test-loadsave.c	17 Mar 2003 23:12:57 -0000
@@ -100,7 +100,8 @@
 	GdomeDOMImplementation *domImpl = NULL;
 	GdomeDocument *domdoc = NULL;
   GdomeException exc = 0;
-  char *mem;
+  GdomeDOMString *mem;
+  int mem_length;
 
 	domImpl = gdome_di_mkref();
 
@@ -133,16 +134,16 @@
 		fprintf (stderr, "DOMImplementation.createDocFromMemory: parsing failed\n");
 		return -1;
   }
-	if (!gdome_di_saveDocToMemory (domImpl, domdoc, &mem, 0, &exc)) {
+	if (!gdome_di_saveDocToMemory (domImpl, domdoc, &mem, &mem_length, 0, &exc)) {
 		fprintf (stderr, "DOMImplementation.saveDocToMemory: failed\n");
 		return -1;
 	}
-  free (mem);
-	if (!gdome_di_saveDocToMemoryEnc (domImpl, domdoc, &mem, "ISO-8859-1", 0, &exc)) {
+  gdome_str_unref (mem);
+	if (!gdome_di_saveDocToMemoryEnc (domImpl, domdoc, &mem, &mem_length, "ISO-8859-1", 0, &exc)) {
 		fprintf (stderr, "DOMImplementation.saveDocToMemory: failed\n");
 		return -1;
   }
-  free (mem);
+  gdome_str_unref (mem);
   gdome_doc_unref(domdoc, &exc);
   dot();
 
Index: test/apigen/core.xml
===================================================================
RCS file: /cvs/gnome/gdome2/test/apigen/core.xml,v
retrieving revision 1.19
diff -u -r1.19 core.xml
--- test/apigen/core.xml	23 May 2002 15:46:23 -0000	1.19
+++ test/apigen/core.xml	17 Mar 2003 23:13:00 -0000
@@ -179,13 +179,15 @@
     <METHOD TYPE="GdomeBoolean" NAME="saveDocToMemory" STANDARD="NO">
       <EXCEPTION TYPE="NULL_POINTER_ERR" ON="self == NULL"/>
       <PARAM TYPE="GdomeDocument *" NAME="doc"/>
-      <PARAM TYPE="char **" NAME="mem"/>
+      <PARAM TYPE="GdomeDOMString **" NAME="mem"/>
+      <PARAM TYPE="int *" NAME="mem_length"/>
       <PARAM TYPE="GdomeSavingCode" NAME="mode"/>
     </METHOD>
     <METHOD TYPE="GdomeBoolean" NAME="saveDocToMemoryEnc" STANDARD="NO">
       <EXCEPTION TYPE="NULL_POINTER_ERR" ON="self == NULL"/>
       <PARAM TYPE="GdomeDocument *" NAME="doc"/>
-      <PARAM TYPE="char **" NAME="mem"/>
+      <PARAM TYPE="GdomeDOMString **" NAME="mem"/>
+      <PARAM TYPE="int *" NAME="mem_length"/>
       <PARAM TYPE="const char *" NAME="encoding"/>
       <PARAM TYPE="GdomeSavingCode" NAME="mode"/>
     </METHOD>


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