Implement session ID for TCP/UDP servers.
* imap4d/imap4d.c (set_strerr_flt,clr_strerr_flt): New functions. (imap4d_connection): Setup session prefix in strerr if mu_log_session_id is set. * imap4d/io.c (io_setio): Bugfix: unref debug stream. * pop3d/extra.c (pop3d_setio): Likewise. * pop3d/pop3d.c (set_strerr_flt,clr_strerr_flt): New functions. (pop3d_connection): Setup session prefix in strerr if mu_log_session_id is set. * include/mailutils/acl.h (mu_acl_setenv) (mu_acl_getenv,mu_acl_set_session_id): New functions. * include/mailutils/server.h (mu_session_id): New extern. (mu_m_server_configured_count): Fix signature. * include/mailutils/syslog.h (mu_log_session_id): New extern. * libmailutils/diag/syslog.c (mu_log_session_id): New global. * libmailutils/server/acl.c (_mu_acl) <envv,envc,envn>: New members. (run_closure) <env>: New member. (mu_acl_destroy): Free environment. (_acl_match): Handle "family" variable. (expand_arg): Propagate ACL environment to wordsplit. (mu_acl_check_sockaddr): Propagate ACL environment. (mu_acl_setenv) (mu_acl_getenv,mu_acl_set_session_id): New functions. * libmailutils/server/ipsrv.c (mu_ip_tcp_accept): Store session ID in the ACL. (mu_ip_udp_accept): Likewise. * libmailutils/server/msrv.c (mu_m_server_configured_count): Fix signature. (mu_m_server_check_acl): Store session ID in the ACL. * libmailutils/server/server.c (mu_session_id): New global variable. (connection_loop): Increment session ID (mu_acl_set_session_id): New function. * libmailutils/stream/fltstream.c (filter_ctl): Handle MU_IOCTL_SUBSTREAM. * libmailutils/stream/logstream.c (_log_ctl): Likewise. * libmu_cfg/common.c (mu_logging_param) <session-id>: New statement.
Showing
15 changed files
with
383 additions
and
39 deletions
... | @@ -409,6 +409,69 @@ get_client_address (int fd, struct sockaddr_in *pcs) | ... | @@ -409,6 +409,69 @@ get_client_address (int fd, struct sockaddr_in *pcs) |
409 | return 0; | 409 | return 0; |
410 | } | 410 | } |
411 | 411 | ||
412 | static int | ||
413 | set_strerr_flt () | ||
414 | { | ||
415 | mu_stream_t flt, trans[2]; | ||
416 | int rc; | ||
417 | |||
418 | rc = mu_stream_ioctl (mu_strerr, MU_IOCTL_SUBSTREAM, MU_IOCTL_OP_GET, trans); | ||
419 | if (rc == 0) | ||
420 | { | ||
421 | char sessidstr[10]; | ||
422 | char *argv[] = { "inline-comment", NULL, "-S", NULL }; | ||
423 | |||
424 | snprintf (sessidstr, sizeof sessidstr, "%08lx:", mu_session_id); | ||
425 | argv[1] = sessidstr; | ||
426 | rc = mu_filter_create_args (&flt, trans[0], "inline-comment", 3, | ||
427 | (const char **)argv, | ||
428 | MU_FILTER_ENCODE, MU_STREAM_WRITE); | ||
429 | mu_stream_unref (trans[0]); | ||
430 | if (rc == 0) | ||
431 | { | ||
432 | mu_stream_set_buffer (flt, mu_buffer_line, 0); | ||
433 | trans[0] = flt; | ||
434 | trans[1] = NULL; | ||
435 | rc = mu_stream_ioctl (mu_strerr, MU_IOCTL_SUBSTREAM, | ||
436 | MU_IOCTL_OP_SET, trans); | ||
437 | mu_stream_unref (trans[0]); | ||
438 | if (rc) | ||
439 | mu_error (_("%s failed: %s"), "MU_IOCTL_SET_STREAM", | ||
440 | mu_stream_strerror (mu_strerr, rc)); | ||
441 | } | ||
442 | else | ||
443 | mu_error (_("cannot create log filter stream: %s"), mu_strerror (rc)); | ||
444 | } | ||
445 | else | ||
446 | { | ||
447 | mu_error (_("%s failed: %s"), "MU_IOCTL_GET_STREAM", | ||
448 | mu_stream_strerror (mu_strerr, rc)); | ||
449 | } | ||
450 | return rc; | ||
451 | } | ||
452 | |||
453 | static void | ||
454 | clr_strerr_flt () | ||
455 | { | ||
456 | mu_stream_t flt, trans[2]; | ||
457 | int rc; | ||
458 | |||
459 | rc = mu_stream_ioctl (mu_strerr, MU_IOCTL_SUBSTREAM, MU_IOCTL_OP_GET, trans); | ||
460 | if (rc == 0) | ||
461 | { | ||
462 | flt = trans[0]; | ||
463 | |||
464 | rc = mu_stream_ioctl (flt, MU_IOCTL_SUBSTREAM, MU_IOCTL_OP_GET, trans); | ||
465 | if (rc == 0) | ||
466 | { | ||
467 | mu_stream_unref (trans[0]); | ||
468 | rc = mu_stream_ioctl (mu_strerr, MU_IOCTL_SUBSTREAM, | ||
469 | MU_IOCTL_OP_SET, trans); | ||
470 | if (rc == 0) | ||
471 | mu_stream_unref (flt); | ||
472 | } | ||
473 | } | ||
474 | } | ||
412 | 475 | ||
413 | void | 476 | void |
414 | imap4d_child_signal_setup (RETSIGTYPE (*handler) (int signo)) | 477 | imap4d_child_signal_setup (RETSIGTYPE (*handler) (int signo)) |
... | @@ -507,10 +570,21 @@ imap4d_connection (int fd, struct sockaddr *sa, int salen, | ... | @@ -507,10 +570,21 @@ imap4d_connection (int fd, struct sockaddr *sa, int salen, |
507 | struct mu_srv_config *pconf, void *data) | 570 | struct mu_srv_config *pconf, void *data) |
508 | { | 571 | { |
509 | struct imap4d_srv_config *cfg = (struct imap4d_srv_config *) pconf; | 572 | struct imap4d_srv_config *cfg = (struct imap4d_srv_config *) pconf; |
573 | int rc; | ||
510 | 574 | ||
511 | idle_timeout = pconf->timeout; | 575 | idle_timeout = pconf->timeout; |
512 | imap4d_transcript = pconf->transcript; | 576 | imap4d_transcript = pconf->transcript; |
577 | |||
578 | if (mu_log_session_id) | ||
579 | rc = set_strerr_flt (); | ||
580 | else | ||
581 | rc = 1; | ||
582 | |||
513 | imap4d_mainloop (fd, fd, cfg->tls); | 583 | imap4d_mainloop (fd, fd, cfg->tls); |
584 | |||
585 | if (rc == 0) | ||
586 | clr_strerr_flt (); | ||
587 | |||
514 | return 0; | 588 | return 0; |
515 | } | 589 | } |
516 | 590 | ... | ... |
... | @@ -76,6 +76,7 @@ io_setio (int ifd, int ofd, int tls) | ... | @@ -76,6 +76,7 @@ io_setio (int ifd, int ofd, int tls) |
76 | else | 76 | else |
77 | { | 77 | { |
78 | rc = mu_xscript_stream_create (&xstr, iostream, dstr, NULL); | 78 | rc = mu_xscript_stream_create (&xstr, iostream, dstr, NULL); |
79 | mu_stream_unref (dstr); | ||
79 | if (rc) | 80 | if (rc) |
80 | mu_error (_("cannot create transcript stream: %s"), | 81 | mu_error (_("cannot create transcript stream: %s"), |
81 | mu_strerror (rc)); | 82 | mu_strerror (rc)); | ... | ... |
... | @@ -63,4 +63,8 @@ int mu_acl_check_fd (mu_acl_t acl, int fd, mu_acl_result_t *pres); | ... | @@ -63,4 +63,8 @@ int mu_acl_check_fd (mu_acl_t acl, int fd, mu_acl_result_t *pres); |
63 | int mu_acl_action_to_string (mu_acl_action_t act, const char **pstr); | 63 | int mu_acl_action_to_string (mu_acl_action_t act, const char **pstr); |
64 | int mu_acl_string_to_action (const char *str, mu_acl_action_t *pres); | 64 | int mu_acl_string_to_action (const char *str, mu_acl_action_t *pres); |
65 | 65 | ||
66 | int mu_acl_setenv (mu_acl_t acl, const char *name, const char *val); | ||
67 | const char *mu_acl_getenv (mu_acl_t acl, const char *name); | ||
68 | int mu_acl_set_session_id (mu_acl_t acl); | ||
69 | |||
66 | #endif | 70 | #endif | ... | ... |
... | @@ -21,6 +21,8 @@ | ... | @@ -21,6 +21,8 @@ |
21 | #include <mailutils/types.h> | 21 | #include <mailutils/types.h> |
22 | #include <signal.h> | 22 | #include <signal.h> |
23 | 23 | ||
24 | extern unsigned long mu_session_id; | ||
25 | |||
24 | typedef int (*mu_conn_loop_fp) (int fd, void *conn_data, void *server_data); | 26 | typedef int (*mu_conn_loop_fp) (int fd, void *conn_data, void *server_data); |
25 | typedef void (*mu_conn_free_fp) (void *conn_data, void *server_data); | 27 | typedef void (*mu_conn_free_fp) (void *conn_data, void *server_data); |
26 | typedef int (*mu_server_idle_fp) (void *server_data); | 28 | typedef int (*mu_server_idle_fp) (void *server_data); |
... | @@ -124,7 +126,7 @@ const char * mu_m_server_pidfile (mu_m_server_t srv); | ... | @@ -124,7 +126,7 @@ const char * mu_m_server_pidfile (mu_m_server_t srv); |
124 | void mu_m_server_get_sigset (mu_m_server_t srv, sigset_t *sigset); | 126 | void mu_m_server_get_sigset (mu_m_server_t srv, sigset_t *sigset); |
125 | int mu_m_server_get_srvlist (mu_m_server_t srv, mu_list_t *plist); | 127 | int mu_m_server_get_srvlist (mu_m_server_t srv, mu_list_t *plist); |
126 | 128 | ||
127 | void mu_m_server_configured_count (mu_m_server_t msrv, size_t count); | 129 | void mu_m_server_configured_count (mu_m_server_t msrv, size_t *count); |
128 | 130 | ||
129 | void mu_m_server_begin (mu_m_server_t msrv); | 131 | void mu_m_server_begin (mu_m_server_t msrv); |
130 | int mu_m_server_run (mu_m_server_t msrv); | 132 | int mu_m_server_run (mu_m_server_t msrv); | ... | ... |
... | @@ -29,6 +29,7 @@ extern int mu_log_facility; | ... | @@ -29,6 +29,7 @@ extern int mu_log_facility; |
29 | extern char *mu_log_tag; | 29 | extern char *mu_log_tag; |
30 | extern int mu_log_print_severity; | 30 | extern int mu_log_print_severity; |
31 | extern unsigned mu_log_severity_threshold; | 31 | extern unsigned mu_log_severity_threshold; |
32 | extern int mu_log_session_id; | ||
32 | 33 | ||
33 | #define MU_LOG_TAG() (mu_log_tag ? mu_log_tag : mu_program_name) | 34 | #define MU_LOG_TAG() (mu_log_tag ? mu_log_tag : mu_program_name) |
34 | 35 | ... | ... |
... | @@ -133,3 +133,4 @@ int mu_log_facility = LOG_FACILITY; | ... | @@ -133,3 +133,4 @@ int mu_log_facility = LOG_FACILITY; |
133 | char *mu_log_tag = NULL; | 133 | char *mu_log_tag = NULL; |
134 | int mu_log_print_severity = 0; | 134 | int mu_log_print_severity = 0; |
135 | unsigned mu_log_severity_threshold = MU_LOG_DEBUG; | 135 | unsigned mu_log_severity_threshold = MU_LOG_DEBUG; |
136 | int mu_log_session_id; | ... | ... |
... | @@ -58,6 +58,21 @@ struct _mu_acl_entry | ... | @@ -58,6 +58,21 @@ struct _mu_acl_entry |
58 | struct _mu_acl | 58 | struct _mu_acl |
59 | { | 59 | { |
60 | mu_list_t aclist; | 60 | mu_list_t aclist; |
61 | char **envv; | ||
62 | size_t envc; | ||
63 | size_t envn; | ||
64 | }; | ||
65 | |||
66 | struct run_closure | ||
67 | { | ||
68 | unsigned idx; | ||
69 | struct mu_cidr addr; | ||
70 | |||
71 | char **env; | ||
72 | char ipstr[40]; | ||
73 | char *addrstr; | ||
74 | char *numbuf; | ||
75 | mu_acl_result_t *result; | ||
61 | }; | 76 | }; |
62 | 77 | ||
63 | 78 | ||
... | @@ -117,11 +132,16 @@ mu_acl_count (mu_acl_t acl, size_t *pcount) | ... | @@ -117,11 +132,16 @@ mu_acl_count (mu_acl_t acl, size_t *pcount) |
117 | int | 132 | int |
118 | mu_acl_destroy (mu_acl_t *pacl) | 133 | mu_acl_destroy (mu_acl_t *pacl) |
119 | { | 134 | { |
135 | size_t i; | ||
136 | |||
120 | mu_acl_t acl; | 137 | mu_acl_t acl; |
121 | if (!pacl || !*pacl) | 138 | if (!pacl || !*pacl) |
122 | return EINVAL; | 139 | return EINVAL; |
123 | acl = *pacl; | 140 | acl = *pacl; |
124 | mu_list_destroy (&acl->aclist); | 141 | mu_list_destroy (&acl->aclist); |
142 | for (i = 0; i < acl->envc && acl->envv[i]; i++) | ||
143 | free (acl->envv[i]); | ||
144 | free (acl->envv); | ||
125 | free (acl); | 145 | free (acl); |
126 | *pacl = acl; | 146 | *pacl = acl; |
127 | return 0; | 147 | return 0; |
... | @@ -249,17 +269,6 @@ mu_acl_string_to_action (const char *str, mu_acl_action_t *pres) | ... | @@ -249,17 +269,6 @@ mu_acl_string_to_action (const char *str, mu_acl_action_t *pres) |
249 | return rc; | 269 | return rc; |
250 | } | 270 | } |
251 | 271 | ||
252 | struct run_closure | ||
253 | { | ||
254 | unsigned idx; | ||
255 | struct mu_cidr addr; | ||
256 | |||
257 | char ipstr[40]; | ||
258 | char *addrstr; | ||
259 | char *numbuf; | ||
260 | mu_acl_result_t *result; | ||
261 | }; | ||
262 | |||
263 | int | 272 | int |
264 | _acl_match (struct _mu_acl_entry *ent, struct run_closure *rp) | 273 | _acl_match (struct _mu_acl_entry *ent, struct run_closure *rp) |
265 | { | 274 | { |
... | @@ -297,6 +306,26 @@ acl_getvar (const char *name, size_t nlen, void *data) | ... | @@ -297,6 +306,26 @@ acl_getvar (const char *name, size_t nlen, void *data) |
297 | { | 306 | { |
298 | struct run_closure *rp = data; | 307 | struct run_closure *rp = data; |
299 | 308 | ||
309 | if (SEQ ("family", name, nlen)) | ||
310 | { | ||
311 | switch (rp->addr.family) | ||
312 | { | ||
313 | case AF_INET: | ||
314 | return "AF_INET"; | ||
315 | |||
316 | #ifdef MAILUTILS_IPV6 | ||
317 | case AF_INET6: | ||
318 | return "AF_INET6"; | ||
319 | #endif | ||
320 | |||
321 | case AF_UNIX: | ||
322 | return "AF_UNIX"; | ||
323 | |||
324 | default: | ||
325 | return NULL; | ||
326 | } | ||
327 | } | ||
328 | |||
300 | if (SEQ ("aclno", name, nlen)) | 329 | if (SEQ ("aclno", name, nlen)) |
301 | { | 330 | { |
302 | if (!rp->numbuf && mu_asprintf (&rp->numbuf, "%u", rp->idx)) | 331 | if (!rp->numbuf && mu_asprintf (&rp->numbuf, "%u", rp->idx)) |
... | @@ -330,33 +359,19 @@ expand_arg (const char *cmdline, struct run_closure *rp, char **s) | ... | @@ -330,33 +359,19 @@ expand_arg (const char *cmdline, struct run_closure *rp, char **s) |
330 | { | 359 | { |
331 | int rc; | 360 | int rc; |
332 | struct mu_wordsplit ws; | 361 | struct mu_wordsplit ws; |
333 | const char *env[3]; | 362 | int envflag = 0; |
334 | 363 | ||
335 | mu_debug (MU_DEBCAT_ACL, MU_DEBUG_TRACE, ("Expanding \"%s\"", cmdline)); | 364 | mu_debug (MU_DEBCAT_ACL, MU_DEBUG_TRACE, ("Expanding \"%s\"", cmdline)); |
336 | env[0] = "family"; | 365 | if (rp->env) |
337 | switch (rp->addr.family) | ||
338 | { | 366 | { |
339 | case AF_INET: | 367 | ws.ws_env = (const char **) rp->env; |
340 | env[1] = "AF_INET"; | 368 | envflag = MU_WRDSF_ENV; |
341 | break; | ||
342 | |||
343 | #ifdef MAILUTILS_IPV6 | ||
344 | case AF_INET6: | ||
345 | env[1] = "AF_INET6"; | ||
346 | break; | ||
347 | #endif | ||
348 | |||
349 | case AF_UNIX: | ||
350 | env[1] = "AF_UNIX"; | ||
351 | break; | ||
352 | } | 369 | } |
353 | env[2] = NULL; | ||
354 | ws.ws_env = env; | ||
355 | ws.ws_getvar = acl_getvar; | 370 | ws.ws_getvar = acl_getvar; |
356 | ws.ws_closure = rp; | 371 | ws.ws_closure = rp; |
357 | rc = mu_wordsplit (cmdline, &ws, | 372 | rc = mu_wordsplit (cmdline, &ws, |
358 | MU_WRDSF_NOSPLIT | MU_WRDSF_NOCMD | | 373 | MU_WRDSF_NOSPLIT | MU_WRDSF_NOCMD | |
359 | MU_WRDSF_ENV | MU_WRDSF_ENV_KV | | 374 | envflag | MU_WRDSF_ENV_KV | |
360 | MU_WRDSF_GETVAR | MU_WRDSF_CLOSURE); | 375 | MU_WRDSF_GETVAR | MU_WRDSF_CLOSURE); |
361 | 376 | ||
362 | if (rc == 0) | 377 | if (rc == 0) |
... | @@ -553,6 +568,7 @@ mu_acl_check_sockaddr (mu_acl_t acl, const struct sockaddr *sa, int salen, | ... | @@ -553,6 +568,7 @@ mu_acl_check_sockaddr (mu_acl_t acl, const struct sockaddr *sa, int salen, |
553 | 568 | ||
554 | r.idx = 0; | 569 | r.idx = 0; |
555 | r.result = pres; | 570 | r.result = pres; |
571 | r.env = acl->envv; | ||
556 | *r.result = mu_acl_result_undefined; | 572 | *r.result = mu_acl_result_undefined; |
557 | r.numbuf = NULL; | 573 | r.numbuf = NULL; |
558 | mu_list_foreach (acl->aclist, _run_entry, &r); | 574 | mu_list_foreach (acl->aclist, _run_entry, &r); |
... | @@ -607,3 +623,94 @@ mu_acl_check_fd (mu_acl_t acl, int fd, mu_acl_result_t *pres) | ... | @@ -607,3 +623,94 @@ mu_acl_check_fd (mu_acl_t acl, int fd, mu_acl_result_t *pres) |
607 | return mu_acl_check_sockaddr (acl, &addr.sa, len, pres); | 623 | return mu_acl_check_sockaddr (acl, &addr.sa, len, pres); |
608 | } | 624 | } |
609 | 625 | ||
626 | static int | ||
627 | _acl_getenv (mu_acl_t acl, const char *name, size_t *pres) | ||
628 | { | ||
629 | size_t i; | ||
630 | |||
631 | if (!acl->envv) | ||
632 | return MU_ERR_NOENT; | ||
633 | for (i = 0; i < acl->envc; i++) | ||
634 | if (strcmp (acl->envv[i], name) == 0) | ||
635 | { | ||
636 | *pres = i; | ||
637 | return 0; | ||
638 | } | ||
639 | return MU_ERR_NOENT; | ||
640 | } | ||
641 | |||
642 | const char * | ||
643 | mu_acl_getenv (mu_acl_t acl, const char *name) | ||
644 | { | ||
645 | size_t i; | ||
646 | |||
647 | if (_acl_getenv (acl, name, &i) == 0) | ||
648 | { | ||
649 | return acl->envv[i + 1]; | ||
650 | } | ||
651 | return NULL; | ||
652 | } | ||
653 | |||
654 | static int | ||
655 | _acl_env_store (mu_acl_t acl, int i, const char *val) | ||
656 | { | ||
657 | char *copy = strdup (val); | ||
658 | if (!copy) | ||
659 | return ENOMEM; | ||
660 | free (acl->envv[i]); | ||
661 | acl->envv[i] = copy; | ||
662 | return 0; | ||
663 | } | ||
664 | |||
665 | int | ||
666 | mu_acl_setenv (mu_acl_t acl, const char *name, const char *val) | ||
667 | { | ||
668 | size_t i; | ||
669 | |||
670 | if (_acl_getenv (acl, name, &i) == 0) | ||
671 | { | ||
672 | if (!val) | ||
673 | { | ||
674 | free (acl->envv[i]); | ||
675 | free (acl->envv[i + 1]); | ||
676 | memmove (acl->envv + i, acl->envv + i + 3, | ||
677 | (acl->envn + 1 - (i + 3)) * sizeof (acl->envv[0])); | ||
678 | acl->envn -= 2; | ||
679 | return 0; | ||
680 | } | ||
681 | return _acl_env_store (acl, i + 1, val); | ||
682 | } | ||
683 | |||
684 | if (!acl->envv || acl->envn + 1 == acl->envc) | ||
685 | { | ||
686 | char **p; | ||
687 | |||
688 | if (!val) | ||
689 | return 0; | ||
690 | |||
691 | if (acl->envv == NULL) | ||
692 | p = calloc (3, sizeof (acl->envv[0])); | ||
693 | else | ||
694 | { | ||
695 | p = realloc (acl->envv, (acl->envc + 3) * sizeof (acl->envv[0])); | ||
696 | if (!p) | ||
697 | return ENOMEM; | ||
698 | p[acl->envc] = NULL; | ||
699 | } | ||
700 | |||
701 | acl->envv = p; | ||
702 | acl->envc += 3; | ||
703 | } | ||
704 | |||
705 | if (_acl_env_store (acl, acl->envn, name)) | ||
706 | return ENOMEM; | ||
707 | if (_acl_env_store (acl, acl->envn + 1, val)) | ||
708 | { | ||
709 | free (acl->envv[acl->envn]); | ||
710 | acl->envv[acl->envn] = NULL; | ||
711 | return ENOMEM; | ||
712 | } | ||
713 | acl->envn += 2; | ||
714 | |||
715 | return 0; | ||
716 | } | ... | ... |
... | @@ -372,7 +372,10 @@ mu_ip_tcp_accept (mu_ip_server_t srv, void *call_data) | ... | @@ -372,7 +372,10 @@ mu_ip_tcp_accept (mu_ip_server_t srv, void *call_data) |
372 | if (srv->acl) | 372 | if (srv->acl) |
373 | { | 373 | { |
374 | mu_acl_result_t res; | 374 | mu_acl_result_t res; |
375 | int rc = mu_acl_check_sockaddr (srv->acl, &client.sa, size, &res); | 375 | int rc; |
376 | |||
377 | mu_acl_set_session_id (srv->acl); | ||
378 | rc = mu_acl_check_sockaddr (srv->acl, &client.sa, size, &res); | ||
376 | if (rc) | 379 | if (rc) |
377 | mu_debug (MU_DEBCAT_SERVER, MU_DEBUG_ERROR, | 380 | mu_debug (MU_DEBCAT_SERVER, MU_DEBUG_ERROR, |
378 | ("%s: mu_acl_check_sockaddr: %s", | 381 | ("%s: mu_acl_check_sockaddr: %s", |
... | @@ -453,7 +456,10 @@ mu_ip_udp_accept (mu_ip_server_t srv, void *call_data) | ... | @@ -453,7 +456,10 @@ mu_ip_udp_accept (mu_ip_server_t srv, void *call_data) |
453 | if (srv->acl) | 456 | if (srv->acl) |
454 | { | 457 | { |
455 | mu_acl_result_t res; | 458 | mu_acl_result_t res; |
456 | int rc = mu_acl_check_sockaddr (srv->acl, &client.sa, size, &res); | 459 | int rc; |
460 | |||
461 | mu_acl_set_session_id (srv->acl); | ||
462 | rc = mu_acl_check_sockaddr (srv->acl, &client.sa, size, &res); | ||
457 | if (rc) | 463 | if (rc) |
458 | mu_debug (MU_DEBCAT_SERVER, MU_DEBUG_ERROR, | 464 | mu_debug (MU_DEBCAT_SERVER, MU_DEBUG_ERROR, |
459 | ("%s: mu_acl_check_sockaddr: %s\n", | 465 | ("%s: mu_acl_check_sockaddr: %s\n", | ... | ... |
... | @@ -343,9 +343,12 @@ mu_m_server_set_max_children (mu_m_server_t srv, size_t num) | ... | @@ -343,9 +343,12 @@ mu_m_server_set_max_children (mu_m_server_t srv, size_t num) |
343 | int | 343 | int |
344 | mu_m_server_set_pidfile (mu_m_server_t srv, const char *pidfile) | 344 | mu_m_server_set_pidfile (mu_m_server_t srv, const char *pidfile) |
345 | { | 345 | { |
346 | char *p = strdup (pidfile); | ||
347 | if (!p) | ||
348 | return errno; | ||
346 | free (srv->pidfile); | 349 | free (srv->pidfile); |
347 | srv->pidfile = strdup (pidfile); | 350 | srv->pidfile = p; |
348 | return srv->pidfile ? 0 : errno; | 351 | return 0; |
349 | } | 352 | } |
350 | 353 | ||
351 | int | 354 | int |
... | @@ -476,9 +479,9 @@ add_server (mu_m_server_t msrv, struct mu_sockaddr *s, int type) | ... | @@ -476,9 +479,9 @@ add_server (mu_m_server_t msrv, struct mu_sockaddr *s, int type) |
476 | } | 479 | } |
477 | 480 | ||
478 | void | 481 | void |
479 | mu_m_server_configured_count (mu_m_server_t msrv, size_t count) | 482 | mu_m_server_configured_count (mu_m_server_t msrv, size_t *count) |
480 | { | 483 | { |
481 | mu_list_count (msrv->srvlist, &count); | 484 | mu_list_count (msrv->srvlist, count); |
482 | } | 485 | } |
483 | 486 | ||
484 | void | 487 | void |
... | @@ -645,7 +648,10 @@ mu_m_server_check_acl (mu_m_server_t msrv, struct sockaddr *s, int salen) | ... | @@ -645,7 +648,10 @@ mu_m_server_check_acl (mu_m_server_t msrv, struct sockaddr *s, int salen) |
645 | if (msrv->acl) | 648 | if (msrv->acl) |
646 | { | 649 | { |
647 | mu_acl_result_t res; | 650 | mu_acl_result_t res; |
648 | int rc = mu_acl_check_sockaddr (msrv->acl, s, salen, &res); | 651 | int rc; |
652 | |||
653 | mu_acl_set_session_id (msrv->acl); | ||
654 | rc = mu_acl_check_sockaddr (msrv->acl, s, salen, &res); | ||
649 | if (rc) | 655 | if (rc) |
650 | { | 656 | { |
651 | char *p = mu_sockaddr_to_astr (s, salen); | 657 | char *p = mu_sockaddr_to_astr (s, salen); | ... | ... |
... | @@ -38,6 +38,8 @@ struct _mu_connection | ... | @@ -38,6 +38,8 @@ struct _mu_connection |
38 | 38 | ||
39 | #define MU_SERVER_TIMEOUT 0x1 | 39 | #define MU_SERVER_TIMEOUT 0x1 |
40 | 40 | ||
41 | unsigned long mu_session_id; | ||
42 | |||
41 | struct _mu_server | 43 | struct _mu_server |
42 | { | 44 | { |
43 | int nfd; | 45 | int nfd; |
... | @@ -104,7 +106,10 @@ connection_loop (mu_server_t srv, fd_set *fdset) | ... | @@ -104,7 +106,10 @@ connection_loop (mu_server_t srv, fd_set *fdset) |
104 | struct _mu_connection *next = conn->next; | 106 | struct _mu_connection *next = conn->next; |
105 | if (FD_ISSET (conn->fd, fdset)) | 107 | if (FD_ISSET (conn->fd, fdset)) |
106 | { | 108 | { |
107 | int rc = conn->f_loop (conn->fd, conn->data, srv->server_data); | 109 | int rc; |
110 | |||
111 | ++mu_session_id; | ||
112 | rc = conn->f_loop (conn->fd, conn->data, srv->server_data); | ||
108 | switch (rc) | 113 | switch (rc) |
109 | { | 114 | { |
110 | case 0: | 115 | case 0: |
... | @@ -291,3 +296,12 @@ mu_server_add_connection (mu_server_t srv, | ... | @@ -291,3 +296,12 @@ mu_server_add_connection (mu_server_t srv, |
291 | srv->tail = p; | 296 | srv->tail = p; |
292 | return 0; | 297 | return 0; |
293 | } | 298 | } |
299 | |||
300 | int | ||
301 | mu_acl_set_session_id (mu_acl_t acl) | ||
302 | { | ||
303 | char sessidstr[9]; | ||
304 | snprintf (sessidstr, sizeof sessidstr, "%08lx", mu_session_id); | ||
305 | return mu_acl_setenv (acl, "sessid", sessidstr); | ||
306 | } | ||
307 | ... | ... |
... | @@ -422,6 +422,32 @@ filter_ctl (struct _mu_stream *stream, int code, int opcode, void *ptr) | ... | @@ -422,6 +422,32 @@ filter_ctl (struct _mu_stream *stream, int code, int opcode, void *ptr) |
422 | } | 422 | } |
423 | break; | 423 | break; |
424 | 424 | ||
425 | case MU_IOCTL_SUBSTREAM: | ||
426 | if (!ptr) | ||
427 | return EINVAL; | ||
428 | else | ||
429 | { | ||
430 | mu_stream_t *pstr = ptr; | ||
431 | switch (opcode) | ||
432 | { | ||
433 | case MU_IOCTL_OP_GET: | ||
434 | pstr[0] = fs->transport; | ||
435 | mu_stream_ref (pstr[0]); | ||
436 | pstr[1] = NULL; | ||
437 | break; | ||
438 | |||
439 | case MU_IOCTL_OP_SET: | ||
440 | mu_stream_unref (fs->transport); | ||
441 | fs->transport = pstr[0]; | ||
442 | mu_stream_ref (fs->transport); | ||
443 | break; | ||
444 | |||
445 | default: | ||
446 | return EINVAL; | ||
447 | } | ||
448 | } | ||
449 | break; | ||
450 | |||
425 | case MU_IOCTL_TRANSPORT: | 451 | case MU_IOCTL_TRANSPORT: |
426 | switch (opcode) | 452 | switch (opcode) |
427 | { | 453 | { | ... | ... |
... | @@ -309,6 +309,32 @@ _log_ctl (struct _mu_stream *str, int code, int opcode, void *arg) | ... | @@ -309,6 +309,32 @@ _log_ctl (struct _mu_stream *str, int code, int opcode, void *arg) |
309 | } | 309 | } |
310 | break; | 310 | break; |
311 | 311 | ||
312 | case MU_IOCTL_SUBSTREAM: | ||
313 | if (!arg) | ||
314 | return EINVAL; | ||
315 | else | ||
316 | { | ||
317 | mu_stream_t *pstr = arg; | ||
318 | switch (opcode) | ||
319 | { | ||
320 | case MU_IOCTL_OP_GET: | ||
321 | pstr[0] = sp->transport; | ||
322 | mu_stream_ref (pstr[0]); | ||
323 | pstr[1] = NULL; | ||
324 | break; | ||
325 | |||
326 | case MU_IOCTL_OP_SET: | ||
327 | mu_stream_unref (sp->transport); | ||
328 | sp->transport = pstr[0]; | ||
329 | mu_stream_ref (sp->transport); | ||
330 | break; | ||
331 | |||
332 | default: | ||
333 | return EINVAL; | ||
334 | } | ||
335 | } | ||
336 | break; | ||
337 | |||
312 | case MU_IOCTL_LOGSTREAM: | 338 | case MU_IOCTL_LOGSTREAM: |
313 | switch (opcode) | 339 | switch (opcode) |
314 | { | 340 | { | ... | ... |
... | @@ -171,6 +171,8 @@ static struct mu_cfg_param mu_logging_param[] = { | ... | @@ -171,6 +171,8 @@ static struct mu_cfg_param mu_logging_param[] = { |
171 | N_("Set syslog facility. Arg is one of the following: user, daemon, " | 171 | N_("Set syslog facility. Arg is one of the following: user, daemon, " |
172 | "auth, authpriv, mail, cron, local0 through local7 (case-insensitive), " | 172 | "auth, authpriv, mail, cron, local0 through local7 (case-insensitive), " |
173 | "or a facility number.") }, | 173 | "or a facility number.") }, |
174 | { "session-id", mu_cfg_bool, &mu_log_session_id, 0, NULL, | ||
175 | N_("Log session ID") }, | ||
174 | { "tag", mu_cfg_string, &mu_log_tag, 0, NULL, | 176 | { "tag", mu_cfg_string, &mu_log_tag, 0, NULL, |
175 | N_("Tag syslog messages with this string.") }, | 177 | N_("Tag syslog messages with this string.") }, |
176 | { NULL } | 178 | { NULL } | ... | ... |
... | @@ -185,6 +185,7 @@ pop3d_setio (int ifd, int ofd, int tls) | ... | @@ -185,6 +185,7 @@ pop3d_setio (int ifd, int ofd, int tls) |
185 | else | 185 | else |
186 | { | 186 | { |
187 | rc = mu_xscript_stream_create (&xstr, iostream, dstr, NULL); | 187 | rc = mu_xscript_stream_create (&xstr, iostream, dstr, NULL); |
188 | mu_stream_unref (dstr); | ||
188 | if (rc) | 189 | if (rc) |
189 | mu_error (_("cannot create transcript stream: %s"), | 190 | mu_error (_("cannot create transcript stream: %s"), |
190 | mu_strerror (rc)); | 191 | mu_strerror (rc)); | ... | ... |
... | @@ -366,17 +366,90 @@ pop3d_mainloop (int ifd, int ofd, int tls) | ... | @@ -366,17 +366,90 @@ pop3d_mainloop (int ifd, int ofd, int tls) |
366 | return status; | 366 | return status; |
367 | } | 367 | } |
368 | 368 | ||
369 | static int | ||
370 | set_strerr_flt () | ||
371 | { | ||
372 | mu_stream_t flt, trans[2]; | ||
373 | int rc; | ||
374 | |||
375 | rc = mu_stream_ioctl (mu_strerr, MU_IOCTL_SUBSTREAM, MU_IOCTL_OP_GET, trans); | ||
376 | if (rc == 0) | ||
377 | { | ||
378 | char sessidstr[10]; | ||
379 | char *argv[] = { "inline-comment", NULL, "-S", NULL }; | ||
380 | |||
381 | snprintf (sessidstr, sizeof sessidstr, "%08lx:", mu_session_id); | ||
382 | argv[1] = sessidstr; | ||
383 | rc = mu_filter_create_args (&flt, trans[0], "inline-comment", 3, | ||
384 | (const char **)argv, | ||
385 | MU_FILTER_ENCODE, MU_STREAM_WRITE); | ||
386 | mu_stream_unref (trans[0]); | ||
387 | if (rc == 0) | ||
388 | { | ||
389 | mu_stream_set_buffer (flt, mu_buffer_line, 0); | ||
390 | trans[0] = flt; | ||
391 | trans[1] = NULL; | ||
392 | rc = mu_stream_ioctl (mu_strerr, MU_IOCTL_SUBSTREAM, | ||
393 | MU_IOCTL_OP_SET, trans); | ||
394 | mu_stream_unref (trans[0]); | ||
395 | if (rc) | ||
396 | mu_error (_("%s failed: %s"), "MU_IOCTL_SET_STREAM", | ||
397 | mu_stream_strerror (mu_strerr, rc)); | ||
398 | } | ||
399 | else | ||
400 | mu_error (_("cannot create log filter stream: %s"), mu_strerror (rc)); | ||
401 | } | ||
402 | else | ||
403 | { | ||
404 | mu_error (_("%s failed: %s"), "MU_IOCTL_GET_STREAM", | ||
405 | mu_stream_strerror (mu_strerr, rc)); | ||
406 | } | ||
407 | return rc; | ||
408 | } | ||
409 | |||
410 | static void | ||
411 | clr_strerr_flt () | ||
412 | { | ||
413 | mu_stream_t flt, trans[2]; | ||
414 | int rc; | ||
415 | |||
416 | rc = mu_stream_ioctl (mu_strerr, MU_IOCTL_SUBSTREAM, MU_IOCTL_OP_GET, trans); | ||
417 | if (rc == 0) | ||
418 | { | ||
419 | flt = trans[0]; | ||
420 | |||
421 | rc = mu_stream_ioctl (flt, MU_IOCTL_SUBSTREAM, MU_IOCTL_OP_GET, trans); | ||
422 | if (rc == 0) | ||
423 | { | ||
424 | mu_stream_unref (trans[0]); | ||
425 | rc = mu_stream_ioctl (mu_strerr, MU_IOCTL_SUBSTREAM, | ||
426 | MU_IOCTL_OP_SET, trans); | ||
427 | if (rc == 0) | ||
428 | mu_stream_unref (flt); | ||
429 | } | ||
430 | } | ||
431 | } | ||
432 | |||
369 | int | 433 | int |
370 | pop3d_connection (int fd, struct sockaddr *sa, int salen, | 434 | pop3d_connection (int fd, struct sockaddr *sa, int salen, |
371 | struct mu_srv_config *pconf, | 435 | struct mu_srv_config *pconf, |
372 | void *data) | 436 | void *data) |
373 | { | 437 | { |
374 | struct pop3d_srv_config *cfg = (struct pop3d_srv_config *) pconf; | 438 | struct pop3d_srv_config *cfg = (struct pop3d_srv_config *) pconf; |
439 | int rc; | ||
375 | 440 | ||
376 | idle_timeout = pconf->timeout; | 441 | idle_timeout = pconf->timeout; |
377 | pop3d_transcript = pconf->transcript; | 442 | pop3d_transcript = pconf->transcript; |
378 | 443 | ||
444 | if (mu_log_session_id) | ||
445 | rc = set_strerr_flt (); | ||
446 | else | ||
447 | rc = 1; | ||
448 | |||
379 | pop3d_mainloop (fd, fd, cfg->tls); | 449 | pop3d_mainloop (fd, fd, cfg->tls); |
450 | |||
451 | if (rc == 0) | ||
452 | clr_strerr_flt (); | ||
380 | return 0; | 453 | return 0; |
381 | } | 454 | } |
382 | 455 | ... | ... |
-
Please register or sign in to post a comment