[U-Boot] [PATCH v2 4/5] arm: socfpga: Add intermediate driver between flash and FPGA manager

Chee, Tien Fong tien.fong.chee at intel.com
Wed Aug 9 04:50:07 UTC 2017


On Sel, 2017-08-08 at 12:11 +0200, Marek Vasut wrote:
> On 08/08/2017 12:06 PM, Chee, Tien Fong wrote:
> > 
> > On Sel, 2017-08-08 at 11:32 +0200, Marek Vasut wrote:
> > > 
> > > On 08/08/2017 11:12 AM, tien.fong.chee at intel.com wrote:
> > > > 
> > > > 
> > > > From: Tien Fong Chee <tien.fong.chee at intel.com>
> > > > 
> > > > Configuration flip-flop driver is mainly used for handling the
> > > > FPGA
> > > > program
> > > > operation where the FPGA image loading from the flash into FPGA
> > > > manager.
> > > I don't understand what this driver is for , sorry.
> > > 
> > this is core driver for handling fpga program operation from flash
> > to
> > fpga manager. I can improve the message. Let me know if you have
> > other
> > comment need to add.
> Yes, it's not clear what this driver is for. It dabbles into multiple
> subsystems , but I don't understand how is this useful.
> 
> > 
> > > 
> > > Coding style issues are present (camel case, wrong comment style,
> > > use
> > > checkpatch).
> > > 
> > Okay, i will run checkpatch.
> You should always run checkpatch before submitting patches.
> 
> > 
> > > 
> > > If this is for some FPGA loading, can this functionality be
> > > scripted
> > > instead?
> > > 
> > Sorry, i'm not getting you. How functionality be scripted? Could
> > you
> > provide some example or details explanation?
> ie. "load" (from fs) + "fpga load" (program FPGA) commands ?
> I think the fpga command already has some support for loading from FS
> too.
> 
Currently, we already have fpga load commands in fpga driver, fpga rbf
is loaded to memory, and programmed to fpga from memory, where memory
location would be decided by user, it could be OCRAM or SDRAM.

for fpga loadfs command, i plan to implement it after having complete
boot to U-boot console, since this is quite complex and involving some
hardware workaround issue, and some use case scenarios need to be
considerd. For example reconfiguring fpga with periperal rbf can
corrupt the sdram since sdram IOs is part of the fpga periph rbf. I
need console to run a lot different scenarios testing.

We still need cff.c, because most functionality in cff.c are required
by fpga loadfs command.
> > 
> > Thanks.
> > > 
> > > > 
> > > > 
> > > > Signed-off-by: Tien Fong Chee <tien.fong.chee at intel.com>
> > > > ---
> > > >  arch/arm/mach-socfpga/cff.c              | 582
> > > > +++++++++++++++++++++++++++++++
> > > >  arch/arm/mach-socfpga/include/mach/cff.h |  40 +++
> > > >  include/configs/socfpga_arria10_socdk.h  |   6 +
> > > >  3 files changed, 628 insertions(+)
> > > >  create mode 100644 arch/arm/mach-socfpga/cff.c
> > > >  create mode 100644 arch/arm/mach-socfpga/include/mach/cff.h
> > > > 
> > > > diff --git a/arch/arm/mach-socfpga/cff.c b/arch/arm/mach-
> > > > socfpga/cff.c
> > > > new file mode 100644
> > > > index 0000000..ccee5e9
> > > > --- /dev/null
> > > > +++ b/arch/arm/mach-socfpga/cff.c
> > > > @@ -0,0 +1,582 @@
> > > > +/*
> > > > + * COPYRIGHT (C) 2017 Intel Corporation <www.intel.com>
> > > > + *
> > > > + * SPDX-License-Identifier:    GPL-2.0
> > > > + */
> > > > +
> > > > +#include <altera.h>
> > > > +#include <common.h>
> > > > +#include <asm/io.h>
> > > > +#include <asm/arch/cff.h>
> > > > +#include <asm/arch/fpga_manager.h>
> > > > +#include <asm/arch/misc.h>
> > > > +#include <asm/arch/system_manager.h>
> > > > +#include <asm/arch/reset_manager.h>
> > > > +#include <errno.h>
> > > > +#include <fat.h>
> > > > +#include <fs.h>
> > > > +#include <fdtdec.h>
> > > > +#include <malloc.h>
> > > > +#include <mmc.h>
> > > > +#include <spi_flash.h>
> > > > +#include <spl.h>
> > > > +#include <watchdog.h>
> > > > +
> > > > +#define RBF_UNENCRYPTED 0xa65c
> > > > +#define RBF_ENCRYPTED 0xa65d
> > > > +#define ARRIA10RBF_PERIPH 0x0001
> > > > +#define ARRIA10RBF_CORE 0x8001
> > > > +
> > > > +DECLARE_GLOBAL_DATA_PTR;
> > > > +
> > > > +static int flash_type = -1;
> > > > +
> > > > +struct mmc *mmc;
> > > > +
> > > > +/* Local functions */
> > > > +static int cff_flash_read(struct cff_flash_info
> > > > *cff_flashinfo,
> > > > u32 *buffer,
> > > > +	u32 *buffer_sizebytes);
> > > > +static int cff_flash_preinit(struct cff_flash_info
> > > > *cff_flashinfo,
> > > > +	fpga_fs_info *fpga_fsinfo, u32 *buffer, u32
> > > > *buffer_sizebytes);
> > > > +#ifdef CONFIG_CMD_FPGA_LOADFS
> > > > +static const char *get_cff_filename(const void *fdt, int *len,
> > > > u32
> > > > core);
> > > > +#else
> > > > +static int get_cff_offset(const void *fdt, u32 core);
> > > > +#endif
> > > > +
> > > > +static struct mmc *init_mmc_device(int dev, bool force_init)
> > > > +{
> > > > +	struct mmc *mmc;
> > > > +
> > > > +	mmc = find_mmc_device(dev);
> > > > +	if (!mmc) {
> > > > +		printf("no mmc device at slot %x\n", dev);
> > > > +		return NULL;
> > > > +	}
> > > > +
> > > > +	if (force_init)
> > > > +		mmc->has_init = 0;
> > > > +	if (mmc_init(mmc))
> > > > +		return NULL;
> > > > +
> > > > +	return mmc;
> > > > +}
> > > > +
> > > > +static int cff_flash_probe(struct cff_flash_info
> > > > *cff_flashinfo)
> > > > +{
> > > > +	int dev = 0;
> > > > +
> > > > +	if(BOOT_DEVICE_MMC1 == flash_type)
> > > > +	{
> > > > +		mmc = init_mmc_device(dev, true);
> > > > +
> > > > +		if (!mmc)
> > > > +			return -ENOTBLK;
> > > > +
> > > > +#ifdef CONFIG_CMD_FPGA_LOADFS
> > > > +		/* we are looking at the FAT partition */
> > > > +		if (fat_register_device(mmc_get_blk_desc(mmc),
> > > > +			cff_flashinfo-
> > > > >sdmmc_flashinfo.dev_part))
> > > > {
> > > > +			printf("Failed to set filesystem to
> > > > FAT.\n");
> > > > +			return -EPERM;
> > > > +		}
> > > > +#endif
> > > > +	}
> > > > +
> > > > +	return flash_type;
> > > > +}
> > > > +
> > > > +static int flash_read(struct cff_flash_info *cff_flashinfo,
> > > > +	u32 size_read,
> > > > +	u32 *buffer_ptr)
> > > > +{
> > > > +	size_t ret = EEXIST;
> > > > +#ifdef CONFIG_CMD_FPGA_LOADFS
> > > > +	loff_t actread;
> > > > +#endif
> > > > +
> > > > +	if(BOOT_DEVICE_MMC1 == flash_type) {
> > > > +#ifdef CONFIG_CMD_FPGA_LOADFS
> > > > +		ret = fat_read_file(cff_flashinfo-
> > > > > 
> > > > > sdmmc_flashinfo.filename,
> > > > +				buffer_ptr, cff_flashinfo-
> > > > > 
> > > > > flash_offset,
> > > > +				 size_read, &actread);
> > > > +
> > > > +		if (ret || actread != size_read) {
> > > > +			printf("Failed to read %s from FAT %d
> > > > ",
> > > > +				cff_flashinfo-
> > > > > 
> > > > > sdmmc_flashinfo.filename,
> > > > +				 ret);
> > > > +			printf("!= %d.\n", size_read);
> > > > +			return -EPERM;
> > > > +		} else
> > > > +			ret = actread;
> > > > +#else
> > > > +		u32 blk = cff_flashinfo->flash_offset/mmc-
> > > > > 
> > > > > read_bl_len;
> > > > +		u32 cnt = size_read / mmc->read_bl_len;
> > > > +
> > > > +		if (!cnt)
> > > > +			cnt = 1;
> > > > +
> > > > +		if((size_read % mmc->read_bl_len) &&
> > > > +				(size_read >= mmc-
> > > > >read_bl_len))
> > > > +			cnt++;
> > > > +
> > > > +		ret = blk_dread(mmc_get_blk_desc(mmc), blk,
> > > > cnt,
> > > > +			 buffer_ptr);
> > > > +
> > > > +		if (cnt != ret)
> > > > +			return -EPERM;
> > > > +#endif
> > > > +	}
> > > > +
> > > > +		return ret;
> > > > +}
> > > > +
> > > > +#ifdef CONFIG_CMD_FPGA_LOADFS
> > > > +const char *get_cff_filename(const void *fdt, int *len, u32
> > > > core)
> > > > +{
> > > > +	const char *cff_filename = NULL;
> > > > +	const char *cell;
> > > > +	int nodeoffset;
> > > > +	nodeoffset = fdt_subnode_offset(fdt, 0, "chosen");
> > > > +
> > > > +	if (nodeoffset >= 0) {
> > > > +		if (core)
> > > > +			cell = fdt_getprop(fdt,
> > > > +					nodeoffset,
> > > > +					"cffcore-file",
> > > > +					len);
> > > > +		else
> > > > +			cell = fdt_getprop(fdt, nodeoffset,
> > > > "cff-
> > > > file", len);
> > > > +
> > > > +		if (cell)
> > > > +			cff_filename = cell;
> > > > +	}
> > > > +
> > > > +	return cff_filename;
> > > > +}
> > > > +#else
> > > > +static int get_cff_offset(const void *fdt, u32 core)
> > > > +{
> > > > +	int nodeoffset = 0;
> > > > +
> > > > +	nodeoffset = fdt_subnode_offset(fdt, 0, "chosen");
> > > > +
> > > > +	if (nodeoffset >= 0) {
> > > > +		if (core)
> > > > +			return fdtdec_get_int(fdt,
> > > > +					nodeoffset,
> > > > +					"cffcore-offset",
> > > > +					-ESPIPE);
> > > > +		else
> > > > +			return fdtdec_get_int(fdt,
> > > > +					nodeoffset,
> > > > +					"cff-offset",
> > > > +					-ESPIPE);
> > > > +	}
> > > > +	return -ESPIPE;
> > > > +}
> > > > +#endif
> > > > +
> > > > +int cff_from_sdmmc_env(u32 core)
> > > > +{
> > > > +	int rval = -ENOENT;
> > > > +	fpga_fs_info fpga_fsinfo;
> > > > +
> > > > +#ifdef CONFIG_CMD_FPGA_LOADFS
> > > > +	int len = 0;
> > > > +	const char *cff = NULL;
> > > > +#else
> > > > +	char addrToString[32] = {0};
> > > > +
> > > > +	int sdmmc_rbf_rawaddr = -ENOENT;
> > > > +#endif
> > > > +
> > > > +	flash_type = spl_boot_device();
> > > > +
> > > > +	fpga_fsinfo.interface = "sdmmc";
> > > > +
> > > > +#ifdef CONFIG_CMD_FPGA_LOADFS
> > > > +	cff = get_cff_filename(gd->fdt_blob, &len, core);
> > > > +
> > > > +	/* FAT periph RBF file reading */
> > > > +	if (cff && (len > 0)) {
> > > > +		mmc_initialize(gd->bd);
> > > > +
> > > > +		fpga_fsinfo.filename = (char *)cff;
> > > > +
> > > > +		fpga_fsinfo.dev_part =
> > > > getenv("cff_devsel_partition");
> > > > +
> > > > +		if (NULL == fpga_fsinfo.dev_part) {
> > > > +			/* FAT partition */
> > > > +			fpga_fsinfo.dev_part = "1";
> > > > +
> > > > +			printf("No SD/MMC partition found in
> > > > environment. ");
> > > > +			printf("Assuming partition 1.\n");
> > > > +		}
> > > > +
> > > > +		rval = cff_from_flash(&fpga_fsinfo);
> > > > +	}
> > > > +#else
> > > > +	sdmmc_rbf_rawaddr = get_cff_offset(gd->fdt_blob,
> > > > core);
> > > > +
> > > > +	 /* RAW periph RBF reading */
> > > > +	if (sdmmc_rbf_rawaddr >= 0) {
> > > > +		sprintf(addrToString, "%x",
> > > > sdmmc_rbf_rawaddr);
> > > > +
> > > > +		fpga_fsinfo.filename = addrToString;
> > > > +
> > > > +		rval = cff_from_flash(&fpga_fsinfo);
> > > > +	}
> > > > +#endif
> > > > +	return rval;
> > > > +}
> > > > +
> > > > +void get_rbf_image_info(struct rbf_info *rbf, u16 *buffer)
> > > > +{
> > > > +	/*
> > > > +	  Magic ID starting at:
> > > > +	   -> 1st dword in periph.rbf
> > > > +	   -> 2nd dword in core.rbf
> > > > +	*/
> > > > +	u32 word_reading_max = 2;
> > > > +	u32 i;
> > > > +
> > > > +	for(i = 0; i < word_reading_max; i++)
> > > > +	{
> > > > +		if(RBF_UNENCRYPTED == *(buffer + i)) /* PERIPH
> > > > RBF
> > > > */
> > > > +			rbf->security = unencrypted;
> > > > +		else if (RBF_ENCRYPTED == *(buffer + i))
> > > > +			rbf->security = encrypted;
> > > > +		else if (RBF_UNENCRYPTED == *(buffer + i + 1))
> > > > /*
> > > > CORE RBF */
> > > > +					rbf->security =
> > > > unencrypted;
> > > > +		else if (RBF_ENCRYPTED == *(buffer + i + 1))
> > > > +					rbf->security =
> > > > encrypted;
> > > > +		else {
> > > > +			rbf->security = invalid;
> > > > +			continue;
> > > > +		}
> > > > +
> > > > +		/* PERIPH RBF */
> > > > +		if (ARRIA10RBF_PERIPH == *(buffer + i + 1)) {
> > > > +			rbf->section = periph_section;
> > > > +			break;
> > > > +		}
> > > > +		else if (ARRIA10RBF_CORE == *(buffer + i + 1))
> > > > {
> > > > +			rbf->section = core_section;
> > > > +			break;
> > > > +		} /* CORE RBF */
> > > > +		else if (ARRIA10RBF_PERIPH == *(buffer + i +
> > > > 2)) {
> > > > +			rbf->section = periph_section;
> > > > +			break;
> > > > +		}
> > > > +		else if (ARRIA10RBF_CORE == *(buffer + i + 2))
> > > > {
> > > > +			rbf->section = core_section;
> > > > +			break;
> > > > +		}
> > > > +		else {
> > > > +			rbf->section = unknown;
> > > > +			break;
> > > > +		}
> > > > +	}
> > > > +
> > > > +	return;
> > > > +}
> > > > +
> > > > +static int cff_flash_preinit(struct cff_flash_info
> > > > *cff_flashinfo,
> > > > +	fpga_fs_info *fpga_fsinfo, u32 *buffer, u32
> > > > *buffer_sizebytes)
> > > > +{
> > > > +	u32 *bufferptr_after_header = NULL;
> > > > +	u32 buffersize_after_header = 0;
> > > > +	u32 rbf_header_data_size = 0;
> > > > +	int ret = 0;
> > > > +	/* To avoid from keeping re-read the contents */
> > > > +	struct image_header *header = &(cff_flashinfo-
> > > > >header);
> > > > +	size_t buffer_size = *buffer_sizebytes;
> > > > +	u32 *buffer_ptr = (u32 *)*buffer;
> > > > +
> > > > +#ifdef CONFIG_CMD_FPGA_LOADFS
> > > > +	cff_flashinfo->sdmmc_flashinfo.filename = fpga_fsinfo-
> > > > > 
> > > > > filename;
> > > > +	cff_flashinfo->flash_offset = 0;
> > > > +#else
> > > > +	cff_flashinfo->flash_offset =
> > > > +		simple_strtoul(fpga_fsinfo->filename, NULL,
> > > > 16);
> > > > +#endif
> > > > +
> > > > +	 /* Load mkimage header into buffer */
> > > > +	ret = flash_read(cff_flashinfo,
> > > > +			sizeof(struct image_header),
> > > > buffer_ptr);
> > > > +
> > > > +	if (0 >= ret) {
> > > > +		printf(" Failed to read mkimage header from
> > > > flash.\n");
> > > > +		return -ENOENT;
> > > > +	}
> > > > +
> > > > +	WATCHDOG_RESET();
> > > > +
> > > > +	memcpy(header, (u_char *)buffer_ptr, sizeof(*header));
> > > > +
> > > > +	if (!image_check_magic(header)) {
> > > > +		printf("FPGA: Bad Magic Number.\n");
> > > > +		return -EBADF;
> > > > +	}
> > > > +
> > > > +	if (!image_check_hcrc(header)) {
> > > > +		printf("FPGA: Bad Header Checksum.\n");
> > > > +		return -EPERM;
> > > > +	}
> > > > +
> > > > +	/* Getting rbf data size */
> > > > +	cff_flashinfo->remaining =
> > > > +		image_get_data_size(header);
> > > > +
> > > > +	/* Calculate total size of both rbf data with mkimage
> > > > header */
> > > > +	rbf_header_data_size = cff_flashinfo->remaining +
> > > > +				sizeof(struct image_header);
> > > > +
> > > > +	/* Loading to buffer chunk by chunk, normally for
> > > > OCRAM
> > > > buffer */
> > > > +	if (rbf_header_data_size > buffer_size) {
> > > > +		/* Calculate size of rbf data in the buffer */
> > > > +		buffersize_after_header =
> > > > +			buffer_size - sizeof(struct
> > > > image_header);
> > > > +		cff_flashinfo->remaining -=
> > > > buffersize_after_header;
> > > > +	} else {
> > > > +	/* Loading whole rbf image into buffer, normally for
> > > > DDR
> > > > buffer */
> > > > +		buffer_size = rbf_header_data_size;
> > > > +		/* Calculate size of rbf data in the buffer */
> > > > +		buffersize_after_header =
> > > > +			buffer_size - sizeof(struct
> > > > image_header);
> > > > +		cff_flashinfo->remaining = 0;
> > > > +	}
> > > > +
> > > > +	/* Loading mkimage header and rbf data into buffer */
> > > > +	ret = flash_read(cff_flashinfo, buffer_size,
> > > > buffer_ptr);
> > > > +
> > > > +	if (0 >= ret) {
> > > > +		printf(" Failed to read mkimage header and rbf
> > > > data ");
> > > > +		printf("from flash.\n");
> > > > +		return -ENOENT;
> > > > +	}
> > > > +
> > > > +	/* Getting pointer of rbf data starting address where
> > > > is
> > > > it
> > > > +	   right after mkimage header */
> > > > +	bufferptr_after_header =
> > > > +		(u32 *)((u_char *)buffer_ptr + sizeof(struct
> > > > image_header));
> > > > +
> > > > +	/* Update next reading rbf data flash offset */
> > > > +	cff_flashinfo->flash_offset += buffer_size;
> > > > +
> > > > +	/* Update the starting addr of rbf data to init FPGA &
> > > > programming
> > > > +	   into FPGA */
> > > > +	*buffer = (u32)bufferptr_after_header;
> > > > +
> > > > +	get_rbf_image_info(&cff_flashinfo->rbfinfo, (u16
> > > > *)bufferptr_after_header);
> > > > +
> > > > +	/* Update the size of rbf data to be programmed into
> > > > FPGA
> > > > */
> > > > +	*buffer_sizebytes = buffersize_after_header;
> > > > +
> > > > +#ifdef CONFIG_CHECK_FPGA_DATA_CRC
> > > > +	cff_flashinfo->datacrc =
> > > > +		crc32(cff_flashinfo->datacrc,
> > > > +		(u_char *)bufferptr_after_header,
> > > > +		buffersize_after_header);
> > > > +#endif
> > > > +if (0 == cff_flashinfo->remaining) {
> > > > +#ifdef CONFIG_CHECK_FPGA_DATA_CRC
> > > > +	if (cff_flashinfo->datacrc !=
> > > > +		image_get_dcrc(&(cff_flashinfo->header))) {
> > > > +		printf("FPGA: Bad Data Checksum.\n");
> > > > +		return -EPERM;
> > > > +	}
> > > > +#endif
> > > > +}
> > > > +	return 0;
> > > > +}
> > > > +
> > > > +
> > > > +static int cff_flash_read(struct cff_flash_info
> > > > *cff_flashinfo,
> > > > u32 *buffer,
> > > > +	u32 *buffer_sizebytes)
> > > > +{
> > > > +	int ret = 0;
> > > > +	/* To avoid from keeping re-read the contents */
> > > > +	size_t buffer_size = *buffer_sizebytes;
> > > > +	u32 *buffer_ptr = (u32 *)*buffer;
> > > > +	u32 flash_addr = cff_flashinfo->flash_offset;
> > > > +
> > > > +	/* Buffer allocated in OCRAM */
> > > > +	/* Read the data by small chunk by chunk. */
> > > > +	if (cff_flashinfo->remaining > buffer_size)
> > > > +		cff_flashinfo->remaining -= buffer_size;
> > > > +	else {
> > > > +		/* Buffer allocated in DDR, larger than rbf
> > > > data
> > > > most
> > > > +		  of the time */
> > > > +		buffer_size = cff_flashinfo->remaining;
> > > > +		cff_flashinfo->remaining = 0;
> > > > +	}
> > > > +
> > > > +	ret = flash_read(cff_flashinfo, buffer_size,
> > > > buffer_ptr);
> > > > +
> > > > +	if (0 >= ret) {
> > > > +		printf(" Failed to read rbf data from
> > > > flash.\n");
> > > > +		return -ENOENT;
> > > > +	}
> > > > +
> > > > +#ifdef CONFIG_CHECK_FPGA_DATA_CRC
> > > > +	cff_flashinfo->datacrc =
> > > > +		crc32(cff_flashinfo->datacrc,
> > > > +			(unsigned char *)buffer_ptr,
> > > > buffer_size);
> > > > +#endif
> > > > +
> > > > +if (0 == cff_flashinfo->remaining) {
> > > > +#ifdef CONFIG_CHECK_FPGA_DATA_CRC
> > > > +	if (cff_flashinfo->datacrc !=
> > > > +		image_get_dcrc(&(cff_flashinfo->header))) {
> > > > +		printf("FPGA: Bad Data Checksum.\n");
> > > > +		return -EPERM;
> > > > +	}
> > > > +#endif
> > > > +}
> > > > +	/* Update next reading rbf data flash offset */
> > > > +	flash_addr += buffer_size;
> > > > +
> > > > +	cff_flashinfo->flash_offset = flash_addr;
> > > > +
> > > > +	/* Update the size of rbf data to be programmed into
> > > > FPGA
> > > > */
> > > > +	*buffer_sizebytes = buffer_size;
> > > > +
> > > > +	return 0;
> > > > +}
> > > > +
> > > > +int cff_from_flash(fpga_fs_info *fpga_fsinfo)
> > > > +{
> > > > +	u32 buffer = 0;
> > > > +	u32 buffer_ori = 0;
> > > > +	u32 buffer_sizebytes = 0;
> > > > +	u32 buffer_sizebytes_ori = 0;
> > > > +	struct cff_flash_info cff_flashinfo;
> > > > +	u32 status;
> > > > +	int ret = 0;
> > > > +
> > > > +	memset(&cff_flashinfo, 0, sizeof(cff_flashinfo));
> > > > +
> > > > +	if (fpga_fsinfo->filename == NULL) {
> > > > +		printf("no [periph/core] rbf [filename/offset]
> > > > specified.\n");
> > > > +		return -EINVAL;
> > > > +	}
> > > > +
> > > > +	WATCHDOG_RESET();
> > > > +
> > > > +#ifdef CONFIG_CMD_FPGA_LOADFS
> > > > +	cff_flashinfo.sdmmc_flashinfo.dev_part =
> > > > +		simple_strtol(fpga_fsinfo->dev_part, NULL,
> > > > 10);
> > > > +#endif
> > > > +
> > > > +	ret = cff_flash_probe(&cff_flashinfo);
> > > > +
> > > > +	if (0 >= ret) {
> > > > +		puts("Flash probe failed.\n");
> > > > +		return ret;
> > > > +	}
> > > > +
> > > > +#ifdef CONFIG_CMD_FPGA_LOADFS
> > > > +	/* Loading rbf data with DDR, faster than OCRAM,
> > > > +	   only for core rbf */
> > > > +	if (gd->ram_size != 0) {
> > > > +		ret = fat_size(fpga_fsinfo->filename, (loff_t
> > > > *)&buffer_sizebytes);
> > > > +
> > > > +		if(ret){
> > > > +			puts("Failed to read file size.\n");
> > > > +			return ret;
> > > > +		}
> > > > +
> > > > +		buffer_ori = (u32)memalign(ARCH_DMA_MINALIGN,
> > > > buffer_sizebytes);
> > > > +
> > > > +		if (!buffer_ori) {
> > > > +			error("RBF calloc failed!\n");
> > > > +			return -ENOMEM;
> > > > +		}
> > > > +
> > > > +		/* Loading mkimage header and rbf data into
> > > > +		   DDR instead of OCRAM */
> > > > +		buffer = buffer_ori;
> > > > +
> > > > +		buffer_sizebytes_ori = buffer_sizebytes;
> > > > +	} else {
> > > > +		buffer = buffer_ori =
> > > > (u32)cff_flashinfo.buffer;
> > > > +
> > > > +		buffer_sizebytes =
> > > > +			buffer_sizebytes_ori =
> > > > +				sizeof(cff_flashinfo.buffer);
> > > > +	}
> > > > +#else
> > > > +	/* Adjust to adjacent block */
> > > > +	buffer_sizebytes = buffer_sizebytes_ori =
> > > > +				(sizeof(cff_flashinfo.buffer)/
> > > > mmc->read_bl_len) *
> > > > +					mmc->read_bl_len;
> > > > +#endif
> > > > +
> > > > +	/* Note: Both buffer and buffer_sizebytes values can
> > > > be
> > > > altered by
> > > > +	   function below. */
> > > > +	ret = cff_flash_preinit(&cff_flashinfo, fpga_fsinfo,
> > > > &buffer,
> > > > +		&buffer_sizebytes);
> > > > +
> > > > +	if (ret)
> > > > +		return ret;
> > > > +
> > > > +	if (periph_section == cff_flashinfo.rbfinfo.section) {
> > > > +		/* initialize the FPGA Manager */
> > > > +		status = fpgamgr_program_init((u32 *)buffer,
> > > > buffer_sizebytes);
> > > > +		if (status) {
> > > > +			printf("FPGA: Init with periph rbf
> > > > failed
> > > > with error. ");
> > > > +			printf("code %d\n", status);
> > > > +			return -EPERM;
> > > > +		}
> > > > +	}
> > > > +
> > > > +	WATCHDOG_RESET();
> > > > +
> > > > +	/* transfer data to FPGA Manager */
> > > > +	fpgamgr_program_write((void *)buffer,
> > > > +		buffer_sizebytes);
> > > > +
> > > > +	WATCHDOG_RESET();
> > > > +
> > > > +	while (cff_flashinfo.remaining) {
> > > > +		ret = cff_flash_read(&cff_flashinfo,
> > > > &buffer_ori,
> > > > +			&buffer_sizebytes_ori);
> > > > +
> > > > +		if (ret)
> > > > +			return ret;
> > > > +
> > > > +		/* transfer data to FPGA Manager */
> > > > +		fpgamgr_program_write((void *)buffer_ori,
> > > > +			buffer_sizebytes_ori);
> > > > +
> > > > +		WATCHDOG_RESET();
> > > > +	}
> > > > +
> > > > +	if ((periph_section == cff_flashinfo.rbfinfo.section)
> > > > &&
> > > > +	 is_early_release_fpga_config(gd->fdt_blob)) {
> > > > +		if (-ETIMEDOUT !=
> > > > fpgamgr_wait_early_user_mode())
> > > > +			printf("FPGA: Early Release
> > > > Succeeded.\n");
> > > > +		else {
> > > > +			printf("FPGA: Failed to see Early
> > > > Release.\n");
> > > > +			return -EIO;
> > > > +		}
> > > > +	} else if ((core_section ==
> > > > cff_flashinfo.rbfinfo.section)
> > > > > 
> > > > > > 
> > > > > > 
> > > > +	 ((periph_section == cff_flashinfo.rbfinfo.section) &&
> > > > +	 !is_early_release_fpga_config(gd->fdt_blob))) {
> > > > +		/* Ensure the FPGA entering config done */
> > > > +		status = fpgamgr_program_finish();
> > > > +		if (status)
> > > > +			return status;
> > > > +		else
> > > > +			printf("FPGA: Enter user mode.\n");
> > > > +
> > > > +	} else {
> > > > +		printf("Config Error: Unsupported FGPA raw
> > > > binary
> > > > type.\n");
> > > > +		return -ENOEXEC;
> > > > +	}
> > > > +
> > > > +	WATCHDOG_RESET();
> > > > +	return 1;
> > > > +}
> > > > diff --git a/arch/arm/mach-socfpga/include/mach/cff.h
> > > > b/arch/arm/mach-socfpga/include/mach/cff.h
> > > > new file mode 100644
> > > > index 0000000..7f3f66b
> > > > --- /dev/null
> > > > +++ b/arch/arm/mach-socfpga/include/mach/cff.h
> > > > @@ -0,0 +1,40 @@
> > > > +/*
> > > > + * Copyright (C) 2017 Intel Corporation <www.intel.com>
> > > > + *
> > > > + * SPDX-License-Identifier:	GPL-2.0
> > > > + */
> > > > +
> > > > +#ifndef	_SOCFPGA_CFF_H_
> > > > +#define	_SOCFPGA_CFF_H_
> > > > +
> > > > +#include <fpga.h>
> > > > +
> > > > +#ifndef __ASSEMBLY_
> > > > +
> > > > +struct flash_info {
> > > > +	char *filename;
> > > > +	int dev_part;
> > > > +};
> > > > +
> > > > +enum rbf_type {unknown, periph_section, core_section};
> > > > +enum rbf_security {invalid, unencrypted, encrypted};
> > > > +
> > > > +struct rbf_info {
> > > > +	enum rbf_type section ;
> > > > +	enum rbf_security security;
> > > > +};
> > > > +
> > > > +struct cff_flash_info {
> > > > +	struct flash_info sdmmc_flashinfo;
> > > > +	u32 buffer[4096] __aligned(ARCH_DMA_MINALIGN);
> > > > +	u32 remaining;
> > > > +	u32 flash_offset;
> > > > +	struct rbf_info rbfinfo;
> > > > +	struct image_header header;
> > > > +};
> > > > +
> > > > +int cff_from_sdmmc_env(unsigned int core);
> > > > +int cff_from_flash(fpga_fs_info *fpga_fsinfo);
> > > > +#endif /* __ASSEMBLY__ */
> > > > +
> > > > +#endif /* _SOCFPGA_CFF_H_ */
> > > > diff --git a/include/configs/socfpga_arria10_socdk.h
> > > > b/include/configs/socfpga_arria10_socdk.h
> > > > index 3b59b6a..aa4c54a 100644
> > > > --- a/include/configs/socfpga_arria10_socdk.h
> > > > +++ b/include/configs/socfpga_arria10_socdk.h
> > > > @@ -58,6 +58,12 @@
> > > >   * Flash configurations
> > > >   */
> > > >  #define CONFIG_SYS_MAX_FLASH_BANKS     1
> > > > +/* Default SDMMC physical address for periph.rbf (sector
> > > > alignment) */
> > > > +#define CONFIG_FS_FAT_MAX_CLUSTSIZE (32 * 1024)
> > > > +
> > > > +#if !defined(CONFIG_SPL_BUILD) &&
> > > > !defined(CONFIG_CMD_FPGA_LOADFS)
> > > > +#define CONFIG_CMD_FPGA_LOADFS
> > > > +#endif
> > > >  
> > > >  /* The rest of the configuration is shared */
> > > >  #include <configs/socfpga_common.h>
> > > > 
> 


More information about the U-Boot mailing list