uint8_t md_sqlite_handle_munin_event(struct md_writer_sqlite *mws, struct md_munin_event *mme) { json_object *value; int64_t boottime = 0; json_object *session_obj; if (!json_object_object_get_ex(mme->json_blob, "session", &session_obj)) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to read data from session module (Munin)\n"); return RETVAL_FAILURE; } if (!json_object_object_get_ex(session_obj, "start", &value)) return RETVAL_FAILURE; if ((boottime = json_object_get_int64(value)) < 1400000000 ) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to read valid start time from session module (Munin): %" PRId64 "\n", boottime); return RETVAL_FAILURE; } sqlite3_stmt *stmt = mws->insert_monitor; sqlite3_clear_bindings(stmt); sqlite3_reset(stmt); if (sqlite3_bind_int(stmt, 1, mws->node_id) || sqlite3_bind_int(stmt, 2, mme->tstamp) || sqlite3_bind_int(stmt, 3, mme->sequence) || sqlite3_bind_int64(stmt, 4, boottime) ){ META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to bind values to INSERT query (Monitor)\n"); return RETVAL_FAILURE; } if (sqlite3_step(stmt) != SQLITE_DONE) return RETVAL_FAILURE; else return RETVAL_SUCCESS; }
static int32_t md_sqlite_execute_insert_update(struct md_writer_sqlite *mws, struct md_conn_event *mce) { sqlite3_stmt *stmt = mws->insert_update; sqlite3_clear_bindings(stmt); sqlite3_reset(stmt); if (sqlite3_bind_int(stmt, 1, mws->node_id) || sqlite3_bind_int64(stmt, 2, mws->session_id) || sqlite3_bind_int64(stmt, 3, mws->session_id_multip) || sqlite3_bind_int64(stmt, 4, mce->tstamp) || sqlite3_bind_int(stmt, 5, mce->sequence) || sqlite3_bind_int(stmt, 6, mce->l3_session_id) || sqlite3_bind_int(stmt, 7, mce->l4_session_id) || sqlite3_bind_text(stmt, 8, mce->event_value_str, strlen(mce->event_value_str), SQLITE_STATIC) || sqlite3_bind_int(stmt, 9, mce->interface_type) || sqlite3_bind_text(stmt, 10, mce->interface_id, strlen(mce->interface_id), SQLITE_STATIC) || sqlite3_bind_text(stmt, 11, mce->network_address, strlen(mce->network_address), SQLITE_STATIC)) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to bind values to INSERT query\n"); return SQLITE_ERROR; } if (mce->network_provider && sqlite3_bind_int(stmt, 12, mce->network_provider)) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to bind network provider\n"); return SQLITE_ERROR; } return sqlite3_step(stmt); }
static void md_sqlite_insert_fake_mode(struct md_writer_sqlite *mws, struct md_conn_event *mce, uint8_t mode) { const char *event_value_str = mce->event_value_str; int32_t retval; //TODO: Not a nice way to access parent variable mce->sequence = mde_inc_seq(mws->parent); mce->event_value = mode; mce->event_param = CONN_EVENT_META_MODE_UPDATE; mce->event_value_str = NULL; retval = md_sqlite_execute_insert(mws, mce); if (retval == SQLITE_DONE) META_PRINT_SYSLOG(mws->parent, LOG_INFO, "Inserted fake mode update\n"); else META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to insert fake mode update\n"); //Restore/update query after mode insert mce->event_param = CONN_EVENT_META_UPDATE; mce->event_value = 0; mce->event_value_str = event_value_str; }
uint8_t md_sqlite_handle_gps_event(struct md_writer_sqlite *mws, struct md_gps_event *mge) { if (mge->speed) mws->gps_speed = mge->speed; if (mge->minmea_id == MINMEA_SENTENCE_RMC) return RETVAL_IGNORE; //We dont need EVERY gps event, some devices send updates very frequently //Some of the devices we work with have timers that are ... strange if (mws->last_gps_insert > mge->tstamp_tv.tv_sec || mge->tstamp_tv.tv_sec - mws->last_gps_insert < GPS_EVENT_INTVL) return RETVAL_IGNORE; sqlite3_stmt *stmt = mws->insert_gps; sqlite3_clear_bindings(stmt); sqlite3_reset(stmt); if (sqlite3_bind_int(stmt, 1, mws->node_id) || sqlite3_bind_int(stmt, 2, mws->session_id) || // BootCount sqlite3_bind_int(stmt, 3, mws->session_id_multip) || // BootMultiplier sqlite3_bind_int(stmt, 4, mge->tstamp_tv.tv_sec) || sqlite3_bind_int(stmt, 5, mge->sequence) || sqlite3_bind_double(stmt, 6, mge->latitude) || sqlite3_bind_double(stmt, 7, mge->longitude)) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to bind values to INSERT query (GPS)\n"); return RETVAL_FAILURE; } if (mge->altitude && sqlite3_bind_double(stmt, 8, mge->altitude)) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to bind altitude\n"); return RETVAL_FAILURE; } if (mws->gps_speed && sqlite3_bind_double(stmt, 9, mws->gps_speed)) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to bind speed\n"); return RETVAL_FAILURE; } if (mge->satellites_tracked && sqlite3_bind_int(stmt, 10, mge->satellites_tracked)) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to bind num. satelites\n"); return RETVAL_FAILURE; } if (sqlite3_step(stmt) != SQLITE_DONE) { return RETVAL_FAILURE; } else { mws->last_gps_insert = mge->tstamp_tv.tv_sec; return RETVAL_SUCCESS; } }
static int32_t md_sqlite_execute_insert(struct md_writer_sqlite *mws, struct md_conn_event *mce) { int32_t retval; sqlite3_stmt *stmt = mws->insert_event; sqlite3_clear_bindings(stmt); sqlite3_reset(stmt); if (sqlite3_bind_int(stmt, 1, mws->node_id) || sqlite3_bind_int64(stmt, 2, mws->session_id) || sqlite3_bind_int64(stmt, 3, mws->session_id_multip) || sqlite3_bind_int64(stmt, 4, mce->tstamp) || sqlite3_bind_int(stmt, 5, mce->sequence) || sqlite3_bind_int(stmt, 6, mce->l3_session_id) || sqlite3_bind_int(stmt, 7, mce->l4_session_id) || sqlite3_bind_int(stmt, 8, mce->event_type) || sqlite3_bind_int(stmt, 9, mce->event_param) || sqlite3_bind_int(stmt, 12, mce->interface_type) || sqlite3_bind_int(stmt, 13, mce->interface_id_type) || sqlite3_bind_text(stmt, 14, mce->interface_id, strlen(mce->interface_id), SQLITE_STATIC) || sqlite3_bind_int(stmt, 16, mce->network_address_family) || sqlite3_bind_text(stmt, 17, mce->network_address, strlen(mce->network_address), SQLITE_STATIC)) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to bind values to INSERT query\n"); return SQLITE_ERROR; } if (mce->event_value != UINT8_MAX && sqlite3_bind_int(stmt, 10, mce->event_value)) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed bind event value (int)\n"); return SQLITE_ERROR; } if (mce->event_value_str != NULL && sqlite3_bind_text(stmt, 11, mce->event_value_str, strlen(mce->event_value_str), SQLITE_STATIC)) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to bind event value (string)\n"); return SQLITE_ERROR; } if (mce->network_provider) { retval = sqlite3_bind_int(stmt, 15, mce->network_provider); if (retval) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to bind provider to INSERT query\n"); return SQLITE_ERROR; } } return sqlite3_step(stmt); }
static void md_sqlite_insert_fake_events(struct md_writer_sqlite *mws, struct md_conn_event *mce, int32_t update_exists) { //TODO: Find a way to respect const int16_t mode_in_update = -1, mode_in_table = -1; int16_t quality_in_update = -1, quality_in_table = -1; char event_str_cpy[EVENT_STR_LEN]; size_t event_str_len; struct timeval t_now; if (mws->first_fake_update.tv_sec != 0) { gettimeofday(&t_now, NULL); if (t_now.tv_sec > mws->first_fake_update.tv_sec && t_now.tv_sec - mws->first_fake_update.tv_sec > FAKE_UPDATE_LIMIT) { mws->do_fake_updates = 0; return; } } else { gettimeofday(&(mws->first_fake_update), NULL); } event_str_len = strlen(mce->event_value_str); if (event_str_len >= EVENT_STR_LEN) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Event string too long\n"); return; } memcpy(event_str_cpy, mce->event_value_str, event_str_len); event_str_cpy[event_str_len] = '\0'; mode_in_update = metadata_utils_get_csv_pos(event_str_cpy, 2); quality_in_update = metadata_utils_get_csv_pos(event_str_cpy, 3); //If there was no update messge from before, then insert the fake mode/quality messages (just to be sure) //and return if (update_exists == SQLITE_DONE) { //Always insert mode on the first update, for consistency (it should be //possible to follow the mode update messages exclusively) if (mode_in_update != -1) md_sqlite_insert_fake_mode(mws, mce, mode_in_update); if (quality_in_update != -1) md_sqlite_insert_fake_quality(mws, mce, quality_in_update); return; } md_sqlite_get_last_update(mws, mce, &mode_in_table, &quality_in_table); //Get mode from last update message. If we can read modem mode, then this //value will be 0 or larger if (mode_in_update != -1 && mode_in_update != mode_in_table) md_sqlite_insert_fake_mode(mws, mce, mode_in_update); if (quality_in_update != -1 && quality_in_update != quality_in_table) md_sqlite_insert_fake_quality(mws, mce, quality_in_update); }
static int16_t md_sqlite_get_last_update(struct md_writer_sqlite *mws, struct md_conn_event *mce, int16_t *mode, int16_t *quality) { int16_t retval = -1; int numbytes = 0; const unsigned char *event_value_str = NULL; char event_str_cpy[EVENT_STR_LEN]; sqlite3_stmt *stmt = mws->last_update; sqlite3_clear_bindings(stmt); sqlite3_reset(stmt); *mode = -1; *quality = -1; if (sqlite3_bind_int(stmt, 1, mce->l3_session_id) || sqlite3_bind_int(stmt, 2, mce->l4_session_id) || sqlite3_bind_text(stmt, 3, mce->interface_id, strlen(mce->interface_id), SQLITE_STATIC) || sqlite3_bind_text(stmt, 4, mce->network_address, strlen(mce->network_address), SQLITE_STATIC)) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to bind values to SELECT query\n"); return retval; } while (sqlite3_step(stmt) == SQLITE_ROW) { event_value_str = sqlite3_column_text(stmt, 0); numbytes = sqlite3_column_bytes(stmt, 0); if (numbytes >= EVENT_STR_LEN) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Event value string will not fit in buffer\n"); return SQLITE_ERROR; } memcpy(event_str_cpy, event_value_str, numbytes); event_str_cpy[numbytes] = '\0'; *mode = metadata_utils_get_csv_pos(event_str_cpy, 2); *quality = metadata_utils_get_csv_pos(event_str_cpy, 3); break; } return retval; }
static uint8_t md_sqlite_handle_insert_conn_event(struct md_writer_sqlite *mws, struct md_conn_event *mce) { int32_t retval = md_sqlite_execute_insert(mws, mce); if (retval != SQLITE_DONE) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "INSERT failed: %s\n", sqlite3_errstr(retval)); return RETVAL_FAILURE; } return RETVAL_SUCCESS; }
static uint8_t md_sqlite_monitor_delete_db(struct md_writer_sqlite *mws) { int32_t retval = 0; sqlite3_reset(mws->delete_monitor); retval = sqlite3_step(mws->delete_monitor); if (retval == SQLITE_DONE) { return RETVAL_SUCCESS; } else { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to delete monitor table\n"); return RETVAL_FAILURE; } }
static void md_sqlite_insert_fake_quality(struct md_writer_sqlite *mws, struct md_conn_event *mce, uint8_t quality) { const char *event_value_str = mce->event_value_str; int32_t retval; mce->sequence = mde_inc_seq(mws->parent); mce->event_value = quality; mce->event_param = CONN_EVENT_META_QUALITY_UPDATE; mce->event_value_str = NULL; retval = md_sqlite_execute_insert(mws, mce); if (retval == SQLITE_DONE) META_PRINT_SYSLOG(mws->parent, LOG_INFO, "Inserted fake quality update\n"); else META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to insert fake quality update\n"); //Restore/update query after quality insert mce->event_param = CONN_EVENT_META_UPDATE; mce->event_value = 0; mce->event_value_str = event_value_str; }
static void run_test_mode(struct md_exporter *mde, uint32_t packets) { pthread_t thread; pthread_attr_t attr; pthread_attr_init(&attr); pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_JOINABLE); pthread_create(&thread, &attr, mde_run, mde); test_netlink(packets); pthread_join(thread, NULL); META_PRINT_SYSLOG(mde, LOG_ERR, "Threads should NEVER exit\n"); }
static int32_t md_sqlite_update_event(struct md_writer_sqlite *mws, struct md_conn_event *mce) { sqlite3_stmt *stmt = mws->update_update; sqlite3_clear_bindings(stmt); sqlite3_reset(stmt); if (sqlite3_bind_int64(stmt, 1, mce->tstamp) || sqlite3_bind_text(stmt, 2, mce->event_value_str, strlen(mce->event_value_str), SQLITE_STATIC) || sqlite3_bind_int(stmt, 3, mce->l3_session_id) || sqlite3_bind_int(stmt, 4, mce->l4_session_id) || sqlite3_bind_text(stmt, 5, mce->network_address, strlen(mce->network_address), SQLITE_STATIC) || sqlite3_bind_text(stmt, 6, mce->interface_id, strlen(mce->interface_id), SQLITE_STATIC)) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "Failed to bind values to UPDATE query\n"); return SQLITE_ERROR; } return sqlite3_step(stmt); }
static uint8_t md_sqlite_handle_update_event(struct md_writer_sqlite *mws, struct md_conn_event *mce) { //Check if update is present in update table by doing an insert int32_t retval = md_sqlite_execute_insert_update(mws, mce); if (mws->do_fake_updates) md_sqlite_insert_fake_events(mws, mce, retval); //No need to do UPDATE if INSERT was successful if (retval == SQLITE_DONE) return RETVAL_SUCCESS; //Update in update table retval = md_sqlite_update_event(mws, mce); if (retval != SQLITE_DONE) { META_PRINT_SYSLOG(mws->parent, LOG_ERR, "UPDATE failed: %s\n", sqlite3_errstr(retval)); return RETVAL_FAILURE; } return RETVAL_SUCCESS; }
int main(int argc, char *argv[]) { struct md_exporter *mde; int32_t i, option_index = 0; uint32_t packets = 0; uint8_t test_mode = 0, show_help = 0, num_writers = 0, num_inputs = 0; const char *logfile_path = NULL; static struct option core_options[] = { {"netlink", no_argument, 0, 'n'}, #ifdef SQLITE_SUPPORT {"sqlite", no_argument, 0, 's'}, #endif #ifdef NSB_GPS {"nsb_gps", no_argument, 0, 0 }, #endif #ifdef ZEROMQ_SUPPORT {"zeromq", no_argument, 0, 'z'}, #endif #ifdef NNE_SUPPORT {"nne", no_argument, 0, 0 }, #endif #ifdef GPSD_SUPPORT {"gpsd", no_argument, 0, 'g'}, #endif #ifdef MUNIN_SUPPORT {"munin", no_argument, 0, 'm'}, #endif #ifdef SYSEVENT_SUPPORT {"sysevent", no_argument, 0, 'y'}, #endif {"packets", required_argument, 0, 'p'}, {"test", no_argument, 0, 't'}, {"logfile", required_argument, 0, 'l'}, {"help", no_argument, 0, 'h'}, {0, 0, 0, 0 }}; //Try to configure core before we set up the outputters if (configure_core(&mde)) exit(EXIT_FAILURE); //Process core options, short options allowed. We do this here since we need //an allocated writers array opterr = 0; while (1) { //Use glic extension to avoid getopt permuting array while processing i = getopt_long(argc, argv, "--szhmgtnkp:l:", core_options, &option_index); if (i == -1) break; if (i == 0) { #ifdef NSB_GPS if (strcmp(core_options[option_index].name, "nsb_gps") == 0) { mde->md_inputs[MD_INPUT_GPS_NSB] = calloc(sizeof(struct md_input_gps_nsb), 1); if (mde->md_inputs[MD_INPUT_GPS_NSB] == NULL) { META_PRINT_SYSLOG(mde, LOG_ERR, "Could not allocate NSB GPS input\n"); exit(EXIT_FAILURE); } md_gps_nsb_setup(mde, (struct md_input_gps_nsb*) mde->md_inputs[MD_INPUT_GPS_NSB]); num_inputs++; } #endif #ifdef NNE_SUPPORT if (strcmp(core_options[option_index].name, "nne") == 0) { mde->md_writers[MD_WRITER_NNE] = calloc(sizeof(struct md_writer_nne), 1); if (mde->md_writers[MD_WRITER_NNE] == NULL) { META_PRINT_SYSLOG(mde, LOG_ERR, "Could not allocate NNE writer\n"); exit(EXIT_FAILURE); } md_nne_setup(mde, (struct md_writer_nne*) mde->md_writers[MD_WRITER_NNE]); num_writers++; } #endif continue; } switch (i) { case 'n': mde->md_inputs[MD_INPUT_NETLINK] = calloc(sizeof(struct md_input_netlink),1); if (mde->md_inputs[MD_INPUT_NETLINK] == NULL) { META_PRINT_SYSLOG(mde, LOG_ERR, "Could not allocate Netlink input\n"); exit(EXIT_FAILURE); } md_netlink_setup(mde, (struct md_input_netlink*) mde->md_inputs[MD_INPUT_NETLINK]); num_inputs++; break; #ifdef GPSD_SUPPORT case 'g': mde->md_inputs[MD_INPUT_GPSD] = calloc(sizeof(struct md_input_gpsd), 1); if (mde->md_inputs[MD_INPUT_GPSD] == NULL) { META_PRINT_SYSLOG(mde, LOG_ERR, "Could not allocate GPSD input\n"); exit(EXIT_FAILURE); } md_gpsd_setup(mde, (struct md_input_gpsd*) mde->md_inputs[MD_INPUT_GPSD]); num_inputs++; break; #endif #ifdef MUNIN_SUPPORT case 'm': mde->md_inputs[MD_INPUT_MUNIN] = calloc(sizeof(struct md_input_munin), 1); if (mde->md_inputs[MD_INPUT_MUNIN] == NULL) { META_PRINT_SYSLOG(mde, LOG_ERR, "Could not allocate Munin input\n"); exit(EXIT_FAILURE); } md_munin_setup(mde, (struct md_input_munin*) mde->md_inputs[MD_INPUT_MUNIN]); num_inputs++; break; #endif #ifdef SYSEVENT_SUPPORT case 'y': mde->md_inputs[MD_INPUT_SYSEVENT] = calloc(sizeof(struct md_input_sysevent), 1); if (mde->md_inputs[MD_INPUT_SYSEVENT] == NULL) { META_PRINT(mde->logfile, "Could not allocate Sysevent input\n"); exit(EXIT_FAILURE); } md_sysevent_setup(mde, (struct md_input_sysevent*) mde->md_inputs[MD_INPUT_SYSEVENT]); num_inputs++; break; #endif #ifdef SQLITE_SUPPORT case 's': mde->md_writers[MD_WRITER_SQLITE] = calloc(sizeof(struct md_writer_sqlite), 1); if (mde->md_writers[MD_WRITER_SQLITE] == NULL) { META_PRINT_SYSLOG(mde, LOG_ERR, "Could not allocate SQLite writer\n"); exit(EXIT_FAILURE); } md_sqlite_setup(mde, (struct md_writer_sqlite*) mde->md_writers[MD_WRITER_SQLITE]); num_writers++; break; #endif #ifdef ZEROMQ_SUPPORT case 'z': mde->md_writers[MD_WRITER_ZEROMQ] = calloc(sizeof(struct md_writer_zeromq), 1); if (mde->md_writers[MD_WRITER_ZEROMQ] == NULL) { META_PRINT_SYSLOG(mde, LOG_ERR, "Could not allocate SQLite writer\n"); exit(EXIT_FAILURE); } md_zeromq_setup(mde, (struct md_writer_zeromq*) mde->md_writers[MD_WRITER_ZEROMQ]); num_writers++; break; #endif case 't': test_mode = 1; break; case 'p': packets = (uint32_t) atoi(optarg); break; case 'l': logfile_path = optarg; break; case 'k': mde->use_syslog = 1; break; case 'h': show_help = 1; break; } } if (show_help) { print_usage(mde); exit(EXIT_SUCCESS); } if (num_writers == 0 || num_inputs == 0) { fprintf(stderr, "No input(s)/writer(s) specified\n"); exit(EXIT_FAILURE); } if (logfile_path) { mde->logfile = fopen(logfile_path, "a"); if (mde->logfile == NULL) { fprintf(stderr, "Could not open logfile: %s\n", logfile_path); exit(EXIT_FAILURE); } } for (i=0; i<=MD_INPUT_MAX; i++) { if (mde->md_inputs[i] != NULL) { META_PRINT_SYSLOG(mde, LOG_INFO, "Will configure input %d\n", i); //glic requires optind to be 0 for internal state to be reset when //using extensions optind = 0; if (mde->md_inputs[i]->init(mde->md_inputs[i], argc, argv)) exit(EXIT_FAILURE); } } for (i=0; i<=MD_WRITER_MAX; i++) { if (mde->md_writers[i] != NULL) { META_PRINT_SYSLOG(mde, LOG_INFO, "Will configure writer %d\n", i); //glic requires optind to be 0 for internal state to be reset when //using extensions optind = 0; if (mde->md_writers[i]->init(mde->md_writers[i], argc, argv)) exit(EXIT_FAILURE); } } if (test_mode) run_test_mode(mde, packets); else backend_event_loop_run(mde->event_loop); META_PRINT_SYSLOG(mde, LOG_ERR, "Threads should NEVER exit\n"); exit(EXIT_FAILURE); }
int main(int argc, char *argv[]) { struct md_exporter *mde; int32_t i; uint32_t packets = 0; uint8_t test_mode = 0, num_writers = 0, num_inputs = 0; const char *logfile_path = NULL; json_object *config = NULL; //Try to configure core before we set up the outputters if (configure_core(&mde)) exit(EXIT_FAILURE); //Process core options, short options allowed. We do this here since we need //an allocated writers array opterr = 0; while ((i = getopt(argc, argv, "c:h")) != -1) { if (i == -1) { break; } else if (i == 'c') { read_config(optarg, &config); } else if (i == 'h') { print_usage(); exit(EXIT_SUCCESS); } } if (config == NULL) { META_PRINT_SYSLOG(mde, LOG_ERR, "Parameter -c is required to run.\n"); exit(EXIT_FAILURE); } json_object_object_foreach(config, key, val) { if (!strcmp(key, "netlink")) { mde->md_inputs[MD_INPUT_NETLINK] = calloc(sizeof(struct md_input_netlink),1); if (mde->md_inputs[MD_INPUT_NETLINK] == NULL) { META_PRINT_SYSLOG(mde, LOG_ERR, "Could not allocate Netlink input\n"); exit(EXIT_FAILURE); } md_netlink_setup(mde, (struct md_input_netlink*) mde->md_inputs[MD_INPUT_NETLINK]); num_inputs++; } #ifdef NSB_GPS else if (!strcmp(key, "nsb_gps")) { mde->md_inputs[MD_INPUT_GPS_NSB] = calloc(sizeof(struct md_input_gps_nsb), 1); if (mde->md_inputs[MD_INPUT_GPS_NSB] == NULL) { META_PRINT_SYSLOG(mde, LOG_ERR, "Could not allocate NSB GPS input\n"); exit(EXIT_FAILURE); } md_gps_nsb_setup(mde, (struct md_input_gps_nsb*) mde->md_inputs[MD_INPUT_GPS_NSB]); num_inputs++; } #endif #ifdef NNE_SUPPORT else if (!strcmp(key, "nne")) { mde->md_writers[MD_WRITER_NNE] = calloc(sizeof(struct md_writer_nne), 1); if (mde->md_writers[MD_WRITER_NNE] == NULL) { META_PRINT_SYSLOG(mde, LOG_ERR, "Could not allocate NNE writer\n"); exit(EXIT_FAILURE); } md_nne_setup(mde, (struct md_writer_nne*) mde->md_writers[MD_WRITER_NNE]); num_writers++; } #endif #ifdef GPSD_SUPPORT else if (!strcmp(key, "gpsd")) { mde->md_inputs[MD_INPUT_GPSD] = calloc(sizeof(struct md_input_gpsd), 1); if (mde->md_inputs[MD_INPUT_GPSD] == NULL) { META_PRINT_SYSLOG(mde, LOG_ERR, "Could not allocate GPSD input\n"); exit(EXIT_FAILURE); } md_gpsd_setup(mde, (struct md_input_gpsd*) mde->md_inputs[MD_INPUT_GPSD]); num_inputs++; } #endif #ifdef MUNIN_SUPPORT else if (!strcmp(key, "munin")) { mde->md_inputs[MD_INPUT_MUNIN] = calloc(sizeof(struct md_input_munin), 1); if (mde->md_inputs[MD_INPUT_MUNIN] == NULL) { META_PRINT_SYSLOG(mde, LOG_ERR, "Could not allocate Munin input\n"); exit(EXIT_FAILURE); } md_munin_setup(mde, (struct md_input_munin*) mde->md_inputs[MD_INPUT_MUNIN]); num_inputs++; } #endif #ifdef SYSEVENT_SUPPORT else if (!strcmp(key, "sysevent")) { mde->md_inputs[MD_INPUT_SYSEVENT] = calloc(sizeof(struct md_input_sysevent), 1); if (mde->md_inputs[MD_INPUT_SYSEVENT] == NULL) { META_PRINT(mde->logfile, "Could not allocate Sysevent input\n"); exit(EXIT_FAILURE); } md_sysevent_setup(mde, (struct md_input_sysevent*) mde->md_inputs[MD_INPUT_SYSEVENT]); num_inputs++; } #endif #ifdef SQLITE_SUPPORT else if (!strcmp(key, "sqlite")) { mde->md_writers[MD_WRITER_SQLITE] = calloc(sizeof(struct md_writer_sqlite), 1); if (mde->md_writers[MD_WRITER_SQLITE] == NULL) { META_PRINT_SYSLOG(mde, LOG_ERR, "Could not allocate SQLite writer\n"); exit(EXIT_FAILURE); } md_sqlite_setup(mde, (struct md_writer_sqlite*) mde->md_writers[MD_WRITER_SQLITE]); num_writers++; } #endif #ifdef ZEROMQ_SUPPORT else if (!strcmp(key, "zmq")) { mde->md_writers[MD_WRITER_ZEROMQ] = calloc(sizeof(struct md_writer_zeromq), 1); if (mde->md_writers[MD_WRITER_ZEROMQ] == NULL) { META_PRINT_SYSLOG(mde, LOG_ERR, "Could not allocate SQLite writer\n"); exit(EXIT_FAILURE); } md_zeromq_setup(mde, (struct md_writer_zeromq*) mde->md_writers[MD_WRITER_ZEROMQ]); num_writers++; } #endif else if (!strcmp(key, "test")) { test_mode = 1; } else if (!strcmp(key, "packets")) { packets = (uint32_t) json_object_get_int(val); } else if (!strcmp(key, "logfile")) { logfile_path = json_object_get_string(val); } else if (!strcmp(key, "syslog")) { mde->use_syslog = json_object_get_int(val); } } if (num_writers == 0 || num_inputs == 0) { fprintf(stderr, "No input(s)/writer(s) specified\n"); exit(EXIT_FAILURE); } if (logfile_path) { mde->logfile = fopen(logfile_path, "a"); if (mde->logfile == NULL) { fprintf(stderr, "Could not open logfile: %s\n", logfile_path); exit(EXIT_FAILURE); } } for (i=0; i<=MD_INPUT_MAX; i++) { if (mde->md_inputs[i] != NULL) { META_PRINT_SYSLOG(mde, LOG_INFO, "Will configure input %d\n", i); //glic requires optind to be 0 for internal state to be reset when //using extensions optind = 0; if (mde->md_inputs[i]->init(mde->md_inputs[i], config)) exit(EXIT_FAILURE); } } for (i=0; i<=MD_WRITER_MAX; i++) { if (mde->md_writers[i] != NULL) { META_PRINT_SYSLOG(mde, LOG_INFO, "Will configure writer %d\n", i); //glic requires optind to be 0 for internal state to be reset when //using extensions optind = 0; if (mde->md_writers[i]->init(mde->md_writers[i], config)) exit(EXIT_FAILURE); } } json_object_put(config); if (test_mode) run_test_mode(mde, packets); else backend_event_loop_run(mde->event_loop); META_PRINT_SYSLOG(mde, LOG_ERR, "Threads should NEVER exit\n"); exit(EXIT_FAILURE); }
static uint8_t md_input_netlink_parse_conn_event(struct md_input_netlink *min, struct json_object *meta_obj) { struct md_conn_event *mce = min->mce; json_object_object_foreach(meta_obj, key, val) { if (!strcmp(key, "md_seq")) mce->sequence = (uint16_t) json_object_get_int(val); if (!strcmp(key, "timestamp")) mce->tstamp = json_object_get_int64(val); if (!strcmp(key, "event_type")) mce->event_type = (uint8_t) json_object_get_int(val); if (!strcmp(key, "event_param")) mce->event_param = (uint8_t) json_object_get_int(val); if (!strcmp(key, "event_value")) mce->event_value = (uint8_t) json_object_get_int(val); if (!strcmp(key, "event_value_str")) mce->event_value_str = json_object_get_string(val); if (!strcmp(key, "interface_id_type")) mce->interface_id_type = (uint8_t) json_object_get_int(val); if (!strcmp(key, "interface_id")) mce->interface_id = json_object_get_string(val); if (!strcmp(key, "imei")) mce->imei = json_object_get_string(val); if (!strcmp(key, "imsi")) mce->imsi = json_object_get_string(val); if (!strcmp(key, "interface_name")) mce->interface_name = json_object_get_string(val); if (!strcmp(key, "interface_type")) mce->interface_type = (uint8_t) json_object_get_int(val); if (!strcmp(key, "network_address_family")) mce->network_address_family = (uint8_t) json_object_get_int(val); if (!strcmp(key, "network_address")) mce->network_address = json_object_get_string(val); if (!strcmp(key, "network_provider_type")) mce->network_provider_type = (uint8_t) json_object_get_int(val); if (!strcmp(key, "network_provider")) mce->network_provider = json_object_get_int(val); if (!strcmp(key, "l3_session_id")) mce->l3_session_id = (uint64_t) json_object_get_int64(val); if (!strcmp(key, "l4_session_id")) mce->l4_session_id = (uint64_t) json_object_get_int64(val); if (!strcmp(key, "signal_strength")) mce->signal_strength = (int8_t) json_object_get_int(val); if (!strcmp(key, "rx_bytes")) mce->rx_bytes = (uint64_t) json_object_get_int64(val); if (!strcmp(key, "tx_bytes")) mce->tx_bytes = (uint64_t) json_object_get_int64(val); } if (mce->event_param == CONN_EVENT_DATA_USAGE_UPDATE) { if (!mce->tstamp || !mce->event_param || !mce->interface_id || (mce->imei && !mce->imsi) || (mce->imsi && !mce->imei)) { META_PRINT_SYSLOG(min->parent, LOG_ERR, "Missing required argument in usage JSON\n"); return RETVAL_FAILURE; } else { return RETVAL_SUCCESS; } } if (!mce->tstamp || !mce->sequence || !mce->l3_session_id || !mce->event_param || !mce->interface_type || !mce->network_address_family || !mce->network_address || !mce->interface_id || !mce->interface_id_type) { META_PRINT_SYSLOG(min->parent, LOG_ERR, "Missing required argument in JSON\n"); return RETVAL_FAILURE; } //We need to update the value in case of a connection event update, since it //is a string //TODO: Implement a more elegant technique if we get more cases like this if (mce->event_param == CONN_EVENT_META_UPDATE && !mce->event_value_str) { META_PRINT_SYSLOG(min->parent, LOG_ERR, "Missing event value for connection update\n"); return RETVAL_FAILURE; } return RETVAL_SUCCESS; }