Each new set of code should be implemented as a C file, which we refer to as a C stored function. Since each stored function will eventually become a library in which the MIM server will load upon startup, the C implementation was chosen so as to avoid problems with loading C++ libraries.
It is essential for a stored function to be able to maintain a state, which would persist between invocations of different stored function functions. The stored function state is represented by the following structure (which we call stored function arguments, thus the name):
typedef struct {
//error string
char *error;
//pointer to a SchSchema object
void *schema;
//pointer to an ExXmimOptions object, containing user defaults
const void *user_defaults;
//pointer to an ExCompiledQuery object corresponding to the current query
void *compiled_query;
//MimUnits (ExRelcol units)
int units;
//ExRelcol modulus
int modulus;
//pointer to the cfunc's characteristic time series,
//a time series which has non-NaN values for times
//when this c stored function is defined and NaN
//values when it is not
void *characteristic_time_series;
//pointer to the cfunc's ExTradingPattern object
void *trading_pattern;
//pointer to the cfunc's ExDateRange object
void *trading_date_range;
//cfunc specific state
xmim_cfunc_state *state;
//constant int args
xmim_cfunc_int_args *int_args;
//constant double args
xmim_cfunc_double_args *double_args;
//category args
xmim_cfunc_ *category_args;
//string args
xmim_cfunc_string_args *string_args;
//ATTR args
xmim_cfunc_attr_args *attr_args;
//time offset args
xmim_cfunc_time_offset_args *offset_args;
//period args
xmim_cfunc_time_period_args *period_args;
//security args
xmim_cfunc_security_args *security_args;
//default return value
double default_val;
//return value of the get_value method
double result;
} xmim_cfunc_args;This structure has a member called state, which is an
array of void*, specific to a particular stored function. A
stored function may store any information it needs to persist between the
function calls in this array.
Each stored function has the following structure. All functions are
mandatory, unless specified otherwise. The function
cfunc_instance_init_defaults initializes the default values of the stored function. Each
stored function should "know" about the arguments it expects. The stored
function will initialize the appropriate arguments in this function, i.e.,
assign the values to the names and size members of the appropriate
structs.
extern "C" int cfunc_instance_init_defaults (xmim_cfunc_args *args) {
...
}For example, if a stored function expects to get three constants as
arguments, it should do something analogous to the following in the
cfunc_instance_init_defaults function:
Also, we suggest that a stored function initialize
args->state in this function.
This can be performed in the |
int num = 3;
args->int_args->size = num;
args->int_args->ptr = new int[num];
for (int i = 0; i < num; i++)
args->int_args->ptr[i] = 0;
args->int_args->names = new char*[num];
args->int_args->names[0] = "day";
args->int_args->names[1] = "month";
args->int_args->names[2] = "year";The function cfunc_instance_init initializes the state ( ) of a stored function. Everything that needs to be initialized
before the argsstate
cfunc_instance_get_value function will be called
should be initialized here.
The stored function's input parameters are set at this point and can be used by the stored function to initialize its state if necessary. |
extern "C" int cfunc_instance_init (xmim_cfunc_args *args) {
...
}The optional function
cfunc_instance_compute_trading_pattern computes the trading pattern for a cfunc.
extern "C" int cfunc_instance_compute_trading_pattern (xmim_cfunc_args *args) {
...
}The optional function
cfunc_instance_compute_trading_date_range computes the trading date range for a stored
function.
extern "C" int cfunc_instance_compute_trading_date_range (xmim_cfunc_args *args) {
...
}The optional function
cfunc_instance_get_characteristic_time_series computes the characteristic time series for a stored
function. A characteristic time series is a time series which has non-NaN
values for times when the date exists and NaN values for times when the
date does not exist.
extern "C" int cfunc_instance_get_characteristic_time_series (xmim_cfunc_args *args) {
...
}The function cfunc_instance_get_value sets args->result to the value this stored
function needs to return for the date and time dt.
extern "C" int cfunc_instance_get_value (xmim_cfunc_args *args, xmim_cfunc_date_time *dt) {
...
}The function cfunc_instance_destroy is a destructor for a stored function. A stored function
should destroy all the instances it creates.
extern "C" int cfunc_instance_destroy (xmim_cfunc_args *args) {
...
}C Stored Functions can have constant (integer, double), attribute,
time offset, time period, security, category, and string input arguments.
The first five argument types are the same as arguments accepted by
macros. The category argument is stored as a string and can be used to
retrieve and process all relations under that category in the MIM schema
hierarchy. The string argument appears as a sequence of characters in
double quotes in the C stored function call. For example, the following is
a call to a C stored function named builtin_string_example
which takes two string arguments ("ALEX" and
"Close"):
builtin_string_example(“ALEX”, “Close”)
A C stored function "registers" a string input argument in the same
way as any other argument. Namely, builtin_string_example may
"register" to receive two string arguments (relation name and column name)
with the following code in its cfunc_instance_init_defaults
functions as follows:
int num = 2;
//string args
xmim_cfunc_string_args *str = new xmim_cfunc_string_args;
str->size = num;
str->names = new char*[num]
str->names[0] = "relation";
str->names[1] = "column";
str->ptr = new char*[num];
for (int i = 0; i < num; i++)
str->ptr[i] = NULL;
args->string_args = str;String input arguments are handled in the same way as the rest of the arguments.
The cfunc_instance_get_characteristic_time_series
function is optional, but when defined, is expected to set
the args->characteristic_time_series member to the
appropriate characteristic time series, such that the time series has a
non-NaN value when the date exists and a NaN value for the times when the
date does not exist. For example, if a stored function is defined at
exactly the times when the Close of IBM is defined, then
args->characteristic_time_series should be set to the time
series retrieved via the xmim_cfunc_get_time_series function
for the Close of IBM.