OpenCores
URL https://opencores.org/ocsvn/xenie/xenie/trunk

Subversion Repositories xenie

[/] [xenie/] [trunk/] [examples/] [Eth_example/] [mb_fw/] [xenie_eth_test_womtd/] [src/] [spansion_flash.c] - Rev 4

Go to most recent revision | Compare with Previous | Blame | View Log

/******************************************************************************
**
** (C) Copyright 2017 DFC Design, s.r.o., Brno, Czech Republic
** Author: Marek Kvas (m.kvas@dspfpga.com)
**
****************************************************************************
**
** This file is part of Xenia Ethernet Example project.
** 
** Xenia Ethernet Example project is free software: you can 
** redistribute it and/or modify it under the terms of 
** the GNU Lesser General Public License as published by the Free 
** Software Foundation, either version 3 of the License, or
** (at your option) any later version.
** 
** Xenia Ethernet Example project is distributed in the hope that 
** it will be useful, but WITHOUT ANY WARRANTY; without even 
** the implied warranty of MERCHANTABILITY or FITNESS FOR A 
** PARTICULAR PURPOSE.  See the GNU Lesser General Public License 
** for more details.
** 
** You should have received a copy of the GNU Lesser General Public 
** License along with Xenia Ethernet Example project.  If not, 
** see <http://www.gnu.org/licenses/>.
****************************************************************************
*/
 
#include <stdio.h>
#include <xspi.h>
#include "spansion_flash.h"
#include "uprintf.h"
 
 
int spansion_flash_init (struct spansion_flash *sf, XSpi *spi, int slave_num)
{
	sf->spi = spi;
	sf->slave_select = (1<<slave_num);
	int res;
 
	res = XSpi_SetOptions(sf->spi, (XSP_MASTER_OPTION | \
						XSP_MANUAL_SSELECT_OPTION | \
						XSP_CLK_PHASE_1_OPTION | \
						XSP_CLK_ACTIVE_LOW_OPTION));
	if(res)
		return res;
 
	res = XSpi_SetSlaveSelect(sf->spi, sf->slave_select);
	if(res)
		return res;
 
	res = XSpi_Start(sf->spi);
	return res;
}
 
static int spansion_flash_transfer(struct spansion_flash *sf, uint8_t *wr_buf, uint8_t *rd_buf, int len)
{
	int res;
 
	res = XSpi_Transfer(sf->spi, wr_buf, rd_buf, len);
	if(res)
		return res;
 
	return XST_SUCCESS;
}
 
 
/* Get status and control register and set QSPI*/
int spansion_flash_quad_mode(struct spansion_flash *sf)
{
#define SPANSION_CFG_REG_QUAD		(1<<1)
	int ret;
	u8 rCfgBuf[2];
	u8 rStBuf[2];
	u8 wCfgBuf[3];
	u8 wEnBuf[1];
 
	rCfgBuf[0] = 0x35;
	ret = spansion_flash_transfer(sf, rCfgBuf, rCfgBuf, 2);
	if(ret)
		return ret;
 
	rStBuf[0] = 0x05;
	ret = spansion_flash_transfer(sf, rStBuf, rStBuf, 2);
	if(ret)
		return ret;
 
	wEnBuf[0] = 0x6;
	ret = spansion_flash_transfer(sf, wEnBuf, wEnBuf, 1);
	if(ret)
		return ret;
 
 
	wCfgBuf[0] = 0x01;
	wCfgBuf[1] = rStBuf[1];
	wCfgBuf[2] = rCfgBuf[1] | SPANSION_CFG_REG_QUAD;
 
	ret = spansion_flash_transfer(sf, wCfgBuf, wCfgBuf, 3);
	if(ret)
		return ret;
 
	/* Reread CFG reg */
	rCfgBuf[0] = 0x35;
	ret = spansion_flash_transfer(sf, rCfgBuf, rCfgBuf, 2);
	if(ret)
		return ret;
 
	return 0;
}
 
/* Set extended addressing mode in Flash and in Xilisf */
/* !!! Doesn't work well for quad command 6b */
int spansion_flash_extended_addressing(struct spansion_flash *sf, int onOff)
{
#define SPANSION_BANK_REG_EXT_ADDR		(1<<7)
	int ret;
	u8 buf[2];
	XSpi *spi = sf->spi;
 
	/* Read bank register*/
	buf[0] = 0x16;
	ret = XSpi_Transfer(spi, buf, buf, 2);
	if(ret)
		return ret;
 
	/* Write bank register with extended addressing setting */
	buf[0] = 0x17;
	if (onOff) {
		buf[1] |=  SPANSION_BANK_REG_EXT_ADDR;
	} else {
		buf[1] &=  ~SPANSION_BANK_REG_EXT_ADDR;
	}
	ret = XSpi_Transfer(spi, buf, buf, 2);
	if(ret)
		return ret;
 
	/* Read bank register*/
	buf[0] = 0x16;
	ret = XSpi_Transfer(spi, buf, buf, 2);
	if(ret)
		return ret;
	uprintf("Modified bank register 0x%02x\r\n", buf[1]);
 
	return 0;
}
 
/*
 *  Use Quad IO 4 byte address read command to read block of data.
 *  spi - SPI core instance to be used
 *  flash_addr - 32 bit start address in flash
 *  buf - pointer to buffer where data shall be stored; must be 8 byte longer then length of data
 *  	  rad data are placed at buf+8 address.
 *  len - number of bytes to be read from flash; must be 8 bytes lower than true buf len
 */
int spansion_flash_quad_io_read(struct spansion_flash *sf, uint32_t flash_addr, uint8_t *buf, int len)
{
	XSpi *spi = sf->spi;
	u8 *cmdbuf = buf;
 
	/* Quad IO read with 32 bit address */
	*(cmdbuf++) = 0xec;
	/* Address MSB first */
	*(cmdbuf++) = flash_addr >> 24;
	*(cmdbuf++) = flash_addr >> 16;
	*(cmdbuf++) = flash_addr >> 8;
	*(cmdbuf++) = flash_addr;
	/* 3 Dummy bytes - 6 cycle for latency code 00b */
	*(cmdbuf++) = 0;
	*(cmdbuf++) = 0;
	*(cmdbuf++) = 0;
 
	return XSpi_Transfer(spi, buf, buf, len + 8);
}
 

Go to most recent revision | Compare with Previous | Blame | View Log

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.