|
Packit Service |
646995 |
/*
|
|
Packit Service |
646995 |
* Copyright (C) 2002-2003 Ardis Technolgies <roman@ardistech.com>
|
|
Packit Service |
646995 |
*
|
|
Packit Service |
646995 |
* Released under the terms of the GNU GPL v2.0.
|
|
Packit Service |
646995 |
*/
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
#include <ctype.h>
|
|
Packit Service |
646995 |
#include <string.h>
|
|
Packit Service |
646995 |
#include <stdarg.h>
|
|
Packit Service |
646995 |
#include <stdio.h>
|
|
Packit Service |
646995 |
#include <stdlib.h>
|
|
Packit Service |
646995 |
#include <unistd.h>
|
|
Packit Service |
646995 |
#include <syslog.h>
|
|
Packit Service |
646995 |
#include <signal.h>
|
|
Packit Service |
646995 |
#include <errno.h>
|
|
Packit Service |
646995 |
#include <sys/shm.h>
|
|
Packit Service |
646995 |
#include <sys/ipc.h>
|
|
Packit Service |
646995 |
#include <sys/types.h>
|
|
Packit Service |
646995 |
#include <sys/types.h>
|
|
Packit Service |
646995 |
#include <sys/wait.h>
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
#include "iscsi_util.h"
|
|
Packit Service |
646995 |
#include "log.h"
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
#define SEMKEY 0xA7L
|
|
Packit Service |
646995 |
#define LOGDBG 0
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
#if LOGDBG
|
|
Packit Service |
646995 |
#define logdbg(file, fmt, args...) fprintf(file, fmt, ##args)
|
|
Packit Service |
646995 |
#else
|
|
Packit Service |
646995 |
#define logdbg(file, fmt, args...) do {} while (0)
|
|
Packit Service |
646995 |
#endif
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
char *log_name;
|
|
Packit Service |
646995 |
int log_level = 0;
|
|
Packit Service |
646995 |
struct logarea *la = NULL;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
static int log_stop_daemon = 0;
|
|
Packit Service |
646995 |
static void (*log_func)(int prio, void *priv, const char *fmt, va_list ap);
|
|
Packit Service |
646995 |
static void *log_func_priv;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
static void free_logarea (void)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
int shmid;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if (!la)
|
|
Packit Service |
646995 |
return;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if (la->semid != -1)
|
|
Packit Service |
646995 |
semctl(la->semid, 0, IPC_RMID, la->semarg);
|
|
Packit Service |
646995 |
if (la->buff) {
|
|
Packit Service |
646995 |
shmdt(la->buff);
|
|
Packit Service |
646995 |
shmctl(la->shmid_buff, IPC_RMID, NULL);
|
|
Packit Service |
646995 |
la->buff = NULL;
|
|
Packit Service |
646995 |
la->shmid_buff = -1;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
if (la->start) {
|
|
Packit Service |
646995 |
shmdt(la->start);
|
|
Packit Service |
646995 |
shmctl(la->shmid_msg, IPC_RMID, NULL);
|
|
Packit Service |
646995 |
la->start = NULL;
|
|
Packit Service |
646995 |
la->shmid_msg = -1;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
shmid = la->shmid;
|
|
Packit Service |
646995 |
shmdt(la);
|
|
Packit Service |
646995 |
shmctl(shmid, IPC_RMID, NULL);
|
|
Packit Service |
646995 |
la = NULL;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
static int logarea_init (int size)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
int shmid;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
logdbg(stderr,"enter logarea_init\n");
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if ((shmid = shmget(IPC_PRIVATE, sizeof(struct logarea),
|
|
Packit Service |
646995 |
0600 | IPC_CREAT | IPC_EXCL)) == -1) {
|
|
Packit Service |
646995 |
syslog(LOG_ERR, "shmget logarea failed %d", errno);
|
|
Packit Service |
646995 |
return 1;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
la = shmat(shmid, NULL, 0);
|
|
Packit Service |
646995 |
if (!la) {
|
|
Packit Service |
646995 |
syslog(LOG_ERR, "shmat logarea failed %d", errno);
|
|
Packit Service |
646995 |
shmctl(shmid, IPC_RMID, NULL);
|
|
Packit Service |
646995 |
return 1;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
la->shmid = shmid;
|
|
Packit Service |
646995 |
la->start = NULL;
|
|
Packit Service |
646995 |
la->buff = NULL;
|
|
Packit Service |
646995 |
la->semid = -1;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if (size < MAX_MSG_SIZE)
|
|
Packit Service |
646995 |
size = DEFAULT_AREA_SIZE;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if ((shmid = shmget(IPC_PRIVATE, size,
|
|
Packit Service |
646995 |
0600 | IPC_CREAT | IPC_EXCL)) == -1) {
|
|
Packit Service |
646995 |
syslog(LOG_ERR, "shmget msg failed %d", errno);
|
|
Packit Service |
646995 |
free_logarea();
|
|
Packit Service |
646995 |
return 1;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
la->shmid_msg = shmid;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
la->start = shmat(la->shmid_msg, NULL, 0);
|
|
Packit Service |
646995 |
if (!la->start) {
|
|
Packit Service |
646995 |
syslog(LOG_ERR, "shmat msg failed %d", errno);
|
|
Packit Service |
646995 |
free_logarea();
|
|
Packit Service |
646995 |
return 1;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
memset(la->start, 0, size);
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
la->empty = 1;
|
|
Packit Service |
646995 |
la->end = la->start + size;
|
|
Packit Service |
646995 |
la->head = la->start;
|
|
Packit Service |
646995 |
la->tail = la->start;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if ((shmid = shmget(IPC_PRIVATE, MAX_MSG_SIZE + sizeof(struct logmsg),
|
|
Packit Service |
646995 |
0600 | IPC_CREAT | IPC_EXCL)) == -1) {
|
|
Packit Service |
646995 |
syslog(LOG_ERR, "shmget logmsg failed %d", errno);
|
|
Packit Service |
646995 |
free_logarea();
|
|
Packit Service |
646995 |
return 1;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
la->buff = shmat(shmid, NULL, 0);
|
|
Packit Service |
646995 |
if (!la->buff) {
|
|
Packit Service |
646995 |
syslog(LOG_ERR, "shmat logmsgfailed %d", errno);
|
|
Packit Service |
646995 |
free_logarea();
|
|
Packit Service |
646995 |
return 1;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if ((la->semid = semget(SEMKEY, 1, 0600 | IPC_CREAT)) < 0) {
|
|
Packit Service |
646995 |
syslog(LOG_ERR, "semget failed %d", errno);
|
|
Packit Service |
646995 |
free_logarea();
|
|
Packit Service |
646995 |
return 1;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
la->semarg.val=1;
|
|
Packit Service |
646995 |
if (semctl(la->semid, 0, SETVAL, la->semarg) < 0) {
|
|
Packit Service |
646995 |
syslog(LOG_ERR, "semctl failed %d", errno);
|
|
Packit Service |
646995 |
free_logarea();
|
|
Packit Service |
646995 |
return 1;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
la->shmid_buff = shmid;
|
|
Packit Service |
646995 |
la->ops[0].sem_num = 0;
|
|
Packit Service |
646995 |
la->ops[0].sem_flg = 0;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
return 0;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
#if LOGDBG
|
|
Packit Service |
646995 |
static void dump_logarea (void)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
struct logmsg * msg;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
logdbg(stderr, "\n==== area: start addr = %p, end addr = %p ====\n",
|
|
Packit Service |
646995 |
la->start, la->end);
|
|
Packit Service |
646995 |
logdbg(stderr, "|addr |next |prio|msg\n");
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
for (msg = (struct logmsg *)la->head; (void *)msg != la->tail;
|
|
Packit Service |
646995 |
msg = msg->next)
|
|
Packit Service |
646995 |
logdbg(stderr, "|%p |%p |%i |%s\n", (void *)msg, msg->next,
|
|
Packit Service |
646995 |
msg->prio, (char *)&msg->str);
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
logdbg(stderr, "|%p |%p |%i |%s\n", (void *)msg, msg->next,
|
|
Packit Service |
646995 |
msg->prio, (char *)&msg->str);
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
logdbg(stderr, "\n\n");
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
#endif
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
int log_enqueue (int prio, const char * fmt, va_list ap)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
int len, fwd;
|
|
Packit Service |
646995 |
char buff[MAX_MSG_SIZE];
|
|
Packit Service |
646995 |
struct logmsg * msg;
|
|
Packit Service |
646995 |
struct logmsg * lastmsg;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
lastmsg = (struct logmsg *)la->tail;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if (!la->empty) {
|
|
Packit Service |
646995 |
fwd = sizeof(struct logmsg) +
|
|
Packit Service |
646995 |
strlen((char *)&lastmsg->str) * sizeof(char) + 1;
|
|
Packit Service |
646995 |
la->tail += fwd;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
vsnprintf(buff, MAX_MSG_SIZE, fmt, ap);
|
|
Packit Service |
646995 |
len = strlen(buff) * sizeof(char) + 1;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
/* not enough space on tail : rewind */
|
|
Packit Service |
646995 |
if (la->head <= la->tail &&
|
|
Packit Service |
646995 |
(long)(len + sizeof(struct logmsg)) > (la->end - la->tail)) {
|
|
Packit Service |
646995 |
logdbg(stderr, "enqueue: rewind tail to %p\n", la->tail);
|
|
Packit Service |
646995 |
la->tail = la->start;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if (la->empty)
|
|
Packit Service |
646995 |
la->head = lastmsg = la->tail;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
/* not enough space on head : drop msg */
|
|
Packit Service |
646995 |
if (la->head > la->tail &&
|
|
Packit Service |
646995 |
(long)(len + sizeof(struct logmsg)) > (la->head - la->tail)) {
|
|
Packit Service |
646995 |
logdbg(stderr, "enqueue: log area overrun, drop msg\n");
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if (!la->empty)
|
|
Packit Service |
646995 |
la->tail = lastmsg;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
return 1;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
/* ok, we can stage the msg in the area */
|
|
Packit Service |
646995 |
la->empty = 0;
|
|
Packit Service |
646995 |
msg = (struct logmsg *)la->tail;
|
|
Packit Service |
646995 |
msg->prio = prio;
|
|
Packit Service |
646995 |
memcpy((void *)&msg->str, buff, len);
|
|
Packit Service |
646995 |
lastmsg->next = la->tail;
|
|
Packit Service |
646995 |
msg->next = la->head;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
logdbg(stderr, "enqueue: %p, %p, %i, %s\n", (void *)msg, msg->next,
|
|
Packit Service |
646995 |
msg->prio, (char *)&msg->str);
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
#if LOGDBG
|
|
Packit Service |
646995 |
dump_logarea();
|
|
Packit Service |
646995 |
#endif
|
|
Packit Service |
646995 |
return 0;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
int log_dequeue (void * buff)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
struct logmsg * src = (struct logmsg *)la->head;
|
|
Packit Service |
646995 |
struct logmsg * dst = (struct logmsg *)buff;
|
|
Packit Service |
646995 |
struct logmsg * lst = (struct logmsg *)la->tail;
|
|
Packit Service |
646995 |
int len;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if (la->empty)
|
|
Packit Service |
646995 |
return 0;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
len = strlen((char *)&src->str) * sizeof(char) +
|
|
Packit Service |
646995 |
sizeof(struct logmsg) + 1;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
dst->prio = src->prio;
|
|
Packit Service |
646995 |
memcpy(dst, src, len);
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if (la->tail == la->head)
|
|
Packit Service |
646995 |
la->empty = 1; /* purge the last log msg */
|
|
Packit Service |
646995 |
else {
|
|
Packit Service |
646995 |
la->head = src->next;
|
|
Packit Service |
646995 |
lst->next = la->head;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
logdbg(stderr, "dequeue: %p, %p, %i, %s\n",
|
|
Packit Service |
646995 |
(void *)src, src->next, src->prio, (char *)&src->str);
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
memset((void *)src, 0, len);
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
return len;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
/*
|
|
Packit Service |
646995 |
* this one can block under memory pressure
|
|
Packit Service |
646995 |
*/
|
|
Packit Service |
646995 |
static void log_syslog (void * buff)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
struct logmsg * msg = (struct logmsg *)buff;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
syslog(msg->prio, "%s", (char *)&msg->str);
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
void log_do_log_daemon(int prio,
|
|
Packit Service |
646995 |
__attribute__((unused))void *priv,
|
|
Packit Service |
646995 |
const char *fmt,
|
|
Packit Service |
646995 |
va_list ap)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
struct sembuf ops[1];
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
ops[0].sem_num = la->ops[0].sem_num;
|
|
Packit Service |
646995 |
ops[0].sem_flg = la->ops[0].sem_flg;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
ops[0].sem_op = -1;
|
|
Packit Service |
646995 |
if (semop(la->semid, ops, 1) < 0) {
|
|
Packit Service |
646995 |
syslog(LOG_ERR, "semop down failed %d", errno);
|
|
Packit Service |
646995 |
return;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
log_enqueue(prio, fmt, ap);
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
ops[0].sem_op = 1;
|
|
Packit Service |
646995 |
if (semop(la->semid, ops, 1) < 0)
|
|
Packit Service |
646995 |
syslog(LOG_ERR, "semop up failed");
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
void log_do_log_std(int prio,
|
|
Packit Service |
646995 |
__attribute__((unused))void *priv,
|
|
Packit Service |
646995 |
const char *fmt,
|
|
Packit Service |
646995 |
va_list ap)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
if (prio == LOG_INFO) {
|
|
Packit Service |
646995 |
vfprintf(stdout, fmt, ap);
|
|
Packit Service |
646995 |
fprintf(stdout, "\n");
|
|
Packit Service |
646995 |
} else {
|
|
Packit Service |
646995 |
fprintf(stderr, "%s: ", log_name);
|
|
Packit Service |
646995 |
vfprintf(stderr, fmt, ap);
|
|
Packit Service |
646995 |
fprintf(stderr, "\n");
|
|
Packit Service |
646995 |
fflush(stderr);
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
void log_warning(const char *fmt, ...)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
va_list ap;
|
|
Packit Service |
646995 |
va_start(ap, fmt);
|
|
Packit Service |
646995 |
log_func(LOG_WARNING, log_func_priv, fmt, ap);
|
|
Packit Service |
646995 |
va_end(ap);
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
void log_error(const char *fmt, ...)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
va_list ap;
|
|
Packit Service |
646995 |
va_start(ap, fmt);
|
|
Packit Service |
646995 |
log_func(LOG_ERR, log_func_priv, fmt, ap);
|
|
Packit Service |
646995 |
va_end(ap);
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
void log_debug(int level, const char *fmt, ...)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
if (log_level > level) {
|
|
Packit Service |
646995 |
va_list ap;
|
|
Packit Service |
646995 |
va_start(ap, fmt);
|
|
Packit Service |
646995 |
log_func(LOG_DEBUG, log_func_priv, fmt, ap);
|
|
Packit Service |
646995 |
va_end(ap);
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
void log_info(const char *fmt, ...)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
va_list ap;
|
|
Packit Service |
646995 |
va_start(ap, fmt);
|
|
Packit Service |
646995 |
log_func(LOG_INFO, log_func_priv, fmt, ap);
|
|
Packit Service |
646995 |
va_end(ap);
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
#if 0 /* Unused */
|
|
Packit Service |
646995 |
static void __dump_line(int level, unsigned char *buf, int *cp)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
char line[16*3+5], *lp = line;
|
|
Packit Service |
646995 |
int i, cnt;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
cnt = *cp;
|
|
Packit Service |
646995 |
if (!cnt)
|
|
Packit Service |
646995 |
return;
|
|
Packit Service |
646995 |
for (i = 0; i < 16; i++) {
|
|
Packit Service |
646995 |
if (i < cnt)
|
|
Packit Service |
646995 |
lp += sprintf(lp, " %02x", buf[i]);
|
|
Packit Service |
646995 |
else
|
|
Packit Service |
646995 |
lp += sprintf(lp, " ");
|
|
Packit Service |
646995 |
if ((i % 4) == 3)
|
|
Packit Service |
646995 |
lp += sprintf(lp, " |");
|
|
Packit Service |
646995 |
if (i >= cnt || !isprint(buf[i]))
|
|
Packit Service |
646995 |
buf[i] = ' ';
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
log_debug(level, "%s %.16s |", line, buf);
|
|
Packit Service |
646995 |
*cp = 0;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
static void __dump_char(int level, unsigned char *buf, int *cp, int ch)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
int cnt = (*cp)++;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
buf[cnt] = ch;
|
|
Packit Service |
646995 |
if (cnt == 15)
|
|
Packit Service |
646995 |
__dump_line(level, buf, cp);
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
#define dump_line() __dump_line(level, char_buf, &char_cnt)
|
|
Packit Service |
646995 |
#define dump_char(ch) __dump_char(level, char_buf, &char_cnt, ch)
|
|
Packit Service |
646995 |
#endif /* Unused */
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
static void log_flush(void)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
int msglen;
|
|
Packit Service |
646995 |
struct sembuf ops[1];
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
ops[0].sem_num = la->ops[0].sem_num;
|
|
Packit Service |
646995 |
ops[0].sem_flg = la->ops[0].sem_flg;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
while (!la->empty) {
|
|
Packit Service |
646995 |
ops[0].sem_op = -1;
|
|
Packit Service |
646995 |
if (semop(la->semid, ops, 1) < 0) {
|
|
Packit Service |
646995 |
syslog(LOG_ERR, "semop down failed %d", errno);
|
|
Packit Service |
646995 |
exit(1);
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
msglen = log_dequeue(la->buff);
|
|
Packit Service |
646995 |
ops[0].sem_op = 1;
|
|
Packit Service |
646995 |
if (semop(la->semid, ops, 1) < 0) {
|
|
Packit Service |
646995 |
syslog(LOG_ERR, "semop up failed");
|
|
Packit Service |
646995 |
exit(1);
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
if (msglen)
|
|
Packit Service |
646995 |
log_syslog(la->buff);
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
static void catch_signal(int signo)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
switch (signo) {
|
|
Packit Service |
646995 |
case SIGSEGV:
|
|
Packit Service |
646995 |
log_flush();
|
|
Packit Service |
646995 |
break;
|
|
Packit Service |
646995 |
case SIGTERM:
|
|
Packit Service |
646995 |
log_stop_daemon = 1;
|
|
Packit Service |
646995 |
break;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
log_debug(1, "pid %d caught signal -%d", getpid(), signo);
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
static void __log_close(void)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
if (log_func == log_do_log_daemon) {
|
|
Packit Service |
646995 |
log_flush();
|
|
Packit Service |
646995 |
closelog();
|
|
Packit Service |
646995 |
free_logarea();
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
int log_init(char *program_name, int size,
|
|
Packit Service |
646995 |
void (*func)(int prio, void *priv, const char *fmt, va_list ap),
|
|
Packit Service |
646995 |
void *priv)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
logdbg(stderr,"enter log_init\n");
|
|
Packit Service |
646995 |
log_name = program_name;
|
|
Packit Service |
646995 |
log_func = func;
|
|
Packit Service |
646995 |
log_func_priv = priv;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if (log_func == log_do_log_daemon) {
|
|
Packit Service |
646995 |
struct sigaction sa_old;
|
|
Packit Service |
646995 |
struct sigaction sa_new;
|
|
Packit Service |
646995 |
pid_t pid;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
openlog(log_name, 0, LOG_DAEMON);
|
|
Packit Service |
646995 |
setlogmask (LOG_UPTO (LOG_DEBUG));
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if (logarea_init(size)) {
|
|
Packit Service |
646995 |
syslog(LOG_ERR, "logarea init failed");
|
|
Packit Service |
646995 |
return -1;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
pid = fork();
|
|
Packit Service |
646995 |
if (pid < 0) {
|
|
Packit Service |
646995 |
syslog(LOG_ERR, "starting logger failed");
|
|
Packit Service |
646995 |
exit(1);
|
|
Packit Service |
646995 |
} else if (pid) {
|
|
Packit Service |
646995 |
syslog(LOG_WARNING,
|
|
Packit Service |
646995 |
"iSCSI logger with pid=%d started!", pid);
|
|
Packit Service |
646995 |
return pid;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
daemon_init();
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
/* flush on daemon's crash */
|
|
Packit Service |
646995 |
sa_new.sa_handler = (void*)catch_signal;
|
|
Packit Service |
646995 |
sigemptyset(&sa_new.sa_mask);
|
|
Packit Service |
646995 |
sa_new.sa_flags = 0;
|
|
Packit Service |
646995 |
sigaction(SIGSEGV, &sa_new, &sa_old );
|
|
Packit Service |
646995 |
sigaction(SIGTERM, &sa_new, &sa_old );
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
while(1) {
|
|
Packit Service |
646995 |
log_flush();
|
|
Packit Service |
646995 |
sleep(1);
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if (log_stop_daemon)
|
|
Packit Service |
646995 |
break;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
__log_close();
|
|
Packit Service |
646995 |
exit(0);
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
return 0;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
void log_close(pid_t pid)
|
|
Packit Service |
646995 |
{
|
|
Packit Service |
646995 |
int status;
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if (log_func != log_do_log_daemon || pid < 0) {
|
|
Packit Service |
646995 |
__log_close();
|
|
Packit Service |
646995 |
return;
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
|
|
Packit Service |
646995 |
if (pid > 0) {
|
|
Packit Service |
646995 |
kill(pid, SIGTERM);
|
|
Packit Service |
646995 |
waitpid(pid, &status, 0);
|
|
Packit Service |
646995 |
}
|
|
Packit Service |
646995 |
}
|