#include <stdio.h>
|
#include <errno.h>
|
#include <string.h>
|
#include <unistd.h>
|
#include <sys/types.h>
|
#include <sys/socket.h>
|
#include <arpa/inet.h>
|
#include <stdlib.h>
|
#include <getopt.h>
|
#include <time.h>
|
|
#include "logger.h"
|
#include "ds18b20.h"
|
#include "packet.h"
|
#include "socket.h"
|
#include "sqlite_blob.h"
|
#include "util_proc.h"
|
#include "util_time.h"
|
|
|
void print_usage(char *progname)
|
{
|
printf("%s usage: \n", progname);
|
printf("-i(--ipaddr) : sepcify server IP address\n");
|
printf("-p(--port) : sepcify server port.\n");
|
printf("-I(--interval): sepcify report interval time\n");
|
printf("-s(--sn) : sepcify device serial number\n");
|
printf("-d(--debug) : run as debug mode\n");
|
printf("-h(--Help) : print this help information.\n");
|
|
return ;
|
}
|
|
static int check_sample_time(time_t *last_time, int interval);
|
|
int main(int argc, char **argv)
|
{
|
int rv = -1;
|
int port;
|
char *serverip;
|
int interval = 30; /* default report termperature every 30 seconds */
|
int sn = 1; /* default serial number for device ID */
|
int debug = 0; /* running in debug mode or not */
|
int loglevel = LOG_LEVEL_INFO;
|
char *logfile="client.log";
|
|
socket_ctx_t sock;
|
time_t last_time = 0;
|
int sample_flag = 0;
|
|
char pack_buf[1024];
|
int pack_bytes;
|
pack_info_t pack_info;
|
pack_proc_t pack_proc = packet_string_pack; /* use string packet */
|
|
struct option opts[] = {
|
{"ipaddr", required_argument, NULL, 'i'},
|
{"port", required_argument, NULL, 'p'},
|
{"interval", no_argument, NULL, 'I'},
|
{"debug", no_argument, NULL, 'd'},
|
{"sn", required_argument, NULL, 's'},
|
{"help", no_argument, NULL, 'h'},
|
{NULL, 0, NULL, 0}
|
};
|
|
while( (rv=getopt_long(argc, argv, "i:p:dI:s:h", opts, NULL)) != -1 )
|
{
|
switch(rv)
|
{
|
case 'i':
|
serverip=optarg;
|
break;
|
|
case 'p':
|
port=atoi(optarg);
|
break;
|
|
case 'd':
|
debug=1;
|
logfile="stdout";
|
loglevel=LOG_LEVEL_DEBUG;
|
break;
|
|
case 'I':
|
interval=atoi(optarg);
|
break;
|
|
case 's':
|
sn=atoi(optarg);
|
break;
|
|
case 'h':
|
print_usage(argv[0]);
|
return 0;
|
}
|
|
}
|
|
if( !serverip || !port )
|
{
|
print_usage(argv[0]);
|
return 0;
|
}
|
|
/* set logger to $logfile with level info */
|
if( logger_init(logfile, loglevel) < 0 )
|
{
|
fprintf(stderr, "Initial logger file '%s' failure: %s\n", logfile, strerror(errno));
|
return 1;
|
}
|
|
if( !debug )
|
{
|
log_info("set program running on background now.\n");
|
daemon(1, 1); /* don't change work path, don't close opened file descriptor */
|
}
|
|
install_default_signal();
|
|
log_info("program start running.\n");
|
|
if( database_init("client.db") < 0 )
|
{
|
return 2;
|
}
|
|
socket_init(&sock, serverip, port);
|
|
while( !g_signal.stop )
|
{
|
/* +----------------------------------+
|
* | check and sample temperature |
|
* +----------------------------------+*/
|
|
sample_flag = 0; /* clear sample flag */
|
|
if( check_sample_time(&last_time, interval) )
|
{
|
log_debug("start DS18B20 sample termperature\n");
|
|
if( (rv=ds18b20_get_temperature(&pack_info.temper)) < 0 )
|
{
|
log_error("DS18B20 sample temperature failure, rv=%d\n", rv);
|
continue;
|
}
|
log_info("DS18B20 sample termperature %d.%d oC\n",
|
temper_integer(pack_info.temper), temper_fract(pack_info.temper));
|
|
get_devid(pack_info.devid, DEVID_LEN, sn);
|
get_time(pack_info.strtime, TIME_LEN);
|
|
pack_bytes = pack_proc(&pack_info, pack_buf, sizeof(pack_buf));
|
sample_flag = 1; /* set sample flag */
|
}
|
|
/* +---------------------------------+
|
* | check and do socket connect |
|
* +---------------------------------+*/
|
|
/* start connect to server if not connected */
|
if( sock.fd < 0 )
|
{
|
socket_connect(&sock);
|
}
|
|
/* check socket connected or not */
|
if( sock_check_connect(sock.fd) < 0 )
|
{
|
if( sock.fd > 0 )
|
{
|
log_error("socket got disconnected, terminate it and reconnect now.\n");
|
socket_term(&sock); /* close the soket */
|
}
|
}
|
|
/* +-------------------------------+
|
* | socket disconnect |
|
* +-------------------------------+*/
|
if( sock.fd < 0 )
|
{
|
if( sample_flag )
|
{
|
blobdb_push_packet(pack_buf, pack_bytes);
|
}
|
|
continue;
|
}
|
|
/* +-------------------------------+
|
* | socket connected |
|
* +-------------------------------+*/
|
|
/* socket send sample packet */
|
if( sample_flag )
|
{
|
log_debug("socket send sample packet bytes[%d]: %s\n", pack_bytes, pack_buf);
|
if( socket_send(&sock, pack_buf, pack_bytes) < 0 )
|
{
|
log_warn("socket send sample packet failure, save it in database now.\n");
|
blobdb_push_packet(pack_buf, pack_bytes);
|
socket_term(&sock); /* close the soket */
|
}
|
}
|
|
/* socket send packet in database */
|
if( !blobdb_pop_packet(pack_buf, sizeof(pack_buf), &pack_bytes) )
|
{
|
log_debug("socket send database packet bytes[%d]: %s\n", pack_bytes, pack_buf);
|
if( socket_send(&sock, pack_buf, pack_bytes) < 0 )
|
{
|
log_error("socket send database packet failure");
|
socket_term(&sock); /* close the soket */
|
}
|
else
|
{
|
log_warn("socket send database packet okay, remove it from database now.\n");
|
blobdb_del_packet();
|
}
|
}
|
|
msleep(100);
|
}
|
|
socket_term(&sock);
|
database_term();
|
|
return 0;
|
}
|
|
int check_sample_time(time_t *last_time, int interval)
|
{
|
int need = 0; /* no need sample now */
|
time_t now;
|
|
time(&now);
|
|
if( now >= *last_time+interval )
|
{
|
need = 1; /* need sample now */
|
*last_time = now;
|
}
|
|
return need;
|
}
|