On Thu, Oct 23, 2025 at 1:00 PM Tao Liu <[email protected]> wrote:

> Hi lianbo,
>
> On Wed, Oct 22, 2025 at 10:59 PM Lianbo Jiang <[email protected]> wrote:
> >
> > Currently, the log command will display human readable Rust
> > symbol name by default if any, but, sometimes still want to
> > print the original messages from the log buffer(do not demangle).
> >
> > In addition, if the log buffer has lines like "_R ... +" which
> > are not Rust symbols unexpectedly, probably the output will be
> > missed, that is unexpected.
> >
> > To fix above cases, add "log -R" to display human readable Rust
> > symbol name, otherwise still print the original messages.
> >
> > With the patch:
> >   crash> log -R
> >   ...
> >   [ 2174.289360] Tainted: [S]=CPU_OUT_OF_SPEC, [O]=OOT_MODULE,
> [E]=UNSIGNED_MODULE
> >   [ 2174.297322] Hardware name: Intel Corporation S2600CWR/S2600CWR,
> BIOS SE5C610.86B.01.01.0018.072020161249 07/20/2016
> >   [ 2174.308966] Call Trace:
> >   [ 2174.311693]  <TASK>
> >   [ 2174.314033]  dump_stack_lvl+0x5d/0x80
> >   [ 2174.318125]  panic+0x156/0x32a
> >   [ 2174.321539]  rust_panic::area_in_hp+0xf7/0x120 [rust_panic]
> >   [ 2174.329700]  ? console_unlock+0x9c/0x140
> >   [ 2174.334080]  ? irq_work_queue+0x2d/0x50
> >   [ 2174.338352]  ? __pfx_init_module+0x10/0x10 [rust_panic]
> >   [ 2174.344183]  <rust_panic::HelloPanic>::step_two+0x20/0xe0
> [rust_panic]
> >   [ 2174.353698]  ? _printk+0x6b/0x90
> >   [ 2174.357303]  init_module+0x57/0xff0 [rust_panic]
> >   [ 2174.362456]  ? __pfx_init_module+0x10/0x10 [rust_panic]
> >   ...
> >
> > Suggested-by: Kazuhito Hagio <[email protected]>
> > Signed-off-by: Lianbo Jiang <[email protected]>
> > ---
> >  defs.h   |  1 +
> >  help.c   | 24 ++++++++++++++++++-
> >  kernel.c |  5 +++-
> >  printk.c | 71 ++++++++++++++++++++++++++++++++++----------------------
> >  4 files changed, 71 insertions(+), 30 deletions(-)
> >
> > diff --git a/defs.h b/defs.h
> > index 3fd7d897c781..c434a5cae702 100644
> > --- a/defs.h
> > +++ b/defs.h
> > @@ -6229,6 +6229,7 @@ void parse_kernel_version(char *);
> >  #define SHOW_LOG_CTIME   (0x10)
> >  #define SHOW_LOG_SAFE    (0x20)
> >  #define SHOW_LOG_CALLER  (0x40)
> > +#define SHOW_LOG_RUST    (0x80)
> >  void set_cpu(int);
> >  void clear_machdep_cache(void);
> >  struct stack_hook *gather_text_list(struct bt_info *);
> > diff --git a/help.c b/help.c
> > index 4f071e0bd0a0..78d7a5c70e30 100644
> > --- a/help.c
> > +++ b/help.c
> > @@ -4026,7 +4026,7 @@ NULL
> >  char *help_log[] = {
> >  "log",
> >  "dump system message buffer",
> > -"[-Ttdmasc]",
> > +"[-TtdmascR]",
> >  "  This command dumps the kernel log_buf contents in chronological
> order.  The",
> >  "  command supports the older log_buf formats, which may or may not
> contain a",
> >  "  timestamp inserted prior to each message, as well as the newer
> variable-length",
> > @@ -4053,6 +4053,8 @@ char *help_log[] = {
> >  "        the CPU id (if in CPU context) that called printk(), if
> available.",
> >  "        Generally available on Linux 5.1 to 5.9 kernels configured
> with",
> >  "        CONFIG_PRINTK_CALLER or Linux 5.10 and later kernels.",
> > +"    -R  Display the message text with human readable Rust symbol name
> if any,",
> > +"        otherwise still print the original message text.",
> >  " ",
> >  "\nEXAMPLES",
> >  "  Dump the kernel message buffer:\n",
> > @@ -4231,6 +4233,26 @@ char *help_log[] = {
> >  "    [    0.014179] [    T29] RAMDISK: [mem 0x3cf4f000-0x437bbfff]",
> >  "    [    0.198789] [     C0] DMAR: DRHD: handling fault status reg 3",
> >  "    ...",
> > +" ",
> > +"  Display the message text with human readable Rust symbol name if
> any,",
> > +"  otherwise still print the original message text.\n",
> > +"    %s> log -R",
> > +"    ...",
> > +"    [ 2174.289360] Tainted: [S]=CPU_OUT_OF_SPEC, [O]=OOT_MODULE,
> [E]=UNSIGNED_MODULE",
> > +"    [ 2174.297322] Hardware name: Intel Corporation S2600CWR/S2600CWR,
> BIOS SE5C610.86B.01.01.0018.072020161249 07/20/2016",
> > +"    [ 2174.308966] Call Trace:",
> > +"    [ 2174.311693]  <TASK>",
> > +"    [ 2174.314033]  dump_stack_lvl+0x5d/0x80",
> > +"    [ 2174.318125]  panic+0x156/0x32a",
> > +"    [ 2174.321539]  rust_panic::area_in_hp+0xf7/0x120 [rust_panic]",
> > +"    [ 2174.329700]  ? console_unlock+0x9c/0x140",
> > +"    [ 2174.334080]  ? irq_work_queue+0x2d/0x50",
> > +"    [ 2174.338352]  ? __pfx_init_module+0x10/0x10 [rust_panic]",
> > +"    [ 2174.344183]  <rust_panic::HelloPanic>::step_two+0x20/0xe0
> [rust_panic]",
> > +"    [ 2174.353698]  ? _printk+0x6b/0x90",
> > +"    [ 2174.357303]  init_module+0x57/0xff0 [rust_panic]",
> > +"    [ 2174.362456]  ? __pfx_init_module+0x10/0x10 [rust_panic]",
> > +"    ...",
> >
> >  NULL
> >  };
> > diff --git a/kernel.c b/kernel.c
> > index e4213d7a663e..e077275d7ed6 100644
> > --- a/kernel.c
> > +++ b/kernel.c
> > @@ -5136,7 +5136,7 @@ cmd_log(void)
> >
> >         msg_flags = 0;
> >
> > -        while ((c = getopt(argcnt, args, "Ttdmasc")) != EOF) {
> > +        while ((c = getopt(argcnt, args, "TtdmascR")) != EOF) {
> >                  switch(c)
> >                  {
> >                 case 'T':
> > @@ -5160,6 +5160,9 @@ cmd_log(void)
> >                 case 'c':
> >                         msg_flags |= SHOW_LOG_CALLER;
> >                         break;
> > +               case 'R':
> > +                       msg_flags |= SHOW_LOG_RUST;
> > +                       break;
> >                  default:
> >                          argerrs++;
> >                          break;
> > diff --git a/printk.c b/printk.c
> > index 51b618e2a434..f7346f4c1c1d 100644
> > --- a/printk.c
> > +++ b/printk.c
> > @@ -116,7 +116,7 @@ dump_record(struct prb_map *m, unsigned long id, int
> msg_flags)
> >         uint64_t ts_nsec;
> >         ulonglong nanos;
> >         ulonglong seq;
> > -       int ilen = 0, i;
> > +       int ilen = 0, i, nlines;
> >         char *desc, *info, *text, *p;
> >         ulong rem;
> >
> > @@ -202,44 +202,59 @@ dump_record(struct prb_map *m, unsigned long id,
> int msg_flags)
> >
> >         text = m->text_data + begin;
> >
> > -       if (text_len > BUFSIZE) {
> > +       if ((msg_flags & SHOW_LOG_RUST) && (text_len > BUFSIZE)) {
> >                 error(WARNING, "\nThe messages could be truncated!\n");
> >                 text_len = BUFSIZE;
> >         }
> >
>
> As I understand the following code change. For any char within the
> (text ~ text + text_len) range, if no '\n' is encountered, then output
> the char into buf for later demangle use; if one '\n' is encountered,
> then output all chars which are already within buf, and output any
> later chars directly to console. In short, if '\n' is 0, chars will be
> rust demangled; otherwise if '\n' is >= 1, then chars won't be rust
> demangled. The number of '\n' is regarded as an indicator for rust
> demangle.
>

So far I haven't got better solution to handle the current case, take the
line breaks to check if there are multiple line breaks to determine what
to do next.


>
> I have no comments for the code change, but could you please add a
> code comment for the following code change? Otherwise after years
> people might lose the context and be confused about why take '\n' as
> the demangle indicator? At least I didn't see the info is logged
> within patch commit message.
>

I agree with you, and I will add the Link to the patch log.
https://www.mail-archive.com/[email protected]/msg01652.html

That can help understand this one.

Thanks
Lianbo


>
> Thanks,
> Tao Liu
> > -       for (i = 0, p = text; i < text_len; i++, p++) {
> > -               if (*p == '\n')
> > +       for (i = 0, nlines = 0, p = text; i < text_len; i++, p++) {
> > +               if (*p == '\n') {
> > +                       if ((msg_flags & SHOW_LOG_RUST) && (i !=
> text_len - 1)) {
> > +                               nlines++;
> > +                               if (strlen(buf)) {
> > +                                       fprintf(fp, "%s", buf);
> > +                                       memset(buf, 0, strlen(buf));
> > +                               }
> > +                       }
> >                         fprintf(fp, "\n%s", space(ilen));
> > -               else if (isprint(*p) || isspace(*p))
> > -                       sprintf(&buf[i], "%c", *p);
> > +               } else if ((msg_flags & SHOW_LOG_RUST) && (isprint(*p)
> || isspace(*p))) {
> > +                       if (nlines >= 1)
> > +                               fputc(*p, fp);
> > +                       else
> > +                               sprintf(&buf[i], "%c", *p);
> > +               } else if (isprint(*p) || isspace(*p))
> > +                       fputc(*p, fp);
> >                 else
> >                         fputc('.', fp);
> >         }
> >         /*
> >          * Try to demangle a mangled Rust symbol(calltrace) from log
> buffer
> >          */
> > -       char *p1 = strstr(buf, "_R");
> > -       if (!p1)
> > -               p1 = strstr(buf, "_ZN");
> > -       char *p2 = strrchr(buf, '+');
> > -       if (p1 && p2) {
> > -               char mangled[BUFSIZE] = {0};
> > -               char demangled[BUFSIZE] = {0};
> > -               char *res;
> > -               size_t slen = p1 - buf;
> > -
> > -               if (slen)
> > -                       memcpy(demangled, buf, slen);
> > -
> > -               memcpy(mangled, p1, p2-p1);
> > -               res = rust_demangle(mangled, DMGL_RUST);
> > -               if (res) {
> > -                       snprintf(demangled+slen, BUFSIZE-slen, "%s%s",
> res, p2);
> > -                       fprintf(fp, "%s",demangled);
> > -                       free(res);
> > -               }
> > -       } else
> > -               fprintf(fp, "%s", buf);
> > +       if (msg_flags & SHOW_LOG_RUST) {
> > +               char *p1 = strstr(buf, "_R");
> > +               if (!p1)
> > +                       p1 = strstr(buf, "_ZN");
> > +               char *p2 = strrchr(buf, '+');
> > +               if (p1 && p2) {
> > +                       char mangled[BUFSIZE] = {0};
> > +                       char demangled[BUFSIZE] = {0};
> > +                       char *res;
> > +                       size_t slen = p1 - buf;
> > +
> > +                       if (slen)
> > +                               memcpy(demangled, buf, slen);
> > +
> > +                       memcpy(mangled, p1, p2-p1);
> > +                       res = rust_demangle(mangled, DMGL_RUST);
> > +                       if (res) {
> > +                               snprintf(demangled+slen, BUFSIZE-slen,
> "%s%s", res, p2);
> > +                               fprintf(fp, "%s",demangled);
> > +                               free(res);
> > +                       } else
> > +                               fprintf(fp, "%s", buf);
> > +               } else
> > +                       fprintf(fp, "%s", buf);
> > +       }
> >
> >         if (msg_flags & SHOW_LOG_DICT) {
> >                 text = info + OFFSET(printk_info_dev_info) +
> > --
> > 2.50.1
> > --
> > Crash-utility mailing list -- [email protected]
> > To unsubscribe send an email to [email protected]
> > https://${domain_name}/admin/lists/devel.lists.crash-utility.osci.io/
> > Contribution Guidelines: https://github.com/crash-utility/crash/wiki
>
>
--
Crash-utility mailing list -- [email protected]
To unsubscribe send an email to [email protected]
https://${domain_name}/admin/lists/devel.lists.crash-utility.osci.io/
Contribution Guidelines: https://github.com/crash-utility/crash/wiki

Reply via email to