summaryrefslogtreecommitdiffstats
path: root/elapi/elapi_event.c
diff options
context:
space:
mode:
Diffstat (limited to 'elapi/elapi_event.c')
-rw-r--r--elapi/elapi_event.c1047
1 files changed, 0 insertions, 1047 deletions
diff --git a/elapi/elapi_event.c b/elapi/elapi_event.c
deleted file mode 100644
index ff73939..0000000
--- a/elapi/elapi_event.c
+++ /dev/null
@@ -1,1047 +0,0 @@
-/*
- ELAPI
-
- Implementation of the ELAPI event interface.
-
- Copyright (C) Dmitri Pal <dpal@redhat.com> 2009
-
- This program is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 3 of the License, or
- (at your option) any later version.
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
- You should have received a copy of the GNU General Public License
- along with this program. If not, see <http://www.gnu.org/licenses/>.
-*/
-
-#define _GNU_SOURCE
-#include <sys/types.h> /* for getpid() */
-#include <unistd.h> /* for getpid() */
-#include <stdlib.h> /* for realloc() */
-#include <syslog.h> /* for contants releted to severity */
-#include <unistd.h> /* for gethostname() */
-#include <errno.h> /* for errors */
-#include <string.h> /* for memset() and other */
-#include <netdb.h> /* for gethostbyname() */
-#include <sys/socket.h> /* for inet_ntop() */
-#include <arpa/inet.h> /* for inet_ntop() */
-#include <ctype.h> /* for isspace() */
-#include <stdarg.h> /* for va_arg() */
-#include <string.h> /* for strndup() */
-
-#include "elapi_priv.h"
-#include "elapi_event.h"
-#include "elapi_net.h"
-#include "trace.h"
-#include "config.h"
-
-#include "collection_tools.h"
-
-/* Internal return states from key processing */
-#define E_LIST_EMPTY 0
-#define E_LIST_ERROR 1
-#define E_LIST_LAST 2
-#define E_LIST_ADD 3
-#define E_LIST_REMOVE 4
-
-#define LOCALHOSTDOMAIN "localhost.localdomain"
-#define LOCALHOST "localhost"
-#define LOCALADDRESS "127.0.0.1"
-#define LOCALADDRESSV6 "::1"
-
-const char *undefined = "undefined";
-const char *str_yes = "yes";
-const char *str_no = "no";
-const char *str_true = "true";
-const char *str_false = "false";
-
-
-/* Function to add host identity information to the template */
-static int add_host_identity(struct collection_item *tpl, unsigned base)
-{
- char hostname[NI_MAXHOST + 1];
- int error = EOK;
- int gai_ret_host = 0;
- int gai_ret_addr = 0;
- char host[NI_MAXHOST];
- char address[NI_MAXHOST];
- char *hnm, *haddr;
- ELAPI_ADDRLIST ifaddr;
- ELAPI_ADDRITEM ifa;
- struct sockaddr *addr;
- int family;
- int set_hostname = 0;
- int set_ip = 0;
- int used_this_ip = 0;
-
- TRACE_FLOW_STRING("add_host_identity", "Entry");
-
- /* The goal here to collect information about the host.
- * there is no need to actually use it for establishing
- * any connections.
- * It is a best effort attempt.
- */
-
- /* If we are not asked for hostname then say we already have it */
- if (!(base & E_HAVE_HOSTNAME)) set_hostname = 1;
- /* If we are not asked for ip then say we already have it */
- if (!(base & E_HAVE_HOSTIP)) set_ip = 1;
-
- if (ELAPI_GET_ADDRLIST(&ifaddr) == EOK) {
-
- TRACE_FLOW_STRING("getifaddrs", "Ok");
-
- /* Walk through linked list, maintaining head pointer so we
- can free list later */
- ELAPI_GET_FIRST_ADDR_ITEM(ifaddr, ifa);
-
- while (ifa != NULL) {
-
- TRACE_FLOW_STRING("Top of the loop", "");
-
- used_this_ip = 0;
-
- ELAPI_GET_ADDR(ifa, addr);
- if (!addr) {
- ELAPI_GET_NEXT_ADDR_ITEM(ifaddr, ifa);
- continue;
- }
-
- family = addr->sa_family;
-
- TRACE_FLOW_NUMBER("Family", family);
-
- /* For an AF_INET* interface address, display the address */
- if (family == AF_INET || family == AF_INET6) {
-
- TRACE_FLOW_NUMBER("Got right family", family);
-
- /* getnameinfo function claims that it returns NULL
- * terminated strings. Well...
- * We will trust it here and not clear memory using memset.
- */
-
- gai_ret_host = getnameinfo(addr,
- (family == AF_INET) ? sizeof(struct sockaddr_in) :
- sizeof(struct sockaddr_in6),
- host,
- NI_MAXHOST,
- NULL,
- 0,
- 0 /* Gets host name */);
-
- gai_ret_addr = getnameinfo(addr,
- (family == AF_INET) ? sizeof(struct sockaddr_in) :
- sizeof(struct sockaddr_in6),
- address,
- NI_MAXHOST,
- NULL,
- 0,
- NI_NUMERICHOST /* Gets address as string */);
-
- TRACE_INFO_STRING("Resolved host:", host);
- TRACE_INFO_STRING("Resolved address:", address);
- /* If we have not set host name set it */
- if(!set_hostname) {
-
- TRACE_FLOW_STRING("Host name is not set", "");
-
- hnm = NULL;
- /* Use host name returned by gethostname() as main host name */
- if (gethostname(hostname, NI_MAXHOST) == EOK) {
- /* Make sure hostname is NULL terminated */
- hostname[NI_MAXHOST] = '\0';
- hnm = hostname;
- }
- else {
- /* Were we able to get a host name ? */
- if (gai_ret_host == EOK) {
- TRACE_INFO_STRING("getnameinfo returned:", host);
- hnm = host;
- }
- }
-
- /* Do we have a host meaningful host name? */
- if ((hnm) &&
- ((strcasecmp(hnm, LOCALHOST) == 0 ) ||
- (strcasecmp(hnm, LOCALHOSTDOMAIN) == 0 ) ||
- (strcasecmp(hnm, address) == 0))) hnm = NULL;
-
- /* If host name is not NULL it would work for us */
- if (hnm) {
- TRACE_INFO_STRING("Adding host name:", hnm);
- error = col_add_str_property(tpl, NULL, E_HOSTNAME, hnm, 0);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add host name. Error", error);
- ELAPI_ADDR_LIST_CLEANUP(ifaddr);
- return error;
- }
- /* Done with the name */
- set_hostname = 1;
- }
- }
-
- /* If we have not set processed ip address do it */
- if(!set_ip) {
-
- TRACE_FLOW_STRING("Address is not set", "");
-
- haddr = NULL;
- if (gai_ret_addr == EOK) {
- TRACE_INFO_STRING("getnameinfo returned:", address);
- if ((strcasecmp(address, LOCALADDRESS) != 0 ) &&
- (strcasecmp(address, LOCALADDRESSV6) != 0 )) {
- TRACE_INFO_STRING("Not an unhelpful address", "");
- haddr = address;
- }
- }
-
- if (haddr) {
- TRACE_INFO_STRING("Adding host address:", haddr);
- error = col_add_str_property(tpl, NULL, E_HOSTIP, haddr, 0);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add host name. Error", error);
- ELAPI_ADDR_LIST_CLEANUP(ifaddr);
- return error;
- }
- set_ip = 1;
- used_this_ip = 1;
- }
- }
-
- /* If we have a name and we are told to deal with alias names */
- if ((set_hostname) && (base & E_HAVE_HOSTALIAS)) {
-
- TRACE_INFO_NUMBER("gai_ret_host:", gai_ret_host);
- TRACE_INFO_STRING("host:", host);
- TRACE_INFO_STRING("address:", address);
- TRACE_INFO_STRING("they are:", ((strcasecmp(host, address) != 0) ? "different" : "same"));
-
- /* Do we have a host meaningful host name? */
- if ((gai_ret_host != EOK) ||
- ((gai_ret_host == EOK) &&
- ((strcasecmp(host, LOCALHOST) == 0 ) ||
- (strcasecmp(host, LOCALHOSTDOMAIN) == 0 ) ||
- (strcasecmp(host, address) == 0)))) hnm = NULL;
- else hnm = host;
-
- if (hnm) {
- TRACE_INFO_STRING("Adding alias host name:", hnm);
- error = col_add_str_property(tpl, NULL, E_HOSTALIAS, hnm, 0);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add host name. Error", error);
- ELAPI_ADDR_LIST_CLEANUP(ifaddr);
- return error;
- }
- }
- }
-
- /* If we got then main IP and we are told to deal with opther IPs */
- if ((set_ip) && (base & E_HAVE_HOSTIPS) && (!used_this_ip)) {
-
- TRACE_INFO_STRING("Considering address:", address);
-
- /* Do we have a host meaningful IP */
- if ((gai_ret_addr != EOK) ||
- ((gai_ret_addr == EOK) &&
- ((strcasecmp(address, LOCALADDRESS) == 0 ) ||
- (strcasecmp(address, LOCALADDRESSV6) == 0 )))) haddr = NULL;
- else haddr = address;
-
- if (haddr) {
- TRACE_INFO_STRING("Adding alias host IP:", haddr);
- error = col_add_str_property(tpl, NULL, E_HOSTIPS, haddr, 0);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add host name. Error", error);
- ELAPI_ADDR_LIST_CLEANUP(ifaddr);
- return error;
- }
- }
- }
- }
- TRACE_INFO_STRING("Moved to next", "");
- ELAPI_GET_NEXT_ADDR_ITEM(ifaddr, ifa);
- TRACE_INFO_NUMBER("Moved to", ifa);
- }
-
- ELAPI_ADDR_LIST_CLEANUP(ifaddr);
- }
-
- /* Make sure that we really have the name after all */
- if (!set_hostname) {
- TRACE_INFO_STRING("No host name using default:", undefined);
- error = col_add_str_property(tpl, NULL, E_HOSTNAME, undefined, 0);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add host name. Error", error);
- return error;
- }
- }
-
- /* Make sure that we really have the IP after all */
- if (!set_ip) {
- TRACE_INFO_STRING("No host name using default:", undefined);
- error = col_add_str_property(tpl, NULL, E_HOSTIP, undefined, 0);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add host name. Error", error);
- return error;
- }
- }
-
- TRACE_FLOW_STRING("add_host_identity", "Exit");
- return error;
-}
-
-/* Add base elements to template collection */
-static int add_base_elements(struct collection_item *tpl, unsigned base)
-{
- int error = EOK;
- unsigned pass_base;
-
- TRACE_FLOW_STRING("add_base_elements", "Entry");
-
- /* Populate the template using base */
- if (base & E_HAVE_TIMESTAMP) {
- /* Value is the format string for strftime() */
- error = col_add_str_property(tpl, NULL, E_TIMESTAMP, E_TIMESTAMP_FORMAT, sizeof(E_TIMESTAMP_FORMAT));
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add timestamp. Error", error);
- return error;
- }
- }
-
- if (base & E_HAVE_UTCTIME) {
- /* Value does not matter */
- error = col_add_int_property(tpl, NULL, E_UTCTIME, 0);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add UTC time. Error", error);
- return error;
- }
- }
-
- if (base & E_HAVE_OFFSET) {
- /* Value does not matter */
- error = col_add_int_property(tpl, NULL, E_OFFSET, 0);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add UTC time. Error", error);
- return error;
- }
- }
-
- if (base & E_HAVE_PID) {
- /* Value is the current pid */
- error = col_add_long_property(tpl, NULL, E_PID, (long)getpid());
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add pid. Error", error);
- return error;
- }
- }
-
- if (base & E_HAVE_APPNAME) {
- /* Value does not matter */
- error = col_add_str_property(tpl, NULL, E_APPNAME, "", 1);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add application name. Error", error);
- return error;
- }
- }
-
- if (base & E_HAVE_SEVERITY) {
- /* Value is the default severity */
- error = col_add_int_property(tpl, NULL, E_SEVERITY, LOG_USER | LOG_INFO);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add pid. Error", error);
- return error;
- }
- }
-
- /* If we need to add aliases or other IPs call the function */
- if ((base & E_HAVE_HOSTNAME) ||
- (base & E_HAVE_HOSTIP) ||
- (base & E_HAVE_HOSTALIAS) ||
- (base & E_HAVE_HOSTIPS)) {
-
- pass_base = base;
-
- /* make sure we have extensions on top of the basic data */
- if ((base & E_HAVE_HOSTALIAS) && (!(base & E_HAVE_HOSTNAME))) pass_base |= E_HAVE_HOSTNAME;
- if ((base & E_HAVE_HOSTIPS) && (!(base & E_HAVE_HOSTIP))) pass_base |= E_HAVE_HOSTIP;
-
- error = add_host_identity(tpl, pass_base);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add host identity. Error", error);
- return error;
- }
- }
-
- TRACE_FLOW_STRING("add_base_elements", "Exit");
- return error;
-}
-
-
-/* Internal untility function to tokenize a string */
-static int interpret_key(char *key,
- int *type,
- char **property,
- int *prop_len,
- int *has_len,
- int *bool_type)
-{
- int adjust_by = 0;
- char *start = NULL;
- char *cursor = NULL;
- char *end = NULL;
- int ret = E_LIST_EMPTY;
-
- TRACE_FLOW_STRING("interpret_key", "Entry");
-
- TRACE_INFO_STRING("Key", key);
-
- /* Initialize passed in data */
- *has_len = 0;
- *property = NULL;
- *type = COL_TYPE_STRING;
-
- cursor = key;
-
- while (isspace(*cursor)) cursor++;
-
- /* End of string - we are done */
- if (*cursor == '\0') {
- TRACE_ERROR_STRING("Empty key - end of processing!", "");
- return E_LIST_EMPTY;
- }
-
- /* This is the beginning of the formatted token */
- if (*cursor == '-') {
-
- /* This is a remove attribute case */
-
- cursor++;
- /* Skip spaces if any */
- while (isspace(*cursor)) cursor++;
-
- /* Mark the start of the actual property */
- start = cursor;
-
- /* Now we need to extract the name of the property */
- /* We will not be nice here - the add_property will validate if the name is ok */
- while ((*cursor != '\0') && (!isspace(*cursor))) cursor++;
-
- /* End of string - we are done */
- if (cursor == start) {
- TRACE_ERROR_STRING("Invalid key - end of processing!", "");
- return E_LIST_EMPTY;
- }
-
- *prop_len = cursor - start;
- *property = start;
- TRACE_INFO_STRING("We are told to remove the property!", *property);
- ret = E_LIST_REMOVE;
- }
- else if (*cursor == '%') {
-
- /* We got a full key with format string */
-
- cursor++;
- if ((*cursor == '*') && (*(cursor+1) == 's') && (*(cursor+2) == '(')) {
- *type = COL_TYPE_STRING;
- *has_len = 1;
- adjust_by = 3;
- }
- else if ((*cursor == 's') && (*(cursor+1) == '(')) {
- *type = COL_TYPE_STRING;
- adjust_by = 2;
- }
- else if (((*cursor == 'i')||(*cursor == 'd')) && (*(cursor+1) == '(')) {
- *type = COL_TYPE_INTEGER;
- adjust_by = 2;
- }
- else if ((*cursor == 'u') && (*(cursor+1) == '(')) {
- *type = COL_TYPE_UNSIGNED;
- adjust_by = 2;
- }
- else if ((*cursor == 'l') && ((*(cursor+1) == 'i')||(*(cursor+1) == 'd')) && (*(cursor+2) == '(')) {
- *type = COL_TYPE_LONG;
- adjust_by = 3;
- }
- else if ((*cursor == 'l') && (*(cursor+1) == 'u') && (*(cursor+2) == '(')) {
- *type = COL_TYPE_ULONG;
- adjust_by = 3;
- }
- else if (((*cursor == 'f')||(*cursor == 'e')) && (*(cursor+1) == '(')) {
- *type = COL_TYPE_DOUBLE;
- adjust_by = 2;
- }
- else if (((*cursor == 's') || (*cursor == 'd')) && (*(cursor+1) == 'b') && (*(cursor+2) == '(')) {
- *type = COL_TYPE_BOOL;
- adjust_by = 3;
- if (*cursor == 's') *bool_type = 1;
- else *bool_type = 0;
- }
- else if ((*cursor == 'n') && (*(cursor+1) == '(')) {
- *type = COL_TYPE_BINARY;
- adjust_by = 2;
- }
- else {
- TRACE_ERROR_STRING("Invalid key - end of processing!", key);
- return E_LIST_ERROR;
- }
-
- cursor += adjust_by;
-
- /* Skip spaces if any */
- while (isspace(*cursor)) cursor++;
-
- start = cursor;
-
- /* Now we need to extract the name of the property */
- /* We will not be nice here - the add_property will validate if the name is ok */
- while ((*cursor != '\0') && (*cursor != ')') && (!isspace(*cursor))) cursor++;
-
- /* End of string - we are done */
- if ((*cursor == '\0') || (cursor == start)) {
- TRACE_ERROR_STRING("Invalid key - end of processing!", "");
- return E_LIST_EMPTY;
- }
-
- end = cursor;
-
- /* Skip spaces if any */
- while (isspace(*cursor)) cursor++;
-
- /* Check that end of the string is in proper format */
- if ((*cursor != ')') && (*(cursor + 1) != '\0')) {
- TRACE_ERROR_STRING("Invalid key - missing ')' .", key);
- return E_LIST_ERROR;
- }
-
- *property = start;
- *prop_len = end - start;
-
- TRACE_INFO_STRING("Property:", *property);
- TRACE_INFO_NUMBER("Property len:", *prop_len);
- ret = E_LIST_ADD;
- }
- else {
- /* Just got a key */
- /* Mark the start of the actual property */
- start = cursor;
-
- /* Now we need to extract the name of the property */
- /* We will not be nice here - the add_property will validate if the name is ok */
- while ((*cursor != '\0') && (!isspace(*cursor))) cursor++;
-
- /* End of string - we are done */
- if (cursor == start) {
- TRACE_ERROR_STRING("Invalid key - end of processing!", "");
- return E_LIST_EMPTY;
- }
-
- *prop_len = cursor - start;
- *property = start;
- TRACE_INFO_STRING("We are told to add/update the property (or last)!", *property);
-
- if(strncmp(*property, E_EOARG, *prop_len) == 0) ret = E_LIST_LAST;
- else ret = E_LIST_ADD;
- }
-
- TRACE_INFO_STRING("Returning Property:",*property);
- TRACE_INFO_NUMBER("Returning Property len:", *prop_len);
- TRACE_INFO_NUMBER("Returning Type:", *type);
- TRACE_INFO_NUMBER("Returning Has length:", *has_len);
-
-
- TRACE_FLOW_STRING("interpret_key", "Exit");
-
- return ret;
-}
-
-/* Make sure that the right string is given for bool value */
-static int convert_bool(char *data_str, unsigned char *data_bool)
-{
- TRACE_FLOW_STRING("convert_bool", "Called");
- TRACE_INFO_STRING("Data", data_str);
-
- if ((strcasecmp(data_str, str_true) == 0) ||
- (strcasecmp(data_str, str_yes) == 0)) {
- TRACE_INFO_STRING("Matched TRUE", "");
- *data_bool = '\1';
- return 1;
- }
- if ((strcasecmp(data_str, str_false) == 0) ||
- (strcasecmp(data_str, str_no) == 0)) {
- TRACE_INFO_STRING("Matched FALSE", "");
- *data_bool = '\0';
- return 1;
- }
- TRACE_INFO_STRING("Matched NOTHING", "");
- return 0;
-}
-
-
-/* Process argument list */
-/* Update collection based on the passed in arguments */
-static int process_arg_list(struct collection_item *col,
- va_list args)
-{
- int error = EOK;
- char *arg = NULL;
- char *propcopy = NULL;
- int ret = 0;
- int type = 0;
- char *property = NULL;
- int prop_len = 0;
- int has_len = 0;
- int bool_type = 0;
- char *data_str = NULL;
- int data_int = 0;
- unsigned int data_uint = 0;
- long data_long = 0;
- unsigned long data_ulong = 0;
- void *data_bin = NULL;
- double data_dbl = 0.;
- int length = 0;
- void *data = NULL;
- unsigned char data_bool = '\0';
-
- TRACE_FLOW_STRING("process_arg_list", "Entry.");
-
- /* We will break from the loop when we find the last item */
- while (1) {
-
- /* Get next key */
- arg = va_arg(args, char *);
-
- if (arg == NULL) {
- TRACE_ERROR_STRING("Invalid NULL argument.", "Key can't be NULL");
- return EINVAL;
- }
-
- /* Interpret the key.
- * It can be just " key ",
- * it can be " - key ",
- * or it can be a formatted string
- * something like " %*s( key )".
- * Function will deal with all cases.
- * Passed in variables initialized and updated inside
- */
- ret = interpret_key(arg,
- &type,
- &property,
- &prop_len,
- &has_len,
- &bool_type);
-
- if (ret == E_LIST_LAST) {
- TRACE_INFO_STRING("Process found last key", arg);
- break;
- }
-
- if ((ret == E_LIST_ADD) || (ret == E_LIST_REMOVE)) {
- /* We need to create a dup of the string */
- propcopy = malloc(prop_len + 1);
- if (propcopy == NULL) {
- TRACE_ERROR_STRING("Failed to allocate property", arg);
- return ENOMEM;
- }
-
- /* Copy property */
- memcpy(propcopy, property, prop_len);
- propcopy[prop_len] = '\0';
-
- TRACE_INFO_STRING("Processing property", propcopy);
-
- /* Are we supposed to add? */
- if (ret == E_LIST_ADD) {
-
-
- /* NOTE: We are not going to check if the key value pairs
- * are consistent.
- * It can be made a bit more bullet proof by adding
- * significant complexity to the code but I do not
- * think it makes much sense to do so.
- * There is no way to prevent the argument mismatch
- * issues 100%. Printf can crash if aguments are
- * missed or bad, so do we...
- */
-
- /* Get data */
- switch(type) {
-
- case COL_TYPE_STRING: data_str = va_arg(args, char *);
- data = (void *)data_str;
- if (has_len) length = va_arg(args, int);
- else length = strlen(data_str) + 1;
- TRACE_INFO_STRING("Adding string:", data_str);
- TRACE_INFO_NUMBER("Length:",length);
- break;
-
- case COL_TYPE_BINARY: data_bin = va_arg(args, void *);
- data = (void *)data_bin;
- length = va_arg(args, int);
- break;
-
- case COL_TYPE_INTEGER: data_int = va_arg(args, int);
- data = (void *)(&data_int);
- length = sizeof(int);
- break;
-
- case COL_TYPE_UNSIGNED: data_uint = va_arg(args, unsigned int);
- data = (void *)(&data_uint);
- length = sizeof(unsigned int);
- break;
-
- case COL_TYPE_LONG: data_long = va_arg(args, long);
- data = (void *)(&data_long);
- length = sizeof(long);
- break;
-
- case COL_TYPE_ULONG: data_ulong = va_arg(args, unsigned long);
- data = (void *)(&data_ulong);
- length = sizeof(unsigned long);
- break;
-
- case COL_TYPE_DOUBLE: data_dbl = va_arg(args, double);
- data = (void *)(&data_dbl);
- length = sizeof(double);
- break;
-
- case COL_TYPE_BOOL: if (bool_type) {
- /* It is a string */
- data_str = va_arg(args,char *);
- /* Check if it is a valid str */
- if (!(convert_bool(data_str, &data_bool))) {
- TRACE_ERROR_STRING("Failed to to convert bool value", data_str);
- free(propcopy);
- return EINVAL;
- }
- }
- else {
- /* It is an int */
- data_int = va_arg(args, int);
- if (data_int) data_bool = 1;
- else data_bool = 0;
- }
-
- data = (void *)(&data_bool);
- length = sizeof(unsigned char);
- break;
-
- default:
- TRACE_ERROR_STRING("Invalid or unknown type", propcopy);
- free(propcopy);
- return EINVAL;
- }
-
- /* Insert or update */
- error = col_insert_property_with_ref(col,
- NULL,
- COL_DSP_END,
- NULL,
- 0,
- COL_INSERT_DUPOVER,
- propcopy,
- type,
- data,
- length,
- NULL);
- if (error) {
- TRACE_ERROR_STRING("Error inserting property", property);
- free(propcopy);
- return error;
- }
- }
- else {
- /* Remove case */
- while (error != ENOENT) {
- error = col_remove_item(col,
- NULL,
- COL_DSP_FIRSTDUP,
- propcopy,
- 0,
- COL_TYPE_ANY);
- if ((error) && (error != ENOENT)) {
- TRACE_ERROR_STRING("Error deleting property", propcopy);
- free(propcopy);
- return error;
- }
- }
- error = EOK;
- }
- free(propcopy);
- }
- else {
- /* Errors related to key interpretation are handled here */
- TRACE_ERROR_STRING("Invalid arg", arg);
- return EINVAL;
- }
- } /* end of arg processing loop */
-
- TRACE_FLOW_STRING("process_arg_list", "Exit");
- return error;
-}
-
-
-
-/*****************************************************************************/
-/* Create event template */
-int elapi_create_event_tplt_with_vargs(struct collection_item **tpl,
- unsigned base,
- va_list args)
-{
- int error = EOK;
- struct collection_item *new_tpl = NULL;
-
- TRACE_FLOW_STRING("elapi_create_event_tplt_with_vargs", "Entry");
-
- if (tpl == NULL ) {
- TRACE_ERROR_STRING("Template storage must be provided", "");
- return EINVAL;
- }
-
- *tpl = NULL;
-
- /* Create collection */
- error = col_create_collection(&new_tpl, E_TEMPLATE_NAME, COL_CLASS_ELAPI_TEMPLATE);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to create collection. Error", error);
- return error;
- }
-
- /* Add elements using base mask */
- error = add_base_elements(new_tpl, base);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add base elements. Error", error);
- col_destroy_collection(new_tpl);
- return error;
- }
-
- /* Process variable argument list */
- error = process_arg_list(new_tpl, args);
-
- if (error) {
- TRACE_ERROR_NUMBER("Failed to process argument list. Error", error);
- col_destroy_collection(new_tpl);
- return error;
- }
-
- *tpl = new_tpl;
-
- TRACE_FLOW_STRING("elapi_create_event_tplt_with_vargs", "Exit");
- return error;
-}
-
-
-/* Create event template */
-int elapi_create_event_tplt(struct collection_item **tpl,
- unsigned base, ...)
-{
- int error = EOK;
- va_list args;
-
- TRACE_FLOW_STRING("elapi_create_event_tplt", "Entry");
-
- /* Process varible arguments */
- va_start(args, base);
-
- /* Create template using arguments */
- error = elapi_create_event_tplt_with_vargs(tpl,
- base,
- args);
-
- va_end(args);
-
- TRACE_FLOW_STRING("elapi_create_event_tplt", "Exit");
- return error;
-}
-
-/* Function to destroy event template */
-void elapi_destroy_event_tplt(struct collection_item *tpl)
-{
- TRACE_FLOW_STRING("elapi_destroy_event_tplt", "Entry");
-
- col_destroy_collection(tpl);
-
- TRACE_FLOW_STRING("elapi_destroy_event_tplt", "Exit");
-}
-
-
-/* Create event from template, colection and arguments */
-int elapi_create_event_with_vargs(struct collection_item **event,
- struct collection_item *tpl,
- struct collection_item *collection,
- int mode, va_list args)
-{
- int error = EOK;
- struct collection_item *evt = NULL;
- const char *alias;
-
- TRACE_FLOW_STRING("elapi_create_event_with_vargs", "Entry");
-
- /* Check storage */
- if (event == NULL) {
- TRACE_ERROR_STRING("Event storage must be provided", "");
- return EINVAL;
- }
-
- *event = NULL;
-
- /* Create collection */
- error = col_create_collection(&evt, E_EVENT_NAME, COL_CLASS_ELAPI_EVENT);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to create collection. Error", error);
- return error;
- }
-
- /* Add elements from the template */
- /* Check for template */
- if (tpl != NULL) {
- error = col_add_collection_to_collection(evt, NULL, NULL,
- (struct collection_item *)tpl,
- COL_ADD_MODE_FLAT);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add elements from the template. Error", error);
- col_destroy_collection(evt);
- return error;
- }
- }
-
- /* Add elements from the collection */
- if (collection != NULL) {
- /* If we are told to use FLAT DOT mode
- * add collection with prefixing here.
- */
- if (mode == COL_ADD_MODE_FLATDOT) {
- alias = col_get_item_property(collection, NULL);
- }
- else alias = NULL;
-
- error = col_add_collection_to_collection(evt, NULL, alias, collection, mode);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add elements from external collection. Error", error);
- col_destroy_collection(evt);
- return error;
- }
- }
-
- /* Process variable argument list */
- error = process_arg_list(evt, args);
-
- if (error) {
- TRACE_ERROR_NUMBER("Failed to process argument list. Error", error);
- col_destroy_collection(evt);
- return error;
- }
-
- *event = evt;
-
- TRACE_FLOW_STRING("elapi_create_event_with_vargs", "Exit");
- return error;
-}
-
-
-/* Create event a wrapper around a function with arg list */
-int elapi_create_event(struct collection_item **event,
- struct collection_item *tpl,
- struct collection_item *collection,
- int mode, ...)
-{
- int error = EOK;
- va_list args;
-
- TRACE_FLOW_STRING("elapi_create_event", "Entry");
-
- va_start(args, mode);
-
- error = elapi_create_event_with_vargs(event,
- tpl,
- collection,
- mode,
- args);
- va_end(args);
-
-
- TRACE_FLOW_STRING("elapi_create_event", "Exit");
- return error;
-}
-
-/* Add/Updates/Removes the event attributes based on the and provided key value pairs */
-int elapi_modify_event(struct collection_item *event,
- struct collection_item *collection,
- int mode, ...)
-{
- int error = EOK;
- va_list args;
- const char *alias;
-
- TRACE_FLOW_STRING("elapi_modify_event", "Entry");
-
- /* Check event */
- if (event == NULL ) {
- TRACE_ERROR_STRING("Event must be provided", "");
- return EINVAL;
- }
-
- /* Add elements from the template */
- if (collection != NULL) {
- /* If we are told to use FLAT DOT mode
- * add collection with prefixing here.
- */
- if (mode == COL_ADD_MODE_FLATDOT) {
- alias = col_get_item_property(collection, NULL);
- }
- else alias = NULL;
- error = col_add_collection_to_collection(event, NULL, alias, collection, mode);
- if (error) {
- TRACE_ERROR_NUMBER("Failed to add elements from external collection. Error", error);
- col_destroy_collection(event);
- return error;
- }
- }
-
- /* Process varible arguments */
- va_start(args, mode);
-
- /* Process variable argument list */
- error = process_arg_list(event, args);
-
- va_end(args);
-
- if (error) {
- TRACE_ERROR_NUMBER("Failed to process argument list. Error", error);
- return error;
- }
-
- TRACE_FLOW_STRING("elapi_modify_event", "Exit");
- return error;
-}
-
-/* Create a copy of the event */
-int elapi_copy_event(struct collection_item **new_event,
- struct collection_item *source_event)
-{
- int error = EOK;
-
- TRACE_FLOW_STRING("elapi_copy_event", "Entry");
-
- error = col_copy_collection(new_event,
- source_event,
- NULL,
- COL_COPY_NORMAL);
-
- TRACE_FLOW_NUMBER("elapi_copy_event. Exit Returning", error);
- return error;
-}
-
-/* Function to destroy event. */
-void elapi_destroy_event(struct collection_item *event)
-{
- TRACE_FLOW_STRING("elapi_destroy_event", "Entry");
-
- col_destroy_collection(event);
-
- TRACE_FLOW_STRING("elapi_destroy_event", "Exit");
-}