From dc71c21f802fdc753384b9f326d2b0ee98529b51 Mon Sep 17 00:00:00 2001 From: Dave Airlie Date: Mon, 3 Aug 2009 00:00:31 +0000 Subject: [PATCH] - Add support for default vga arb device selection - Update libpciaccess VGA arb code for newer kernel API --- libpciaccess-vga-arbiter.patch | 754 ++++++++++++++++++--------------- libpciaccess.spec | 6 +- 2 files changed, 418 insertions(+), 342 deletions(-) diff --git a/libpciaccess-vga-arbiter.patch b/libpciaccess-vga-arbiter.patch index 6fb69fb..21f79cb 100644 --- a/libpciaccess-vga-arbiter.patch +++ b/libpciaccess-vga-arbiter.patch @@ -1,88 +1,6 @@ -diff -up libpciaccess-0.10.6/include/pciaccess.h.da libpciaccess-0.10.6/include/pciaccess.h ---- libpciaccess-0.10.6/include/pciaccess.h.da 2009-07-31 11:29:24.000000000 +1000 -+++ libpciaccess-0.10.6/include/pciaccess.h 2009-07-31 11:29:36.000000000 +1000 -@@ -21,6 +21,31 @@ - * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER - * DEALINGS IN THE SOFTWARE. - */ -+/* -+ * Copyright (c) 2007 Paulo R. Zanoni, Tiago Vignatti -+ * -+ * Permission is hereby granted, free of charge, to any person -+ * obtaining a copy of this software and associated documentation -+ * files (the "Software"), to deal in the Software without -+ * restriction, including without limitation the rights to use, -+ * copy, modify, merge, publish, distribute, sublicense, and/or sell -+ * copies of the Software, and to permit persons to whom the -+ * Software is furnished to do so, subject to the following -+ * conditions: -+ * -+ * The above copyright notice and this permission notice shall be -+ * included in all copies or substantial portions of the Software. -+ * -+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, -+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES -+ * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND -+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT -+ * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, -+ * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR -+ * OTHER DEALINGS IN THE SOFTWARE. -+ * -+ */ - - /** - * \file pciaccess.h -@@ -50,6 +75,8 @@ struct pci_slot_match; - extern "C" { - #endif - -+int pci_device_has_kernel_driver(struct pci_device *dev); -+ - int pci_device_is_boot_vga(struct pci_device *dev); - - int pci_device_read_rom(struct pci_device *dev, void *buffer); -@@ -350,6 +377,11 @@ struct pci_device { - * the \c pci_device structure. - */ - intptr_t user_data; -+ -+ /** -+ * Used by the VGA arbiter. Type of resource decoded by the device and -+ * the file descriptor (/dev/vga_arbiter). */ -+ int vgaarb_rsrc; - }; - - -@@ -449,4 +481,25 @@ struct pci_pcmcia_bridge_info { - - }; - -+ -+/** -+ * VGA Arbiter definitions, functions and related. -+ */ -+ -+/* Legacy VGA regions */ -+#define VGA_ARB_RSRC_NONE 0x00 -+#define VGA_ARB_RSRC_LEGACY_IO 0x01 -+#define VGA_ARB_RSRC_LEGACY_MEM 0x02 -+/* Non-legacy access */ -+#define VGA_ARB_RSRC_NORMAL_IO 0x04 -+#define VGA_ARB_RSRC_NORMAL_MEM 0x08 -+ -+int pci_device_vgaarb_init (void); -+void pci_device_vgaarb_fini (void); -+int pci_device_vgaarb_set_target (struct pci_device *dev); -+int pci_device_vgaarb_decodes (struct pci_device *dev, int new_vga_rsrc); -+int pci_device_vgaarb_lock (struct pci_device *dev); -+int pci_device_vgaarb_trylock (struct pci_device *dev); -+int pci_device_vgaarb_unlock (struct pci_device *dev); -+ - #endif /* PCIACCESS_H */ diff -up libpciaccess-0.10.6/src/common_interface.c.da libpciaccess-0.10.6/src/common_interface.c ---- libpciaccess-0.10.6/src/common_interface.c.da 2009-07-31 11:29:24.000000000 +1000 -+++ libpciaccess-0.10.6/src/common_interface.c 2009-07-31 11:29:36.000000000 +1000 +--- libpciaccess-0.10.6/src/common_interface.c.da 2009-08-03 09:57:13.000000000 +1000 ++++ libpciaccess-0.10.6/src/common_interface.c 2009-08-03 09:57:21.000000000 +1000 @@ -124,6 +124,21 @@ pci_device_is_boot_vga( struct pci_devic } @@ -105,258 +23,9 @@ diff -up libpciaccess-0.10.6/src/common_interface.c.da libpciaccess-0.10.6/src/c * Probe a PCI device to learn information about the device. * * Probes a PCI device to learn various information about the device. Before -diff -up /dev/null libpciaccess-0.10.6/src/common_vgaarb.c ---- /dev/null 2009-07-28 15:36:51.159175345 +1000 -+++ libpciaccess-0.10.6/src/common_vgaarb.c 2009-07-31 11:29:36.000000000 +1000 -@@ -0,0 +1,245 @@ -+/* -+ * Copyright (c) 2007 Paulo R. Zanoni, Tiago Vignatti -+ * 2009 Tiago Vignatti -+ * -+ * Permission is hereby granted, free of charge, to any person -+ * obtaining a copy of this software and associated documentation -+ * files (the "Software"), to deal in the Software without -+ * restriction, including without limitation the rights to use, -+ * copy, modify, merge, publish, distribute, sublicense, and/or sell -+ * copies of the Software, and to permit persons to whom the -+ * Software is furnished to do so, subject to the following -+ * conditions: -+ * -+ * The above copyright notice and this permission notice shall be -+ * included in all copies or substantial portions of the Software. -+ * -+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, -+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES -+ * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND -+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT -+ * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, -+ * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR -+ * OTHER DEALINGS IN THE SOFTWARE. -+ * -+ */ -+ -+#include -+#include -+#include -+#include -+#include -+#include -+#include -+ -+#include "pciaccess.h" -+#include "pciaccess_private.h" -+ -+#define BUFSIZE 64 -+ -+int -+pci_device_vgaarb_init(void) -+{ -+ if ((pci_sys->vgaarb_fd = open ("/dev/vga_arbiter", O_RDWR)) < 0) { -+ return errno; -+ } -+ -+ return 0; -+} -+ -+void -+pci_device_vgaarb_fini(void) -+{ -+ close(pci_sys->vgaarb_fd); -+} -+ -+/** -+ * Writes message on vga device. The messages are defined by the kernel -+ * implementation. -+ * -+ * \param fd vga arbiter device. -+ * \param buf message itself. -+ * \param len message length. -+ * -+ * \return -+ * Zero on success, 1 if something gets wrong and 2 if fd is busy (only for -+ * 'trylock') -+ */ -+static int -+vgaarb_write(int fd, char *buf, int len) -+{ -+ int ret; -+ -+ -+ buf[len] = '\0'; -+ -+ ret = write(fd, buf, len); -+ if (ret == -1) { -+ /* the user may have called "trylock" and didn't get the lock */ -+ if (errno == EBUSY) -+ return 2; -+ -+#ifdef DEBUG -+ fprintf(stderr, "write error"); -+#endif -+ return 1; -+ } -+ else if (ret != len) { -+ /* it's need to receive the exactly amount required. */ -+#ifdef DEBUG -+ fprintf(stderr, "write error: wrote different than expected\n"); -+#endif -+ return 1; -+ } -+ -+#ifdef DEBUG -+ fprintf(stderr, "%s: successfully wrote: '%s'\n", __FUNCTION__, buf); -+#endif -+ -+ return 0; -+} -+ -+static int -+parse_string_to_decodes_rsrc(char *input, int *vga_count) -+{ -+ char *tok; -+ char count[16]; -+ -+ strncpy(count, input, 10); -+ count[11] = 0; -+ -+ tok = strtok(count,":"); -+ if (!tok) -+ goto fail; -+ tok = strtok(NULL, ""); -+ if (!tok) -+ goto fail; -+ -+ *vga_count = strtoul(tok, NULL, 10); -+ if (*vga_count == LONG_MAX) -+ goto fail; -+ -+#ifdef DEBUG -+ fprintf(stderr,"vga count is %d\n", *vga_count); -+#endif -+ -+ tok = strtok(input, ","); -+ if (!tok) -+ goto fail; -+ -+ tok = strtok(NULL, ","); -+ if (!tok) -+ goto fail; -+ tok = strtok(tok, "="); -+ if (!tok) -+ goto fail; -+ tok = strtok(NULL, "="); -+ if (!tok) -+ goto fail; -+ -+ if (!strncmp(tok, "io+mem", 6)) -+ return VGA_ARB_RSRC_LEGACY_IO | VGA_ARB_RSRC_LEGACY_MEM; -+ if (!strncmp(tok, "io", 2)) -+ return VGA_ARB_RSRC_LEGACY_IO; -+ if (!strncmp(tok, "mem", 3)) -+ return VGA_ARB_RSRC_LEGACY_MEM; -+fail: -+ return VGA_ARB_RSRC_NONE; -+} -+ -+static const char * -+rsrc_to_str(int iostate) -+{ -+ switch (iostate) { -+ case VGA_ARB_RSRC_LEGACY_IO | VGA_ARB_RSRC_LEGACY_MEM: -+ return "io+mem"; -+ case VGA_ARB_RSRC_LEGACY_IO: -+ return "io"; -+ case VGA_ARB_RSRC_LEGACY_MEM: -+ return "mem"; -+ } -+ -+ return "none"; -+} -+ -+int -+pci_device_vgaarb_set_target(struct pci_device *dev) -+{ -+ int len; -+ char buf[BUFSIZE]; -+ int ret; -+ -+ len = snprintf(buf, BUFSIZE, "target PCI:%d:%d:%d.%d", -+ dev->domain, dev->bus, dev->dev, dev->func); -+ -+ ret = vgaarb_write(pci_sys->vgaarb_fd, buf, len); -+ if (ret) -+ return ret; -+ -+ ret = read(pci_sys->vgaarb_fd, buf, BUFSIZE); -+ if (ret <= 0) -+ return -1; -+ -+ dev->vgaarb_rsrc = parse_string_to_decodes_rsrc(buf, &pci_sys->vga_count); -+ return 0; -+} -+ -+int -+pci_device_vgaarb_decodes(struct pci_device *dev, int new_vgaarb_rsrc) -+{ -+ int len; -+ char buf[BUFSIZE]; -+ int ret; -+ -+ if (dev->vgaarb_rsrc == new_vgaarb_rsrc) -+ return 0; -+ -+ len = snprintf(buf, BUFSIZE, "decodes %s", rsrc_to_str(dev->vgaarb_rsrc)); -+ ret = vgaarb_write(pci_sys->vgaarb_fd, buf, len); -+ if (ret == 0) -+ dev->vgaarb_rsrc = new_vgaarb_rsrc; -+ return ret; -+} -+ -+int -+pci_device_vgaarb_lock(struct pci_device *dev) -+{ -+ int len; -+ char buf[BUFSIZE]; -+ -+ if (dev->vgaarb_rsrc == 0 || pci_sys->vga_count == 1) -+ return 0; -+ -+ len = snprintf(buf, BUFSIZE, "lock %s", rsrc_to_str(dev->vgaarb_rsrc)); -+ -+ return vgaarb_write(pci_sys->vgaarb_fd, buf, len); -+} -+ -+int -+pci_device_vgaarb_trylock(struct pci_device *dev) -+{ -+ int len; -+ char buf[BUFSIZE]; -+ -+ if (dev->vgaarb_rsrc == 0 || pci_sys->vga_count == 1) -+ return 0; -+ -+ len = snprintf(buf, BUFSIZE, "trylock %s", rsrc_to_str(dev->vgaarb_rsrc)); -+ -+ return vgaarb_write(pci_sys->vgaarb_fd, buf, len); -+} -+ -+int -+pci_device_vgaarb_unlock(struct pci_device *dev) -+{ -+ int len; -+ char buf[BUFSIZE]; -+ -+ if (dev->vgaarb_rsrc == 0 || pci_sys->vga_count == 1) -+ return 0; -+ -+ len = snprintf(buf, BUFSIZE, "unlock %s", rsrc_to_str(dev->vgaarb_rsrc)); -+ -+ return vgaarb_write(pci_sys->vgaarb_fd, buf, len); -+} diff -up /dev/null libpciaccess-0.10.6/src/common_vgaarb_stub.c ---- /dev/null 2009-07-28 15:36:51.159175345 +1000 -+++ libpciaccess-0.10.6/src/common_vgaarb_stub.c 2009-07-31 11:29:36.000000000 +1000 +--- /dev/null 2009-08-03 09:43:13.273251881 +1000 ++++ libpciaccess-0.10.6/src/common_vgaarb_stub.c 2009-08-03 09:57:21.000000000 +1000 @@ -0,0 +1,73 @@ +/* + * Copyright (c) 2009 Tiago Vignatti @@ -432,8 +101,8 @@ diff -up /dev/null libpciaccess-0.10.6/src/common_vgaarb_stub.c + return 0; +} diff -up libpciaccess-0.10.6/src/linux_sysfs.c.da libpciaccess-0.10.6/src/linux_sysfs.c ---- libpciaccess-0.10.6/src/linux_sysfs.c.da 2009-07-31 11:29:24.000000000 +1000 -+++ libpciaccess-0.10.6/src/linux_sysfs.c 2009-07-31 11:29:36.000000000 +1000 +--- libpciaccess-0.10.6/src/linux_sysfs.c.da 2009-08-03 09:57:13.000000000 +1000 ++++ libpciaccess-0.10.6/src/linux_sysfs.c 2009-08-03 09:57:21.000000000 +1000 @@ -78,6 +78,7 @@ static int pci_device_linux_sysfs_write( pciaddr_t * bytes_written ); @@ -473,9 +142,327 @@ diff -up libpciaccess-0.10.6/src/linux_sysfs.c.da libpciaccess-0.10.6/src/linux_ + return 0; + return 1; +} +diff -up /dev/null libpciaccess-0.10.6/src/common_vgaarb.c +--- /dev/null 2009-08-03 09:43:13.273251881 +1000 ++++ libpciaccess-0.10.6/src/common_vgaarb.c 2009-08-03 09:57:21.000000000 +1000 +@@ -0,0 +1,314 @@ ++/* ++ * Copyright (c) 2007 Paulo R. Zanoni, Tiago Vignatti ++ * 2009 Tiago Vignatti ++ * ++ * Permission is hereby granted, free of charge, to any person ++ * obtaining a copy of this software and associated documentation ++ * files (the "Software"), to deal in the Software without ++ * restriction, including without limitation the rights to use, ++ * copy, modify, merge, publish, distribute, sublicense, and/or sell ++ * copies of the Software, and to permit persons to whom the ++ * Software is furnished to do so, subject to the following ++ * conditions: ++ * ++ * The above copyright notice and this permission notice shall be ++ * included in all copies or substantial portions of the Software. ++ * ++ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, ++ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES ++ * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND ++ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT ++ * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, ++ * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ++ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR ++ * OTHER DEALINGS IN THE SOFTWARE. ++ * ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#include "pciaccess.h" ++#include "pciaccess_private.h" ++ ++#define BUFSIZE 64 ++ ++static int ++parse_string_to_decodes_rsrc(char *input, int *vga_count, struct pci_slot_match *match) ++{ ++ char *tok; ++ char *input_sp, *count_sp, *pci_sp; ++ char tmp[32]; ++ ++ tok = strtok_r(input,",",&input_sp); ++ if (!tok) ++ goto fail; ++ ++ strncpy(tmp, input, 15); ++ tmp[15] = 0; ++ ++ tok = strtok_r(tmp,":",&count_sp); ++ if (!tok) ++ goto fail; ++ tok = strtok_r(NULL, ":",&count_sp); ++ if (!tok) ++ goto fail; ++ ++ *vga_count = strtoul(tok, NULL, 10); ++ if (*vga_count == LONG_MAX) ++ goto fail; ++ ++#ifdef DEBUG ++ fprintf(stderr,"vga count is %d\n", *vga_count); ++#endif ++ ++ tok = strtok_r(NULL, ",",&input_sp); ++ if (!tok) ++ goto fail; ++ ++ if (match) { ++ strncpy(tmp, tok, 32); ++ tmp[31] = 0; ++ tok = strtok_r(tmp, ":", &pci_sp); ++ if (!tok) ++ goto fail; ++ tok = strtok_r(NULL, ":", &pci_sp); ++ if (!tok) ++ goto fail; ++ match->domain = strtoul(tok, NULL, 16); ++ ++ tok = strtok_r(NULL, ":", &pci_sp); ++ if (!tok) ++ goto fail; ++ match->bus = strtoul(tok, NULL, 16); ++ ++ tok = strtok_r(NULL, ".", &pci_sp); ++ if (!tok) ++ goto fail; ++ match->dev = strtoul(tok, NULL, 16); ++ ++ tok = strtok_r(NULL, ".", &pci_sp); ++ if (!tok) ++ goto fail; ++ match->func = strtoul(tok, NULL, 16); ++ } ++ ++ tok = strtok_r(NULL, ",",&input_sp); ++ if (!tok) ++ goto fail; ++ tok = strtok_r(tok, "=", &input_sp); ++ if (!tok) ++ goto fail; ++ tok = strtok_r(NULL, "=", &input_sp); ++ if (!tok) ++ goto fail; ++ ++ if (!strncmp(tok, "io+mem", 6)) ++ return VGA_ARB_RSRC_LEGACY_IO | VGA_ARB_RSRC_LEGACY_MEM; ++ if (!strncmp(tok, "io", 2)) ++ return VGA_ARB_RSRC_LEGACY_IO; ++ if (!strncmp(tok, "mem", 3)) ++ return VGA_ARB_RSRC_LEGACY_MEM; ++fail: ++ return VGA_ARB_RSRC_NONE; ++} ++ ++int ++pci_device_vgaarb_init(void) ++{ ++ struct pci_slot_match match; ++ char buf[BUFSIZE]; ++ int ret, rsrc; ++ if ((pci_sys->vgaarb_fd = open ("/dev/vga_arbiter", O_RDWR)) < 0) { ++ return errno; ++ } ++ ++ ret = read(pci_sys->vgaarb_fd, buf, BUFSIZE); ++ if (ret <= 0) ++ return -1; ++ ++ memset(&match, 0xff, sizeof(match)); ++ /* need to find the device to go back to and what it was decoding */ ++ rsrc = parse_string_to_decodes_rsrc(buf, &pci_sys->vga_count, &match); ++ ++ pci_sys->vga_default_dev = pci_device_find_by_slot(match.domain, match.bus, match.dev, match.func); ++ ++ if (pci_sys->vga_default_dev) ++ pci_sys->vga_default_dev->vgaarb_rsrc = rsrc; ++ return 0; ++} ++ ++void ++pci_device_vgaarb_fini(void) ++{ ++ close(pci_sys->vgaarb_fd); ++} ++ ++/** ++ * Writes message on vga device. The messages are defined by the kernel ++ * implementation. ++ * ++ * \param fd vga arbiter device. ++ * \param buf message itself. ++ * \param len message length. ++ * ++ * \return ++ * Zero on success, 1 if something gets wrong and 2 if fd is busy (only for ++ * 'trylock') ++ */ ++static int ++vgaarb_write(int fd, char *buf, int len) ++{ ++ int ret; ++ ++ ++ buf[len] = '\0'; ++ ++ ret = write(fd, buf, len); ++ if (ret == -1) { ++ /* the user may have called "trylock" and didn't get the lock */ ++ if (errno == EBUSY) ++ return 2; ++ ++#ifdef DEBUG ++ fprintf(stderr, "write error"); ++#endif ++ return 1; ++ } ++ else if (ret != len) { ++ /* it's need to receive the exactly amount required. */ ++#ifdef DEBUG ++ fprintf(stderr, "write error: wrote different than expected\n"); ++#endif ++ return 1; ++ } ++ ++#ifdef DEBUG ++ fprintf(stderr, "%s: successfully wrote: '%s'\n", __FUNCTION__, buf); ++#endif ++ ++ return 0; ++} ++ ++ ++static const char * ++rsrc_to_str(int iostate) ++{ ++ switch (iostate) { ++ case VGA_ARB_RSRC_LEGACY_IO | VGA_ARB_RSRC_LEGACY_MEM: ++ return "io+mem"; ++ case VGA_ARB_RSRC_LEGACY_IO: ++ return "io"; ++ case VGA_ARB_RSRC_LEGACY_MEM: ++ return "mem"; ++ } ++ ++ return "none"; ++} ++ ++int ++pci_device_vgaarb_set_target(struct pci_device *dev) ++{ ++ int len; ++ char buf[BUFSIZE]; ++ int ret; ++ ++ if (!dev) ++ dev = pci_sys->vga_default_dev; ++ if (!dev) ++ return -1; ++ ++ len = snprintf(buf, BUFSIZE, "target PCI:%04x:%02x:%02x.%x", ++ dev->domain, dev->bus, dev->dev, dev->func); ++ ++ ret = vgaarb_write(pci_sys->vgaarb_fd, buf, len); ++ if (ret) ++ return ret; ++ ++ ret = read(pci_sys->vgaarb_fd, buf, BUFSIZE); ++ if (ret <= 0) ++ return -1; ++ ++ dev->vgaarb_rsrc = parse_string_to_decodes_rsrc(buf, &pci_sys->vga_count, NULL); ++ pci_sys->vga_target = dev; ++ return 0; ++} ++ ++int ++pci_device_vgaarb_decodes(int new_vgaarb_rsrc) ++{ ++ int len; ++ char buf[BUFSIZE]; ++ int ret; ++ struct pci_device *dev = pci_sys->vga_target; ++ ++ if (!dev) ++ return -1; ++ if (dev->vgaarb_rsrc == new_vgaarb_rsrc) ++ return 0; ++ ++ len = snprintf(buf, BUFSIZE, "decodes %s", rsrc_to_str(dev->vgaarb_rsrc)); ++ ret = vgaarb_write(pci_sys->vgaarb_fd, buf, len); ++ if (ret == 0) ++ dev->vgaarb_rsrc = new_vgaarb_rsrc; ++ return ret; ++} ++ ++int ++pci_device_vgaarb_lock(void) ++{ ++ int len; ++ char buf[BUFSIZE]; ++ struct pci_device *dev = pci_sys->vga_target; ++ ++ if (!dev) ++ return -1; ++ ++ if (dev->vgaarb_rsrc == 0 || pci_sys->vga_count == 1) ++ return 0; ++ ++ len = snprintf(buf, BUFSIZE, "lock %s", rsrc_to_str(dev->vgaarb_rsrc)); ++ ++ return vgaarb_write(pci_sys->vgaarb_fd, buf, len); ++} ++ ++int ++pci_device_vgaarb_trylock(void) ++{ ++ int len; ++ char buf[BUFSIZE]; ++ struct pci_device *dev = pci_sys->vga_target; ++ ++ if (!dev) ++ return -1; ++ ++ if (dev->vgaarb_rsrc == 0 || pci_sys->vga_count == 1) ++ return 0; ++ ++ len = snprintf(buf, BUFSIZE, "trylock %s", rsrc_to_str(dev->vgaarb_rsrc)); ++ ++ return vgaarb_write(pci_sys->vgaarb_fd, buf, len); ++} ++ ++int ++pci_device_vgaarb_unlock(void) ++{ ++ int len; ++ char buf[BUFSIZE]; ++ struct pci_device *dev = pci_sys->vga_target; ++ ++ if (!dev) ++ return -1; ++ ++ if (dev->vgaarb_rsrc == 0 || pci_sys->vga_count == 1) ++ return 0; ++ ++ len = snprintf(buf, BUFSIZE, "unlock %s", rsrc_to_str(dev->vgaarb_rsrc)); ++ ++ return vgaarb_write(pci_sys->vgaarb_fd, buf, len); ++} diff -up libpciaccess-0.10.6/src/Makefile.am.da libpciaccess-0.10.6/src/Makefile.am --- libpciaccess-0.10.6/src/Makefile.am.da 2009-04-18 15:01:36.000000000 +1000 -+++ libpciaccess-0.10.6/src/Makefile.am 2009-07-31 11:29:36.000000000 +1000 ++++ libpciaccess-0.10.6/src/Makefile.am 2009-08-03 09:57:21.000000000 +1000 @@ -45,6 +45,12 @@ if SOLARIS OS_SUPPORT = solx_devfs.c pci_tools.h endif @@ -498,8 +485,8 @@ diff -up libpciaccess-0.10.6/src/Makefile.am.da libpciaccess-0.10.6/src/Makefile INCLUDES = -I$(top_srcdir)/include diff -up libpciaccess-0.10.6/src/pciaccess_private.h.da libpciaccess-0.10.6/src/pciaccess_private.h ---- libpciaccess-0.10.6/src/pciaccess_private.h.da 2009-07-31 11:29:24.000000000 +1000 -+++ libpciaccess-0.10.6/src/pciaccess_private.h 2009-07-31 11:29:36.000000000 +1000 +--- libpciaccess-0.10.6/src/pciaccess_private.h.da 2009-08-03 09:57:13.000000000 +1000 ++++ libpciaccess-0.10.6/src/pciaccess_private.h 2009-08-03 09:57:21.000000000 +1000 @@ -61,6 +61,7 @@ struct pci_system_methods { int (*fill_capabilities)( struct pci_device * dev ); void (*enable)( struct pci_device *dev ); @@ -508,12 +495,97 @@ diff -up libpciaccess-0.10.6/src/pciaccess_private.h.da libpciaccess-0.10.6/src/ }; struct pci_device_mapping { -@@ -131,6 +132,8 @@ struct pci_system { +@@ -131,6 +132,10 @@ struct pci_system { #ifdef HAVE_MTRR int mtrr_fd; #endif + int vgaarb_fd; + int vga_count; ++ struct pci_device *vga_target; ++ struct pci_device *vga_default_dev; }; extern struct pci_system * pci_sys; +diff -up libpciaccess-0.10.6/include/pciaccess.h.da libpciaccess-0.10.6/include/pciaccess.h +--- libpciaccess-0.10.6/include/pciaccess.h.da 2009-08-03 09:57:13.000000000 +1000 ++++ libpciaccess-0.10.6/include/pciaccess.h 2009-08-03 09:57:21.000000000 +1000 +@@ -21,6 +21,31 @@ + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ ++/* ++ * Copyright (c) 2007 Paulo R. Zanoni, Tiago Vignatti ++ * ++ * Permission is hereby granted, free of charge, to any person ++ * obtaining a copy of this software and associated documentation ++ * files (the "Software"), to deal in the Software without ++ * restriction, including without limitation the rights to use, ++ * copy, modify, merge, publish, distribute, sublicense, and/or sell ++ * copies of the Software, and to permit persons to whom the ++ * Software is furnished to do so, subject to the following ++ * conditions: ++ * ++ * The above copyright notice and this permission notice shall be ++ * included in all copies or substantial portions of the Software. ++ * ++ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, ++ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES ++ * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND ++ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT ++ * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, ++ * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING ++ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR ++ * OTHER DEALINGS IN THE SOFTWARE. ++ * ++ */ + + /** + * \file pciaccess.h +@@ -50,6 +75,8 @@ struct pci_slot_match; + extern "C" { + #endif + ++int pci_device_has_kernel_driver(struct pci_device *dev); ++ + int pci_device_is_boot_vga(struct pci_device *dev); + + int pci_device_read_rom(struct pci_device *dev, void *buffer); +@@ -350,6 +377,11 @@ struct pci_device { + * the \c pci_device structure. + */ + intptr_t user_data; ++ ++ /** ++ * Used by the VGA arbiter. Type of resource decoded by the device and ++ * the file descriptor (/dev/vga_arbiter). */ ++ int vgaarb_rsrc; + }; + + +@@ -449,4 +481,26 @@ struct pci_pcmcia_bridge_info { + + }; + ++ ++/** ++ * VGA Arbiter definitions, functions and related. ++ */ ++ ++/* Legacy VGA regions */ ++#define VGA_ARB_RSRC_NONE 0x00 ++#define VGA_ARB_RSRC_LEGACY_IO 0x01 ++#define VGA_ARB_RSRC_LEGACY_MEM 0x02 ++/* Non-legacy access */ ++#define VGA_ARB_RSRC_NORMAL_IO 0x04 ++#define VGA_ARB_RSRC_NORMAL_MEM 0x08 ++ ++int pci_device_vgaarb_init (void); ++void pci_device_vgaarb_fini (void); ++int pci_device_vgaarb_set_target (struct pci_device *dev); ++/* use the targetted device */ ++int pci_device_vgaarb_decodes (int new_vga_rsrc); ++int pci_device_vgaarb_lock (void); ++int pci_device_vgaarb_trylock (void); ++int pci_device_vgaarb_unlock (void); ++ + #endif /* PCIACCESS_H */ diff --git a/libpciaccess.spec b/libpciaccess.spec index 56ad30c..2275d46 100644 --- a/libpciaccess.spec +++ b/libpciaccess.spec @@ -3,7 +3,7 @@ Name: libpciaccess Version: 0.10.6 -Release: 3%{?dist} +Release: 4%{?dist} Summary: PCI access library Group: System Environment/Libraries @@ -74,6 +74,10 @@ rm -rf $RPM_BUILD_ROOT %{_libdir}/pkgconfig/pciaccess.pc %changelog +* Mon Aug 03 2009 Dave Airlie 0.10.6-4 +- Add support for default vga arb device selection +- Update libpciaccess VGA arb code for newer kernel API + * Fri Jul 31 2009 Dave Airlie 0.10.6-3 - enable autoreconf to rebuild configure properly