void pstrcpy_targphys(target_phys_addr_t dest, int buf_size, const char *source) { static const uint8_t nul_byte = 0; const char *nulp; if (buf_size <= 0) return; nulp = memchr(source, 0, buf_size); if (nulp) { cpu_physical_memory_write_rom(dest, (uint8_t *)source, (nulp - source) + 1); } else { cpu_physical_memory_write_rom(dest, (uint8_t *)source, buf_size - 1); cpu_physical_memory_write_rom(dest, &nul_byte, 1); } }
static void idreg_init(hwaddr addr) { DeviceState *dev; SysBusDevice *s; dev = qdev_create(NULL, TYPE_MACIO_ID_REGISTER); qdev_init_nofail(dev); s = SYS_BUS_DEVICE(dev); sysbus_mmio_map(s, 0, addr); cpu_physical_memory_write_rom(&address_space_memory, addr, idreg_data, sizeof(idreg_data)); }
/* read()-like version */ int read_targphys(int fd, target_phys_addr_t dst_addr, size_t nbytes) { uint8_t buf[4096]; target_phys_addr_t dst_begin = dst_addr; size_t want, did; while (nbytes) { want = nbytes > sizeof(buf) ? sizeof(buf) : nbytes; did = read(fd, buf, want); if (did != want) break; cpu_physical_memory_write_rom(dst_addr, buf, did); dst_addr += did; nbytes -= did; } return dst_addr - dst_begin; }
/* Load a U-Boot image. */ int load_uboot(const char *filename, target_ulong *ep, int *is_linux) { int fd; int size; uboot_image_header_t h; uboot_image_header_t *hdr = &h; uint8_t *data = NULL; fd = open(filename, O_RDONLY | O_BINARY); if (fd < 0) return -1; size = read(fd, hdr, sizeof(uboot_image_header_t)); if (size < 0) goto fail; bswap_uboot_header(hdr); if (hdr->ih_magic != IH_MAGIC) goto fail; /* TODO: Implement Multi-File images. */ if (hdr->ih_type == IH_TYPE_MULTI) { fprintf(stderr, "Unable to load multi-file u-boot images\n"); goto fail; } /* TODO: Implement compressed images. */ if (hdr->ih_comp != IH_COMP_NONE) { fprintf(stderr, "Unable to load compressed u-boot images\n"); goto fail; } /* TODO: Check CPU type. */ if (is_linux) { if (hdr->ih_type == IH_TYPE_KERNEL && hdr->ih_os == IH_OS_LINUX) *is_linux = 1; else *is_linux = 0; } *ep = hdr->ih_ep; data = qemu_malloc(hdr->ih_size); if (!data) goto fail; if (read(fd, data, hdr->ih_size) != hdr->ih_size) { fprintf(stderr, "Error reading file\n"); goto fail; } cpu_physical_memory_write_rom(hdr->ih_load, data, hdr->ih_size); return hdr->ih_size; fail: if (data) qemu_free(data); close(fd); return -1; }
/* Load a U-Boot image. */ int load_uimage(const char *filename, target_ulong *ep, target_ulong *loadaddr, int *is_linux) { int fd; int size; uboot_image_header_t h; uboot_image_header_t *hdr = &h; uint8_t *data = NULL; int ret = -1; fd = open(filename, O_RDONLY | O_BINARY); if (fd < 0) return -1; size = read(fd, hdr, sizeof(uboot_image_header_t)); if (size < 0) goto out; bswap_uboot_header(hdr); if (hdr->ih_magic != IH_MAGIC) goto out; /* TODO: Implement other image types. */ if (hdr->ih_type != IH_TYPE_KERNEL) { fprintf(stderr, "Can only load u-boot image type \"kernel\"\n"); goto out; } switch (hdr->ih_comp) { case IH_COMP_NONE: case IH_COMP_GZIP: break; default: fprintf(stderr, "Unable to load u-boot images with compression type %d\n", hdr->ih_comp); goto out; } /* TODO: Check CPU type. */ if (is_linux) { if (hdr->ih_os == IH_OS_LINUX) *is_linux = 1; else *is_linux = 0; } *ep = hdr->ih_ep; data = qemu_malloc(hdr->ih_size); if (read(fd, data, hdr->ih_size) != hdr->ih_size) { fprintf(stderr, "Error reading file\n"); goto out; } if (hdr->ih_comp == IH_COMP_GZIP) { uint8_t *compressed_data; size_t max_bytes; ssize_t bytes; compressed_data = data; max_bytes = UBOOT_MAX_GUNZIP_BYTES; data = qemu_malloc(max_bytes); bytes = gunzip(data, max_bytes, compressed_data, hdr->ih_size); qemu_free(compressed_data); if (bytes < 0) { fprintf(stderr, "Unable to decompress gzipped image!\n"); goto out; } hdr->ih_size = bytes; } cpu_physical_memory_write_rom(hdr->ih_load, data, hdr->ih_size); if (loadaddr) *loadaddr = hdr->ih_load; ret = hdr->ih_size; out: if (data) qemu_free(data); close(fd); return ret; }