----- Original Message -----
> From: Masayoshi Mizuma <m.miz...@jp.fujitsu.com>
> 
> Update for the "kmem -n" option to also dump memory block.
> Currently, "kmem -n" shows the memory section only. This
> patch gets available the memory block as well if 'memory_block'
> structure and 'memory_subsys' symbol exist.
> The memory block information is useful to investigate memory
> hot-plug issue.


Hello Masa,

First let me say that I appreciate the work you've done to add this new 
information.

However, I don't like the new output format...

Taking a simple example, the current display looks like this:

NR      SECTION        CODED_MEM_MAP        MEM_MAP       PFN
 0  ffff880002664000  ffffea0000000000  ffffea0000000000  0
 1  ffff880002664020  ffffea0000000000  ffffea0000340000  32768
 2  ffff880002664040  ffffea0000000000  ffffea0000680000  65536
 3  ffff880002664060  ffffea0000000000  ffffea00009c0000  98304
 4  ffff880002664080  ffffea0000000000  ffffea0000d00000  131072
 5  ffff8800026640a0  ffffea0000000000  ffffea0001040000  163840
 6  ffff8800026640c0  ffffea0000000000  ffffea0001380000  196608
 7  ffff8800026640e0  ffffea0000000000  ffffea00016c0000  229376

With your patch on a system without memory blocks, it looks like this:

NR         SECTION        CODED_MEM_MAP        MEM_MAP           PFN      STATE
    0  ffff880002664000  ffffea0000000000  ffffea0000000000  0            
PRESENT|HAS_MEMMAP
    1  ffff880002664020  ffffea0000000000  ffffea0000340000  32768        
PRESENT|HAS_MEMMAP
    2  ffff880002664040  ffffea0000000000  ffffea0000680000  65536        
PRESENT|HAS_MEMMAP
    3  ffff880002664060  ffffea0000000000  ffffea00009c0000  98304        
PRESENT|HAS_MEMMAP
    4  ffff880002664080  ffffea0000000000  ffffea0000d00000  131072       
PRESENT|HAS_MEMMAP
    5  ffff8800026640a0  ffffea0000000000  ffffea0001040000  163840       
PRESENT|HAS_MEMMAP
    6  ffff8800026640c0  ffffea0000000000  ffffea0001380000  196608       
PRESENT|HAS_MEMMAP
    7  ffff8800026640e0  ffffea0000000000  ffffea00016c0000  229376       
PRESENT|HAS_MEMMAP

Your patch stretches the output well beyond the preferred 80 column maximum,
which I try to avoid if at all possible.

Could you please:

 (1) restore the original display size w/respect to the "NR" column
 (2) restore the left-justified "PFN" header string.
 (3) put the new "STATE" column as a fixed-size column somewhere
     before the "PFN" column, and instead of using the PRESENT, 
     HAS_MEMMAP, and ONLINE strings, use "P", "M" and "O".

That will keep it under 80 columns, and the "P", "M" and "O" should
be described in the "kmem" help page for the -n option (which 
currently doesn't even have the memory section in the example).

Now, when memory blocks are supported, the output is really difficult
to read, mainly because each of the (possible hundreds of) entries 
has two headers. 

I understand that you want to link the memory sections with the memory
blocks, but here's what I suggest the output should be.  To clarify their
relationship, you could add a "NR" column to your memory block display,
and separate the two sections, to look like this:
 
crash> kmem -n
... [ cut ] ...

NR      SECTION        CODED_MEM_MAP        MEM_MAP       STATE  PFN 
 0  ffff88047e5d6000  ffffea0000000000  ffffea0000000000   PM    0    
 1  ffff88047e5d6020  ffffea0000000000  ffffea0000200000   PM    32768
 2  ffff88047e5d6040  ffffea0000000000  ffffea0000400000   PM    65536
 3  ffff88047e5d6060  ffffea0000000000  ffffea0000600000   PM    98304
...

NR      MEM_BLOCK     NAME         PHYSICAL RANGE      STATE
 0  ffff880181e59000  memory0           0 -  7ffffff   ONLINE        
 1  ffff880181e58c00  memory1     8000000 -  fffffff   ONLINE        
 2  ffff88047e268000  memory2    10000000 - 17ffffff   ONLINE        
 3  ffff88047e268400  memory3    18000000 - 1fffffff   ONLINE        
...

Also, I would prefer that you separate the functionality for the
sake of clarity and maintainability, for example:

@@ -16355,7 +16357,7 @@ dump_memory_nodes(int initialize)
        }

        if (IS_SPARSEMEM())
-               dump_mem_sections(initialize);
+               dump_mem_block_and_sections(initialize);
 }

Could you create a separate dump_memory_blocks() function?  I understand 
that other functions can and should be utilized by both functions.

Lastly, for any new additions to the offset_table, please add them
to the dump_offset_table() function in symbols.c for "help -o".
I mistakenly forgot to mention that when accepting your "dev -p" patch,
but I subsequently added them.

Thanks,
  Dave







> 
> Signed-off-by: Masayoshi Mizuma <m.miz...@jp.fujitsu.com>
> ---
>  defs.h   |   8 ++
>  memory.c | 412 +++++++++++++++++++++++++++++++++++++++++++++++++------
>  2 files changed, 379 insertions(+), 41 deletions(-)
> 
> diff --git a/defs.h b/defs.h
> index 5b64bb7..f707c64 100644
> --- a/defs.h
> +++ b/defs.h
> @@ -2049,6 +2049,14 @@ struct offset_table {                    /* stash of
> commonly-used offsets */
>          long pci_bus_self;
>       long device_kobj;
>       long kobject_name;
> +     long memory_block_dev;
> +     long memory_block_start_section_nr;
> +     long mem_section_pageblock_flags;
> +     long memory_block_state;
> +     long memory_block_nid;
> +     long bus_type_p;
> +     long device_private_device;
> +     long device_private_knode_bus;
>  };
>  
>  struct size_table {         /* stash of commonly-used sizes */
> diff --git a/memory.c b/memory.c
> index ea25047..c7a4787 100644
> --- a/memory.c
> +++ b/memory.c
> @@ -254,14 +254,16 @@ static void PG_reserved_flag_init(void);
>  static void PG_slab_flag_init(void);
>  static ulong nr_blockdev_pages(void);
>  void sparse_mem_init(void);
> -void dump_mem_sections(int);
> +void dump_mem_block_and_sections(int);
> +void _dump_mem_block_and_sections(void);
> +void dump_mem_sections(void);
>  void list_mem_sections(void);
>  ulong sparse_decode_mem_map(ulong, ulong);
>  char *read_mem_section(ulong);
>  ulong nr_to_section(ulong);
>  int valid_section(ulong);
>  int section_has_mem_map(ulong);
> -ulong section_mem_map_addr(ulong);
> +ulong section_mem_map_addr(ulong, int);
>  ulong valid_section_nr(ulong);
>  ulong pfn_to_map(ulong);
>  static int get_nodes_online(void);
> @@ -5528,7 +5530,7 @@ dump_mem_map_SPARSEMEM(struct meminfo *mi)
>                       pc->curcmd_flags |= HEADER_PRINTED;
>               }
>  
> -             pp = section_mem_map_addr(section);
> +             pp = section_mem_map_addr(section, 0);
>               pp = sparse_decode_mem_map(pp, section_nr);
>               phys = (physaddr_t) section_nr * PAGES_PER_SECTION() * 
> PAGESIZE();
>               section_size = PAGES_PER_SECTION();
> @@ -13389,7 +13391,7 @@ is_page_ptr(ulong addr, physaddr_t *phys)
>               nr_mem_sections = vt->max_mem_section_nr+1;
>               for (nr = 0; nr < nr_mem_sections ; nr++) {
>                       if ((sec_addr = valid_section_nr(nr))) {
> -                             coded_mem_map = section_mem_map_addr(sec_addr);
> +                             coded_mem_map = section_mem_map_addr(sec_addr, 
> 0);
>                               mem_map = sparse_decode_mem_map(coded_mem_map, 
> nr);
>                               end_mem_map = mem_map + (PAGES_PER_SECTION() * 
> SIZE(page));
>  
> @@ -16355,7 +16357,7 @@ dump_memory_nodes(int initialize)
>       }
>  
>       if (IS_SPARSEMEM())
> -             dump_mem_sections(initialize);
> +             dump_mem_block_and_sections(initialize);
>  }
>  
>  /*
> @@ -17140,7 +17142,7 @@ section_has_mem_map(ulong addr)
>  }
>  
>  ulong
> -section_mem_map_addr(ulong addr)
> +section_mem_map_addr(ulong addr, int raw)
>  {
>       char *mem_section;
>       ulong map;
> @@ -17148,7 +17150,8 @@ section_mem_map_addr(ulong addr)
>       if ((mem_section = read_mem_section(addr))) {
>               map = ULONG(mem_section +
>                       OFFSET(mem_section_section_mem_map));
> -             map &= SECTION_MAP_MASK;
> +             if (!raw)
> +                     map &= SECTION_MAP_MASK;
>               return map;
>       }
>       return 0;
> @@ -17179,7 +17182,7 @@ pfn_to_map(ulong pfn)
>  
>       if (section_has_mem_map(section)) {
>               page_offset = pfn - section_nr_to_pfn(section_nr);
> -             coded_mem_map = section_mem_map_addr(section);
> +             coded_mem_map = section_mem_map_addr(section, 0);
>               mem_map = sparse_decode_mem_map(coded_mem_map, section_nr) +
>                       (page_offset * SIZE(page));
>               return mem_map;
> @@ -17188,16 +17191,365 @@ pfn_to_map(ulong pfn)
>       return 0;
>  }
>  
> -void
> -dump_mem_sections(int initialize)
> +struct memory_block_info {
> +     ulong memory_block;
> +     ulong start_sec;
> +     ulong start_pfn;
> +     ulong nid;
> +     char state[24];
> +     char name[32];
> +};
> +
> +#define MIN_MEMORY_BLOCK_SIZE     (1UL << _SECTION_SIZE_BITS)
> +
> +#define MEM_ONLINE              (1<<0)
> +#define MEM_GOING_OFFLINE       (1<<1)
> +#define MEM_OFFLINE             (1<<2)
> +#define MEM_GOING_ONLINE        (1<<3)
> +#define MEM_CANCEL_ONLINE       (1<<4)
> +#define MEM_CANCEL_OFFLINE      (1<<5)
> +
> +static void
> +fill_memory_block_state(ulong memblock, char *buf)
>  {
> -     ulong nr, max, addr;
> -     ulong nr_mem_sections;
> +     ulong state;
> +
> +     memset(buf, 0, sizeof(*buf) * BUFSIZE);
> +
> +     readmem(memblock + OFFSET(memory_block_state), KVADDR, &state,
> +             sizeof(void *), "memory_block state", FAULT_ON_ERROR);
> +
> +     switch (state) {
> +     case MEM_ONLINE:
> +             sprintf(buf, "%s", "ONLINE");
> +             break;
> +     case MEM_GOING_OFFLINE:
> +             sprintf(buf, "%s", "GOING_OFFLINE");
> +             break;
> +     case MEM_OFFLINE:
> +             sprintf(buf, "%s", "OFFLINE");
> +             break;
> +     case MEM_GOING_ONLINE:
> +             sprintf(buf, "%s", "GOING_ONLINE");
> +             break;
> +     case MEM_CANCEL_ONLINE:
> +             sprintf(buf, "%s", "CANCEL_ONLINE");
> +             break;
> +     case MEM_CANCEL_OFFLINE:
> +             sprintf(buf, "%s",  "CANCEL_OFFLINE");
> +             break;
> +     default:
> +             sprintf(buf, "%s", "UNKNOWN");
> +     }
> +}
> +
> +static void
> +fill_mem_section_state(ulong state, char *buf)
> +{
> +     int bufidx = 0, others = 0;
> +
> +     memset(buf, 0, sizeof(*buf) * BUFSIZE);
> +
> +#define printflag(X) sprintf(buf + bufidx, X, others++ ? "|" : "")
> +
> +     if (state & SECTION_MARKED_PRESENT)
> +             bufidx += printflag("%sPRESENT");
> +     if (state & SECTION_HAS_MEM_MAP)
> +             bufidx += printflag("%sHAS_MEMMAP");
> +     if (state & SECTION_IS_ONLINE)
> +             bufidx += printflag("%sONLINE");
> +}
> +
> +static ulong
> +pfn_to_phys(ulong pfn)
> +{
> +     return pfn << PAGE_SHIFT;
> +}
> +
> +static ulong
> +get_memory_block_size(void)
> +{
> +     static ulong blksz;
> +
> +     if (blksz)
> +             return blksz;
> +
> +     if (symbol_exists("memory_block_size_probed"))
> +             get_symbol_data("memory_block_size_probed", sizeof(ulong),
> +                             &blksz);
> +     else
> +             blksz = MIN_MEMORY_BLOCK_SIZE;
> +
> +     return blksz;
> +}
> +
> +static void
> +fill_memory_block_name(ulong memblock, char *name)
> +{
> +     ulong kobj, value;
> +
> +     memset(name, 0, sizeof(*name) * BUFSIZE);
> +
> +     kobj = memblock + OFFSET(memory_block_dev) + OFFSET(device_kobj);
> +
> +     readmem(kobj + OFFSET(kobject_name),
> +             KVADDR, &value, sizeof(void *), "kobject name",
> +             FAULT_ON_ERROR);
> +
> +     read_string(value, name, BUFSIZE-1);
> +}
> +
> +static void
> +fill_memory_block_info(ulong mb, struct memory_block_info *mbi)
> +{
> +     ulong start, start_pfn, nid;
> +     char statebuf[BUFSIZE];
> +     char name[BUFSIZE];
> +
> +     readmem(mb + OFFSET(memory_block_start_section_nr), KVADDR,
> +             &start, sizeof(void *), "memory_block start_section_nr",
> +             FAULT_ON_ERROR);
> +
> +     start_pfn = section_nr_to_pfn(start);
> +     fill_memory_block_state(mb, statebuf);
> +     fill_memory_block_name(mb, name);
> +
> +     mbi->memory_block = mb;
> +     mbi->start_sec = start;
> +     mbi->start_pfn = start_pfn;
> +     strncpy(mbi->state, statebuf, sizeof(mbi->state));
> +     strncpy(mbi->name, name, sizeof(mbi->name));
> +     if (MEMBER_EXISTS("memory_block", "nid")) {
> +             readmem(mb + OFFSET(memory_block_nid), KVADDR, &nid,
> +                     sizeof(void *), "memory_block nid", FAULT_ON_ERROR);
> +             mbi->nid = nid;
> +     }
> +}
> +
> +static void
> +init_memory_block(void)
> +{
> +     MEMBER_OFFSET_INIT(bus_type_p, "bus_type", "p");
> +     MEMBER_OFFSET_INIT(subsys_private_klist_devices,
> +                             "subsys_private", "klist_devices");
> +     MEMBER_OFFSET_INIT(klist_k_list, "klist", "k_list");
> +     MEMBER_OFFSET_INIT(klist_node_n_node, "klist_node", "n_node");
> +     MEMBER_OFFSET_INIT(device_private_knode_bus,
> +                             "device_private", "knode_bus");
> +     MEMBER_OFFSET_INIT(device_private_device, "device_private", "device");
> +     MEMBER_OFFSET_INIT(memory_block_dev, "memory_block", "dev");
> +     MEMBER_OFFSET_INIT(memory_block_start_section_nr,
> +                             "memory_block", "start_section_nr");
> +     MEMBER_OFFSET_INIT(memory_block_state, "memory_block", "state");
> +     if (MEMBER_EXISTS("memory_block", "nid"))
> +             MEMBER_OFFSET_INIT(memory_block_nid, "memory_block", "nid");
> +}
> +
> +static struct memory_block_info*
> +parse_memory_block(void)
> +{
> +     ulong memory_subsys = symbol_value("memory_subsys");
> +     ulong private, klist, memory_block, device;
> +     ulong *klistbuf;
> +     int klistcnt, i;
> +     struct list_data list_data, *ld;
> +     struct memory_block_info *memory_block_info;
> +
> +     init_memory_block();
> +
> +     readmem(memory_subsys + OFFSET(bus_type_p), KVADDR, &private,
> +             sizeof(void *), "memory_subsys.private", FAULT_ON_ERROR);
> +     klist = private + OFFSET(subsys_private_klist_devices) +
> +                                     OFFSET(klist_k_list);
> +     ld = &list_data;
> +     BZERO(ld, sizeof(struct list_data));
> +
> +     ld->start = klist;
> +     ld->end = klist;
> +     ld->list_head_offset = OFFSET(klist_node_n_node) +
> +                                     OFFSET(device_private_knode_bus);
> +     hq_open();
> +     klistcnt = do_list(ld);
> +     klistbuf = (ulong *)GETBUF(klistcnt * sizeof(ulong));
> +     klistcnt = retrieve_list(klistbuf, klistcnt);
> +     hq_close();
> +
> +     memory_block_info = calloc(klistcnt + 1,
> +                                     sizeof(struct memory_block_info));
> +     if (!memory_block_info)
> +             error(FATAL, "cannot allocate memory for memory_block_info\n");
> +
> +     for (i = 0; i < klistcnt; i++) {
> +             readmem(klistbuf[i] + OFFSET(device_private_device), KVADDR,
> +                     &device, sizeof(void *), "device_private device",
> +                     FAULT_ON_ERROR);
> +             memory_block = device - OFFSET(memory_block_dev);
> +             fill_memory_block_info(memory_block, &memory_block_info[i]);
> +     }
> +     FREEBUF(klistbuf);
> +
> +     return memory_block_info;
> +}
> +
> +static struct memory_block_info*
> +get_memory_block_info(ulong pfn, struct memory_block_info *mbi_tbl)
> +{
> +     int i;
> +
> +     for (i = 0; mbi_tbl[i].memory_block != 0; i++)
> +             if (pfn == mbi_tbl[i].start_pfn)
> +                     return &mbi_tbl[i];
> +
> +     return NULL;
> +}
> +
> +
> +static int
> +is_memory_block_head(ulong pfn)
> +{
> +     ulong nr_pages = get_memory_block_size() / PAGE_SIZE;
> +
> +     return (pfn % nr_pages) == 0;
> +}
> +
> +static void
> +print_memory_block(ulong pfn, ulong nr_mb_pages, struct memory_block_info
> *mbi)
> +{
> +     char buf1[BUFSIZE];
> +     char buf2[BUFSIZE];
> +     char buf3[BUFSIZE];
> +     char buf4[BUFSIZE];
> +     char buf5[BUFSIZE];
> +     char buf6[BUFSIZE];
> +
> +     if (MEMBER_EXISTS("memory_block", "nid"))
> +             fprintf(fp, " %s %s %s - %s %s %s\n",
> +                     mkstring(buf1, VADDR_PRLEN, LJUST|LONG_HEX,
> +                     MKSTR(mbi->memory_block)),
> +                     mkstring(buf2, 12, CENTER, mbi->name),
> +                     mkstring(buf3, PADDR_PRLEN, RJUST|LONG_HEX,
> +                     MKSTR(pfn_to_phys(pfn))),
> +                     mkstring(buf4, PADDR_PRLEN, LJUST|LONG_HEX,
> +                     MKSTR(pfn_to_phys(pfn + nr_mb_pages) - 1)),
> +                     mkstring(buf5, strlen("NODE"), CENTER|LONG_DEC,
> +                     MKSTR(mbi->nid)),
> +                     mkstring(buf6, strlen("CANCEL_OFFLINE"), LJUST,
> +                     mbi->state));
> +     else
> +             fprintf(fp, " %s %s %s - %s %s\n",
> +                     mkstring(buf1, VADDR_PRLEN, LJUST|LONG_HEX,
> +                     MKSTR(mbi->memory_block)),
> +                     mkstring(buf2, 10, CENTER, mbi->name),
> +                     mkstring(buf3, PADDR_PRLEN, RJUST|LONG_HEX,
> +                     MKSTR(pfn_to_phys(pfn))),
> +                     mkstring(buf4, PADDR_PRLEN, LJUST|LONG_HEX,
> +                     MKSTR(pfn_to_phys(pfn + nr_mb_pages) - 1)),
> +                     mkstring(buf5, strlen("CANCEL_OFFLINE"), LJUST,
> +                     mbi->state));
> +}
> +
> +static void
> +do_mem_block_and_sections(int print_memblk, struct memory_block_info
> *mbi_tbl)
> +{
> +     ulong nr, addr;
> +     ulong nr_mem_sections, nr_mb_pages;
>       ulong coded_mem_map, mem_map, pfn;
> +     struct memory_block_info *mbi;
> +     char mb_hdr[BUFSIZE];
> +     char ms_hdr[BUFSIZE];
> +     char statebuf[BUFSIZE];
>       char buf1[BUFSIZE];
>       char buf2[BUFSIZE];
>       char buf3[BUFSIZE];
>       char buf4[BUFSIZE];
> +     char buf5[BUFSIZE];
> +
> +     nr_mb_pages = PAGES_PER_SECTION() *
> +                     get_memory_block_size() / MIN_MEMORY_BLOCK_SIZE;
> +
> +     if (MEMBER_EXISTS("memory_block", "nid"))
> +             sprintf(mb_hdr, "\n%s %s %s     %s %s\n",
> +                     mkstring(buf1, VADDR_PRLEN, CENTER|LJUST, "MEM_BLOCK"),
> +                     mkstring(buf2, 10, CENTER, "NAME"),
> +                     mkstring(buf3, PADDR_PRLEN*2 + 2, CENTER, "PHYSICAL 
> RANGE"),
> +                     mkstring(buf4, strlen("NODE"), CENTER, "NODE"),
> +                     mkstring(buf5, strlen("CANCEL_OFFLINE"), LJUST, 
> "STATE"));
> +     else
> +             sprintf(mb_hdr, "\n%s %s %s     %s\n",
> +                     mkstring(buf1, VADDR_PRLEN, CENTER|LJUST, "MEM_BLOCK"),
> +                     mkstring(buf2, 10, CENTER, "NAME"),
> +                     mkstring(buf3, PADDR_PRLEN*2, CENTER, "PHYSICAL RANGE"),
> +                     mkstring(buf4, strlen("CANCEL_OFFLINE"), LJUST, 
> "STATE"));
> +
> +     sprintf(ms_hdr, "NR     %s  %s  %s  %s %s\n",
> +             mkstring(buf1, VADDR_PRLEN, CENTER|LJUST, "SECTION"),
> +             mkstring(buf2, MAX(VADDR_PRLEN, strlen("CODED_MEM_MAP")),
> +             CENTER|LJUST, "CODED_MEM_MAP"),
> +             mkstring(buf3, VADDR_PRLEN, CENTER|LJUST, "MEM_MAP"),
> +             mkstring(buf4, 12, CENTER, "PFN"),
> +             mkstring(buf5, 12, LJUST, "STATE"));
> +
> +     if (!print_memblk)
> +             fprintf(fp, "%s", ms_hdr);
> +
> +     nr_mem_sections = NR_MEM_SECTIONS();
> +     for (nr = 0; nr < nr_mem_sections ; nr++) {
> +             addr = valid_section_nr(nr);
> +             if (addr) {
> +                     coded_mem_map = section_mem_map_addr(addr, 0);
> +                     mem_map = sparse_decode_mem_map(coded_mem_map, nr);
> +                     pfn = section_nr_to_pfn(nr);
> +                     fill_mem_section_state(section_mem_map_addr(addr, 1),
> +                                             statebuf);
> +
> +                     if ((print_memblk) && (is_memory_block_head(pfn))) {
> +                             mbi = get_memory_block_info(pfn, mbi_tbl);
> +                             fprintf(fp, "%s", mb_hdr);
> +                             print_memory_block(pfn, nr_mb_pages, mbi);
> +                             fprintf(fp, "%s", ms_hdr);
> +                     }
> +
> +                     fprintf(fp, "%5ld  %s  %s  %s  %s %s\n",
> +                             nr,
> +                             mkstring(buf1, VADDR_PRLEN,
> +                             CENTER|LONG_HEX, MKSTR(addr)),
> +                             mkstring(buf2, MAX(VADDR_PRLEN,
> +                             strlen("CODED_MEM_MAP")),
> +                             CENTER|LONG_HEX|RJUST, MKSTR(coded_mem_map)),
> +                             mkstring(buf3, VADDR_PRLEN,
> +                             CENTER|LONG_HEX|RJUST, MKSTR(mem_map)),
> +                             pc->output_radix == 10 ?
> +                             mkstring(buf4, 12,
> +                             LONG_DEC|LJUST, MKSTR(pfn)) :
> +                             mkstring(buf4, 12,
> +                             LONG_HEX|LJUST, MKSTR(pfn)),
> +                             mkstring(buf5, 12, LJUST, statebuf));
> +             }
> +     }
> +}
> +
> +
> +void
> +dump_mem_sections(void)
> +{
> +     do_mem_block_and_sections(0, NULL);
> +}
> +
> +void
> +_dump_mem_block_and_sections(void)
> +{
> +     struct memory_block_info *mbi_tbl;
> +
> +     mbi_tbl = parse_memory_block();
> +     do_mem_block_and_sections(1, mbi_tbl);
> +     free(mbi_tbl);
> +}
> +
> +void
> +dump_mem_block_and_sections(int initialize)
> +{
> +     ulong nr, max;
> +     ulong nr_mem_sections;
>  
>       nr_mem_sections = NR_MEM_SECTIONS();
>  
> @@ -17212,34 +17564,12 @@ dump_mem_sections(int initialize)
>  
>       fprintf(fp, "\n");
>       pad_line(fp, BITS32() ? 59 : 67, '-');
> -        fprintf(fp, "\n\nNR  %s  %s  %s  PFN\n",
> -                mkstring(buf1, VADDR_PRLEN, CENTER|LJUST, "SECTION"),
> -                mkstring(buf2, MAX(VADDR_PRLEN,strlen("CODED_MEM_MAP")),
> -             CENTER|LJUST, "CODED_MEM_MAP"),
> -                mkstring(buf3, VADDR_PRLEN, CENTER|LJUST, "MEM_MAP"));
> -
> -     for (nr = 0; nr < nr_mem_sections ; nr++) {
> -             if ((addr = valid_section_nr(nr))) {
> -                     coded_mem_map = section_mem_map_addr(addr);
> -                     mem_map = sparse_decode_mem_map(coded_mem_map,nr);
> -                     pfn = section_nr_to_pfn(nr);
> -
> -                     fprintf(fp, "%2ld  %s  %s  %s  %s\n",
> -                             nr,
> -                             mkstring(buf1, VADDR_PRLEN,
> -                             CENTER|LONG_HEX, MKSTR(addr)),
> -                             mkstring(buf2, MAX(VADDR_PRLEN,
> -                             strlen("CODED_MEM_MAP")),
> -                             CENTER|LONG_HEX|RJUST, MKSTR(coded_mem_map)),
> -                             mkstring(buf3, VADDR_PRLEN,
> -                             CENTER|LONG_HEX|RJUST, MKSTR(mem_map)),
> -                             pc->output_radix == 10 ?
> -                             mkstring(buf4, VADDR_PRLEN,
> -                             LONG_DEC|LJUST, MKSTR(pfn)) :
> -                             mkstring(buf4, VADDR_PRLEN,
> -                             LONG_HEX|LJUST, MKSTR(pfn)));
> -             }
> -     }
> +     fprintf(fp, "\n\n");
> +     if ((!STRUCT_EXISTS("memory_block")) ||
> +                             (!symbol_exists("memory_subsys")))
> +             dump_mem_sections();
> +     else
> +             _dump_mem_block_and_sections();
>  }
>  
>  void
> @@ -17251,7 +17581,7 @@ list_mem_sections(void)
>  
>       for (nr = 0; nr <= nr_mem_sections ; nr++) {
>               if ((addr = valid_section_nr(nr))) {
> -                     coded_mem_map = section_mem_map_addr(addr);
> +                     coded_mem_map = section_mem_map_addr(addr, 0);
>                       fprintf(fp,
>                           "nr=%ld section = %lx coded_mem_map=%lx pfn=%ld 
> mem_map=%lx\n",
>                               nr,
> --
> 2.19.0
> 
> --
> Crash-utility mailing list
> Crash-utility@redhat.com
> https://www.redhat.com/mailman/listinfo/crash-utility
> 

--
Crash-utility mailing list
Crash-utility@redhat.com
https://www.redhat.com/mailman/listinfo/crash-utility

Reply via email to