Fixed expression searching in sicslogquery Added proton monitot to tasscan output Chnaged SICS scripts to reflect the switch from TRICS to ZEBRA
215 lines
5.5 KiB
C
215 lines
5.5 KiB
C
/**
|
|
* This does the query execution for the new mongodb based sicslog.
|
|
*
|
|
* COPYRIGHT GPL
|
|
*
|
|
* Mark Koennecke, February 2016
|
|
*/
|
|
#include <sicslogquery.h>
|
|
#include <unistd.h>
|
|
#include <sys/time.h>
|
|
#include <logv2.h>
|
|
#include <approxidate.h>
|
|
|
|
static char lastError[1024];
|
|
static char mongoURL[1024];
|
|
static char inst[132];
|
|
|
|
static mongoc_client_t *client;
|
|
static mongoc_collection_t *collection;
|
|
|
|
/*--------------------------------------------------------------------------------*/
|
|
char * sicslogGetError(void)
|
|
{
|
|
/*
|
|
May be change to strdup(lastError);
|
|
*/
|
|
return lastError;
|
|
}
|
|
/*--------------------------------------------------------------------------------*/
|
|
int sicslogSetup(char *url, char *instPar)
|
|
{
|
|
memset(inst,0,sizeof(inst));
|
|
|
|
if(instPar != NULL){
|
|
strncpy(inst,instPar, sizeof(inst));
|
|
}
|
|
strncpy(mongoURL,url,sizeof(mongoURL));
|
|
|
|
mongoc_init();
|
|
client = mongoc_client_new (mongoURL);
|
|
if(!client){
|
|
snprintf(lastError,sizeof(lastError),"ERROR: failed to connect to mongodb, bad URL?");
|
|
return 1;
|
|
}
|
|
return 0;
|
|
}
|
|
/*--------------------------------------------------------------------------------*/
|
|
static unsigned int sevFromText(const char *txt)
|
|
{
|
|
static const char *severityText[] = {"fatal",
|
|
"error",
|
|
"warn",
|
|
"info",
|
|
"verbose",
|
|
"debug",
|
|
NULL
|
|
};
|
|
int sev = 0;
|
|
while(severityText[sev] != NULL){
|
|
if(strcmp(txt,severityText[sev]) == 0){
|
|
break;
|
|
}
|
|
sev++;
|
|
}
|
|
sev++; /* starting at 1 rather then 0 */
|
|
return sev;
|
|
}
|
|
/*---------------------------------------------------------------------------*/
|
|
int sicslogQuery(int argc, char *argv[], ResultCallback_t func, void *userData)
|
|
{
|
|
char c;
|
|
time_t to = time(NULL), from = to - 3600;
|
|
int severity = INFO, mult = 1, status = 0;
|
|
char *sub = NULL;
|
|
char *exp = NULL;
|
|
char *instLocal = NULL;
|
|
char *tmp, *pPtr;
|
|
char jsonQuery[2024], subQuery[132];
|
|
struct timeval tv;
|
|
mongoc_collection_t *collection = NULL;
|
|
bson_t *query;
|
|
const bson_t *doc;
|
|
mongoc_cursor_t *cursor;
|
|
bson_error_t err;
|
|
|
|
/*
|
|
parse options
|
|
*/
|
|
optind = 1;
|
|
while((c = getopt(argc,argv,"s:l:f:t:i:e:c:h")) != -1) {
|
|
switch (c){
|
|
case 's':
|
|
sub = strdup(optarg);
|
|
break;
|
|
case 'l':
|
|
tmp = strdup(optarg);
|
|
if((pPtr = strrchr(tmp,(int)'h')) != NULL){
|
|
mult = 60;
|
|
*pPtr = '\0';
|
|
} else if((pPtr = strrchr(tmp,(int)'d')) != NULL){
|
|
mult = 24*60;
|
|
*pPtr = '\0';
|
|
}
|
|
from = to - atoi(tmp)*mult*60;
|
|
free(tmp);
|
|
break;
|
|
case 'f':
|
|
if(approxidate(optarg,&tv) == 0){
|
|
from = tv.tv_sec;
|
|
} else {
|
|
snprintf(lastError,sizeof(lastError),"Failed to parse date from %s", optarg);
|
|
return 1;
|
|
}
|
|
break;
|
|
case 't':
|
|
if(approxidate(optarg,&tv) == 0){
|
|
to = tv.tv_sec;
|
|
} else {
|
|
snprintf(lastError,sizeof(lastError),"Failed to parse date from %s", optarg);
|
|
return 1;
|
|
}
|
|
break;
|
|
case 'i':
|
|
instLocal = strdup(optarg);
|
|
break;
|
|
case 'e':
|
|
exp = strdup(optarg);
|
|
break;
|
|
case 'c':
|
|
severity = sevFromText(optarg);
|
|
break;
|
|
case 'h':
|
|
snprintf(
|
|
lastError,sizeof(lastError),
|
|
"Options: \n-s subsystem\n-l last(h,d)\n-f fromtime\n-t totime\n-i instrument\n-c severity\n%s",
|
|
"-e search-expression");
|
|
return 1;
|
|
break;
|
|
case '?':
|
|
if( optopt == 's' || optopt == 'l' || optopt == 'f' || optopt == 't'
|
|
|| optopt == 'i' || optopt == 'e' || optopt == 'c') {
|
|
snprintf(lastError,sizeof(lastError),"Option %c requires an argument", optopt);
|
|
} else {
|
|
snprintf(lastError,sizeof(lastError),"Unknown option %c", optopt);
|
|
}
|
|
return 1;
|
|
break;
|
|
}
|
|
}
|
|
|
|
if(instLocal == NULL && strlen(inst) > 1){
|
|
instLocal = strdup(inst);
|
|
}
|
|
if(instLocal == NULL){
|
|
snprintf(lastError,sizeof(lastError),"Do not know which instrument log to query, specify with -i");
|
|
return 1;
|
|
}
|
|
|
|
/*
|
|
build the query
|
|
*/
|
|
snprintf(jsonQuery, sizeof(jsonQuery),"{ \"timestamp\" : {\"$gt\": %ld, \"$lt\": %ld}, \"severity\": {\"$lte\": %d}",
|
|
from,to,severity);
|
|
if(sub != NULL){
|
|
snprintf(subQuery,sizeof(subQuery),", \"sub\" : \"%s\"", sub);
|
|
strncat(jsonQuery,subQuery,sizeof(jsonQuery));
|
|
}
|
|
if(exp != NULL){
|
|
snprintf(subQuery,sizeof(subQuery),", \"message\" : {\"$regex\": \"%s\" }", exp);
|
|
strncat(jsonQuery,subQuery,sizeof(jsonQuery));
|
|
}
|
|
strncat(jsonQuery,"}",sizeof(jsonQuery));
|
|
|
|
/*
|
|
now execute the query
|
|
*/
|
|
collection = mongoc_client_get_collection(client,instLocal,"log");
|
|
if(collection == NULL){
|
|
snprintf(lastError,sizeof(lastError),"Failed to find log for %s", instLocal);
|
|
status = 1;
|
|
goto cleanup;
|
|
}
|
|
fprintf(stdout,"The query: %s\n", jsonQuery);
|
|
query = bson_new_from_json((const uint8_t *)jsonQuery,strlen(jsonQuery), &err);
|
|
if(query == NULL){
|
|
snprintf(lastError,sizeof(lastError),"Failed to parse query with %s", err.message);
|
|
status = 1;
|
|
goto cleanup;
|
|
}
|
|
|
|
cursor = mongoc_collection_find (collection, MONGOC_QUERY_NONE, 0, 0, 0, query, NULL, NULL);
|
|
while (mongoc_cursor_next (cursor, &doc)) {
|
|
func(doc,userData);
|
|
}
|
|
|
|
cleanup:
|
|
if(sub != NULL){
|
|
free(sub);
|
|
}
|
|
if(exp != NULL){
|
|
free(exp);
|
|
}
|
|
if(query != NULL){
|
|
bson_destroy(query);
|
|
}
|
|
if(cursor != NULL){
|
|
/* mongoc_cursor_destroy(cursor); */
|
|
}
|
|
if(collection != NULL){
|
|
mongoc_collection_destroy(collection);
|
|
}
|
|
|
|
return status;
|
|
}
|