Exemplo n.º 1
0
void *cbfs_get_contents(struct cbfs_handle *handle, size_t *size, size_t limit)
{
	struct cbfs_media *m = &handle->media;
	size_t on_media_size = handle->content_size;
	int algo = CBFS_COMPRESS_NONE;
	void *ret = NULL;
	size_t dummy_size;

	if (!size)
		size = &dummy_size;

	struct cbfs_file_attr_compression *comp =
		cbfs_get_attr(handle, CBFS_FILE_ATTR_TAG_COMPRESSION);
	if (comp) {
		algo = ntohl(comp->compression);
		DEBUG("File '%s' is compressed (alg=%d)\n", name, algo);
		*size = ntohl(comp->decompressed_size);
		/* TODO: Implement partial decompression with |limit| */
	}

	if (algo == CBFS_COMPRESS_NONE) {
		if (limit != 0 && limit < on_media_size) {
			*size = limit;
			on_media_size = limit;
		} else {
			*size = on_media_size;
		}
	}

	void *data = m->map(m, handle->media_offset + handle->content_offset,
			    on_media_size);
	if (data == CBFS_MEDIA_INVALID_MAP_ADDRESS)
		return NULL;

	ret = malloc(*size);
	if (ret != NULL && !cbfs_decompress(algo, data, ret, *size)) {
		free(ret);
		ret = NULL;
	}

	m->unmap(m, data);
	return ret;
}
Exemplo n.º 2
0
int rmodule_stage_load(struct rmod_stage_load *rsl, struct cbfs_stage *stage)
{
	struct rmodule rmod_stage;
	size_t region_size;
	char *stage_region;
	int rmodule_offset;
	int load_offset;

	if (stage == NULL || rsl->prog == NULL || rsl->prog->name == NULL)
		return -1;

	rmodule_offset =
		rmodule_calc_region(DYN_CBMEM_ALIGN_SIZE,
		                    stage->memlen, &region_size, &load_offset);

	stage_region = cbmem_add(rsl->cbmem_id, region_size);

	if (stage_region == NULL)
		return -1;

	printk(BIOS_INFO, "Decompressing stage %s @ 0x%p (%d bytes)\n",
	       rsl->prog->name, &stage_region[rmodule_offset], stage->memlen);

	if (!cbfs_decompress(stage->compression, &stage[1],
	                    &stage_region[rmodule_offset], stage->len))
		return -1;

	if (rmodule_parse(&stage_region[rmodule_offset], &rmod_stage))
		return -1;

	if (rmodule_load(&stage_region[load_offset], &rmod_stage))
		return -1;

	prog_set_area(rsl->prog, rmod_stage.location,
			rmodule_memory_size(&rmod_stage));
	prog_set_entry(rsl->prog, rmodule_entry(&rmod_stage), NULL);

	return 0;
}
Exemplo n.º 3
0
void *cbfs_get_file_content(struct cbfs_media *media, const char *name,
			    int type, size_t *sz)
{
	struct cbfs_media default_media;

	if (media == CBFS_DEFAULT_MEDIA) {
		media = &default_media;
		if (init_default_cbfs_media(media) != 0) {
			ERROR("Failed to initialize default media.\n");
			return NULL;
		}
	}

	struct cbfs_file *file = cbfs_get_file(media, name);

	if (sz)
		*sz = 0;

	if (file == NULL) {
		ERROR("Could not find file '%s'.\n", name);
		return NULL;
	}

	if (ntohl(file->type) != type) {
		ERROR("File '%s' is of type %x, but we requested %x.\n", name,
		      ntohl(file->type), type);
		return NULL;
	}

	void *file_content = (void *)CBFS_SUBHEADER(file);

	struct cbfs_file_attribute *attr =
		cbfs_file_find_attr(file, CBFS_FILE_ATTR_TAG_COMPRESSION);

	size_t final_size = ntohl(file->len);
	int compression_algo = CBFS_COMPRESS_NONE;
	if (attr) {
		struct cbfs_file_attr_compression *comp =
			(struct cbfs_file_attr_compression *)attr;
		compression_algo = ntohl(comp->compression);
		DEBUG("File '%s' is compressed (alg=%d)\n",
		      name, compression_algo);
		final_size = ntohl(comp->decompressed_size);
	}

	void *dst = malloc(final_size);
	if (dst == NULL)
		goto err;

	if (!cbfs_decompress(compression_algo, file_content, dst, final_size))
		goto err;

	if (sz)
		*sz = final_size;

	media->unmap(media, file);
	return dst;

err:
	media->unmap(media, file);
	free(dst);
	return NULL;
}