Signed-off-by: Olivia Yin <hong-hua....@freescale.com> --- hw/loader.c | 43 +++++++++++++++++++++++++++++++++++++------ hw/loader.h | 20 ++++++++++++++++---- hw/ppc/e500.c | 2 +- hw/ppc440_bamboo.c | 2 +- monitor.c | 7 +++++++ 5 files changed, 62 insertions(+), 12 deletions(-)
diff --git a/hw/loader.c b/hw/loader.c index 5849e32..ccbbef4 100644 --- a/hw/loader.c +++ b/hw/loader.c @@ -55,6 +55,7 @@ #include <zlib.h> static int roms_loaded; +static QTAILQ_HEAD(, ImageFile) reloadable_image_list = QTAILQ_HEAD_INITIALIZER(reloadable_image_list); /* return the size or -1 if error */ int get_image_size(const char *filename) @@ -130,13 +131,15 @@ int load_image_targphys(const char *filename, return -1; } if (size > 0) { - rom_add_file_fixed(filename, addr, -1); + rom_add_initrd(filename, addr, -1); ImageFile *image; image = g_malloc0(sizeof(*image)); image->name = g_strdup(filename); image->loadaddr = addr; image->size = size; + image->type = IMAGE_FILE_FLAT; + QTAILQ_INSERT_TAIL(&reloadable_image_list, image, next); qemu_register_reset(image_file_reset, image); } return size; @@ -363,6 +366,11 @@ int load_elf(const char *filename, uint64_t (*translate_fn)(void *, uint64_t), qemu_register_reset(elf_reset32, elf); } + elf->image.size = ret; + elf->image.type = IMAGE_FILE_FLAT; + /* insert vmlinux into QLIST reloadable_image_list */ + QTAILQ_INSERT_TAIL(&reloadable_image_list, &elf->image, next); + close(fd); return ret; @@ -584,9 +592,13 @@ int load_uimage(const char *filename, hwaddr *ep, img->image.name = g_strdup(filename); img->image.loadaddr = *loadaddr; img->image.size = size; + img->image.type = IMAGE_FILE_UIMAGE; img->ep = ep; img->is_linux = is_linux; qemu_register_reset(uimage_reset, img); + + /* insert uImage into QLIST reloadable_image_list */ + QTAILQ_INSERT_TAIL(&reloadable_image_list, &img->image, next); } return size; } @@ -605,6 +617,7 @@ struct Rom { size_t romsize; uint8_t *data; int isrom; + int reloadable; char *fw_dir; char *fw_file; @@ -634,7 +647,7 @@ static void rom_insert(Rom *rom) } int rom_add_file(const char *file, const char *fw_dir, - hwaddr addr, int32_t bootindex) + hwaddr addr, int32_t bootindex, int reloadable) { Rom *rom; int rc, fd = -1; @@ -659,6 +672,7 @@ int rom_add_file(const char *file, const char *fw_dir, rom->fw_file = g_strdup(file); } rom->addr = addr; + rom->reloadable = reloadable; rom->romsize = lseek(fd, 0, SEEK_END); rom->data = g_malloc0(rom->romsize); lseek(fd, 0, SEEK_SET); @@ -702,7 +716,7 @@ err: } int rom_add_blob(const char *name, const void *blob, size_t len, - hwaddr addr) + hwaddr addr, int reloadable) { Rom *rom; @@ -710,6 +724,7 @@ int rom_add_blob(const char *name, const void *blob, size_t len, rom->name = g_strdup(name); rom->addr = addr; rom->romsize = len; + rom->reloadable = reloadable; rom->data = g_malloc0(rom->romsize); memcpy(rom->data, blob, len); rom_insert(rom); @@ -718,12 +733,12 @@ int rom_add_blob(const char *name, const void *blob, size_t len, int rom_add_vga(const char *file) { - return rom_add_file(file, "vgaroms", 0, -1); + return rom_add_file(file, "vgaroms", 0, -1, 0); } int rom_add_option(const char *file, int32_t bootindex) { - return rom_add_file(file, "genroms", 0, bootindex); + return rom_add_file(file, "genroms", 0, bootindex, 0); } static void rom_reset(void *unused) @@ -738,8 +753,9 @@ static void rom_reset(void *unused) continue; } cpu_physical_memory_write_rom(rom->addr, rom->data, rom->romsize); - if (rom->isrom) { + if ( rom->isrom || rom->reloadable ) { /* rom needs to be written only once */ + /* reloadable images could be free and reloaded on reset */ g_free(rom->data); rom->data = NULL; } @@ -767,6 +783,7 @@ int rom_load_all(void) addr += rom->romsize; section = memory_region_find(get_system_memory(), rom->addr, 1); rom->isrom = section.size && memory_region_is_rom(section.mr); + rom->reloadable = !rom->isrom && rom->reloadable; } qemu_register_reset(rom_reset, NULL); roms_loaded = 1; @@ -868,3 +885,16 @@ void do_info_roms(Monitor *mon) } } } + +void do_info_images(Monitor *mon) +{ + ImageFile *image; + + QTAILQ_FOREACH(image, &reloadable_image_list, next) { + monitor_printf(mon, "load_addr=" TARGET_FMT_plx + " size=0x%07zx type=%s file=\"%s\"\n", + image->loadaddr, image->size, + image->type ? "UIMAGE" : "FLAT", + image->name); + } +} diff --git a/hw/loader.h b/hw/loader.h index 69fac87..a2439ac 100644 --- a/hw/loader.h +++ b/hw/loader.h @@ -1,7 +1,14 @@ #ifndef LOADER_H #define LOADER_H +enum ImageFileType { + IMAGE_FILE_FLAT, + IMAGE_FILE_UIMAGE, +}; + typedef struct ImageFile { + QTAILQ_ENTRY(ImageFile) next; + enum ImageFileType type; char *name; hwaddr loadaddr; ssize_t size; @@ -44,19 +51,24 @@ void pstrcpy_targphys(const char *name, int rom_add_file(const char *file, const char *fw_dir, - hwaddr addr, int32_t bootindex); + hwaddr addr, int32_t bootindex, int reloadable); int rom_add_blob(const char *name, const void *blob, size_t len, - hwaddr addr); + hwaddr addr, int reloadable); int rom_load_all(void); void rom_set_fw(void *f); int rom_copy(uint8_t *dest, hwaddr addr, size_t size); void *rom_ptr(hwaddr addr); void do_info_roms(Monitor *mon); +void do_info_images(Monitor *mon); #define rom_add_file_fixed(_f, _a, _i) \ - rom_add_file(_f, NULL, _a, _i) + rom_add_file(_f, NULL, _a, _i, 0) +#define rom_add_initrd(_f, _a, _i) \ + rom_add_file(_f, NULL, _a, _i, 1) #define rom_add_blob_fixed(_f, _b, _l, _a) \ - rom_add_blob(_f, _b, _l, _a) + rom_add_blob(_f, _b, _l, _a, 1) +#define rom_add_fdt(_f, _b, _l, _a) \ + rom_add_blob(_f, _b, _l, _a, 0) #define PC_ROM_MIN_VGA 0xc0000 #define PC_ROM_MIN_OPTION 0xc8000 diff --git a/hw/ppc/e500.c b/hw/ppc/e500.c index 6749fff..2e5264a 100644 --- a/hw/ppc/e500.c +++ b/hw/ppc/e500.c @@ -332,7 +332,7 @@ static int ppce500_load_device_tree(CPUPPCState *env, done: qemu_devtree_dumpdtb(fdt, fdt_size); - ret = rom_add_blob_fixed(BINARY_DEVICE_TREE_FILE, fdt, fdt_size, addr); + ret = rom_add_fdt(BINARY_DEVICE_TREE_FILE, fdt, fdt_size, addr); if (ret < 0) { goto out; } diff --git a/hw/ppc440_bamboo.c b/hw/ppc440_bamboo.c index cc85607..a43050d 100644 --- a/hw/ppc440_bamboo.c +++ b/hw/ppc440_bamboo.c @@ -111,7 +111,7 @@ static int bamboo_load_device_tree(hwaddr addr, qemu_devtree_setprop_cell(fdt, "/cpus/cpu@0", "timebase-frequency", tb_freq); - ret = rom_add_blob_fixed(BINARY_DEVICE_TREE_FILE, fdt, fdt_size, addr); + ret = rom_add_fdt(BINARY_DEVICE_TREE_FILE, fdt, fdt_size, addr); g_free(fdt); out: diff --git a/monitor.c b/monitor.c index c0e32d6..91425c6 100644 --- a/monitor.c +++ b/monitor.c @@ -2708,6 +2708,13 @@ static mon_cmd_t info_cmds[] = { .mhandler.info = hmp_info_balloon, }, { + .name = "images", + .args_type = "", + .params = "", + .help = "show the images which could be reloaded on reset", + .mhandler.info = do_info_images, + }, + { .name = "qtree", .args_type = "", .params = "", -- 1.7.1