ws-axis-cvs mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From nand...@apache.org
Subject svn commit: r391581 - in /webservices/axis2/trunk/c: include/ modules/util/ modules/xml/om/ modules/xml/parser/libxml2/
Date Wed, 05 Apr 2006 10:57:21 GMT
Author: nandika
Date: Wed Apr  5 03:57:18 2006
New Revision: 391581

URL: http://svn.apache.org/viewcvs?rev=391581&view=rev
Log:
axis2_libxml2 writer wrapper changed to handle namespaces properly
om_node serialize function is also changed , added a stack 

Added:
    webservices/axis2/trunk/c/include/axis2_stack.h
    webservices/axis2/trunk/c/modules/util/stack.c
Modified:
    webservices/axis2/trunk/c/modules/xml/om/om_element.c
    webservices/axis2/trunk/c/modules/xml/om/om_namespace.c
    webservices/axis2/trunk/c/modules/xml/om/om_node.c
    webservices/axis2/trunk/c/modules/xml/parser/libxml2/libxml2_reader_wrapper.c
    webservices/axis2/trunk/c/modules/xml/parser/libxml2/libxml2_writer_wrapper.c

Added: webservices/axis2/trunk/c/include/axis2_stack.h
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/c/include/axis2_stack.h?rev=391581&view=auto
==============================================================================
--- webservices/axis2/trunk/c/include/axis2_stack.h (added)
+++ webservices/axis2/trunk/c/include/axis2_stack.h Wed Apr  5 03:57:18 2006
@@ -0,0 +1,115 @@
+/*
+ * Copyright 2004,2005 The Apache Software Foundation.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+ 
+ #ifndef AXIS2_STACK_H
+ #define AXIS2_STACK_H
+ 
+ 
+ /**
+ * @file axis2_stack.h
+ * @brief represents a stack
+ */
+
+#include <axis2_defines.h>
+#include <axis2_env.h>
+
+#ifdef __cplusplus
+extern "C"
+{
+#endif
+
+typedef struct axis2_stack_ops axis2_stack_ops_t;
+typedef struct axis2_stack axis2_stack_t;
+
+/**
+ * @defgroup axis2_util represents a data structure stack
+ * @ingroup axis2_util
+ * @{
+ */
+
+/**
+ * \brief Axis2 stack ops struct
+ * Encapsulator struct for ops of axis2_qname
+ */
+
+AXIS2_DECLARE_DATA struct axis2_stack_ops
+{
+    /**
+     * Free function of the stack
+     * @param stack pointer to stack
+     * @param env environemnt
+     */
+     
+    axis2_status_t (AXIS2_CALL*
+    free)(axis2_stack_t *stack,
+          axis2_env_t **env);      
+       
+    void* (AXIS2_CALL*
+    pop)(axis2_stack_t *stack,
+         axis2_env_t **env); 
+    
+    axis2_status_t (AXIS2_CALL *
+    push)(axis2_stack_t *stack,
+          axis2_env_t **env,
+          void* value);
+          
+    int (AXIS2_CALL *
+    size)(axis2_stack_t *stack,
+          axis2_env_t **env);
+    /** 
+     * returns the last put value from the stack
+     * without removing it from stack
+     */      
+          
+    void* (AXIS2_CALL *
+    get)(axis2_stack_t *stack,
+         axis2_env_t **env);                    
+          
+}axis2_stack_ops;
+ 
+struct axis2_stack
+{
+    axis2_stack_ops_t *ops;
+};
+
+AXIS2_DECLARE(axis2_stack_t *)
+axis2_stack_create(axis2_env_t **env);
+ 
+ 
+/*************MACROS ********************************************************/
+ 
+#define AXIS2_STACK_FREE( stack, env) \
+        ((stack)->ops->free( stack, env))
+        
+#define AXIS2_STACK_POP( stack, env) \
+        ((stack)->ops->pop( stack, env))
+        
+#define AXIS2_STACK_PUSH( stack, env, value) \
+        ((stack)->ops->push( stack, env, value))
+        
+#define AXIS2_STACK_SIZE( stack, env) \
+        ((stack)->ops->size( stack, env)) 
+        
+#define AXIS2_STACK_GET( stack, env) \
+        ((stack)->ops->get( stack, env))
+ 
+/*************END MACROS ****************************************************/
+ /** @} */
+
+#ifdef __cplusplus
+}
+#endif
+ #endif /* AXIS2_STACK_H */
\ No newline at end of file

Added: webservices/axis2/trunk/c/modules/util/stack.c
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/c/modules/util/stack.c?rev=391581&view=auto
==============================================================================
--- webservices/axis2/trunk/c/modules/util/stack.c (added)
+++ webservices/axis2/trunk/c/modules/util/stack.c Wed Apr  5 03:57:18 2006
@@ -0,0 +1,238 @@
+/*
+ * Copyright 2004,2005 The Apache Software Foundation.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+ 
+#include <axis2_stack.h>
+#include <axis2.h>
+#include <axis2_env.h>
+#include <stdlib.h>
+#include <string.h>
+
+#define AXIS2_STACK_DEFAULT_CAPACITY 10
+ 
+typedef struct axis2_stack_impl 
+{
+    axis2_stack_t stack;
+
+    void **data;
+    /** current number of elements */
+    int size;
+    /** total capacity */
+    int capacity;
+
+    axis2_bool_t is_empty_stack;
+
+}axis2_stack_impl_t;
+
+#define AXIS2_INTF_TO_IMPL(stack) ((axis2_stack_impl_t *)stack)
+
+ 
+axis2_status_t AXIS2_CALL
+axis2_stack_free(axis2_stack_t *stack,
+                 axis2_env_t **env);      
+    
+void* AXIS2_CALL
+axis2_stack_pop(axis2_stack_t *stack,
+                axis2_env_t **env); 
+
+axis2_status_t AXIS2_CALL 
+axis2_stack_push(axis2_stack_t *stack,
+                 axis2_env_t **env,
+                 void* value);
+        
+int AXIS2_CALL
+axis2_stack_size(axis2_stack_t *stack,
+                 axis2_env_t **env);
+                 
+void* AXIS2_CALL
+axis2_stack_get(axis2_stack_t *stack,
+                axis2_env_t **env);                 
+
+static axis2_status_t 
+axis2_stack_ensure_capacity(axis2_stack_t *stack,
+                            axis2_env_t **env);
+                            
+AXIS2_DECLARE(axis2_stack_t *)
+axis2_stack_create(axis2_env_t **env)
+{
+    axis2_stack_impl_t *stack_impl = NULL;
+    
+    AXIS2_ENV_CHECK(env, NULL);
+
+    stack_impl = (axis2_stack_impl_t*)AXIS2_MALLOC((*env)->allocator, 
+                        sizeof(axis2_stack_impl_t));
+                        
+    if(!stack_impl)
+    {
+        AXIS2_ERROR_SET((*env)->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE);
+        return NULL;
+    }
+    
+    stack_impl->data = NULL;
+    stack_impl->size = 0;
+    stack_impl->capacity = AXIS2_STACK_DEFAULT_CAPACITY;
+    stack_impl->is_empty_stack = AXIS2_TRUE;
+    stack_impl->stack.ops = NULL;
+    
+    stack_impl->data = AXIS2_MALLOC((*env)->allocator, sizeof(void*)*                 
+                                       AXIS2_STACK_DEFAULT_CAPACITY);
+    if(NULL == stack_impl->data)
+    {
+        AXIS2_ERROR_SET((*env)->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE);
+        axis2_stack_free(&(stack_impl->stack) , env);
+        return NULL;
+    }
+
+    stack_impl->stack.ops = (axis2_stack_ops_t *)AXIS2_MALLOC((*env)->allocator,
+                                sizeof(axis2_stack_ops_t));
+                                
+    if(NULL ==  stack_impl->stack.ops)
+    {
+        AXIS2_ERROR_SET((*env)->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE);
+        axis2_stack_free(&(stack_impl->stack) , env);
+        return NULL;
+    }                                   
+    
+    
+    stack_impl->stack.ops->free = 
+        axis2_stack_free;
+        
+    stack_impl->stack.ops->pop = 
+        axis2_stack_pop;
+        
+    stack_impl->stack.ops->push =
+        axis2_stack_push;
+        
+    stack_impl->stack.ops->size =
+        axis2_stack_size;    
+        
+    stack_impl->stack.ops->get =
+        axis2_stack_get;            
+    
+    return &(stack_impl->stack);                   
+} 
+
+axis2_status_t AXIS2_CALL
+axis2_stack_free(axis2_stack_t *stack,
+                 axis2_env_t **env)
+{
+    axis2_stack_impl_t *stack_impl = NULL;
+    AXIS2_ENV_CHECK(env, AXIS2_FAILURE);
+    
+    stack_impl = AXIS2_INTF_TO_IMPL(stack);
+    
+    if(NULL != stack_impl->data)
+    {
+        AXIS2_FREE((*env)->allocator, stack_impl->data);
+        stack_impl->data = NULL;
+    }
+    if(NULL != stack->ops)
+    {
+        AXIS2_FREE((*env)->allocator, stack->ops);
+        stack->ops = NULL;
+    }
+    AXIS2_FREE((*env)->allocator, stack_impl);
+    stack_impl = NULL;
+    return AXIS2_SUCCESS;
+}  
+
+void* AXIS2_CALL
+axis2_stack_pop(axis2_stack_t *stack,
+                axis2_env_t **env)
+{
+    axis2_stack_impl_t *stack_impl = NULL;
+    void *value = NULL;
+    AXIS2_ENV_CHECK(env, NULL);
+    
+    stack_impl = AXIS2_INTF_TO_IMPL(stack);
+    if(stack_impl->is_empty_stack == AXIS2_TRUE || 
+            stack_impl->size == 0)
+    {            
+        return NULL;
+    }
+    if(stack_impl->size > 0)
+    {
+        value = stack_impl->data[stack_impl->size -1 ];
+        stack_impl->data[stack_impl->size-1] = NULL;
+        stack_impl->size--;
+        if(stack_impl->size == 0)
+        {
+            stack_impl->is_empty_stack = AXIS2_TRUE;
+        }
+    }
+    return value;
+}                 
+
+axis2_status_t AXIS2_CALL 
+axis2_stack_push(axis2_stack_t *stack,
+                 axis2_env_t **env,
+                 void* value)
+{
+    axis2_stack_impl_t *stack_impl = NULL;
+    AXIS2_ENV_CHECK(env, AXIS2_FAILURE);
+    AXIS2_PARAM_CHECK((*env)->error, value, AXIS2_FAILURE);
+
+    stack_impl = AXIS2_INTF_TO_IMPL(stack);
+    if((stack_impl->size  < stack_impl->capacity) && (stack_impl->capacity >0 ))
+    {
+        stack_impl->data[stack_impl->size++] = value;
+    }
+    else
+    {
+        void **new_data = NULL;
+        
+        int new_capacity = stack_impl->capacity + AXIS2_STACK_DEFAULT_CAPACITY; 
+        
+        new_data = AXIS2_MALLOC((*env)->allocator, sizeof(void*)*new_capacity);
+        if(!new_data)
+        {
+            AXIS2_ERROR_SET((*env)->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE);
+            return AXIS2_FAILURE;
+        }
+        memset(new_data, 0, sizeof(void*)*new_capacity);
+        memcpy(new_data, stack_impl->data, sizeof(void*) *(stack_impl->capacity));
+        stack_impl->capacity = new_capacity;
+        
+        AXIS2_FREE((*env)->allocator, stack_impl->data);
+        stack_impl->data = NULL;
+        stack_impl->data = new_data;
+        
+        stack_impl->data[stack_impl->size++] = value;
+    }
+    stack_impl->is_empty_stack = AXIS2_FALSE;
+    return AXIS2_SUCCESS;    
+}                 
+        
+int AXIS2_CALL
+axis2_stack_size(axis2_stack_t *stack,
+                 axis2_env_t **env)
+{
+    AXIS2_ENV_CHECK(env, AXIS2_FAILURE);
+    return AXIS2_INTF_TO_IMPL(stack)->size;
+}   
+
+void * AXIS2_CALL
+axis2_stack_get(axis2_stack_t *stack,
+                axis2_env_t **env)
+{
+    axis2_stack_impl_t *stack_impl = NULL;
+    AXIS2_ENV_CHECK(env, NULL);
+    stack_impl = AXIS2_INTF_TO_IMPL(stack);
+    if(stack_impl->size > 0)
+    {
+        return stack_impl->data[stack_impl->size-1];
+    }
+    return NULL;
+}                              
\ No newline at end of file

Modified: webservices/axis2/trunk/c/modules/xml/om/om_element.c
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/c/modules/xml/om/om_element.c?rev=391581&r1=391580&r2=391581&view=diff
==============================================================================
--- webservices/axis2/trunk/c/modules/xml/om/om_element.c (original)
+++ webservices/axis2/trunk/c/modules/xml/om/om_element.c Wed Apr  5 03:57:18 2006
@@ -528,8 +528,10 @@
 
     if (NULL != declared_ns)
     {
-        /*Namespace already declared, so return */
-        return AXIS2_SUCCESS;
+        if(AXIS2_OM_NAMESPACE_EQUALS(ns, env, declared_ns) == AXIS2_TRUE)
+        {/*Namespace already declared, so return */
+            return AXIS2_SUCCESS;
+        }            
     }
     
     if(AXIS2_OM_NODE_GET_NODE_TYPE(node, env) != AXIS2_OM_ELEMENT)

Modified: webservices/axis2/trunk/c/modules/xml/om/om_namespace.c
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/c/modules/xml/om/om_namespace.c?rev=391581&r1=391580&r2=391581&view=diff
==============================================================================
--- webservices/axis2/trunk/c/modules/xml/om/om_namespace.c (original)
+++ webservices/axis2/trunk/c/modules/xml/om/om_namespace.c Wed Apr  5 03:57:18 2006
@@ -219,9 +219,18 @@
     ns_impl = AXIS2_INTF_TO_IMPL(om_namespace);
     
     if (ns_impl->uri && ns_impl->prefix)
+    {
             status = axis2_om_output_write ( om_output, env, AXIS2_OM_NAMESPACE,
                                          2, ns_impl->prefix,
                                          ns_impl->uri);
+    }
+    else if(ns_impl->uri)
+    {
+        status = axis2_om_output_write(om_output, env, AXIS2_OM_NAMESPACE,
+                                        2, NULL, ns_impl->uri);
+    
+    }
+                                             
     return status;
 }
 

Modified: webservices/axis2/trunk/c/modules/xml/om/om_node.c
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/c/modules/xml/om/om_node.c?rev=391581&r1=391580&r2=391581&view=diff
==============================================================================
--- webservices/axis2/trunk/c/modules/xml/om/om_node.c (original)
+++ webservices/axis2/trunk/c/modules/xml/om/om_node.c Wed Apr  5 03:57:18 2006
@@ -460,6 +460,7 @@
     
     int status = AXIS2_SUCCESS;
     axis2_om_node_impl_t *node_impl = NULL;
+    axis2_om_node_t *temp_node = NULL;
     
     AXIS2_ENV_CHECK(env, AXIS2_FAILURE);
     
@@ -537,10 +538,15 @@
         break;
     }
     
-    /* serialize children of this node */
-    if(NULL != node_impl->first_child)
-            status =  axis2_om_node_serialize(node_impl->first_child, env, om_output);
 
+    temp_node = node_impl->first_child;
+    /* serialize children of this node */
+    while(NULL != temp_node)
+    {
+        status =  axis2_om_node_serialize(temp_node, env, om_output);
+        temp_node = AXIS2_OM_NODE_GET_NEXT_SIBLING(temp_node, env);
+    }
+    
     switch (node_impl->node_type)
     {
     case AXIS2_OM_ELEMENT:
@@ -558,10 +564,7 @@
     default:
         break;
     }
-    /* serialize next sibling */  
-    if(NULL != node_impl->next_sibling)    
-        status = axis2_om_node_serialize(node_impl->next_sibling, env, om_output);
-    
+  
     return status;
 }
 

Modified: webservices/axis2/trunk/c/modules/xml/parser/libxml2/libxml2_reader_wrapper.c
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/c/modules/xml/parser/libxml2/libxml2_reader_wrapper.c?rev=391581&r1=391580&r2=391581&view=diff
==============================================================================
--- webservices/axis2/trunk/c/modules/xml/parser/libxml2/libxml2_reader_wrapper.c (original)
+++ webservices/axis2/trunk/c/modules/xml/parser/libxml2/libxml2_reader_wrapper.c Wed Apr  5 03:57:18 2006
@@ -434,7 +434,7 @@
 	axis2_libxml2_reader_wrapper_impl_t *wrapper_impl = NULL;
     
     AXIS2_ENV_CHECK( env, NULL);
-    AXIS2_PARAM_CHECK((*env)->error, buffer , AXIS2_FAILURE);
+    AXIS2_PARAM_CHECK((*env)->error, buffer , NULL);
         
     wrapper_impl = (axis2_libxml2_reader_wrapper_impl_t*)AXIS2_MALLOC((*env)->allocator,
          sizeof(axis2_libxml2_reader_wrapper_impl_t));

Modified: webservices/axis2/trunk/c/modules/xml/parser/libxml2/libxml2_writer_wrapper.c
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/c/modules/xml/parser/libxml2/libxml2_writer_wrapper.c?rev=391581&r1=391580&r2=391581&view=diff
==============================================================================
--- webservices/axis2/trunk/c/modules/xml/parser/libxml2/libxml2_writer_wrapper.c (original)
+++ webservices/axis2/trunk/c/modules/xml/parser/libxml2/libxml2_writer_wrapper.c Wed Apr  5 03:57:18 2006
@@ -21,17 +21,64 @@
 #include <axis2_xml_writer.h>
 #include <axis2_string.h>
 #include <string.h>
+#include <axis2_stack.h>
+#include <axis2_hash.h>
+#include <axis2_array_list.h>
 
 /*******************************************************************************/
 
-/** TODO namespace validation in element scope */
-/******************************************************************************/
 #define ENCODING "ISO-8859-1"
 
+#define AXIS2_XMLNS_NAMESPACE_URI "http://www.w3.org/XML/1998/namespace"
+#define AXIS2_XMLNS_PREFIX "xml"
+
 #define AXIS2_LIBXML2_WRITER_MEMORY 1
 #define AXIS2_LIBXML2_WRITER_FILE   2
 
+/************************ structures *****************************************/
 
+typedef struct uri_prefix_element
+{
+    axis2_char_t *prefix;
+    
+    axis2_char_t *uri;
+    
+    axis2_char_t *key;
+    
+}uri_prefix_element_t;
+
+typedef struct axis2_libxml2_writer_wrapper_impl
+{
+    axis2_xml_writer_t writer;
+    
+    xmlTextWriterPtr xml_writer;
+    
+    xmlBufferPtr buffer;
+    
+    int writer_type;
+    
+    axis2_char_t *encoding;
+    
+    int is_prefix_defaulting;
+    
+    int compression;
+
+    axis2_stack_t *stack;
+    
+    axis2_bool_t in_empty_element;
+    
+    axis2_bool_t in_start_element;
+    
+    axis2_hash_t *uri_prefix_map;
+    
+    uri_prefix_element_t *default_lang_namespace;
+    
+}axis2_libxml2_writer_wrapper_impl_t;
+
+
+/***************************** Macros ******************************************/
+
+#define AXIS2_INTF_TO_IMPL(p) ((axis2_libxml2_writer_wrapper_impl_t*)p)
 
 
 /*********************** function prototypes ***********************************/
@@ -213,50 +260,49 @@
 axis2_char_t* AXIS2_CALL
 axis2_libxml2_writer_wrapper_get_xml(axis2_xml_writer_t *writer,
                                      axis2_env_t **env);
-
-static axis2_bool_t 
-axis2_libxml2_writer_wrapper_validate_namespace(axis2_xml_writer_t *writer,
-                                         axis2_env_t **env,
-                                         axis2_char_t *ns_uri,
-                                         axis2_char_t *prefix);
-static axis2_status_t 
-axis2_libxml2_writer_wrapper_reset(axis2_xml_writer_t *writer,
-                                   axis2_env_t **env);
-
-                                   
-                                                                            
-
-
+                                     
+/*********************** static functions ************************************/
+static axis2_status_t
+axis2_libxml2_writer_wrapper_pop_context(axis2_xml_writer_t *writer,
+                                         axis2_env_t **env);
+                                         
+static axis2_status_t
+axis2_libxml2_writer_wrapper_push(axis2_xml_writer_t *writer, 
+                                  axis2_env_t **env,
+                                  axis2_char_t *uri,
+                                  axis2_char_t *prefix);
+                                  
+static axis2_bool_t
+axis2_libxml2_writer_wrapper_is_namespace_declared(axis2_xml_writer_t *writer,
+                                             axis2_env_t **env,
+                                             axis2_char_t *key);
+                                             
+static axis2_status_t
+uri_prefix_element_free(uri_prefix_element_t *up_element,
+                        axis2_env_t **env);
+                                             
+static uri_prefix_element_t *
+uri_prefix_element_create(axis2_env_t **env,
+                          axis2_char_t *uri,
+                          axis2_char_t *prefix,
+                          axis2_char_t *key);    
+                          
+static axis2_status_t
+axis2_libxml2_writer_wrapper_push_context(axis2_xml_writer_t *writer,
+                                          axis2_env_t **env);                  
+                                          
+static axis2_char_t *
+create_key_from_uri_prefix(axis2_env_t **env,
+                           axis2_char_t *uri,
+                           axis2_char_t *prefix);
+                                                                                                static axis2_status_t
+axis2_libxml2_writer_wrapper_set_default_lang_namespace(
+                            axis2_xml_writer_t *writer,
+                            axis2_env_t **env);
+                                                     
 /**************************** end function pointers ****************************/
-typedef struct axis2_qname_array
-{
-    int allocated;
-    int current_no;
-    axis2_char_t **prefix;
-    axis2_char_t **uri;
-}axis2_qname_array_t;
-
-
-
-typedef struct axis2_libxml2_writer_wrapper_impl
-{
-    axis2_xml_writer_t writer;
-    xmlTextWriterPtr xml_writer;
-    xmlBufferPtr buffer;
-    int writer_type;
-    axis2_char_t *encoding;
-    int is_prefix_defaulting;
-    int compression;
-    axis2_qname_array_t qname_array;
-    
-}axis2_libxml2_writer_wrapper_impl_t;
 
 
-/***************************** Macros ******************************************/
-
-#define AXIS2_INTF_TO_IMPL(p) ((axis2_libxml2_writer_wrapper_impl_t*)p)
-
-/****************************** End macro **************************************/
 
 
 AXIS2_DECLARE(axis2_xml_writer_t *)
@@ -287,36 +333,44 @@
     }
     writer_impl->buffer = NULL;
     writer_impl->encoding = NULL;
-    
-    
-    if(encoding)
+    writer_impl->compression = 0;
+    writer_impl->in_empty_element = AXIS2_FALSE;
+    writer_impl->in_start_element = AXIS2_FALSE;
+    writer_impl->stack = NULL;
+    writer_impl->uri_prefix_map = NULL;
+    writer_impl->default_lang_namespace = NULL;
+    writer_impl->writer.ops = NULL;
+
+    writer_impl->writer_type = AXIS2_LIBXML2_WRITER_FILE;   
+    writer_impl->compression = compression;
+ 
+    if(NULL != encoding)
         writer_impl->encoding = AXIS2_STRDUP(encoding , env);
     else
         writer_impl->encoding = AXIS2_STRDUP(ENCODING, env);
      
-    /********** allocate qname array 10 default size ******************************/
-    writer_impl->qname_array.prefix = AXIS2_MALLOC((*env)->allocator,
-                                        sizeof(axis2_char_t*)*10);
-    writer_impl->qname_array.uri = AXIS2_MALLOC((*env)->allocator,
-                                        sizeof(axis2_char_t*)*10);                                        
-    if(!(writer_impl->qname_array.uri) || !(writer_impl->qname_array.prefix))
+
+    writer_impl->uri_prefix_map = axis2_hash_make(env);
+    if(!(writer_impl->uri_prefix_map))
     {
         axis2_libxml2_writer_wrapper_free(&(writer_impl->writer), env);
-    
-        AXIS2_ERROR_SET((*env)->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE);
+        AXIS2_ERROR_SET((*env)->error, 
+            AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE);
+        
         return NULL;
-    }                                       
-    
-    writer_impl->qname_array.allocated = 10;
-    writer_impl->qname_array.current_no = 0;
+    }
+    writer_impl->stack = axis2_stack_create(env);
+    if(!(writer_impl->stack))
+    {
+        axis2_libxml2_writer_wrapper_free(&(writer_impl->writer), env);
+        AXIS2_ERROR_SET((*env)->error, 
+            AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE);
+        
+        return NULL;
+    }
     
-      
-    /*************************************************************************/  
-    writer_impl->compression = compression;
-    /* writer type */
-    writer_impl->writer_type = AXIS2_LIBXML2_WRITER_FILE;   
+    axis2_libxml2_writer_wrapper_set_default_lang_namespace(&(writer_impl->writer), env);
     
-    writer_impl->writer.ops = NULL;
     writer_impl->writer.ops = (axis2_xml_writer_ops_t*)AXIS2_MALLOC((*env)->allocator,
                                     sizeof(axis2_xml_writer_ops_t));
     
@@ -327,63 +381,93 @@
         return NULL;
     }
     /* ops */
-    writer_impl->writer.ops->free = axis2_libxml2_writer_wrapper_free;
-    writer_impl->writer.ops->write_start_element = axis2_libxml2_writer_wrapper_write_start_element;
+    writer_impl->writer.ops->free = 
+            axis2_libxml2_writer_wrapper_free;
+        
+    writer_impl->writer.ops->write_start_element = 
+            axis2_libxml2_writer_wrapper_write_start_element;
+        
     writer_impl->writer.ops->write_start_element_with_namespace =
             axis2_libxml2_writer_wrapper_write_start_element_with_namespace;
+            
     writer_impl->writer.ops->write_start_element_with_namespace_prefix = 
             axis2_libxml2_writer_wrapper_write_start_element_with_namespace_prefix;
     
-    writer_impl->writer.ops->write_empty_element = axis2_libxml2_writer_wrapper_write_empty_element;
+    writer_impl->writer.ops->write_empty_element = 
+            axis2_libxml2_writer_wrapper_write_empty_element;
+        
     writer_impl->writer.ops->write_empty_element_with_namespace  =
             axis2_libxml2_writer_wrapper_write_empty_element_with_namespace;
+            
     writer_impl->writer.ops->write_empty_element_with_namespace_prefix =
             axis2_libxml2_writer_wrapper_write_empty_element_with_namespace_prefix;
     
     writer_impl->writer.ops->write_end_element = 
             axis2_libxml2_writer_wrapper_write_end_element;
+            
     writer_impl->writer.ops->write_end_document = 
             axis2_libxml2_writer_wrapper_write_end_document;
     
     writer_impl->writer.ops->write_attribute = 
             axis2_libxml2_writer_wrapper_write_attribute;
+            
     writer_impl->writer.ops->write_attribute_with_namespace =
             axis2_libxml2_writer_wrapper_write_attribute_with_namespace;
+            
     writer_impl->writer.ops->write_attribute_with_namespace_prefix =
             axis2_libxml2_writer_wrapper_write_attribute_with_namespace_prefix;
+            
     writer_impl->writer.ops->write_namespace = 
             axis2_libxml2_writer_wrapper_write_namespace;
+            
     writer_impl->writer.ops->write_default_namespace =
             axis2_libxml2_writer_wrapper_write_default_namespace;
+            
     writer_impl->writer.ops->write_comment = 
             axis2_libxml2_writer_wrapper_write_comment;
+            
     writer_impl->writer.ops->write_processing_instruction = 
             axis2_libxml2_writer_wrapper_write_processing_instruction;
+            
     writer_impl->writer.ops->write_processing_instruction_data = 
             axis2_libxml2_writer_wrapper_write_processing_instruction_data;
+            
     writer_impl->writer.ops->write_cdata = 
             axis2_libxml2_writer_wrapper_write_cdata;
+            
     writer_impl->writer.ops->write_dtd = 
             axis2_libxml2_writer_wrapper_write_dtd;
+            
     writer_impl->writer.ops->write_entity_ref = 
             axis2_libxml2_writer_wrapper_write_entity_ref;
+            
     writer_impl->writer.ops->write_start_document = 
             axis2_libxml2_writer_wrapper_write_start_document;
+            
     writer_impl->writer.ops->write_start_document_with_version = 
             axis2_libxml2_writer_wrapper_write_start_document_with_version;
+            
     writer_impl->writer.ops->write_start_document_with_version_encoding = 
             axis2_libxml2_writer_wrapper_write_start_document_with_version_encoding;
+            
     writer_impl->writer.ops->write_characters = 
             axis2_libxml2_writer_wrapper_write_characters;
+            
     writer_impl->writer.ops->get_prefix =
             axis2_libxml2_writer_wrapper_get_prefix;
-    writer_impl->writer.ops->set_prefix = axis2_libxml2_writer_wrapper_set_prefix;
+            
+    writer_impl->writer.ops->set_prefix = 
+            axis2_libxml2_writer_wrapper_set_prefix;
+            
     writer_impl->writer.ops->set_default_prefix = 
             axis2_libxml2_writer_wrapper_set_default_prefix;
+            
     writer_impl->writer.ops->write_encoded = 
-            axis2_libxml2_writer_wrapper_write_encoded;    
+            axis2_libxml2_writer_wrapper_write_encoded; 
+               
     writer_impl->writer.ops->get_xml =
-            axis2_libxml2_writer_wrapper_get_xml;            
+            axis2_libxml2_writer_wrapper_get_xml;    
+                    
     return &(writer_impl->writer);
 }
 
@@ -408,9 +492,14 @@
     writer_impl->writer.ops = NULL;
     writer_impl->encoding = NULL;
     writer_impl->buffer = NULL;
-    writer_impl->qname_array.prefix = NULL;
-    writer_impl->qname_array.uri = NULL;
+    writer_impl->in_empty_element = AXIS2_FALSE;
+    writer_impl->in_start_element = AXIS2_FALSE;
+    writer_impl->stack = NULL;
+    writer_impl->uri_prefix_map = NULL;
+    writer_impl->default_lang_namespace = NULL;
+    
     writer_impl->writer_type = AXIS2_LIBXML2_WRITER_MEMORY;
+    writer_impl->compression = compression;
     
     
     writer_impl->buffer = xmlBufferCreate();
@@ -434,25 +523,26 @@
     else
         writer_impl->encoding = AXIS2_STRDUP(ENCODING, env);
      
-    /********** allocate qname array 10 default size ******************************/
-    writer_impl->qname_array.prefix = AXIS2_MALLOC((*env)->allocator,
-                                        sizeof(axis2_char_t*)*10);
-    writer_impl->qname_array.uri = AXIS2_MALLOC((*env)->allocator,
-                                        sizeof(axis2_char_t*)*10);                                        
-    if(!(writer_impl->qname_array.uri) || !(writer_impl->qname_array.prefix))
+    
+    writer_impl->uri_prefix_map = axis2_hash_make(env);
+    if(!(writer_impl->uri_prefix_map))
     {
         axis2_libxml2_writer_wrapper_free(&(writer_impl->writer), env);
-    
-        AXIS2_ERROR_SET((*env)->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE);
+        AXIS2_ERROR_SET((*env)->error, 
+            AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE);
+        
         return NULL;
-    }                                       
-    
-    writer_impl->qname_array.allocated = 10;
-    writer_impl->qname_array.current_no = 0;
-    /*************************************************************************/  
-    
-    writer_impl->compression = compression;
+    }
+    writer_impl->stack = axis2_stack_create(env);
+    if(!(writer_impl->stack))
+    {
+        axis2_libxml2_writer_wrapper_free(&(writer_impl->writer), env);
+        AXIS2_ERROR_SET((*env)->error, 
+            AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE);
+        return NULL;
+    }
     
+    axis2_libxml2_writer_wrapper_set_default_lang_namespace(&(writer_impl->writer), env);
     
     writer_impl->writer.ops = (axis2_xml_writer_ops_t*)AXIS2_MALLOC((*env)->allocator,
                                     sizeof(axis2_xml_writer_ops_t));
@@ -464,65 +554,93 @@
     }
     
     /* ops */
-    writer_impl->writer.ops->free = axis2_libxml2_writer_wrapper_free;
+    writer_impl->writer.ops->free = 
+            axis2_libxml2_writer_wrapper_free;
+            
     writer_impl->writer.ops->write_start_element = 
             axis2_libxml2_writer_wrapper_write_start_element;
+            
     writer_impl->writer.ops->write_start_element_with_namespace =
             axis2_libxml2_writer_wrapper_write_start_element_with_namespace;
+            
     writer_impl->writer.ops->write_start_element_with_namespace_prefix = 
             axis2_libxml2_writer_wrapper_write_start_element_with_namespace_prefix;
     
     writer_impl->writer.ops->write_empty_element =
             axis2_libxml2_writer_wrapper_write_empty_element;
+            
     writer_impl->writer.ops->write_empty_element_with_namespace  =
             axis2_libxml2_writer_wrapper_write_empty_element_with_namespace;
+            
     writer_impl->writer.ops->write_empty_element_with_namespace_prefix =
             axis2_libxml2_writer_wrapper_write_empty_element_with_namespace_prefix;
     
     writer_impl->writer.ops->write_end_element = 
             axis2_libxml2_writer_wrapper_write_end_element;
+            
     writer_impl->writer.ops->write_end_document = 
             axis2_libxml2_writer_wrapper_write_end_document;
     
     writer_impl->writer.ops->write_attribute = 
             axis2_libxml2_writer_wrapper_write_attribute;
+            
     writer_impl->writer.ops->write_attribute_with_namespace =
             axis2_libxml2_writer_wrapper_write_attribute_with_namespace;
+            
     writer_impl->writer.ops->write_attribute_with_namespace_prefix =
             axis2_libxml2_writer_wrapper_write_attribute_with_namespace_prefix;
+            
     writer_impl->writer.ops->write_namespace = 
             axis2_libxml2_writer_wrapper_write_namespace;
+            
     writer_impl->writer.ops->write_default_namespace =
             axis2_libxml2_writer_wrapper_write_default_namespace;
+            
     writer_impl->writer.ops->write_comment = 
             axis2_libxml2_writer_wrapper_write_comment;
+            
     writer_impl->writer.ops->write_processing_instruction = 
             axis2_libxml2_writer_wrapper_write_processing_instruction;
+            
     writer_impl->writer.ops->write_processing_instruction_data = 
             axis2_libxml2_writer_wrapper_write_processing_instruction_data;
+            
     writer_impl->writer.ops->write_cdata = 
             axis2_libxml2_writer_wrapper_write_cdata;
+            
     writer_impl->writer.ops->write_dtd = 
             axis2_libxml2_writer_wrapper_write_dtd;
+            
     writer_impl->writer.ops->write_entity_ref = 
             axis2_libxml2_writer_wrapper_write_entity_ref;
+            
     writer_impl->writer.ops->write_start_document = 
             axis2_libxml2_writer_wrapper_write_start_document;
+            
     writer_impl->writer.ops->write_start_document_with_version = 
             axis2_libxml2_writer_wrapper_write_start_document_with_version;
+            
     writer_impl->writer.ops->write_start_document_with_version_encoding = 
             axis2_libxml2_writer_wrapper_write_start_document_with_version_encoding;
+            
     writer_impl->writer.ops->write_characters = 
             axis2_libxml2_writer_wrapper_write_characters;
+            
     writer_impl->writer.ops->get_prefix =
             axis2_libxml2_writer_wrapper_get_prefix;
-    writer_impl->writer.ops->set_prefix = axis2_libxml2_writer_wrapper_set_prefix;
+            
+    writer_impl->writer.ops->set_prefix = 
+            axis2_libxml2_writer_wrapper_set_prefix;
+            
     writer_impl->writer.ops->set_default_prefix = 
             axis2_libxml2_writer_wrapper_set_default_prefix;
+            
     writer_impl->writer.ops->write_encoded = 
             axis2_libxml2_writer_wrapper_write_encoded;
+            
     writer_impl->writer.ops->get_xml =
-            axis2_libxml2_writer_wrapper_get_xml;                 
+            axis2_libxml2_writer_wrapper_get_xml;
+                             
     return &(writer_impl->writer);
 }
 
@@ -535,28 +653,32 @@
     AXIS2_ENV_CHECK( env, AXIS2_FAILURE);
     writer_impl = AXIS2_INTF_TO_IMPL(writer);
 
-   
- 
-           
-    if(writer_impl->encoding)
+    if(NULL != writer_impl->encoding)
     {
         AXIS2_FREE((*env)->allocator, writer_impl->encoding);
         writer_impl->encoding = NULL;
     }
-    if(writer_impl->qname_array.current_no >0)
-        axis2_libxml2_writer_wrapper_reset(writer, env);
-    
-    AXIS2_FREE((*env)->allocator, writer_impl->qname_array.prefix);
-    AXIS2_FREE((*env)->allocator, writer_impl->qname_array.uri);
-    writer_impl->qname_array.prefix = NULL;
-    writer_impl->qname_array.prefix = NULL;
-
-    
-    if(writer->ops)
+    if(NULL != writer_impl->uri_prefix_map)
+    {
+        axis2_hash_free(writer_impl->uri_prefix_map, env);
+        writer_impl->uri_prefix_map = NULL;
+    }
+    if(NULL != writer_impl->stack)
+    {
+        AXIS2_STACK_FREE(writer_impl->stack, env);
+        writer_impl->stack = NULL;
+    }
+    if(NULL != writer_impl->default_lang_namespace)
+    {
+        uri_prefix_element_free(writer_impl->default_lang_namespace, env);
+        writer_impl->default_lang_namespace = NULL;
+    }
+    if(NULL != writer->ops)
     {
         AXIS2_FREE((*env)->allocator, writer->ops);
         writer->ops = NULL;
     }
+    
     AXIS2_FREE((*env)->allocator, writer_impl);
     writer_impl = NULL;
     return AXIS2_SUCCESS;
@@ -574,8 +696,9 @@
     AXIS2_PARAM_CHECK((*env)->error, localname, AXIS2_FAILURE);
     writer_impl = AXIS2_INTF_TO_IMPL(writer);
     
-    axis2_libxml2_writer_wrapper_reset(writer, env);
-    
+    axis2_libxml2_writer_wrapper_push_context(writer, env);
+    writer_impl->in_start_element = AXIS2_TRUE;
+
     status =  xmlTextWriterStartElement(writer_impl->xml_writer,(xmlChar *)localname);
     if(status < 0)
     {
@@ -604,18 +727,26 @@
 {
     axis2_libxml2_writer_wrapper_impl_t *writer_impl = NULL;
     int status = 0;
+    axis2_bool_t declared = AXIS2_FALSE;
+    
     AXIS2_ENV_CHECK( env, AXIS2_FAILURE);
     AXIS2_PARAM_CHECK((*env)->error, localname, AXIS2_FAILURE);
     AXIS2_PARAM_CHECK((*env)->error,namespace_uri, AXIS2_FAILURE);
     
     writer_impl = AXIS2_INTF_TO_IMPL(writer);
-    axis2_libxml2_writer_wrapper_reset(writer, env);
-
-    axis2_libxml2_writer_wrapper_validate_namespace(writer, env, namespace_uri, NULL); 
-
+    
+    axis2_libxml2_writer_wrapper_push_context(writer, env);
+    declared = axis2_libxml2_writer_wrapper_is_namespace_declared(writer, env, namespace_uri);
+    
+    if(declared == AXIS2_FALSE)
+    {
+        /** this should be the case all the time */
+        axis2_libxml2_writer_wrapper_push(writer, env, namespace_uri, NULL);
+        writer_impl->in_start_element = AXIS2_TRUE;
+    }
     status = xmlTextWriterStartElementNS(writer_impl->xml_writer
                 , NULL, BAD_CAST localname, BAD_CAST namespace_uri);
-    
+
     if(status < 0)
     {
         AXIS2_ERROR_SET((*env)->error,
@@ -635,26 +766,46 @@
 {
     axis2_libxml2_writer_wrapper_impl_t *writer_impl = NULL;
     int status = 0;
+    axis2_bool_t is_declared = AXIS2_FALSE;
+    axis2_char_t *key = NULL;
+    
     AXIS2_ENV_CHECK( env, AXIS2_FAILURE);
     AXIS2_PARAM_CHECK((*env)->error, localname,  AXIS2_FAILURE);
     AXIS2_PARAM_CHECK((*env)->error, namespace_uri, AXIS2_FAILURE);
     AXIS2_PARAM_CHECK((*env)->error, prefix, AXIS2_FAILURE);
     
     writer_impl = AXIS2_INTF_TO_IMPL(writer);
-    axis2_libxml2_writer_wrapper_reset(writer, env);
-
-    /**
-        we intentionally write a null namespace_uri 
-        to avoid namespace duplication since wrapper does not
-        do namespace validation
-    */
-
-   /* axis2_libxml2_writer_wrapper_validate_namespace(writer, env, namespace_uri, prefix);
-    */
-    status = xmlTextWriterStartElementNS(writer_impl->xml_writer,
+   
+    axis2_libxml2_writer_wrapper_push_context(writer, env);
+    writer_impl->in_start_element = AXIS2_TRUE;
+    
+    key = create_key_from_uri_prefix(env, namespace_uri, prefix);
+    
+    is_declared = axis2_libxml2_writer_wrapper_is_namespace_declared(writer, env, key);
+    
+    if(NULL != key)
+    {
+        AXIS2_FREE((*env)->allocator, key);
+        key = NULL;
+    }
+    if(is_declared == AXIS2_TRUE)
+    {
+        status = xmlTextWriterStartElementNS(writer_impl->xml_writer,
                                         BAD_CAST prefix,
                                         BAD_CAST localname, 
                                         BAD_CAST NULL);
+    } 
+    else
+    {
+        axis2_libxml2_writer_wrapper_push(writer, env, namespace_uri, prefix);
+        
+        status = xmlTextWriterStartElementNS(writer_impl->xml_writer,
+                                        BAD_CAST prefix,
+                                        BAD_CAST localname, 
+                                        BAD_CAST namespace_uri);
+    
+    
+    }                                       
     if(status < 0)
     {
         AXIS2_ERROR_SET((*env)->error,
@@ -675,8 +826,7 @@
     AXIS2_ENV_CHECK( env, AXIS2_FAILURE);
     AXIS2_PARAM_CHECK((*env)->error, localname, AXIS2_FAILURE);
     writer_impl = AXIS2_INTF_TO_IMPL(writer);
-
-    axis2_libxml2_writer_wrapper_reset(writer, env);
+        
     status =  xmlTextWriterStartElement(writer_impl->xml_writer,(xmlChar *)localname);
 
     if(status < 0)
@@ -707,8 +857,6 @@
     AXIS2_PARAM_CHECK((*env)->error,namespace_uri, AXIS2_FAILURE);
     
     writer_impl = AXIS2_INTF_TO_IMPL(writer);
-    axis2_libxml2_writer_wrapper_reset(writer, env);
-    axis2_libxml2_writer_wrapper_validate_namespace(writer, env, namespace_uri, NULL);
     
     status = xmlTextWriterStartElementNS(writer_impl->xml_writer
                 , NULL, BAD_CAST localname, BAD_CAST namespace_uri);
@@ -740,23 +888,38 @@
 {
     axis2_libxml2_writer_wrapper_impl_t *writer_impl = NULL;
     int status = 0;
+    axis2_bool_t is_declared = AXIS2_FALSE;
+    axis2_char_t *key = NULL;
     AXIS2_ENV_CHECK( env, AXIS2_FAILURE);
     AXIS2_PARAM_CHECK((*env)->error, localname,  AXIS2_FAILURE);
     AXIS2_PARAM_CHECK((*env)->error, namespace_uri, AXIS2_FAILURE);
     AXIS2_PARAM_CHECK((*env)->error, prefix, AXIS2_FAILURE);
     
     writer_impl = AXIS2_INTF_TO_IMPL(writer);
-    axis2_libxml2_writer_wrapper_reset(writer, env);
-    /**
-        we intentionally write a null namespace uri to avoid namespace
-        duplication 
-    axis2_libxml2_writer_wrapper_validate_namespace(writer, env, namespace_uri, prefix);
-    */
-    status = xmlTextWriterStartElementNS(writer_impl->xml_writer,
+    
+    key = create_key_from_uri_prefix(env, namespace_uri, prefix);
+    
+    is_declared = axis2_libxml2_writer_wrapper_is_namespace_declared(writer, env, key);
+    
+    if(NULL != key)
+    {
+        AXIS2_FREE((*env)->allocator, key);
+        key = NULL;
+    }
+    if(is_declared == AXIS2_TRUE)
+    {
+        status = xmlTextWriterStartElementNS(writer_impl->xml_writer,
                                         BAD_CAST prefix,
                                         BAD_CAST localname, 
                                         BAD_CAST NULL);
-                                        
+    }
+    else
+    {
+        status = xmlTextWriterStartElementNS(writer_impl->xml_writer,
+                                        BAD_CAST prefix,
+                                        BAD_CAST localname, 
+                                        BAD_CAST namespace_uri);
+    }                                    
     if(status < 0)
     {
         AXIS2_ERROR_SET((*env)->error,
@@ -783,6 +946,11 @@
     AXIS2_ENV_CHECK( env, AXIS2_FAILURE);
     
     writer_impl = AXIS2_INTF_TO_IMPL(writer);
+    
+    axis2_libxml2_writer_wrapper_pop_context(writer, env);
+    
+    writer_impl->in_start_element = AXIS2_FALSE;
+    
     status = xmlTextWriterFullEndElement(writer_impl->xml_writer);
     if(status < 0)
     {
@@ -858,16 +1026,22 @@
     
     writer_impl = AXIS2_INTF_TO_IMPL(writer);
     
-    exists = axis2_libxml2_writer_wrapper_validate_namespace(writer, env, namespace_uri, NULL);
+    exists = axis2_libxml2_writer_wrapper_is_namespace_declared(writer, env, namespace_uri);
+
     if(exists == AXIS2_TRUE)
+    {
         status = xmlTextWriterWriteAttributeNS(writer_impl->xml_writer,
                         NULL, BAD_CAST localname, BAD_CAST NULL,
                         BAD_CAST value);
-    else                   
+    }
+    else
+    {
+        axis2_libxml2_writer_wrapper_push(writer, env, namespace_uri, NULL);
+                           
         status = xmlTextWriterWriteAttributeNS(writer_impl->xml_writer,
                         NULL, BAD_CAST localname, BAD_CAST namespace_uri,
                         BAD_CAST value);
-                    
+    }                
     if(status < 0)
     {
         AXIS2_ERROR_SET((*env)->error,
@@ -889,6 +1063,8 @@
 {
     axis2_libxml2_writer_wrapper_impl_t *writer_impl = NULL;
     int status = 0;
+    axis2_bool_t is_declared = AXIS2_FALSE;
+    axis2_char_t *key = NULL;
     
     AXIS2_ENV_CHECK( env, AXIS2_FAILURE);
     AXIS2_PARAM_CHECK((*env)->error, localname,  AXIS2_FAILURE);
@@ -897,23 +1073,31 @@
     AXIS2_PARAM_CHECK((*env)->error, prefix, AXIS2_FAILURE);
         
     writer_impl = AXIS2_INTF_TO_IMPL(writer);
-    /*
-    we intentionally write null namespace uri to avoid namespace duplication
     
-    exists = axis2_libxml2_writer_wrapper_validate_namespace(writer, env, namespace_uri, prefix);
-    if(exists == AXIS2_TRUE)
-            status = xmlTextWriterWriteAttributeNS(writer_impl->xml_writer,
+    key = create_key_from_uri_prefix(env, namespace_uri, prefix);
+    
+    is_declared = axis2_libxml2_writer_wrapper_is_namespace_declared(writer, env, key);
+    if(NULL != key)
+    {
+        AXIS2_FREE((*env)->allocator, key);
+        key = NULL;
+    }
+    
+    if(is_declared == AXIS2_TRUE)
+    {
+         status = xmlTextWriterWriteAttributeNS(writer_impl->xml_writer,
                     BAD_CAST prefix , BAD_CAST localname, 
                         BAD_CAST NULL , BAD_CAST value);
-    else                        
+    }
+    else
+    {
+        axis2_libxml2_writer_wrapper_push(writer, env, namespace_uri, prefix);
+                                
         status = xmlTextWriterWriteAttributeNS(writer_impl->xml_writer,
                     BAD_CAST prefix , BAD_CAST localname, 
                         BAD_CAST namespace_uri , BAD_CAST value);
-     */
-    status = xmlTextWriterWriteAttributeNS(writer_impl->xml_writer,
-                    BAD_CAST prefix , BAD_CAST localname, 
-                        BAD_CAST NULL , BAD_CAST value);
-                  
+     
+    }              
     if(status < 0)
     {
         AXIS2_ERROR_SET((*env)->error,
@@ -933,30 +1117,51 @@
 {
     axis2_libxml2_writer_wrapper_impl_t *writer_impl = NULL;
     int status = 0;
-    int exists = AXIS2_FALSE;
+    int is_declared = AXIS2_FALSE;
+    axis2_char_t *key = NULL;
     char *xmlnsprefix = NULL;
+    
     AXIS2_ENV_CHECK( env, AXIS2_FAILURE);
     AXIS2_PARAM_CHECK((*env)->error, namespace_uri, AXIS2_FAILURE);
-    AXIS2_PARAM_CHECK((*env)->error, prefix , AXIS2_FAILURE);
+    /* AXIS2_PARAM_CHECK((*env)->error, prefix , AXIS2_FAILURE); */
     
     writer_impl = AXIS2_INTF_TO_IMPL(writer);
-    exists = axis2_libxml2_writer_wrapper_validate_namespace(writer, env, 
-                                namespace_uri, prefix);
-
-    if(exists == AXIS2_TRUE)
-        return AXIS2_SUCCESS;                                
-    
-    xmlnsprefix = (axis2_char_t*)AXIS2_MALLOC((*env)->allocator,
-                    (sizeof(char)* (strlen(prefix) +7)));
-    sprintf(xmlnsprefix,"xmlns:%s",prefix);
     
+    key = create_key_from_uri_prefix(env, namespace_uri, prefix);
     
-    status = xmlTextWriterWriteAttribute(writer_impl->xml_writer,
-                   BAD_CAST xmlnsprefix, BAD_CAST namespace_uri);
-    AXIS2_FREE((*env)->allocator, xmlnsprefix);
-    xmlnsprefix = NULL;
-                       
     
+    is_declared = axis2_libxml2_writer_wrapper_is_namespace_declared(writer, env, key);
+
+    if(NULL != key)
+    {
+        AXIS2_FREE((*env)->allocator, key);
+        key = NULL;
+    }
+
+    if(is_declared == AXIS2_TRUE)
+    {
+        return AXIS2_SUCCESS;
+    }
+    else
+    {
+        axis2_libxml2_writer_wrapper_push(writer, env, namespace_uri, prefix);
+        if(NULL != prefix)
+        {
+            xmlnsprefix = (axis2_char_t*)AXIS2_MALLOC((*env)->allocator,
+                        (sizeof(char)* (AXIS2_STRLEN(prefix) +7)));
+            sprintf(xmlnsprefix,"xmlns:%s",prefix);
+        }
+        else
+        {
+            xmlnsprefix = AXIS2_STRDUP("xmlns", env);
+        }
+        
+        status = xmlTextWriterWriteAttribute(writer_impl->xml_writer,
+                    BAD_CAST xmlnsprefix, BAD_CAST namespace_uri);
+        AXIS2_FREE((*env)->allocator, xmlnsprefix);
+        xmlnsprefix = NULL;
+                           
+    }
     if(status < 0)
     {
         AXIS2_ERROR_SET((*env)->error,
@@ -970,7 +1175,6 @@
     return AXIS2_SUCCESS;   
 }
 
-/** should be implemented */
 axis2_status_t AXIS2_CALL
 axis2_libxml2_writer_wrapper_write_default_namespace
                                             (axis2_xml_writer_t *writer,
@@ -979,25 +1183,31 @@
 {
     axis2_libxml2_writer_wrapper_impl_t *writer_impl = NULL;
     int status = 0;
-    int exists = AXIS2_FALSE;
+    axis2_bool_t is_declared = AXIS2_FALSE;
     axis2_char_t *xmlns = NULL;
     AXIS2_ENV_CHECK( env, AXIS2_FAILURE);
     AXIS2_PARAM_CHECK((*env)->error, namespace_uri, AXIS2_FAILURE)
     
-    exists = axis2_libxml2_writer_wrapper_validate_namespace(writer, env, namespace_uri, NULL);
-    if(exists == AXIS2_TRUE)
+    is_declared = axis2_libxml2_writer_wrapper_is_namespace_declared(writer, env, namespace_uri);
+ 
+    if(is_declared == AXIS2_TRUE)
     {
         /* namespace already declared , nothing to do */
         return AXIS2_SUCCESS;
     }
-    
+   
     xmlns = AXIS2_MALLOC((*env)->allocator, 
             sizeof(axis2_char_t)*(strlen("xmlns")+1));
     sprintf(xmlns,"xmlns");
     
     status = xmlTextWriterWriteAttribute(writer_impl->xml_writer,
-                   NULL , BAD_CAST namespace_uri);
-                   
+                   xmlns , BAD_CAST namespace_uri);
+    
+    if(NULL != xmlns)
+    {
+        AXIS2_FREE((*env)->allocator, xmlns);
+        xmlns = NULL;
+    }                   
     if(status < 0)
     {
         AXIS2_ERROR_SET((*env)->error, AXIS2_ERROR_WRITING_DEFAULT_NAMESPACE, AXIS2_FAILURE);
@@ -1275,131 +1485,295 @@
     return AXIS2_FAILURE;    
 }
 
-
-static axis2_status_t 
-axis2_libxml2_writer_wrapper_validate_namespace(axis2_xml_writer_t *writer,
-                                         axis2_env_t **env,
-                                         axis2_char_t *ns_uri,
-                                         axis2_char_t *prefix)
+axis2_char_t* AXIS2_CALL
+axis2_libxml2_writer_wrapper_get_xml(axis2_xml_writer_t *writer,
+                                     axis2_env_t **env)
 {
-    int i = 0;
     axis2_libxml2_writer_wrapper_impl_t *writer_impl = NULL;
-    
-    AXIS2_ENV_CHECK( env, AXIS2_FAILURE);
+    axis2_char_t *output = NULL;
     writer_impl = AXIS2_INTF_TO_IMPL(writer);
-    if(!prefix && !ns_uri)
-        return AXIS2_FAILURE;
-    
-    /* default namespace handling */
-    if(!prefix && ns_uri)
+    if(writer_impl->xml_writer)
     {
-        for(i =0; i < writer_impl->qname_array.current_no; i++)
-        {
-            if(AXIS2_STRCMP(writer_impl->qname_array.uri[i], ns_uri) == 0)
-            {
-                return AXIS2_TRUE;
-            }        
-        }
-        if(writer_impl->qname_array.current_no == writer_impl->qname_array.allocated)
-        {
-           writer_impl->qname_array.prefix = AXIS2_REALLOC((*env)->allocator,
-                                                writer_impl->qname_array.prefix,
-                                                sizeof(axis2_char_t *)*10);
-           writer_impl->qname_array.uri = AXIS2_REALLOC((*env)->allocator,
-                                                writer_impl->qname_array.prefix,
-                                                sizeof(axis2_char_t *)*10);
-           writer_impl->qname_array.allocated += 10;
-            
-        }
-        writer_impl->qname_array.prefix[writer_impl->qname_array.current_no] = 
-                AXIS2_STRDUP("",env);
-        writer_impl->qname_array.uri[writer_impl->qname_array.current_no] =
-                AXIS2_STRDUP(ns_uri, env);
-        writer_impl->qname_array.current_no++;                
-        return AXIS2_FALSE;
+        xmlFreeTextWriter(writer_impl->xml_writer);
+        writer_impl->xml_writer = NULL;
     }
-  
-    for(i =0; i < writer_impl->qname_array.current_no; i++)
+    if(writer_impl->writer_type == AXIS2_LIBXML2_WRITER_MEMORY)
     {
-        if(AXIS2_STRCMP(writer_impl->qname_array.prefix[i], prefix) == 0)
+
+        if(writer_impl->buffer != NULL)
         {
-            return AXIS2_TRUE;
-        }        
+           output = AXIS2_MALLOC((*env)->allocator,     
+                    sizeof(axis2_char_t)*(
+                        strlen((const axis2_char_t*)(writer_impl->buffer->content))+1));
+            sprintf(output, 
+                    ((const axis2_char_t*)(writer_impl->buffer->content)));
+    	    xmlBufferFree(writer_impl->buffer);
+    	    writer_impl->buffer = NULL;
+        }
     }
-    if(writer_impl->qname_array.current_no == writer_impl->qname_array.allocated)
+    else if(writer_impl->writer_type == AXIS2_LIBXML2_WRITER_FILE)
     {
-        writer_impl->qname_array.prefix = AXIS2_REALLOC((*env)->allocator,
-                                            writer_impl->qname_array.prefix,
-                                            sizeof(axis2_char_t *)*10);
-        writer_impl->qname_array.uri = AXIS2_REALLOC((*env)->allocator,
-                                            writer_impl->qname_array.prefix,
-                                            sizeof(axis2_char_t *)*10);
-        writer_impl->qname_array.allocated += 10;
-        
+        printf(" This is not supported for this type of writer");
     }
-    writer_impl->qname_array.prefix[writer_impl->qname_array.current_no] = 
-            AXIS2_STRDUP(prefix ,env);
-    writer_impl->qname_array.uri[writer_impl->qname_array.current_no] =
-            AXIS2_STRDUP(ns_uri, env);
-    writer_impl->qname_array.current_no++;                
-return AXIS2_FALSE;
 
+    return output;   
 }
 
-static axis2_status_t 
-axis2_libxml2_writer_wrapper_reset(axis2_xml_writer_t *writer,
-                                   axis2_env_t **env)
+static axis2_status_t
+axis2_libxml2_writer_wrapper_pop_context(axis2_xml_writer_t *writer,
+                                         axis2_env_t **env)
 {
     axis2_libxml2_writer_wrapper_impl_t *writer_impl = NULL;
+    axis2_array_list_t *ns_list = NULL;
+    int size = 0;
     int i = 0;
-    
-    AXIS2_ENV_CHECK( env, AXIS2_FAILURE);
-    
     writer_impl = AXIS2_INTF_TO_IMPL(writer);
     
-        for( i = 0; i < writer_impl->qname_array.current_no; i++)
+    ns_list = AXIS2_STACK_POP(writer_impl->stack, env);
+    if(!ns_list)
+        return AXIS2_FAILURE;
+            
+    size = AXIS2_ARRAY_LIST_SIZE(ns_list, env);
+    for(i=0; i < size; i++)
+    {
+        uri_prefix_element_t *ele = NULL;
+        void *value = NULL;
+        value = AXIS2_ARRAY_LIST_GET(ns_list, env, i);
+        if(NULL != value)
         {
-            AXIS2_FREE((*env)->allocator, writer_impl->qname_array.prefix[i]);
-            AXIS2_FREE((*env)->allocator, writer_impl->qname_array.uri[i]);
-            writer_impl->qname_array.prefix[i] = NULL;
-            writer_impl->qname_array.uri[i] = NULL;
+           ele = (uri_prefix_element_t *)value;
+           if(NULL != writer_impl->uri_prefix_map && NULL != ele->key)
+           {
+                axis2_char_t *prefix = NULL;
+                void *val = NULL;
+                
+                val = axis2_hash_get(writer_impl->uri_prefix_map, ele->key, 
+                        AXIS2_HASH_KEY_STRING);
+                if(NULL != val)
+                {
+                    /** this namespace uri and prefix should be removed*/
+                    axis2_hash_set(writer_impl->uri_prefix_map, ele->key, 
+                        AXIS2_HASH_KEY_STRING, NULL);
+                }
+            uri_prefix_element_free(ele, env);           
+           }
         }
-        
-        writer_impl->qname_array.current_no = 0;    
+    }
+    AXIS2_ARRAY_LIST_FREE(ns_list, env);
+    ns_list = NULL;
     return AXIS2_SUCCESS;
-}
-
-
-axis2_char_t* AXIS2_CALL
-axis2_libxml2_writer_wrapper_get_xml(axis2_xml_writer_t *writer,
-                                     axis2_env_t **env)
+}                                         
+                                         
+static axis2_status_t
+axis2_libxml2_writer_wrapper_push(axis2_xml_writer_t *writer, 
+                                  axis2_env_t **env,
+                                  axis2_char_t *uri,
+                                  axis2_char_t *prefix)
 {
     axis2_libxml2_writer_wrapper_impl_t *writer_impl = NULL;
-    axis2_char_t *output = NULL;
+    axis2_array_list_t *current_list = NULL;
+    axis2_char_t *key = NULL;
+    axis2_char_t *temp_prefix = NULL;
     writer_impl = AXIS2_INTF_TO_IMPL(writer);
-    if(writer_impl->xml_writer)
+    if(!prefix || AXIS2_STRCMP(prefix, "") == 0)
     {
-        xmlFreeTextWriter(writer_impl->xml_writer);
-        writer_impl->xml_writer = NULL;
+        temp_prefix = "default";
     }
-    if(writer_impl->writer_type == AXIS2_LIBXML2_WRITER_MEMORY)
+    else
     {
+        temp_prefix = prefix;
+    }
+    
+    if(NULL != writer_impl->stack)
+    {
+        current_list = (axis2_array_list_t *)
+                AXIS2_STACK_GET(writer_impl->stack, env);
+        
+        if(NULL != current_list)
+        {
+            uri_prefix_element_t *ele = NULL;
+            key = create_key_from_uri_prefix(env, uri, prefix);
+            
+            ele = uri_prefix_element_create(env, uri , temp_prefix, key);
+            if(NULL != key)
+            {
+                AXIS2_FREE((*env)->allocator, key);
+                key = NULL;
+            }
+            if(NULL != ele)
+            {
+                AXIS2_ARRAY_LIST_ADD(current_list, env, ele);
+                axis2_hash_set(writer_impl->uri_prefix_map, ele->key, 
+                    AXIS2_HASH_KEY_STRING, ele->prefix);
+            }
+        }
+    }
+    return AXIS2_SUCCESS;    
+}                                  
+                                  
+static axis2_bool_t
+axis2_libxml2_writer_wrapper_is_namespace_declared(axis2_xml_writer_t *writer,
+                                             axis2_env_t **env,
+                                             axis2_char_t *key)
+{
+    axis2_libxml2_writer_wrapper_impl_t *writer_impl = NULL;
+    AXIS2_ENV_CHECK(env, AXIS2_FALSE);
+    writer_impl = AXIS2_INTF_TO_IMPL(writer);
+    if(NULL != writer_impl->uri_prefix_map && NULL != key)
+    {
+        axis2_char_t *pre = NULL;
+        void *ret = NULL;
+        ret = axis2_hash_get(writer_impl->uri_prefix_map, key, 
+                AXIS2_HASH_KEY_STRING);
+        if(NULL != ret)
+        {
+           return AXIS2_TRUE;
+        }
+    }
+    return AXIS2_FALSE;
+} 
 
-        if(writer_impl->buffer != NULL)
+static axis2_status_t
+uri_prefix_element_free(uri_prefix_element_t *up_element,
+                        axis2_env_t **env)
+{
+    if(NULL != up_element)
+    {
+        if(NULL != up_element->uri)
         {
-           output = AXIS2_MALLOC((*env)->allocator,     
-                    sizeof(axis2_char_t)*(
-                        strlen((const axis2_char_t*)(writer_impl->buffer->content))+1));
-            sprintf(output, 
-                    ((const axis2_char_t*)(writer_impl->buffer->content)));
-    	    xmlBufferFree(writer_impl->buffer);
-    	    writer_impl->buffer = NULL;
+            AXIS2_FREE((*env)->allocator, up_element->uri);
+            up_element->uri = NULL;
+        }
+        if(NULL != up_element->prefix)
+        {
+            AXIS2_FREE((*env)->allocator, up_element->prefix);
+            up_element->prefix = NULL;
+        }
+        if(NULL != up_element->key)
+        {
+            AXIS2_FREE((*env)->allocator, up_element->key);
+            up_element->key = NULL;
         }
+        
+     AXIS2_FREE((*env)->allocator, up_element);
+     up_element = NULL;
+     return AXIS2_SUCCESS;   
     }
-    else if(writer_impl->writer_type == AXIS2_LIBXML2_WRITER_FILE)
+    return AXIS2_FAILURE;
+}                        
+                                             
+static uri_prefix_element_t *
+uri_prefix_element_create(axis2_env_t **env,
+                          axis2_char_t *uri,
+                          axis2_char_t *prefix,
+                          axis2_char_t *key)
+{
+    uri_prefix_element_t *up_element = NULL;
+    up_element = (uri_prefix_element_t *)AXIS2_MALLOC((*env)->allocator, 
+                    sizeof(uri_prefix_element_t));
+    
+    if(!uri)
+        return NULL;
+                                
+    if(!up_element)
     {
-        printf(" This is not supported for this type of writer");
+        AXIS2_ERROR_SET((*env)->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE);
+        return NULL;
     }
+    up_element->key = NULL;
+    up_element->prefix = NULL;
+    up_element->uri = NULL;
+    
+    up_element->uri = AXIS2_STRDUP(uri, env);
+    if(!up_element->uri)
+    {
+        uri_prefix_element_free(up_element, env);
+        AXIS2_ERROR_SET((*env)->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE);
+        return NULL;
+    }
+    up_element->prefix = AXIS2_STRDUP(prefix, env);
+    if(NULL != prefix && !up_element->prefix)
+    {
+        uri_prefix_element_free(up_element, env);
+        AXIS2_ERROR_SET((*env)->error , AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE);
+        return NULL;            
+    }
+    up_element->key = AXIS2_STRDUP(key, env);
+    if(NULL != key  && !up_element->key)
+    {
+        uri_prefix_element_free(up_element, env);
+        AXIS2_ERROR_SET((*env)->error, AXIS2_ERROR_NO_MEMORY, AXIS2_FAILURE);
+        return NULL;
+    }
+    return up_element;                    
+} 
 
-    return output;   
-}
+static axis2_status_t
+axis2_libxml2_writer_wrapper_push_context(axis2_xml_writer_t *writer,
+                                          axis2_env_t **env)
+{
+    axis2_libxml2_writer_wrapper_impl_t *writer_impl = NULL;
+    AXIS2_ENV_CHECK(env, AXIS2_FAILURE);
+    writer_impl = AXIS2_INTF_TO_IMPL(writer);
+    if(NULL != writer_impl->stack)
+    {
+        axis2_array_list_t *array_list = NULL;
+        array_list = axis2_array_list_create(env, 10);
+        if(NULL != array_list)
+        {
+            AXIS2_STACK_PUSH(writer_impl->stack, env, array_list);
+            return AXIS2_SUCCESS;
+        }
+    }
+    return AXIS2_FAILURE;
+}                                                                                                 
+static axis2_char_t *
+create_key_from_uri_prefix(axis2_env_t **env,
+                           axis2_char_t *uri,
+                           axis2_char_t *prefix)
+{
+    axis2_char_t *key = NULL;
+    axis2_char_t *temp_val = NULL;
+    if(!prefix || AXIS2_STRCMP(prefix, "") == 0)
+    {
+        key = AXIS2_STRDUP(uri, env);
+    }
+    else
+    {
+        temp_val = AXIS2_STRACAT(uri, "|", env);
+        key = AXIS2_STRACAT(temp_val, prefix, env);
+        AXIS2_FREE((*env)->allocator, temp_val);
+    }
+    return key;
+} 
+
+static axis2_status_t
+axis2_libxml2_writer_wrapper_set_default_lang_namespace(
+                            axis2_xml_writer_t *writer,
+                            axis2_env_t **env)
+{
+    axis2_libxml2_writer_wrapper_impl_t *writer_impl = NULL;
+    axis2_char_t *key = NULL;
+    AXIS2_ENV_CHECK(env, AXIS2_FAILURE);
+    
+    writer_impl = AXIS2_INTF_TO_IMPL(writer);
+    key = create_key_from_uri_prefix( env,
+             AXIS2_XMLNS_NAMESPACE_URI, AXIS2_XMLNS_PREFIX);        
+    
+    writer_impl->default_lang_namespace = 
+        uri_prefix_element_create(env, AXIS2_XMLNS_NAMESPACE_URI, 
+                AXIS2_XMLNS_PREFIX, key);
+    if(NULL != key)
+    {
+        AXIS2_FREE((*env)->allocator, key);
+        key = NULL;
+    }
+        
+    if(NULL != writer_impl->uri_prefix_map)
+    {
+        axis2_hash_set(writer_impl->uri_prefix_map, 
+           writer_impl->default_lang_namespace->key , 
+           AXIS2_HASH_KEY_STRING, AXIS2_XMLNS_PREFIX);
+    }
+    return AXIS2_SUCCESS;
+}                                                                    
\ No newline at end of file



Mime
View raw message