comparison src/core/ngx_syslog.c @ 9225:1c9264603adc

Syslog: introduced ngx_syslog_send() error logging moderation. Errors when logging to syslog are now logged at most once per second. This ensures that persistent errors won't flood other logs, and spontaneous errors, such as ENOBUFS as observed on BSD systems when syslogd cannot cope with load, or EAGAIN as seen in similar situation on Linux, won't further overload logging subsystem, leading to more errors. Further, errors now can only trigger reconnects at most once per second. This ensures that persistent errors, which cannot be fixed with reconnects, don't trigger too much unneeded work. Additionally, in case of connection errors, such as when syslogd is not running, connection attempts are only made once per second.
author Maxim Dounin <mdounin@mdounin.ru>
date Fri, 01 Mar 2024 05:42:12 +0300
parents c7c8354f99fa
children c769217b4a5c
comparison
equal deleted inserted replaced
9224:c7c8354f99fa 9225:1c9264603adc
301 if (ngx_syslog_init_peer(peer) != NGX_OK) { 301 if (ngx_syslog_init_peer(peer) != NGX_OK) {
302 return NGX_ERROR; 302 return NGX_ERROR;
303 } 303 }
304 } 304 }
305 305
306 if (ngx_time() == peer->error_log_time) {
307 peer->conn.log_error = NGX_ERROR_DEBUG;
308 }
309
306 if (ngx_send) { 310 if (ngx_send) {
307 n = ngx_send(&peer->conn, buf, len); 311 n = ngx_send(&peer->conn, buf, len);
308 312
309 } else { 313 } else {
310 /* event module has not yet set ngx_io */ 314 /* event module has not yet set ngx_io */
311 n = ngx_os_io.send(&peer->conn, buf, len); 315 n = ngx_os_io.send(&peer->conn, buf, len);
312 } 316 }
313 317
314 if (n == NGX_ERROR) { 318 if (n == NGX_ERROR
315 319 && peer->conn.log_error != NGX_ERROR_DEBUG)
320 {
316 if (ngx_close_socket(peer->conn.fd) == -1) { 321 if (ngx_close_socket(peer->conn.fd) == -1) {
317 ngx_log_error(NGX_LOG_ALERT, &peer->log, ngx_socket_errno, 322 ngx_log_error(NGX_LOG_ALERT, &peer->log, ngx_socket_errno,
318 ngx_close_socket_n " failed"); 323 ngx_close_socket_n " failed");
319 } 324 }
320 325
321 peer->conn.fd = (ngx_socket_t) -1; 326 peer->conn.fd = (ngx_socket_t) -1;
322 327 peer->error_log_time = ngx_time();
323 } else if ((size_t) n != len) { 328
329 } else if ((size_t) n != len
330 && peer->conn.log_error != NGX_ERROR_DEBUG)
331 {
324 ngx_log_error(NGX_LOG_CRIT, &peer->log, 0, 332 ngx_log_error(NGX_LOG_CRIT, &peer->log, 0,
325 "send() incomplete"); 333 "send() incomplete");
326 } 334 peer->error_log_time = ngx_time();
335 }
336
337 peer->conn.log_error = NGX_ERROR_ERR;
327 338
328 return n; 339 return n;
329 } 340 }
330 341
331 342
332 static ngx_int_t 343 static ngx_int_t
333 ngx_syslog_init_peer(ngx_syslog_peer_t *peer) 344 ngx_syslog_init_peer(ngx_syslog_peer_t *peer)
334 { 345 {
335 ngx_socket_t fd; 346 ngx_socket_t fd;
347
348 if (ngx_time() == peer->connect_error_time) {
349 return NGX_ERROR;
350 }
336 351
337 fd = ngx_socket(peer->server.sockaddr->sa_family, SOCK_DGRAM, 0); 352 fd = ngx_socket(peer->server.sockaddr->sa_family, SOCK_DGRAM, 0);
338 if (fd == (ngx_socket_t) -1) { 353 if (fd == (ngx_socket_t) -1) {
339 ngx_log_error(NGX_LOG_ALERT, &peer->log, ngx_socket_errno, 354 ngx_log_error(NGX_LOG_ALERT, &peer->log, ngx_socket_errno,
340 ngx_socket_n " failed"); 355 ngx_socket_n " failed");
356 peer->connect_error_time = ngx_time();
341 return NGX_ERROR; 357 return NGX_ERROR;
342 } 358 }
343 359
344 if (ngx_nonblocking(fd) == -1) { 360 if (ngx_nonblocking(fd) == -1) {
345 ngx_log_error(NGX_LOG_ALERT, &peer->log, ngx_socket_errno, 361 ngx_log_error(NGX_LOG_ALERT, &peer->log, ngx_socket_errno,
353 goto failed; 369 goto failed;
354 } 370 }
355 371
356 peer->conn.fd = fd; 372 peer->conn.fd = fd;
357 peer->conn.log = &peer->log; 373 peer->conn.log = &peer->log;
374 peer->conn.log_error = NGX_ERROR_ERR;
358 375
359 /* UDP sockets are always ready to write */ 376 /* UDP sockets are always ready to write */
360 peer->conn.write->ready = 1; 377 peer->conn.write->ready = 1;
361 378
362 return NGX_OK; 379 return NGX_OK;
363 380
364 failed: 381 failed:
382
383 peer->connect_error_time = ngx_time();
365 384
366 if (ngx_close_socket(fd) == -1) { 385 if (ngx_close_socket(fd) == -1) {
367 ngx_log_error(NGX_LOG_ALERT, &peer->log, ngx_socket_errno, 386 ngx_log_error(NGX_LOG_ALERT, &peer->log, ngx_socket_errno,
368 ngx_close_socket_n " failed"); 387 ngx_close_socket_n " failed");
369 } 388 }