
/*
 * Licensed to the Apache Software Foundation (ASF) under one or more
 * contributor license agreements.  See the NOTICE file distributed with
 * this work for additional information regarding copyright ownership.
 * The ASF licenses this file to You 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 <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#include <guththila.h>

#define GUTHTHILA_VALIDATION_PARSER

/*
 * Read the next char from the reader and return it.
 */
static int
guththila_next_char(
    guththila_t * m,
    const axutil_env_t * env);

/* part of guththila_next_char method. this was included as macro for performance. 99% of the time
 * following will be called, so having it as next_char method is very expensive (method calling
 * overhead is higher) so, common case is checked as part of the macro and if not satisfied, method
 * is called
 */
#define GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c)\
{\
    int result_found = 0;\
    if(!buffer)\
    {\
        if(m->reader->type == GUTHTHILA_MEMORY_READER)\
        {\
            buffer = m->buffer.buff[0];\
            data_size = m->buffer.data_size[0];\
            previous_size = 0;\
        }\
        else\
        {\
            if(m->buffer.cur_buff != -1)\
            {\
                buffer = m->buffer.buff[m->buffer.cur_buff];\
                data_size = GUTHTHILA_BUFFER_CURRENT_DATA_SIZE(m->buffer);\
                previous_size = GUTHTHILA_BUFFER_PRE_DATA_SIZE(m->buffer);\
            }\
            else\
            {\
                c = guththila_next_char(m, env);\
                if(c < 0)\
                    return -1;\
                result_found  = 1;\
            }\
        }\
    }\
\
    if(!result_found)\
    {\
        size_t index = m->next++ - previous_size;\
        if(index < data_size)\
        {\
            c = buffer[index];\
        }\
        else\
        {\
            buffer = NULL;\
            data_size = -1;\
            --(m->next);\
            if(m->reader->type == GUTHTHILA_MEMORY_READER)\
            {\
                return -1;\
            }\
            else\
            {\
                c = guththila_next_char(m, env);\
                if(c < 0)\
                    return -1;\
            }\
        }\
    }\
}

/*
 * Read the specified number of characters at once.
 */
static int
guththila_next_no_char(
    guththila_t * m,
    int eof,
    guththila_char_t *bytes,
    size_t no,
    const axutil_env_t * env);

/*
 * Close a token that is opened previously. 
 */
static void
guththila_token_close(
    guththila_t * m,
    guththila_token_t * tok,
    int tok_type,
    int referer,
    const axutil_env_t * env);

/* 
 * Process the XMl declaration part of a XML document.
 */
static int
guththila_process_xml_dec(
    guththila_t * m,
    const axutil_env_t * env);

/*
 * Return non zero value if the given argument is a space. (c < 0x21) is added to improve the
 * performance. common case is printable characters. and if given character is printable, we can
 * return false immediately.
 */
#define GUTHTHILA_IS_SPACE(c) ((c < 0x21) && (c == 0x20 || c == 0xD || c == 0xA || c == 0x9))

/* 
 * Read characters until all the white spaces are read.
 */
#define GUTHTHILA_SKIP_SPACES(m, c, buffer, data_size, previous_size, _env)while(GUTHTHILA_IS_SPACE(c)){GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, _env, c);}


#define GUTHTHILA_XML_NAME "xml"

#define GUTHTHILA_XML_URI "http://www.w3.org/XML/1998/namespace"

/*
 * Open a token. When we open a token we don't know it's type. We only 
 * set the starting values.
 */
#define GUTHTHILA_TOKEN_OPEN(m, tok, _env)					\
    m->temp_tok = guththila_tok_list_get_token(&m->tokens, _env); \
    m->temp_tok->type = _Unknown; \
    m->temp_tok->_start = (int)m->next; \
    m->last_start = (int)m->next - 1;
/* We are sure that the difference lies within the int range */

/*
 * Read until we met a = character.
 */
#define GUTHTHILA_PROCESS_EQU(m, c, ic, buffer, data_size, previous_size, _env)\
{\
    GUTHTHILA_SKIP_SPACES(m, c, buffer, data_size, previous_size, _env); \
    if (c == '=')\
    { \
        GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, _env, ic); \
        GUTHTHILA_SKIP_SPACES(m, ic, buffer, data_size, previous_size, _env); \
    }\
}

/*
 * Initialize a attribute to the values given.
 */
#define GUTHTHILA_ATTRIBUTE_INITIALIZE(_attr, _pref, _name, _val)	\
    (_attr->pref = (_pref)); \
    (_attr->name = (_name)); \
    (_attr->val = (_val));

/*
 * Initialize namespace to the values given.
 */
#define GUTHTHILA_NAMESPACE_INITIALIZE(_namesp, _name, _uri)	\
    (_namesp->name = _name); \
    (_namesp->uri = _uri);

/*
 * Determine weahter a given character is a valid starting char for a xml name.
 */
#define GUTHTHILA_IS_VALID_STARTING_CHAR(c) (isalpha(c) || '_' == c || ':' == c)

/*
 * Initialize the variables in the guththila_t structure.
 */
#define GUTHTHILA_VARIABLE_INITIALZE(m) \
    m->temp_prefix = NULL; \
    m->temp_name = NULL; \
    m->temp_tok = NULL; \
    if (m->value) guththila_tok_list_release_token(&m->tokens, m->value, env); \
    m->name = NULL; \
    m->prefix = NULL; \
    m->value = NULL;

/*
 * Initialize the guththila_t structure with the reader. 
 * All the values will be set to default values. 
 */
GUTHTHILA_EXPORT int GUTHTHILA_CALL
guththila_init(
    guththila_t * m,
    void *reader,
    const axutil_env_t * env)
{
    guththila_token_t* temp_name = NULL;
    guththila_token_t* temp_tok = NULL;
    guththila_elem_namesp_t* e_namesp = NULL;

    if(!((guththila_reader_t *)reader))
        return GUTHTHILA_FAILURE;
    m->reader = (guththila_reader_t *)reader;
    if(!guththila_tok_list_init(&m->tokens, env))
    {
        return GUTHTHILA_FAILURE;
    }
    if(m->reader->type == GUTHTHILA_MEMORY_READER)
    {
        guththila_buffer_init_for_buffer(&m->buffer, m->reader->buff, m->reader->buff_size, env);
    }
    else if(m->reader->type == GUTHTHILA_FILE_READER || m->reader->type == GUTHTHILA_IO_READER)
    {
        guththila_buffer_init(&m->buffer, 0, env);
    }
    guththila_stack_init(&m->elem, env);
    guththila_stack_init(&m->attrib, env);
    guththila_stack_init(&m->namesp, env);
    temp_name = guththila_tok_list_get_token(&m->tokens, env);
    temp_tok = guththila_tok_list_get_token(&m->tokens, env);
    if(temp_tok && temp_name)
    {
        guththila_set_token(temp_name, GUTHTHILA_XML_NAME, 0, (int)strlen(GUTHTHILA_XML_NAME), 1,
            0, 0, env);

        guththila_set_token(temp_tok, GUTHTHILA_XML_URI, 0, (int)strlen(GUTHTHILA_XML_URI), 1, 0,
            0, env);

    }

    e_namesp = (guththila_elem_namesp_t *)AXIS2_MALLOC(env->allocator,
        sizeof(guththila_elem_namesp_t));
    if(e_namesp && temp_tok && temp_name)
    {
        e_namesp->namesp = (guththila_namespace_t *)AXIS2_MALLOC(env->allocator,
            sizeof(guththila_namespace_t) * GUTHTHILA_NAMESPACE_DEF_SIZE);
    }
    if(e_namesp->namesp)
    {
        e_namesp->no = 1;
        e_namesp->size = GUTHTHILA_NAMESPACE_DEF_SIZE;
        e_namesp->namesp[0].name = temp_name;
        e_namesp->namesp[0].uri = temp_tok;
        guththila_stack_push(&m->namesp, e_namesp, env);
    }
    else
    {
        if(temp_name)
        {
            AXIS2_FREE(env->allocator, temp_name);
            temp_name = NULL;
        }
        if(temp_tok)
        {
            AXIS2_FREE(env->allocator, temp_tok);
            temp_tok = NULL;
        }
        if(e_namesp)
        {
            AXIS2_FREE(env->allocator, e_namesp);
            e_namesp = NULL;
        }
        return GUTHTHILA_FAILURE;
    }
    m->name = NULL;
    m->prefix = NULL;
    m->value = NULL;
    m->status = S_1;
    m->guththila_event = -1;
    m->next = 0;
    m->last_start = -1;
    m->temp_name = NULL;
    m->temp_prefix = NULL;
    m->temp_tok = NULL;
    return GUTHTHILA_SUCCESS;
}

/*
 * Uninitialize a guththila_t structure. This method deallocates all the 
 * resources that are held in the guththila_t structure.
 */
GUTHTHILA_EXPORT int GUTHTHILA_CALL
guththila_un_init(
    guththila_t * m,
    const axutil_env_t * env)
{
    int size = 0, i = 0, j = 0;
    guththila_attr_t * attr = NULL;
    guththila_element_t* elem = NULL;
    guththila_elem_namesp_t * e_namesp = NULL;

    if(m->prefix)
    {
        guththila_tok_list_release_token(&m->tokens, m->prefix, env);
    }
    if(m->name)
    {
        guththila_tok_list_release_token(&m->tokens, m->name, env);
    }
    if(m->value)
    {
        guththila_tok_list_release_token(&m->tokens, m->value, env);
    }
    if(m->temp_tok)
    {
        guththila_tok_list_release_token(&m->tokens, m->temp_tok, env);
    }
    if(m->temp_name)
    {
        guththila_tok_list_release_token(&m->tokens, m->temp_name, env);
    }
    if(m->temp_prefix)
    {
        guththila_tok_list_release_token(&m->tokens, m->temp_prefix, env);
    }
    size = GUTHTHILA_STACK_SIZE(m->attrib);
    for(i = 0; i < size; i++)
    {
        attr = (guththila_attr_t *)guththila_stack_pop(&m->attrib, env);
        if(attr)
        {
            if(attr->name)
                guththila_tok_list_release_token(&m->tokens, attr->name, env);
            if(attr->pref)
                guththila_tok_list_release_token(&m->tokens, attr->pref, env);
            AXIS2_FREE(env->allocator, attr);
        }
    }
    guththila_stack_un_init(&m->attrib, env);

#ifndef GUTHTHILA_VALIDATION_PARSER
    guththila_namespace_t * namesp = NULL;

    size = GUTHTHILA_STACK_SIZE(m->namesp);
    for (i = 0; i < size; i++)
    {
        namesp =
        (guththila_namespace_t *) guththila_stack_pop(&m->namesp, env);
        if (namesp)
        {
            if (namesp->name)
            guththila_tok_list_release_token(&m->tokens, namesp->name, env);
            if (namesp->uri)
            guththila_tok_list_release_token(&m->tokens, namesp->uri, env);
            AXIS2_FREE(env->allocator, namesp);
        }
    }
#else 

    size = GUTHTHILA_STACK_SIZE(m->namesp);
    for(i = 0; i < size; i++)
    {
        e_namesp = (guththila_elem_namesp_t *)guththila_stack_pop(&m->namesp, env);
        if(e_namesp)
        {
            for(j = 0; j < e_namesp->no; j++)
            {
                if(e_namesp->namesp[j].name)
                {
                    guththila_tok_list_release_token(&m->tokens, e_namesp->namesp[j].name, env);
                }
                if(e_namesp->namesp[j].uri)
                {
                    guththila_tok_list_release_token(&m->tokens, e_namesp->namesp[j].uri, env);
                }
            }
            AXIS2_FREE(env->allocator, e_namesp->namesp);
            AXIS2_FREE(env->allocator, e_namesp);
        }
    }
#endif  

    size = GUTHTHILA_STACK_SIZE(m->elem);
    for(i = 0; i < size; i++)
    {
        elem = (guththila_element_t *)guththila_stack_pop(&m->elem, env);
        if(elem)
        {
            if(elem->name)
                guththila_tok_list_release_token(&m->tokens, elem->name, env);
            if(elem->prefix)
                guththila_tok_list_release_token(&m->tokens, elem->prefix, env);
            AXIS2_FREE(env->allocator, elem);
        }
    }
    guththila_stack_un_init(&m->elem, env);
    guththila_stack_un_init(&m->namesp, env);
    guththila_tok_list_free_data(&m->tokens, env);
    guththila_buffer_un_init(&m->buffer, env);
    AXIS2_FREE(env->allocator, m);
    return GUTHTHILA_SUCCESS;
}

/*static int
guththila_utf8_bytes_len(
    unsigned int c)
{
    if (c < 0x80)
        return 1;
    else if (c < 0x800)
        return 2;
    else if (c < 0x10000)
        return 3;
    else if (c < 0x200000)
        return 4;
    else if (c < 0x4000000)
        return 5;
    else
        return 6;
}*/

/*
 * Stores the given unicode char as UTF-8
 */
static guththila_char_t*
guththila_utf8_bytes(
    unsigned int c,
    guththila_char_t *start)
{
    int first;
    guththila_char_t *end, *p;

    if(c <           0x80)
    {
        *start = c;
        return start + 1;
    }
    if(c <          0x800)
    {
        first = 0xc0;
        end = start + 2;
    }
    else if(c <   0x10000)
    {
        first = 0xe0;
        end = start + 3;
    }
    else if(c <  0x200000)
    {
        first = 0xf0;
        end = start + 4;
    }
    else if(c < 0x4000000)
    {
        first = 0xf8;
        end = start + 5;
    }
    else
    {
        first = 0xfc;
        end = start + 6;
    }

    p = end;
    while(--p > start)
    {
        *p = (c & 0x3f) | 0x80;
        c >>= 6;
    }
    *start = c | first;
    return end;
}


/*
 * Replace the references with the corresponding actual values.
 */
static void
guththila_token_evaluate_references(
    guththila_token_t * tok)
{
    guththila_char_t *start = tok->start;
    guththila_char_t *end = start + tok->size;
    guththila_char_t *p = start;
    guththila_char_t *q = NULL;
    guththila_char_t *entity = NULL;
    size_t entity_len = 0;

    while(p < end && *p != '&')
    {
        p++;
    }
    q = p;
    while(p < end)
    {
        /* Copy characters until the next ampersand */
        if(*p != '&')
        {
            *q++ = *p++;
            continue;
        }
        entity = ++p;
        /* Find the end of the entity, marked by ';' */
        while(p < end && *p != ';')
        {
            p++;
        }
        if(p == end)
        {
            break; /* Drop unterminated entity */
        }
        entity_len = p - entity;
        if(entity_len == 2 && entity[1] == 't')
        {
            if(entity[0] == 'g')
                *q++ = '>';
            else if(entity[0] == 'l')
                *q++ = '<';
            /* else drop */
        }
        else if(entity_len == 3 && entity[0] == 'a' && entity[1] == 'm' && entity[2] == 'p')
        {
            *q++ = '&';
        }
        else if(entity_len == 4 && entity[2] == 'o')
        {
            if(entity[0] == 'q' && entity[1] == 'u' && entity[3] == 't')
            {
                *q++ = '"';
            }
            else if(entity[0] == 'a' && entity[1] == 'p' && entity[3] == 's')
            {
                *q++ = '\'';
            }
        }
        else if(entity_len >= 2 && entity[0] == '#')
        {
            /* p points to the ';' */
            int c = 0;
            guththila_char_t b;
            guththila_char_t *digit = entity + 1;
            if(*digit == 'x')
            { /* &#x...; */
                while(++digit < p)
                {
                    b = *digit;
                    if(b >= '0' && b <= '9')
                        c = c << 4 | (b - '0');
                    else if(b >= 'A' && b <= 'F')
                        c = c << 4 | (b - 'A' + 10);
                    else if(b >= 'a' && b <= 'f')
                        c = c << 4 | (b - 'a' + 10);
                    else
                        break; /* stop and drop */
                }
            }
            else
            { /* &#...; */
                while(digit < p)
                {
                    b = *digit;
                    if(b >= '0' && b <= '9')
                        c = c * 10 + (b - '0');
                    else
                        break; /* stop and drop */
                    digit++;
                }
            }
            if(digit == p && c != 0)
            { /* drop null char or unparsable entity */
                /* Replace the entity with the UTF-8 representation */
                q = guththila_utf8_bytes(c, q);
            }
        } /* else drop unknown entity */
        p++; /* go over ';' */
    }
    tok->size = q - start;
}

/*
 * Close a token. This method accepts the type of the token as a parameter.
 */
static void
guththila_token_close(
    guththila_t * m,
    guththila_token_t * tok,
    int tok_type,
    int referer,
    const axutil_env_t * env)
{
    guththila_attr_t * attr = NULL;
    guththila_element_t * elem = NULL;
    guththila_elem_namesp_t * e_namesp = NULL;
    guththila_namespace_t * namesp;
    int i = 0;
    /* We are sure that the difference lies within the short range */
    m->temp_tok->type = (short)tok_type;
    m->temp_tok->size = m->next - m->temp_tok->_start;
    m->temp_tok->start = GUTHTHILA_BUF_POS(m->buffer, m->next - 1) - m->temp_tok->size;
    m->temp_tok->ref = referer;
    m->last_start = -1;
    switch(tok_type)
    {
        case _attribute_name:
            m->temp_name = m->temp_tok;
            m->temp_tok = NULL;
            break;
        case _char_data:
            m->value = m->temp_tok;
            m->temp_tok = NULL;
            break;
        case _text_data:
            guththila_token_evaluate_references(m->temp_tok);
            m->value = m->temp_tok;
            m->temp_tok = NULL;
            break;
        case _attribute_value:
            guththila_token_evaluate_references(m->temp_tok);
            /* Chech weather we are at a xml namespace declaration */
            if((m->temp_prefix && (guththila_tok_str_cmp(m->temp_prefix, "xmlns", 5u, env) == 0))
                || (guththila_tok_str_cmp(m->temp_name, "xmlns", 5u, env) == 0))
            /*checks inside the m->temp_name to parse the default namespace*/
            /*checks inside the m->temp_prefix to parse namespace with prefix*/
            {
#ifndef GUTHTHILA_VALIDATION_PARSER
                namesp =
                (guththila_namespace_t *)
                AXIS2_MALLOC(sizeof(guththila_namespace_t));
                GUTHTHILA_NAMESPACE_INITIALIZE(namesp, m->temp_name, m->temp_tok);
                guththila_stack_push(&m->namesp, namesp);
#else   
                elem = (guththila_element_t *)guththila_stack_peek(&m->elem, env);
                /* This is the first namespace */
                if(elem && !elem->is_namesp)
                {
                    e_namesp = (guththila_elem_namesp_t *)AXIS2_MALLOC(env->allocator,
                        sizeof(guththila_elem_namesp_t));
                    if(e_namesp)
                    {
                        e_namesp->namesp = (guththila_namespace_t *)AXIS2_MALLOC(env->allocator,
                            sizeof(guththila_namespace_t) * GUTHTHILA_NAMESPACE_DEF_SIZE);
                        if(e_namesp->namesp)
                        {
                            e_namesp->no = 1;
                            e_namesp->size = GUTHTHILA_NAMESPACE_DEF_SIZE;
                            e_namesp->namesp[0].name = m->temp_name;
                            e_namesp->namesp[0].uri = m->temp_tok;
                            guththila_stack_push(&m->namesp, e_namesp, env);
                            elem->is_namesp = 1;
                        }
                        else
                        {
                            AXIS2_FREE(env->allocator, e_namesp);
                            e_namesp = NULL;
                        }
                    }
                }
                /* Already there is a namespace */
                else if(elem && elem->is_namesp)
                {
                    e_namesp = (guththila_elem_namesp_t *)guththila_stack_peek(&m->namesp, env);
                    /* if we have enough space allocated */
                    if(e_namesp->no < e_namesp->size)
                    {
                        e_namesp->namesp[e_namesp->no].name = m->temp_name;
                        e_namesp->namesp[e_namesp->no].uri = m->temp_tok;
                        e_namesp->no++;
                    }
                    else
                    {
                        namesp = (guththila_namespace_t *)AXIS2_MALLOC(env->allocator,
                            sizeof(guththila_namespace_t) * e_namesp->size * 2);
                        if(namesp)
                        {
                            for(i = 0; i < e_namesp->no; i++)
                            {
                                namesp[i].name = e_namesp->namesp[i].name;
                                namesp[i].uri = e_namesp->namesp[i].uri;
                            }
                            AXIS2_FREE(env->allocator, e_namesp->namesp);
                            e_namesp->namesp = namesp;
                            e_namesp->size *= 2;

                            e_namesp->namesp[e_namesp->no].name = m->temp_name;
                            e_namesp->namesp[e_namesp->no].uri = m->temp_tok;
                            e_namesp->no++;
                        }
                    }
                }
#endif  
            }
            else
            {
                /* It is just a attribute */
                attr = (guththila_attr_t *)AXIS2_MALLOC(env->allocator, sizeof(guththila_attr_t));

                GUTHTHILA_ATTRIBUTE_INITIALIZE(attr,
                    m->temp_prefix,
                    m->temp_name,
                    m->temp_tok);
                guththila_stack_push(&m->attrib, attr, env);
            }
            m->temp_prefix = NULL;
            m->temp_name = NULL;
            m->temp_tok = NULL;
            break;
        case _prefix:
            m->temp_prefix = m->temp_tok;
            m->temp_tok = NULL;
            break;
        default:
            m->prefix = m->temp_prefix;
            m->name = m->temp_tok;
            m->temp_tok = NULL;
            m->temp_prefix = NULL;
            break;
    }
}

int GUTHTHILA_CALL
guththila_validate_namespaces(
    guththila_t *m,
    const axutil_env_t *env)
{
    int size = 0, i = 0, nmsp_no = 0, j = 0, k = 0;
    int namesp_found = GUTHTHILA_FALSE;
    guththila_elem_namesp_t *e_namesp = NULL;

    size = GUTHTHILA_STACK_SIZE(m->attrib);
    /* Loop through all the attributes */
    for(i = 0; i < size; i++)
    {
        guththila_attr_t *attr = (guththila_attr_t *)guththila_stack_get_by_index(&m->attrib, i,
            env);
        if(attr && attr->pref)
        {
            /* We have a attribute prefix. Need to validate the prefix */
            nmsp_no = GUTHTHILA_STACK_SIZE(m->namesp);
            for(j = nmsp_no - 1; j >= 0; j--)
            {
                e_namesp = (guththila_elem_namesp_t *)guththila_stack_get_by_index(&m->namesp, j,
                    env);
                for(k = 0; k < e_namesp->no; k++)
                {
                    if(!guththila_tok_tok_cmp(e_namesp->namesp[k].name, attr->pref, env))
                    {
                        namesp_found = GUTHTHILA_TRUE;
                        j = -1; /* force exit from second for loop */
                        break;
                    }
                }
            }
            if(!namesp_found)
                return GUTHTHILA_FAILURE;
        }
    }
    /* If the element has a prefix. Need to validate the prefix*/
    if(m->prefix)
    {
        namesp_found = AXIS2_FALSE;
        nmsp_no = GUTHTHILA_STACK_SIZE(m->namesp);
        for(j = nmsp_no - 1; j >= 0; j--)
        {
            e_namesp = (guththila_elem_namesp_t *)guththila_stack_get_by_index(&m->namesp, j, env);
            for(k = 0; k < e_namesp->no; k++)
            {
                if(!guththila_tok_tok_cmp(e_namesp->namesp[k].name, m->prefix, env))
                {
                    namesp_found = GUTHTHILA_TRUE;
                    j = -1; /* force exit from outer loop */
                    break;
                }
            }
        }
        if(!namesp_found)
            return AXIS2_FAILURE;
    }
    return GUTHTHILA_SUCCESS;
}

GUTHTHILA_EXPORT int GUTHTHILA_CALL
guththila_next(
    guththila_t * m,
    const axutil_env_t * env)
{
    guththila_element_t * elem = NULL;
    guththila_elem_namesp_t * nmsp = NULL;
    guththila_token_t * tok = NULL;
    int quote = 0, ref = 0;
    int c = -1;
    guththila_attr_t * attr = NULL;
    int size = 0, i = 0, nmsp_counter, loop = 0, white_space = 0;
    size_t data_size = -1;
    size_t previous_size = -1;
    guththila_char_t *buffer = NULL;

    /* Need to release the resources for attributes */
    size = GUTHTHILA_STACK_SIZE(m->attrib);
    for(i = 0; i < size; i++)
    {
        attr = (guththila_attr_t *)guththila_stack_pop(&m->attrib, env);
        if(attr)
        {
            if(attr->name)
                guththila_tok_list_release_token(&m->tokens, attr->name, env);
            if(attr->pref)
                guththila_tok_list_release_token(&m->tokens, attr->pref, env);
            AXIS2_FREE(env->allocator, attr);
        }
    }

#ifdef GUTHTHILA_VALIDATION_PARSER    
    if(m->guththila_event == GUTHTHILA_END_ELEMENT && m->name)
    {
        guththila_tok_list_release_token(&m->tokens, m->name, env);
        if(m->prefix)
        {
            guththila_tok_list_release_token(&m->tokens, m->prefix, env);
        }
    }
    /* If the previous event was a empty element we need to do some clean up */
    else if(m->guththila_event == GUTHTHILA_EMPTY_ELEMENT)
    {
        elem = (guththila_element_t *)guththila_stack_pop(&m->elem, env);
        if(elem->is_namesp)
        {
            nmsp = (guththila_elem_namesp_t *)guththila_stack_pop(&m->namesp, env);
            for(nmsp_counter = 0; nmsp_counter < nmsp->no; nmsp_counter++)
            {
                if(nmsp->namesp[nmsp_counter].name)
                    guththila_tok_list_release_token(&m->tokens, nmsp->namesp[nmsp_counter]. name,
                        env);
                if(nmsp->namesp[nmsp_counter].uri)
                    guththila_tok_list_release_token(&m->tokens, nmsp->namesp[nmsp_counter]. uri,
                        env);
            }
            AXIS2_FREE(env->allocator, nmsp->namesp);
            AXIS2_FREE(env->allocator, nmsp);
        }
        if(elem->name)
            guththila_tok_list_release_token(&m->tokens, elem->name, env);
        if(elem->prefix)
            guththila_tok_list_release_token(&m->tokens, elem->prefix, env);
        AXIS2_FREE(env->allocator, elem);
    }
    GUTHTHILA_VARIABLE_INITIALZE(m);
#endif  
    /* Actual XML parsing logic */
    do
    {
        loop = 0;
        GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
        if(m->status == S_1)
        {
            while(isspace(c))
            {
                GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
            }
            if('<' == c)
            {
                m->status = S_2;
            }
            else
            {
                return -1;
            }
        }
        if(m->status != S_2)
        {
            return -1;
        }
        if(c == '<')
        {
            GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
            if(c != '?' && c != '!' && c != '/')
            {
                /* We are at the beginning of a xml element */
                if(GUTHTHILA_IS_VALID_STARTING_CHAR(c))
                {
                    GUTHTHILA_TOKEN_OPEN(m, tok, env);
                    GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                    while(!GUTHTHILA_IS_SPACE(c) && c != '>' && c != '/')
                    {
                        if(c != ':')
                        {
                            GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                        }
                        else
                        {
                            /* We know for sure that this is a prefix */
                            guththila_token_close(m, tok, _prefix, 0, env);
                            GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                            GUTHTHILA_TOKEN_OPEN(m, tok, env);
                        }
                    }
                    /* XML element name */
                    guththila_token_close(m, tok, _name, 0, env);
#ifdef GUTHTHILA_VALIDATION_PARSER		
                    elem = (guththila_element_t *)AXIS2_MALLOC(env->allocator,
                        sizeof(guththila_element_t));
                    elem->name = m->name;
                    elem->prefix = m->prefix;
                    elem->is_namesp = 0;
                    guththila_stack_push(&m->elem, elem, env);
#endif  
                }
                GUTHTHILA_SKIP_SPACES(m, c, buffer, data_size, previous_size, env);
                /* Process the attributes */
                for(;;)
                {
                    /* Empty element */
                    if(c == '/')
                    {
                        GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                        if(c == '>')
                        {
                            m->guththila_event = GUTHTHILA_EMPTY_ELEMENT;
                            if(!guththila_validate_namespaces(m, env))
                                return -1;
                            else
                                return GUTHTHILA_EMPTY_ELEMENT;
                        }
                        else
                        {
                            return -1;
                        }
                    }
                    /* Normal element */
                    else if(c == '>')
                    {
                        m->guththila_event = GUTHTHILA_START_ELEMENT;
                        if(!guththila_validate_namespaces(m, env))
                            return -1;
                        else
                            return GUTHTHILA_START_ELEMENT;
                    }
                    /* We are in the middle of a element */
                    else
                    {
                        /* Process the attributes */
                        if(GUTHTHILA_IS_VALID_STARTING_CHAR(c))
                        {
                            GUTHTHILA_TOKEN_OPEN(m, tok, env);

                            GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                            while(!GUTHTHILA_IS_SPACE(c) && c != '=')
                            {
                                if(c != ':')
                                {
                                    GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                                }
                                else if(c == ':')
                                {
                                    /* Prefix */
                                    guththila_token_close(m, tok, _prefix, 0, env);
                                    GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                                    GUTHTHILA_TOKEN_OPEN(m, tok, env);
                                }
                            }
                            /* Attribute name*/
                            guththila_token_close(m, tok, _attribute_name, 0, env);
                        }
                        else
                        {
                            return -1;
                        }
                        /* Attribute Value */
                        GUTHTHILA_PROCESS_EQU(m, c, quote, buffer, data_size, previous_size, env);
                        if(quote == '\'' || quote == '\"')
                        {
                            GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                            GUTHTHILA_TOKEN_OPEN(m, tok, env);
                            while(c != quote)
                            {
                                GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                            }
                            guththila_token_close(m, tok, _attribute_value, 0, env);
                            GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                            GUTHTHILA_SKIP_SPACES(m, c, buffer, data_size, previous_size, env);
                        }
                        else
                        {
                            return -1;
                        }
                    }
                } /* for(;;) */
            }
            else if(c == '/')
            {
                /* End Element */
                m->guththila_event = GUTHTHILA_END_ELEMENT;
                GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                if(GUTHTHILA_IS_VALID_STARTING_CHAR(c))
                {
                    GUTHTHILA_TOKEN_OPEN(m, tok, env);
                    GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                    while(!GUTHTHILA_IS_SPACE(c) && c != '>')
                    {
                        if(c != ':')
                        {
                            GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                        }
                        else
                        {
                            /* Prefix */
                            guththila_token_close(m, tok, _prefix, 0, env);
                            GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                            GUTHTHILA_TOKEN_OPEN(m, tok, env);
                        }
                    }
                    /* name */
                    guththila_token_close(m, tok, _name, 0, env);

#ifdef GUTHTHILA_VALIDATION_PARSER	
                    elem = (guththila_element_t *)guththila_stack_pop(&m->elem, env);
                    if(!elem || (!elem->prefix && m->prefix) || (elem->prefix && !m->prefix))
                        return -1;
                    if(guththila_tok_tok_cmp(m->name, elem->name, env))
                    {
                        return -1;
                    }
                    if(elem->prefix && m->prefix && guththila_tok_tok_cmp(m->prefix, elem->prefix,
                        env))
                    {
                        return -1;
                    }
                    /* Releasing the namespace related resources */
                    if(elem->is_namesp)
                    {
                        nmsp = (guththila_elem_namesp_t *)guththila_stack_pop(&m->namesp, env);
                        for(nmsp_counter = 0; nmsp_counter < nmsp->no; nmsp_counter++)
                        {
                            if(nmsp->namesp[nmsp_counter].name)
                                guththila_tok_list_release_token(&m->tokens,
                                    nmsp-> namesp[nmsp_counter]. name, env);
                            if(nmsp->namesp[nmsp_counter].uri)
                                guththila_tok_list_release_token(&m->tokens,
                                    nmsp-> namesp[nmsp_counter]. uri, env);
                        }
                        AXIS2_FREE(env->allocator, nmsp->namesp);
                        AXIS2_FREE(env->allocator, nmsp);
                    }
                    /* Release the tokens */
                    if(elem->name)
                        guththila_tok_list_release_token(&m->tokens, elem->name, env);
                    if(elem->prefix)
                        guththila_tok_list_release_token(&m->tokens, elem->prefix, env);
                    AXIS2_FREE(env->allocator, elem);
#endif  
                    GUTHTHILA_SKIP_SPACES(m, c, buffer, data_size, previous_size, env);
                    if(c != '>')
                        return -1;
                    return GUTHTHILA_END_ELEMENT;
                }
                return -1;
            }
            else if(c == '!')
            {
                /* Comment */
                guththila_char_t c_arra[16] = { 0 };
                if(2 == guththila_next_no_char(m, 0, c_arra, 2, env) && '-' == c_arra[0] && '-'
                    == c_arra[1])
                {
                    int loop_state = 1;
                    GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                    GUTHTHILA_TOKEN_OPEN(m, tok, env);
                    while(loop_state)
                    {
                        GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                        if('-' == c)
                        {
                            if(2 == guththila_next_no_char(m, 0, c_arra, 2, env) && '-'
                                == c_arra[0])
                            {
                                if('>' == c_arra[1])
                                {
                                    m->guththila_event = GUTHTHILA_COMMENT;
                                    /* position after first hyphen, as if we just scanned it */
                                    m->next = m->next - 2;
                                    guththila_token_close(m, tok, _char_data, 0, env);
                                    m->next = m->next + 2;
                                    return GUTHTHILA_COMMENT;
                                }
                                else
                                {
                                    return -1;
                                }
                            }
                        }
                    }
                }
                else
                {
                    GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                    while('<' != c)
                    {
                        GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                    }
                }
            }
            else if(c == '?')
            {
                /* XML declaration */
                c = guththila_process_xml_dec(m, env);
                if(c != -1)
                    return GUTHTHILA_START_DOCUMENT;
                else
                    return -1;
            }
        }
        else
        {
            /* Text */
            m->guththila_event = GUTHTHILA_CHARACTER;
            if(!GUTHTHILA_IS_SPACE(c))
                white_space = 0;
            else
                white_space = 1;
            GUTHTHILA_TOKEN_OPEN(m, tok, env);

            /* code given below is having two do-while loop wrapped by another do-while loop.
             * This is done to improve the performance for big messages. Most of the cases, the
             * content will be not whitespace, so checking for whitespace even if we already found
             * that we have some valid characters is big overhead. Hence better to do the looping
             * separately to find white_space = false and normal case
             */
            do
            {
                if(white_space)
                {
                    do
                    {
                        GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                        if(!GUTHTHILA_IS_SPACE(c) && c != '<')
                        {
                            white_space = 0;
                            break;
                        }
                    }
                    while(c != '<');
                }
                else
                {
                    do
                    {
                        if(buffer)
                        {
                            guththila_char_t *pos = NULL;
                            size_t index = m->next - previous_size;
                            pos = (guththila_char_t*)memchr(buffer + index, '<', data_size - index);
                            if(pos)
                            {
                                m->next += pos - (buffer + index);
                            }
                            else
                            {
                                m->next = previous_size + data_size;
                            }

                            GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                        }
                        else
                        {
                            GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                        }
                    }while(c != '<');
                }
            }
            while(c != '<');
            guththila_token_close(m, tok, _text_data, ref, env);
            m->next--;
            if(white_space)
            {
#ifndef GUTHTHILA_IGNORE_SPACES
                m->guththila_event = GUTHTHILA_SPACE;
                return GUTHTHILA_SPACE;
#else
                loop = 1;
                if (m->value)
                {
                    guththila_tok_list_release_token(&m->tokens, m->value,
                        env);
                    m->value = NULL;
                }
#endif
            }

            else
                return GUTHTHILA_CHARACTER;
        }
    }
    while(loop);
    return c;
}

/* Process the XML declaration */
static int
guththila_process_xml_dec(
    guththila_t * m,
    const axutil_env_t * env)
{
    guththila_token_t * tok = NULL;
    guththila_char_t c_arra[16] = { 0 };
    int c = -1;
    int quote = -1;
    int nc = -1;
    size_t data_size = -1;
    size_t previous_size = -1;
    guththila_char_t *buffer = NULL;
    if(3 == guththila_next_no_char(m, GUTHTHILA_EOF, c_arra, 3, env) && 'x' == c_arra[0] && 'm'
        == c_arra[1] && 'l' == c_arra[2])
    {
        GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
        GUTHTHILA_SKIP_SPACES(m, c, buffer, data_size, previous_size, env);
        if(c == 'v')
        {
            GUTHTHILA_TOKEN_OPEN(m, tok, env);
            if(6 == guththila_next_no_char(m, 0, c_arra, 6, env) && 'e' == c_arra[0] && 'r'
                == c_arra[1] && 's' == c_arra[2] && 'i' == c_arra[3] && 'o' == c_arra[4] && 'n'
                == c_arra[5])
            {
                GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                guththila_token_close(m, tok, _attribute_name, 0, env);
                GUTHTHILA_PROCESS_EQU(m, c, quote, buffer, data_size, previous_size, env);
                GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, nc);
                GUTHTHILA_TOKEN_OPEN(m, tok, env);
                while(nc != quote)
                {
                    GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, nc);
                }
                guththila_token_close(m, tok, _attribute_value, 0, env);
                GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                GUTHTHILA_SKIP_SPACES(m, c, buffer, data_size, previous_size, env);
            }
            else
            {
                return -1;
            }
        }
        if(c == 'e')
        {
            GUTHTHILA_TOKEN_OPEN(m, tok, env);
            if(7 == guththila_next_no_char(m, 0, c_arra, 7, env) && 'n' == c_arra[0] && 'c'
                == c_arra[1] && 'o' == c_arra[2] && 'd' == c_arra[3] && 'i' == c_arra[4] && 'n'
                == c_arra[5] && 'g' == c_arra[6])
            {
                GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                guththila_token_close(m, tok, _attribute_name, 0, env);
                GUTHTHILA_PROCESS_EQU(m, c, quote, buffer, data_size, previous_size, env);
                GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, nc);
                GUTHTHILA_TOKEN_OPEN(m, tok, env);
                while(nc != quote)
                {
                    GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, nc);
                }
                guththila_token_close(m, tok, _attribute_value, 0, env);
                GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                GUTHTHILA_SKIP_SPACES(m, c, buffer, data_size, previous_size, env);
            }
        }
        if(c == 's')
        {
            GUTHTHILA_TOKEN_OPEN(m, tok, env);
            if(9 == guththila_next_no_char(m, 0, c_arra, 9, env) && 't' == c_arra[0] && 'a'
                == c_arra[1] && 'n' == c_arra[2] && 'd' == c_arra[3] && 'a' == c_arra[4] && 'l'
                == c_arra[5] && 'o' == c_arra[6] && 'n' == c_arra[7] && 'e' == c_arra[8])
            {
                GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                guththila_token_close(m, tok, _attribute_name, 0, env);
                GUTHTHILA_PROCESS_EQU(m, c, quote, buffer, data_size, previous_size, env);
                GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, nc);
                GUTHTHILA_TOKEN_OPEN(m, tok, env);
                while(nc != quote)
                {
                    GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, nc);
                }
                guththila_token_close(m, tok, _attribute_value, 0, env);
                GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, c);
                GUTHTHILA_SKIP_SPACES(m, c, buffer, data_size, previous_size, env);
            }
        }
        if(c == '?')
        {
            int nc;
            GUTHTHILA_NEXT_CHAR(m, buffer, data_size, previous_size, env, nc);
            if('>' == nc)
            {
                m->guththila_event = GUTHTHILA_START_DOCUMENT;
            }
            else
            {
                return -1;
            }
        }
    }
    return c;
}

GUTHTHILA_EXPORT int GUTHTHILA_CALL
guththila_get_attribute_count(
    guththila_t * m,
    const axutil_env_t * env)
{
    return GUTHTHILA_STACK_SIZE(m->attrib);
}

GUTHTHILA_EXPORT guththila_char_t *GUTHTHILA_CALL
guththila_get_attribute_name(
    guththila_t * m,
    guththila_attr_t * att,
    const axutil_env_t * env)
{
    guththila_char_t *str = NULL;
    if(att->name)
    {
        GUTHTHILA_TOKEN_TO_STRING(att->name, str, env);
        return str;
    }
    return NULL;
}

GUTHTHILA_EXPORT guththila_char_t *GUTHTHILA_CALL
guththila_get_attribute_value(
    guththila_t * m,
    guththila_attr_t * att,
    const axutil_env_t * env)
{
    guththila_char_t *str = NULL;
    if(att->val)
    {
        GUTHTHILA_TOKEN_TO_STRING(att->val, str, env);
        return str;
    }
    return NULL;
}

GUTHTHILA_EXPORT guththila_char_t *GUTHTHILA_CALL
guththila_get_attribute_prefix(
    guththila_t * m,
    guththila_attr_t * att,
    const axutil_env_t * env)
{
    guththila_char_t *str = NULL;
    if(att->pref)
    {
        GUTHTHILA_TOKEN_TO_STRING(att->pref, str, env);
        return str;
    }
    return NULL;
}

GUTHTHILA_EXPORT guththila_attr_t *GUTHTHILA_CALL
guththila_get_attribute(
    guththila_t * m,
    const axutil_env_t * env)
{
    return (guththila_attr_t *)guththila_stack_pop(&m->attrib, env);
}

GUTHTHILA_EXPORT guththila_char_t *GUTHTHILA_CALL
guththila_get_attribute_name_by_number(
    guththila_t * m,
    int i,
    const axutil_env_t *env)
{
    guththila_char_t *str = NULL;
    guththila_attr_t * attr = (guththila_attr_t *)guththila_stack_get_by_index(&m->attrib, i - 1,
        env);
    if(attr->name)
    {
        GUTHTHILA_TOKEN_TO_STRING(attr->name, str, env);
        return str;
    }
    return NULL;
}

GUTHTHILA_EXPORT guththila_char_t *GUTHTHILA_CALL
guththila_get_attribute_value_by_number(
    guththila_t * m,
    int i,
    const axutil_env_t *env)
{
    guththila_char_t *str = NULL;
    guththila_attr_t * attr = (guththila_attr_t *)guththila_stack_get_by_index(&m->attrib, i - 1,
        env);
    if(attr->val)
    {
        GUTHTHILA_TOKEN_TO_STRING(attr->val, str, env);
        return str;
    }
    return NULL;
}

GUTHTHILA_EXPORT guththila_char_t *GUTHTHILA_CALL
guththila_get_attribute_prefix_by_number(
    guththila_t * m,
    int i,
    const axutil_env_t *env)
{
    guththila_char_t *str = NULL;
    guththila_attr_t * attr = (guththila_attr_t *)guththila_stack_get_by_index(&m->attrib, i - 1,
        env);
    if(attr && attr->pref)
    {
        GUTHTHILA_TOKEN_TO_STRING(attr->pref, str, env);
        return str;
    }
    return NULL;
}

GUTHTHILA_EXPORT guththila_char_t *GUTHTHILA_CALL
guththila_get_name(
    guththila_t * m,
    const axutil_env_t * env)
{
    guththila_char_t *str = NULL;
    if(m->name)
    {
        GUTHTHILA_TOKEN_TO_STRING(m->name, str, env);
        return str;
    }
    return NULL;
}

GUTHTHILA_EXPORT guththila_char_t *GUTHTHILA_CALL
guththila_get_prefix(
    guththila_t * m,
    const axutil_env_t * env)
{
    guththila_char_t *str = NULL;
    if(m->prefix)
    {
        GUTHTHILA_TOKEN_TO_STRING(m->prefix, str, env);
        return str;
    }
    return NULL;
}

GUTHTHILA_EXPORT guththila_char_t * GUTHTHILA_CALL
guththila_get_value(
    guththila_t * m,
    const axutil_env_t * env)
{
    guththila_char_t *str = NULL;
    if(m->value)
    {
        GUTHTHILA_TOKEN_TO_STRING(m->value, str, env);
        return str;
    }
    return NULL;
}

GUTHTHILA_EXPORT guththila_namespace_t *GUTHTHILA_CALL
guththila_get_namespace(
    guththila_t * m,
    const axutil_env_t * env)
{

#ifndef GUTHTHILA_VALIDATION_PARSER
    return (guththila_namespace_t *) guththila_stack_pop(&m->namesp, env);
#else  
    return NULL;
#endif  
}

GUTHTHILA_EXPORT int GUTHTHILA_CALL
guththila_get_namespace_count(
    guththila_t * m,
    const axutil_env_t * env)
{

#ifndef GUTHTHILA_VALIDATION_PARSER
    return GUTHTHILA_STACK_SIZE(m->namesp);
#else   
    guththila_elem_namesp_t * nmsp = NULL;
    if(((guththila_element_t *)guththila_stack_peek(&m->elem, env))->is_namesp)
    {
        nmsp = (guththila_elem_namesp_t *)guththila_stack_peek(&m->namesp, env);
        return nmsp->no;
    }
    return 0;

#endif  
}

GUTHTHILA_EXPORT guththila_char_t *GUTHTHILA_CALL
guththila_get_namespace_uri(
    guththila_t * m,
    guththila_namespace_t * ns,
    const axutil_env_t * env)
{
    guththila_char_t *str = NULL;
    if(ns->uri)
    {
        GUTHTHILA_TOKEN_TO_STRING(ns->uri, str, env);
        return str;
    }
    return NULL;
}

GUTHTHILA_EXPORT guththila_char_t *GUTHTHILA_CALL
guththila_get_namespace_prefix(
    guththila_t * m,
    guththila_namespace_t * ns,
    const axutil_env_t * env)
{
    guththila_char_t *str = NULL;
    if(ns->name)
    {
        GUTHTHILA_TOKEN_TO_STRING(ns->name, str, env);
        return str;
    }
    return NULL;
}

GUTHTHILA_EXPORT guththila_char_t *GUTHTHILA_CALL
guththila_get_namespace_prefix_by_number(
    guththila_t * m,
    int i,
    const axutil_env_t *env)
{
    guththila_char_t *str = NULL;

#ifndef GUTHTHILA_VALIDATION_PARSER
    if (GUTHTHILA_STACK_SIZE(m->namesp) >= i)
    {
        namesp = guththila_stack_get_by_index(&m->namesp, i - 1, env);
        if (namesp && namesp->name)
        {
            GUTHTHILA_TOKEN_TO_STRING(namesp->name, str, env);
            return str;
        }
    }

#else   
    guththila_elem_namesp_t * nmsp = NULL;
    if(((guththila_element_t *)guththila_stack_peek(&m->elem, env))->is_namesp)
    {
        nmsp = (guththila_elem_namesp_t *)guththila_stack_peek(&m->namesp, env);
        if(nmsp && nmsp->no >= i)
        {
            GUTHTHILA_TOKEN_TO_STRING(nmsp->namesp[i - 1].name, str, env);
            return str;
        }
    }
#endif  /*  */
    return NULL;
}

GUTHTHILA_EXPORT guththila_char_t *GUTHTHILA_CALL
guththila_get_namespace_uri_by_number(
    guththila_t * m,
    int i,
    const axutil_env_t *env)
{
    guththila_char_t *str = NULL;
#ifndef GUTHTHILA_VALIDATION_PARSER
    if (GUTHTHILA_STACK_SIZE(m->namesp) >= i)
    {
        namesp = guththila_stack_get_by_index(&m->namesp, i - 1, env);
        if (namesp && namesp->uri)
        {
            GUTHTHILA_TOKEN_TO_STRING(namesp->uri, str, env);
            return str;
        }
    }
#else  
    guththila_elem_namesp_t * nmsp = NULL;
    if(((guththila_element_t *)guththila_stack_peek(&m->elem, env))->is_namesp)
    {
        nmsp = (guththila_elem_namesp_t *)guththila_stack_peek(&m->namesp, env);
        if(nmsp && nmsp->no >= i)
        {
            GUTHTHILA_TOKEN_TO_STRING(nmsp->namesp[i - 1].uri, str, env);
            return str;
        }
    }
#endif  
    return NULL;
}

GUTHTHILA_EXPORT guththila_char_t *GUTHTHILA_CALL
guththila_get_attribute_namespace_by_number(
    guththila_t * m,
    int i,
    const axutil_env_t *env)
{

#ifndef GUTHTHILA_VALIDATION_PARSER
    return NULL;

#else  
    guththila_attr_t * attr = NULL;
    guththila_char_t* str = NULL;
    int j = 0, k = 0, count = 0;
    guththila_elem_namesp_t * nmsp = NULL;
    if(i <= GUTHTHILA_STACK_SIZE(m->attrib))
    {
        attr = (guththila_attr_t *)guththila_stack_get_by_index(&m->attrib, i - 1, env);
        if(attr && attr->pref)
        {
            count = GUTHTHILA_STACK_SIZE(m->namesp);
            for(j = count - 1; j >= 0; j--)
            {
                nmsp = (guththila_elem_namesp_t *)guththila_stack_get_by_index(&m->namesp, j, env);
                for(k = 0; k < nmsp->no; k++)
                {
                    if(!guththila_tok_tok_cmp(nmsp->namesp[k].name, attr->pref, env))
                    {
                        GUTHTHILA_TOKEN_TO_STRING(nmsp->namesp[k].uri, str, env);
                        return str;
                    }
                }
            }
        }
    }
    return NULL;

#endif 
}

GUTHTHILA_EXPORT guththila_char_t *GUTHTHILA_CALL
guththila_get_encoding(
    guththila_t * m,
    const axutil_env_t * env)
{
    return "UTF-8";
}

/* Return the next character */
static int
guththila_next_char(
    guththila_t * m,
    const axutil_env_t * env)
{
    int c;
    size_t data_move, i;
    int temp;
    guththila_char_t **temp1;
    size_t * temp2, *temp3;

    /* we have a buffered reader. Easiest case just fetch the character from 
     * the buffer. Here we have a single buffer. 
     * */
    if(m->reader->type == GUTHTHILA_MEMORY_READER)
    {
        size_t index = m->next++;
        if(index < m->buffer.data_size[0])
        {
            return m->buffer.buff[0][index];
        }
    }
    else
    {
        /* comlex stuff. We have a array of buffers */
        if(m->buffer.cur_buff != -1 && m->next < GUTHTHILA_BUFFER_PRE_DATA_SIZE(m->buffer)
            + GUTHTHILA_BUFFER_CURRENT_DATA_SIZE(m->buffer))
        {
            /* What we are looking for is already in the buffer */
            c = m->buffer.buff[m->buffer.cur_buff][m->next++ - GUTHTHILA_BUFFER_PRE_DATA_SIZE(
                m->buffer)];
            return c;
        }
        else if(m->buffer.cur_buff != -1 && m->next >= GUTHTHILA_BUFFER_PRE_DATA_SIZE(m->buffer)
            + GUTHTHILA_BUFFER_CURRENT_DATA_SIZE(m->buffer))
        {
            /* if we have don't have enough space in current buffer, have to create new buffer */
            if(m->buffer.buffs_size[m->buffer.cur_buff] <
                GUTHTHILA_BUFFER_CURRENT_DATA_SIZE(m->buffer) + GUTHTHILA_BUFFER_DEF_MIN_SIZE)
            {
                if(m->buffer.cur_buff == (int)m->buffer.no_buffers - 1)
                {
                    /* we are out of allocated buffers. Need to allocate more buffers */
                    temp = m->buffer.no_buffers * 2;
                    temp1 = (guththila_char_t **)AXIS2_MALLOC(env->allocator,
                        sizeof(guththila_char_t *) * temp);
                    temp2 = (size_t *)AXIS2_MALLOC(env->allocator, sizeof(size_t) * temp);
                    temp3 = (size_t *)AXIS2_MALLOC(env->allocator, sizeof(size_t) * temp);
                    if(!temp1 || !temp2 || !temp3)
                        return (-1);
                    for(i = 0; i < m->buffer.no_buffers; i++)
                    {
                        temp1[i] = m->buffer.buff[i];
                        temp2[i] = m->buffer.buffs_size[i];
                        temp3[i] = m->buffer.data_size[i];
                    }
                    AXIS2_FREE(env->allocator, m->buffer.buff);
                    AXIS2_FREE(env->allocator, m->buffer.data_size);
                    AXIS2_FREE(env->allocator, m->buffer.buffs_size);
                    m->buffer.buff = temp1;
                    m->buffer.buffs_size = temp2;
                    m->buffer.data_size = temp3;
                    m->buffer.no_buffers *= 2;
                }
                m->buffer.buff[m->buffer.cur_buff + 1] = (guththila_char_t *)AXIS2_MALLOC(
                    env->allocator,
                    sizeof(guththila_char_t) * m->buffer.buffs_size[m->buffer.cur_buff] * 2);
                if(!m->buffer.buff[m->buffer.cur_buff + 1])
                    return -1;
                m->buffer.cur_buff++;
                m->buffer.buffs_size[m->buffer.cur_buff] =
                    m->buffer.buffs_size[m->buffer.cur_buff - 1] * 2;
                m->buffer.data_size[m->buffer.cur_buff] = 0;
                /* We need to have the content for one token in a single buffer.
                 * So if the space is not sufficient we have to move first part
                 * of the token to the next buffer */
                if(m->last_start != -1)
                {
                    data_move = m->buffer.data_size[m->buffer.cur_buff - 1] -
                        (m->last_start - m->buffer.pre_tot_data);
                    memcpy(m->buffer.buff[m->buffer.cur_buff], m->buffer.buff[m->buffer.cur_buff - 1]
                        + m->buffer.data_size[m->buffer.cur_buff - 1] - data_move, data_move);
                    m->buffer.data_size[m->buffer.cur_buff - 1] -= data_move;
                    m->buffer.data_size[m->buffer.cur_buff] += data_move;
                }
                m->buffer.pre_tot_data += m->buffer.data_size[m->buffer.cur_buff - 1];
            }
            temp = guththila_reader_read(m->reader, GUTHTHILA_BUFFER_CURRENT_BUFF(m->buffer), 0,
                (int)GUTHTHILA_BUFFER_CURRENT_BUFF_SIZE(m->buffer), env);
            if(temp > 0)
            {
                m->buffer.data_size[m->buffer.cur_buff] += temp;
            }
            else
            {
                return -1;
            }
            c = m->buffer.buff[m->buffer.cur_buff][m->next++ - GUTHTHILA_BUFFER_PRE_DATA_SIZE(
                m->buffer)];
            return c;
        }
        /* Initial stage. We dont' have the array of buffers allocated*/
        else if(m->buffer.cur_buff == -1)
        {
            m->buffer.buff[0] = (guththila_char_t *)AXIS2_MALLOC(env->allocator,
                sizeof(guththila_char_t) * GUTHTHILA_BUFFER_DEF_SIZE);
            m->buffer.buffs_size[0] = GUTHTHILA_BUFFER_DEF_SIZE;
            m->buffer.cur_buff = 0;
            temp = guththila_reader_read(m->reader, m->buffer.buff[0], 0,
                GUTHTHILA_BUFFER_DEF_SIZE, env);
            m->buffer.data_size[0] = temp;
            c = m->buffer.buff[0][m->next++];
            return c;
        }
    }
    return -1;
}

/* Same functionality as the guththila_next_char. But insted of reading 
 * one character this function reads several characters at once 
 * */
static int
guththila_next_no_char(
    guththila_t * m,
    int eof,
    guththila_char_t *bytes,
    size_t no,
    const axutil_env_t * env)
{
    int temp, data_move;
    size_t i;
    guththila_char_t **temp1;
    size_t * temp2, *temp3;
    if(m->reader->type == GUTHTHILA_MEMORY_READER && m->next + no - 1
        < GUTHTHILA_BUFFER_CURRENT_DATA_SIZE(m->buffer) && m->buffer.cur_buff != -1)
    {
        for(i = 0; i < no; i++)
        {
            bytes[i] = m->buffer.buff[0][m->next++];
        }
        return (int)no;
        /* We are sure that the difference lies within the int range */
    }
    else if(m->reader->type == GUTHTHILA_IO_READER || m->reader->type == GUTHTHILA_FILE_READER)
    {
        if(m->next + no <= GUTHTHILA_BUFFER_PRE_DATA_SIZE(m->buffer)
            + GUTHTHILA_BUFFER_CURRENT_DATA_SIZE(m->buffer) && m->buffer.cur_buff != -1) 
        {
            for(i = 0; i < no; i++)
            {
                bytes[i] = m->buffer.buff[m->buffer.cur_buff][m->next++
                    - GUTHTHILA_BUFFER_PRE_DATA_SIZE(m->buffer)];
            }
            return (int)no;
            /* We are sure that the difference lies within the int range */
        }
        else if(m->next + no > GUTHTHILA_BUFFER_PRE_DATA_SIZE(m->buffer)
            + GUTHTHILA_BUFFER_CURRENT_DATA_SIZE(m->buffer) && m->buffer.cur_buff != -1) 
        {
            /* We are sure that the difference lies within the int range */
            if(m->buffer.cur_buff == (int)m->buffer.no_buffers - 1)
            {
                temp = m->buffer.no_buffers * 2;
                temp1 = (guththila_char_t **)AXIS2_MALLOC(env->allocator,
                    sizeof(guththila_char_t *) * temp);
                temp2 = (size_t *)AXIS2_MALLOC(env->allocator, sizeof(size_t) * temp);
                temp3 = (size_t *)AXIS2_MALLOC(env->allocator, sizeof(size_t) * temp);
                if(!temp1 || !temp2 || !temp3)
                    return (-1);
                for(i = 0; i < m->buffer.no_buffers; i++)
                {
                    temp1[i] = m->buffer.buff[i];
                    temp2[i] = m->buffer.buffs_size[i];
                    temp3[i] = m->buffer.data_size[i];
                }
                AXIS2_FREE(env->allocator, m->buffer.buff);
                AXIS2_FREE(env->allocator, m->buffer.data_size);
                AXIS2_FREE(env->allocator, m->buffer.buffs_size);
                m->buffer.buff = temp1;
                m->buffer.buffs_size = temp2;
                m->buffer.data_size = temp3;
                m->buffer.no_buffers *= 2;
            }
            m->buffer.buff[m->buffer.cur_buff + 1] = (guththila_char_t *)AXIS2_MALLOC(
                env->allocator, sizeof(guththila_char_t) * m->buffer.data_size[m->buffer.cur_buff]
                    * 2);
            if(!m->buffer.buff[m->buffer.cur_buff + 1])
                return -1;
            m->buffer.cur_buff++;
            m->buffer.buffs_size[m->buffer.cur_buff] = m->buffer.buffs_size[m->buffer.cur_buff - 1]
                * 2;
            m->buffer.data_size[m->buffer.cur_buff] = 0;
            data_move = (int)m->next;
            /* We are sure that the difference lies within the int range */
            if((m->last_start != -1) && (m->last_start < data_move))
                data_move = m->last_start;
            data_move = (int)m->buffer.data_size[m->buffer.cur_buff - 1] - (data_move
                - (int)m->buffer.pre_tot_data);
            /* We are sure that the difference lies within the int range */
            if(data_move)
            {
                memcpy(m->buffer.buff[m->buffer.cur_buff], m->buffer.buff[m->buffer.cur_buff - 1]
                    + m->buffer.data_size[m->buffer.cur_buff - 1] - data_move, data_move);
                m->buffer.data_size[m->buffer.cur_buff - 1] -= data_move;
                m->buffer.data_size[m->buffer.cur_buff] += data_move;
            }
            m->buffer.pre_tot_data += m->buffer.data_size[m->buffer.cur_buff - 1];
            temp = guththila_reader_read(m->reader, GUTHTHILA_BUFFER_CURRENT_BUFF(m->buffer), 0,
                (int)GUTHTHILA_BUFFER_CURRENT_BUFF_SIZE(m-> buffer), env);
            /* We are sure that the difference lies within the int range */
            if(temp > 0)
            {
                m->buffer.data_size[m->buffer.cur_buff] += temp;
            }
            else
            {
                return -1;
            }
            for(i = 0; i < no; i++)
            {
                bytes[i] = m->buffer.buff[m->buffer.cur_buff][m->next++
                    - GUTHTHILA_BUFFER_PRE_DATA_SIZE(m->buffer)];
            }
            return (int)no;
            /* We are sure that the difference lies within the int range */
        }
        else if(m->buffer.cur_buff == -1)
        {
            m->buffer.buff[0] = (guththila_char_t *)AXIS2_MALLOC(env->allocator,
                sizeof(guththila_char_t) * GUTHTHILA_BUFFER_DEF_SIZE);
            m->buffer.buffs_size[0] = GUTHTHILA_BUFFER_DEF_SIZE;
            m->buffer.cur_buff = 0;
            temp = guththila_reader_read(m->reader, m->buffer.buff[0], 0,
                GUTHTHILA_BUFFER_DEF_SIZE, env);
            m->buffer.data_size[0] = temp;
            for(i = 0; i < no; i++)
            {
                bytes[i] = m->buffer.buff[m->buffer.cur_buff][m->next++
                    - GUTHTHILA_BUFFER_PRE_DATA_SIZE(m->buffer)];
            }
            return (int)no;
            /* We are sure that the difference lies within the int range */
        }
    }
    return -1;
}

GUTHTHILA_EXPORT guththila_char_t *GUTHTHILA_CALL
guththila_get_current_buffer(
    guththila_t * m,
    const axutil_env_t * env)
{
    return guththila_buffer_get(&m->buffer, env);
}

