Commit message: MFH: Fixed bug #46746 (xmlrpc_decode_request outputs non-suppressable error
when given bad data).
CVE: CVE-2019-9020
CWE: CWE-125
Vulnerability description: An issue was discovered in PHP before 5.6.40, 7.x before 7.1.26, 7.2.x before 7.2.14, and 7.3.x before 7.3.1. Invalid input to the function xmlrpc_decode() can lead to an invalid memory access (heap out of bounds read or read after free). This is related to xml_elem_parse_buf in ext/xmlrpc/libxmlrpc/xml_element.c.

Project: php-src
File: xmlrpc.c

const char* XMLRPC_RequestSetMethodName(XMLRPC_REQUEST request, const char* methodName) {
   if(request) {
      simplestring_clear(&request->methodName);
      simplestring_add(&request->methodName, methodName);
      return request->methodName.str;
   }
   return NULL;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_RequestSetData(XMLRPC_REQUEST request, XMLRPC_VALUE data) {
   if(request && data) {
		if (request->io) {
			XMLRPC_CleanupValue (request->io);
		}
      request->io = XMLRPC_CopyValue(data);
      return request->io;
   }
   return NULL;
}

Project: php-src
File: xmlrpc.c

void XMLRPC_CleanupValue(XMLRPC_VALUE value) {
   if(value) {
      if(value->iRefCount > 0) {
         value->iRefCount --;
      }

#ifdef XMLRPC_DEBUG_REFCOUNT
      if(value->id.str) {
			printf ("decremented refcount of %s, now %i\n", value->id.str,
					  value->iRefCount);
      }
      else {
			printf ("decremented refcount of 0x%x, now %i\n", value,
					  value->iRefCount);
      }
#endif

      if(value->type == xmlrpc_vector) {
         if(value->v) {
            if(value->iRefCount == 0) {
               XMLRPC_VALUE cur = (XMLRPC_VALUE)Q_Head(value->v->q);
               while( cur ) {
                  XMLRPC_CleanupValue(cur);
   
                  /* Make sure some idiot didn't include a vector as a child of itself
                   * and thus it would have already free'd these.
                   */
                  if(value->v && value->v->q) {
                     cur = Q_Next(value->v->q);
                  }
                  else {
                     break;
                  }
               }

               Q_Destroy(value->v->q);
               my_free(value->v->q);
               my_free(value->v);
            }
         }
      }


      if(value->iRefCount == 0) {

         /* guard against freeing invalid types */
         switch(value->type) {
            case xmlrpc_empty:
            case xmlrpc_base64:
            case xmlrpc_boolean:
            case xmlrpc_datetime:
            case xmlrpc_double:
            case xmlrpc_int:
            case xmlrpc_string:
            case xmlrpc_vector:
#ifdef XMLRPC_DEBUG_REFCOUNT
               if(value->id.str) {
                  printf("free'd %s\n", value->id.str);
               }
               else {
                  printf("free'd 0x%x\n", value);
               }
#endif 
               simplestring_free(&value->id);
               simplestring_free(&value->str);

               memset(value, 0, sizeof(STRUCT_XMLRPC_VALUE));
               my_free(value);
               break;
            default:
				/* fprintf (stderr,
							"xmlrpc: attempted to free value of invalid type\n"); */
               break;
         }
      }
   }
}

Project: php-src
File: xml_element.c

static void _xmlrpc_endElement(void *userData, const char *name)
{
   xml_elem_data* mydata = (xml_elem_data*)userData;

   if(mydata && mydata->current && mydata->current->parent) {
      Q_PushTail(&mydata->current->parent->children, mydata->current);

      mydata->current = mydata->current->parent;
   }
}

Project: php-src
File: xmlrpc.c

int XMLRPC_GetValueBoolean(XMLRPC_VALUE value) {
    return ((value && value->type == xmlrpc_boolean) ? value->i : 0);
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_VectorNext(XMLRPC_VALUE value) {
   XMLRPC_VALUE xReturn = NULL;
   if(value && value->type == xmlrpc_vector && value->v) {
      xReturn = (XMLRPC_VALUE)Q_Next(value->v->q);
   }
   return xReturn;
}

Project: php-src
File: xmlrpc.c

XMLRPC_SERVER XMLRPC_GetGlobalServer() {
   static XMLRPC_SERVER xsServer = 0;
   if(!xsServer) {
      xsServer = XMLRPC_ServerCreate();
   }
   return xsServer;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_CreateVector(const char* id, XMLRPC_VECTOR_TYPE type) {
   XMLRPC_VALUE val = NULL;

   val = XMLRPC_CreateValueEmpty();
   if(val) {
      if(XMLRPC_SetIsVector(val, type)) {
         if(id) {
            const char *pSVI = NULL;

            pSVI = XMLRPC_SetValueID(val, id, 0);
            if(NULL == pSVI) {
               val = NULL;
            }
         }
      }
      else {
         val = NULL;
      }
   }
   return val;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_VectorGetValueWithID_Case (XMLRPC_VALUE vector, const char *id,
															  XMLRPC_CASE_COMPARISON id_case) {
   if(vector && vector->v && vector->v->q) {
       q_iter qi = Q_Iter_Head_F(vector->v->q);

       while(qi) {
          XMLRPC_VALUE xIter = Q_Iter_Get_F(qi);
          if(xIter && xIter->id.str) {
             if(id_case == xmlrpc_case_sensitive) {
                if(!strcmp(xIter->id.str, id)) {
                   return xIter;
                }
             }
             else if(id_case == xmlrpc_case_insensitive) {
                if(!strcasecmp(xIter->id.str, id)) {
                   return xIter;
                }
             }
          }
          qi = Q_Iter_Next_F(qi);
       }
   }
   return NULL;
}

Project: php-src
File: xmlrpc.c

static int isDuplicateEntry(XMLRPC_VALUE target, XMLRPC_VALUE source) {
   return 0;
}

Project: php-src
File: xmlrpc.c

int XMLRPC_AddValuesToVector(XMLRPC_VALUE target, ...) {
   int iRetval = 0;

   if(target) {
      if(target->type == xmlrpc_vector) {
         XMLRPC_VALUE v = NULL;
         va_list vl;

         va_start(vl, target);

         do {
            v = va_arg(vl, XMLRPC_VALUE);
            if(v) {
               if(!XMLRPC_AddValueToVector(target, v)) {
                  iRetval = 0;
                  break;
               }
            }
			}
			while (v);

         va_end(vl);

         if(NULL == v) {
            iRetval = 1;
         }
      }
   }
   return iRetval;
}

Project: php-src
File: xml_element.c

static void xml_element_serialize(xml_element *el, int (*fptr)(void *data, const char *text, int size), void *data, XML_ELEM_OUTPUT_OPTIONS options, int depth)
{
   int i;
   static STRUCT_XML_ELEM_OUTPUT_OPTIONS default_opts = {xml_elem_pretty, xml_elem_markup_escaping | xml_elem_non_print_escaping, XML_DECL_ENCODING_DEFAULT};
   static char whitespace[] = "                                                                                               "
                              "                                                                                               "
                              "                                                                                               ";
   depth++;

   if(!el) {
      /* fprintf(stderr, "Nothing to write\n"); */
      return;
   }
   if(!options) {
      options = &default_opts;
   }

   /* print xml declaration if at root level */
   if(depth == 1) {
      xml_elem_writefunc(fptr, XML_DECL_START, data, XML_DECL_START_LEN);
      xml_elem_writefunc(fptr, WHITESPACE, data, WHITESPACE_LEN);
      xml_elem_writefunc(fptr, XML_DECL_VERSION, data, XML_DECL_VERSION_LEN);
      if(options->encoding && *options->encoding) {
          xml_elem_writefunc(fptr, WHITESPACE, data, WHITESPACE_LEN);
          xml_elem_writefunc(fptr, XML_DECL_ENCODING_ATTR, data, XML_DECL_ENCODING_ATTR_LEN);
          xml_elem_writefunc(fptr, EQUALS, data, EQUALS_LEN);
          xml_elem_writefunc(fptr, ATTR_DELIMITER, data, ATTR_DELIMITER_LEN);
          xml_elem_writefunc(fptr, options->encoding, data, 0);
          xml_elem_writefunc(fptr, ATTR_DELIMITER, data, ATTR_DELIMITER_LEN);
      }
      xml_elem_writefunc(fptr, XML_DECL_END, data, XML_DECL_END_LEN);
      if(options->verbosity != xml_elem_no_white_space) {
         xml_elem_writefunc(fptr, NEWLINE, data, NEWLINE_LEN);
      }
   }

   if(options->verbosity == xml_elem_pretty && depth > 2) {
         xml_elem_writefunc(fptr, whitespace, data, depth - 2);
   }
   /* begin element */
   xml_elem_writefunc(fptr,START_TOKEN_BEGIN, data, START_TOKEN_BEGIN_LEN);
   if(el->name) {
      xml_elem_writefunc(fptr, el->name, data, 0);

      /* write attrs, if any */
      if(Q_Size(&el->attrs)) {
         xml_element_attr* iter = Q_Head(&el->attrs);
         while( iter ) {
            xml_elem_writefunc(fptr, WHITESPACE, data, WHITESPACE_LEN);
            xml_elem_writefunc(fptr, iter->key, data, 0);
            xml_elem_writefunc(fptr, EQUALS, data, EQUALS_LEN);
            xml_elem_writefunc(fptr, ATTR_DELIMITER, data, ATTR_DELIMITER_LEN);
            xml_elem_writefunc(fptr, iter->val, data, 0);
            xml_elem_writefunc(fptr, ATTR_DELIMITER, data, ATTR_DELIMITER_LEN);

            iter = Q_Next(&el->attrs);
         }
      }
   }
   else {
      xml_elem_writefunc(fptr, "None", data, 0);
   }
   /* if no text and no children, use abbreviated form, eg: <foo/> */
   if(!el->text.len && !Q_Size(&el->children)) {
       xml_elem_writefunc(fptr, EMPTY_START_TOKEN_END, data, EMPTY_START_TOKEN_END_LEN);
   }
   /* otherwise, print element contents */
   else {
       xml_elem_writefunc(fptr, START_TOKEN_END, data, START_TOKEN_END_LEN);

       /* print text, if any */
       if(el->text.len) {
          char* escaped_str = el->text.str;
          int buflen = el->text.len;

          if(options->escaping && options->escaping != xml_elem_cdata_escaping) {
             escaped_str = xml_elem_entity_escape(el->text.str, buflen, &buflen, options->escaping );
             if(!escaped_str) {
                escaped_str = el->text.str;
             }
          }

          if(options->escaping & xml_elem_cdata_escaping) {
             xml_elem_writefunc(fptr, CDATA_BEGIN, data, CDATA_BEGIN_LEN);
          }

          xml_elem_writefunc(fptr, escaped_str, data, buflen);

          if(escaped_str != el->text.str) {
             my_free(escaped_str);
          }

          if(options->escaping & xml_elem_cdata_escaping) {
             xml_elem_writefunc(fptr, CDATA_END, data, CDATA_END_LEN);
          }
       }
       /* no text, so print child elems */
       else {
          xml_element *kids = Q_Head(&el->children);
          i = 0;
          while( kids ) {
             if(i++ == 0) {
                if(options->verbosity != xml_elem_no_white_space) {
                   xml_elem_writefunc(fptr, NEWLINE, data, NEWLINE_LEN);
                }
             }
             xml_element_serialize(kids, fptr, data, options, depth);
             kids = Q_Next(&el->children);
          }
          if(i) {
             if(options->verbosity == xml_elem_pretty && depth > 2) {
                   xml_elem_writefunc(fptr, whitespace, data, depth - 2);
             }
          }
       }

       xml_elem_writefunc(fptr, END_TOKEN_BEGIN, data, END_TOKEN_BEGIN_LEN);
       xml_elem_writefunc(fptr,el->name ? el->name : "None", data, 0);
       xml_elem_writefunc(fptr, END_TOKEN_END, data, END_TOKEN_END_LEN);
   }
   if(options->verbosity != xml_elem_no_white_space) {
      xml_elem_writefunc(fptr, NEWLINE, data, NEWLINE_LEN);
   }
}

Project: php-src
File: xmlrpc.c

const char* XMLRPC_GetResponseFaultString (XMLRPC_REQUEST response) {
   return XMLRPC_GetValueFaultString( XMLRPC_RequestGetData(response) );
}

Project: php-src
File: xmlrpc.c

void XMLRPC_SetValueBase64(XMLRPC_VALUE value, const char* s, int len) {
   if(value && s) {
      simplestring_clear(&value->str);
      (len > 0) ? simplestring_addn(&value->str, s, len) :
                  simplestring_add(&value->str, s);
      value->type = xmlrpc_base64;
   }
}

Project: php-src
File: xmlrpc.c

int XMLRPC_SetIsVector(XMLRPC_VALUE value, XMLRPC_VECTOR_TYPE type) {
   int bSuccess = 0;

	if (value) {
		/* we can change the type so long as nothing is currently stored. */
		if(value->type == xmlrpc_vector) {
			if(value->v) {
				if(!Q_Size(value->v->q)) {
					value->v->type = type;
				}
			}
		}
		else {
      value->v = calloc(1, sizeof(STRUCT_XMLRPC_VECTOR));
      if(value->v) {
         value->v->q = (queue*)malloc(sizeof(queue));
         if(value->v->q) {
            Q_Init(value->v->q);
            value->v->type = type;
            value->type = xmlrpc_vector;
            bSuccess = 1;
         }
      }
   }
	}

   return bSuccess;
}

Project: php-src
File: xmlrpc.c

XMLRPC_REQUEST XMLRPC_RequestNew() {
   XMLRPC_REQUEST xRequest = calloc(1, sizeof(STRUCT_XMLRPC_REQUEST));
   if(xRequest) {
      simplestring_init(&xRequest->methodName);
   }
   return xRequest;
}

Project: php-src
File: xml_element.c

void xml_elem_free_non_recurse(xml_element* root) {
   if(root) {
      xml_element_attr* attrs = Q_Head(&root->attrs);
      while(attrs) {
         my_free(attrs->key);
         my_free(attrs->val);
         my_free(attrs);
         attrs = Q_Next(&root->attrs);
      }

      Q_Destroy(&root->children);
      Q_Destroy(&root->attrs);
      if(root->name) {
          free((char *)root->name);
          root->name = NULL;
      }
      simplestring_free(&root->text);
      my_free(root);
   }
}

Project: php-src
File: xmlrpc.c

int XMLRPC_ServerRegisterMethod(XMLRPC_SERVER server, const char *name, XMLRPC_Callback cb) {
   if(server && name && cb) {

      server_method* sm = malloc(sizeof(server_method));
      
      if(sm) {
         sm->name = strdup(name);
         sm->method = cb;
         sm->desc = NULL;

         return Q_PushTail(&server->methodlist, sm);
      }
   }
   return 0;
}

Project: php-src
File: xmlrpc.c

const char* type_to_str(XMLRPC_VALUE_TYPE type, XMLRPC_VECTOR_TYPE vtype) {
    switch(type) {
       case xmlrpc_none:
          return "none";
       case xmlrpc_empty:
          return "empty";
       case xmlrpc_base64:
          return "base64";
       case xmlrpc_boolean:
          return "boolean";
       case xmlrpc_datetime:
          return "datetime";
       case xmlrpc_double:
          return "double";
       case xmlrpc_int:
          return "int";
       case xmlrpc_string:
          return "string";
       case xmlrpc_vector:
          switch(vtype) {
             case xmlrpc_vector_none:
                return "none";
             case xmlrpc_vector_array:
                return "array";
             case xmlrpc_vector_mixed:
                return "mixed vector (struct)";
             case xmlrpc_vector_struct:
                return "struct";
          }
    }
    return "unknown";
}

Project: php-src
File: xml_element.c

xml_element* xml_elem_new() {
   xml_element* elem = calloc(1, sizeof(xml_element));
   if(elem) {
      Q_Init(&elem->children);
      Q_Init(&elem->attrs);
      simplestring_init(&elem->text);

      /* init empty string in case we don't find any char data */
      simplestring_addn(&elem->text, "", 0);
   }
   return elem;
}

Project: php-src
File: xml_element.c

static char* xml_elem_entity_escape(const char* buf, int old_len, int *newlen, XML_ELEM_ESCAPING flags) {
  char *pRetval = 0;
  int iNewBufLen=0;

#define should_escape(c, flag) ( ((flag & xml_elem_markup_escaping) && markup(c)) || \
                                 ((flag & xml_elem_non_ascii_escaping) && non_ascii(c)) || \
                                 ((flag & xml_elem_non_print_escaping) && non_print(c)) )

  if(buf && *buf) {
    const unsigned char *bufcopy;
    char *NewBuffer;
    int ToBeXmlEscaped=0;
    int iLength;
    bufcopy = buf;
    iLength= old_len ? old_len : strlen(buf);
    while(*bufcopy) {
      if( should_escape(*bufcopy, flags) ) {
	/* the length will increase by length of xml escape - the character length */
	iLength += entity_length(*bufcopy);
	ToBeXmlEscaped=1;
      }
      bufcopy++;
    }

    if(ToBeXmlEscaped) {

      NewBuffer= malloc(iLength+1);
      if(NewBuffer) {
	bufcopy=buf;
	while(*bufcopy) {
	  if(should_escape(*bufcopy, flags)) {
	    iNewBufLen += create_xml_escape(NewBuffer+iNewBufLen,*bufcopy);
	  }
	  else {
	    NewBuffer[iNewBufLen++]=*bufcopy;
	  }
	  bufcopy++;
	}
	NewBuffer[iNewBufLen] = 0;
	pRetval = NewBuffer;
      }
    }
  }

  if(newlen) {
     *newlen = iNewBufLen;
  }

  return pRetval;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_CreateValueDateTime_ISO8601(const char* id, const char *s) {
   XMLRPC_VALUE val = XMLRPC_CreateValueEmpty();
   if(val) {
      XMLRPC_SetValueDateTime_ISO8601(val, s);
      if(id) {
         XMLRPC_SetValueID(val, id, 0);
      }
   }
   return val;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_CreateValueDateTime(const char* id, time_t time) {
   XMLRPC_VALUE val = XMLRPC_CreateValueEmpty();
   if(val) {
      XMLRPC_SetValueDateTime(val, time);
      if(id) {
         XMLRPC_SetValueID(val, id, 0);
      }
   }
   return val;
}

Project: php-src
File: xml_element.c

static int file_out_fptr(void *f, const char *text, int size)
{
   fputs(text, (FILE *)f);
   return 0;
}

Project: php-src
File: xmlrpc.c

XMLRPC_REQUEST_OUTPUT_OPTIONS XMLRPC_RequestGetOutputOptions(XMLRPC_REQUEST request) {
   return request ? &request->output : NULL;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VECTOR_TYPE XMLRPC_GetVectorType(XMLRPC_VALUE value) {
   return(value && value->v) ? value->v->type : xmlrpc_none;
}

Project: php-src
File: xmlrpc.c

int XMLRPC_GetValueFaultCode (XMLRPC_VALUE value) {
   return XMLRPC_VectorGetIntWithID(value, "faultCode");
}

Project: php-src
File: xmlrpc.c

server_method* find_method(XMLRPC_SERVER server, const char* name) {
   server_method* sm;

   q_iter qi = Q_Iter_Head_F(&server->methodlist);

   while( qi ) {
      sm = Q_Iter_Get_F(qi);
      if(sm && !strcmp(sm->name, name)) {
         return sm;
      }
      qi = Q_Iter_Next_F(qi);
   }
   return NULL;
}

Project: php-src
File: xmlrpc.c

int XMLRPC_VectorRemoveValue(XMLRPC_VALUE vector, XMLRPC_VALUE value) {
   if(vector && vector->v && vector->v->q && value) {
       q_iter qi = Q_Iter_Head_F(vector->v->q);

       while(qi) {
          XMLRPC_VALUE xIter = Q_Iter_Get_F(qi);
          if(xIter == value) {
             XMLRPC_CleanupValue(xIter);
             Q_Iter_Del(vector->v->q, qi);
             return 1;
          }
          qi = Q_Iter_Next_F(qi);
       }
   }
   return 0;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_CreateValueString(const char* id, const char* val, int len) {
   XMLRPC_VALUE value = NULL;
   if(val) {
      value = XMLRPC_CreateValueEmpty();
      if(value) {
         XMLRPC_SetValueString(value, val, len);
         if(id) {
            XMLRPC_SetValueID(value, id, 0);
         }
      }
   }
   return value;
}

Project: php-src
File: xmlrpc.c

void XMLRPC_RequestFree(XMLRPC_REQUEST request, int bFreeIO) {
   if(request) {
      simplestring_free(&request->methodName);

      if(request->io && bFreeIO) {
         XMLRPC_CleanupValue(request->io);
      }
      if(request->error) {
         XMLRPC_CleanupValue(request->error);
      }
      my_free(request);
   }
}

Project: php-src
File: xmlrpc.c

const char* XMLRPC_GetValueString(XMLRPC_VALUE value) {
    return ((value && value->type == xmlrpc_string) ? value->str.str : 0);
}

Project: php-src
File: xmlrpc.c

const char *XMLRPC_SetValueString(XMLRPC_VALUE value, const char* val, int len) {
   char *pRetval = NULL;
   if(value && val) {
      simplestring_clear(&value->str);
      (len > 0) ? simplestring_addn(&value->str, val, len) :
                  simplestring_add(&value->str, val);
      value->type = xmlrpc_string;
      pRetval = (char *)value->str.str;
   }

   return pRetval;
}

Project: php-src
File: xmlrpc.c

void XMLRPC_Free(void* mem) {
   my_free(mem);
}

Project: php-src
File: xmlrpc.c

double XMLRPC_GetValueDouble(XMLRPC_VALUE value) {
    return ((value && value->type == xmlrpc_double) ? value->d : 0);
}

Project: php-src
File: xmlrpc.c

XMLRPC_REQUEST XMLRPC_REQUEST_FromXML (const char *in_buf, int len, 
													XMLRPC_REQUEST_INPUT_OPTIONS in_options) {
   XMLRPC_REQUEST request = XMLRPC_RequestNew();
   STRUCT_XML_ELEM_ERROR error = {0};

   if(request) {
		xml_element *root_elem =
		xml_elem_parse_buf (in_buf, len,
								  (in_options ? &in_options->xml_elem_opts : NULL),
								  &error);

      if(root_elem) {
         if(!strcmp(root_elem->name, "simpleRPC")) {
            request->output.version = xmlrpc_version_simple;
            xml_element_to_DANDARPC_REQUEST(request, root_elem);
         }
			else if (!strcmp (root_elem->name, "SOAP-ENV:Envelope")) {
				request->output.version = xmlrpc_version_soap_1_1;
				xml_element_to_SOAP_REQUEST (request, root_elem);
			}
         else {
            request->output.version = xmlrpc_version_1_0;
            xml_element_to_XMLRPC_REQUEST(request, root_elem);
         }
         xml_elem_free(root_elem);
      }
      else {
         if(error.parser_error) {
				XMLRPC_RequestSetError (request, map_expat_errors (&error));
         }
      }
   }

   return request;
}

Project: php-src
File: xmlrpc.c

const char* XMLRPC_GetValueFaultString (XMLRPC_VALUE value) {
   return XMLRPC_VectorGetStringWithID(value, "faultString");
}

Project: php-src
File: xmlrpc.c

char* XMLRPC_REQUEST_ToXML(XMLRPC_REQUEST request, int* buf_len) {
      char* pRet = NULL;
	if (request) {
		xml_element *root_elem = NULL;
		if (request->output.version == xmlrpc_version_simple) {
			root_elem = DANDARPC_REQUEST_to_xml_element (request);
		}
		else if (request->output.version == xmlrpc_version_1_0 ||
					request->output.version == xmlrpc_version_none) {
			root_elem = XMLRPC_REQUEST_to_xml_element (request);
		}
		else if (request->output.version == xmlrpc_version_soap_1_1) {
			root_elem = SOAP_REQUEST_to_xml_element (request);
		}

      if(root_elem) {
			pRet =
			xml_elem_serialize_to_string (root_elem,
													&request->output.xml_elem_opts,
													buf_len);
         xml_elem_free(root_elem);
      }
   }
	return pRet;
}

Project: php-src
File: xmlrpc.c

void XMLRPC_ServerDestroy(XMLRPC_SERVER server) {
   if(server) {
      doc_method* dm = Q_Head(&server->docslist);
      server_method* sm = Q_Head(&server->methodlist);
      while( dm ) {
         my_free(dm);
         dm = Q_Next(&server->docslist);
      }
      while( sm ) {
         if(sm->name) {
            my_free(sm->name);
         }
         if(sm->desc) {
            XMLRPC_CleanupValue(sm->desc);
         }
         my_free(sm);
         sm = Q_Next(&server->methodlist);
      }
      if(server->xIntrospection) {
         XMLRPC_CleanupValue(server->xIntrospection);
      }

      Q_Destroy(&server->methodlist);
      Q_Destroy(&server->docslist);
      my_free(server);
   }
}

Project: php-src
File: xmlrpc.c

int XMLRPC_GetValueStringLen(XMLRPC_VALUE value) {
    return ((value) ? value->str.len : 0);
}

Project: php-src
File: xml_element.c

static void _xmlrpc_startElement(void *userData, const char *name, const char **attrs)
{
   xml_element *c;
   xml_elem_data* mydata = (xml_elem_data*)userData;
   const char** p = attrs;

   if(mydata) {
      c = mydata->current;

      mydata->current = xml_elem_new();
      mydata->current->name = (char*)strdup(name);
      mydata->current->parent = c;

      /* init attrs */
      while(p && *p) {
         xml_element_attr* attr = malloc(sizeof(xml_element_attr));
         if(attr) {
            attr->key = strdup(*p);
            attr->val = strdup(*(p+1));
            Q_PushTail(&mydata->current->attrs, attr);

            p += 2;
         }
      }
   }
}

Project: php-src
File: xml_element.c

void xml_elem_free(xml_element* root) {
   if(root) {
      xml_element* kids = Q_Head(&root->children);
      while(kids) {
         xml_elem_free(kids);
         kids = Q_Next(&root->children);
      }
      xml_elem_free_non_recurse(root);
   }
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_UtilityCreateFault(int fault_code, const char* fault_string) {
   XMLRPC_VALUE xOutput = NULL;

   char* string = NULL;
   simplestring description;
   simplestring_init(&description);

   switch (fault_code) {
	case xmlrpc_error_parse_xml_syntax:
		string = xmlrpc_error_parse_xml_syntax_str;
		break;
	case xmlrpc_error_parse_unknown_encoding:
		string = xmlrpc_error_parse_unknown_encoding_str;
		break;
	case xmlrpc_error_parse_bad_encoding:
		string = xmlrpc_error_parse_bad_encoding_str;
		break;
	case xmlrpc_error_invalid_xmlrpc:
		string = xmlrpc_error_invalid_xmlrpc_str;
		break;
	case xmlrpc_error_unknown_method:
		string = xmlrpc_error_unknown_method_str;
		break;
	case xmlrpc_error_invalid_params:
		string = xmlrpc_error_invalid_params_str;
		break;
	case xmlrpc_error_internal_server:
		string = xmlrpc_error_internal_server_str;
		break;
	case xmlrpc_error_application:
		string = xmlrpc_error_application_str;
		break;
	case xmlrpc_error_system:
		string = xmlrpc_error_system_str;
		break;
	case xmlrpc_error_transport:
		string = xmlrpc_error_transport_str;
		break;
   }

   simplestring_add(&description, string);

   if(string && fault_string) {
      simplestring_add(&description, "\n\n");
   }
   simplestring_add(&description, fault_string);


   if(description.len) {
      xOutput = XMLRPC_CreateVector(NULL, xmlrpc_vector_struct);

		XMLRPC_VectorAppendString (xOutput, "faultString", description.str,
											description.len);
      XMLRPC_VectorAppendInt(xOutput, "faultCode", fault_code);
   }

   simplestring_free(&description);

   return xOutput;
}

Project: php-src
File: xmlrpc.c

static time_t mkgmtime(struct tm *tm)
{
    static const int mdays[12] = {0,31,59,90,120,151,181,212,243,273,304,334};

    return ((((((tm->tm_year - 70) * 365) + mdays[tm->tm_mon] + tm->tm_mday-1 +
                  (tm->tm_year-68-1+(tm->tm_mon>=2))/4) * 24) + tm->tm_hour) * 60 +
        tm->tm_min) * 60 + tm->tm_sec;
}

Project: php-src
File: xmlrpc.c

const char* XMLRPC_GetValueID(XMLRPC_VALUE value) {
    return (const char*)((value && value->id.len) ? value->id.str : 0);
}

Project: php-src
File: xmlrpc.c

XMLRPC_REQUEST_TYPE XMLRPC_RequestGetRequestType(XMLRPC_REQUEST request) {
   return request ? request->request_type : xmlrpc_request_none;
}

Project: php-src
File: xmlrpc.c

const char*  XMLRPC_GetVersionString() {
   return XMLRPC_VERSION_STR;
}

Project: php-src
File: xml_element.c

static int simplestring_out_fptr(void *f, const char *text, int size)
{
   simplestring* buf = (simplestring*)f;
   if(buf) {
      simplestring_addn(buf, text, size);
   }
   return 0;
}

Project: php-src
File: xmlrpc.c

int XMLRPC_ValueIsFault (XMLRPC_VALUE value) {
   if( XMLRPC_VectorGetValueWithID(value, "faultCode") &&
       XMLRPC_VectorGetValueWithID(value, "faultString") ) {
      return 1;
   }
   return 0;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE_TYPE XMLRPC_GetValueType(XMLRPC_VALUE value) {
   return value ? value->type : xmlrpc_empty;
}

Project: php-src
File: xml_element.c

static void _xmlrpc_charHandler(void *userData,
                        const char *s,
                        int len)
{
   xml_elem_data* mydata = (xml_elem_data*)userData;
   if(mydata && mydata->current) {

      /* Check if we need to decode utf-8 parser output to another encoding */
      if(mydata->needs_enc_conversion && mydata->input_options->encoding) {
         int new_len = 0;
         char* add_text = utf8_decode(s, len, &new_len, mydata->input_options->encoding);
         if(add_text) {
            len = new_len;
            simplestring_addn(&mydata->current->text, add_text, len);
            free(add_text);
            return;
         }
      }
      simplestring_addn(&mydata->current->text, s, len);
   }
}

Project: php-src
File: xmlrpc.c

XMLRPC_Callback XMLRPC_ServerFindMethod(XMLRPC_SERVER server, const char* callName) {
   if(server && callName) {
      q_iter qi = Q_Iter_Head_F(&server->methodlist);
      while( qi ) {
         server_method* sm = Q_Iter_Get_F(qi);
         if(sm && !strcmp(sm->name, callName)) {
            return sm->method;
         }
         qi = Q_Iter_Next_F(qi);
      }
   }
   return NULL;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_CreateValueInt(const char* id, int i) {
   XMLRPC_VALUE val = XMLRPC_CreateValueEmpty();
   if(val) {
      XMLRPC_SetValueInt(val, i);
      if(id) {
         XMLRPC_SetValueID(val, id, 0);
      }
   }
   return val;
}

Project: php-src
File: xmlrpc.c

int XMLRPC_GetResponseFaultCode(XMLRPC_REQUEST response) {
   return XMLRPC_GetValueFaultCode( XMLRPC_RequestGetData(response) );
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_CreateValueEmpty() {
   XMLRPC_VALUE v = calloc(1, sizeof(STRUCT_XMLRPC_VALUE));
   if(v) {
#ifdef XMLRPC_DEBUG_REFCOUNT
		printf ("calloc'd 0x%x\n", v);
#endif
      v->type = xmlrpc_empty;
      simplestring_init(&v->id);
      simplestring_init(&v->str);
   }
   return v;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_CreateValueBase64(const char* id, const char* s, int len) {
   XMLRPC_VALUE val = XMLRPC_CreateValueEmpty();
   if(val) {
      XMLRPC_SetValueBase64(val, s, len);
      if(id) {
         XMLRPC_SetValueID(val, id, 0);
      }
   }
   return val;
}

Project: php-src
File: xmlrpc.c

XMLRPC_REQUEST_TYPE XMLRPC_RequestSetRequestType (XMLRPC_REQUEST request,
																  XMLRPC_REQUEST_TYPE type) {
   if(request) {
      request->request_type = type;
      return request->request_type;
   }
   return xmlrpc_request_none;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_VectorRewind(XMLRPC_VALUE value) {
   XMLRPC_VALUE xReturn = NULL;
   if(value && value->type == xmlrpc_vector && value->v) {
      xReturn = (XMLRPC_VALUE)Q_Head(value->v->q);
   }
   return xReturn;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE_TYPE_EASY XMLRPC_GetValueTypeEasy (XMLRPC_VALUE value) {
	if (value) {
		switch (value->type) {
		case xmlrpc_vector:
			switch (value->v->type) {
			case xmlrpc_vector_none:
				return xmlrpc_type_none;
			case xmlrpc_vector_struct:
				return xmlrpc_type_struct;
			case xmlrpc_vector_mixed:
				return xmlrpc_type_mixed;
			case xmlrpc_vector_array:
				return xmlrpc_type_array;
			}
		default:
			/* evil cast, but we know they are the same */
			return(XMLRPC_VALUE_TYPE_EASY) value->type;
		}
	}
	return xmlrpc_none;
}

Project: php-src
File: xmlrpc.c

int XMLRPC_ResponseIsFault(XMLRPC_REQUEST response) {
   return XMLRPC_ValueIsFault( XMLRPC_RequestGetData(response) );
}

Project: php-src
File: xmlrpc.c

int XMLRPC_AddValueToVector(XMLRPC_VALUE target, XMLRPC_VALUE source) {
   if(target && source) {
      if(target->type == xmlrpc_vector && target->v && 
         target->v->q && target->v->type != xmlrpc_vector_none) {

         /* guard against putting value of unknown type into vector */
         switch(source->type) {
            case xmlrpc_empty:
            case xmlrpc_base64:
            case xmlrpc_boolean:
            case xmlrpc_datetime:
            case xmlrpc_double:
            case xmlrpc_int:
            case xmlrpc_string:
            case xmlrpc_vector:
               /* Guard against putting a key/val pair into an array vector */
               if( !(source->id.len && target->v->type == xmlrpc_vector_array) ) {
					if (isDuplicateEntry (target, source)
						 || Q_PushTail (target->v->q, XMLRPC_CopyValue (source))) {
                     return 1;
                  }
               }
               else {
					/* fprintf (stderr,
								"xmlrpc: attempted to add key/val pair to vector of type array\n"); */
               }
               break;
            default:
				/* fprintf (stderr,
							"xmlrpc: attempted to add value of unknown type to vector\n"); */
               break;
         }
      }
   }
   return 0;
}

Project: php-src
File: xmlrpc.c

const char *XMLRPC_SetValueID_Case(XMLRPC_VALUE value, const char* id, int len, XMLRPC_CASE id_case) {
   const char* pRetval = NULL;
   if(value) {
      if(id) {
         simplestring_clear(&value->id);
         (len > 0) ? simplestring_addn(&value->id, id, len) :
                     simplestring_add(&value->id, id);

         /* upper or lower case string in place if required. could be a seperate func. */
         if(id_case == xmlrpc_case_lower || id_case == xmlrpc_case_upper) {
            int i;
            for(i = 0; i < value->id.len; i++) {
					value->id.str[i] =
					(id_case ==
					 xmlrpc_case_lower) ? tolower (value->id.
															 str[i]) : toupper (value->
																					  id.
																					  str[i]);
            }
         }

         pRetval = value->id.str;

#ifdef XMLRPC_DEBUG_REFCOUNT
         printf("set value id: %s\n", pRetval);
#endif 
      }
   }

   return pRetval;
}

Project: php-src
File: xml_element.c

static int create_xml_escape(char *pString, unsigned char c)
{ 
  int counter = 0;

  pString[counter++] = '&';
  pString[counter++] = '#';
  if(c >= 100) {
    pString[counter++] = c / 100 + '0';
    c = c % 100;
  }
  pString[counter++] = c / 10 + '0';
  c = c % 10;

  pString[counter++] = c + '0';
  pString[counter++] = ';';
  return counter; 
}

Project: php-src
File: xml_element.c

xml_element* xml_elem_parse_buf(const char* in_buf, int len, XML_ELEM_INPUT_OPTIONS options, XML_ELEM_ERROR error)
{
   xml_element* xReturn = NULL;
   char buf[100] = "";
   static STRUCT_XML_ELEM_INPUT_OPTIONS default_opts = {encoding_utf_8};

   if(!options) {
      options = &default_opts;
   }

   if(in_buf) {
      XML_Parser parser;
      xml_elem_data mydata = {0};

      parser = XML_ParserCreate(NULL);

      mydata.root = xml_elem_new();
      mydata.current = mydata.root;
      mydata.input_options = options;
      mydata.needs_enc_conversion = options->encoding && strcmp(options->encoding, encoding_utf_8);

      XML_SetElementHandler(parser, (XML_StartElementHandler)_xmlrpc_startElement, (XML_EndElementHandler)_xmlrpc_endElement);
      XML_SetCharacterDataHandler(parser, (XML_CharacterDataHandler)_xmlrpc_charHandler);

      /* pass the xml_elem_data struct along */
      XML_SetUserData(parser, (void*)&mydata);

      if(!len) {
         len = strlen(in_buf);
      }

      /* parse the XML */
      if(XML_Parse(parser, in_buf, len, 1) == 0) {
         enum XML_Error err_code = XML_GetErrorCode(parser);
         int line_num = XML_GetCurrentLineNumber(parser);
         int col_num = XML_GetCurrentColumnNumber(parser);
         long byte_idx = XML_GetCurrentByteIndex(parser);
         int byte_total = XML_GetCurrentByteCount(parser);
         const char * error_str = XML_ErrorString(err_code);
         if(byte_idx >= 0) {
             snprintf(buf, 
                      sizeof(buf),
                      "\n\tdata beginning %ld before byte index: %s\n",
                      byte_idx > 10  ? 10 : byte_idx,
                      in_buf + (byte_idx > 10 ? byte_idx - 10 : byte_idx));
         }
/*
         fprintf(stderr, "expat reports error code %i\n"
                "\tdescription: %s\n"
                "\tline: %i\n"
                "\tcolumn: %i\n"
                "\tbyte index: %ld\n"
                "\ttotal bytes: %i\n%s ",
                err_code, error_str, line_num, 
                col_num, byte_idx, byte_total, buf);
*/

          /* error condition */
          if(error) {
              error->parser_code = (long)err_code;
              error->line = line_num;
              error->column = col_num;
              error->byte_index = byte_idx;
              error->parser_error = error_str;
          }
      }
      else {
         xReturn = (xml_element*)Q_Head(&mydata.root->children);
         xReturn->parent = NULL;
      }

      XML_ParserFree(parser);


      xml_elem_free_non_recurse(mydata.root);
   }

   return xReturn;
}

Project: php-src
File: xmlrpc.c

int XMLRPC_GetValueInt(XMLRPC_VALUE value) {
    return ((value && value->type == xmlrpc_int) ? value->i : 0);
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_CopyValue(XMLRPC_VALUE value) {
   if(value) {
      value->iRefCount ++;
#ifdef XMLRPC_DEBUG_REFCOUNT
      if(value->id.str) {
			printf ("incremented refcount of %s, now %i\n", value->id.str,
					  value->iRefCount);
		}
		else {
			printf ("incremented refcount of 0x%x, now %i\n", value,
					  value->iRefCount);
      }
#endif
   }
   return value;
}

Project: php-src
File: xmlrpc.c

static int date_to_ISO8601 (time_t value, char *buf, int length) {
   struct tm *tm, tmbuf;
   tm = php_gmtime_r(&value, &tmbuf);
   if (!tm) {
	   return 0;
   }
#if 0  /* TODO: soap seems to favor this method. xmlrpc the latter. */
	return strftime (buf, length, "%Y-%m-%dT%H:%M:%SZ", tm);
#else
   return strftime(buf, length, "%Y%m%dT%H:%M:%SZ", tm);
#endif
}

Project: php-src
File: xmlrpc.c

const char* XMLRPC_RequestGetMethodName(XMLRPC_REQUEST request) {
   return request ? request->methodName.str : NULL;
}

Project: php-src
File: xmlrpc.c

char* XMLRPC_VALUE_ToXML(XMLRPC_VALUE val, int* buf_len) {
   xml_element *root_elem = XMLRPC_VALUE_to_xml_element(val);
   char* pRet = NULL;

   if(root_elem) {
      pRet = xml_elem_serialize_to_string(root_elem, NULL, buf_len);
      xml_elem_free(root_elem);
   }
   return pRet;
}

Project: php-src
File: xmlrpc.c

const char* XMLRPC_GetValueDateTime_ISO8601(XMLRPC_VALUE value) {
    return ((value && value->type == xmlrpc_datetime) ? value->str.str : 0);
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_CreateValueDouble(const char* id, double d) {
   XMLRPC_VALUE val = XMLRPC_CreateValueEmpty();
   if(val) {
      XMLRPC_SetValueDouble(val, d);
      if(id) {
         XMLRPC_SetValueID(val, id, 0);
      }
   }
   return val;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_RequestSetError (XMLRPC_REQUEST request, XMLRPC_VALUE error) {
	if (request && error) {
		if (request->error) {
			XMLRPC_CleanupValue (request->error);
		}
		request->error = XMLRPC_CopyValue (error);
		return request->error;
	}
	return NULL;
}

Project: php-src
File: xmlrpc.c

XMLRPC_CASE XMLRPC_SetDefaultIdCase(XMLRPC_CASE id_case) {
   XMLRPC_OPTIONS options = XMLRPC_GetDefaultOptions();
   options->id_case = id_case;
   return options->id_case;
}

Project: php-src
File: xmlrpc.c

XMLRPC_CASE XMLRPC_GetDefaultIdCase() {
   XMLRPC_OPTIONS options = XMLRPC_GetDefaultOptions();
   return options->id_case;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_CreateValueBoolean(const char* id, int i) {
   XMLRPC_VALUE val = XMLRPC_CreateValueEmpty();
   if(val) {
      XMLRPC_SetValueBoolean(val, i);
      if(id) {
         XMLRPC_SetValueID(val, id, 0);
      }
   }
   return val;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_VALUE_FromXML (const char *in_buf, int len, XMLRPC_REQUEST_INPUT_OPTIONS in_options) {
   XMLRPC_VALUE xResponse = NULL;
   XMLRPC_REQUEST req = XMLRPC_REQUEST_FromXML(in_buf, len, in_options);

   if(req) {
      xResponse = req->io;
      XMLRPC_RequestFree(req, 0);
   }
   return xResponse;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_ServerCallMethod(XMLRPC_SERVER server, XMLRPC_REQUEST request, void* userData) {
   XMLRPC_VALUE xReturn = NULL;

   /* check for error set during request parsing / generation */
   if(request && request->error) {
      xReturn = XMLRPC_CopyValue(request->error);
   }
	else if (server && request) {
		XMLRPC_Callback cb =
		XMLRPC_ServerFindMethod (server, request->methodName.str);
      if(cb) {
         xReturn = cb(server, request, userData);
      }
      else {
			xReturn =
			XMLRPC_UtilityCreateFault (xmlrpc_error_unknown_method,
												request->methodName.str);
      }
   }
   return xReturn;
}

Project: php-src
File: xmlrpc.c

XMLRPC_CASE_COMPARISON XMLRPC_SetDefaultIdCaseComparison(XMLRPC_CASE_COMPARISON id_case_compare) {
   XMLRPC_OPTIONS options = XMLRPC_GetDefaultOptions();
   options->id_case_compare = id_case_compare;
   return options->id_case_compare;
}

Project: php-src
File: xml_element.c

void xml_elem_serialize_to_stream(xml_element *el, FILE *output, XML_ELEM_OUTPUT_OPTIONS options)
{
   xml_element_serialize(el, file_out_fptr, (void *)output, options, 0);
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_RequestGetData(XMLRPC_REQUEST request) {
   return request ? request->io : NULL;
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_DupValueNew (XMLRPC_VALUE xSource) {
	XMLRPC_VALUE xReturn = NULL;
	if (xSource) {
		xReturn = XMLRPC_CreateValueEmpty ();
		if (xSource->id.len) {
			XMLRPC_SetValueID (xReturn, xSource->id.str, xSource->id.len);
		}

		switch (xSource->type) {
		case xmlrpc_int:
		case xmlrpc_boolean:
			XMLRPC_SetValueInt (xReturn, xSource->i);
			break;
		case xmlrpc_string:
		case xmlrpc_base64:
			XMLRPC_SetValueString (xReturn, xSource->str.str, xSource->str.len);
			break;
		case xmlrpc_datetime:
			XMLRPC_SetValueDateTime (xReturn, xSource->i);
			break;
		case xmlrpc_double:
			XMLRPC_SetValueDouble (xReturn, xSource->d);
			break;
		case xmlrpc_vector:
			{
				q_iter qi = Q_Iter_Head_F (xSource->v->q);
				XMLRPC_SetIsVector (xReturn, xSource->v->type);

				while (qi) {
					XMLRPC_VALUE xIter = Q_Iter_Get_F (qi);
					XMLRPC_AddValueToVector (xReturn, XMLRPC_DupValueNew (xIter));
					qi = Q_Iter_Next_F (qi);
				}
			}
			break;
		default:
			break;
		}
	}
	return xReturn;
}

Project: php-src
File: xmlrpc.c

time_t XMLRPC_GetValueDateTime(XMLRPC_VALUE value) {
    return (time_t)((value && value->type == xmlrpc_datetime) ? value->i : 0);
}

Project: php-src
File: xml_element.c

char* xml_elem_serialize_to_string(xml_element *el, XML_ELEM_OUTPUT_OPTIONS options, int *buf_len)
{
   simplestring buf;
   simplestring_init(&buf);

   xml_element_serialize(el, simplestring_out_fptr, (void *)&buf, options, 0);

   if(buf_len) {
      *buf_len = buf.len;
   }

   return buf.str;
}

Project: php-src
File: xmlrpc.c

XMLRPC_SERVER XMLRPC_ServerCreate() {
   XMLRPC_SERVER server = calloc(1, sizeof(STRUCT_XMLRPC_SERVER));
   if(server) {
      Q_Init(&server->methodlist);
      Q_Init(&server->docslist);

      /* register system methods */
      xsm_register(server);
   }
   return server;
}

Project: php-src
File: xml_element.c

static int xml_elem_writefunc(int (*fptr)(void *data, const char *text, int size), const char *text, void *data, int len)
{
   return fptr && text ? fptr(data, text, len ? len : strlen(text)) : 0;
}

Project: php-src
File: xmlrpc.c

XMLRPC_CASE_COMPARISON XMLRPC_GetDefaultIdCaseComparison() {
   XMLRPC_OPTIONS options = XMLRPC_GetDefaultOptions();
   return options->id_case_compare;
}

Project: php-src
File: xmlrpc.c

int XMLRPC_VectorSize(XMLRPC_VALUE value) {
   int size = 0;
   if(value && value->type == xmlrpc_vector && value->v) {
      size = Q_Size(value->v->q);
   }
   return size;
}

Project: php-src
File: xmlrpc.c

static XMLRPC_VALUE map_expat_errors(XML_ELEM_ERROR error) {
   XMLRPC_VALUE xReturn = NULL;
   if(error) {
      XMLRPC_ERROR_CODE code;
      char buf[1024];
      snprintf(buf, sizeof(buf), 
               "error occurred at line %ld, column %ld, byte index %ld", 
					 error->line, error->column, error->byte_index);

      /* expat specific errors */
      switch(error->parser_code) {
      case XML_ERROR_UNKNOWN_ENCODING:
         code = xmlrpc_error_parse_unknown_encoding;
         break;
      case XML_ERROR_INCORRECT_ENCODING:
         code = xmlrpc_error_parse_bad_encoding;
         break;
      default:
         code = xmlrpc_error_parse_xml_syntax;
         break;
      }
      xReturn = XMLRPC_UtilityCreateFault(code, buf);
   }
   return xReturn;
}

Project: php-src
File: xmlrpc.c

static XMLRPC_OPTIONS XMLRPC_GetDefaultOptions() {
   static STRUCT_XMLRPC_OPTIONS options = {
      xmlrpc_case_exact,
      xmlrpc_case_sensitive
   };
   return &options;
}

Project: php-src
File: xmlrpc.c

void XMLRPC_SetValueBoolean(XMLRPC_VALUE value, int val) {
   if(value) {
      value->type = xmlrpc_boolean;
      value->i = val ? 1 : 0;
   }
}

Project: php-src
File: xmlrpc.c

void XMLRPC_SetValueDateTime(XMLRPC_VALUE value, time_t time) {
   if(value) {
      char timeBuf[30];
      value->type = xmlrpc_datetime;
      value->i = time;

      timeBuf[0] = 0;

      date_to_ISO8601(time, timeBuf, sizeof(timeBuf));

      if(timeBuf[0]) {
         XMLRPC_SetValueDateTime_ISO8601 (value, timeBuf);
      }
   }
}

Project: php-src
File: xmlrpc.c

XMLRPC_VALUE XMLRPC_RequestGetError (XMLRPC_REQUEST request) {
	return request ? request->error : NULL;
}

Project: php-src
File: xmlrpc.c

XMLRPC_REQUEST_OUTPUT_OPTIONS XMLRPC_RequestSetOutputOptions(XMLRPC_REQUEST request, XMLRPC_REQUEST_OUTPUT_OPTIONS output) {
   if(request && output) {
		memcpy (&request->output, output,
				  sizeof (STRUCT_XMLRPC_REQUEST_OUTPUT_OPTIONS));
      return &request->output;
   }
   return NULL;
}

Project: php-src
File: xmlrpc.c

void XMLRPC_SetValueInt(XMLRPC_VALUE value, int val) {
   if(value) {
      value->type = xmlrpc_int;
      value->i = val;
   }
}

Project: php-src
File: xmlrpc.c

const char* XMLRPC_GetValueBase64(XMLRPC_VALUE value) {
    return ((value && value->type == xmlrpc_base64) ? value->str.str : 0);
}

Project: php-src
File: xmlrpc.c

void XMLRPC_SetValueDouble(XMLRPC_VALUE value, double val) {
   if(value) {
      value->type = xmlrpc_double;
      value->d = val;
   }
}

Project: php-src
File: xmlrpc.c

void XMLRPC_SetValueDateTime_ISO8601(XMLRPC_VALUE value, const char* s) {
   if(value) {
      time_t time_val = 0;
      if(s) {
         value->type = xmlrpc_datetime;
         date_from_ISO8601(s, &time_val);
         value->i = time_val;
         simplestring_clear(&value->str);
         simplestring_add(&value->str, s);
      }
   }
}