<!doctype html public "-//w3c//dtd html 4.0 transitional//en">
<html>
<tt>Dave Anderson wrote:</tt>
<blockquote TYPE=CITE><tt>Itsuro ODA wrote:</tt><tt></tt>
<p><tt>> Hi Dave,</tt>
<br><tt>></tt>
<br><tt>> > - Introduced support for xendumps of para-virtualized ia64
kernels.</tt>
<br><tt>> >   It should be noted that currently the ia64 Xen
kernel does not</tt>
<br><tt>> >   lay down a switch_stack for the panic task, so
only raw "bt -t"</tt>
<br><tt>> >   backtraces can be done on the panic task. 
(anderson@redhat.com)</tt>
<br><tt>></tt>
<br><tt>> page_index may contain INVALID_MFN (0xffffffffffffffffUL).</tt>
<br><tt>> I think it is better to check it.</tt>
<br><tt>> Here is a patch for this.</tt>
<br><tt>></tt>
<br><tt>> ---</tt>
<br><tt>> --- crash-4.0-3.15-org/xendump.h       
2006-12-21 09:57:29.000000000 +0900</tt>
<br><tt>> +++ crash-4.0-3.15/xendump.h    2006-12-21 14:37:35.000000000
+0900</tt>
<br><tt>> @@ -113,3 +113,8 @@</tt>
<br><tt>>      uint32_t hypercall_imm; /* Break
imm for Xen hypercalls.  */</tt>
<br><tt>>  /* #endif */</tt>
<br><tt>>  } xen_domctl_arch_setup_t;</tt>
<br><tt>> +</tt>
<br><tt>> +#ifdef IA64</tt>
<br><tt>> +#define INVALID_MFN (0xffffffffffffffffUL)</tt>
<br><tt>> +#endif</tt>
<br><tt>> +</tt>
<br><tt>> --- crash-4.0-3.15-org/xendump.c       
2006-12-21 09:57:29.000000000 +0900</tt>
<br><tt>> +++ crash-4.0-3.15/xendump.c    2006-12-21 14:42:48.000000000
+0900</tt>
<br><tt>> @@ -31,6 +31,7 @@</tt>
<br><tt>></tt>
<br><tt>>  static void xc_core_p2m_create(void);</tt>
<br><tt>>  static ulong xc_core_pfn_to_page_index(ulong);</tt>
<br><tt>> +static int check_mfn_is_valid(ulong);</tt>
<br><tt>></tt>
<br><tt>>  /*</tt>
<br><tt>>   *  Determine whether a file is a xendump creation,
and if TRUE,</tt>
<br><tt>> @@ -1362,7 +1363,7 @@</tt>
<br><tt>>         off_t offset;</tt>
<br><tt>></tt>
<br><tt>>         if (xd->flags
& XC_CORE_NO_P2MM)</tt>
<br><tt>> -              
return pfn;</tt>
<br><tt>> +              
return check_mfn_is_valid(pfn) ? pfn : PFN_NOT_FOUND;</tt>
<br><tt>></tt>
<br><tt>>         idx = pfn/PFNS_PER_PAGE;</tt>
<br><tt>></tt>
<br><tt>> @@ -1405,6 +1406,34 @@</tt>
<br><tt>>         return mfn_idx;</tt>
<br><tt>>  }</tt>
<br><tt>></tt>
<br><tt>> +static int</tt>
<br><tt>> +check_mfn_is_valid(ulong idx)</tt>
<br><tt>> +{</tt>
<br><tt>> +        ulong mfn;</tt>
<br><tt>> +</tt>
<br><tt>> +       if (idx >= xd->xc_core.header.xch_nr_pages)</tt>
<br><tt>> +              
return FALSE;</tt>
<br><tt>> +</tt>
<br><tt>> +        if (lseek(xd->xfd,</tt>
<br><tt>> +          
(off_t)xd->xc_core.header.xch_index_offset + idx * sizeof(ulong),</tt>
<br><tt>> +           
SEEK_SET) == -1) {</tt>
<br><tt>> +               
error(INFO, "cannot lseek to page index\n");</tt>
<br><tt>> +               
return FALSE;</tt>
<br><tt>> +        }</tt>
<br><tt>> +</tt>
<br><tt>> +       if (read(xd->xfd, &mfn,
sizeof(ulong)) != sizeof(ulong)) {</tt>
<br><tt>> +              
error(INFO, "cannot read index page %d\n", idx);</tt>
<br><tt>> +              
return FALSE;</tt>
<br><tt>> +       }</tt>
<br><tt>> +</tt>
<br><tt>> +       if (mfn == INVALID_MFN)
{</tt>
<br><tt>> +              
error(INFO, "idx: %lx indicates INVALID_MFN\n", idx);</tt>
<br><tt>> +              
return FALSE;</tt>
<br><tt>> +       } else {</tt>
<br><tt>> +              
return TRUE;</tt>
<br><tt>> +       }</tt>
<br><tt>> +}</tt>
<br><tt>> +</tt>
<br><tt>>  /*</tt>
<br><tt>>   *  Store the panic task's stack hooks from where
it was found</tt>
<br><tt>>   *  in get_active_set_panic_task().</tt>
<br><tt>> ---</tt>
<br><tt>></tt>
<br><tt>> Thanks.</tt>
<br><tt>> --</tt>
<br><tt>> Itsuro ODA <oda@valinux.co.jp></tt><tt></tt>
<p><tt>Oda-san,</tt><tt></tt>
<p><tt>Good catch.  I was never reading "bad addresses", so I didn't</tt>
<br><tt>see any issue there.  Now, after going back and checking it
out,</tt>
<br><tt>I see that if you attempt to read an uninstantiated pfn, it returns</tt>
<br><tt>the page index, and so it seeks to and reads whatever's in the</tt>
<br><tt>xendump from that location.  Given the way the FV xendump
is</tt>
<br><tt>laid out, there has to be *something* there in the dumpfile, which</tt>
<br><tt>I would have thought would have been sparse file space and</tt>
<br><tt>read as all zeroes?  But in some dumps, it looks like there's
"junk"</tt>
<br><tt>data there?  Whatever -- it's harmless.</tt><tt></tt>
<p><tt>In any case, I agree with you -- it's much better to return a read</tt>
<br><tt>error as xc_core_read() expects.  I'll just adjust your patch
slightly</tt>
<br><tt>to handle all architectures.</tt><tt></tt>
<p><tt>Thanks,</tt>
<br><tt>  Dave</tt></blockquote>
<tt></tt>
<p><br><tt>Oda-san,</tt><tt></tt>
<p><tt>Thanks again for the "overnight-QA" and for introducing support</tt>
<br><tt>for xendumps of fully-virtualized ia64 kernels!  I've posted
a new</tt>
<br><tt>crash version with both fixes.</tt><tt></tt>
<p><tt>I modified your check_mfn_is_valid() function so that
it could</tt>
<br><tt>be used by all 3 architectures as well as for xendumps of</tt>
<br><tt>32-bit kernels running on a 64-bit host:</tt>
<br><tt></tt> <tt></tt>
<p><tt>/*</tt>
<br><tt> *  In xendumps containing INVALID_MFN markers in the
page index,</tt>
<br><tt> *  return the validity of the pfn.</tt>
<br><tt> */</tt>
<br><tt>static int</tt>
<br><tt>xc_core_pfn_valid(ulong pfn)</tt>
<br><tt>{</tt>
<br><tt>        ulong mfn;</tt>
<br><tt>        off_t offset;</tt><tt></tt>
<p><tt>        if (pfn >= (ulong)xd->xc_core.header.xch_nr_pages)</tt>
<br><tt>               
return FALSE;</tt><tt></tt>
<p><tt>        offset = (off_t)xd->xc_core.header.xch_index_offset;</tt><tt></tt>
<p><tt>        if (xd->flags & XC_CORE_64BIT_HOST)</tt>
<br><tt>               
offset += (off_t)(pfn * sizeof(ulonglong));</tt>
<br><tt>        else</tt>
<br><tt>               
offset += (off_t)(pfn * sizeof(ulong));</tt><tt></tt>
<p><tt>        /*</tt>
<br><tt>         *  The lseek
and read should never fail, so report</tt>
<br><tt>         *  any errors
unconditionally.</tt>
<br><tt>         */</tt>
<br><tt>        if (lseek(xd->xfd, offset,
SEEK_SET) == -1) {</tt>
<br><tt>               
error(INFO,</tt>
<br><tt>                   
"xendump: cannot lseek to page index for pfn %lx\n",</tt>
<br><tt>                       
pfn);</tt>
<br><tt>               
return FALSE;</tt>
<br><tt>        }</tt><tt></tt>
<p><tt>        if (read(xd->xfd, &mfn,
sizeof(ulong)) != sizeof(ulong)) {</tt>
<br><tt>               
error(INFO,</tt>
<br><tt>                   
"xendump: cannot read index page for pfn %lx\n",</tt>
<br><tt>                       
pfn);</tt>
<br><tt>               
return FALSE;</tt>
<br><tt>        }</tt><tt></tt>
<p><tt>        /*</tt>
<br><tt>         *  If it's
an invalid mfn, let the caller decide whether</tt>
<br><tt>         *  to display
an error message (unless debugging).</tt>
<br><tt>         */</tt>
<br><tt>        if (mfn == INVALID_MFN)
{</tt>
<br><tt>               
if (CRASHDEBUG(1))</tt>
<br><tt>                       
error(INFO,</tt>
<br><tt>                           
"xendump: pfn %lx contains INVALID_MFN\n",</tt>
<br><tt>                               
pfn);</tt>
<br><tt>               
return FALSE;</tt>
<br><tt>        }</tt><tt></tt>
<p><tt>        return TRUE;</tt>
<br><tt>}</tt><tt></tt>
<p><tt>Thanks again,</tt>
<br><tt>  Dave</tt>
<br><tt></tt> </html>