2018-11-27 12:47:18 +01:00
|
|
|
#include <stdio.h>
|
|
|
|
#include <stdlib.h>
|
|
|
|
#include <stdint.h>
|
|
|
|
#include <getopt.h>
|
|
|
|
#include <string.h>
|
2018-11-27 15:19:40 +01:00
|
|
|
#include <sys/types.h>
|
|
|
|
#include <sys/stat.h>
|
|
|
|
#include <fcntl.h>
|
|
|
|
#include <unistd.h>
|
|
|
|
#include <errno.h>
|
2018-11-27 23:14:23 +01:00
|
|
|
#include <time.h>
|
2018-11-27 12:47:18 +01:00
|
|
|
|
|
|
|
#include "d4.h"
|
2018-11-27 22:37:44 +01:00
|
|
|
//
|
|
|
|
int d4_check_config(d4_t* d4)
|
|
|
|
{
|
|
|
|
// TODO implement other sources, file, fifo, unix_socket ...
|
|
|
|
if (strlen(d4->conf[SOURCE]) > strlen(STDIN)) {
|
|
|
|
if (!strncmp(d4->conf[SOURCE],STDIN, strlen(STDIN))) {
|
|
|
|
d4->source.fd = STDIN_FILENO;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
//TODO implement other destinations file, fifo unix_socket ...
|
|
|
|
if (strlen(d4->conf[DESTINATION]) > strlen(STDOUT)) {
|
|
|
|
if (!strncmp(d4->conf[DESTINATION],STDOUT, strlen(STDOUT))) {
|
|
|
|
d4->destination.fd = STDOUT_FILENO;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
d4->snaplen = atoi(d4->conf[SNAPLEN]);
|
|
|
|
if ((d4->snaplen < 0) || (d4->snaplen > MAXSNAPLEN)) {
|
|
|
|
d4->snaplen = 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
printf("TEST snaplen %d stdin %d stdout %d\n", d4->snaplen, STDIN_FILENO, STDOUT_FILENO);
|
|
|
|
//FIXME Check other parameters
|
|
|
|
if (( d4->destination.fd > 0 ) && ( d4->snaplen >0 )) {
|
|
|
|
return 1;
|
|
|
|
}
|
|
|
|
return -1;
|
|
|
|
}
|
|
|
|
|
2018-11-27 12:47:18 +01:00
|
|
|
//Returns -1 on error, 0 otherwise
|
|
|
|
int d4_load_config(d4_t* d4)
|
|
|
|
{
|
2018-11-27 14:42:35 +01:00
|
|
|
int i;
|
2018-11-27 15:19:40 +01:00
|
|
|
int fd;
|
2018-11-27 14:42:35 +01:00
|
|
|
char *buf;
|
|
|
|
buf=calloc(1,2*FILENAME_MAX);
|
|
|
|
if (buf) {
|
|
|
|
for (i=0; i < ND4PARAMS; i++) {
|
|
|
|
snprintf(buf,2*FILENAME_MAX, "%s/%s",d4->confdir, d4params[i]);
|
2018-11-27 15:19:40 +01:00
|
|
|
fd = open(buf,O_RDONLY);
|
2018-11-27 16:39:48 +01:00
|
|
|
if (fd > 0) {
|
2018-11-27 15:19:40 +01:00
|
|
|
//FIXME error handling
|
|
|
|
read(fd, d4->conf[i], SZCONFVALUE);
|
|
|
|
} else {
|
|
|
|
d4->errno_copy = errno;
|
2018-11-27 17:27:52 +01:00
|
|
|
INSERT_ERROR("Failed to load %s", d4params[i]);
|
2018-11-27 15:19:40 +01:00
|
|
|
}
|
2018-11-27 14:42:35 +01:00
|
|
|
}
|
|
|
|
}
|
2018-11-27 22:37:44 +01:00
|
|
|
return d4_check_config(d4);
|
2018-11-27 12:47:18 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
void usage(void)
|
|
|
|
{
|
|
|
|
printf("d4 client help\n");
|
|
|
|
}
|
|
|
|
|
|
|
|
d4_t* d4_init(char* confdir)
|
|
|
|
{
|
|
|
|
d4_t* out;
|
2018-11-27 15:00:43 +01:00
|
|
|
int i;
|
2018-11-27 12:47:18 +01:00
|
|
|
out = calloc(1,sizeof(d4_t));
|
|
|
|
if (out) {
|
|
|
|
strncpy(out->confdir, confdir, FILENAME_MAX);
|
|
|
|
}
|
2018-11-27 15:00:43 +01:00
|
|
|
|
|
|
|
for (i=0; i< ND4PARAMS; i++) {
|
|
|
|
bzero(out->conf[i],SZCONFVALUE);
|
|
|
|
}
|
2018-11-27 12:47:18 +01:00
|
|
|
// Do other inititalization stuff here
|
|
|
|
return out;
|
|
|
|
}
|
|
|
|
|
2018-11-27 23:14:23 +01:00
|
|
|
|
|
|
|
//FIXME split in prepare and update. Do not copy uuid each time
|
|
|
|
void d4_update_header(d4_t* d4, ssize_t nread) {
|
|
|
|
bzero(&d4->header,sizeof(d4_update_header));
|
|
|
|
//TODO Check format
|
|
|
|
d4->header.version = atoi(d4->conf[VERSION]);
|
|
|
|
//TODO set type
|
|
|
|
d4->header.timestamp = time(NULL);
|
|
|
|
//FIXME length handling
|
|
|
|
strncpy((char*)&(d4->header.uuid), d4->conf[UUID], SZUUID);
|
|
|
|
//TODO hmac
|
|
|
|
d4->header.size=nread;
|
|
|
|
}
|
|
|
|
|
|
|
|
//Core routine. Transfers data from the source to the destinations
|
|
|
|
void d4_transfert(d4_t* d4)
|
|
|
|
{
|
|
|
|
ssize_t nread;
|
|
|
|
char* buf;
|
|
|
|
|
|
|
|
buf = calloc(1, d4->snaplen);
|
|
|
|
//TODO error handling -> insert error message
|
|
|
|
if (!buf)
|
|
|
|
return;
|
|
|
|
|
|
|
|
while ( 1 ) {
|
|
|
|
//In case of errors see block of 0 bytes
|
|
|
|
bzero(buf, d4->snaplen);
|
|
|
|
nread = read(d4->source.fd, buf, d4->snaplen);
|
|
|
|
if ( nread > 0 ) {
|
|
|
|
d4_update_header(d4, nread);
|
|
|
|
write(d4->destination.fd, &d4->header, sizeof(d4->header));
|
|
|
|
write(d4->destination.fd,buf,nread);
|
|
|
|
} else{
|
|
|
|
//FIXME no data available, sleep, abort, retry
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2018-11-27 12:47:18 +01:00
|
|
|
int main (int argc, char* argv[])
|
|
|
|
{
|
|
|
|
int opt;
|
|
|
|
char* confdir;
|
|
|
|
d4_t* d4;
|
|
|
|
|
|
|
|
confdir=calloc(1,FILENAME_MAX);
|
|
|
|
if (!confdir)
|
|
|
|
return EXIT_FAILURE;
|
|
|
|
|
|
|
|
while ((opt = getopt(argc, argv, "c:h")) != -1) {
|
|
|
|
switch (opt) {
|
|
|
|
case 'h':
|
|
|
|
usage();
|
|
|
|
return EXIT_SUCCESS;
|
|
|
|
case 'c':
|
|
|
|
strncpy(confdir, optarg, FILENAME_MAX);
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
fprintf(stderr,"An invalid command line argument was specified\n");
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if (!confdir[0]){
|
|
|
|
fprintf(stderr,"A config directory must be specified\n");
|
|
|
|
return EXIT_FAILURE;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2018-11-27 14:48:09 +01:00
|
|
|
d4 = d4_init(confdir);
|
2018-11-27 12:47:18 +01:00
|
|
|
free(confdir);
|
2018-11-27 23:14:23 +01:00
|
|
|
if (d4_load_config(d4)) {
|
|
|
|
d4_transfert(d4);
|
|
|
|
}
|
2018-11-27 17:35:31 +01:00
|
|
|
|
2018-11-27 12:47:18 +01:00
|
|
|
return EXIT_SUCCESS;
|
|
|
|
}
|