WARNING - OLD ARCHIVES

This is an archived copy of the Xen.org mailing list, which we have preserved to ensure that existing links to archives are not broken. The live archive, which contains the latest emails, can be found at http://lists.xen.org/
   
 
 
Xen 
 
Home Products Support Community News
 
   
 

xen-devel

[Xen-devel] xen-detect fail.

To: xen-devel@xxxxxxxxxxxxxxxxxxx
Subject: [Xen-devel] xen-detect fail.
From: Qiang Fu <fu7iang@xxxxxxxxx>
Date: Thu, 8 Apr 2010 13:56:38 +0800
Delivery-date: Wed, 14 Apr 2010 07:16:50 -0700
Dkim-signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=gamma; h=domainkey-signature:mime-version:received:date:received:message-id :subject:from:to:content-type; bh=UD/sV6gryFxZ8vMlk4LICX4Y6qLovg2z6TN/WHcOiEE=; b=t4UztvIfbKrS9yHRgfUovlZMByXCEAlf7pzAPE4ffduN6dNRLCGngSMksnszjQHbat WTkN4zoJWOIHr+3H9lIaaMBORHIy8NxSRSr6gpDrb0t1DO/6OMag0Y9ue1j2i+uj7vMv 7oZSBqd2hYPz/cDTD6DGAfJGMT7Tp2XCJizf0=
Domainkey-signature: a=rsa-sha1; c=nofws; d=gmail.com; s=gamma; h=mime-version:date:message-id:subject:from:to:content-type; b=TX+7SH6iz4sTd+goHyIGRhaIUx40OHCKyuPw0U6TVuAtSxcAq+g7zJRgbsul/+tcqM hg63Q8dzKZDSbxRN01zQwxNKkaJy+c1tdrkIA+LfYZ8PKJVOEjAETMQWSmhtQLYjC0sZ YWDCm7caagINhpKCX/EyDQJaUBt43uQYPSQSc=
Envelope-to: www-data@xxxxxxxxxxxxxxxxxxx
List-help: <mailto:xen-devel-request@lists.xensource.com?subject=help>
List-id: Xen developer discussion <xen-devel.lists.xensource.com>
List-post: <mailto:xen-devel@lists.xensource.com>
List-subscribe: <http://lists.xensource.com/mailman/listinfo/xen-devel>, <mailto:xen-devel-request@lists.xensource.com?subject=subscribe>
List-unsubscribe: <http://lists.xensource.com/mailman/listinfo/xen-devel>, <mailto:xen-devel-request@lists.xensource.com?subject=unsubscribe>
Sender: xen-devel-bounces@xxxxxxxxxxxxxxxxxxx
Hi,

xen-detect may hang on some cases.
I hit this issue on one of my box. And I found that
it hang when executing "ud2a". Seems it not trap
and sig the user.

OS: RHEL 5.4       2.6.18-164.15.1.el5
glibc-2.5-42.el5_4.3.x86_64

/var/log/message
kernel: xen-detect general protection rip:400665 rsp:7fff3a922888 error:0

On platform it work correctly, the message is
kernel: xen-detect trap invalid opcode rip:40068d rsp:7fffa8acadc8 error:0

Any idea of this, why it behaves different?

source codes:
------------------------
#include <stdint.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <setjmp.h>
#include <signal.h>
#include <unistd.h>
#include <getopt.h>

static void cpuid(uint32_t idx,
                  uint32_t *eax,
                  uint32_t *ebx,
                  uint32_t *ecx,
                  uint32_t *edx,
                  int pv_context)
{
    asm volatile (
        "test %1,%1 ; jz 1f ; ud2a ; .ascii \"xen\" ; 1: cpuid"
        : "=a" (*eax), "=b" (*ebx), "=c" (*ecx), "=d" (*edx)
        : "0" (idx), "1" (pv_context) );
}

static int check_for_xen(int pv_context)
{
    uint32_t eax, ebx, ecx, edx;
    char signature[13];
    uint32_t base;

    for ( base = 0x40000000; base < 0x40010000; base += 0x100 )
    {
        cpuid(base, &eax, &ebx, &ecx, &edx, pv_context);

        *(uint32_t *)(signature + 0) = ebx;
        *(uint32_t *)(signature + 4) = ecx;
        *(uint32_t *)(signature + 8) = edx;
        signature[12] = '\0';

        if ( !strcmp("XenVMMXenVMM", signature) && (eax >= (base + 2)) )
            goto found;
    }

    return 0;

 found:
    cpuid(base + 1, &eax, &ebx, &ecx, &edx, pv_context);
    return 1;
}

static jmp_buf sigill_jmp;
void sigill_handler(int sig)
{
    longjmp(sigill_jmp, 1);
}

static void usage(void)
{
    printf("Usage: xen_detect [options]\n");
    printf("Options:\n");
    printf("  -h, --help    Display this information\n");
    printf("  -q, --quiet   Quiesce normal informational output\n");
    printf("  -P, --pv      Exit status 1 if not running as PV guest\n");
    printf("  -H, --hvm     Exit status 1 if not running as HVM guest.\n");
    printf("  -N, --none    Exit status 1 if running on Xen (PV or HVM)\n");
}

int main(int argc, char **argv)
{
    enum { XEN_PV = 1, XEN_HVM = 2, XEN_NONE = 3 } detected = 0, expected = 0;
    uint32_t version = 0;
    int ch, quiet = 0;

    const static char sopts[] = "hqPHN";
    const static struct option lopts[] = {
        { "help",  0, NULL, 'h' },
        { "quiet", 0, NULL, 'q' },
        { "pv",    0, NULL, 'P' },
        { "hvm",   0, NULL, 'H' },
        { "none",  0, NULL, 'N' },
        { 0, 0, 0, 0}
    };

    while ( (ch = getopt_long(argc, argv, sopts, lopts, NULL)) != -1 )
    {
        switch ( ch )
        {
        case 'q':
            quiet = 1;
            break;
        case 'P':
            expected = XEN_PV;
            break;
        case 'H':
            expected = XEN_HVM;
            break;
        case 'N':
            expected = XEN_NONE;
            break;
        default:
            usage();
            exit(1);
        }
    }

    /* Check for execution in HVM context. */
    detected = XEN_HVM;
    if ( (version = check_for_xen(0)) != 0 )
        goto out;

    /*
     * Set up a signal handler to test the paravirtualised CPUID instruction.
     * If executed outside Xen PV context, the extended opcode will fault, we
     * will longjmp via the signal handler, and print "Not running on Xen".
     */
    detected = XEN_PV;
    if ( !setjmp(sigill_jmp)
         && (signal(SIGILL, sigill_handler) != SIG_ERR)
         && ((version = check_for_xen(1)) != 0) )
        goto out;

    detected = XEN_NONE;

 out:
    if ( quiet )
        /* nothing */;
    else if ( detected == XEN_NONE )
        printf("Not running on Xen.\n");
    else
        printf("Running in %s context on Xen v%d.%d.\n",
               (detected == XEN_PV) ? "PV" : "HVM",
               (uint16_t)(version >> 16), (uint16_t)version);

    return expected && (expected != detected);
}

_______________________________________________
Xen-devel mailing list
Xen-devel@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-devel
<Prev in Thread] Current Thread [Next in Thread>