multipathd crash on shutdown
[multipath-tools/.git] / libmultipath / log_pthread.c
1 /*
2  * Copyright (c) 2005 Christophe Varoqui
3  */
4 #include <stdio.h>
5 #include <stdlib.h>
6 #include <stdarg.h>
7 #include <pthread.h>
8 #include <sys/mman.h>
9
10 #include <memory.h>
11
12 #include "log_pthread.h"
13 #include "log.h"
14
15 void log_safe (int prio, const char * fmt, va_list ap)
16 {
17         pthread_mutex_lock(logq_lock);
18         log_enqueue(prio, fmt, ap);
19         pthread_mutex_unlock(logq_lock);
20
21         pthread_mutex_lock(logev_lock);
22         pthread_cond_signal(logev_cond);
23         pthread_mutex_unlock(logev_lock);
24 }
25
26 static void flush_logqueue (void)
27 {
28         int empty;
29
30         do {
31                 pthread_mutex_lock(logq_lock);
32                 empty = log_dequeue(la->buff);
33                 pthread_mutex_unlock(logq_lock);
34                 if (!empty)
35                         log_syslog(la->buff);
36         } while (empty == 0);
37 }
38
39 static void * log_thread (void * et)
40 {
41         mlockall(MCL_CURRENT | MCL_FUTURE);
42         logdbg(stderr,"enter log_thread\n");
43
44         while (1) {
45                 pthread_mutex_lock(logev_lock);
46                 pthread_cond_wait(logev_cond, logev_lock);
47                 pthread_mutex_unlock(logev_lock);
48
49                 flush_logqueue();
50         }
51 }
52
53 void log_thread_start (void)
54 {
55         pthread_attr_t attr;
56         
57         logdbg(stderr,"enter log_thread_start\n");
58
59         logq_lock = (pthread_mutex_t *) malloc(sizeof(pthread_mutex_t));
60         logev_lock = (pthread_mutex_t *) malloc(sizeof(pthread_mutex_t));
61         logev_cond = (pthread_cond_t *) malloc(sizeof(pthread_cond_t));
62         
63         pthread_mutex_init(logq_lock, NULL);
64         pthread_mutex_init(logev_lock, NULL);
65         pthread_cond_init(logev_cond, NULL);
66         
67         pthread_attr_init(&attr);
68         pthread_attr_setstacksize(&attr, 64 * 1024);
69
70         if (log_init("multipathd", 0)) {
71                 fprintf(stderr,"can't initialize log buffer\n");
72                 exit(1);
73         }
74         pthread_create(&log_thr, &attr, log_thread, NULL);
75
76         return;
77 }
78
79 void log_thread_stop (void)
80 {
81         logdbg(stderr,"enter log_thread_stop\n");
82
83         pthread_mutex_lock(logq_lock);
84         pthread_cancel(log_thr);
85         pthread_mutex_unlock(logq_lock);
86
87         flush_logqueue();
88
89         pthread_mutex_destroy(logq_lock);
90         pthread_mutex_destroy(logev_lock);
91         pthread_cond_destroy(logev_cond);
92
93         free_logarea();
94 }