win-pvdrivers

view xenpci/gnttbl.c @ 265:8fef16f8fc08

fix warnings on x64 build. Xen apparently limits PFNs to 32 bits, so make this limitation stand out a little more
author Andy Grover <andy.grover@oracle.com>
date Mon May 05 13:24:03 2008 -0700 (2008-05-05)
parents 2d25f964e1d1
children 3673f1f07746
line source
1 /*
2 PV Drivers for Windows Xen HVM Domains
3 Copyright (C) 2007 James Harper
5 This program is free software; you can redistribute it and/or
6 modify it under the terms of the GNU General Public License
7 as published by the Free Software Foundation; either version 2
8 of the License, or (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
18 */
20 #include "xenpci.h"
22 VOID
23 GntTbl_PutRef(WDFDEVICE Device, grant_ref_t ref)
24 {
25 PXENPCI_DEVICE_DATA xpdd = GetDeviceData(Device);
26 KIRQL OldIrql;
28 KeAcquireSpinLock(&xpdd->grant_lock, &OldIrql);
29 xpdd->gnttab_list[ref] = xpdd->gnttab_list[0];
30 xpdd->gnttab_list[0] = ref;
31 KeReleaseSpinLock(&xpdd->grant_lock, OldIrql);
32 }
34 grant_ref_t
35 GntTbl_GetRef(WDFDEVICE Device)
36 {
37 PXENPCI_DEVICE_DATA xpdd = GetDeviceData(Device);
38 unsigned int ref;
39 KIRQL OldIrql;
41 KeAcquireSpinLock(&xpdd->grant_lock, &OldIrql);
42 ref = xpdd->gnttab_list[0];
43 xpdd->gnttab_list[0] = xpdd->gnttab_list[ref];
44 KeReleaseSpinLock(&xpdd->grant_lock, OldIrql);
46 return ref;
47 }
49 static int
50 GntTbl_Map(WDFDEVICE Device, unsigned int start_idx, unsigned int end_idx)
51 {
52 PXENPCI_DEVICE_DATA xpdd = GetDeviceData(Device);
53 struct xen_add_to_physmap xatp;
54 unsigned int i = end_idx;
56 //KdPrint((__DRIVER_NAME " --> GntTbl_Init\n"));
57 /* Loop backwards, so that the first hypercall has the largest index,
58 * ensuring that the table will grow only once.
59 */
60 do {
61 xatp.domid = DOMID_SELF;
62 xatp.idx = i;
63 xatp.space = XENMAPSPACE_grant_table;
64 xatp.gpfn = (xen_pfn_t)(xpdd->gnttab_table_physical.QuadPart >> PAGE_SHIFT) + i;
65 if (HYPERVISOR_memory_op(Device, XENMEM_add_to_physmap, &xatp))
66 {
67 KdPrint((__DRIVER_NAME " ***ERROR MAPPING FRAME***\n"));
68 }
69 } while (i-- > start_idx);
71 return 0;
72 }
74 VOID
75 GntTbl_Init(WDFDEVICE Device)
76 {
77 PXENPCI_DEVICE_DATA xpdd = GetDeviceData(Device);
78 int i;
80 //KdPrint((__DRIVER_NAME " --> GntTbl_Init\n"));
83 KeInitializeSpinLock(&xpdd->grant_lock);
85 for (i = NR_RESERVED_ENTRIES; i < NR_GRANT_ENTRIES; i++)
86 GntTbl_PutRef(Device, i);
88 xpdd->gnttab_table_physical = XenPCI_AllocMMIO(Device,
89 PAGE_SIZE * NR_GRANT_FRAMES);
90 xpdd->gnttab_table = MmMapIoSpace(xpdd->gnttab_table_physical,
91 PAGE_SIZE * NR_GRANT_FRAMES, MmCached);
92 if (!xpdd->gnttab_table)
93 {
94 KdPrint((__DRIVER_NAME " Error Mapping Grant Table Shared Memory\n"));
95 return;
96 }
97 GntTbl_Map(Device, 0, NR_GRANT_FRAMES - 1);
99 //KdPrint((__DRIVER_NAME " <-- GntTbl_Init table mapped at %p\n", gnttab_table));
100 }
102 grant_ref_t
103 GntTbl_GrantAccess(
104 WDFDEVICE Device,
105 domid_t domid,
106 uint32_t frame, // xen api limits pfn to 32bit, so no guests over 8TB
107 int readonly,
108 grant_ref_t ref)
109 {
110 PXENPCI_DEVICE_DATA xpdd = GetDeviceData(Device);
112 //KdPrint((__DRIVER_NAME " --> GntTbl_GrantAccess\n"));
114 //KdPrint((__DRIVER_NAME " Granting access to frame %08x\n", frame));
116 if (ref == 0)
117 ref = GntTbl_GetRef(Device);
118 xpdd->gnttab_table[ref].frame = frame;
119 xpdd->gnttab_table[ref].domid = domid;
121 if (xpdd->gnttab_table[ref].flags)
122 KdPrint((__DRIVER_NAME " WARNING: Attempting to re-use grant entry that is already in use!\n"));
124 KeMemoryBarrier();
125 readonly *= GTF_readonly;
126 xpdd->gnttab_table[ref].flags = GTF_permit_access | (uint16_t)readonly;
128 //KdPrint((__DRIVER_NAME " <-- GntTbl_GrantAccess (ref = %d)\n", ref));
130 return ref;
131 }
133 BOOLEAN
134 GntTbl_EndAccess(
135 WDFDEVICE Device,
136 grant_ref_t ref,
137 BOOLEAN keepref)
138 {
139 PXENPCI_DEVICE_DATA xpdd = GetDeviceData(Device);
140 unsigned short flags, nflags;
142 //KdPrint((__DRIVER_NAME " --> GntTbl_EndAccess\n"));
144 nflags = xpdd->gnttab_table[ref].flags;
145 do {
146 if ((flags = nflags) & (GTF_reading|GTF_writing))
147 {
148 KdPrint((__DRIVER_NAME "WARNING: g.e. still in use!\n"));
149 return FALSE;
150 }
151 } while ((nflags = InterlockedCompareExchange16(
152 (volatile SHORT *)&xpdd->gnttab_table[ref].flags, 0, flags)) != flags);
154 if (!keepref)
155 GntTbl_PutRef(Device, ref);
156 //KdPrint((__DRIVER_NAME " <-- GntTbl_EndAccess\n"));
157 return TRUE;
158 }