* [Qemu-devel] [PATCH] Memory Based Block Device
@ 2007-07-25 17:17 Evan Felix
2007-07-25 18:39 ` [Qemu-devel] Re: [kvm-devel] " Anthony Liguori
0 siblings, 1 reply; 4+ messages in thread
From: Evan Felix @ 2007-07-25 17:17 UTC (permalink / raw)
To: qemu-devel, kvm-devel
Folks here is a patch i've made for qemu that adds a memory based
block device, it utilizes memory on the Host side to emulate a block
device.
I've tested this on a few boxes to allow a kernel/initramfs system to
boot without needing a specified block device(it automatically creates
a small one) and for installing a usable system on. One note you can
never shut down the running system, but seems to work fine when only
re-boots are required. I've installed debian on it a few times.
Some Things I'd like comments on:
- The auto-detection code in the block code causes the code to
allocate the memory used twice, even though it only gets used the
second time.
- using qemu_mallocz seems to pre-allocate all the memory used, which
is fine, but my early code with calloc only allocated what blocks were
actually used. Does this bother people.
Evan Felix
diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
kvm-28/qemu.orig/block.c kvm-28/qemu/block.c
--- kvm-28/qemu.orig/block.c 2007-06-07 08:13:47.000000000 -0700
+++ kvm-28/qemu/block.c 2007-07-11 13:29:02.000000000 -0700
@@ -1244,6 +1244,7 @@ static int bdrv_write_em(BlockDriverStat
void bdrv_init(void)
{
bdrv_register(&bdrv_raw);
+ bdrv_register(&bdrv_mem);
bdrv_register(&bdrv_host_device);
#ifndef _WIN32
bdrv_register(&bdrv_cow);
diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
kvm-28/qemu.orig/block-mem.c kvm-28/qemu/block-mem.c
--- kvm-28/qemu.orig/block-mem.c 1969-12-31 16:00:00.000000000 -0800
+++ kvm-28/qemu/block-mem.c 2007-07-09 13:46:39.000000000 -0700
@@ -0,0 +1,129 @@
+/*
+ * Block Driver for a Memory disk on the host side.
+ *
+ * Copyright (c) 2007 Pacific Northwest National Laboratory
+ * and Evan Felix <e@pnl.gov>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program (see the file COPYING included with this
+ * distribution); if not, write to the Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+#include "vl.h"
+#include "block_int.h"
+
+//I took this from block-raw.c
+#ifdef __sun__
+#define _POSIX_PTHREAD_SEMANTICS 1
+#include <signal.h>
+#include <sys/dkio.h>
+#endif
+#ifdef __linux__
+#include <sys/ioctl.h>
+#include <linux/cdrom.h>
+#include <linux/fd.h>
+#endif
+#ifdef __FreeBSD__
+#include <sys/disk.h>
+#endif
+
+#define DEBUG_MEM 0
+
+#ifdef DEBUG_MEM
+#define DEBUG(fmt,a...) printf("D:%s:%d> " fmt "\n",__FILE__,__LINE__,##a)
+#else
+#define DEBUG(fmt,a...)
+#endif
+
+typedef struct BDRVMemState {
+ void *memory;
+ int64_t length;
+} BDRVMemState;
+
+static int mem_open(BlockDriverState *bs, const char *filename, int flags)
+{
+ BDRVMemState *s = bs->opaque;
+
+ bs->locked = 1;
+ bs->type = BDRV_TYPE_HD;
+ //Try to parse the filename as a number of bytes. add recognize M,K,G laterz.
+ s->length = strtol(filename+4,NULL,0);
+ DEBUG("mem_open:Raw Image size: %s -> %ld\n",filename,s->length);
+
+ s->memory=qemu_mallocz(s->length);
+ if (! s->memory)
+ return -ENOMEM;
+ return 0;
+}
+
+static void mem_close(BlockDriverState *bs) {
+
+ BDRVMemState *s = bs->opaque;
+ DEBUG("mem_close: %lld\n",s->length);
+ qemu_free(s->memory);
+ s->length=0;
+}
+
+static int mem_pread(BlockDriverState *bs, int64_t offset,
+ uint8_t *buf, int count)
+{
+ BDRVMemState *s = bs->opaque;
+
+ if (offset < 0 || (offset + count)>s->length) {
+ return -EINVAL;
+ }
+
+ memcpy(buf,(s->memory+offset),count);
+ return count;
+}
+
+static int mem_pwrite(BlockDriverState *bs, int64_t offset,
+ const uint8_t *buf, int count)
+{
+ BDRVMemState *s = bs->opaque;
+
+ if (offset < 0 || (offset + count)>s->length) {
+ return -EINVAL;
+ }
+
+ memcpy((s->memory+offset),buf,count);
+ return count;
+}
+
+static void mem_flush(BlockDriverState *bs)
+{
+ //Do Nothing for now
+ DEBUG("mem_flush\n");
+}
+
+static int64_t mem_getlength(BlockDriverState *bs)
+{
+ BDRVMemState *s = bs->opaque;
+
+ return s->length;
+}
+
+BlockDriver bdrv_mem = {
+ .format_name = "mem",
+ .instance_size = sizeof(BDRVMemState),
+ .protocol_name = "mem",
+
+ .bdrv_open = mem_open,
+ .bdrv_close = mem_close,
+ .bdrv_flush = mem_flush,
+
+ .bdrv_pread = mem_pread,
+ .bdrv_pwrite = mem_pwrite,
+ .bdrv_getlength = mem_getlength,
+};
diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
kvm-28/qemu.orig/hw/pc.c kvm-28/qemu/hw/pc.c
--- kvm-28/qemu.orig/hw/pc.c 2007-06-07 08:13:47.000000000 -0700
+++ kvm-28/qemu/hw/pc.c 2007-07-06 16:48:12.000000000 -0700
@@ -583,8 +583,13 @@ static void pc_init1(int ram_size, int v
uint8_t old_bootsect[512];
if (bs_table[0] == NULL) {
- fprintf(stderr, "A disk image must be given for 'hda'
when booting a Linux kernel\n");
- exit(1);
+ fprintf(stderr, "A disk image must be given when booting
a Linux kernel....\n\tCreating Simple memory backed Disk\n");
+ bs_table[i] = bdrv_new("hda");
+ if (bdrv_open(bs_table[0], "mem:4096", 0) < 0) {
+ fprintf(stderr, "qemu: could not open hard disk image '%s'\n",
+ "mem:512");
+ exit(1);
+ }
}
snprintf(buf, sizeof(buf), "%s/%s", bios_dir, LINUX_BOOT_FILENAME);
ret = load_image(buf, bootsect);
diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
kvm-28/qemu.orig/Makefile kvm-28/qemu/Makefile
--- kvm-28/qemu.orig/Makefile 2007-06-07 08:13:47.000000000 -0700
+++ kvm-28/qemu/Makefile 2007-07-06 14:24:44.000000000 -0700
@@ -39,7 +39,7 @@ subdir-%: dyngen$(EXESUF)
recurse-all: $(patsubst %,subdir-%, $(TARGET_DIRS))
-qemu-img$(EXESUF): qemu-img.c cutils.c block.c block-raw.c
block-cow.c block-qcow.c aes.c block-vmdk.c block-cloop.c block-dmg.c
block-bochs.c block-vpc.c block-vvfat.c block-qcow2.c
+qemu-img$(EXESUF): qemu-img.c cutils.c block.c block-raw.c
block-cow.c block-qcow.c aes.c block-vmdk.c block-cloop.c block-dmg.c
block-bochs.c block-vpc.c block-vvfat.c block-qcow2.c block-mem.c
$(CC) -DQEMU_TOOL $(CFLAGS) $(CPPFLAGS) $(BASE_CFLAGS) $(LDFLAGS)
$(BASE_LDFLAGS) -o $@ $^ -lz $(LIBS)
dyngen$(EXESUF): dyngen.c
diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
kvm-28/qemu.orig/Makefile.target kvm-28/qemu/Makefile.target
--- kvm-28/qemu.orig/Makefile.target 2007-06-07 08:13:47.000000000 -0700
+++ kvm-28/qemu/Makefile.target 2007-07-06 13:43:31.000000000 -0700
@@ -326,7 +326,7 @@ endif
VL_OBJS=vl.o osdep.o readline.o monitor.o pci.o console.o loader.o isa_mmio.o
VL_OBJS+=cutils.o migration.o
VL_OBJS+=block.o block-raw.o
-VL_OBJS+=block-cow.o block-qcow.o aes.o block-vmdk.o block-cloop.o
block-dmg.o block-bochs.o block-vpc.o block-vvfat.o block-qcow2.o
+VL_OBJS+=block-cow.o block-qcow.o aes.o block-vmdk.o block-cloop.o
block-dmg.o block-bochs.o block-vpc.o block-vvfat.o block-qcow2.o
block-mem.o
ifdef CONFIG_WIN32
VL_OBJS+=tap-win32.o
endif
diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
kvm-28/qemu.orig/vl.h kvm-28/qemu/vl.h
--- kvm-28/qemu.orig/vl.h 2007-06-07 08:13:47.000000000 -0700
+++ kvm-28/qemu/vl.h 2007-07-06 14:23:50.000000000 -0700
@@ -561,6 +561,7 @@ typedef struct BlockDriverState BlockDri
typedef struct BlockDriver BlockDriver;
extern BlockDriver bdrv_raw;
+extern BlockDriver bdrv_mem;
extern BlockDriver bdrv_host_device;
extern BlockDriver bdrv_cow;
extern BlockDriver bdrv_qcow;
^ permalink raw reply [flat|nested] 4+ messages in thread
* [Qemu-devel] Re: [kvm-devel] [PATCH] Memory Based Block Device
2007-07-25 17:17 [Qemu-devel] [PATCH] Memory Based Block Device Evan Felix
@ 2007-07-25 18:39 ` Anthony Liguori
2007-07-25 22:14 ` Evan Felix
0 siblings, 1 reply; 4+ messages in thread
From: Anthony Liguori @ 2007-07-25 18:39 UTC (permalink / raw)
To: Evan Felix; +Cc: kvm-devel, qemu-devel
Evan Felix wrote:
> Folks here is a patch i've made for qemu that adds a memory based
> block device, it utilizes memory on the Host side to emulate a block
> device.
>
I often use -hda /dev/null for -kernel/-append.
If you really want to implement a "proper" solution for -kernel/-append,
I think the right thing to do would be to use an option ROM instead of a
fake boot sector.
Regards,
Anthony Liguori
> I've tested this on a few boxes to allow a kernel/initramfs system to
> boot without needing a specified block device(it automatically creates
> a small one) and for installing a usable system on. One note you can
> never shut down the running system, but seems to work fine when only
> re-boots are required. I've installed debian on it a few times.
>
> Some Things I'd like comments on:
> - The auto-detection code in the block code causes the code to
> allocate the memory used twice, even though it only gets used the
> second time.
> - using qemu_mallocz seems to pre-allocate all the memory used, which
> is fine, but my early code with calloc only allocated what blocks were
> actually used. Does this bother people.
>
> Evan Felix
>
>
> diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
> kvm-28/qemu.orig/block.c kvm-28/qemu/block.c
> --- kvm-28/qemu.orig/block.c 2007-06-07 08:13:47.000000000 -0700
> +++ kvm-28/qemu/block.c 2007-07-11 13:29:02.000000000 -0700
> @@ -1244,6 +1244,7 @@ static int bdrv_write_em(BlockDriverStat
> void bdrv_init(void)
> {
> bdrv_register(&bdrv_raw);
> + bdrv_register(&bdrv_mem);
> bdrv_register(&bdrv_host_device);
> #ifndef _WIN32
> bdrv_register(&bdrv_cow);
> diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
> kvm-28/qemu.orig/block-mem.c kvm-28/qemu/block-mem.c
> --- kvm-28/qemu.orig/block-mem.c 1969-12-31 16:00:00.000000000 -0800
> +++ kvm-28/qemu/block-mem.c 2007-07-09 13:46:39.000000000 -0700
> @@ -0,0 +1,129 @@
> +/*
> + * Block Driver for a Memory disk on the host side.
> + *
> + * Copyright (c) 2007 Pacific Northwest National Laboratory
> + * and Evan Felix <e@pnl.gov>
> + *
> + * This program is free software; you can redistribute it and/or modify
> + * it under the terms of the GNU General Public License as published by
> + * the Free Software Foundation; either version 2 of the License, or
> + * (at your option) any later version.
> + *
> + * This program is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
> + * GNU General Public License for more details.
> + *
> + * You should have received a copy of the GNU General Public License
> + * along with this program (see the file COPYING included with this
> + * distribution); if not, write to the Free Software Foundation, Inc.,
> + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
> + */
> +
> +#include "vl.h"
> +#include "block_int.h"
> +
> +//I took this from block-raw.c
> +#ifdef __sun__
> +#define _POSIX_PTHREAD_SEMANTICS 1
> +#include <signal.h>
> +#include <sys/dkio.h>
> +#endif
> +#ifdef __linux__
> +#include <sys/ioctl.h>
> +#include <linux/cdrom.h>
> +#include <linux/fd.h>
> +#endif
> +#ifdef __FreeBSD__
> +#include <sys/disk.h>
> +#endif
> +
> +#define DEBUG_MEM 0
> +
> +#ifdef DEBUG_MEM
> +#define DEBUG(fmt,a...) printf("D:%s:%d> " fmt "\n",__FILE__,__LINE__,##a)
> +#else
> +#define DEBUG(fmt,a...)
> +#endif
> +
> +typedef struct BDRVMemState {
> + void *memory;
> + int64_t length;
> +} BDRVMemState;
> +
> +static int mem_open(BlockDriverState *bs, const char *filename, int flags)
> +{
> + BDRVMemState *s = bs->opaque;
> +
> + bs->locked = 1;
> + bs->type = BDRV_TYPE_HD;
> + //Try to parse the filename as a number of bytes. add recognize M,K,G laterz.
> + s->length = strtol(filename+4,NULL,0);
> + DEBUG("mem_open:Raw Image size: %s -> %ld\n",filename,s->length);
> +
> + s->memory=qemu_mallocz(s->length);
> + if (! s->memory)
> + return -ENOMEM;
> + return 0;
> +}
> +
> +static void mem_close(BlockDriverState *bs) {
> +
> + BDRVMemState *s = bs->opaque;
> + DEBUG("mem_close: %lld\n",s->length);
> + qemu_free(s->memory);
> + s->length=0;
> +}
> +
> +static int mem_pread(BlockDriverState *bs, int64_t offset,
> + uint8_t *buf, int count)
> +{
> + BDRVMemState *s = bs->opaque;
> +
> + if (offset < 0 || (offset + count)>s->length) {
> + return -EINVAL;
> + }
> +
> + memcpy(buf,(s->memory+offset),count);
> + return count;
> +}
> +
> +static int mem_pwrite(BlockDriverState *bs, int64_t offset,
> + const uint8_t *buf, int count)
> +{
> + BDRVMemState *s = bs->opaque;
> +
> + if (offset < 0 || (offset + count)>s->length) {
> + return -EINVAL;
> + }
> +
> + memcpy((s->memory+offset),buf,count);
> + return count;
> +}
> +
> +static void mem_flush(BlockDriverState *bs)
> +{
> + //Do Nothing for now
> + DEBUG("mem_flush\n");
> +}
> +
> +static int64_t mem_getlength(BlockDriverState *bs)
> +{
> + BDRVMemState *s = bs->opaque;
> +
> + return s->length;
> +}
> +
> +BlockDriver bdrv_mem = {
> + .format_name = "mem",
> + .instance_size = sizeof(BDRVMemState),
> + .protocol_name = "mem",
> +
> + .bdrv_open = mem_open,
> + .bdrv_close = mem_close,
> + .bdrv_flush = mem_flush,
> +
> + .bdrv_pread = mem_pread,
> + .bdrv_pwrite = mem_pwrite,
> + .bdrv_getlength = mem_getlength,
> +};
> diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
> kvm-28/qemu.orig/hw/pc.c kvm-28/qemu/hw/pc.c
> --- kvm-28/qemu.orig/hw/pc.c 2007-06-07 08:13:47.000000000 -0700
> +++ kvm-28/qemu/hw/pc.c 2007-07-06 16:48:12.000000000 -0700
> @@ -583,8 +583,13 @@ static void pc_init1(int ram_size, int v
> uint8_t old_bootsect[512];
>
> if (bs_table[0] == NULL) {
> - fprintf(stderr, "A disk image must be given for 'hda'
> when booting a Linux kernel\n");
> - exit(1);
> + fprintf(stderr, "A disk image must be given when booting
> a Linux kernel....\n\tCreating Simple memory backed Disk\n");
> + bs_table[i] = bdrv_new("hda");
> + if (bdrv_open(bs_table[0], "mem:4096", 0) < 0) {
> + fprintf(stderr, "qemu: could not open hard disk image '%s'\n",
> + "mem:512");
> + exit(1);
> + }
> }
> snprintf(buf, sizeof(buf), "%s/%s", bios_dir, LINUX_BOOT_FILENAME);
> ret = load_image(buf, bootsect);
> diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
> kvm-28/qemu.orig/Makefile kvm-28/qemu/Makefile
> --- kvm-28/qemu.orig/Makefile 2007-06-07 08:13:47.000000000 -0700
> +++ kvm-28/qemu/Makefile 2007-07-06 14:24:44.000000000 -0700
> @@ -39,7 +39,7 @@ subdir-%: dyngen$(EXESUF)
>
> recurse-all: $(patsubst %,subdir-%, $(TARGET_DIRS))
>
> -qemu-img$(EXESUF): qemu-img.c cutils.c block.c block-raw.c
> block-cow.c block-qcow.c aes.c block-vmdk.c block-cloop.c block-dmg.c
> block-bochs.c block-vpc.c block-vvfat.c block-qcow2.c
> +qemu-img$(EXESUF): qemu-img.c cutils.c block.c block-raw.c
> block-cow.c block-qcow.c aes.c block-vmdk.c block-cloop.c block-dmg.c
> block-bochs.c block-vpc.c block-vvfat.c block-qcow2.c block-mem.c
> $(CC) -DQEMU_TOOL $(CFLAGS) $(CPPFLAGS) $(BASE_CFLAGS) $(LDFLAGS)
> $(BASE_LDFLAGS) -o $@ $^ -lz $(LIBS)
>
> dyngen$(EXESUF): dyngen.c
> diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
> kvm-28/qemu.orig/Makefile.target kvm-28/qemu/Makefile.target
> --- kvm-28/qemu.orig/Makefile.target 2007-06-07 08:13:47.000000000 -0700
> +++ kvm-28/qemu/Makefile.target 2007-07-06 13:43:31.000000000 -0700
> @@ -326,7 +326,7 @@ endif
> VL_OBJS=vl.o osdep.o readline.o monitor.o pci.o console.o loader.o isa_mmio.o
> VL_OBJS+=cutils.o migration.o
> VL_OBJS+=block.o block-raw.o
> -VL_OBJS+=block-cow.o block-qcow.o aes.o block-vmdk.o block-cloop.o
> block-dmg.o block-bochs.o block-vpc.o block-vvfat.o block-qcow2.o
> +VL_OBJS+=block-cow.o block-qcow.o aes.o block-vmdk.o block-cloop.o
> block-dmg.o block-bochs.o block-vpc.o block-vvfat.o block-qcow2.o
> block-mem.o
> ifdef CONFIG_WIN32
> VL_OBJS+=tap-win32.o
> endif
> diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
> kvm-28/qemu.orig/vl.h kvm-28/qemu/vl.h
> --- kvm-28/qemu.orig/vl.h 2007-06-07 08:13:47.000000000 -0700
> +++ kvm-28/qemu/vl.h 2007-07-06 14:23:50.000000000 -0700
> @@ -561,6 +561,7 @@ typedef struct BlockDriverState BlockDri
> typedef struct BlockDriver BlockDriver;
>
> extern BlockDriver bdrv_raw;
> +extern BlockDriver bdrv_mem;
> extern BlockDriver bdrv_host_device;
> extern BlockDriver bdrv_cow;
> extern BlockDriver bdrv_qcow;
>
> -------------------------------------------------------------------------
> This SF.net email is sponsored by: Splunk Inc.
> Still grepping through log files to find problems? Stop.
> Now Search log events and configuration files using AJAX and a browser.
> Download your FREE copy of Splunk now >> http://get.splunk.com/
> _______________________________________________
> kvm-devel mailing list
> kvm-devel@lists.sourceforge.net
> https://lists.sourceforge.net/lists/listinfo/kvm-devel
>
>
^ permalink raw reply [flat|nested] 4+ messages in thread
* [Qemu-devel] Re: [kvm-devel] [PATCH] Memory Based Block Device
2007-07-25 18:39 ` [Qemu-devel] Re: [kvm-devel] " Anthony Liguori
@ 2007-07-25 22:14 ` Evan Felix
2007-07-25 22:37 ` Anthony Liguori
0 siblings, 1 reply; 4+ messages in thread
From: Evan Felix @ 2007-07-25 22:14 UTC (permalink / raw)
Cc: kvm-devel, qemu-devel
The Current way to boot a kernel and initrd is to use an option ROM,
bt it still needs a boot sector to hand to the bios so that it knows
where the code got loaded into ram. This patch makes a fake one just
before its needed.
I never though of the /dev/null trick. :)
Evan
On 7/25/07, Anthony Liguori <anthony@codemonkey.ws> wrote:
> Evan Felix wrote:
> > Folks here is a patch i've made for qemu that adds a memory based
> > block device, it utilizes memory on the Host side to emulate a block
> > device.
> >
>
> I often use -hda /dev/null for -kernel/-append.
>
> If you really want to implement a "proper" solution for -kernel/-append,
> I think the right thing to do would be to use an option ROM instead of a
> fake boot sector.
>
> Regards,
>
> Anthony Liguori
>
> > I've tested this on a few boxes to allow a kernel/initramfs system to
> > boot without needing a specified block device(it automatically creates
> > a small one) and for installing a usable system on. One note you can
> > never shut down the running system, but seems to work fine when only
> > re-boots are required. I've installed debian on it a few times.
> >
> > Some Things I'd like comments on:
> > - The auto-detection code in the block code causes the code to
> > allocate the memory used twice, even though it only gets used the
> > second time.
> > - using qemu_mallocz seems to pre-allocate all the memory used, which
> > is fine, but my early code with calloc only allocated what blocks were
> > actually used. Does this bother people.
> >
> > Evan Felix
> >
> >
> > diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
> > kvm-28/qemu.orig/block.c kvm-28/qemu/block.c
> > --- kvm-28/qemu.orig/block.c 2007-06-07 08:13:47.000000000 -0700
> > +++ kvm-28/qemu/block.c 2007-07-11 13:29:02.000000000 -0700
> > @@ -1244,6 +1244,7 @@ static int bdrv_write_em(BlockDriverStat
> > void bdrv_init(void)
> > {
> > bdrv_register(&bdrv_raw);
> > + bdrv_register(&bdrv_mem);
> > bdrv_register(&bdrv_host_device);
> > #ifndef _WIN32
> > bdrv_register(&bdrv_cow);
> > diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
> > kvm-28/qemu.orig/block-mem.c kvm-28/qemu/block-mem.c
> > --- kvm-28/qemu.orig/block-mem.c 1969-12-31 16:00:00.000000000 -0800
> > +++ kvm-28/qemu/block-mem.c 2007-07-09 13:46:39.000000000 -0700
> > @@ -0,0 +1,129 @@
> > +/*
> > + * Block Driver for a Memory disk on the host side.
> > + *
> > + * Copyright (c) 2007 Pacific Northwest National Laboratory
> > + * and Evan Felix <e@pnl.gov>
> > + *
> > + * This program is free software; you can redistribute it and/or modify
> > + * it under the terms of the GNU General Public License as published by
> > + * the Free Software Foundation; either version 2 of the License, or
> > + * (at your option) any later version.
> > + *
> > + * This program is distributed in the hope that it will be useful,
> > + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> > + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
> > + * GNU General Public License for more details.
> > + *
> > + * You should have received a copy of the GNU General Public License
> > + * along with this program (see the file COPYING included with this
> > + * distribution); if not, write to the Free Software Foundation, Inc.,
> > + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
> > + */
> > +
> > +#include "vl.h"
> > +#include "block_int.h"
> > +
> > +//I took this from block-raw.c
> > +#ifdef __sun__
> > +#define _POSIX_PTHREAD_SEMANTICS 1
> > +#include <signal.h>
> > +#include <sys/dkio.h>
> > +#endif
> > +#ifdef __linux__
> > +#include <sys/ioctl.h>
> > +#include <linux/cdrom.h>
> > +#include <linux/fd.h>
> > +#endif
> > +#ifdef __FreeBSD__
> > +#include <sys/disk.h>
> > +#endif
> > +
> > +#define DEBUG_MEM 0
> > +
> > +#ifdef DEBUG_MEM
> > +#define DEBUG(fmt,a...) printf("D:%s:%d> " fmt "\n",__FILE__,__LINE__,##a)
> > +#else
> > +#define DEBUG(fmt,a...)
> > +#endif
> > +
> > +typedef struct BDRVMemState {
> > + void *memory;
> > + int64_t length;
> > +} BDRVMemState;
> > +
> > +static int mem_open(BlockDriverState *bs, const char *filename, int flags)
> > +{
> > + BDRVMemState *s = bs->opaque;
> > +
> > + bs->locked = 1;
> > + bs->type = BDRV_TYPE_HD;
> > + //Try to parse the filename as a number of bytes. add recognize M,K,G laterz.
> > + s->length = strtol(filename+4,NULL,0);
> > + DEBUG("mem_open:Raw Image size: %s -> %ld\n",filename,s->length);
> > +
> > + s->memory=qemu_mallocz(s->length);
> > + if (! s->memory)
> > + return -ENOMEM;
> > + return 0;
> > +}
> > +
> > +static void mem_close(BlockDriverState *bs) {
> > +
> > + BDRVMemState *s = bs->opaque;
> > + DEBUG("mem_close: %lld\n",s->length);
> > + qemu_free(s->memory);
> > + s->length=0;
> > +}
> > +
> > +static int mem_pread(BlockDriverState *bs, int64_t offset,
> > + uint8_t *buf, int count)
> > +{
> > + BDRVMemState *s = bs->opaque;
> > +
> > + if (offset < 0 || (offset + count)>s->length) {
> > + return -EINVAL;
> > + }
> > +
> > + memcpy(buf,(s->memory+offset),count);
> > + return count;
> > +}
> > +
> > +static int mem_pwrite(BlockDriverState *bs, int64_t offset,
> > + const uint8_t *buf, int count)
> > +{
> > + BDRVMemState *s = bs->opaque;
> > +
> > + if (offset < 0 || (offset + count)>s->length) {
> > + return -EINVAL;
> > + }
> > +
> > + memcpy((s->memory+offset),buf,count);
> > + return count;
> > +}
> > +
> > +static void mem_flush(BlockDriverState *bs)
> > +{
> > + //Do Nothing for now
> > + DEBUG("mem_flush\n");
> > +}
> > +
> > +static int64_t mem_getlength(BlockDriverState *bs)
> > +{
> > + BDRVMemState *s = bs->opaque;
> > +
> > + return s->length;
> > +}
> > +
> > +BlockDriver bdrv_mem = {
> > + .format_name = "mem",
> > + .instance_size = sizeof(BDRVMemState),
> > + .protocol_name = "mem",
> > +
> > + .bdrv_open = mem_open,
> > + .bdrv_close = mem_close,
> > + .bdrv_flush = mem_flush,
> > +
> > + .bdrv_pread = mem_pread,
> > + .bdrv_pwrite = mem_pwrite,
> > + .bdrv_getlength = mem_getlength,
> > +};
> > diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
> > kvm-28/qemu.orig/hw/pc.c kvm-28/qemu/hw/pc.c
> > --- kvm-28/qemu.orig/hw/pc.c 2007-06-07 08:13:47.000000000 -0700
> > +++ kvm-28/qemu/hw/pc.c 2007-07-06 16:48:12.000000000 -0700
> > @@ -583,8 +583,13 @@ static void pc_init1(int ram_size, int v
> > uint8_t old_bootsect[512];
> >
> > if (bs_table[0] == NULL) {
> > - fprintf(stderr, "A disk image must be given for 'hda'
> > when booting a Linux kernel\n");
> > - exit(1);
> > + fprintf(stderr, "A disk image must be given when booting
> > a Linux kernel....\n\tCreating Simple memory backed Disk\n");
> > + bs_table[i] = bdrv_new("hda");
> > + if (bdrv_open(bs_table[0], "mem:4096", 0) < 0) {
> > + fprintf(stderr, "qemu: could not open hard disk image '%s'\n",
> > + "mem:512");
> > + exit(1);
> > + }
> > }
> > snprintf(buf, sizeof(buf), "%s/%s", bios_dir, LINUX_BOOT_FILENAME);
> > ret = load_image(buf, bootsect);
> > diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
> > kvm-28/qemu.orig/Makefile kvm-28/qemu/Makefile
> > --- kvm-28/qemu.orig/Makefile 2007-06-07 08:13:47.000000000 -0700
> > +++ kvm-28/qemu/Makefile 2007-07-06 14:24:44.000000000 -0700
> > @@ -39,7 +39,7 @@ subdir-%: dyngen$(EXESUF)
> >
> > recurse-all: $(patsubst %,subdir-%, $(TARGET_DIRS))
> >
> > -qemu-img$(EXESUF): qemu-img.c cutils.c block.c block-raw.c
> > block-cow.c block-qcow.c aes.c block-vmdk.c block-cloop.c block-dmg.c
> > block-bochs.c block-vpc.c block-vvfat.c block-qcow2.c
> > +qemu-img$(EXESUF): qemu-img.c cutils.c block.c block-raw.c
> > block-cow.c block-qcow.c aes.c block-vmdk.c block-cloop.c block-dmg.c
> > block-bochs.c block-vpc.c block-vvfat.c block-qcow2.c block-mem.c
> > $(CC) -DQEMU_TOOL $(CFLAGS) $(CPPFLAGS) $(BASE_CFLAGS) $(LDFLAGS)
> > $(BASE_LDFLAGS) -o $@ $^ -lz $(LIBS)
> >
> > dyngen$(EXESUF): dyngen.c
> > diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
> > kvm-28/qemu.orig/Makefile.target kvm-28/qemu/Makefile.target
> > --- kvm-28/qemu.orig/Makefile.target 2007-06-07 08:13:47.000000000 -0700
> > +++ kvm-28/qemu/Makefile.target 2007-07-06 13:43:31.000000000 -0700
> > @@ -326,7 +326,7 @@ endif
> > VL_OBJS=vl.o osdep.o readline.o monitor.o pci.o console.o loader.o isa_mmio.o
> > VL_OBJS+=cutils.o migration.o
> > VL_OBJS+=block.o block-raw.o
> > -VL_OBJS+=block-cow.o block-qcow.o aes.o block-vmdk.o block-cloop.o
> > block-dmg.o block-bochs.o block-vpc.o block-vvfat.o block-qcow2.o
> > +VL_OBJS+=block-cow.o block-qcow.o aes.o block-vmdk.o block-cloop.o
> > block-dmg.o block-bochs.o block-vpc.o block-vvfat.o block-qcow2.o
> > block-mem.o
> > ifdef CONFIG_WIN32
> > VL_OBJS+=tap-win32.o
> > endif
> > diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
> > kvm-28/qemu.orig/vl.h kvm-28/qemu/vl.h
> > --- kvm-28/qemu.orig/vl.h 2007-06-07 08:13:47.000000000 -0700
> > +++ kvm-28/qemu/vl.h 2007-07-06 14:23:50.000000000 -0700
> > @@ -561,6 +561,7 @@ typedef struct BlockDriverState BlockDri
> > typedef struct BlockDriver BlockDriver;
> >
> > extern BlockDriver bdrv_raw;
> > +extern BlockDriver bdrv_mem;
> > extern BlockDriver bdrv_host_device;
> > extern BlockDriver bdrv_cow;
> > extern BlockDriver bdrv_qcow;
> >
> > -------------------------------------------------------------------------
> > This SF.net email is sponsored by: Splunk Inc.
> > Still grepping through log files to find problems? Stop.
> > Now Search log events and configuration files using AJAX and a browser.
> > Download your FREE copy of Splunk now >> http://get.splunk.com/
> > _______________________________________________
> > kvm-devel mailing list
> > kvm-devel@lists.sourceforge.net
> > https://lists.sourceforge.net/lists/listinfo/kvm-devel
> >
> >
>
>
^ permalink raw reply [flat|nested] 4+ messages in thread
* [Qemu-devel] Re: [kvm-devel] [PATCH] Memory Based Block Device
2007-07-25 22:14 ` Evan Felix
@ 2007-07-25 22:37 ` Anthony Liguori
0 siblings, 0 replies; 4+ messages in thread
From: Anthony Liguori @ 2007-07-25 22:37 UTC (permalink / raw)
To: Evan Felix; +Cc: kvm-devel, qemu-devel
Evan Felix wrote:
> The Current way to boot a kernel and initrd is to use an option ROM,
>
Currently, the block infrastructure has this nasty hack that allows you
to set an override of the first sector of the disk (which is the boot
sector). It has the appropriate magic to do this in such a way that it
preserves the partition table. -kernel uses this hack to override the
boot sector with a specialized boot loader that boots a kernel from a
special place that it's stashed in in physical memory.
A more elegant approach would be to do away with the boot sector hacks
in the block code and to implement an option ROM. The option ROM code
would hook the appropriate BIOS interrupts such that it could generate
the fake boot sector for the first disk.
The advantage to such an approach is that you get rid of the nasty hacks
in the block devices to make -kernel work. It also generalizes nicely
to other things like SCSI boot.
Regards,
Anthony Liguori
> bt it still needs a boot sector to hand to the bios so that it knows
> where the code got loaded into ram. This patch makes a fake one just
> before its needed.
>
> I never though of the /dev/null trick. :)
>
> Evan
>
> On 7/25/07, Anthony Liguori <anthony@codemonkey.ws> wrote:
>
>> Evan Felix wrote:
>>
>>> Folks here is a patch i've made for qemu that adds a memory based
>>> block device, it utilizes memory on the Host side to emulate a block
>>> device.
>>>
>>>
>> I often use -hda /dev/null for -kernel/-append.
>>
>> If you really want to implement a "proper" solution for -kernel/-append,
>> I think the right thing to do would be to use an option ROM instead of a
>> fake boot sector.
>>
>> Regards,
>>
>> Anthony Liguori
>>
>>
>>> I've tested this on a few boxes to allow a kernel/initramfs system to
>>> boot without needing a specified block device(it automatically creates
>>> a small one) and for installing a usable system on. One note you can
>>> never shut down the running system, but seems to work fine when only
>>> re-boots are required. I've installed debian on it a few times.
>>>
>>> Some Things I'd like comments on:
>>> - The auto-detection code in the block code causes the code to
>>> allocate the memory used twice, even though it only gets used the
>>> second time.
>>> - using qemu_mallocz seems to pre-allocate all the memory used, which
>>> is fine, but my early code with calloc only allocated what blocks were
>>> actually used. Does this bother people.
>>>
>>> Evan Felix
>>>
>>>
>>> diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
>>> kvm-28/qemu.orig/block.c kvm-28/qemu/block.c
>>> --- kvm-28/qemu.orig/block.c 2007-06-07 08:13:47.000000000 -0700
>>> +++ kvm-28/qemu/block.c 2007-07-11 13:29:02.000000000 -0700
>>> @@ -1244,6 +1244,7 @@ static int bdrv_write_em(BlockDriverStat
>>> void bdrv_init(void)
>>> {
>>> bdrv_register(&bdrv_raw);
>>> + bdrv_register(&bdrv_mem);
>>> bdrv_register(&bdrv_host_device);
>>> #ifndef _WIN32
>>> bdrv_register(&bdrv_cow);
>>> diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
>>> kvm-28/qemu.orig/block-mem.c kvm-28/qemu/block-mem.c
>>> --- kvm-28/qemu.orig/block-mem.c 1969-12-31 16:00:00.000000000 -0800
>>> +++ kvm-28/qemu/block-mem.c 2007-07-09 13:46:39.000000000 -0700
>>> @@ -0,0 +1,129 @@
>>> +/*
>>> + * Block Driver for a Memory disk on the host side.
>>> + *
>>> + * Copyright (c) 2007 Pacific Northwest National Laboratory
>>> + * and Evan Felix <e@pnl.gov>
>>> + *
>>> + * This program is free software; you can redistribute it and/or modify
>>> + * it under the terms of the GNU General Public License as published by
>>> + * the Free Software Foundation; either version 2 of the License, or
>>> + * (at your option) any later version.
>>> + *
>>> + * This program is distributed in the hope that it will be useful,
>>> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
>>> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
>>> + * GNU General Public License for more details.
>>> + *
>>> + * You should have received a copy of the GNU General Public License
>>> + * along with this program (see the file COPYING included with this
>>> + * distribution); if not, write to the Free Software Foundation, Inc.,
>>> + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
>>> + */
>>> +
>>> +#include "vl.h"
>>> +#include "block_int.h"
>>> +
>>> +//I took this from block-raw.c
>>> +#ifdef __sun__
>>> +#define _POSIX_PTHREAD_SEMANTICS 1
>>> +#include <signal.h>
>>> +#include <sys/dkio.h>
>>> +#endif
>>> +#ifdef __linux__
>>> +#include <sys/ioctl.h>
>>> +#include <linux/cdrom.h>
>>> +#include <linux/fd.h>
>>> +#endif
>>> +#ifdef __FreeBSD__
>>> +#include <sys/disk.h>
>>> +#endif
>>> +
>>> +#define DEBUG_MEM 0
>>> +
>>> +#ifdef DEBUG_MEM
>>> +#define DEBUG(fmt,a...) printf("D:%s:%d> " fmt "\n",__FILE__,__LINE__,##a)
>>> +#else
>>> +#define DEBUG(fmt,a...)
>>> +#endif
>>> +
>>> +typedef struct BDRVMemState {
>>> + void *memory;
>>> + int64_t length;
>>> +} BDRVMemState;
>>> +
>>> +static int mem_open(BlockDriverState *bs, const char *filename, int flags)
>>> +{
>>> + BDRVMemState *s = bs->opaque;
>>> +
>>> + bs->locked = 1;
>>> + bs->type = BDRV_TYPE_HD;
>>> + //Try to parse the filename as a number of bytes. add recognize M,K,G laterz.
>>> + s->length = strtol(filename+4,NULL,0);
>>> + DEBUG("mem_open:Raw Image size: %s -> %ld\n",filename,s->length);
>>> +
>>> + s->memory=qemu_mallocz(s->length);
>>> + if (! s->memory)
>>> + return -ENOMEM;
>>> + return 0;
>>> +}
>>> +
>>> +static void mem_close(BlockDriverState *bs) {
>>> +
>>> + BDRVMemState *s = bs->opaque;
>>> + DEBUG("mem_close: %lld\n",s->length);
>>> + qemu_free(s->memory);
>>> + s->length=0;
>>> +}
>>> +
>>> +static int mem_pread(BlockDriverState *bs, int64_t offset,
>>> + uint8_t *buf, int count)
>>> +{
>>> + BDRVMemState *s = bs->opaque;
>>> +
>>> + if (offset < 0 || (offset + count)>s->length) {
>>> + return -EINVAL;
>>> + }
>>> +
>>> + memcpy(buf,(s->memory+offset),count);
>>> + return count;
>>> +}
>>> +
>>> +static int mem_pwrite(BlockDriverState *bs, int64_t offset,
>>> + const uint8_t *buf, int count)
>>> +{
>>> + BDRVMemState *s = bs->opaque;
>>> +
>>> + if (offset < 0 || (offset + count)>s->length) {
>>> + return -EINVAL;
>>> + }
>>> +
>>> + memcpy((s->memory+offset),buf,count);
>>> + return count;
>>> +}
>>> +
>>> +static void mem_flush(BlockDriverState *bs)
>>> +{
>>> + //Do Nothing for now
>>> + DEBUG("mem_flush\n");
>>> +}
>>> +
>>> +static int64_t mem_getlength(BlockDriverState *bs)
>>> +{
>>> + BDRVMemState *s = bs->opaque;
>>> +
>>> + return s->length;
>>> +}
>>> +
>>> +BlockDriver bdrv_mem = {
>>> + .format_name = "mem",
>>> + .instance_size = sizeof(BDRVMemState),
>>> + .protocol_name = "mem",
>>> +
>>> + .bdrv_open = mem_open,
>>> + .bdrv_close = mem_close,
>>> + .bdrv_flush = mem_flush,
>>> +
>>> + .bdrv_pread = mem_pread,
>>> + .bdrv_pwrite = mem_pwrite,
>>> + .bdrv_getlength = mem_getlength,
>>> +};
>>> diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
>>> kvm-28/qemu.orig/hw/pc.c kvm-28/qemu/hw/pc.c
>>> --- kvm-28/qemu.orig/hw/pc.c 2007-06-07 08:13:47.000000000 -0700
>>> +++ kvm-28/qemu/hw/pc.c 2007-07-06 16:48:12.000000000 -0700
>>> @@ -583,8 +583,13 @@ static void pc_init1(int ram_size, int v
>>> uint8_t old_bootsect[512];
>>>
>>> if (bs_table[0] == NULL) {
>>> - fprintf(stderr, "A disk image must be given for 'hda'
>>> when booting a Linux kernel\n");
>>> - exit(1);
>>> + fprintf(stderr, "A disk image must be given when booting
>>> a Linux kernel....\n\tCreating Simple memory backed Disk\n");
>>> + bs_table[i] = bdrv_new("hda");
>>> + if (bdrv_open(bs_table[0], "mem:4096", 0) < 0) {
>>> + fprintf(stderr, "qemu: could not open hard disk image '%s'\n",
>>> + "mem:512");
>>> + exit(1);
>>> + }
>>> }
>>> snprintf(buf, sizeof(buf), "%s/%s", bios_dir, LINUX_BOOT_FILENAME);
>>> ret = load_image(buf, bootsect);
>>> diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
>>> kvm-28/qemu.orig/Makefile kvm-28/qemu/Makefile
>>> --- kvm-28/qemu.orig/Makefile 2007-06-07 08:13:47.000000000 -0700
>>> +++ kvm-28/qemu/Makefile 2007-07-06 14:24:44.000000000 -0700
>>> @@ -39,7 +39,7 @@ subdir-%: dyngen$(EXESUF)
>>>
>>> recurse-all: $(patsubst %,subdir-%, $(TARGET_DIRS))
>>>
>>> -qemu-img$(EXESUF): qemu-img.c cutils.c block.c block-raw.c
>>> block-cow.c block-qcow.c aes.c block-vmdk.c block-cloop.c block-dmg.c
>>> block-bochs.c block-vpc.c block-vvfat.c block-qcow2.c
>>> +qemu-img$(EXESUF): qemu-img.c cutils.c block.c block-raw.c
>>> block-cow.c block-qcow.c aes.c block-vmdk.c block-cloop.c block-dmg.c
>>> block-bochs.c block-vpc.c block-vvfat.c block-qcow2.c block-mem.c
>>> $(CC) -DQEMU_TOOL $(CFLAGS) $(CPPFLAGS) $(BASE_CFLAGS) $(LDFLAGS)
>>> $(BASE_LDFLAGS) -o $@ $^ -lz $(LIBS)
>>>
>>> dyngen$(EXESUF): dyngen.c
>>> diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
>>> kvm-28/qemu.orig/Makefile.target kvm-28/qemu/Makefile.target
>>> --- kvm-28/qemu.orig/Makefile.target 2007-06-07 08:13:47.000000000 -0700
>>> +++ kvm-28/qemu/Makefile.target 2007-07-06 13:43:31.000000000 -0700
>>> @@ -326,7 +326,7 @@ endif
>>> VL_OBJS=vl.o osdep.o readline.o monitor.o pci.o console.o loader.o isa_mmio.o
>>> VL_OBJS+=cutils.o migration.o
>>> VL_OBJS+=block.o block-raw.o
>>> -VL_OBJS+=block-cow.o block-qcow.o aes.o block-vmdk.o block-cloop.o
>>> block-dmg.o block-bochs.o block-vpc.o block-vvfat.o block-qcow2.o
>>> +VL_OBJS+=block-cow.o block-qcow.o aes.o block-vmdk.o block-cloop.o
>>> block-dmg.o block-bochs.o block-vpc.o block-vvfat.o block-qcow2.o
>>> block-mem.o
>>> ifdef CONFIG_WIN32
>>> VL_OBJS+=tap-win32.o
>>> endif
>>> diff -urNp -x '*~' -x '*html' -x '*.mak' -x '*.1'
>>> kvm-28/qemu.orig/vl.h kvm-28/qemu/vl.h
>>> --- kvm-28/qemu.orig/vl.h 2007-06-07 08:13:47.000000000 -0700
>>> +++ kvm-28/qemu/vl.h 2007-07-06 14:23:50.000000000 -0700
>>> @@ -561,6 +561,7 @@ typedef struct BlockDriverState BlockDri
>>> typedef struct BlockDriver BlockDriver;
>>>
>>> extern BlockDriver bdrv_raw;
>>> +extern BlockDriver bdrv_mem;
>>> extern BlockDriver bdrv_host_device;
>>> extern BlockDriver bdrv_cow;
>>> extern BlockDriver bdrv_qcow;
>>>
>>> -------------------------------------------------------------------------
>>> This SF.net email is sponsored by: Splunk Inc.
>>> Still grepping through log files to find problems? Stop.
>>> Now Search log events and configuration files using AJAX and a browser.
>>> Download your FREE copy of Splunk now >> http://get.splunk.com/
>>> _______________________________________________
>>> kvm-devel mailing list
>>> kvm-devel@lists.sourceforge.net
>>> https://lists.sourceforge.net/lists/listinfo/kvm-devel
>>>
>>>
>>>
>>
>
> -------------------------------------------------------------------------
> This SF.net email is sponsored by: Splunk Inc.
> Still grepping through log files to find problems? Stop.
> Now Search log events and configuration files using AJAX and a browser.
> Download your FREE copy of Splunk now >> http://get.splunk.com/
> _______________________________________________
> kvm-devel mailing list
> kvm-devel@lists.sourceforge.net
> https://lists.sourceforge.net/lists/listinfo/kvm-devel
>
>
^ permalink raw reply [flat|nested] 4+ messages in thread
end of thread, other threads:[~2007-07-25 22:37 UTC | newest]
Thread overview: 4+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2007-07-25 17:17 [Qemu-devel] [PATCH] Memory Based Block Device Evan Felix
2007-07-25 18:39 ` [Qemu-devel] Re: [kvm-devel] " Anthony Liguori
2007-07-25 22:14 ` Evan Felix
2007-07-25 22:37 ` Anthony Liguori
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).