ia64/linux-2.6.18-xen.hg

view drivers/acpi/pci_root.c @ 897:329ea0ccb344

balloon: try harder to balloon up under memory pressure.

Currently if the balloon driver is unable to increase the guest's
reservation it assumes the failure was due to reaching its full
allocation, gives up on the ballooning operation and records the limit
it reached as the "hard limit". The driver will not try again until
the target is set again (even to the same value).

However it is possible that ballooning has in fact failed due to
memory pressure in the host and therefore it is desirable to keep
attempting to reach the target in case memory becomes available. The
most likely scenario is that some guests are ballooning down while
others are ballooning up and therefore there is temporary memory
pressure while things stabilise. You would not expect a well behaved
toolstack to ask a domain to balloon to more than its allocation nor
would you expect it to deliberately over-commit memory by setting
balloon targets which exceed the total host memory.

This patch drops the concept of a hard limit and causes the balloon
driver to retry increasing the reservation on a timer in the same
manner as when decreasing the reservation.

Also if we partially succeed in increasing the reservation
(i.e. receive less pages than we asked for) then we may as well keep
those pages rather than returning them to Xen.

Signed-off-by: Ian Campbell <ian.campbell@citrix.com>
author Keir Fraser <keir.fraser@citrix.com>
date Fri Jun 05 14:01:20 2009 +0100 (2009-06-05)
parents 2fdc121e9b5d
children
line source
1 /*
2 * pci_root.c - ACPI PCI Root Bridge Driver ($Revision: 40 $)
3 *
4 * Copyright (C) 2001, 2002 Andy Grover <andrew.grover@intel.com>
5 * Copyright (C) 2001, 2002 Paul Diefenbaugh <paul.s.diefenbaugh@intel.com>
6 *
7 * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
8 *
9 * This program is free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License as published by
11 * the Free Software Foundation; either version 2 of the License, or (at
12 * your option) any later version.
13 *
14 * This program is distributed in the hope that it will be useful, but
15 * WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17 * General Public License for more details.
18 *
19 * You should have received a copy of the GNU General Public License along
20 * with this program; if not, write to the Free Software Foundation, Inc.,
21 * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
22 *
23 * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
24 */
26 #include <linux/kernel.h>
27 #include <linux/module.h>
28 #include <linux/init.h>
29 #include <linux/types.h>
30 #include <linux/proc_fs.h>
31 #include <linux/spinlock.h>
32 #include <linux/pm.h>
33 #include <linux/pci.h>
34 #include <linux/acpi.h>
35 #include <acpi/acpi_bus.h>
36 #include <acpi/acpi_drivers.h>
38 #define _COMPONENT ACPI_PCI_COMPONENT
39 ACPI_MODULE_NAME("pci_root")
40 #define ACPI_PCI_ROOT_CLASS "pci_bridge"
41 #define ACPI_PCI_ROOT_HID "PNP0A03"
42 #define ACPI_PCI_ROOT_DRIVER_NAME "ACPI PCI Root Bridge Driver"
43 #define ACPI_PCI_ROOT_DEVICE_NAME "PCI Root Bridge"
44 static int acpi_pci_root_add(struct acpi_device *device);
45 static int acpi_pci_root_remove(struct acpi_device *device, int type);
46 static int acpi_pci_root_start(struct acpi_device *device);
48 static struct acpi_driver acpi_pci_root_driver = {
49 .name = ACPI_PCI_ROOT_DRIVER_NAME,
50 .class = ACPI_PCI_ROOT_CLASS,
51 .ids = ACPI_PCI_ROOT_HID,
52 .ops = {
53 .add = acpi_pci_root_add,
54 .remove = acpi_pci_root_remove,
55 .start = acpi_pci_root_start,
56 },
57 };
59 struct acpi_pci_root {
60 struct list_head node;
61 struct acpi_device * device;
62 struct acpi_pci_id id;
63 struct pci_bus *bus;
64 };
66 static LIST_HEAD(acpi_pci_roots);
68 static struct acpi_pci_driver *sub_driver;
70 int acpi_pci_register_driver(struct acpi_pci_driver *driver)
71 {
72 int n = 0;
73 struct list_head *entry;
75 struct acpi_pci_driver **pptr = &sub_driver;
76 while (*pptr)
77 pptr = &(*pptr)->next;
78 *pptr = driver;
80 if (!driver->add)
81 return 0;
83 list_for_each(entry, &acpi_pci_roots) {
84 struct acpi_pci_root *root;
85 root = list_entry(entry, struct acpi_pci_root, node);
86 driver->add(root->device->handle);
87 n++;
88 }
90 return n;
91 }
93 EXPORT_SYMBOL(acpi_pci_register_driver);
95 void acpi_pci_unregister_driver(struct acpi_pci_driver *driver)
96 {
97 struct list_head *entry;
99 struct acpi_pci_driver **pptr = &sub_driver;
100 while (*pptr) {
101 if (*pptr != driver)
102 continue;
103 *pptr = (*pptr)->next;
104 break;
105 }
107 if (!driver->remove)
108 return;
110 list_for_each(entry, &acpi_pci_roots) {
111 struct acpi_pci_root *root;
112 root = list_entry(entry, struct acpi_pci_root, node);
113 driver->remove(root->device->handle);
114 }
115 }
117 EXPORT_SYMBOL(acpi_pci_unregister_driver);
119 static acpi_status
120 get_root_bridge_busnr_callback(struct acpi_resource *resource, void *data)
121 {
122 int *busnr = (int *)data;
123 struct acpi_resource_address64 address;
125 if (resource->type != ACPI_RESOURCE_TYPE_ADDRESS16 &&
126 resource->type != ACPI_RESOURCE_TYPE_ADDRESS32 &&
127 resource->type != ACPI_RESOURCE_TYPE_ADDRESS64)
128 return AE_OK;
130 acpi_resource_to_address64(resource, &address);
131 if ((address.address_length > 0) &&
132 (address.resource_type == ACPI_BUS_NUMBER_RANGE))
133 *busnr = address.minimum;
135 return AE_OK;
136 }
138 static acpi_status try_get_root_bridge_busnr(acpi_handle handle, int *busnum)
139 {
140 acpi_status status;
142 *busnum = -1;
143 status =
144 acpi_walk_resources(handle, METHOD_NAME__CRS,
145 get_root_bridge_busnr_callback, busnum);
146 if (ACPI_FAILURE(status))
147 return status;
148 /* Check if we really get a bus number from _CRS */
149 if (*busnum == -1)
150 return AE_ERROR;
151 return AE_OK;
152 }
154 ssize_t
155 acpi_device_seg_show(struct acpi_device *acpi_dev, char *buf)
156 {
157 struct list_head *entry;
159 list_for_each(entry, &acpi_pci_roots) {
160 struct acpi_pci_root *root;
161 root = list_entry(entry, struct acpi_pci_root, node);
162 if (root->device == acpi_dev)
163 return sprintf(buf, "%04x\n", root->id.segment);
164 }
165 return 0;
166 }
167 ACPI_DEVICE_ATTR(seg, 0444, acpi_device_seg_show, NULL);
169 ssize_t
170 acpi_device_bbn_show(struct acpi_device *acpi_dev, char *buf)
171 {
172 struct list_head *entry;
174 list_for_each(entry, &acpi_pci_roots) {
175 struct acpi_pci_root *root;
176 root = list_entry(entry, struct acpi_pci_root, node);
177 if (root->device == acpi_dev)
178 return sprintf(buf, "%02x\n", root->id.bus);
179 }
180 return 0;
181 }
182 ACPI_DEVICE_ATTR(bbn, 0444, acpi_device_bbn_show, NULL);
184 static int acpi_pci_root_add(struct acpi_device *device)
185 {
186 int result = 0;
187 struct acpi_pci_root *root = NULL;
188 struct acpi_pci_root *tmp;
189 acpi_status status = AE_OK;
190 unsigned long value = 0;
191 acpi_handle handle = NULL;
194 if (!device)
195 return -EINVAL;
197 root = kmalloc(sizeof(struct acpi_pci_root), GFP_KERNEL);
198 if (!root)
199 return -ENOMEM;
200 memset(root, 0, sizeof(struct acpi_pci_root));
201 INIT_LIST_HEAD(&root->node);
203 root->device = device;
204 strcpy(acpi_device_name(device), ACPI_PCI_ROOT_DEVICE_NAME);
205 strcpy(acpi_device_class(device), ACPI_PCI_ROOT_CLASS);
206 acpi_driver_data(device) = root;
208 /*
209 * TBD: Doesn't the bus driver automatically set this?
210 */
211 device->ops.bind = acpi_pci_bind;
213 /*
214 * Segment
215 * -------
216 * Obtained via _SEG, if exists, otherwise assumed to be zero (0).
217 */
218 status = acpi_evaluate_integer(device->handle, METHOD_NAME__SEG, NULL,
219 &value);
220 switch (status) {
221 case AE_OK:
222 root->id.segment = (u16) value;
223 break;
224 case AE_NOT_FOUND:
225 ACPI_DEBUG_PRINT((ACPI_DB_INFO,
226 "Assuming segment 0 (no _SEG)\n"));
227 root->id.segment = 0;
228 break;
229 default:
230 ACPI_EXCEPTION((AE_INFO, status, "Evaluating _SEG"));
231 result = -ENODEV;
232 goto end;
233 }
235 /*
236 * Bus
237 * ---
238 * Obtained via _BBN, if exists, otherwise assumed to be zero (0).
239 */
240 status = acpi_evaluate_integer(device->handle, METHOD_NAME__BBN, NULL,
241 &value);
242 switch (status) {
243 case AE_OK:
244 root->id.bus = (u16) value;
245 break;
246 case AE_NOT_FOUND:
247 ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Assuming bus 0 (no _BBN)\n"));
248 root->id.bus = 0;
249 break;
250 default:
251 ACPI_EXCEPTION((AE_INFO, status, "Evaluating _BBN"));
252 result = -ENODEV;
253 goto end;
254 }
256 /* Some systems have wrong _BBN */
257 list_for_each_entry(tmp, &acpi_pci_roots, node) {
258 if ((tmp->id.segment == root->id.segment)
259 && (tmp->id.bus == root->id.bus)) {
260 int bus = 0;
261 acpi_status status;
263 printk(KERN_ERR PREFIX
264 "Wrong _BBN value, reboot"
265 " and use option 'pci=noacpi'\n");
267 status = try_get_root_bridge_busnr(device->handle, &bus);
268 if (ACPI_FAILURE(status))
269 break;
270 if (bus != root->id.bus) {
271 printk(KERN_INFO PREFIX
272 "PCI _CRS %d overrides _BBN 0\n", bus);
273 root->id.bus = bus;
274 }
275 break;
276 }
277 }
278 /*
279 * Device & Function
280 * -----------------
281 * Obtained from _ADR (which has already been evaluated for us).
282 */
283 root->id.device = device->pnp.bus_address >> 16;
284 root->id.function = device->pnp.bus_address & 0xFFFF;
286 /*
287 * TBD: Need PCI interface for enumeration/configuration of roots.
288 */
290 /* TBD: Locking */
291 list_add_tail(&root->node, &acpi_pci_roots);
293 printk(KERN_INFO PREFIX "%s [%s] (%04x:%02x)\n",
294 acpi_device_name(device), acpi_device_bid(device),
295 root->id.segment, root->id.bus);
297 /*
298 * Scan the Root Bridge
299 * --------------------
300 * Must do this prior to any attempt to bind the root device, as the
301 * PCI namespace does not get created until this call is made (and
302 * thus the root bridge's pci_dev does not exist).
303 */
304 root->bus = pci_acpi_scan_root(device, root->id.segment, root->id.bus);
305 if (!root->bus) {
306 printk(KERN_ERR PREFIX
307 "Bus %04x:%02x not present in PCI namespace\n",
308 root->id.segment, root->id.bus);
309 result = -ENODEV;
310 goto end;
311 }
313 /*
314 * Attach ACPI-PCI Context
315 * -----------------------
316 * Thus binding the ACPI and PCI devices.
317 */
318 result = acpi_pci_bind_root(device, &root->id, root->bus);
319 if (result)
320 goto end;
322 /*
323 * PCI Routing Table
324 * -----------------
325 * Evaluate and parse _PRT, if exists.
326 */
327 status = acpi_get_handle(device->handle, METHOD_NAME__PRT, &handle);
328 if (ACPI_SUCCESS(status))
329 result = acpi_pci_irq_add_prt(device->handle, root->id.segment,
330 root->id.bus);
331 if (result)
332 goto end;
334 sysfs_create_file(&device->kobj, &acpi_device_attr_seg.attr);
336 sysfs_create_file(&device->kobj, &acpi_device_attr_bbn.attr);
338 end:
339 if (result) {
340 if (!list_empty(&root->node))
341 list_del(&root->node);
342 kfree(root);
343 }
345 return result;
346 }
348 static int acpi_pci_root_start(struct acpi_device *device)
349 {
350 struct acpi_pci_root *root;
353 list_for_each_entry(root, &acpi_pci_roots, node) {
354 if (root->device == device) {
355 pci_bus_add_devices(root->bus);
356 return 0;
357 }
358 }
359 return -ENODEV;
360 }
362 static int acpi_pci_root_remove(struct acpi_device *device, int type)
363 {
364 struct acpi_pci_root *root = NULL;
367 if (!device || !acpi_driver_data(device))
368 return -EINVAL;
370 root = (struct acpi_pci_root *)acpi_driver_data(device);
372 kfree(root);
374 return 0;
375 }
377 static int __init acpi_pci_root_init(void)
378 {
380 if (acpi_pci_disabled)
381 return 0;
383 /* DEBUG:
384 acpi_dbg_layer = ACPI_PCI_COMPONENT;
385 acpi_dbg_level = 0xFFFFFFFF;
386 */
388 if (acpi_bus_register_driver(&acpi_pci_root_driver) < 0)
389 return -ENODEV;
391 return 0;
392 }
394 subsys_initcall(acpi_pci_root_init);
396 int acpi_pci_get_root_seg_bbn(char *hid, char *uid, int *seg, int *bbn)
397 {
398 struct list_head *entry;
400 list_for_each(entry, &acpi_pci_roots) {
401 struct acpi_pci_root *root;
402 root = list_entry(entry, struct acpi_pci_root, node);
403 if (!root->device->flags.hardware_id)
404 continue;
406 if (strcmp(root->device->pnp.hardware_id, hid))
407 continue;
409 if (!root->device->flags.unique_id) {
410 if (strlen(uid))
411 continue;
412 } else {
413 if (strcmp(root->device->pnp.unique_id, uid))
414 continue;
415 }
417 *seg = (int)root->id.segment;
418 *bbn = (int)root->id.bus;
419 return TRUE;
420 }
421 return FALSE;
422 }
423 EXPORT_SYMBOL(acpi_pci_get_root_seg_bbn);