M7350/wlan/8192es/DriverSrcPkg/Users/mini_upnp/upnpreplyparse.c
2024-09-09 08:59:52 +00:00

398 lines
9.1 KiB
C
Executable File

#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <sys/stat.h>
#include "upnpreplyparse.h"
#include "minixml.h"
static void
NameValueParserStartElt(void * d, const char * name, int l)
{
struct NameValueParserData * data = (struct NameValueParserData *)d;
if(l>63)
l = 63;
memcpy(data->curelt, name, l);
data->curelt[l] = '\0';
}
static void
NameValueParserGetData(void * d, const char * datas, int l)
{
struct NameValueParserData * data = (struct NameValueParserData *)d;
struct NameValue * nv;
nv = malloc(sizeof(struct NameValue));
memset(nv, 0, sizeof(struct NameValue));
nv->value = (char *) malloc(l+1);
memset(nv->value, 0, l+1);
strncpy(nv->name, data->curelt, 64);
memcpy(nv->value, datas, l);
LIST_INSERT_HEAD( &(data->head), nv, entries);
}
void ParseNameValue(const char * buffer, int bufsize,
struct NameValueParserData * data)
{
struct xmlparser parser;
LIST_INIT(&(data->head));
/* init xmlparser object */
parser.xmlstart = buffer;
parser.xmlsize = bufsize;
parser.data = data;
parser.starteltfunc = NameValueParserStartElt;
parser.endeltfunc = 0;
parser.datafunc = NameValueParserGetData;
parser.attfunc = 0;
parsexml(&parser);
}
void ClearNameValueList(struct NameValueParserData * pdata)
{
struct NameValue * nv;
while((nv = pdata->head.lh_first) != NULL)
{
if (nv->value)
free(nv->value);
LIST_REMOVE(nv, entries);
free(nv);
}
}
char *
GetValueFromNameValueList(struct NameValueParserData * pdata,
const char * Name)
{
struct NameValue * nv;
char * p = NULL;
for(nv = pdata->head.lh_first;
(nv != NULL) && (p == NULL);
nv = nv->entries.le_next)
{
if(strcmp(nv->name, Name) == 0)
p = nv->value;
}
return p;
}
char *
GetValueFromNameValueListIgnoreNS(struct NameValueParserData * pdata,
const char * Name)
{
struct NameValue * nv;
char * p = NULL;
char * pname;
for(nv = pdata->head.lh_first;
(nv != NULL) && (p == NULL);
nv = nv->entries.le_next)
{
pname = strrchr(nv->name, ':');
if(pname)
pname++;
else
pname = nv->name;
if(strcmp(pname, Name)==0)
p = nv->value;
}
return p;
}
/* debug all-in-one function
* do parsing then display to stdout */
void DisplayNameValueList(char * buffer, int bufsize)
{
struct NameValueParserData pdata;
struct NameValue * nv;
ParseNameValue(buffer, bufsize, &pdata);
for(nv = pdata.head.lh_first;
nv != NULL;
nv = nv->entries.le_next)
{
printf("%s = %s\n", nv->name, nv->value);
}
ClearNameValueList(&pdata);
}
/* MUST free the returned buffer after this call */
char *mini_UPnPGetFirstElement(char *file_start, unsigned int len, char *tag_name, unsigned int tag_name_len)
{
char * line;
unsigned long file_end;
unsigned long string_begin=0;
unsigned long string_end=0;
char *tag_name_first=NULL;
char *tag_name_second=NULL;
char *buf=NULL;
unsigned int string_len=0;
if (file_start == NULL || tag_name == NULL)
return NULL;
if (len <= 0 || tag_name_len <= 0)
return NULL;
tag_name_first = (char *)malloc(tag_name_len+3);
if (tag_name_first == NULL)
return NULL;
memcpy(tag_name_first+1, tag_name, tag_name_len);
tag_name_first[0] = '<';
tag_name_first[tag_name_len+1] = '>';
tag_name_first[tag_name_len+2] = 0;
tag_name_second = (char *)malloc(tag_name_len+4);
if (tag_name_second == NULL) {
free(tag_name_first);
return NULL;
}
memcpy(tag_name_second+2, tag_name, tag_name_len);
tag_name_second[0] = '<';
tag_name_second[1] = '/';
tag_name_second[tag_name_len+2] = '>';
tag_name_second[tag_name_len+3] = 0;
line = file_start;
file_end = (unsigned long)file_start + len;
while ((unsigned long)line < (file_end-tag_name_len-3))
{
if (strncasecmp(line, tag_name_first, tag_name_len+2) == 0) {
if (string_begin == 0) {
string_begin = (unsigned long)line + tag_name_len + 2;
}
else {
//DEBUG_ERR("Duplicated tag %s\n", tag_name_first);
free(tag_name_first);
free(tag_name_second);
return NULL;
}
}
else if (strncasecmp(line, tag_name_second, tag_name_len+3) == 0) {
if (string_begin == 0) {
//DEBUG_ERR("Missing tag %s\n", tag_name_first);
free(tag_name_first);
free(tag_name_second);
return NULL;
}
else {
string_end = (unsigned long)line;
break;
}
}
line++;
}
free(tag_name_first);
free(tag_name_second);
if (string_begin < string_end) {
string_len = string_end - string_begin;
buf = (char *)malloc(string_len+1);
if (buf == NULL)
return NULL;
memcpy(buf, (char *)string_begin, string_len);
buf[string_len] = 0;
return buf;
}
else {
//DEBUG_ERR("XML parse erroe!\n");
return NULL;
}
}
char *mini_UPnPGetFirstElementAndReturnAddr(char *file_start, unsigned int len, char *tag_name, unsigned int tag_name_len, char *buf)
{
char * line;
unsigned long file_end;
unsigned long string_begin=0;
unsigned long string_end=0;
char *tag_name_first=NULL;
char *tag_name_second=NULL;
unsigned int string_len=0;
char *end=NULL;
unsigned char found=0;
if (file_start == NULL || tag_name == NULL || buf == NULL)
return NULL;
if (len <= 0 || tag_name_len <= 0)
return NULL;
tag_name_first = (char *)malloc(tag_name_len+3);
if (tag_name_first == NULL)
return NULL;
memcpy(tag_name_first+1, tag_name, tag_name_len);
tag_name_first[0] = '<';
tag_name_first[tag_name_len+1] = '>';
tag_name_first[tag_name_len+2] = 0;
tag_name_second = (char *)malloc(tag_name_len+4);
if (tag_name_second == NULL) {
free(tag_name_first);
return NULL;
}
memcpy(tag_name_second+2, tag_name, tag_name_len);
tag_name_second[0] = '<';
tag_name_second[1] = '/';
tag_name_second[tag_name_len+2] = '>';
tag_name_second[tag_name_len+3] = 0;
line = file_start;
file_end = (unsigned long)file_start + len;
while ((unsigned long)line < (file_end-tag_name_len-3))
{
if (strncasecmp(line, tag_name_first, tag_name_len+2) == 0) {
if (string_begin == 0) {
string_begin = (unsigned long)line + tag_name_len + 2;
}
else {
//DEBUG_ERR("Duplicated tag %s\n", tag_name_first);
free(tag_name_first);
free(tag_name_second);
return NULL;
}
}
else if (strncasecmp(line, tag_name_second, tag_name_len+3) == 0) {
if (string_begin == 0) {
//DEBUG_ERR("Missing tag %s\n", tag_name_first);
free(tag_name_first);
free(tag_name_second);
return NULL;
}
else {
string_end = (unsigned long)line;
end = (char *)(line + (tag_name_len+3));
found = 1;
break;
}
}
line++;
}
free(tag_name_first);
free(tag_name_second);
if (string_begin < string_end) {
string_len = string_end - string_begin;
memcpy(buf, (char *)string_begin, string_len);
buf[string_len] = 0;
return end;
}
else {
if (found) {
buf[0] = 0;
return end;
}
else
return NULL;
}
}
char *mini_UPnP_UploadXML(char *file_path)
{
FILE *fp = NULL;
int retVal = 0;
struct stat file_info;
char *buf=NULL;
unsigned int fileLen=0;
unsigned int num_read=0;
char *membuf=NULL;
buf = file_path;
retVal = stat(buf, &file_info );
if ( retVal == -1 ) {
//printf("Failed to get file info. EXITING\n");
return NULL;
}
fileLen = file_info.st_size;
if ( ( fp = fopen( buf, "rb" ) ) == NULL ) {
printf("Failed to open file [%s]. EXITING\n", buf);
return NULL;
}
if ( ( membuf = ( char * )malloc( fileLen + 1 ) ) == NULL ) {
fclose( fp );
printf("mini_UPnP_UploadXML Out of memory! EXITING\n");
return NULL;
}
num_read = fread( membuf, 1, fileLen, fp );
if ( num_read != fileLen ) {
fclose( fp );
free( membuf );
printf("mini_UPnP_UploadXML File length mismatched! EXITING\n");
return NULL;
}
membuf[fileLen] = 0;
fclose( fp );
return membuf;
}
char *get_token(char *data, char *token)
{
char *ptr=data;
int len=0, idx=0;
while (*ptr && *ptr != '\n' ) {
if (*ptr == '=') {
if (len <= 1)
return NULL;
memcpy(token, data, len);
/* delete ending space */
for (idx=len-1; idx>=0; idx--) {
if (token[idx] != ' ')
break;
}
token[idx+1] = '\0';
return ptr+1;
}
len++;
ptr++;
}
return NULL;
}
int get_value(char *data, char *value)
{
char *ptr=data;
int len=0, idx, i;
while (*ptr && *ptr != '\n' && *ptr != '\r') {
len++;
ptr++;
}
/* delete leading space */
idx = 0;
while (len-idx > 0) {
if (data[idx] != ' ')
break;
idx++;
}
len -= idx;
/* delete bracing '"' */
if (data[idx] == '"') {
for (i=idx+len-1; i>idx; i--) {
if (data[i] == '"') {
idx++;
len = i - idx;
}
break;
}
}
if (len > 0) {
memcpy(value, &data[idx], len);
value[len] = '\0';
}
return len;
}