Hello Dave,
I was using ‘kmem �Cp’ to get status of memory. And I could only get
"PAGE PHYSICAL MAPPING INDEX CNT FLAGS" in 2.6.x kernel and later, which
makes me feel the lack of information. So I think of displaying
‘page._mapcount’ and ‘page.private’, when using ‘kmem -p’.
When adding these two items, I found ‘page._count’ is declared to be
atomic_t whose definition is:
typedef struct {
volatile int counter;
} atomic_t;
However, current crash codes use UINT to get the value of ‘page._count’.
The first patch (0001-kmem_p_6.0.2.patch) is used to change UINT to INT,
and the second one (0002-kmem_p_6.0.2.patch) will add the items talked
above. Both patches are based on crash 6.0.2.
BTW, I have tested these two patches on RHEL6.2_x86_64, RHEL6.2_i386,
RHEL5.8_x86_64 and RHEL5.8_i386.
--
Regards
Qiao Nuohan
diff --git a/defs.h b/defs.h
index 82d51e5..bcf8d6b 100755
--- a/defs.h
+++ b/defs.h
@@ -1184,6 +1184,8 @@ struct offset_table { /* stash of
commonly-used offsets */
long page_buffers;
long page_lru;
long page_pte;
+ long page_mapcount;
+ long page_private;
long swap_info_struct_swap_file;
long swap_info_struct_swap_vfsmnt;
long swap_info_struct_flags;
diff --git a/memory.c b/memory.c
index 9e8e7d0..15e2b0f 100755
--- a/memory.c
+++ b/memory.c
@@ -374,6 +374,12 @@ vm_init(void)
MEMBER_OFFSET_INIT(page_buffers, "page", "buffers");
MEMBER_OFFSET_INIT(page_lru, "page", "lru");
MEMBER_OFFSET_INIT(page_pte, "page", "pte");
+ MEMBER_OFFSET_INIT(page_mapcount, "page", "_mapcount");
+ if (INVALID_MEMBER(page_mapcount))
+ ANON_MEMBER_OFFSET_INIT(page_mapcount, "page", "_mapcount");
+ MEMBER_OFFSET_INIT(page_private, "page", "private");
+ if (INVALID_MEMBER(page_private))
+ ANON_MEMBER_OFFSET_INIT(page_private, "page", "private");
MEMBER_OFFSET_INIT(mm_struct_pgd, "mm_struct", "pgd");
@@ -4418,21 +4424,25 @@ dump_mem_map_SPARSEMEM(struct meminfo *mi)
ulong tmp, reserved, shared, slabs;
ulong PG_reserved_flag;
long buffers;
- ulong inode, offset, flags, mapping, index;
- int count;
+ ulong inode, offset, flags, mapping, index, private;
+ int count, mapcount;
int print_hdr, pg_spec, phys_spec, done;
int v22;
+ int v26;
char hdr[BUFSIZE];
char buf0[BUFSIZE];
char buf1[BUFSIZE];
char buf2[BUFSIZE];
char buf3[BUFSIZE];
char buf4[BUFSIZE];
+ char buf5[BUFSIZE];
char *page_cache;
char *pcache;
ulong section, section_nr, nr_mem_sections, section_size;
v22 = VALID_MEMBER(page_inode); /* page.inode vs. page.mapping */
+ v26 = VALID_MEMBER(page_mapcount) && VALID_MEMBER(page_private);
+ /* page._mapcount & page.private both exist in 2.6.9 kernel and later */
if (v22) {
sprintf(hdr, "%s%s%s%s%s%s%s%sCNT FLAGS\n",
@@ -4445,6 +4455,17 @@ dump_mem_map_SPARSEMEM(struct meminfo *mi)
space(MINSPACE),
mkstring(buf4, 8, CENTER|LJUST, "OFFSET"),
space(MINSPACE-1));
+ } else if (v26) {
+ sprintf(hdr, "%s%s%s%s%s%s%sCNT MCNT %s FLAGS\n",
+ mkstring(buf1, VADDR_PRLEN, CENTER, "PAGE"),
+ space(MINSPACE),
+ mkstring(buf2, MAX(PADDR_PRLEN, strlen("PHYSICAL")),
+ RJUST, "PHYSICAL"),
+ space(MINSPACE),
+ mkstring(buf3, VADDR_PRLEN, CENTER|RJUST, "MAPPING"),
+ space(MINSPACE),
+ mkstring(buf4, 8, CENTER|RJUST, "INDEX"),
+ mkstring(buf5, VADDR_PRLEN, CENTER|RJUST, "PRIVATE"));
} else {
sprintf(hdr, "%s%s%s%s%s%s%sCNT FLAGS\n",
mkstring(buf1, VADDR_PRLEN, CENTER, "PAGE"),
@@ -4519,6 +4540,8 @@ dump_mem_map_SPARSEMEM(struct meminfo *mi)
page_cache = GETBUF(SIZE(page) * PGMM_CACHED);
done = FALSE;
total_pages = 0;
+ mapcount = 0;
+ private = 0;
nr_mem_sections = NR_MEM_SECTIONS();
@@ -4611,6 +4634,10 @@ dump_mem_map_SPARSEMEM(struct meminfo *mi)
if (SIZE(page_flags) == 4)
flags &= 0xffffffff;
count = INT(pcache + OFFSET(page_count));
+ if (v26) {
+ mapcount = INT(pcache + OFFSET(page_mapcount));
+ private = ULONG(pcache + OFFSET(page_private));
+ }
switch (mi->flags)
{
@@ -4694,6 +4721,64 @@ dump_mem_map_SPARSEMEM(struct meminfo *mi)
offset,
count,
space(MINSPACE));
+ } else if (v26) {
+ if ((vt->flags & V_MEM_MAP)) {
+ if (!machdep->verify_paddr(phys))
+ phys_not_mapped = TRUE;
+ if (!kvtop(NULL, pp, NULL, 0))
+ page_not_mapped = TRUE;
+ }
+ if (page_not_mapped)
+ fprintf(fp, "%s%s%s%s%s%s%s %2s %4s %s ",
+ mkstring(buf0, VADDR_PRLEN,
+ LJUST|LONG_HEX, MKSTR(pp)),
+ space(MINSPACE),
+ mkstring(buf1, MAX(PADDR_PRLEN,
+ strlen("PHYSICAL")),
+ RJUST|LONGLONG_HEX, MKSTR(&phys)),
+ space(MINSPACE),
+ mkstring(buf3, VADDR_PRLEN,
+ CENTER|RJUST, " "),
+ space(MINSPACE),
+ mkstring(buf4, 8, CENTER|RJUST, " "),
+ " ",
+ " ",
+ mkstring(buf5, VADDR_PRLEN,
+ RJUST|LONG_HEX, " "));
+ else if (!page_mapping)
+ fprintf(fp, "%s%s%s%s%s%s%s %2d %4d %s ",
+ mkstring(buf0, VADDR_PRLEN,
+ LJUST|LONG_HEX, MKSTR(pp)),
+ space(MINSPACE),
+ mkstring(buf1, MAX(PADDR_PRLEN,
+ strlen("PHYSICAL")),
+ RJUST|LONGLONG_HEX, MKSTR(&phys)),
+ space(MINSPACE),
+ mkstring(buf3, VADDR_PRLEN,
+ CENTER|RJUST, "-------"),
+ space(MINSPACE),
+ mkstring(buf4, 8, CENTER|RJUST,
"-----"),
+ count,
+ mapcount,
+ mkstring(buf5, VADDR_PRLEN,
+ RJUST|LONG_HEX, MKSTR(private)));
+ else
+ fprintf(fp, "%s%s%s%s%s%s%8lx %2d %4d %s ",
+ mkstring(buf0, VADDR_PRLEN,
+ LJUST|LONG_HEX, MKSTR(pp)),
+ space(MINSPACE),
+ mkstring(buf1, MAX(PADDR_PRLEN,
+ strlen("PHYSICAL")),
+ RJUST|LONGLONG_HEX, MKSTR(&phys)),
+ space(MINSPACE),
+ mkstring(buf2, VADDR_PRLEN,
+ RJUST|LONG_HEX, MKSTR(mapping)),
+ space(MINSPACE),
+ index,
+ count,
+ mapcount,
+ mkstring(buf5, VADDR_PRLEN,
+ RJUST|LONG_HEX, MKSTR(private)));
} else {
if ((vt->flags & V_MEM_MAP)) {
if (!machdep->verify_paddr(phys))
@@ -4902,11 +4987,12 @@ dump_mem_map(struct meminfo *mi)
ulong tmp, reserved, shared, slabs;
ulong PG_reserved_flag;
long buffers;
- ulong inode, offset, flags, mapping, index;
+ ulong inode, offset, flags, mapping, index, private;
ulong node_size;
- int count;
+ int count, mapcount;
int print_hdr, pg_spec, phys_spec, done;
int v22;
+ int v26;
struct node_table *nt;
char hdr[BUFSIZE];
char buf0[BUFSIZE];
@@ -4914,6 +5000,7 @@ dump_mem_map(struct meminfo *mi)
char buf2[BUFSIZE];
char buf3[BUFSIZE];
char buf4[BUFSIZE];
+ char buf5[BUFSIZE];
char *page_cache;
char *pcache;
@@ -4923,6 +5010,8 @@ dump_mem_map(struct meminfo *mi)
}
v22 = VALID_MEMBER(page_inode); /* page.inode vs. page.mapping */
+ v26 = VALID_MEMBER(page_mapcount) && VALID_MEMBER(page_private);
+ /* page._mapcount & page.private both exist in 2.6.9 kernel and later */
if (v22) {
sprintf(hdr, "%s%s%s%s%s%s%s%sCNT FLAGS\n",
@@ -4935,6 +5024,17 @@ dump_mem_map(struct meminfo *mi)
space(MINSPACE),
mkstring(buf4, 8, CENTER|LJUST, "OFFSET"),
space(MINSPACE-1));
+ } else if (v26) {
+ sprintf(hdr, "%s%s%s%s%s%s%sCNT MCNT %s FLAGS\n",
+ mkstring(buf1, VADDR_PRLEN, CENTER, "PAGE"),
+ space(MINSPACE),
+ mkstring(buf2, MAX(PADDR_PRLEN, strlen("PHYSICAL")),
+ RJUST, "PHYSICAL"),
+ space(MINSPACE),
+ mkstring(buf3, VADDR_PRLEN, CENTER|RJUST, "MAPPING"),
+ space(MINSPACE),
+ mkstring(buf4, 8, CENTER|RJUST, "INDEX"),
+ mkstring(buf5, VADDR_PRLEN, CENTER|RJUST, "PRIVATE"));
} else {
sprintf(hdr, "%s%s%s%s%s%s%sCNT FLAGS\n",
mkstring(buf1, VADDR_PRLEN, CENTER, "PAGE"),
@@ -5009,6 +5109,8 @@ dump_mem_map(struct meminfo *mi)
page_cache = GETBUF(SIZE(page) * PGMM_CACHED);
done = FALSE;
total_pages = 0;
+ mapcount = 0;
+ private = 0;
for (n = 0; n < vt->numnodes; n++) {
if (print_hdr) {
@@ -5062,6 +5164,10 @@ dump_mem_map(struct meminfo *mi)
if (SIZE(page_flags) == 4)
flags &= 0xffffffff;
count = INT(pcache + OFFSET(page_count));
+ if (v26) {
+ mapcount = INT(pcache + OFFSET(page_mapcount));
+ private = ULONG(pcache + OFFSET(page_private));
+ }
switch (mi->flags)
{
@@ -5146,6 +5252,64 @@ dump_mem_map(struct meminfo *mi)
offset,
count,
space(MINSPACE));
+ } else if (v26) {
+ if ((vt->flags & V_MEM_MAP)) {
+ if (!machdep->verify_paddr(phys))
+ phys_not_mapped = TRUE;
+ if (!kvtop(NULL, pp, NULL, 0))
+ page_not_mapped = TRUE;
+ }
+ if (page_not_mapped)
+ fprintf(fp, "%s%s%s%s%s%s%s %2s %4s %s ",
+ mkstring(buf0, VADDR_PRLEN,
+ LJUST|LONG_HEX, MKSTR(pp)),
+ space(MINSPACE),
+ mkstring(buf1, MAX(PADDR_PRLEN,
+ strlen("PHYSICAL")),
+ RJUST|LONGLONG_HEX, MKSTR(&phys)),
+ space(MINSPACE),
+ mkstring(buf3, VADDR_PRLEN,
+ CENTER|RJUST, " "),
+ space(MINSPACE),
+ mkstring(buf4, 8, CENTER|RJUST, " "),
+ " ",
+ " ",
+ mkstring(buf5, VADDR_PRLEN,
+ RJUST|LONG_HEX, " "));
+ else if (!page_mapping)
+ fprintf(fp, "%s%s%s%s%s%s%s %2d %4d %s ",
+ mkstring(buf0, VADDR_PRLEN,
+ LJUST|LONG_HEX, MKSTR(pp)),
+ space(MINSPACE),
+ mkstring(buf1, MAX(PADDR_PRLEN,
+ strlen("PHYSICAL")),
+ RJUST|LONGLONG_HEX, MKSTR(&phys)),
+ space(MINSPACE),
+ mkstring(buf3, VADDR_PRLEN,
+ CENTER|RJUST, "-------"),
+ space(MINSPACE),
+ mkstring(buf4, 8, CENTER|RJUST,
"-----"),
+ count,
+ mapcount,
+ mkstring(buf5, VADDR_PRLEN,
+ RJUST|LONG_HEX, MKSTR(private)));
+ else
+ fprintf(fp, "%s%s%s%s%s%s%8lx %2d %4d %s ",
+ mkstring(buf0, VADDR_PRLEN,
+ LJUST|LONG_HEX, MKSTR(pp)),
+ space(MINSPACE),
+ mkstring(buf1, MAX(PADDR_PRLEN,
+ strlen("PHYSICAL")),
+ RJUST|LONGLONG_HEX, MKSTR(&phys)),
+ space(MINSPACE),
+ mkstring(buf2, VADDR_PRLEN,
+ RJUST|LONG_HEX, MKSTR(mapping)),
+ space(MINSPACE),
+ index,
+ count,
+ mapcount,
+ mkstring(buf5, VADDR_PRLEN,
+ RJUST|LONG_HEX, MKSTR(private)));
} else {
if ((vt->flags & V_MEM_MAP)) {
if (!machdep->verify_paddr(phys))
diff --git a/memory.c b/memory.c
index 95eefc9..9e8e7d0 100755
--- a/memory.c
+++ b/memory.c
@@ -4419,7 +4419,7 @@ dump_mem_map_SPARSEMEM(struct meminfo *mi)
ulong PG_reserved_flag;
long buffers;
ulong inode, offset, flags, mapping, index;
- uint count;
+ int count;
int print_hdr, pg_spec, phys_spec, done;
int v22;
char hdr[BUFSIZE];
@@ -4610,7 +4610,7 @@ dump_mem_map_SPARSEMEM(struct meminfo *mi)
flags = ULONG(pcache + OFFSET(page_flags));
if (SIZE(page_flags) == 4)
flags &= 0xffffffff;
- count = UINT(pcache + OFFSET(page_count));
+ count = INT(pcache + OFFSET(page_count));
switch (mi->flags)
{
@@ -4904,7 +4904,7 @@ dump_mem_map(struct meminfo *mi)
long buffers;
ulong inode, offset, flags, mapping, index;
ulong node_size;
- uint count;
+ int count;
int print_hdr, pg_spec, phys_spec, done;
int v22;
struct node_table *nt;
@@ -5061,7 +5061,7 @@ dump_mem_map(struct meminfo *mi)
flags = ULONG(pcache + OFFSET(page_flags));
if (SIZE(page_flags) == 4)
flags &= 0xffffffff;
- count = UINT(pcache + OFFSET(page_count));
+ count = INT(pcache + OFFSET(page_count));
switch (mi->flags)
{
--
Crash-utility mailing list
[email protected]
https://www.redhat.com/mailman/listinfo/crash-utility