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] 32-on-64: pvfb issue

To: Xen devel list <xen-devel@xxxxxxxxxxxxxxxxxxx>
Subject: [Xen-devel] 32-on-64: pvfb issue
From: Gerd Hoffmann <kraxel@xxxxxxx>
Date: Thu, 18 Jan 2007 14:57:49 +0100
Delivery-date: Thu, 18 Jan 2007 05:57:33 -0800
Envelope-to: www-data@xxxxxxxxxxxxxxxxxx
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/cgi-bin/mailman/listinfo/xen-devel>, <mailto:xen-devel-request@lists.xensource.com?subject=subscribe>
List-unsubscribe: <http://lists.xensource.com/cgi-bin/mailman/listinfo/xen-devel>, <mailto:xen-devel-request@lists.xensource.com?subject=unsubscribe>
Sender: xen-devel-bounces@xxxxxxxxxxxxxxxxxxx
User-agent: Thunderbird 1.5.0.9 (X11/20060911)
  Hi,

There is a problem with the virtual framebuffer: The page directory in
the shared page (xenfb_page->pd[]) is unsigned long and thus has
different sizes on 32bit and 64bit.  The alignment is different too. And
on top of that the frontend driver doesn't clear the shared page, which
makes it difficult to autodetect the bitsize.  I've tried nevertheless,
patch (untested!) attached for comments.  In the long run this code is
supposed to be replaced by grant tables anyway, so it is probably okay
to live with the hack for the time being.  We could of course also fix
the struct if we can afford breaking the interface.  As it is quite new
and probably (hmm, does fc6 ship it?) not widely used yet that might be
an option.

cheers,
  Gerd
--- build-32-unstable-13401/tools/xenfb/xenfb.c-13401   2007-01-18 
11:35:53.000000000 +0100
+++ build-32-unstable-13401/tools/xenfb/xenfb.c 2007-01-18 12:30:44.000000000 
+0100
@@ -329,12 +329,59 @@
        struct xenfb_page *page = xenfb->fb.page;
        int n_fbmfns;
        int n_fbdirs;
+       unsigned long pgmfns[2];
        unsigned long *fbmfns;
+       uint32_t *ptr32;
+       uint64_t *ptr64;
+       int i,mode;
+
+/*
+ * bimodal guess work.
+ * page->depth is at a 64bit border, thus we get for page->pg[] ...
+ *
+ *  i386    | depth | 3b pad |  pg0  |  pg1  |  pg2  |  pg3  |  pg4  |
+ *  x86_64  | depth | 7b pad         |      pg0      |      pg1      |
+ *
+ * frontend does *not* clear the page.  pg0 and pg1 are initialized.
+ * at the moment pg0 is used only (800x600x32 needs less than 512 pages,
+ * which fits into one page directory even with 64bit), pg1 is initialized
+ * to zero.  We also assume the machine has less than 16 TB main memory,
+ * thus 32bit are enougth for the page frame numbers.  By the time this
+ * assumtion is rendered invalid the code should have been converted to
+ * grant tables anyway.
+ */
+#if defined(__i386__)
+       mode = 32;
+       ptr32 = (void*)page->pd;
+       ptr64 = ((void*)ptr32) + 4;
+       if (ptr32[1] > 0 &&
+           ptr32[2] == 0 && 
+           ptr32[3] == 0 &&
+           ptr32[4] == 0)
+               mode = 64;
+#elif defined(__x86_64__)
+       mode = 64;
+       ptr64 = (void*)page->pd;
+       ptr32 = ((void*)ptr64) - 4;
+       if (ptr32[0] > 0 &&
+           ptr32[1] == 0)
+               mode = 32;
+#else
+# error unknown arch
+#endif
 
        n_fbmfns = (xenfb->fb_len + (XC_PAGE_SIZE - 1)) / XC_PAGE_SIZE;
-       n_fbdirs = n_fbmfns * sizeof(unsigned long);
+       n_fbdirs = n_fbmfns * mode / 4;
        n_fbdirs = (n_fbdirs + (XC_PAGE_SIZE - 1)) / XC_PAGE_SIZE;
 
+       if (32 == mode) {
+               for (i = 0; i < n_fbdirs; i++)
+                       pgmfns[i] = ptr32[i];
+       } else {
+               for (i = 0; i < n_fbdirs; i++)
+                       pgmfns[i] = ptr64[i];
+       }
+
        /*
         * Bug alert: xc_map_foreign_batch() can fail partly and
         * return a non-null value.  This is a design flaw.  When it
@@ -342,18 +389,31 @@
         * access.
         */
        fbmfns = xc_map_foreign_batch(xenfb->xc, domid,
-                       PROT_READ, page->pd, n_fbdirs);
+                       PROT_READ, pgmfns, n_fbdirs);
        if (fbmfns == NULL)
                return -1;
 
+       if (32 == mode) {
+               ptr32 = (void*)fbmfns;
+               fbmfns = malloc(n_fbmfns * sizeof(*fbmfns));
+               for (i = 0; i < n_fbmfns; i++)
+                       fbmfns[i] = ptr32[i];
+               munmap(ptr32, n_fbdirs * XC_PAGE_SIZE);
+       } else {
+               ptr64 = (void*)fbmfns;
+               fbmfns = malloc(n_fbmfns * sizeof(*fbmfns));
+               for (i = 0; i < n_fbmfns; i++)
+                       fbmfns[i] = ptr64[i];
+               munmap(ptr64, n_fbdirs * XC_PAGE_SIZE);
+       }
+
        xenfb->pub.pixels = xc_map_foreign_batch(xenfb->xc, domid,
                                PROT_READ | PROT_WRITE, fbmfns, n_fbmfns);
-       if (xenfb->pub.pixels == NULL) {
-               munmap(fbmfns, n_fbdirs * XC_PAGE_SIZE);
+       if (xenfb->pub.pixels == NULL)
                return -1;
-       }
 
-       return munmap(fbmfns, n_fbdirs * XC_PAGE_SIZE);
+       free(fbmfns);
+       return 0;
 }
 
 static int xenfb_bind(struct xenfb_device *dev)
_______________________________________________
Xen-devel mailing list
Xen-devel@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-devel
<Prev in Thread] Current Thread [Next in Thread>