[Skiboot] [PATCH v8 07/11] Load the ultravisor from flash and decompress
Ryan Grimm
grimm at linux.vnet.ibm.com
Wed Sep 9 06:19:16 AEST 2020
On Fri, 2020-08-28 at 14:54 +1000, Oliver O'Halloran wrote:
>
> > +static int uv_decompress_image(void)
> > +{
> > + struct xz_decompress uv_xz;
> > + uint64_t uv_fw_size;
> > +
> > + if (!uv_image) {
> > + prerror("UV: Preload hasn't started yet!
> > Aborting.\n");
> > + return OPAL_INTERNAL_ERROR;
> > + }
> > +
> > + if (wait_for_resource_loaded(RESOURCE_ID_UV_IMAGE,
> > + RESOURCE_SUBID_NONE) !=
> > OPAL_SUCCESS) {
> > + prerror("UV: Ultravisor image load failed\n");
> > + return OPAL_INTERNAL_ERROR;
> > + }
> > +
> > + uv_xz.dst = (void *)dt_get_address(uv_fw_node, 0,
> > &uv_fw_size);
> > + uv_xz.dst_size = uv_fw_size;
> > + uv_xz.src_size = uv_image_size;
> > + uv_xz.src = uv_image;
> > +
> > + if (stb_is_container((void*)uv_xz.src, uv_xz.src_size))
> > + uv_xz.src = uv_xz.src + SECURE_BOOT_HEADERS_SIZE;
> > +
> > + xz_start_decompress(&uv_xz);
> > + if ((uv_xz.status != OPAL_PARTIAL) && (uv_xz.status
> > != OPAL_SUCCESS)) {
>
> Weird indentation and why would we get OPAL_PARTIAL here?
>
Oh, oops, indents fixed.
Well, the comment in xz_start_decompress show this:
* The `status` value will be OPAL_PARTIAL till the job completes
(successfully
* or not)
The code seems to work that way and it's a job queue so we need to
check for both since it might not complete right?
-Ryan
> > + prerror("UV: XZ decompression failed status
> > 0x%x\n", uv_xz.status);
> > + return OPAL_INTERNAL_ERROR;
> > + }
> > +
> > + return OPAL_SUCCESS;
> > +}
> > +
> > void init_uv()
> > {
> > uint64_t uv_dt_src, uv_fw_sz;
> > struct dt_node *reserved_mem;
> > + int ret;
> >
> > if (!is_msr_bit_set(MSR_S)) {
> > prlog(PR_DEBUG, "UV: S bit not set\n");
> > @@ -84,23 +123,59 @@ void init_uv()
> > if (!uv_fw_node) {
> > prlog(PR_DEBUG, "UV: No ibm,uv-firmware node found,
> > disabling pef\n");
> > cpu_disable_pef();
> > - return;
> > + goto err;
> > }
> >
> > - reserved_mem = dt_find_by_path(dt_root, "/reserved-
> > memory/ibm,uv-firmware");
> > - if (!reserved_mem) {
> > - prerror("UV: No reserved memory for ibm,uv-firmware
> > found\n");
> > - return;
> > - }
> > + /* If decompress fails, look for reserved memory by Mambo
> > tcl or cronus BML */
> > + ret = uv_decompress_image();
> > + if (ret) {
> > + reserved_mem = dt_find_by_path(dt_root, "/reserved-
> > memory/ibm,uv-firmware");
> > + if (!reserved_mem) {
> > + prerror("UV: No reserved memory for ibm,uv-
> > firmware found\n");
> > + return;
> > + }
> >
> > - uv_dt_src = dt_get_address(reserved_mem, 0, &uv_fw_sz);
> > - uv_base_addr = dt_get_address(uv_fw_node, 0, NULL);
> > + uv_dt_src = dt_get_address(reserved_mem, 0,
> > &uv_fw_sz);
> > + uv_base_addr = dt_get_address(uv_fw_node, 0, NULL);
> >
> > - prlog(PR_INFO, "UV: Copying 0x%llx bytes to protected
> > memory 0x%llx from 0x%llx\n",
> > + prlog(PR_INFO, "UV: Copying 0x%llx bytes to
> > protected memory 0x%llx from 0x%llx\n",
> > uv_fw_sz, uv_base_addr,
> > uv_dt_src);
> >
> > - memcpy((void *)uv_base_addr, (void *)uv_dt_src, uv_fw_sz);
> > + memcpy((void *)uv_base_addr, (void *)uv_dt_src,
> > uv_fw_sz);
> > + }
> >
> > dt_add_property_u64(uv_fw_node, "memcons",
> > (u64)&uv_memcons);
> > debug_descriptor.uv_memcons_phys = (u64)&uv_memcons;
> > +err:
> > + local_free(uv_image);
> > +}
> > +
> > +/*
> > + * Preload the UV image from PNOR partition
> > + *
> > + * uv_image is allocated locally to the chip and freed here if
> > preload fails
> > + * or free in init_uv
> > + */
> > +void uv_preload_image(void)
> > +{
> > + struct proc_chip *chip = next_chip(NULL);
> > + int ret;
> > +
> > + prlog(PR_DEBUG, "UV: Preload starting\n");
> > +
> > + uv_image_size = MAX_COMPRESSED_UV_IMAGE_SIZE;
> > + uv_image = local_alloc(chip->id, uv_image_size,
> > uv_image_size);
> > + if (!uv_image) {
> > + prerror("UV: Memory allocation failed\n");
> > + return;
> > + }
> > + memset(uv_image, 0, uv_image_size);
> > +
> > + ret = start_preload_resource(RESOURCE_ID_UV_IMAGE,
> > RESOURCE_SUBID_NONE,
> > + uv_image, &uv_image_size);
> > +
> > + if (ret != OPAL_SUCCESS) {
> > + local_free(uv_image);
> > + prerror("UV: platform load failed: %d\n", ret);
> > + }
> > }
> > diff --git a/include/platform.h b/include/platform.h
> > index ef93278b..57b2eeef 100644
> > --- a/include/platform.h
> > +++ b/include/platform.h
> > @@ -17,6 +17,7 @@ enum resource_id {
> > RESOURCE_ID_INITRAMFS,
> > RESOURCE_ID_CAPP,
> > RESOURCE_ID_IMA_CATALOG,
> > + RESOURCE_ID_UV_IMAGE,
> > RESOURCE_ID_VERSION,
> > RESOURCE_ID_KERNEL_FW,
> > };
> > diff --git a/include/ultravisor.h b/include/ultravisor.h
> > index 84217d66..8048cb76 100644
> > --- a/include/ultravisor.h
> > +++ b/include/ultravisor.h
> > @@ -64,4 +64,7 @@ static inline int uv_xscom_write(u64 partid, u64
> > pcb_addr, u64 val)
> > return ucall(UV_WRITE_SCOM, retbuf, partid, pcb_addr, val);
> > }
> >
> > +#define MAX_COMPRESSED_UV_IMAGE_SIZE 0x40000 /* 256 Kilobytes */
> > +void uv_preload_image(void);
> > +
> > #endif /* __ULTRAVISOR_H */
> > --
> > 2.18.4
> >
> > _______________________________________________
> > Skiboot mailing list
> > Skiboot at lists.ozlabs.org
> > https://lists.ozlabs.org/listinfo/skiboot
More information about the Skiboot
mailing list