- added pardef
This commit is contained in:
234
pardef.h
Normal file
234
pardef.h
Normal file
@ -0,0 +1,234 @@
|
||||
/*---------------------------------------------------------------------------
|
||||
pardef.h
|
||||
|
||||
my way to define and handle objects and its parameters
|
||||
|
||||
Markus Zolliker, March 2005
|
||||
----------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
#ifndef PARDEF_H
|
||||
#define PARDEF_H
|
||||
|
||||
#include "sics.h"
|
||||
#include "logger.h"
|
||||
|
||||
int ParPrintf(void *object, int iOut, const char *fmt, ...);
|
||||
|
||||
typedef enum { PAR_ALWAYS_READY, PAR_NOT_READY, PAR_NOW_READY } ReadyState;
|
||||
|
||||
typedef struct ParInfo {
|
||||
struct ParInfo *next;
|
||||
char *name;
|
||||
Logger *log;
|
||||
int saveIt; /* bool */
|
||||
int saveLog; /* bool */
|
||||
ReadyState state; /* enum ReadyState */
|
||||
int sugarStatus; /* =1: sugar object made */
|
||||
} ParInfo;
|
||||
|
||||
#define PAR_LEVELS 8
|
||||
#define PAR_NAN -999999.
|
||||
#define PAR_LNAN -999999
|
||||
|
||||
typedef void (*ParDef)(void *);
|
||||
|
||||
typedef struct ParClass {
|
||||
char *name;
|
||||
size_t size;
|
||||
int level;
|
||||
struct ParClass *base[PAR_LEVELS];
|
||||
} ParClass;
|
||||
|
||||
typedef struct ParData {
|
||||
pObjectDescriptor desc; /* SICS object descriptor */
|
||||
ParClass *class; /* class descriptor */
|
||||
ParDef pardef;
|
||||
char *creationCmd; /* the command to create this object */
|
||||
char *name; /* object name */
|
||||
time_t logTime; /* last logging time */
|
||||
int logPending;
|
||||
int period; /* logging interval */
|
||||
ParInfo *infoList; /* list for additional info on parameters */
|
||||
pICallBack pCall; /* sics callback function */
|
||||
SCStore conn; /* last connection with user or manager priv. */
|
||||
int verbose; /* verbosity, mainly for tests */
|
||||
} ParData;
|
||||
|
||||
/*
|
||||
Implementation of an object:
|
||||
|
||||
object data:
|
||||
|
||||
The first member of the objects data struct must be a plain ParData (not a pointer)
|
||||
The ParData member may also be the first member of an nested struct, the only
|
||||
condition is, that it is at offset 0, i.e. a cast to ParData is always valid.
|
||||
|
||||
typedef struct {
|
||||
ParData p;
|
||||
// object members:
|
||||
float value;
|
||||
char *text;
|
||||
FooSpecialObject *obj;
|
||||
} FooData;
|
||||
|
||||
a static class object of type ParClass has to be declared and initialized
|
||||
with its name and the object data size:
|
||||
|
||||
static ParClass fooClass {"Foo", sizeof(FooData) }
|
||||
|
||||
at initialisation, or at least before it is used first, it has
|
||||
to be initialized with
|
||||
|
||||
ParMakeClass(&fooClass, NULL);
|
||||
|
||||
(NULL as the second argument makes ParData to be the base class,
|
||||
if more levels of inheritance are used, use the base class as argument)
|
||||
|
||||
parameter definition:
|
||||
|
||||
The parameters definition is within the pardef function, for example
|
||||
|
||||
void FooPardef(void *object) {
|
||||
FooData *data = ParCast(&fooClass, object);
|
||||
|
||||
ParName("value"); ParFmt("%.3f"); ParFloat(&data->value, 0.0);
|
||||
ParName("text"); ParList(NULL); ParStr(&data->text, "");
|
||||
if (ParAction() == PAR_KILL) {
|
||||
if (data->obj) {
|
||||
FreeSpecialObject(data->obj);
|
||||
data->obj = NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
The first line in FooPardef is a cast converting the anonymous object to
|
||||
your data type. ParCast does some validity checks, which are strongly recommended.
|
||||
|
||||
The next two lines are parameters definitions. A parameter definition starts always
|
||||
with ParName, followed by some options, and ends with the parameter type definition.
|
||||
|
||||
FooPardef is called for all operations on data, so do not insert long calculations
|
||||
inside it. For special actions, code may be inserted for something like killing
|
||||
members.
|
||||
|
||||
All char arguments in the following functions might be referred even after
|
||||
the function returned. If they are not a constant, it is the callers responsibility
|
||||
to make its contents valid whenever they are used.
|
||||
|
||||
*/
|
||||
void ParName(char *name); /* name must not change during lifetime of the object,
|
||||
normally it is a constant */
|
||||
/*
|
||||
Options (to be called before parameter type definitions):
|
||||
*/
|
||||
void ParFmt(char *fmt); /* format (float only) */
|
||||
void ParAccess(int access); /* access rights (default usInternal = read only) */
|
||||
void ParSave(int save); /* save on status file
|
||||
(default: 0 for ParAccess(usInternal), 1 for others) */
|
||||
void ParEnum(char *list[]); /* automatic keyword to number conversion */
|
||||
void ParList(char *group); /* ParList may be repeated with several group arguments,
|
||||
to appear on a list <group> subcommand. Give NULL
|
||||
for std list. */
|
||||
void ParTail(char *tail); /* comment to appear after list entry (e.g. units).
|
||||
If ParList is not called, ParTail will force to appear
|
||||
in standard list. */
|
||||
void ParLogAs(char *name); /* switch log on and give sugar name (NULL for default name) */
|
||||
|
||||
/*
|
||||
Parameter type definitions:
|
||||
select one out of these per parameter, with
|
||||
a pointer to the corresponding object member as argument
|
||||
*/
|
||||
void ParFloat(float *value, float defValue);
|
||||
void ParInt(int *value, int defValue);
|
||||
void ParFixedStr(char *value, int maxsize, char *defValue); /* fixed size string */
|
||||
void ParStr(char **value, char *defValue); /* dynamic string */
|
||||
|
||||
typedef int (*ParCommand)(void *object, void *userarg, int argc, char *argv[]);
|
||||
/* command function to be executed */
|
||||
int ParCmd(ParCommand cmd, void *userarg); /* command, returns 0 when not executed
|
||||
else return value from cmd, default access
|
||||
is usUser */
|
||||
/*
|
||||
If code has to be executed for a specific to a parameter and and action,
|
||||
ParActionIs (see below) may be used. Typical usage:
|
||||
|
||||
if (ParActionIs(PAR_SET) > 0) {
|
||||
things to do when parameter has changed
|
||||
}
|
||||
|
||||
A parameter definition finishes after these calls.
|
||||
|
||||
There are predefined actions which are all handled by this module:
|
||||
*/
|
||||
typedef enum {
|
||||
PAR_NOOP, /* no operation */
|
||||
PAR_INIT, /* initialize object (called during initialisation) */
|
||||
PAR_SHOW, /* show single parameter (1) */
|
||||
PAR_SET, /* set a single parameter (1) */
|
||||
PAR_GET, /* get a single float parameter (1) */
|
||||
PAR_LIST, /* list all or a group of parameters (2) */
|
||||
PAR_LOG, /* log all parameters activated for logging (2) */
|
||||
PAR_LOGSWITCH, /* (de)activate single parameter for logging (1) */
|
||||
PAR_SAVE, /* save all parameters activated for saving (2) */
|
||||
PAR_SAVESWITCH,/* (de)activate single parameter for saving (1) */
|
||||
PAR_KILL /* kill content (called before remove) */
|
||||
} ParAct;
|
||||
|
||||
int ParActionIs(ParAct action);
|
||||
/* to be called inside the pardef function.
|
||||
returns 0, when the action is not active.
|
||||
returns 1 or -1 when the action is active.
|
||||
the return value -1 is used under following conditions:
|
||||
- for actions marked with (1), when the name does not match
|
||||
(for this case ParActionIs may be called between the call to ParName
|
||||
for the parameter referred and before the next call to ParName)
|
||||
- for actions marked with (2), when the parameter was not used
|
||||
(for this case ParActionIs must be called after the parameter definition
|
||||
for the parameter referred and before the next call to ParName)
|
||||
*/
|
||||
|
||||
void ParStdDef(void); /* handle the standard parameters "verbose" and "driver" */
|
||||
void *ParObject(void); /* get the current object (to be called by functions
|
||||
called inside pardef, when the object is not in the argument
|
||||
list */
|
||||
void ParLogReady(ReadyState state); /* set ready state for log */
|
||||
|
||||
/*
|
||||
functions to be used outside pardef:
|
||||
*/
|
||||
int ParLog(void *object); /* log all parameters of this object, but only if not
|
||||
already logged in the interval, returns >= 0 when done,
|
||||
or < 0, when not done (execute PAR_LOG action) */
|
||||
void ParKill(void *object); /* free the object (execute PAR_KILL action) */
|
||||
void ParGetFloat(SConnection *con, void *object, char *name, float *value);
|
||||
/* get a float parameter (execute PAR_GET action) */
|
||||
void *ParCast(ParClass *class, void *object);
|
||||
/* returns object, if the object has type "class" or
|
||||
inherits type "class", returns NULL otherwise */
|
||||
void *ParCheck(ParClass *class, void *object) ;
|
||||
/* dumps core when object has not or does not inherit "class" */
|
||||
void *ParMakeClass(ParClass *class, ParClass *base) ;
|
||||
/* initialize "class". base defines its base class or NULL
|
||||
when ParData is its direct base class */
|
||||
|
||||
void *ParMake(SConnection *con, char *name, ParClass *class, ParDef pardef, char *creationCmd);
|
||||
/* make an object of class "class", and declare its
|
||||
pardef function. Add it as command "name" to SICS,
|
||||
and execute pardef with PAR_INIT action.
|
||||
When creationCmd is not NULL, it is saved in order to
|
||||
recreate the object.
|
||||
|
||||
The SICS system will execute:
|
||||
- PAR_SHOW, PAR_SET, PAR_LIST, PAR_LOGSWITCH
|
||||
from the corresponding command
|
||||
- PAR_LOG after a PAR_SET action
|
||||
- PAR_SAVE after a parameter change on any SICS command
|
||||
- PAR_KILL on RemoveCommand */
|
||||
|
||||
char *ParArg2Text(int argc, char *argv[], char *res, int maxsize);
|
||||
/* convert args to text. if res==NULL, the result is
|
||||
allocated and maxsize is ignored */
|
||||
#endif
|
||||
|
Reference in New Issue
Block a user