Skip to content

Commit 96edd61

Browse files
committed
xen/balloon: don't online new memory initially
When setting up the Xenstore watch for the memory target size the new watch will fire at once. Don't try to reach the configured target size by onlining new memory in this case, as the current memory size will be smaller in almost all cases due to e.g. BIOS reserved pages. Onlining new memory will lead to more problems e.g. undesired conflicts with NVMe devices meant to be operated as block devices. Instead remember the difference between target size and current size when the watch fires for the first time and apply it to any further size changes, too. In order to avoid races between balloon.c and xen-balloon.c init calls do the xen-balloon.c initialization from balloon.c. Signed-off-by: Juergen Gross <[email protected]> Reviewed-by: Boris Ostrovsky <[email protected]> Signed-off-by: Juergen Gross <[email protected]>
1 parent c185dde commit 96edd61

File tree

3 files changed

+23
-10
lines changed

3 files changed

+23
-10
lines changed

drivers/xen/balloon.c

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -780,6 +780,9 @@ static int __init balloon_init(void)
780780
}
781781
#endif
782782

783+
/* Init the xen-balloon driver. */
784+
xen_balloon_init();
785+
783786
return 0;
784787
}
785788
subsys_initcall(balloon_init);

drivers/xen/xen-balloon.c

Lines changed: 12 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,8 @@ static void watch_target(struct xenbus_watch *watch,
5959
{
6060
unsigned long long new_target;
6161
int err;
62+
static bool watch_fired;
63+
static long target_diff;
6264

6365
err = xenbus_scanf(XBT_NIL, "memory", "target", "%llu", &new_target);
6466
if (err != 1) {
@@ -69,7 +71,14 @@ static void watch_target(struct xenbus_watch *watch,
6971
/* The given memory/target value is in KiB, so it needs converting to
7072
* pages. PAGE_SHIFT converts bytes to pages, hence PAGE_SHIFT - 10.
7173
*/
72-
balloon_set_new_target(new_target >> (PAGE_SHIFT - 10));
74+
new_target >>= PAGE_SHIFT - 10;
75+
if (watch_fired) {
76+
balloon_set_new_target(new_target - target_diff);
77+
return;
78+
}
79+
80+
watch_fired = true;
81+
target_diff = new_target - balloon_stats.target_pages;
7382
}
7483
static struct xenbus_watch target_watch = {
7584
.node = "memory/target",
@@ -94,22 +103,15 @@ static struct notifier_block xenstore_notifier = {
94103
.notifier_call = balloon_init_watcher,
95104
};
96105

97-
static int __init balloon_init(void)
106+
void xen_balloon_init(void)
98107
{
99-
if (!xen_domain())
100-
return -ENODEV;
101-
102-
pr_info("Initialising balloon driver\n");
103-
104108
register_balloon(&balloon_dev);
105109

106110
register_xen_selfballooning(&balloon_dev);
107111

108112
register_xenstore_notifier(&xenstore_notifier);
109-
110-
return 0;
111113
}
112-
subsys_initcall(balloon_init);
114+
EXPORT_SYMBOL_GPL(xen_balloon_init);
113115

114116
#define BALLOON_SHOW(name, format, args...) \
115117
static ssize_t show_##name(struct device *dev, \

include/xen/balloon.h

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,3 +35,11 @@ static inline int register_xen_selfballooning(struct device *dev)
3535
return -ENOSYS;
3636
}
3737
#endif
38+
39+
#ifdef CONFIG_XEN_BALLOON
40+
void xen_balloon_init(void);
41+
#else
42+
static inline void xen_balloon_init(void)
43+
{
44+
}
45+
#endif

0 commit comments

Comments
 (0)