summaryrefslogtreecommitdiffstats
path: root/output/ulogd_output_JSON.c
diff options
context:
space:
mode:
Diffstat (limited to 'output/ulogd_output_JSON.c')
-rw-r--r--output/ulogd_output_JSON.c86
1 files changed, 56 insertions, 30 deletions
diff --git a/output/ulogd_output_JSON.c b/output/ulogd_output_JSON.c
index 6edfa90..f80d0e2 100644
--- a/output/ulogd_output_JSON.c
+++ b/output/ulogd_output_JSON.c
@@ -33,6 +33,10 @@
#include <ulogd/conffile.h>
#include <jansson.h>
+#ifndef UNIX_PATH_MAX
+#define UNIX_PATH_MAX 108
+#endif
+
#ifndef ULOGD_JSON_DEFAULT
#define ULOGD_JSON_DEFAULT "/var/log/ulogd.json"
#endif
@@ -146,23 +150,21 @@ static void close_socket(struct json_priv *op) {
static int _connect_socket_unix(struct ulogd_pluginstance *pi)
{
+ const char *socket_path = file_ce(pi->config_kset).u.string;
struct json_priv *op = (struct json_priv *) &pi->private;
- struct sockaddr_un u_addr;
+ struct sockaddr_un u_addr = { .sun_family = AF_UNIX };
int sfd;
close_socket(op);
- ulogd_log(ULOGD_DEBUG, "connecting to unix:%s\n",
- file_ce(pi->config_kset).u.string);
+ ulogd_log(ULOGD_DEBUG, "connecting to unix:%s\n", socket_path);
+ strcpy(u_addr.sun_path, socket_path);
sfd = socket(AF_UNIX, SOCK_STREAM, 0);
- if (sfd == -1) {
+ if (sfd == -1)
return -1;
- }
- u_addr.sun_family = AF_UNIX;
- strncpy(u_addr.sun_path, file_ce(pi->config_kset).u.string,
- sizeof(u_addr.sun_path) - 1);
- if (connect(sfd, (struct sockaddr *) &u_addr, sizeof(struct sockaddr_un)) == -1) {
+
+ if (connect(sfd, (struct sockaddr *) &u_addr, sizeof(u_addr)) == -1) {
close(sfd);
return -1;
}
@@ -269,14 +271,14 @@ static int json_interp_file(struct ulogd_pluginstance *upi, char *buf)
return ULOGD_IRET_OK;
}
-#define MAX_LOCAL_TIME_STRING 38
+#define MAX_LOCAL_TIME_STRING 80
static int json_interp(struct ulogd_pluginstance *upi)
{
struct json_priv *opi = (struct json_priv *) &upi->private;
+ char *dvc, *buf, *tmp;
unsigned int i;
- char *buf;
- int buflen;
+ size_t buflen;
json_t *msg;
msg = json_object();
@@ -302,11 +304,12 @@ static int json_interp(struct ulogd_pluginstance *upi)
now = time(NULL);
t = localtime_r(&now, &result);
if (unlikely(*opi->cached_tz = '\0' || t->tm_gmtoff != opi->cached_gmtoff)) {
+ int gmtoff = t->tm_gmtoff % 86400;
+ int gmtoff_hours = gmtoff / 3600;
+ int gmtoff_minutes = abs(gmtoff) / 60 % 60;
+
snprintf(opi->cached_tz, sizeof(opi->cached_tz),
- "%c%02d%02d",
- t->tm_gmtoff > 0 ? '+' : '-',
- abs(t->tm_gmtoff) / 60 / 60,
- abs(t->tm_gmtoff) / 60 % 60);
+ "%+03d%02d", gmtoff_hours, gmtoff_minutes);
}
if (pp_is_valid(inp, opi->usec_idx)) {
@@ -332,12 +335,8 @@ static int json_interp(struct ulogd_pluginstance *upi)
json_object_set_new(msg, "timestamp", json_string(timestr));
}
- if (upi->config_kset->ces[JSON_CONF_DEVICE].u.string) {
- char *dvc = upi->config_kset->ces[JSON_CONF_DEVICE].u.string;
- json_object_set_new(msg, "dvc", json_string(dvc));
- }
-
-
+ dvc = upi->config_kset->ces[JSON_CONF_DEVICE].u.string;
+ json_object_set_new(msg, "dvc", json_string(dvc));
for (i = 0; i < upi->input.num_keys; i++) {
struct ulogd_key *key = upi->input.keys[i].u.source;
@@ -365,6 +364,9 @@ static int json_interp(struct ulogd_pluginstance *upi)
case ULOGD_RET_INT32:
json_object_set_new(msg, field_name, json_integer(key->u.value.i32));
break;
+ case ULOGD_RET_INT64:
+ json_object_set_new(msg, field_name, json_integer(key->u.value.i64));
+ break;
case ULOGD_RET_UINT8:
if ((upi->config_kset->ces[JSON_CONF_BOOLEAN_LABEL].u.value != 0)
&& (!strcmp(key->name, "raw.label"))) {
@@ -391,7 +393,6 @@ static int json_interp(struct ulogd_pluginstance *upi)
}
}
-
buf = json_dumps(msg, 0);
json_decref(msg);
if (buf == NULL) {
@@ -399,13 +400,15 @@ static int json_interp(struct ulogd_pluginstance *upi)
return ULOGD_IRET_ERR;
}
buflen = strlen(buf);
- buf = realloc(buf, sizeof(char)*(buflen+2));
- if (buf == NULL) {
+ tmp = realloc(buf, buflen + sizeof("\n"));
+ if (tmp == NULL) {
+ free(buf);
ulogd_log(ULOGD_ERROR, "Could not create message\n");
return ULOGD_IRET_ERR;
}
- strncat(buf, "\n", 1);
- buflen++;
+ buf = tmp;
+ buf[buflen++] = '\n';
+ buf[buflen] = '\0';
if (opi->mode == JSON_MODE_FILE)
return json_interp_file(upi, buf);
@@ -430,9 +433,33 @@ static void reopen_file(struct ulogd_pluginstance *upi)
}
}
+static int validate_unix_socket(struct ulogd_pluginstance *upi)
+{
+ const char *socket_path = file_ce(upi->config_kset).u.string;
+
+ if (!socket_path[0]) {
+ ulogd_log(ULOGD_ERROR, "missing unix socket path");
+ return -1;
+ }
+ if (strlen(socket_path) >= UNIX_PATH_MAX) {
+ ulogd_log(ULOGD_ERROR, "unix socket path `%s' is longer than %u\n",
+ file_ce(upi->config_kset).u.string, UNIX_PATH_MAX);
+ return -1;
+ }
+
+ return 0;
+}
+
static void reopen_socket(struct ulogd_pluginstance *upi)
{
+ struct json_priv *op = (struct json_priv *) &upi->private;
+
ulogd_log(ULOGD_NOTICE, "JSON: reopening socket\n");
+
+ if (op->mode == JSON_MODE_UNIX &&
+ validate_unix_socket(upi) < 0)
+ return;
+
if (_connect_socket(upi) < 0) {
ulogd_log(ULOGD_ERROR, "can't open JSON "
"socket: %s\n",
@@ -505,9 +532,8 @@ static int json_init_socket(struct ulogd_pluginstance *upi)
{
struct json_priv *op = (struct json_priv *) &upi->private;
- if (host_ce(upi->config_kset).u.string == NULL)
- return -1;
- if (port_ce(upi->config_kset).u.string == NULL)
+ if (op->mode == JSON_MODE_UNIX &&
+ validate_unix_socket(upi) < 0)
return -1;
op->sock = -1;