mirror of
https://github.com/signalwire/freeswitch.git
synced 2025-02-24 18:41:57 +00:00
git-svn-id: http://svn.freeswitch.org/svn/freeswitch/trunk@8689 d0543943-73ff-0310-b7d9-9358b9ac24b2
380 lines
6.8 KiB
C
380 lines
6.8 KiB
C
/*
|
|
File: exprval.c
|
|
Auth: Brian Allen Vanderburg II
|
|
Date: Thursday, April 24, 2003
|
|
Desc: Value lists for variables and constants
|
|
|
|
This file is part of ExprEval.
|
|
*/
|
|
|
|
/* Includes */
|
|
#include "exprincl.h"
|
|
|
|
#include "exprpriv.h"
|
|
#include "exprmem.h"
|
|
|
|
|
|
/* Internal functions */
|
|
static exprVal *exprCreateVal(char *name, EXPRTYPE val, EXPRTYPE * addr);
|
|
static void exprValListFreeData(exprVal * val);
|
|
static void exprValListResetData(exprVal * val);
|
|
|
|
/* This function creates the value list, */
|
|
int exprValListCreate(exprValList ** vlist)
|
|
{
|
|
exprValList *tmp;
|
|
|
|
if (vlist == NULL)
|
|
return EXPR_ERROR_NULLPOINTER;
|
|
|
|
*vlist = NULL; /* Set to NULL initially */
|
|
|
|
tmp = exprAllocMem(sizeof(exprValList));
|
|
|
|
if (tmp == NULL)
|
|
return EXPR_ERROR_MEMORY; /* Could not allocate memory */
|
|
|
|
/* Update pointer */
|
|
*vlist = tmp;
|
|
|
|
return EXPR_ERROR_NOERROR;
|
|
}
|
|
|
|
/* Add a value to the list */
|
|
int exprValListAdd(exprValList * vlist, char *name, EXPRTYPE val)
|
|
{
|
|
exprVal *tmp;
|
|
exprVal *cur;
|
|
int result;
|
|
|
|
if (vlist == NULL)
|
|
return EXPR_ERROR_NULLPOINTER;
|
|
|
|
/* Make sure the name is valid */
|
|
if (!exprValidIdent(name))
|
|
return EXPR_ERROR_BADIDENTIFIER;
|
|
|
|
if (vlist->head == NULL) {
|
|
/* Create the node right here */
|
|
tmp = exprCreateVal(name, val, NULL);
|
|
|
|
if (tmp == NULL)
|
|
return EXPR_ERROR_MEMORY;
|
|
|
|
vlist->head = tmp;
|
|
return EXPR_ERROR_NOERROR;
|
|
}
|
|
|
|
/* See if already exists */
|
|
cur = vlist->head;
|
|
|
|
while (cur) {
|
|
result = strcmp(name, cur->vname);
|
|
|
|
if (result == 0)
|
|
return EXPR_ERROR_ALREADYEXISTS;
|
|
|
|
cur = cur->next;
|
|
}
|
|
|
|
/* We did not find it, create it and add it to the beginning */
|
|
tmp = exprCreateVal(name, val, NULL);
|
|
|
|
if (tmp == NULL)
|
|
return EXPR_ERROR_MEMORY;
|
|
|
|
tmp->next = vlist->head;
|
|
vlist->head = tmp;
|
|
|
|
return EXPR_ERROR_NOERROR;
|
|
}
|
|
|
|
/* Set a value in the list */
|
|
int exprValListSet(exprValList * vlist, char *name, EXPRTYPE val)
|
|
{
|
|
exprVal *cur;
|
|
int result;
|
|
|
|
if (vlist == NULL)
|
|
return EXPR_ERROR_NULLPOINTER;
|
|
|
|
if (name == NULL || name[0] == '\0')
|
|
return EXPR_ERROR_NOTFOUND;
|
|
|
|
/* Find and set it */
|
|
cur = vlist->head;
|
|
|
|
while (cur) {
|
|
result = strcmp(name, cur->vname);
|
|
|
|
if (result == 0) {
|
|
if (cur->vptr)
|
|
*(cur->vptr) = val;
|
|
else
|
|
cur->vval = val;
|
|
|
|
return EXPR_ERROR_NOERROR;
|
|
}
|
|
|
|
cur = cur->next;
|
|
}
|
|
|
|
return EXPR_ERROR_NOTFOUND;
|
|
}
|
|
|
|
/* Get the value from a list */
|
|
int exprValListGet(exprValList * vlist, char *name, EXPRTYPE * val)
|
|
{
|
|
exprVal *cur;
|
|
int result;
|
|
|
|
if (vlist == NULL)
|
|
return EXPR_ERROR_NULLPOINTER;
|
|
|
|
if (name == NULL || name[0] == '\0')
|
|
return EXPR_ERROR_NOTFOUND;
|
|
|
|
/* Search for the item */
|
|
cur = vlist->head;
|
|
|
|
while (cur) {
|
|
result = strcmp(name, cur->vname);
|
|
|
|
if (result == 0) {
|
|
/* We found it. */
|
|
if (cur->vptr)
|
|
*val = *(cur->vptr);
|
|
else
|
|
*val = cur->vval;
|
|
|
|
/* return now */
|
|
return EXPR_ERROR_NOERROR;
|
|
}
|
|
|
|
cur = cur->next;
|
|
}
|
|
|
|
/* If we got here, we did not find the item in the list */
|
|
return EXPR_ERROR_NOTFOUND;
|
|
}
|
|
|
|
/* Add an address to the list */
|
|
int exprValListAddAddress(exprValList * vlist, char *name, EXPRTYPE * addr)
|
|
{
|
|
exprVal *tmp;
|
|
exprVal *cur;
|
|
int result;
|
|
|
|
if (vlist == NULL)
|
|
return EXPR_ERROR_NULLPOINTER;
|
|
|
|
/* Make sure the name is valid */
|
|
if (!exprValidIdent(name))
|
|
return EXPR_ERROR_BADIDENTIFIER;
|
|
|
|
if (vlist->head == NULL) {
|
|
/* Create the node right here */
|
|
tmp = exprCreateVal(name, (EXPRTYPE) 0.0, addr);
|
|
|
|
if (tmp == NULL)
|
|
return EXPR_ERROR_MEMORY;
|
|
|
|
vlist->head = tmp;
|
|
return EXPR_ERROR_NOERROR;
|
|
}
|
|
|
|
/* See if it already exists */
|
|
cur = vlist->head;
|
|
|
|
while (cur) {
|
|
result = strcmp(name, cur->vname);
|
|
|
|
if (result == 0)
|
|
return EXPR_ERROR_ALREADYEXISTS;
|
|
|
|
cur = cur->next;
|
|
}
|
|
|
|
/* Add it to the list */
|
|
tmp = exprCreateVal(name, (EXPRTYPE) 0.0, addr);
|
|
|
|
if (tmp == NULL)
|
|
return EXPR_ERROR_MEMORY;
|
|
|
|
tmp->next = vlist->head;
|
|
vlist->head = tmp;
|
|
|
|
return EXPR_ERROR_NOERROR;
|
|
}
|
|
|
|
/* Get memory address of a variable value in a value list */
|
|
int exprValListGetAddress(exprValList * vlist, char *name, EXPRTYPE ** addr)
|
|
{
|
|
exprVal *cur;
|
|
int result;
|
|
|
|
/* Not found yet */
|
|
*addr = NULL;
|
|
|
|
if (vlist == NULL || addr == NULL)
|
|
return EXPR_ERROR_NULLPOINTER;
|
|
|
|
|
|
if (name == NULL || name[0] == '\0')
|
|
return EXPR_ERROR_NOTFOUND;
|
|
|
|
/* Search for the item */
|
|
cur = vlist->head;
|
|
|
|
while (cur) {
|
|
result = strcmp(name, cur->vname);
|
|
|
|
if (result == 0) {
|
|
/* We found it. */
|
|
if (cur->vptr)
|
|
*addr = cur->vptr;
|
|
else
|
|
*addr = &(cur->vval);
|
|
|
|
/* return now */
|
|
return EXPR_ERROR_NOERROR;
|
|
}
|
|
|
|
cur = cur->next;
|
|
}
|
|
|
|
/* If we got here, we did not find it in the list */
|
|
return EXPR_ERROR_NOTFOUND;
|
|
}
|
|
|
|
/* This function is used to enumerate the values in a value list */
|
|
void *exprValListGetNext(exprValList * vlist, char **name, EXPRTYPE * value, EXPRTYPE ** addr, void *cookie)
|
|
{
|
|
exprVal *cur;
|
|
|
|
if (vlist == NULL)
|
|
return NULL;
|
|
|
|
/* Get the current item */
|
|
cur = (exprVal *) cookie;
|
|
|
|
/* Find the next item */
|
|
if (cur == NULL)
|
|
cur = vlist->head;
|
|
else
|
|
cur = cur->next;
|
|
|
|
/* Set up the data */
|
|
if (cur) {
|
|
if (name)
|
|
*name = cur->vname;
|
|
|
|
if (value) {
|
|
if (cur->vptr)
|
|
*value = *(cur->vptr);
|
|
else
|
|
*value = cur->vval;
|
|
}
|
|
|
|
if (addr) {
|
|
if (cur->vptr)
|
|
*addr = cur->vptr;
|
|
else
|
|
*addr = &(cur->vval);
|
|
}
|
|
}
|
|
|
|
/* If there was no value, return NULL, otherwise, return the item */
|
|
return (void *) cur;
|
|
}
|
|
|
|
/* This routine will free the value list */
|
|
int exprValListFree(exprValList * vlist)
|
|
{
|
|
/* Make sure it exists, if not it is not error */
|
|
if (vlist == NULL)
|
|
return EXPR_ERROR_NOERROR;
|
|
|
|
/* Free the nodes */
|
|
exprValListFreeData(vlist->head);
|
|
|
|
/* Freethe container */
|
|
exprFreeMem(vlist);
|
|
|
|
return EXPR_ERROR_NOERROR;
|
|
}
|
|
|
|
/* This routine will reset the value list to 0.0 */
|
|
int exprValListClear(exprValList * vlist)
|
|
{
|
|
if (vlist == NULL)
|
|
return EXPR_ERROR_NOERROR;
|
|
|
|
exprValListResetData(vlist->head);
|
|
|
|
return EXPR_ERROR_NOERROR;
|
|
}
|
|
|
|
/* This routine will free any child nodes, and then free itself */
|
|
static void exprValListFreeData(exprVal * val)
|
|
{
|
|
exprVal *next;
|
|
|
|
while (val) {
|
|
/* Remember the next */
|
|
next = val->next;
|
|
|
|
/* Free name */
|
|
exprFreeMem(val->vname);
|
|
|
|
/* Free ourself */
|
|
exprFreeMem(val);
|
|
|
|
val = next;
|
|
}
|
|
}
|
|
|
|
/* This routine will reset variables to 0.0 */
|
|
static void exprValListResetData(exprVal * val)
|
|
{
|
|
while (val) {
|
|
/* Reset data */
|
|
if (val->vptr)
|
|
*(val->vptr) = 0.0;
|
|
|
|
val->vval = 0.0;
|
|
|
|
val = val->next;
|
|
}
|
|
}
|
|
|
|
/* This routine will create the value object */
|
|
static exprVal *exprCreateVal(char *name, EXPRTYPE val, EXPRTYPE * addr)
|
|
{
|
|
exprVal *tmp;
|
|
char *vtmp;
|
|
|
|
/* Name already tested in exprValListAdd */
|
|
|
|
/* Create it */
|
|
tmp = exprAllocMem(sizeof(exprVal));
|
|
if (tmp == NULL)
|
|
return NULL;
|
|
|
|
/* Allocate space for the name */
|
|
vtmp = exprAllocMem(strlen(name) + 1);
|
|
|
|
if (vtmp == NULL) {
|
|
exprFreeMem(tmp);
|
|
return NULL;
|
|
}
|
|
|
|
/* Copy the data over */
|
|
strcpy(vtmp, name);
|
|
tmp->vname = vtmp;
|
|
tmp->vval = val;
|
|
tmp->vptr = addr;
|
|
|
|
return tmp;
|
|
}
|