Unless I find any unsurmountable problems, consider it queued for
 the next release. 
Is it necessary that the "pcpu_info" check in get_active_set()
needs to come before the "runqueues" and "per_cpu__runqueues"
checks?  I'd prefer it to be done last if at all possible.
Dave
>
------------------------------------------------------------------------
>
> --- crash-4.0-4.12/defs.h.kirshil    2008-01-15 18:52:34.000000000 +0300
> +++ crash-4.0-4.12/defs.h    2008-01-15 18:52:42.000000000 +0300
> @@ -1429,6 +1429,9 @@ struct offset_table {                            
> long kmem_cache_cpu_freelist;
>          long kmem_cache_cpu_page;
>          long kmem_cache_cpu_node;
> +    long pcpu_info_vcpu;
> +    long pcpu_info_idle;
> +    long vcpu_struct_rq;
>  };
>  
>  struct size_table {         /* stash of commonly-used sizes */
> @@ -1532,6 +1535,8 @@ struct size_table {         /* stash of      
> long upid;
>      long kmem_cache_cpu;
>      long cfs_rq;
> +    long pcpu_info;
> +    long vcpu_struct;
>  };
>  
>  struct array_table {
> --- crash-4.0-4.12/kernel.c.kirshil    2008-01-15 18:52:38.000000000 
> +0300
> +++ crash-4.0-4.12/kernel.c    2008-01-15 18:52:42.000000000 +0300
> @@ -475,6 +475,14 @@ kernel_init()
>      if (!(kt->flags & DWARF_UNWIND))
>          kt->flags |= NO_DWARF_UNWIND;  
> +    if(STRUCT_EXISTS("pcpu_info")) {
> +        MEMBER_OFFSET_INIT(pcpu_info_vcpu, "pcpu_info",
"vcpu");
> +        MEMBER_OFFSET_INIT(pcpu_info_idle, "pcpu_info",
"idle");
> +        MEMBER_OFFSET_INIT(vcpu_struct_rq, "vcpu_struct",
"rq");
> +        STRUCT_SIZE_INIT(pcpu_info, "pcpu_info");
> +        STRUCT_SIZE_INIT(vcpu_struct, "vcpu_struct");
> +    }
> +
>      BUG_bytes_init();
>  }
>  
> --- crash-4.0-4.12/task.c.kirshil    2008-01-15 18:52:39.000000000 +0300
> +++ crash-4.0-4.12/task.c    2008-01-15 18:53:56.000000000 +0300
> @@ -5696,6 +5696,14 @@ get_idle_threads(ulong *tasklist, int nr
>              cnt++;
>          else
>                      BZERO(tasklist, sizeof(ulong) * NR_CPUS);
> +    } else if (symbol_exists("pcpu_info") ){
> +        runq=symbol_value("pcpu_info");        /* vzk */
> +        runqbuf=GETBUF(SIZE(pcpu_info));
> +        for (i = 0; i < nr_cpus; i++, runq += SIZE(pcpu_info)) {
> +            readmem(runq,KVADDR,runqbuf,SIZE(pcpu_info),"pcpu 
> info",FAULT_ON_ERROR);
> +            tasklist[i] = ULONG(runqbuf + OFFSET(pcpu_info_idle));
> +            if (IS_KVADDR(tasklist[i]))  cnt++;
> +        }
>      }
>  
>      if (runqbuf)
> @@ -5777,13 +5785,15 @@ int
>  get_active_set(void)
>  {
>          int i, cnt, per_cpu;
> -        ulong runq, runqaddr;
> +        ulong runq, runqaddr, pcpu_info = 0;
>          char *runqbuf;
>  
>          if (tt->flags & ACTIVE_SET)
>                  return TRUE;
>  
> -    if (symbol_exists("runqueues")) {
> +    if (symbol_exists("pcpu_info") &&
VALID_MEMBER(pcpu_info_vcpu)) {
> +        pcpu_info = symbol_value("pcpu_info");
> +    } else if (symbol_exists("runqueues")) {
>          runq = symbol_value("runqueues");
>          per_cpu = FALSE;
>      } else if (symbol_exists("per_cpu__runqueues")) {
> @@ -5796,7 +5806,23 @@ get_active_set(void)
>          runqbuf = GETBUF(SIZE(runqueue));
>      cnt = 0;
>  
> -    if (VALID_MEMBER(runqueue_curr) && per_cpu) {
> +    if (pcpu_info != 0) {
> +        ulong vcpu_struct; +        char *pcpu_info_buf, 
> *vcpu_struct_buf;
> +
> +        pcpu_info_buf   = GETBUF(SIZE(pcpu_info));
> +        vcpu_struct_buf = GETBUF(SIZE(vcpu_struct));
> +        for (i = 0; i < kt->cpus; i++, pcpu_info += SIZE(pcpu_info)) {
> +            readmem(pcpu_info,KVADDR,pcpu_info_buf,SIZE(pcpu_info), 
> "pcpu_info",FAULT_ON_ERROR);
> +            vcpu_struct= ULONG(pcpu_info_buf +OFFSET(pcpu_info_vcpu));
> +            
>
readmem(vcpu_struct,KVADDR,vcpu_struct_buf,SIZE(vcpu_struct),"pcpu_info->vcpu",FAULT_ON_ERROR);
>
> +            tt->active_set[i] = 
> ULONG(vcpu_struct_buf+OFFSET(vcpu_struct_rq)+OFFSET(runqueue_curr));
> +            if (IS_KVADDR(tt->active_set[i]))
> +                cnt++;
> +        }
> +        FREEBUF(pcpu_info_buf);
> +        FREEBUF(vcpu_struct_buf);
> +    } else if (VALID_MEMBER(runqueue_curr) && per_cpu) {
>                     for (i = 0; i < kt->cpus; i++) {
>                          if ((kt->flags & SMP) && (kt->flags &
> PER_CPU_OFF)) {
>                                  runq = 
> symbol_value("per_cpu__runqueues") +
 
 -- 
 Crash-utility mailing list
 Crash-utility(a)redhat.com
 
https://www.redhat.com/mailman/listinfo/crash-utility