📄 cifile.c
字号:
/*
NOTICE:
This document contains information that is proprietary to RADVISION LTD.
No part of this publication may be reproduced in any form whatsoever without
written prior approval by RADVISION LTD.
RADVISION LTD reserves the right to revise this publication and make changes
without obligation to notify any person of such revisions or changes.
*/
/***************************************************************************
ciFile.c -- Configuration load/save functions - file version
Module Author: Oz Solomonovich
This Comment: 18-Dec-1996
Abstract: CI routines for loading and saving the configuration to
and from files.
Platforms: All.
Known Bugs: None.
***************************************************************************/
#ifndef NOFILESYSTEM
#include "rvstdio.h"
#include <stdlib.h>
#include "rvmemory.h"
#include "rvaddress.h"
#include "rtree.h"
#include "rpool.h"
#include "oidutils.h"
#include "strutils.h"
#include "ci.h"
#include "cisupp.h"
#ifdef __cplusplus
extern "C" {
#endif
#define FILE_BUF_SIZE 1024
static void buildFromFile(FILE *inf, char *fileBuffer, HRPOOL pool,
HRTREE tree, int nodeID, int level);
static void outputToFile(FILE *outf, HRTREE tree, int nodeID, int level, HRPOOL pool);
static int parseLine(IN int currLevel, IN char *line,
OUT char **name, OUT char **rawValue);
int ciIDFile(const char *source)
{
return (source && source[0]);
}
void ciGetModuleDirectoryFileName(const char* name, char* szPath, int szPathSize)
{
RvChar* p;
p = (RvChar*) strchr(name, '\\');
strncpy(szPath, name, (RvSize_t)szPathSize);
#if (RV_OS_TYPE == RV_OS_TYPE_WIN32)
if (!p)
{
GetModuleFileName(GetModuleHandle(NULL), szPath, szPathSize);
p = strrchr(szPath, '\\');
if (p)
{
p++;
strcpy(p, name);
}
}
#endif
}
int ciEstimateCfgSizeFile(const char *source, int *nodes, int *data)
{
FILE *inf;
char sourceWithPath[300];
char *fileBuffer = NULL;
char *name, *value;
if(RvMemoryAlloc(NULL, (void**)&fileBuffer, FILE_BUF_SIZE) != RV_OK)
return ERR_CI_ALLOCERROR;
ciGetModuleDirectoryFileName(source, sourceWithPath, sizeof(sourceWithPath));
if ( (inf = fopen(sourceWithPath, "rb")) == NULL)
{
RvMemoryFree(fileBuffer);
return ERR_CI_FILEOPEN;
}
*nodes = 0;
*data = 0;
while (fgets(fileBuffer, FILE_BUF_SIZE, inf))
{
parseLine(0, fileBuffer, &name, &value);
if (name)
{
int len = strlen(name);
(*nodes)++;
(*data) += (len + CONFIG_RPOOL_BLOCK_SIZE - (len % CONFIG_RPOOL_BLOCK_SIZE));
}
if (value)
{
int len = strlen(value);
(*data) += (len + CONFIG_RPOOL_BLOCK_SIZE - (len % CONFIG_RPOOL_BLOCK_SIZE));
}
}
fclose(inf);
RvMemoryFree(fileBuffer);
return 0;
}
int ciBuildFromFile(const char *source, HRTREE tree, HRPOOL pool)
{
FILE *inf;
char sourceWithPath[300];
char *fileBuffer = NULL;
if(RvMemoryAlloc(NULL, (void**)&fileBuffer, FILE_BUF_SIZE+1) != RV_OK)
return ERR_CI_ALLOCERROR;
memset(fileBuffer, 0, FILE_BUF_SIZE+1);
ciGetModuleDirectoryFileName(source, sourceWithPath,
sizeof(sourceWithPath));
if ( (inf = fopen(sourceWithPath, "rb")) == NULL)
{
RvMemoryFree(fileBuffer);
return ERR_CI_FILEOPEN;
}
buildFromFile(inf, fileBuffer, pool, tree, rtRoot(tree), 0);
fclose(inf);
RvMemoryFree(fileBuffer);
return 0;
}
int ciOutputToFile(const char *target, HRTREE tree, HRPOOL pool)
{
FILE *outf;
char targetWithPath[300];
ciGetModuleDirectoryFileName(target, targetWithPath,
sizeof(targetWithPath));
if ( (outf = fopen(targetWithPath, "wb")) == NULL)
return ERR_CI_FILEOPEN;
/* output standard header */
fprintf(outf,
"# RADVISION H.323 Stack Configuration File\n"
"#\n"
"# Value encodings:\n"
"# '' - String (and asciiz is not appended)\n"
"# \"\" - BMP string of ASCII charactes\n"
"# [] - Hex octet string\n"
"# <> - IP\n"
"# {} - Object ID\n"
"# %% - Bit string\n"
"# Other - Integer\n"
"\n");
outputToFile(outf, tree, rtRoot(tree), 0, pool);
fclose(outf);
return 0;
}
static char *skipWhite(char *s)
{
if (s)
for (; *s && isspace((int)*s); s++);
return s;
}
static char *findMatchingQuote(char *s, char quote)
{
/* stops only at '\n' */
for (; *s != '\n' && *s != quote; s++);
return (*s == '\n') ? (char*)NULL : s;
}
/* parseLine() returns the new level, or -1 on parse error
line format:
[level] name [= value]
lines beginning with # are a comment.
level: a number (the level number), '+' (advance to next level),
+Number (advance Number levels), ditto for '-'.
when no level is specified, the same level is intended
*/
static int parseLine(IN int currLevel, IN char *line,
OUT char **name, OUT char **rawValue)
{
static char name_buf[256];
static char val_buf[256];
int newLevel, i;
char sign, *p;
*name = NULL;
*rawValue = NULL;
line = skipWhite(line);
if (!line[0] || line[0] == '#') /* comment or end of line */
{
return -1;
}
/* first section (optional): the level */
if (isdigit((int)line[0]))
{
newLevel = 0;
while (line[0] && isdigit((int)line[0]))
{
newLevel = (newLevel * 10) + (line[0] - '0');
line++;
}
}
else
{
/* '+' or '-' */
newLevel = currLevel;
sign = line[0];
if (sign == '+' || sign == '-')
{
line++;
if (!line[0])
{
return -1;
}
if (isdigit((int)line[0]))
{
i = 0;
while (line[0] && isdigit((int)line[0]))
{
i = (i * 10) + (line[0] - '0');
line++;
}
}
else
{
i = 1;
}
newLevel = newLevel + ((sign == '+')? i : -i);
}
}
line = skipWhite(line);
if (!line[0] || line[0] == '#') /* comment or end of line */
{
return -1;
}
/* second section: the name */
p = (char *)name_buf;
while (line[0] && !isspace((int)line[0]) && line[0] != '=')
{
*p = line[0];
line++;
p++;
}
*p = '\0';
*name = (char *)name_buf;
/* simulate a value of zero in case there is no value */
strcpy((char *)val_buf, "0");
*rawValue = (char *)val_buf;
line = skipWhite(line);
if (!line[0] || line[0] == '#' || line[0] != '=')
{
return newLevel;
}
++line;
line = skipWhite(line);
if (!line[0] || line[0] == '#')
{
return newLevel;
}
/* third section: the value */
p = (char *)val_buf;
while (line[0])
{
*p = line[0];
line++;
p++;
}
*p = '\0';
return newLevel;
}
/* this macro scans the buffer for the matching quote character, then
updates the following variables:
p - beginning of string between quotes
p2 - end of string (points to the asciiz)
length - length of string
cfgVal->string - allocated variable string
the macro will break from the loop if the string is null
*/
#define MATCH_QUOTE(quote_char) \
p2 = findMatchingQuote(p + 1, quote_char); \
if (!p2 || ((p2 - p) < 1)) \
break; \
p++; \
*p2 = '\0'; \
length = p2 - p; \
assistLen = length; \
assistBuff[length] = '\0';
/* Check that a parent doesn't have a node with a given name.
If it does - return that node, so we can use it instead of adding a new one
with the same name */
static int getSameNode(IN HRTREE tree, IN int parent, IN HRPOOL pool, IN const void* nodeName)
{
int nodeId;
int len;
pcfgValue cfgVal;
nodeId = rtHead(tree, parent);
if (nodeId < 0)
return nodeId;
len = rpoolChunkSize(pool, (void *)nodeName);
cfgVal = (pcfgValue)rtGetByPath(tree, nodeId);
while (rpoolChunkSize(pool, cfgVal->name) != len ||
rpoolCompareInternal(pool, cfgVal->name, (void *)nodeName, len))
{
nodeId = rtBrother(tree, nodeId);
if (nodeId < 0)
return RV_ERROR_UNKNOWN;
cfgVal = (pcfgValue)rtGetByPath(tree, nodeId);
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -