Turn on nvm in 3.0.

Its 256b on M0 and 8k on M4 to match flash erase sizes.

Fixes #758
This commit is contained in:
Scott Shawcroft 2018-04-12 18:13:40 -07:00
parent 10eabf6bc2
commit 812fe0c93f
24 changed files with 55 additions and 125 deletions

View File

@ -285,6 +285,8 @@ SRC_COMMON_HAL = \
analogio/__init__.c \ analogio/__init__.c \
analogio/AnalogIn.c \ analogio/AnalogIn.c \
analogio/AnalogOut.c \ analogio/AnalogOut.c \
nvm/__init__.c \
nvm/ByteArray.c \
pulseio/__init__.c \ pulseio/__init__.c \
pulseio/PulseIn.c \ pulseio/PulseIn.c \
pulseio/PulseOut.c \ pulseio/PulseOut.c \
@ -293,9 +295,7 @@ SRC_COMMON_HAL = \
usb_hid/Device.c \ usb_hid/Device.c \
audioio/__init__.c \ audioio/__init__.c \
audioio/AudioOut.c \ audioio/AudioOut.c \
# nvm/__init__.c \ # audiobusio/PDMIn.c \
audiobusio/PDMIn.c \
nvm/ByteArray.c \
touchio/__init__.c \ touchio/__init__.c \
touchio/TouchIn.c \ touchio/TouchIn.c \

View File

@ -42,8 +42,7 @@
// If you change this, then make sure to update the linker scripts as well to // If you change this, then make sure to update the linker scripts as well to
// make sure you don't overwrite code. // make sure you don't overwrite code.
// #define CIRCUITPY_INTERNAL_NVM_SIZE 256 #define CIRCUITPY_INTERNAL_NVM_SIZE 256
#define CIRCUITPY_INTERNAL_NVM_SIZE 0
#define BOARD_FLASH_SIZE (0x00040000 - 0x2000 - CIRCUITPY_INTERNAL_NVM_SIZE) #define BOARD_FLASH_SIZE (0x00040000 - 0x2000 - CIRCUITPY_INTERNAL_NVM_SIZE)

View File

@ -35,8 +35,7 @@
// If you change this, then make sure to update the linker scripts as well to // If you change this, then make sure to update the linker scripts as well to
// make sure you don't overwrite code. // make sure you don't overwrite code.
// #define CIRCUITPY_INTERNAL_NVM_SIZE 256 #define CIRCUITPY_INTERNAL_NVM_SIZE 256
#define CIRCUITPY_INTERNAL_NVM_SIZE 0
#define BOARD_FLASH_SIZE (0x00040000 - 0x2000 - CIRCUITPY_INTERNAL_NVM_SIZE) #define BOARD_FLASH_SIZE (0x00040000 - 0x2000 - CIRCUITPY_INTERNAL_NVM_SIZE)

View File

@ -37,8 +37,7 @@
// If you change this, then make sure to update the linker scripts as well to // If you change this, then make sure to update the linker scripts as well to
// make sure you don't overwrite code. // make sure you don't overwrite code.
// #define CIRCUITPY_INTERNAL_NVM_SIZE 256 #define CIRCUITPY_INTERNAL_NVM_SIZE 256
#define CIRCUITPY_INTERNAL_NVM_SIZE 0
#define BOARD_FLASH_SIZE (0x00040000 - 0x2000 - CIRCUITPY_INTERNAL_NVM_SIZE) #define BOARD_FLASH_SIZE (0x00040000 - 0x2000 - CIRCUITPY_INTERNAL_NVM_SIZE)

View File

@ -19,8 +19,7 @@
// If you change this, then make sure to update the linker scripts as well to // If you change this, then make sure to update the linker scripts as well to
// make sure you don't overwrite code // make sure you don't overwrite code
// #define CIRCUITPY_INTERNAL_NVM_SIZE 256 #define CIRCUITPY_INTERNAL_NVM_SIZE 8192
#define CIRCUITPY_INTERNAL_NVM_SIZE 0
#define BOARD_FLASH_SIZE (FLASH_SIZE - 0x4000 - CIRCUITPY_INTERNAL_NVM_SIZE) #define BOARD_FLASH_SIZE (FLASH_SIZE - 0x4000 - CIRCUITPY_INTERNAL_NVM_SIZE)

View File

@ -35,8 +35,8 @@
// If you change this, then make sure to update the linker scripts as well to // If you change this, then make sure to update the linker scripts as well to
// make sure you don't overwrite code. // make sure you don't overwrite code.
// #define CIRCUITPY_INTERNAL_NVM_SIZE 256 #define CIRCUITPY_INTERNAL_NVM_SIZE 256
#define CIRCUITPY_INTERNAL_NVM_SIZE 0
#define BOARD_FLASH_SIZE (0x00040000 - 0x2000 - CIRCUITPY_INTERNAL_NVM_SIZE) #define BOARD_FLASH_SIZE (0x00040000 - 0x2000 - CIRCUITPY_INTERNAL_NVM_SIZE)
#include "external_flash/devices.h" #include "external_flash/devices.h"

View File

@ -19,8 +19,7 @@
// If you change this, then make sure to update the linker scripts as well to // If you change this, then make sure to update the linker scripts as well to
// make sure you don't overwrite code // make sure you don't overwrite code
// #define CIRCUITPY_INTERNAL_NVM_SIZE 256 #define CIRCUITPY_INTERNAL_NVM_SIZE 8192
#define CIRCUITPY_INTERNAL_NVM_SIZE 0
#define BOARD_FLASH_SIZE (FLASH_SIZE - 0x4000 - CIRCUITPY_INTERNAL_NVM_SIZE) #define BOARD_FLASH_SIZE (FLASH_SIZE - 0x4000 - CIRCUITPY_INTERNAL_NVM_SIZE)

View File

@ -36,8 +36,7 @@
// If you change this, then make sure to update the linker scripts as well to // If you change this, then make sure to update the linker scripts as well to
// make sure you don't overwrite code. // make sure you don't overwrite code.
// #define CIRCUITPY_INTERNAL_NVM_SIZE 256 #define CIRCUITPY_INTERNAL_NVM_SIZE 256
#define CIRCUITPY_INTERNAL_NVM_SIZE 0
#define BOARD_FLASH_SIZE (0x00040000 - 0x2000 - CIRCUITPY_INTERNAL_NVM_SIZE) #define BOARD_FLASH_SIZE (0x00040000 - 0x2000 - CIRCUITPY_INTERNAL_NVM_SIZE)

View File

@ -22,8 +22,7 @@
// If you change this, then make sure to update the linker scripts as well to // If you change this, then make sure to update the linker scripts as well to
// make sure you don't overwrite code // make sure you don't overwrite code
// #define CIRCUITPY_INTERNAL_NVM_SIZE 256 #define CIRCUITPY_INTERNAL_NVM_SIZE 8192
#define CIRCUITPY_INTERNAL_NVM_SIZE 0
#define BOARD_FLASH_SIZE (FLASH_SIZE - 0x4000 - CIRCUITPY_INTERNAL_NVM_SIZE) #define BOARD_FLASH_SIZE (FLASH_SIZE - 0x4000 - CIRCUITPY_INTERNAL_NVM_SIZE)

View File

@ -49,8 +49,7 @@
// If you change this, then make sure to update the linker scripts as well to // If you change this, then make sure to update the linker scripts as well to
// make sure you don't overwrite code // make sure you don't overwrite code
// #define CIRCUITPY_INTERNAL_NVM_SIZE 256 #define CIRCUITPY_INTERNAL_NVM_SIZE 8192
#define CIRCUITPY_INTERNAL_NVM_SIZE 0
#define BOARD_FLASH_SIZE (FLASH_SIZE - 0x4000 - CIRCUITPY_INTERNAL_NVM_SIZE) #define BOARD_FLASH_SIZE (FLASH_SIZE - 0x4000 - CIRCUITPY_INTERNAL_NVM_SIZE)

View File

@ -5,8 +5,8 @@
/* Specify the memory areas */ /* Specify the memory areas */
MEMORY MEMORY
{ {
/* Leave 16KiB for the bootloader. */ /* Leave 16KiB for the bootloader. 8K for user data*/
FLASH (rx) : ORIGIN = 0x00000000 + 16K, LENGTH = 256K - 16K FLASH (rx) : ORIGIN = 0x00000000 + 16K, LENGTH = 256K - 16K - 8K
RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 128K RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 128K
} }
@ -76,7 +76,7 @@ SECTIONS
.stack : .stack :
{ {
. = ALIGN(4); . = ALIGN(4);
. = . + 2K; /* Reserve a minimum of 2K for the stack. */ . = . + 10K; /* Reserve a minimum of 10K for the stack. nvm will temporarily store 8k on the stack when writing. */
. = ALIGN(4); . = ALIGN(4);
} >RAM } >RAM

View File

@ -5,8 +5,8 @@
/* Specify the memory areas */ /* Specify the memory areas */
MEMORY MEMORY
{ {
/* Leave 16KiB for the bootloader. */ /* Leave 16KiB for the bootloader. 8K for user data*/
FLASH (rx) : ORIGIN = 0x00000000 + 16K, LENGTH = 512K - 16K FLASH (rx) : ORIGIN = 0x00000000 + 16K, LENGTH = 512K - 16K - 8K
RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 192K RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 192K
} }
@ -76,7 +76,7 @@ SECTIONS
.stack : .stack :
{ {
. = ALIGN(4); . = ALIGN(4);
. = . + 2K; /* Reserve a minimum of 2K for the stack. */ . = . + 10K; /* Reserve a minimum of 10K for the stack. nvm will temporarily store 8k on the stack when writing. */
. = ALIGN(4); . = ALIGN(4);
} >RAM } >RAM

View File

@ -5,8 +5,8 @@
/* Specify the memory areas */ /* Specify the memory areas */
MEMORY MEMORY
{ {
/* Leave 16KiB for the bootloader and 256KiB for the internal file system. */ /* Leave 16KiB for the bootloader, 256KiB for the internal file system, and 8KiB for user binary data. */
FLASH (rx) : ORIGIN = 0x00000000 + 16K, LENGTH = 512K - 16K - 256K FLASH (rx) : ORIGIN = 0x00000000 + 16K, LENGTH = 512K - 16K - 256K - 8K
RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 192K RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 192K
} }
@ -76,7 +76,7 @@ SECTIONS
.stack : .stack :
{ {
. = ALIGN(4); . = ALIGN(4);
. = . + 2K; /* Reserve a minimum of 2K for the stack. */ . = . + 10K; /* Reserve a minimum of 10K for the stack. nvm will temporarily store 8k on the stack when writing. */
. = ALIGN(4); . = ALIGN(4);
} >RAM } >RAM

View File

@ -6,7 +6,7 @@
MEMORY MEMORY
{ {
/* Leave 16KiB for the bootloader. */ /* Leave 16KiB for the bootloader. */
FLASH (rx) : ORIGIN = 0x00000000 + 16K, LENGTH = 1M - 16K FLASH (rx) : ORIGIN = 0x00000000 + 16K, LENGTH = 1M - 16K - 8K
RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 256K RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 256K
} }
@ -76,7 +76,7 @@ SECTIONS
.stack : .stack :
{ {
. = ALIGN(4); . = ALIGN(4);
. = . + 2K; /* Reserve a minimum of 2K for the stack. */ . = . + 10K; /* Reserve a minimum of 10K for the stack. nvm will temporarily store 8k on the stack when writing. */
. = ALIGN(4); . = ALIGN(4);
} >RAM } >RAM

View File

@ -5,8 +5,8 @@
/* Specify the memory areas */ /* Specify the memory areas */
MEMORY MEMORY
{ {
/* Leave 16KiB for the bootloader and 512k for the filesystem. */ /* Leave 16KiB for the bootloader, 512k for the filesystem and 8k for user config data. */
FLASH (rx) : ORIGIN = 0x00000000 + 16K, LENGTH = 1M - 16K - 512K FLASH (rx) : ORIGIN = 0x00000000 + 16K, LENGTH = 1M - 16K - 512K - 8K
RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 256K RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 256K
} }
@ -76,7 +76,7 @@ SECTIONS
.stack : .stack :
{ {
. = ALIGN(4); . = ALIGN(4);
. = . + 2K; /* Reserve a minimum of 2K for the stack. */ . = . + 10K; /* Reserve a minimum of 10K for the stack. nvm will temporarily store 8k on the stack when writing. */
. = ALIGN(4); . = ALIGN(4);
} >RAM } >RAM

View File

@ -5,7 +5,7 @@
/* Specify the memory areas */ /* Specify the memory areas */
MEMORY MEMORY
{ {
FLASH (rx) : ORIGIN = 0x00000000, LENGTH = 1M FLASH (rx) : ORIGIN = 0x00000000, LENGTH = 1M - 8K
RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 256K RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 256K
} }
@ -74,7 +74,7 @@ SECTIONS
.stack : .stack :
{ {
. = ALIGN(4); . = ALIGN(4);
. = . + 2K; /* Reserve a minimum of 2K for the stack. */ . = . + 10K; /* Reserve a minimum of 10K for the stack. nvm will temporarily store 8k on the stack when writing. */
. = ALIGN(4); . = ALIGN(4);
} >RAM } >RAM

View File

@ -5,8 +5,8 @@
/* Specify the memory areas */ /* Specify the memory areas */
MEMORY MEMORY
{ {
/* 1024 KiB minus 512KiB for the internal file system. */ /* 1024 KiB minus 512KiB for the internal file system and 8KiB for the user nvm. */
FLASH (rx) : ORIGIN = 0x00000000, LENGTH = 1M - 512K FLASH (rx) : ORIGIN = 0x00000000, LENGTH = 1M - 512K - 8K
RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 256K RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 256K
} }
@ -75,7 +75,7 @@ SECTIONS
.stack : .stack :
{ {
. = ALIGN(4); . = ALIGN(4);
. = . + 2K; /* Reserve a minimum of 2K for the stack. */ . = . + 10K; /* Reserve a minimum of 10K for the stack. nvm will temporarily store 8k on the stack when writing. */
. = ALIGN(4); . = ALIGN(4);
} >RAM } >RAM

View File

@ -44,8 +44,8 @@
// If you change this, then make sure to update the linker scripts as well to // If you change this, then make sure to update the linker scripts as well to
// make sure you don't overwrite code. // make sure you don't overwrite code.
//#define CIRCUITPY_INTERNAL_NVM_SIZE 256 #define CIRCUITPY_INTERNAL_NVM_SIZE 256
#define CIRCUITPY_INTERNAL_NVM_SIZE 0
#define BOARD_FLASH_SIZE (0x00040000 - 0x2000 - CIRCUITPY_INTERNAL_NVM_SIZE) #define BOARD_FLASH_SIZE (0x00040000 - 0x2000 - CIRCUITPY_INTERNAL_NVM_SIZE)
#include "external_flash/devices.h" #include "external_flash/devices.h"

View File

@ -37,8 +37,8 @@
// If you change this, then make sure to update the linker scripts as well to // If you change this, then make sure to update the linker scripts as well to
// make sure you don't overwrite code. // make sure you don't overwrite code.
//#define CIRCUITPY_INTERNAL_NVM_SIZE 256 #define CIRCUITPY_INTERNAL_NVM_SIZE 256
#define CIRCUITPY_INTERNAL_NVM_SIZE 0
#define BOARD_FLASH_SIZE (0x00040000 - 0x2000 - CIRCUITPY_INTERNAL_NVM_SIZE) #define BOARD_FLASH_SIZE (0x00040000 - 0x2000 - CIRCUITPY_INTERNAL_NVM_SIZE)
#include "external_flash/devices.h" #include "external_flash/devices.h"

View File

@ -74,10 +74,12 @@ bool gclk_enabled(uint8_t gclk) {
void disable_gclk(uint8_t gclk) { void disable_gclk(uint8_t gclk) {
#ifdef SAMD51 #ifdef SAMD51
while ((GCLK->SYNCBUSY.vec.GENCTRL & (1 << gclk)) != 0) {}
GCLK->GENCTRL[gclk].bit.GENEN = false; GCLK->GENCTRL[gclk].bit.GENEN = false;
while ((GCLK->SYNCBUSY.vec.GENCTRL & (1 << gclk)) != 0) {} while ((GCLK->SYNCBUSY.vec.GENCTRL & (1 << gclk)) != 0) {}
#endif #endif
#ifdef SAMD21 #ifdef SAMD21
while (GCLK->STATUS.bit.SYNCBUSY == 1) {}
GCLK->GENCTRL.reg = GCLK_GENCTRL_ID(gclk); GCLK->GENCTRL.reg = GCLK_GENCTRL_ID(gclk);
while (GCLK->STATUS.bit.SYNCBUSY == 1) {} while (GCLK->STATUS.bit.SYNCBUSY == 1) {}
#endif #endif

View File

@ -85,13 +85,13 @@ const mcu_processor_obj_t common_hal_mcu_processor_obj = {
// NVM is only available on Express boards for now. // NVM is only available on Express boards for now.
#if CIRCUITPY_INTERNAL_NVM_SIZE > 0 #if CIRCUITPY_INTERNAL_NVM_SIZE > 0
// The singleton nvm.ByteArray object. // The singleton nvm.ByteArray object.
// const nvm_bytearray_obj_t common_hal_mcu_nvm_obj = { const nvm_bytearray_obj_t common_hal_mcu_nvm_obj = {
// .base = { .base = {
// .type = &nvm_bytearray_type, .type = &nvm_bytearray_type,
// }, },
// .len = NVMCTRL_ROW_SIZE, .len = CIRCUITPY_INTERNAL_NVM_SIZE,
// .start_address = (uint8_t*) (FLASH_SIZE - NVMCTRL_ROW_SIZE) .start_address = (uint8_t*) (FLASH_SIZE - CIRCUITPY_INTERNAL_NVM_SIZE)
// }; };
#endif #endif
// This maps MCU pin names to pin objects. // This maps MCU pin names to pin objects.

View File

@ -26,7 +26,7 @@
#include "common-hal/nvm/ByteArray.h" #include "common-hal/nvm/ByteArray.h"
#include "asf/sam0/drivers/nvm/nvm.h" #include "hal_flash.h"
#include <stdint.h> #include <stdint.h>
#include <string.h> #include <string.h>
@ -37,47 +37,11 @@ uint32_t common_hal_nvm_bytearray_get_length(nvm_bytearray_obj_t *self) {
bool common_hal_nvm_bytearray_set_bytes(nvm_bytearray_obj_t *self, bool common_hal_nvm_bytearray_set_bytes(nvm_bytearray_obj_t *self,
uint32_t start_index, uint8_t* values, uint32_t len) { uint32_t start_index, uint8_t* values, uint32_t len) {
uint32_t total_written = 0; // We don't use features that use any advanced NVMCTRL features so we can fake the descriptor
for (uint32_t i = 0; i < self->len / NVMCTRL_ROW_SIZE; i++) { // whenever we need it instead of storing it long term.
uint32_t row_start = NVMCTRL_ROW_SIZE * i; struct flash_descriptor desc;
if (row_start + NVMCTRL_ROW_SIZE < start_index || start_index + len < row_start) { desc.dev.hw = NVMCTRL;
continue; flash_write(&desc, (uint32_t) self->start_address + start_index, values, len);
}
uint8_t temp_row[NVMCTRL_ROW_SIZE];
memcpy(temp_row,
self->start_address + row_start,
NVMCTRL_ROW_SIZE);
enum status_code error_code;
do {
error_code = nvm_erase_row((uint32_t) self->start_address + row_start);
} while (error_code == STATUS_BUSY);
if (error_code != STATUS_OK) {
return false;
}
uint32_t data_start = 0;
if (start_index > row_start) {
data_start = start_index - row_start;
}
uint32_t data_len = len;
uint32_t data_remaining = data_len - total_written;
uint32_t row_remaining = NVMCTRL_ROW_SIZE - data_start;
if (data_remaining > row_remaining) {
data_len = row_remaining;
}
memcpy(temp_row + data_start,
values + total_written,
data_len);
for (int page = 0; page < NVMCTRL_ROW_SIZE / NVMCTRL_PAGE_SIZE; page++) {
do {
error_code = nvm_write_buffer((uint32_t) self->start_address + row_start + page * NVMCTRL_PAGE_SIZE,
temp_row + page * NVMCTRL_PAGE_SIZE,
NVMCTRL_PAGE_SIZE);
} while (error_code == STATUS_BUSY);
if (error_code != STATUS_OK) {
return false;
}
}
}
return true; return true;
} }

View File

@ -147,35 +147,6 @@ safe_mode_t port_init(void) {
return USER_SAFE_MODE; return USER_SAFE_MODE;
} }
// #if CIRCUITPY_INTERNAL_NVM_SIZE > 0
// // Upgrade the nvm flash to include one sector for eeprom emulation.
// struct nvm_fusebits fuses;
// if (nvm_get_fuses(&fuses) == STATUS_OK &&
// fuses.eeprom_size == NVM_EEPROM_EMULATOR_SIZE_0) {
// #ifdef INTERNAL_FLASH_FS
// // Shift the internal file system up one row.
// for (uint8_t row = 0; row < TOTAL_INTERNAL_FLASH_SIZE / NVMCTRL_ROW_SIZE; row++) {
// uint32_t new_row_address = INTERNAL_FLASH_MEM_SEG1_START_ADDR + row * NVMCTRL_ROW_SIZE;
// nvm_erase_row(new_row_address);
// nvm_write_buffer(new_row_address,
// (uint8_t*) (new_row_address + CIRCUITPY_INTERNAL_EEPROM_SIZE),
// NVMCTRL_ROW_SIZE);
// }
// #endif
// uint32_t nvm_size = CIRCUITPY_INTERNAL_NVM_SIZE;
// uint8_t enum_value = 6;
// while (nvm_size > 256 && enum_value != 255) {
// nvm_size /= 2;
// enum_value -= 1;
// }
// if (enum_value != 255 && nvm_size == 256) {
// // Mark the last section as eeprom now.
// fuses.eeprom_size = (enum nvm_eeprom_emulator_size) enum_value;
// nvm_set_fuses(&fuses);
// }
// }
// #endif
return NO_SAFE_MODE; return NO_SAFE_MODE;
} }

View File

@ -36,12 +36,13 @@
//| ================================================================================ //| ================================================================================
//| //|
//| Non-volatile memory is available as a byte array that persists over reloads //| Non-volatile memory is available as a byte array that persists over reloads
//| and power cycles. //| and power cycles. Each assignment causes an erase and write cycle so its recommended to assign
//| all values to change at once.
//| //|
//| Usage:: //| Usage::
//| //|
//| import microcontroller //| import microcontroller
//| microcontroller.nvm[0] = 0xcc //| microcontroller.nvm[0:] = b"\xcc\x10\x00"
//| //|
//| .. class:: ByteArray() //| .. class:: ByteArray()