ia64/linux-2.6.18-xen.hg

view drivers/net/ixp2000/caleb.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 /*
2 * Helper functions for the SPI-3 bridge FPGA on the Radisys ENP2611
3 * Copyright (C) 2004, 2005 Lennert Buytenhek <buytenh@wantstofly.org>
4 * Dedicated to Marija Kulikova.
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 */
12 #include <linux/module.h>
13 #include <linux/delay.h>
14 #include <asm/io.h>
15 #include "caleb.h"
17 #define CALEB_IDLO 0x00
18 #define CALEB_IDHI 0x01
19 #define CALEB_RID 0x02
20 #define CALEB_RESET 0x03
21 #define CALEB_INTREN0 0x04
22 #define CALEB_INTREN1 0x05
23 #define CALEB_INTRSTAT0 0x06
24 #define CALEB_INTRSTAT1 0x07
25 #define CALEB_PORTEN 0x08
26 #define CALEB_BURST 0x09
27 #define CALEB_PORTPAUS 0x0A
28 #define CALEB_PORTPAUSD 0x0B
29 #define CALEB_PHY0RX 0x10
30 #define CALEB_PHY1RX 0x11
31 #define CALEB_PHY0TX 0x12
32 #define CALEB_PHY1TX 0x13
33 #define CALEB_IXPRX_HI_CNTR 0x15
34 #define CALEB_PHY0RX_HI_CNTR 0x16
35 #define CALEB_PHY1RX_HI_CNTR 0x17
36 #define CALEB_IXPRX_CNTR 0x18
37 #define CALEB_PHY0RX_CNTR 0x19
38 #define CALEB_PHY1RX_CNTR 0x1A
39 #define CALEB_IXPTX_CNTR 0x1B
40 #define CALEB_PHY0TX_CNTR 0x1C
41 #define CALEB_PHY1TX_CNTR 0x1D
42 #define CALEB_DEBUG0 0x1E
43 #define CALEB_DEBUG1 0x1F
46 static u8 caleb_reg_read(int reg)
47 {
48 u8 value;
50 value = *((volatile u8 *)(ENP2611_CALEB_VIRT_BASE + reg));
52 // printk(KERN_INFO "caleb_reg_read(%d) = %.2x\n", reg, value);
54 return value;
55 }
57 static void caleb_reg_write(int reg, u8 value)
58 {
59 u8 dummy;
61 // printk(KERN_INFO "caleb_reg_write(%d, %.2x)\n", reg, value);
63 *((volatile u8 *)(ENP2611_CALEB_VIRT_BASE + reg)) = value;
65 dummy = *((volatile u8 *)ENP2611_CALEB_VIRT_BASE);
66 __asm__ __volatile__("mov %0, %0" : "+r" (dummy));
67 }
70 void caleb_reset(void)
71 {
72 /*
73 * Perform a chip reset.
74 */
75 caleb_reg_write(CALEB_RESET, 0x02);
76 udelay(1);
78 /*
79 * Enable all interrupt sources. This is needed to get
80 * meaningful results out of the status bits (register 6
81 * and 7.)
82 */
83 caleb_reg_write(CALEB_INTREN0, 0xff);
84 caleb_reg_write(CALEB_INTREN1, 0x07);
86 /*
87 * Set RX and TX FIFO thresholds to 1.5kb.
88 */
89 caleb_reg_write(CALEB_PHY0RX, 0x11);
90 caleb_reg_write(CALEB_PHY1RX, 0x11);
91 caleb_reg_write(CALEB_PHY0TX, 0x11);
92 caleb_reg_write(CALEB_PHY1TX, 0x11);
94 /*
95 * Program SPI-3 burst size.
96 */
97 caleb_reg_write(CALEB_BURST, 0); // 64-byte RBUF mpackets
98 // caleb_reg_write(CALEB_BURST, 1); // 128-byte RBUF mpackets
99 // caleb_reg_write(CALEB_BURST, 2); // 256-byte RBUF mpackets
100 }
102 void caleb_enable_rx(int port)
103 {
104 u8 temp;
106 temp = caleb_reg_read(CALEB_PORTEN);
107 temp |= 1 << port;
108 caleb_reg_write(CALEB_PORTEN, temp);
109 }
111 void caleb_disable_rx(int port)
112 {
113 u8 temp;
115 temp = caleb_reg_read(CALEB_PORTEN);
116 temp &= ~(1 << port);
117 caleb_reg_write(CALEB_PORTEN, temp);
118 }
120 void caleb_enable_tx(int port)
121 {
122 u8 temp;
124 temp = caleb_reg_read(CALEB_PORTEN);
125 temp |= 1 << (port + 4);
126 caleb_reg_write(CALEB_PORTEN, temp);
127 }
129 void caleb_disable_tx(int port)
130 {
131 u8 temp;
133 temp = caleb_reg_read(CALEB_PORTEN);
134 temp &= ~(1 << (port + 4));
135 caleb_reg_write(CALEB_PORTEN, temp);
136 }