From a56dfbdcb4cb3eb9ffd3db641efb3e5605a6c3f0 Mon Sep 17 00:00:00 2001 From: Willy Tarreau Date: Fri, 21 Feb 2025 11:31:36 +0100 Subject: [PATCH] BUG/MINOR: mux-h1: always make sure h1s->sd exists in h1_dump_h1s_info() This function may be called from a signal handler during a warning, a panic or a show thread. We need to be more cautious about what may or may not be dereferenced since an h1s is not necessarily fully initialized. Loops of "show threads" sometimes manage to crash when dereferencing a null h1s->sd, so let's guard it and add a comment remining about the unusual call place. This can be backported to the relevant versions. --- src/mux_h1.c | 16 +++++++++++----- 1 file changed, 11 insertions(+), 5 deletions(-) diff --git a/src/mux_h1.c b/src/mux_h1.c index 3b09a9acf..c355edd0b 100644 --- a/src/mux_h1.c +++ b/src/mux_h1.c @@ -5364,6 +5364,10 @@ static int h1_dump_h1c_info(struct buffer *msg, struct h1c *h1c, const char *pfx * is NULL. Returns non-zero if the stream is considered suspicious. May * emit multiple lines, each new one being prefixed with , if is not * NULL, otherwise a single line is used. + * + * Remember that this may be called in a signal context from a "show threads" + * or panic dump, so the code must be careful about each data it accesses. + * However data are stable since the dump happens from the owner thread. */ static int h1_dump_h1s_info(struct buffer *msg, const struct h1s *h1s, const char *pfx) { @@ -5378,7 +5382,7 @@ static int h1_dump_h1s_info(struct buffer *msg, const struct h1s *h1s, const cha else method = "UNKNOWN"; - chunk_appendf(msg, " h1s=%p h1s.flg=0x%x .sd.flg=0x%x", h1s, h1s->flags, se_fl_get(h1s->sd)); + chunk_appendf(msg, " h1s=%p h1s.flg=0x%x", h1s, h1s->flags); chunk_appendf(msg, " .req.state=%s .res.state=%s", h1m_state_str(h1s->req.state), h1m_state_str(h1s->res.state)); if (pfx) @@ -5387,10 +5391,12 @@ static int h1_dump_h1s_info(struct buffer *msg, const struct h1s *h1s, const cha chunk_appendf(msg, " .meth=%s status=%d", method, h1s->status); - chunk_appendf(msg, " .sd.flg=0x%08x .sd.evts=%s", se_fl_get(h1s->sd), tevt_evts2str(h1s->sd->term_evts_log)); - if (!se_fl_test(h1s->sd, SE_FL_ORPHAN)) { - chunk_appendf(msg, " .sc.flg=0x%08x .sc.app=%p .sc.evts=%s", - h1s_sc(h1s)->flags, h1s_sc(h1s)->app, tevt_evts2str(h1s_sc(h1s)->term_evts_log)); + if (h1s->sd) { + chunk_appendf(msg, " .sd.flg=0x%08x .sd.evts=%s", se_fl_get(h1s->sd), tevt_evts2str(h1s->sd->term_evts_log)); + if (!se_fl_test(h1s->sd, SE_FL_ORPHAN)) { + chunk_appendf(msg, " .sc.flg=0x%08x .sc.app=%p .sc.evts=%s", + h1s_sc(h1s)->flags, h1s_sc(h1s)->app, tevt_evts2str(h1s_sc(h1s)->term_evts_log)); + } } if (pfx && h1s->subs)