diff mbox

kvm tools: Add option to specify backing storage for RAM

Message ID 1303389930-30303-1-git-send-email-levinsasha928@gmail.com (mailing list archive)
State New, archived
Headers show

Commit Message

Sasha Levin April 21, 2011, 12:45 p.m. UTC
Add --use-backing to allow for the usage of a temporary backing file for guest RAM.
A temporary file is created and aollocated under /tmp and is used to back the RAM memory which is mmaped for the guest.
There should be enough storage space under /tmp to use this option (at least the size of the guest RAM).

Signed-off-by: Sasha Levin <levinsasha928@gmail.com>
---
 tools/kvm/include/kvm/kvm.h |    2 +-
 tools/kvm/kvm-run.c         |    5 ++++-
 tools/kvm/kvm.c             |   21 +++++++++++++++++++--
 3 files changed, 24 insertions(+), 4 deletions(-)

Comments

Pekka Enberg April 21, 2011, 12:48 p.m. UTC | #1
On Thu, Apr 21, 2011 at 3:45 PM, Sasha Levin <levinsasha928@gmail.com> wrote:
> Add --use-backing to allow for the usage of a temporary backing file for guest RAM.
> A temporary file is created and aollocated under /tmp and is used to back the RAM memory which is mmaped for the guest.
> There should be enough storage space under /tmp to use this option (at least the size of the guest RAM).
>
> Signed-off-by: Sasha Levin <levinsasha928@gmail.com>

OK, but what is this useful for? Why would someone want to do this?
--
To unsubscribe from this list: send the line "unsubscribe kvm" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Sasha Levin April 21, 2011, 1 p.m. UTC | #2
On Thu, 2011-04-21 at 15:48 +0300, Pekka Enberg wrote:
> On Thu, Apr 21, 2011 at 3:45 PM, Sasha Levin <levinsasha928@gmail.com> wrote:
> > Add --use-backing to allow for the usage of a temporary backing file for guest RAM.
> > A temporary file is created and aollocated under /tmp and is used to back the RAM memory which is mmaped for the guest.
> > There should be enough storage space under /tmp to use this option (at least the size of the guest RAM).
> >
> > Signed-off-by: Sasha Levin <levinsasha928@gmail.com>
> 
> OK, but what is this useful for? Why would someone want to do this?

It's an alternative to creating more swap.
When using large RAM sizes for guests on hosts with limited physical
RAM/swap this option gives the user a way to use files instead of swap.

This can also be extended to use hugetlbfs.
Pekka Enberg April 21, 2011, 1:12 p.m. UTC | #3
On Thu, Apr 21, 2011 at 4:00 PM, Sasha Levin <levinsasha928@gmail.com> wrote:
> It's an alternative to creating more swap.
> When using large RAM sizes for guests on hosts with limited physical
> RAM/swap this option gives the user a way to use files instead of swap.

Well, I don't still quite see the point of this feature. Is there some
real world use for running guests with huge memory space that's
swap-backed?

On Thu, Apr 21, 2011 at 4:00 PM, Sasha Levin <levinsasha928@gmail.com> wrote:
> This can also be extended to use hugetlbfs.

Recent Linux kernels support transparent hugepages so you can do
MADV_HUGEPAGE on mmap'd memory.
--
To unsubscribe from this list: send the line "unsubscribe kvm" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Sasha Levin April 21, 2011, 2:08 p.m. UTC | #4
On Thu, 2011-04-21 at 16:12 +0300, Pekka Enberg wrote:
> Well, I don't still quite see the point of this feature. Is there some
> real world use for running guests with huge memory space that's
> swap-backed?

Not a single guest, but multiple guests which take more RAM than the
host can provide using paging. This happened to me when I tried booting
several servers to test network bridging.

Can't say it's a common use-case though.
Avi Kivity April 21, 2011, 2:12 p.m. UTC | #5
On 04/21/2011 04:12 PM, Pekka Enberg wrote:
> On Thu, Apr 21, 2011 at 4:00 PM, Sasha Levin<levinsasha928@gmail.com>  wrote:
> >  This can also be extended to use hugetlbfs.
>
> Recent Linux kernels support transparent hugepages so you can do
> MADV_HUGEPAGE on mmap'd memory.

Note, it has to be aligned correctly (to a 2M boundary), and it must be 
anonymous memory.
diff mbox

Patch

diff --git a/tools/kvm/include/kvm/kvm.h b/tools/kvm/include/kvm/kvm.h
index fc76f98..3a44c53 100644
--- a/tools/kvm/include/kvm/kvm.h
+++ b/tools/kvm/include/kvm/kvm.h
@@ -25,7 +25,7 @@  struct kvm {
 	struct interrupt_table	interrupt_table;
 };
 
-struct kvm *kvm__init(const char *kvm_dev, unsigned long ram_size);
+struct kvm *kvm__init(const char *kvm_dev, unsigned long ram_size, bool use_backing);
 void kvm__init_ram(struct kvm *self);
 void kvm__delete(struct kvm *self);
 bool kvm__load_kernel(struct kvm *kvm, const char *kernel_filename,
diff --git a/tools/kvm/kvm-run.c b/tools/kvm/kvm-run.c
index fb8dcae7..a925a98 100644
--- a/tools/kvm/kvm-run.c
+++ b/tools/kvm/kvm-run.c
@@ -69,6 +69,7 @@  static const char *host_ip_addr;
 static const char *guest_mac;
 static const char *script;
 static bool single_step;
+static bool use_backing;
 static bool readonly_image;
 extern bool ioport_debug;
 extern int  active_console;
@@ -84,6 +85,8 @@  static const struct option options[] = {
 	OPT_GROUP("Basic options:"),
 	OPT_INTEGER('\0', "cpus", &nrcpus, "Number of CPUs"),
 	OPT_U64('m', "mem", &ram_size, "Virtual machine memory size in MiB."),
+	OPT_BOOLEAN('\0', "use-backing", &use_backing,
+			"Use a backing file for virtual RAM"),
 	OPT_STRING('i', "image", &image_filename, "image", "Disk image"),
 	OPT_BOOLEAN('\0', "readonly", &readonly_image,
 			"Don't write changes back to disk image"),
@@ -366,7 +369,7 @@  int kvm_cmd_run(int argc, const char **argv, const char *prefix)
 
 	term_init();
 
-	kvm = kvm__init(kvm_dev, ram_size);
+	kvm = kvm__init(kvm_dev, ram_size, use_backing);
 
 	memset(real_cmdline, 0, sizeof(real_cmdline));
 	strcpy(real_cmdline, "notsc nolapic noacpi pci=conf1 console=ttyS0 ");
diff --git a/tools/kvm/kvm.c b/tools/kvm/kvm.c
index eb1a46c..5e312e9 100644
--- a/tools/kvm/kvm.c
+++ b/tools/kvm/kvm.c
@@ -170,11 +170,12 @@  void kvm__init_ram(struct kvm *self)
 		die_perror("KVM_SET_USER_MEMORY_REGION ioctl");
 }
 
-struct kvm *kvm__init(const char *kvm_dev, unsigned long ram_size)
+struct kvm *kvm__init(const char *kvm_dev, unsigned long ram_size, bool use_backing)
 {
 	struct kvm_pit_config pit_config = { .flags = 0, };
 	struct kvm *self;
 	int ret;
+	int backfd;
 
 	if (!kvm__cpu_supports_vm())
 		die("Your CPU does not support hardware virtualization");
@@ -214,7 +215,23 @@  struct kvm *kvm__init(const char *kvm_dev, unsigned long ram_size)
 
 	self->ram_size		= ram_size;
 
-	self->ram_start = mmap(NULL, ram_size, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS | MAP_NORESERVE, -1, 0);
+	if (use_backing) {
+		char tmp_template[] = "/tmp/kvm_ram.XXXXXX";
+
+		backfd = mkstemp(tmp_template);
+		if (backfd < 0)
+			die("Failed creating RAM backing file");
+
+		unlink(tmp_template);
+
+		if (ftruncate(backfd, ram_size) < 0)
+			die("Failed resizing RAM backing file");
+
+		self->ram_start = mmap(NULL, ram_size, PROT_READ | PROT_WRITE, MAP_SHARED, backfd, 0);
+	} else {
+		self->ram_start = mmap(NULL, ram_size, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS | MAP_NORESERVE, -1, 0);
+	}
+
 	if (self->ram_start == MAP_FAILED)
 		die("out of memory");