[RFC PATCH 0/1] support lockless printk ringbuffer
by John Ogness
Hi Kazu,
Here is a patch adding full support for the new lockless printk
ringbuffer as it is currently being proposed. Note that the latest
version has not yet been submitted to LKML. I was waiting until I
finished tests with crash(8) and makedumpfile(8).
The new ringbuffer will export all the necessary symbols, sizes,
and offsets in VMCOREINFO.
Note that I created a separate printk.c for the iteration logic.
Also note that I modified dwarf_info.c to support resolving
typedefs of typedefs. This was necessary in order to support
atomic_long_t and its "counter" member.
I don't expect you to take the patch as-is, but I hope it can
provide some positive ground work for moving forward.
John Ogness (1):
printk: add support for lockless ringbuffer
Makefile | 2 +-
dwarf_info.c | 36 +++++++++-
makedumpfile.c | 101 ++++++++++++++++++++++++++--
makedumpfile.h | 25 +++++++
printk.c | 177 +++++++++++++++++++++++++++++++++++++++++++++++++
5 files changed, 333 insertions(+), 8 deletions(-)
create mode 100644 printk.c
--
2.20.1
4 years, 7 months
p_* commands
by Vasily Averin
Dear Dave,
RH knowledge base article shows nice p_* commands
https://access.redhat.com/solutions/4490051
crash> p_super_block ffff9ad87724f000
(struct super_block *)0xffff9ad87724f000 dm-15
.s_type - (struct file_system_type *)0xffffffffc1050460 - 'xfs'
.s_flags = 0x0000000030810001 - RDONLY | POSIXACL | I_VERSION | [NOSEC] | [BORN]
.s_blocksize - 4096
.s_root - (struct dentry *)0x0000000000000000
.s_bdev - (struct block_device *)0xffff9ab8431a8680
.bd_inode - (struct inode *)0xffff9ab8431a8770
.bd_super - (struct super_block *)0x0000000000000000
.bd_disk - (struct gendisk *)0xffff9ab878ace400 dm-15
.bd_queue - (struct request_queue *)0xffff9ab779be1330
.bd_mutex - (struct mutex *)0x0000000000000001 - not implemente
Do you know something about extension implemented this nice commend?
Cold you please find its author and ask him to publish it?
Thank you,
Vasily Averin
4 years, 7 months
crash help: using list for traversing pages through page.next
by Lin Feng
Hi all,
Recently I found an slub related problem(kmalloc-1024 objects eat tons of memory):
# ./slabinfo -l | grep "t-0001024"
:t-0001024 46448117 1024 47.5G 4074/505/11608097 4 0 0 99 *
Then I make the memroy coredump trying to find out why, it seems something wrong with
the slub's cpu_slab(kmem_cache_cpu) list. But as I want to walk through the page list
like following, crash seems can't identify:
crash> struct page.next,pages,pobjects 0xffffea0049e85140
next = 0xffffea0014533c40
pages = 13511054
pobjects = -545576266
crash> list page.next 0xffffea0049e85140
list: invalid argument: page.next
While my usage case is similar to the case in the 'help list' man page:
crash> p file_systems
file_systems = $1 = (struct file_system_type *) 0xc03adc90
crash> list file_system_type.next -s file_system_type.name,fs_flags c03adc90
So what is wrong, is there a way that I can walk through the page list?
thanks in advance~
linfeng
4 years, 7 months
ramdump support for va_bits_actual
by vinayak menon
Hi Dave,
Noticed that raw ramdumps of 5.4 kernel aren't working with crash tip.
With the patches attached, I could get it working. Please take a look.
Thanks,
Vinayak
4 years, 7 months
[PATCH v3] Determine the ARM64 kernel's Pointer Authentication mask value by reading the new KERNELPACMASK vmcoreinfo entry.
by Amit Daniel Kachhap
Pointer authentication support is added in the recent versions of the arm64
kernel. This basically add PAC bits to the top unused bits of the lr
register in the stack to prevent ROP kind of attack.
However the presence of PAC bits fails to match with the correct symbol
name. Hence a KERNELPACMASK field is added in the vmcoreinfo to help
in masking out this PAC details.
This patch fetches the KERNELPACMASK info and use it to mask the PAC bits
and generate correct backtrace and symbol name.
(amit.kachhap(a)arm.com)
---
Changes sice v2:
* Removed PAC mask check from arm64_is_kernel_exception_frame function
* More details in commit.
Changes since v1:
* Moved PAC mask code from arm64_print_stackframe_entry to
arm64_unwind_frame.
* PAC mask check on all kernel text during complete stack parsing
with bt -t <pid> command.
* dump_machdep_table now prints CONFIG_ARM64_KERNELPACMASK.
The kernel version for the corresponding vmcoreinfo entry is posted here[1].
[1]: https://lore.kernel.org/patchwork/patch/1211981/
arm64.c | 50 +++++++++++++++++++++++++++++++++++++++++---------
defs.h | 1 +
2 files changed, 42 insertions(+), 9 deletions(-)
diff --git a/arm64.c b/arm64.c
index 7662d71..e0a5cf2 100644
--- a/arm64.c
+++ b/arm64.c
@@ -84,6 +84,7 @@ static int arm64_get_kvaddr_ranges(struct vaddr_range *);
static void arm64_get_crash_notes(void);
static void arm64_calc_VA_BITS(void);
static int arm64_is_uvaddr(ulong, struct task_context *);
+static void arm64_calc_KERNELPACMASK(void);
/*
@@ -213,6 +214,7 @@ arm64_init(int when)
machdep->pagemask = ~((ulonglong)machdep->pageoffset);
arm64_calc_VA_BITS();
+ arm64_calc_KERNELPACMASK();
ms = machdep->machspec;
if (ms->VA_BITS_ACTUAL) {
ms->page_offset = ARM64_PAGE_OFFSET_ACTUAL;
@@ -472,6 +474,7 @@ arm64_init(int when)
case LOG_ONLY:
machdep->machspec = &arm64_machine_specific;
arm64_calc_VA_BITS();
+ arm64_calc_KERNELPACMASK();
arm64_calc_phys_offset();
machdep->machspec->page_offset = ARM64_PAGE_OFFSET;
break;
@@ -659,6 +662,11 @@ arm64_dump_machdep_table(ulong arg)
fprintf(fp, "%ld\n", ms->VA_BITS_ACTUAL);
else
fprintf(fp, "(unused)\n");
+ fprintf(fp, "CONFIG_ARM64_KERNELPACMASK: ");
+ if (ms->CONFIG_ARM64_KERNELPACMASK)
+ fprintf(fp, "%lx\n", ms->CONFIG_ARM64_KERNELPACMASK);
+ else
+ fprintf(fp, "(unused)\n");
fprintf(fp, " userspace_top: %016lx\n", ms->userspace_top);
fprintf(fp, " page_offset: %016lx\n", ms->page_offset);
fprintf(fp, " vmalloc_start_addr: %016lx\n", ms->vmalloc_start_addr);
@@ -1774,13 +1782,14 @@ static int
arm64_is_kernel_exception_frame(struct bt_info *bt, ulong stkptr)
{
struct arm64_pt_regs *regs;
+ struct machine_specific *ms = machdep->machspec;
regs = (struct arm64_pt_regs *)&bt->stackbuf[(ulong)(STACK_OFFSET_TYPE(stkptr))];
if (INSTACK(regs->sp, bt) && INSTACK(regs->regs[29], bt) &&
!(regs->pstate & (0xffffffff00000000ULL | PSR_MODE32_BIT)) &&
is_kernel_text(regs->pc) &&
- is_kernel_text(regs->regs[30])) {
+ is_kernel_text(regs->regs[30] | ms->CONFIG_ARM64_KERNELPACMASK)) {
switch (regs->pstate & PSR_MODE_MASK)
{
case PSR_MODE_EL1t:
@@ -1924,6 +1933,7 @@ arm64_print_stackframe_entry(struct bt_info *bt, int level, struct arm64_stackfr
* See, for example, "bl schedule" before ret_to_user().
*/
branch_pc = frame->pc - 4;
+
name = closest_symbol(branch_pc);
name_plus_offset = NULL;
@@ -2135,7 +2145,7 @@ arm64_unwind_frame(struct bt_info *bt, struct arm64_stackframe *frame)
unsigned long stack_mask;
unsigned long irq_stack_ptr, orig_sp;
struct arm64_pt_regs *ptregs;
- struct machine_specific *ms;
+ struct machine_specific *ms = machdep->machspec;
stack_mask = (unsigned long)(ARM64_STACK_SIZE) - 1;
fp = frame->fp;
@@ -2149,6 +2159,8 @@ arm64_unwind_frame(struct bt_info *bt, struct arm64_stackframe *frame)
frame->sp = fp + 0x10;
frame->fp = GET_STACK_ULONG(fp);
frame->pc = GET_STACK_ULONG(fp + 8);
+ if (is_kernel_text(frame->pc | ms->CONFIG_ARM64_KERNELPACMASK))
+ frame->pc |= ms->CONFIG_ARM64_KERNELPACMASK;
if ((frame->fp == 0) && (frame->pc == 0))
return FALSE;
@@ -2200,7 +2212,6 @@ arm64_unwind_frame(struct bt_info *bt, struct arm64_stackframe *frame)
* irq_stack_ptr = IRQ_STACK_PTR(raw_smp_processor_id());
* orig_sp = IRQ_STACK_TO_TASK_STACK(irq_stack_ptr); (pt_regs pointer on process stack)
*/
- ms = machdep->machspec;
irq_stack_ptr = ms->irq_stacks[bt->tc->processor] + ms->irq_stack_size - 16;
if (frame->sp == irq_stack_ptr) {
@@ -2802,6 +2813,8 @@ arm64_print_text_symbols(struct bt_info *bt, struct arm64_stackframe *frame, FIL
char buf2[BUFSIZE];
char *name;
ulong start;
+ ulong val;
+ struct machine_specific *ms = machdep->machspec;
if (bt->flags & BT_TEXT_SYMBOLS_ALL)
start = bt->stackbase;
@@ -2816,8 +2829,10 @@ arm64_print_text_symbols(struct bt_info *bt, struct arm64_stackframe *frame, FIL
for (i = (start - bt->stackbase)/sizeof(ulong); i < LONGS_PER_STACK; i++) {
up = (ulong *)(&bt->stackbuf[i*sizeof(ulong)]);
- if (is_kernel_text(*up)) {
- name = closest_symbol(*up);
+ val = *up;
+ if (is_kernel_text(val | ms->CONFIG_ARM64_KERNELPACMASK)) {
+ val |= ms->CONFIG_ARM64_KERNELPACMASK;
+ name = closest_symbol(val);
fprintf(ofp, " %s[%s] %s at %lx",
bt->flags & BT_ERROR_MASK ?
" " : "",
@@ -2826,13 +2841,13 @@ arm64_print_text_symbols(struct bt_info *bt, struct arm64_stackframe *frame, FIL
MKSTR(bt->stackbase +
(i * sizeof(long)))),
bt->flags & BT_SYMBOL_OFFSET ?
- value_to_symstr(*up, buf2, bt->radix) :
- name, *up);
- if (module_symbol(*up, NULL, &lm, NULL, 0))
+ value_to_symstr(val, buf2, bt->radix) :
+ name, val);
+ if (module_symbol(val, NULL, &lm, NULL, 0))
fprintf(ofp, " [%s]", lm->mod_name);
fprintf(ofp, "\n");
if (BT_REFERENCE_CHECK(bt))
- arm64_do_bt_reference_check(bt, *up, name);
+ arm64_do_bt_reference_check(bt, val, name);
}
}
}
@@ -3135,6 +3150,7 @@ arm64_print_exception_frame(struct bt_info *bt, ulong pt_regs, int mode, FILE *o
struct syment *sp;
ulong LR, SP, offset;
char buf[BUFSIZE];
+ struct machine_specific *ms = machdep->machspec;
if (CRASHDEBUG(1))
fprintf(ofp, "pt_regs: %lx\n", pt_regs);
@@ -3150,6 +3166,8 @@ arm64_print_exception_frame(struct bt_info *bt, ulong pt_regs, int mode, FILE *o
rows = 4;
} else {
LR = regs->regs[30];
+ if (is_kernel_text (LR | ms->CONFIG_ARM64_KERNELPACMASK))
+ LR |= ms->CONFIG_ARM64_KERNELPACMASK;
SP = regs->sp;
top_reg = 29;
is_64_bit = TRUE;
@@ -4058,6 +4076,20 @@ arm64_swp_offset(ulong pte)
return pte;
}
+static void arm64_calc_KERNELPACMASK(void)
+{
+ ulong value;
+ char *string;
+
+ if ((string = pc->read_vmcoreinfo("NUMBER(KERNELPACMASK)"))) {
+ value = htol(string, QUIET, NULL);
+ free(string);
+ machdep->machspec->CONFIG_ARM64_KERNELPACMASK = value;
+ if (CRASHDEBUG(1))
+ fprintf(fp, "CONFIG_ARM64_KERNELPACMASK=%lx\n", value);
+ }
+}
+
#endif /* ARM64 */
diff --git a/defs.h b/defs.h
index ac24a5d..4c3e509 100644
--- a/defs.h
+++ b/defs.h
@@ -3263,6 +3263,7 @@ struct machine_specific {
ulong machine_kexec_end;
ulong VA_BITS_ACTUAL;
ulong CONFIG_ARM64_VA_BITS;
+ ulong CONFIG_ARM64_KERNELPACMASK;
ulong VA_START;
};
--
2.17.1
4 years, 7 months
[PATCH v2] Determine the ARM64 kernel's Pointer Authentication mask value by reading the new KERNELPACMASK vmcoreinfo entry.
by Amit Daniel Kachhap
This value is used to mask the PAC bits and generate correct backtrace
and symbol name.
(amit.kachhap(a)arm.com)
---
Changes since v1:
* Moved PAC mask code from arm64_print_stackframe_entry to
arm64_unwind_frame.
* PAC mask check on all kernel text during complete stack parsing
with bt -t <pid> command.
* dump_machdep_table now prints CONFIG_ARM64_KERNELPACMASK.
The kernel version for the corresponding vmcoreinfo entry is posted here[1].
[1]: https://lore.kernel.org/patchwork/patch/1211981/
arm64.c | 52 ++++++++++++++++++++++++++++++++++++++++++----------
defs.h | 1 +
2 files changed, 43 insertions(+), 10 deletions(-)
diff --git a/arm64.c b/arm64.c
index 7662d71..326b8e0 100644
--- a/arm64.c
+++ b/arm64.c
@@ -84,6 +84,7 @@ static int arm64_get_kvaddr_ranges(struct vaddr_range *);
static void arm64_get_crash_notes(void);
static void arm64_calc_VA_BITS(void);
static int arm64_is_uvaddr(ulong, struct task_context *);
+static void arm64_calc_KERNELPACMASK(void);
/*
@@ -213,6 +214,7 @@ arm64_init(int when)
machdep->pagemask = ~((ulonglong)machdep->pageoffset);
arm64_calc_VA_BITS();
+ arm64_calc_KERNELPACMASK();
ms = machdep->machspec;
if (ms->VA_BITS_ACTUAL) {
ms->page_offset = ARM64_PAGE_OFFSET_ACTUAL;
@@ -472,6 +474,7 @@ arm64_init(int when)
case LOG_ONLY:
machdep->machspec = &arm64_machine_specific;
arm64_calc_VA_BITS();
+ arm64_calc_KERNELPACMASK();
arm64_calc_phys_offset();
machdep->machspec->page_offset = ARM64_PAGE_OFFSET;
break;
@@ -659,6 +662,11 @@ arm64_dump_machdep_table(ulong arg)
fprintf(fp, "%ld\n", ms->VA_BITS_ACTUAL);
else
fprintf(fp, "(unused)\n");
+ fprintf(fp, "CONFIG_ARM64_KERNELPACMASK: ");
+ if (ms->CONFIG_ARM64_KERNELPACMASK)
+ fprintf(fp, "%lx\n", ms->CONFIG_ARM64_KERNELPACMASK);
+ else
+ fprintf(fp, "(unused)\n");
fprintf(fp, " userspace_top: %016lx\n", ms->userspace_top);
fprintf(fp, " page_offset: %016lx\n", ms->page_offset);
fprintf(fp, " vmalloc_start_addr: %016lx\n", ms->vmalloc_start_addr);
@@ -1774,13 +1782,14 @@ static int
arm64_is_kernel_exception_frame(struct bt_info *bt, ulong stkptr)
{
struct arm64_pt_regs *regs;
+ struct machine_specific *ms = machdep->machspec;
regs = (struct arm64_pt_regs *)&bt->stackbuf[(ulong)(STACK_OFFSET_TYPE(stkptr))];
if (INSTACK(regs->sp, bt) && INSTACK(regs->regs[29], bt) &&
!(regs->pstate & (0xffffffff00000000ULL | PSR_MODE32_BIT)) &&
- is_kernel_text(regs->pc) &&
- is_kernel_text(regs->regs[30])) {
+ is_kernel_text(regs->pc | ms->CONFIG_ARM64_KERNELPACMASK) &&
+ is_kernel_text(regs->regs[30] | ms->CONFIG_ARM64_KERNELPACMASK)) {
switch (regs->pstate & PSR_MODE_MASK)
{
case PSR_MODE_EL1t:
@@ -1924,6 +1933,7 @@ arm64_print_stackframe_entry(struct bt_info *bt, int level, struct arm64_stackfr
* See, for example, "bl schedule" before ret_to_user().
*/
branch_pc = frame->pc - 4;
+
name = closest_symbol(branch_pc);
name_plus_offset = NULL;
@@ -2135,7 +2145,7 @@ arm64_unwind_frame(struct bt_info *bt, struct arm64_stackframe *frame)
unsigned long stack_mask;
unsigned long irq_stack_ptr, orig_sp;
struct arm64_pt_regs *ptregs;
- struct machine_specific *ms;
+ struct machine_specific *ms = machdep->machspec;
stack_mask = (unsigned long)(ARM64_STACK_SIZE) - 1;
fp = frame->fp;
@@ -2149,6 +2159,8 @@ arm64_unwind_frame(struct bt_info *bt, struct arm64_stackframe *frame)
frame->sp = fp + 0x10;
frame->fp = GET_STACK_ULONG(fp);
frame->pc = GET_STACK_ULONG(fp + 8);
+ if (is_kernel_text(frame->pc | ms->CONFIG_ARM64_KERNELPACMASK))
+ frame->pc |= ms->CONFIG_ARM64_KERNELPACMASK;
if ((frame->fp == 0) && (frame->pc == 0))
return FALSE;
@@ -2200,7 +2212,6 @@ arm64_unwind_frame(struct bt_info *bt, struct arm64_stackframe *frame)
* irq_stack_ptr = IRQ_STACK_PTR(raw_smp_processor_id());
* orig_sp = IRQ_STACK_TO_TASK_STACK(irq_stack_ptr); (pt_regs pointer on process stack)
*/
- ms = machdep->machspec;
irq_stack_ptr = ms->irq_stacks[bt->tc->processor] + ms->irq_stack_size - 16;
if (frame->sp == irq_stack_ptr) {
@@ -2802,6 +2813,8 @@ arm64_print_text_symbols(struct bt_info *bt, struct arm64_stackframe *frame, FIL
char buf2[BUFSIZE];
char *name;
ulong start;
+ ulong val;
+ struct machine_specific *ms = machdep->machspec;
if (bt->flags & BT_TEXT_SYMBOLS_ALL)
start = bt->stackbase;
@@ -2816,8 +2829,10 @@ arm64_print_text_symbols(struct bt_info *bt, struct arm64_stackframe *frame, FIL
for (i = (start - bt->stackbase)/sizeof(ulong); i < LONGS_PER_STACK; i++) {
up = (ulong *)(&bt->stackbuf[i*sizeof(ulong)]);
- if (is_kernel_text(*up)) {
- name = closest_symbol(*up);
+ val = *up;
+ if (is_kernel_text(val | ms->CONFIG_ARM64_KERNELPACMASK)) {
+ val |= ms->CONFIG_ARM64_KERNELPACMASK;
+ name = closest_symbol(val);
fprintf(ofp, " %s[%s] %s at %lx",
bt->flags & BT_ERROR_MASK ?
" " : "",
@@ -2826,13 +2841,13 @@ arm64_print_text_symbols(struct bt_info *bt, struct arm64_stackframe *frame, FIL
MKSTR(bt->stackbase +
(i * sizeof(long)))),
bt->flags & BT_SYMBOL_OFFSET ?
- value_to_symstr(*up, buf2, bt->radix) :
- name, *up);
- if (module_symbol(*up, NULL, &lm, NULL, 0))
+ value_to_symstr(val, buf2, bt->radix) :
+ name, val);
+ if (module_symbol(val, NULL, &lm, NULL, 0))
fprintf(ofp, " [%s]", lm->mod_name);
fprintf(ofp, "\n");
if (BT_REFERENCE_CHECK(bt))
- arm64_do_bt_reference_check(bt, *up, name);
+ arm64_do_bt_reference_check(bt, val, name);
}
}
}
@@ -3135,6 +3150,7 @@ arm64_print_exception_frame(struct bt_info *bt, ulong pt_regs, int mode, FILE *o
struct syment *sp;
ulong LR, SP, offset;
char buf[BUFSIZE];
+ struct machine_specific *ms = machdep->machspec;
if (CRASHDEBUG(1))
fprintf(ofp, "pt_regs: %lx\n", pt_regs);
@@ -3150,6 +3166,8 @@ arm64_print_exception_frame(struct bt_info *bt, ulong pt_regs, int mode, FILE *o
rows = 4;
} else {
LR = regs->regs[30];
+ if (is_kernel_text (LR | ms->CONFIG_ARM64_KERNELPACMASK))
+ LR |= ms->CONFIG_ARM64_KERNELPACMASK;
SP = regs->sp;
top_reg = 29;
is_64_bit = TRUE;
@@ -4058,6 +4076,20 @@ arm64_swp_offset(ulong pte)
return pte;
}
+static void arm64_calc_KERNELPACMASK(void)
+{
+ ulong value;
+ char *string;
+
+ if ((string = pc->read_vmcoreinfo("NUMBER(KERNELPACMASK)"))) {
+ value = htol(string, QUIET, NULL);
+ free(string);
+ machdep->machspec->CONFIG_ARM64_KERNELPACMASK = value;
+ if (CRASHDEBUG(1))
+ fprintf(fp, "CONFIG_ARM64_KERNELPACMASK=%lx\n", value);
+ }
+}
+
#endif /* ARM64 */
diff --git a/defs.h b/defs.h
index ac24a5d..4c3e509 100644
--- a/defs.h
+++ b/defs.h
@@ -3263,6 +3263,7 @@ struct machine_specific {
ulong machine_kexec_end;
ulong VA_BITS_ACTUAL;
ulong CONFIG_ARM64_VA_BITS;
+ ulong CONFIG_ARM64_KERNELPACMASK;
ulong VA_START;
};
--
2.17.1
4 years, 7 months
Strip llvm text symbol name ending
by 赵乾利
Hi
I found an issue when the kernel build by LLVM,many symbol missing,such as irq_desc_tree,causes irq -s command execution failed ,so i add llvm to strip_symbol_end:
Issue fix after applying the patch
crash> irq -s
CPU0 CPU1 CPU2 CPU3 CPU4 CPU5 CPU6 CPU7
irq: neither irq_desc, _irq_desc, irq_desc_ptrs or irq_desc_tree symbols exist
crash> sym irq_desc_tree
symbol not found: irq_desc_tree
possible alternatives:
ffffffd44bcbbf60 (d) irq_desc_tree.llvm.7481403593665956221
diff --git a/symbols.c b/symbols.c
index 449d6d4..3b1f08a 100644
--- a/symbols.c
+++ b/symbols.c
@@ -540,30 +540,28 @@ get_text_init_space(void)
static char *
strip_symbol_end(const char *name, char *buf)
{
+ int i;
char *p;
+ char *strip[] = {
+ ".isra.",
+ ".part.",
+ ".llvm.",
+ NULL
+ };
if (st->flags & NO_STRIP)
return (char *)name;
- if ((p = strstr(name, ".isra."))) {
- if (buf) {
- strcpy(buf, name);
- buf[p-name] = NULLCHAR;
- return buf;
- } else {
- *p = NULLCHAR;
- return (char *)name;
- }
- }
-
- if ((p = strstr(name, ".part."))) {
- if (buf) {
- strcpy(buf, name);
- buf[p-name] = NULLCHAR;
- return buf;
- } else {
- *p = NULLCHAR;
- return (char *)name;
+ for (i = 0; strip[i]; i++) {
+ if ((p = strstr(name, strip[i]))) {
+ if (buf) {
+ strcpy(buf, name);
+ buf[p-name] = NULLCHAR;
+ return buf;
+ } else {
+ *p = NULLCHAR;
+ return (char *)name;
+ }
}
}
#/******本邮件及其附件含有小米公司的保密信息,仅限于发送给上面地址中列出的个人或群组。禁止任何其他人以任何形式使用(包括但不限于全部或部分地泄露、复制、或散发)本邮件中的信息。如果您错收了本邮件,请您立即电话或邮件通知发件人并删除本邮件! This e-mail and its attachments contain confidential information from XIAOMI, which is intended only for the person or entity whose address is listed above. Any use of the information contained herein in any way (including, but not limited to, total or partial disclosure, reproduction, or dissemination) by persons other than the intended recipient(s) is prohibited. If you receive this e-mail in error, please notify the sender by phone or email immediately and delete it!******/#
4 years, 7 months
[PATCH v2] add log -T option to display the message text with human readable timestamp
by Wang Long
Sometimes, we need to know the accurate time of the log, which
helps us analyze the problem.
add -T option(like dmesg -T command) for log command to display
the message text with human readable timestamp.
Signed-off-by: Wang Long <w(a)laoqinren.net>
---
defs.h | 2 ++
help.c | 28 +++++++++++++++++++++++++++-
kernel.c | 23 +++++++++++++++++++++--
3 files changed, 50 insertions(+), 3 deletions(-)
diff --git a/defs.h b/defs.h
index d8eda5e..4e57a56 100644
--- a/defs.h
+++ b/defs.h
@@ -763,6 +763,7 @@ struct kernel_table { /* kernel data */
} vmcoreinfo;
ulonglong flags2;
char *source_tree;
+ struct timespec boot_date;
};
/*
@@ -5577,6 +5578,7 @@ void dump_log(int);
#define SHOW_LOG_DICT (0x2)
#define SHOW_LOG_TEXT (0x4)
#define SHOW_LOG_AUDIT (0x8)
+#define SHOW_LOG_CTIME (0x10)
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 c443cad..1ee70f7 100644
--- a/help.c
+++ b/help.c
@@ -3892,12 +3892,13 @@ NULL
char *help_log[] = {
"log",
"dump system message buffer",
-"[-tdma]",
+"[-Ttdma]",
" 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",
" record format, where the timestamp is contained in each log entry's header.",
" ",
+" -T Display the message text with human readable timestamp.",
" -t Display the message text without the timestamp; only applicable to the",
" variable-length record format.",
" -d Display the dictionary of key/value pair properties that are optionally",
@@ -4031,6 +4032,31 @@ char *help_log[] = {
" type=1307 audit(1489384479.809:4346): cwd=\"/proc\"",
" ...",
" ",
+" Display the message text with human readable timestamp.\n"
+" %s> log -T",
+" [Sat Apr 4 07:41:09 2020] BIOS-e820: [mem 0x0000000000000000-0x000000000009fbff] usable",
+" [Sat Apr 4 07:41:09 2020] BIOS-e820: [mem 0x000000000009fc00-0x000000000009ffff] reserved",
+" [Sat Apr 4 07:41:09 2020] BIOS-e820: [mem 0x00000000000f0000-0x00000000000fffff] reserved",
+" [Sat Apr 4 07:41:09 2020] BIOS-e820: [mem 0x0000000000100000-0x00000000dffeffff] usable",
+" [Sat Apr 4 07:41:09 2020] BIOS-e820: [mem 0x00000000dfff0000-0x00000000dfffffff] ACPI data",
+" [Sat Apr 4 07:41:09 2020] BIOS-e820: [mem 0x00000000fec00000-0x00000000fec00fff] reserved",
+" [Sat Apr 4 07:41:09 2020] BIOS-e820: [mem 0x00000000fee00000-0x00000000fee00fff] reserved",
+" [Sat Apr 4 07:41:09 2020] BIOS-e820: [mem 0x00000000fffc0000-0x00000000ffffffff] reserved",
+" [Sat Apr 4 07:41:09 2020] BIOS-e820: [mem 0x0000000100000000-0x000000011fffffff] usable",
+" [Sat Apr 4 07:41:09 2020] NX (Execute Disable) protection: active",
+" [Sat Apr 4 07:41:09 2020] SMBIOS 2.5 present.",
+" [Sat Apr 4 07:41:09 2020] DMI: innotek GmbH VirtualBox/VirtualBox, BIOS VirtualBox 12/01/2006",
+" [Sat Apr 4 07:41:09 2020] Hypervisor detected: KVM",
+" [Sat Apr 4 07:41:09 2020] kvm-clock: Using msrs 4b564d01 and 4b564d00",
+" [Sat Apr 4 07:41:09 2020] kvm-clock: cpu 0, msr 6de01001, primary cpu clock",
+" [Sat Apr 4 07:41:09 2020] kvm-clock: using sched offset of 11838753697 cycles",
+" [Sat Apr 4 07:41:09 2020] clocksource: kvm-clock: mask: 0xffffffffffffffff max_cycles: 0x1cd42e4dffb, max_idle_ns: 881590591483 ns",
+" [Sat Apr 4 07:41:09 2020] e820: update [mem 0x00000000-0x00000fff] usable ==> reserved",
+" [Sat Apr 4 07:41:09 2020] e820: remove [mem 0x000a0000-0x000fffff] usable",
+" [Sat Apr 4 07:41:09 2020] last_pfn = 0x120000 max_arch_pfn = 0x400000000",
+" [Sat Apr 4 07:41:09 2020] MTRR default type: uncachable",
+" [Sat Apr 4 07:41:09 2020] MTRR variable ranges disabled:",
+" ...",
NULL
};
diff --git a/kernel.c b/kernel.c
index 7604fac..7e68e6d 100644
--- a/kernel.c
+++ b/kernel.c
@@ -4912,9 +4912,12 @@ cmd_log(void)
msg_flags = 0;
- while ((c = getopt(argcnt, args, "tdma")) != EOF) {
+ while ((c = getopt(argcnt, args, "Ttdma")) != EOF) {
switch(c)
{
+ case 'T':
+ msg_flags |= SHOW_LOG_CTIME;
+ break;
case 't':
msg_flags |= SHOW_LOG_TEXT;
break;
@@ -4936,6 +4939,15 @@ cmd_log(void)
if (argerrs)
cmd_usage(pc->curcmd, SYNOPSIS);
+ if (kt->boot_date.tv_sec == 0) {
+ ulonglong uptime_jiffies;
+ ulong uptime_sec;
+ get_uptime(NULL, &uptime_jiffies);
+ uptime_sec = (uptime_jiffies)/(ulonglong)machdep->hz;
+ kt->boot_date.tv_sec = kt->date.tv_sec - uptime_sec;
+ kt->boot_date.tv_nsec = 0;
+ }
+
if (msg_flags & SHOW_LOG_AUDIT) {
dump_audit();
return;
@@ -5154,7 +5166,12 @@ dump_log_entry(char *logptr, int msg_flags)
if ((msg_flags & SHOW_LOG_TEXT) == 0) {
nanos = (ulonglong)ts_nsec / (ulonglong)1000000000;
rem = (ulonglong)ts_nsec % (ulonglong)1000000000;
- sprintf(buf, "[%5lld.%06ld] ", nanos, rem/1000);
+ if (msg_flags & SHOW_LOG_CTIME) {
+ time_t t = kt->boot_date.tv_sec + nanos;
+ sprintf(buf, "[%s] ", strip_linefeeds(ctime(&t)));
+ }
+ else
+ sprintf(buf, "[%5lld.%06ld] ", nanos, rem/1000);
ilen = strlen(buf);
fprintf(fp, "%s", buf);
}
@@ -6018,6 +6035,8 @@ dump_kernel_table(int verbose)
get_xtime(&kt->date);
fprintf(fp, " date: %s\n",
strip_linefeeds(ctime(&kt->date.tv_sec)));
+ fprintf(fp, " boot_ date: %s\n",
+ strip_linefeeds(ctime(&kt->boot_date.tv_sec)));
fprintf(fp, " proc_version: %s\n", strip_linefeeds(kt->proc_version));
fprintf(fp, " new_utsname: \n");
fprintf(fp, " .sysname: %s\n", uts->sysname);
--
1.8.3.1
4 years, 7 months
[PATCH] Determine the ARM64 kernel's Pointer Authentication mask value by reading the new KERNELPACMASK vmcoreinfo entry.
by Amit Daniel Kachhap
This value is used to mask the PAC bits and generate correct backtrace.
(amit.kachhap(a)arm.com)
---
The kernel version for the corresponding vmcoreinfo entry is posted here[1].
[1]: https://lore.kernel.org/patchwork/patch/1211981/
arm64.c | 20 ++++++++++++++++++++
defs.h | 1 +
2 files changed, 21 insertions(+)
diff --git a/arm64.c b/arm64.c
index 09b1b76..55e084f 100644
--- a/arm64.c
+++ b/arm64.c
@@ -84,6 +84,7 @@ static int arm64_get_kvaddr_ranges(struct vaddr_range *);
static void arm64_get_crash_notes(void);
static void arm64_calc_VA_BITS(void);
static int arm64_is_uvaddr(ulong, struct task_context *);
+static void arm64_calc_KERNELPACMASK(void);
/*
@@ -213,6 +214,7 @@ arm64_init(int when)
machdep->pagemask = ~((ulonglong)machdep->pageoffset);
arm64_calc_VA_BITS();
+ arm64_calc_KERNELPACMASK();
ms = machdep->machspec;
if (ms->VA_BITS_ACTUAL) {
ms->page_offset = ARM64_PAGE_OFFSET_ACTUAL;
@@ -472,6 +474,7 @@ arm64_init(int when)
case LOG_ONLY:
machdep->machspec = &arm64_machine_specific;
arm64_calc_VA_BITS();
+ arm64_calc_KERNELPACMASK();
arm64_calc_phys_offset();
machdep->machspec->page_offset = ARM64_PAGE_OFFSET;
break;
@@ -1925,6 +1928,7 @@ arm64_print_stackframe_entry(struct bt_info *bt, int level, struct arm64_stackfr
struct syment *sp;
struct load_module *lm;
char buf[BUFSIZE];
+ struct machine_specific *ms = machdep->machspec;
/*
* if pc comes from a saved lr, it actually points to an instruction
@@ -1932,6 +1936,9 @@ arm64_print_stackframe_entry(struct bt_info *bt, int level, struct arm64_stackfr
* See, for example, "bl schedule" before ret_to_user().
*/
branch_pc = frame->pc - 4;
+ if (ms->CONFIG_ARM64_KERNELPACMASK)
+ branch_pc |= ms->CONFIG_ARM64_KERNELPACMASK;
+
name = closest_symbol(branch_pc);
name_plus_offset = NULL;
@@ -4070,6 +4077,19 @@ arm64_swp_offset(ulong pte)
return pte;
}
+static void arm64_calc_KERNELPACMASK(void)
+{
+ ulong value;
+ char *string;
+
+ if ((string = pc->read_vmcoreinfo("NUMBER(KERNELPACMASK)"))) {
+ value = htol(string, QUIET, NULL);
+ free(string);
+ machdep->machspec->CONFIG_ARM64_KERNELPACMASK = value;
+ }
+ fprintf(fp, " got NUMBER(KERNELPACMASK) =%llx\n", value);
+}
+
#endif /* ARM64 */
diff --git a/defs.h b/defs.h
index a3f828d..f37a957 100644
--- a/defs.h
+++ b/defs.h
@@ -3269,6 +3269,7 @@ struct machine_specific {
ulong machine_kexec_end;
ulong VA_BITS_ACTUAL;
ulong CONFIG_ARM64_VA_BITS;
+ ulong CONFIG_ARM64_KERNELPACMASK;
ulong VA_START;
};
--
2.7.4
4 years, 7 months
Re: [Crash-utility] [PATCH] add log -T option to display the message text with human readable timestamp
by Dave Anderson
----- Original Message -----
>
>
> On 20/4/2020 3:48 am, Dave Anderson wrote:
> >
> > FWIW, I tried it on another RHEL7 machine running live,
> > but then also on a RHEL8 kernel dumpfile, and they all hang:
>
> I apply this patch on RHEL7 virtual machine(VirtualBbox) and it work ok.
> and on a RHEL7 kernel dumpfile, I found it hang after I send the patch.
>
>
> and I debug it and found the machdep->hz == 0 on the following:
>
> get_uptime(NULL, &uptime_jiffies);
> uptime_sec = (uptime_jiffies)/(ulonglong)machdep->hz;
> kt->boot_date.tv_sec = kt->date.tv_sec - uptime_sec;
> kt->boot_date.tv_nsec = 0;
>
> because machdep-> hz has not been initialized here. divide by zero make
> the cpu spinning at 100%.
>
> I thought two solutions:
>
> (1) add misc_init function after machdep_init(POST_INIT) call, and
> calculate the value of kt-> boot_date in it.
> read_in_kernel_config(IKCFG_INIT);
> kernel_init();
> machdep_init(POST_GDB);
> vm_init();
> machdep_init(POST_VM);
> module_init();
> help_init();
> task_init();
> vfs_init();
> net_init();
> dev_init();
> machdep_init(POST_INIT);
> + misc_init();
>
> (2) calculate the value of kt-> boot_date on cmd_log function, when we
> call log command.
>
>
> Dave, Which one do you like?
Definitely option #2. Since it's not required unless your new command option is run,
you can simply check whether the new boot_date structure is still zero-filled, and do
your initialization at that time.
And BTW, please move the boot_date structure to the end of the kernel_table
to prevent any possible breakage of previously-compiled extension modules
that use the kernel_table. And also can you please display the new structure's
contents in dump_kernel_table()? You can put the display under the current
"date" display.
Thanks,
Dave
4 years, 7 months