ia64/linux-2.6.18-xen.hg

view arch/sparc/prom/mp.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 831230e53067
children
line source
1 /* $Id: mp.c,v 1.12 2000/08/26 02:38:03 anton Exp $
2 * mp.c: OpenBoot Prom Multiprocessor support routines. Don't call
3 * these on a UP or else you will halt and catch fire. ;)
4 *
5 * Copyright (C) 1995 David S. Miller (davem@caip.rutgers.edu)
6 */
8 #include <linux/types.h>
9 #include <linux/kernel.h>
10 #include <linux/sched.h>
12 #include <asm/openprom.h>
13 #include <asm/oplib.h>
15 extern void restore_current(void);
17 /* Start cpu with prom-tree node 'cpunode' using context described
18 * by 'ctable_reg' in context 'ctx' at program counter 'pc'.
19 *
20 * XXX Have to look into what the return values mean. XXX
21 */
22 int
23 prom_startcpu(int cpunode, struct linux_prom_registers *ctable_reg, int ctx, char *pc)
24 {
25 int ret;
26 unsigned long flags;
28 spin_lock_irqsave(&prom_lock, flags);
29 switch(prom_vers) {
30 case PROM_V0:
31 case PROM_V2:
32 default:
33 ret = -1;
34 break;
35 case PROM_V3:
36 ret = (*(romvec->v3_cpustart))(cpunode, (int) ctable_reg, ctx, pc);
37 break;
38 };
39 restore_current();
40 spin_unlock_irqrestore(&prom_lock, flags);
42 return ret;
43 }
45 /* Stop CPU with device prom-tree node 'cpunode'.
46 * XXX Again, what does the return value really mean? XXX
47 */
48 int
49 prom_stopcpu(int cpunode)
50 {
51 int ret;
52 unsigned long flags;
54 spin_lock_irqsave(&prom_lock, flags);
55 switch(prom_vers) {
56 case PROM_V0:
57 case PROM_V2:
58 default:
59 ret = -1;
60 break;
61 case PROM_V3:
62 ret = (*(romvec->v3_cpustop))(cpunode);
63 break;
64 };
65 restore_current();
66 spin_unlock_irqrestore(&prom_lock, flags);
68 return ret;
69 }
71 /* Make CPU with device prom-tree node 'cpunode' idle.
72 * XXX Return value, anyone? XXX
73 */
74 int
75 prom_idlecpu(int cpunode)
76 {
77 int ret;
78 unsigned long flags;
80 spin_lock_irqsave(&prom_lock, flags);
81 switch(prom_vers) {
82 case PROM_V0:
83 case PROM_V2:
84 default:
85 ret = -1;
86 break;
87 case PROM_V3:
88 ret = (*(romvec->v3_cpuidle))(cpunode);
89 break;
90 };
91 restore_current();
92 spin_unlock_irqrestore(&prom_lock, flags);
94 return ret;
95 }
97 /* Resume the execution of CPU with nodeid 'cpunode'.
98 * XXX Come on, somebody has to know... XXX
99 */
100 int
101 prom_restartcpu(int cpunode)
102 {
103 int ret;
104 unsigned long flags;
106 spin_lock_irqsave(&prom_lock, flags);
107 switch(prom_vers) {
108 case PROM_V0:
109 case PROM_V2:
110 default:
111 ret = -1;
112 break;
113 case PROM_V3:
114 ret = (*(romvec->v3_cpuresume))(cpunode);
115 break;
116 };
117 restore_current();
118 spin_unlock_irqrestore(&prom_lock, flags);
120 return ret;
121 }