arch/arm/src/tiva: Implemented Flash CONFIG_MTD_BYTE_WRITE for TM4c1294. Implemented the tiva_write function which will write an arbitrary number of bytes to flash (in multiple of 4).
This commit is contained in:
parent
0835143537
commit
ba0bbb93b0
@ -2,7 +2,7 @@
|
||||
* arch/arm/src/tiva/tiva_flash.c
|
||||
*
|
||||
* Copyright (c) 2013 Max Holtzberg. All rights reserved.
|
||||
* Copyright (C) 2013 Gregory Nutt. All rights reserved.
|
||||
* Copyright (C) 2013, 2018 Gregory Nutt. All rights reserved.
|
||||
*
|
||||
* Authors: Max Holtzberg <mh@uvc.de>
|
||||
* Gregory Nutt <gnutt@nuttx.org>
|
||||
@ -64,8 +64,8 @@
|
||||
****************************************************************************/
|
||||
|
||||
#define TIVA_VIRTUAL_NPAGES (TIVA_FLASH_NPAGES - CONFIG_TIVA_FLASH_STARTPAGE)
|
||||
#define TIVA_VIRTUAL_BASE (TIVA_FLASH_BASE \
|
||||
+ CONFIG_TIVA_FLASH_STARTPAGE * TIVA_FLASH_PAGESIZE)
|
||||
#define TIVA_VIRTUAL_OFFSET (CONFIG_TIVA_FLASH_STARTPAGE * TIVA_FLASH_PAGESIZE)
|
||||
#define TIVA_VIRTUAL_BASE (TIVA_FLASH_BASE + TIVA_VIRTUAL_OFFSET)
|
||||
|
||||
/****************************************************************************
|
||||
* Private Types
|
||||
@ -120,6 +120,7 @@ static struct tiva_dev_s g_lmdev =
|
||||
#endif
|
||||
tiva_ioctl
|
||||
},
|
||||
|
||||
/* Initialization of any other implementation specific data goes here */
|
||||
};
|
||||
|
||||
@ -138,12 +139,15 @@ static struct tiva_dev_s g_lmdev =
|
||||
static int tiva_erase(FAR struct mtd_dev_s *dev, off_t startblock,
|
||||
size_t nblocks)
|
||||
{
|
||||
int curpage;
|
||||
off_t endblock;
|
||||
uint32_t pageaddr;
|
||||
uint32_t regval;
|
||||
int curpage;
|
||||
|
||||
DEBUGASSERT(nblocks <= TIVA_VIRTUAL_NPAGES);
|
||||
endblock = startblock + nblocks;
|
||||
DEBUGASSERT(endblock <= TIVA_VIRTUAL_NPAGES);
|
||||
|
||||
for (curpage = startblock; curpage < nblocks; curpage++)
|
||||
for (curpage = startblock; curpage < endblock; curpage++)
|
||||
{
|
||||
pageaddr = TIVA_VIRTUAL_BASE + curpage * TIVA_FLASH_PAGESIZE;
|
||||
|
||||
@ -160,7 +164,19 @@ static int tiva_erase(FAR struct mtd_dev_s *dev, off_t startblock,
|
||||
|
||||
/* wait until erase has finished */
|
||||
|
||||
while (getreg32(TIVA_FLASH_FMC) & FLASH_FMC_ERASE);
|
||||
while (getreg32(TIVA_FLASH_FMC) & FLASH_FMC_ERASE)
|
||||
{
|
||||
}
|
||||
|
||||
/* Return an error if an access violation or erase error occurred. */
|
||||
|
||||
regval = getreg32(TIVA_FLASH_FCRIS);
|
||||
regval &= (FLASH_FCRIS_ARIS | FLASH_FCRIS_VOLTRIS | FLASH_FCRIS_ERRIS);
|
||||
|
||||
if (regval != 0)
|
||||
{
|
||||
return -EACCES;
|
||||
}
|
||||
}
|
||||
|
||||
return OK;
|
||||
@ -255,7 +271,90 @@ static ssize_t tiva_read(FAR struct mtd_dev_s *dev, off_t offset, size_t nbytes,
|
||||
static ssize_t tiva_write(FAR struct mtd_dev_s *dev, off_t offset, size_t nbytes,
|
||||
FAR const uint8_t *buf)
|
||||
{
|
||||
return -ENOSYS;
|
||||
FAR const uint32_t *src = (uint32_t *)((uintptr_t)buf & ~3);
|
||||
ssize_t remaining;
|
||||
uint32_t regval;
|
||||
|
||||
DEBUGASSERT(dev != NULL && buf != NULL);
|
||||
DEBUGASSERT(((uintptr_t)buf & 3) == 0 && (offset & 3) == 0 && (nbytes && 3) == 0);
|
||||
|
||||
/* Clear the flash access and error interrupts. */
|
||||
|
||||
putreg32(FLASH_FCMISC_AMISC | FLASH_FCMISC_VOLTMISC | FLASH_FCMISC_ERMISC,
|
||||
TIVA_FLASH_FCMISC);
|
||||
|
||||
/* Adjust the offset to the start of the partition.
|
||||
* REVISIT: If we really wanted to gracefully handler unaligned addresses,
|
||||
* offsets, and sizes we would have to do a little more than this.
|
||||
*/
|
||||
|
||||
offset &= ~3;
|
||||
offset += TIVA_VIRTUAL_OFFSET;
|
||||
nbytes &= ~3;
|
||||
remaining = nbytes;
|
||||
|
||||
#if defined(CONFIG_ARCH_CHIP_TM4C1294NC)
|
||||
while (remaining > 0)
|
||||
{
|
||||
/* Set the address of this block of words. */
|
||||
|
||||
putreg32((offset & ~(0x7f)), TIVA_FLASH_FMA);
|
||||
|
||||
/* Loop over the words in this 32-word block. */
|
||||
|
||||
while(((offset & 0x7c) || (getreg32(TIVA_FLASH_FWBN) == 0)) &&
|
||||
(remaining > 0))
|
||||
{
|
||||
/* Write this word into the write buffer. */
|
||||
|
||||
putreg32(*src++, (TIVA_FLASH_FWBN + (offset & 0x7c)));
|
||||
offset += 4;
|
||||
remaining -= 4;
|
||||
}
|
||||
|
||||
/* Program the contents of the write buffer into flash. */
|
||||
|
||||
putreg32(FLASH_FMC_WRKEY | FLASH_FMC2_WRBUF, TIVA_FLASH_FMC2);
|
||||
|
||||
/* Wait until the write buffer has been programmed. */
|
||||
|
||||
while(getreg32(TIVA_FLASH_FMC2) & FLASH_FMC2_WRBUF)
|
||||
{
|
||||
}
|
||||
}
|
||||
#else
|
||||
while (remaining > 0)
|
||||
{
|
||||
/* Program the next word. */
|
||||
|
||||
putreg32(offset, TIVA_FLASH_FMA);
|
||||
putreg32(*src, TIVA_FLASH_FMD);
|
||||
putreg32(FLASH_FMC_WRKEY | FLASH_FMC_WRITE, TIVA_FLASH_FMC);
|
||||
|
||||
/* Wait until the word has been programmed. */
|
||||
|
||||
while(getreg32(TIVA_FLASH_FMC) & FLASH_FMC_WRITE);
|
||||
|
||||
/* Increment to the next word. */
|
||||
|
||||
src++;
|
||||
offset += 4;
|
||||
remaining -= 4;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* Return an error if an access violation or erase error occurred. */
|
||||
|
||||
regval = getreg32(TIVA_FLASH_FCRIS);
|
||||
regval &= (FLASH_FCRIS_ARIS | FLASH_FCRIS_VOLTRIS | FLASH_FCRIS_INVDRIS |
|
||||
FLASH_FCRIS_PROGRIS);
|
||||
|
||||
if (regval != 0)
|
||||
{
|
||||
return -EACCES;
|
||||
}
|
||||
|
||||
return nbytes;
|
||||
}
|
||||
#endif
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user