Skip to content

Commit 6e4fad8

Browse files
authored
Merge pull request syslog-ng#4998 from HofiOne/syslog-ng-3241-sometimes-crash-in-log_pipe_queue-4989
wilcard-file-reader: Fix detection of file delete/move when using ivykis poll events
2 parents 1663eb7 + d20281f commit 6e4fad8

34 files changed

+603
-242
lines changed

cmake/print_config_summary.cmake

+5-4
Original file line numberDiff line numberDiff line change
@@ -67,11 +67,12 @@ endfunction()
6767

6868
function(_print_libraries _variableNames)
6969
foreach(_variableName ${_variableNames})
70-
string(REGEX MATCH ".*(_LIBRARY|_LIBRARIES)$" _match_lib "${_variableName}")
71-
string(REGEX MATCH ".*(INCLUDE_DIR|INCLUDEDIR|INCLUDE_DIRS)$" _match_incl "${_variableName}")
70+
string(REGEX MATCH ".*(_FOUND)$" _match_found "${_variableName}")
71+
string(REGEX MATCH ".*(_LIBRARY|_LIBRARIES|_LIBRARY_OPTS)$" _match_lib "${_variableName}")
72+
string(REGEX MATCH ".*(INCLUDE_DIR|INCLUDEDIR|INCLUDE_DIRS|INCLUDE_OPTS)$" _match_incl "${_variableName}")
7273
string(REGEX MATCH "^(CMAKE_|_).*" _cmakeInternal "${_variableName}")
7374

74-
if((_match_lib OR _match_incl) AND NOT _cmakeInternal)
75+
if ((_match_lib OR _match_incl OR _match_found) AND NOT _cmakeInternal)
7576
_print_summary_line("${_variableName}=" "${${_variableName}}" 0)
7677
endif()
7778
endforeach()
@@ -146,7 +147,7 @@ function(print_config_summary)
146147
_print_separator()
147148
endif()
148149

149-
list(APPEND _importantVariableNames "IVYKIS_INTERNAL" "BUILD_TESTING" "CMAKE_C_COMPILER" "CMAKE_CXX_COMPILER" "CMAKE_OBJC_COMPILER")
150+
list(APPEND _importantVariableNames "IVYKIS_INTERNAL" "BUILD_TESTING" "CMAKE_C_COMPILER" "CMAKE_CXX_COMPILER" "CMAKE_OBJC_COMPILER" "CMAKE_BUILD_TYPE")
150151
if (APPLE)
151152
list(APPEND _importantVariableNames "FORCE_CLASSIC_LINKING")
152153
endif()

lib/logpipe.h

+8-3
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,10 @@
4242
#define NC_REOPEN_REQUIRED 6
4343
#define NC_FILE_DELETED 7
4444

45+
/* notify result mask values */
46+
#define NR_OK 0x0000
47+
#define NR_STOP_ON_EOF 0x0001
48+
4549
/* indicates that the LogPipe was initialized */
4650
#define PIF_INITIALIZED 0x0001
4751
/* indicates that this LogPipe got cloned into the tree already */
@@ -332,7 +336,7 @@ struct _LogPipe
332336
LogPipe *(*clone)(LogPipe *self);
333337

334338
void (*free_fn)(LogPipe *self);
335-
void (*notify)(LogPipe *self, gint notify_code, gpointer user_data);
339+
gint (*notify)(LogPipe *self, gint notify_code, gpointer user_data);
336340
GList *info;
337341
};
338342

@@ -498,11 +502,12 @@ log_pipe_clone(LogPipe *self)
498502
return self->clone(self);
499503
}
500504

501-
static inline void
505+
static inline gint
502506
log_pipe_notify(LogPipe *s, gint notify_code, gpointer user_data)
503507
{
504508
if (s->notify)
505-
s->notify(s, notify_code, user_data);
509+
return s->notify(s, notify_code, user_data);
510+
return NR_OK;
506511
}
507512

508513
static inline void

lib/logreader.c

+33-1
Original file line numberDiff line numberDiff line change
@@ -283,7 +283,7 @@ log_reader_open(LogReader *self, LogProtoServer *proto, PollEvents *poll_events)
283283
log_reader_apply_proto_and_poll_events(self, proto, poll_events);
284284
}
285285

286-
static gboolean
286+
gboolean
287287
log_reader_is_opened(LogReader *self)
288288
{
289289
return self->proto && self->poll_events;
@@ -349,6 +349,32 @@ log_reader_update_watches(LogReader *self)
349349
}
350350
}
351351

352+
static inline gboolean
353+
log_reader_work_in_progress(LogReader *self)
354+
{
355+
main_loop_assert_main_thread();
356+
357+
return self->io_job.working;
358+
}
359+
360+
static inline void
361+
log_reader_set_work_in_progress(LogReader *self, gboolean state)
362+
{
363+
if ((self->options->flags & LR_THREADED) == 0)
364+
{
365+
main_loop_assert_main_thread();
366+
self->io_job.working = state;
367+
}
368+
}
369+
370+
/* NOTE: See file-reader, file_reader_notify_method() why this is needed */
371+
inline void
372+
log_reader_trigger_one_check(LogReader *self)
373+
{
374+
if (FALSE == log_reader_work_in_progress(self))
375+
log_reader_force_check_in_next_poll(self);
376+
}
377+
352378
/*****************************************************************************
353379
* Glue into MainLoopIOWorker
354380
*****************************************************************************/
@@ -358,6 +384,8 @@ log_reader_work_perform(void *s, gpointer arg)
358384
{
359385
LogReader *self = (LogReader *) s;
360386

387+
log_reader_set_work_in_progress(self, TRUE);
388+
361389
self->notify_code = log_reader_fetch_log(self);
362390
}
363391

@@ -366,6 +394,8 @@ log_reader_work_finished(void *s, gpointer arg)
366394
{
367395
LogReader *self = (LogReader *) s;
368396

397+
log_reader_set_work_in_progress(self, FALSE);
398+
369399
if (self->pending_close)
370400
{
371401
/* pending proto is only set in the main thread, so no need to
@@ -389,6 +419,7 @@ log_reader_work_finished(void *s, gpointer arg)
389419
self->notify_code = 0;
390420
log_pipe_notify(self->control, notify_code, self);
391421
}
422+
392423
if (self->super.super.flags & PIF_INITIALIZED)
393424
{
394425
/* reenable polling the source assuming that we're still in
@@ -567,6 +598,7 @@ log_reader_io_handle_in(gpointer s)
567598
LogReader *self = (LogReader *) s;
568599

569600
log_reader_disable_watches(self);
601+
570602
if ((self->options->flags & LR_THREADED))
571603
{
572604
main_loop_io_worker_job_submit(&self->io_job, NULL);

lib/logreader.h

+2-1
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,6 @@ struct _LogReader
7979
guint watches_running:1, suspended:1, realloc_window_after_fetch:1;
8080
gint notify_code;
8181

82-
8382
/* proto & poll_events pending to be applied. As long as the previous
8483
* processing is being done, we can't replace these in self->proto and
8584
* self->poll_events, they get applied to the production ones as soon as
@@ -99,6 +98,8 @@ void log_reader_set_peer_addr(LogReader *s, GSockAddr *peer_addr);
9998
void log_reader_set_local_addr(LogReader *s, GSockAddr *local_addr);
10099
void log_reader_set_immediate_check(LogReader *s);
101100
void log_reader_disable_bookmark_saving(LogReader *s);
101+
void log_reader_trigger_one_check(LogReader *s);
102+
gboolean log_reader_is_opened(LogReader *s);
102103
void log_reader_open(LogReader *s, LogProtoServer *proto, PollEvents *poll_events);
103104
void log_reader_close_proto(LogReader *s);
104105
LogReader *log_reader_new(GlobalConfig *cfg);

lib/poll-events.c

+7
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,13 @@ poll_events_set_callback(PollEvents *self, PollCallback callback, gpointer user_
3636
self->callback_data = user_data;
3737
}
3838

39+
void
40+
poll_events_set_checker(PollEvents *self, PollChecker check_watches, gpointer user_data)
41+
{
42+
self->check_watches = check_watches;
43+
self->checker_data = user_data;
44+
}
45+
3946
void
4047
poll_events_init(PollEvents *self)
4148
{

lib/poll-events.h

+28
Original file line numberDiff line numberDiff line change
@@ -28,19 +28,38 @@
2828

2929
typedef struct _PollEvents PollEvents;
3030
typedef void (*PollCallback)(gpointer user_data);
31+
typedef gboolean (*PollChecker)(PollEvents *self, gpointer user_data);
3132

3233
struct _PollEvents
3334
{
35+
gboolean system_polled;
3436
PollCallback callback;
3537
gpointer callback_data;
38+
gpointer checker_data;
3639

3740
void (*start_watches)(PollEvents *self);
3841
void (*stop_watches)(PollEvents *self);
42+
PollChecker check_watches;
3943
void (*update_watches)(PollEvents *self, GIOCondition cond);
4044
void (*suspend_watches)(PollEvents *self);
45+
gint (*get_fd)(PollEvents *self);
4146
void (*free_fn)(PollEvents *self);
4247
};
4348

49+
static inline gint
50+
poll_events_get_fd(PollEvents *self)
51+
{
52+
if (self->get_fd)
53+
return self->get_fd(self);
54+
return -1;
55+
}
56+
57+
static inline gboolean
58+
poll_events_system_polled(PollEvents *self)
59+
{
60+
return self->system_polled;
61+
}
62+
4463
static inline void
4564
poll_events_start_watches(PollEvents *self)
4665
{
@@ -54,6 +73,14 @@ poll_events_stop_watches(PollEvents *self)
5473
self->stop_watches(self);
5574
}
5675

76+
static inline gboolean
77+
poll_events_check_watches(PollEvents *self)
78+
{
79+
if (self->check_watches)
80+
return self->check_watches(self, self->checker_data);
81+
return TRUE;
82+
}
83+
5784
static inline void
5885
poll_events_update_watches(PollEvents *self, GIOCondition cond)
5986
{
@@ -70,6 +97,7 @@ poll_events_suspend_watches(PollEvents *self)
7097

7198
void poll_events_invoke_callback(PollEvents *self);
7299
void poll_events_set_callback(PollEvents *self, PollCallback callback, gpointer user_data);
100+
void poll_events_set_checker(PollEvents *self, PollChecker check_watches, gpointer user_data);
73101
void poll_events_init(PollEvents *self);
74102
void poll_events_free(PollEvents *self);
75103

lib/poll-fd-events.c

+18-6
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,13 @@ typedef struct _PollFdEvents
3333

3434
#define IV_FD_CALLBACK(x) ((void (*)(void *)) (x))
3535

36+
static inline gint
37+
_get_fd(PollEvents *s)
38+
{
39+
PollFdEvents *self = (PollFdEvents *) s;
40+
return self->fd_watch.fd;
41+
}
42+
3643
static void
3744
poll_fd_events_start_watches(PollEvents *s)
3845
{
@@ -68,14 +75,17 @@ poll_fd_events_update_watches(PollEvents *s, GIOCondition cond)
6875

6976
poll_events_suspend_watches(s);
7077

71-
if (cond & G_IO_IN)
72-
iv_fd_set_handler_in(&self->fd_watch, IV_FD_CALLBACK(poll_events_invoke_callback));
78+
if (poll_events_check_watches(s))
79+
{
80+
if (cond & G_IO_IN)
81+
iv_fd_set_handler_in(&self->fd_watch, IV_FD_CALLBACK(poll_events_invoke_callback));
7382

74-
if (cond & G_IO_OUT)
75-
iv_fd_set_handler_out(&self->fd_watch, IV_FD_CALLBACK(poll_events_invoke_callback));
83+
if (cond & G_IO_OUT)
84+
iv_fd_set_handler_out(&self->fd_watch, IV_FD_CALLBACK(poll_events_invoke_callback));
7685

77-
if (cond & (G_IO_IN + G_IO_OUT))
78-
iv_fd_set_handler_err(&self->fd_watch, IV_FD_CALLBACK(poll_events_invoke_callback));
86+
if (cond & (G_IO_IN + G_IO_OUT))
87+
iv_fd_set_handler_err(&self->fd_watch, IV_FD_CALLBACK(poll_events_invoke_callback));
88+
}
7989
}
8090

8191
PollEvents *
@@ -89,6 +99,8 @@ poll_fd_events_new(gint fd)
8999
self->super.stop_watches = poll_fd_events_stop_watches;
90100
self->super.update_watches = poll_fd_events_update_watches;
91101
self->super.suspend_watches = poll_fd_events_suspend_watches;
102+
self->super.system_polled = TRUE;
103+
self->super.get_fd = _get_fd;
92104

93105
IV_FD_INIT(&self->fd_watch);
94106
self->fd_watch.fd = fd;

modules/affile/affile-dest.c

+2-1
Original file line numberDiff line numberDiff line change
@@ -353,7 +353,7 @@ affile_dw_free(LogPipe *s)
353353
log_pipe_free_method(s);
354354
}
355355

356-
static void
356+
static gint
357357
affile_dw_notify(LogPipe *s, gint notify_code, gpointer user_data)
358358
{
359359
AFFileDestWriter *self = (AFFileDestWriter *)s;
@@ -368,6 +368,7 @@ affile_dw_notify(LogPipe *s, gint notify_code, gpointer user_data)
368368
default:
369369
break;
370370
}
371+
return NR_OK;
371372
}
372373

373374
static AFFileDestWriter *

modules/affile/affile-grammar.ym

+8-6
Original file line numberDiff line numberDiff line change
@@ -89,6 +89,7 @@ affile_grammar_set_wildcard_file_source_driver(WildcardSourceDriver *sd)
8989

9090
%token KW_FSYNC
9191
%token KW_FOLLOW_FREQ
92+
%token KW_MONITOR_FREQ
9293
%token KW_OVERWRITE_IF_OLDER
9394
%token KW_SYMLINK_AS
9495
%token KW_MULTI_LINE_TIMEOUT
@@ -189,15 +190,16 @@ source_affile_option
189190
;
190191

191192
source_wildcard_option
192-
: KW_BASE_DIR '(' string ')' { wildcard_sd_set_base_dir(last_driver, $3); free($3); }
193-
| KW_FILENAME_PATTERN '(' string ')'
194-
{
195-
wildcard_sd_set_filename_pattern(last_driver, $3);
196-
free($3);
197-
}
193+
: KW_BASE_DIR '(' string ')' { wildcard_sd_set_base_dir(last_driver, $3); free($3); }
194+
| KW_FILENAME_PATTERN '(' string ')'
195+
{
196+
wildcard_sd_set_filename_pattern(last_driver, $3);
197+
free($3);
198+
}
198199
| KW_RECURSIVE '(' yesno ')' { wildcard_sd_set_recursive(last_driver, $3); }
199200
| KW_MAX_FILES '(' positive_integer ')' { wildcard_sd_set_max_files(last_driver, $3); }
200201
| KW_MONITOR_METHOD '(' string ')' { CHECK_ERROR(wildcard_sd_set_monitor_method(last_driver, $3), @3, "Invalid monitor-method"); free($3); }
202+
| KW_MONITOR_FREQ '(' nonnegative_float ')' { wildcard_sd_set_monitor_freq(last_driver, (gint) ($3 * 1000)); }
201203
| source_affile_option
202204
;
203205

modules/affile/affile-parser.c

+1
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,7 @@ static CfgLexerKeyword affile_keywords[] =
5050
{ "overwrite_if_older", KW_OVERWRITE_IF_OLDER },
5151
{ "symlink_as", KW_SYMLINK_AS },
5252
{ "follow_freq", KW_FOLLOW_FREQ },
53+
{ "monitor_freq", KW_MONITOR_FREQ },
5354
{ "multi_line_timeout", KW_MULTI_LINE_TIMEOUT },
5455
{ "time_reap", KW_TIME_REAP },
5556
{ NULL }

0 commit comments

Comments
 (0)