summaryrefslogtreecommitdiff
path: root/ports/nrf
diff options
context:
space:
mode:
Diffstat (limited to 'ports/nrf')
-rwxr-xr-xports/nrf/Makefile5
-rw-r--r--ports/nrf/bluetooth/s140_nrf52_6.1.0/s140_nrf52_6.1.0_API/doc/ble_api.dox23
-rw-r--r--ports/nrf/bluetooth/s140_nrf52_6.1.0/s140_nrf52_6.1.0_API/include/ble.h2
-rw-r--r--ports/nrf/bluetooth/s140_nrf52_6.1.0/s140_nrf52_6.1.0_API/include/ble_gap.h2
-rw-r--r--ports/nrf/bluetooth/s140_nrf52_7.0.1/s140_nrf52_7.0.1_API/doc/ble_api.dox39
-rw-r--r--ports/nrf/bluetooth/s140_nrf52_7.0.1/s140_nrf52_7.0.1_API/include/ble.h12
-rw-r--r--ports/nrf/boards/common.template.ld22
-rw-r--r--ports/nrf/boards/electronut_labs_papyr/README.md2
-rw-r--r--ports/nrf/boards/hiibot_bluefi/board.c103
-rw-r--r--ports/nrf/boards/hiibot_bluefi/mpconfigboard.h64
-rw-r--r--ports/nrf/boards/hiibot_bluefi/mpconfigboard.mk17
-rw-r--r--ports/nrf/boards/hiibot_bluefi/pins.c180
-rw-r--r--ports/nrf/boards/particle_argon/mpconfigboard.mk2
-rw-r--r--ports/nrf/boards/particle_boron/mpconfigboard.mk2
-rw-r--r--ports/nrf/boards/particle_xenon/mpconfigboard.mk2
-rw-r--r--ports/nrf/boards/pca10100/mpconfigboard.mk6
-rw-r--r--ports/nrf/boards/simmel/mpconfigboard.h2
-rw-r--r--ports/nrf/boards/simmel/mpconfigboard.mk1
-rw-r--r--ports/nrf/boards/sparkfun_nrf52840_mini/README.md2
-rw-r--r--ports/nrf/common-hal/audiobusio/I2SOut.c9
-rw-r--r--ports/nrf/common-hal/audiopwmio/PWMAudioOut.c6
-rw-r--r--ports/nrf/common-hal/digitalio/DigitalInOut.c6
-rw-r--r--ports/nrf/common-hal/microcontroller/__init__.c14
-rw-r--r--ports/nrf/common-hal/neopixel_write/__init__.h2
-rw-r--r--ports/nrf/common-hal/rotaryio/IncrementalEncoder.c6
-rw-r--r--ports/nrf/common-hal/rtc/RTC.c1
-rwxr-xr-xports/nrf/common-hal/supervisor/Runtime.c1
-rwxr-xr-xports/nrf/common-hal/supervisor/__init__.c2
-rw-r--r--ports/nrf/common-hal/watchdog/WatchDogMode.c0
-rw-r--r--ports/nrf/common-hal/watchdog/WatchDogTimer.c189
-rw-r--r--ports/nrf/common-hal/watchdog/WatchDogTimer.h44
-rw-r--r--ports/nrf/common-hal/watchdog/__init__.c25
-rw-r--r--ports/nrf/common-hal/watchdog/__init__.h30
-rw-r--r--ports/nrf/examples/ubluepy_eddystone.py4
-rw-r--r--ports/nrf/examples/ubluepy_scan.py8
-rw-r--r--ports/nrf/examples/ubluepy_temp.py9
-rw-r--r--ports/nrf/gccollect.c2
-rw-r--r--ports/nrf/mpconfigport.mk4
-rw-r--r--ports/nrf/nrfx_config.h7
-rw-r--r--ports/nrf/nrfx_glue.h8
-rw-r--r--ports/nrf/peripherals/nrf/nvm.c2
-rw-r--r--ports/nrf/supervisor/port.c62
42 files changed, 835 insertions, 94 deletions
diff --git a/ports/nrf/Makefile b/ports/nrf/Makefile
index 8a7b1104b..5b81fa9a7 100755
--- a/ports/nrf/Makefile
+++ b/ports/nrf/Makefile
@@ -93,7 +93,7 @@ else
endif
-CFLAGS += $(INC) -Wall -Werror -std=gnu11 -nostdlib $(BASE_CFLAGS) $(CFLAGS_MOD) $(COPT)
+CFLAGS += $(INC) -Wall -Werror -std=gnu11 -nostdlib -fshort-enums $(BASE_CFLAGS) $(CFLAGS_MOD) $(COPT)
# Undo some warnings.
# nrfx uses undefined preprocessor variables quite casually, so we can't do warning checks for these.
@@ -114,7 +114,7 @@ CFLAGS += \
# TODO: check this
CFLAGS += -D__START=main
-LDFLAGS = $(CFLAGS) -nostartfiles -fshort-enums -Wl,-nostdlib -Wl,-T,$(GENERATED_LD_FILE) -Wl,-Map=$@.map -Wl,-cref -Wl,-gc-sections -specs=nano.specs
+LDFLAGS = $(CFLAGS) -nostartfiles -Wl,-nostdlib -Wl,-T,$(GENERATED_LD_FILE) -Wl,-Map=$@.map -Wl,-cref -Wl,-gc-sections -specs=nano.specs
LIBS := -lgcc -lc
LDFLAGS += -mthumb -mcpu=cortex-m4
@@ -136,6 +136,7 @@ SRC_NRFX = $(addprefix nrfx/,\
drivers/src/nrfx_gpiote.c \
drivers/src/nrfx_rtc.c \
drivers/src/nrfx_nvmc.c \
+ drivers/src/nrfx_wdt.c \
)
ifdef EXTERNAL_FLASH_DEVICES
diff --git a/ports/nrf/bluetooth/s140_nrf52_6.1.0/s140_nrf52_6.1.0_API/doc/ble_api.dox b/ports/nrf/bluetooth/s140_nrf52_6.1.0/s140_nrf52_6.1.0_API/doc/ble_api.dox
index a444c5e4e..ecabf96aa 100644
--- a/ports/nrf/bluetooth/s140_nrf52_6.1.0/s140_nrf52_6.1.0_API/doc/ble_api.dox
+++ b/ports/nrf/bluetooth/s140_nrf52_6.1.0/s140_nrf52_6.1.0_API/doc/ble_api.dox
@@ -968,11 +968,11 @@
* |||;
* SD<-ADVERTISERS [label = "Scannable Advertisement (ADV_SCAN_IND)", textcolor="#000080", linecolor="#000080"];
* SD->ADVERTISERS [label = "Scan Request (SCAN_REQ)", textcolor="#000080", linecolor="#000080"];
- * SD<-ADVERTISERS [label = "Scan Response (SCAN_RSP)", textcolor="#000080", linecolor="#000080"];
+ * SD<-ADVERTISERS [label = "Scan Response (SCAN_RSP)", textcolor="#000080", linecolor="#000080"];
* APP<<=SD [label = "BLE_GAP_EVT_ADV_REPORT {bdaddr, rssi, data}"];
- * ...;
- * APP<<=SD [label = "BLE_GAP_EVT_TIMEOUT {BLE_GAP_TIMEOUT_SRC_SCAN}"];
- * |||;
+ * ...;
+ * APP<<=SD [label = "BLE_GAP_EVT_TIMEOUT {BLE_GAP_TIMEOUT_SRC_SCAN}"];
+ * |||;
* @endmsc
* @defgroup BLE_GAP_SCAN_MSC_AE Scanning for advertisers performing legacy and extended advertising
* @msc
@@ -1011,7 +1011,7 @@
* APP<<=SD [label = "BLE_GAP_EVT_ADV_REPORT {type : {extended_pdu = 1, scannable = 1, scan_response = 1}, data}"];
* APP=>SD [label = "sd_ble_gap_scan_start(params = NULL, adv_report_buffer)"];
* APP<<SD [label = "NRF_SUCCESS"];
- * SD<-ADVERTISERS [label = "Legacy Scannable Advertisement (ADV_SCAN_IND) with adv_data ", textcolor="#000080", linecolor="#000080"];
+ * SD<-ADVERTISERS [label = "Legacy Scannable Advertisement (ADV_SCAN_IND) with adv_data ", textcolor="#000080", linecolor="#000080"];
* SD->ADVERTISERS [label = "Legacy Scan Request (SCAN_REQ)", textcolor="#000080", linecolor="#000080"];
* APP<<=SD [label = "BLE_GAP_EVT_ADV_REPORT {type : {extended_pdu = 0, scannable = 1, scan_response = 0}, adv_data}"];
* APP=>SD [label = "sd_ble_gap_scan_start(params = NULL, adv_report_buffer)"];
@@ -1030,8 +1030,8 @@
* --- [label = " Variant #2 Reporting incomplete advertising reports"];
* |||;
* APP=>SD [label = "sd_ble_gap_scan_start(params : {extended = 1, report_incomplete_evts = 1}, adv_report_buffer)"];
- * APP<<SD [label = "NRF_SUCCESS"];
- * |||;
+ * APP<<SD [label = "NRF_SUCCESS"];
+ * |||;
* SD<-ADVERTISERS [label = "Advertisement (ADV_*_IND)", textcolor="#000080", linecolor="#000080"];
* APP<<=SD [label = "BLE_GAP_EVT_ADV_REPORT {type : status = BLE_GAP_ADV_DATA_STATUS_INCOMPLETE_MORE_DATA, aux_pointer}"];
* |||;
@@ -1052,7 +1052,7 @@
* @defgroup BLE_GAP_CENTRAL_CONN_MSC Central Connection Establishment and Termination
* @{
* @defgroup BLE_GAP_CENTRAL_CONN_MSC_LEGACY Connecting to legacy advertisers
-
+
* @msc
* hscale = "1.5";
* APP,SD,PERIPHERAL;
@@ -1114,9 +1114,9 @@
* SD rbox SD [label = "Connection timeout reached"];
* |||;
* APP<<=SD [label = "BLE_GAP_EVT_TIMEOUT {BLE_GAP_TIMEOUT_SRC_CONN}"];
- * @endmsc
+ * @endmsc
* @}
-
+
*
* @defgroup BLE_GAP_CENTRAL_CPU_MSC Central Connection Parameter Update
* @msc
@@ -1868,7 +1868,7 @@
* APP=>SD [label = "sd_ble_gap_privacy_set(params: {mode: DEVICE_PRIVACY, private_addr_type: RESOLVABLE } "];
* APP<<SD [label = "NRF_SUCCESS"];
* |||;
-
+
* APP=>SD [label = "sd_ble_gap_device_identities_set(pp_id_keys: {{peer_addr1, peer_irk1}}, pp_local_irks: {local_irk1}) "];
* APP<<SD [label = "NRF_SUCCESS"];
* |||;
@@ -3894,4 +3894,3 @@
* @}
* @}
*/
-
diff --git a/ports/nrf/bluetooth/s140_nrf52_6.1.0/s140_nrf52_6.1.0_API/include/ble.h b/ports/nrf/bluetooth/s140_nrf52_6.1.0/s140_nrf52_6.1.0_API/include/ble.h
index da1a06bbc..e2abcd7ad 100644
--- a/ports/nrf/bluetooth/s140_nrf52_6.1.0/s140_nrf52_6.1.0_API/include/ble.h
+++ b/ports/nrf/bluetooth/s140_nrf52_6.1.0/s140_nrf52_6.1.0_API/include/ble.h
@@ -521,7 +521,7 @@ SVCALL(SD_BLE_UUID_VS_ADD, uint32_t, sd_ble_uuid_vs_add(ble_uuid128_t const *p_v
/**@brief Remove a Vendor Specific base UUID.
- *
+ *
* @details This call removes a Vendor Specific base UUID that has been added with @ref sd_ble_uuid_vs_add. This function allows
* the application to reuse memory allocated for Vendor Specific base UUIDs.
*
diff --git a/ports/nrf/bluetooth/s140_nrf52_6.1.0/s140_nrf52_6.1.0_API/include/ble_gap.h b/ports/nrf/bluetooth/s140_nrf52_6.1.0/s140_nrf52_6.1.0_API/include/ble_gap.h
index a130d7b51..6750e742f 100644
--- a/ports/nrf/bluetooth/s140_nrf52_6.1.0/s140_nrf52_6.1.0_API/include/ble_gap.h
+++ b/ports/nrf/bluetooth/s140_nrf52_6.1.0/s140_nrf52_6.1.0_API/include/ble_gap.h
@@ -1664,7 +1664,7 @@ SVCALL(SD_BLE_GAP_ADDR_GET, uint32_t, sd_ble_gap_addr_get(ble_gap_addr_t *p_addr
*
* @retval ::NRF_SUCCESS Address successfully retrieved.
* @retval ::NRF_ERROR_INVALID_ADDR Invalid or NULL pointer supplied.
- * @retval ::BLE_ERROR_INVALID_ADV_HANDLE The provided advertising handle was not found.
+ * @retval ::BLE_ERROR_INVALID_ADV_HANDLE The provided advertising handle was not found.
* @retval ::NRF_ERROR_INVALID_STATE The advertising set is currently not advertising.
*/
SVCALL(SD_BLE_GAP_ADV_ADDR_GET, uint32_t, sd_ble_gap_adv_addr_get(uint8_t adv_handle, ble_gap_addr_t *p_addr));
diff --git a/ports/nrf/bluetooth/s140_nrf52_7.0.1/s140_nrf52_7.0.1_API/doc/ble_api.dox b/ports/nrf/bluetooth/s140_nrf52_7.0.1/s140_nrf52_7.0.1_API/doc/ble_api.dox
index 6cdfc8870..ceebf55a7 100644
--- a/ports/nrf/bluetooth/s140_nrf52_7.0.1/s140_nrf52_7.0.1_API/doc/ble_api.dox
+++ b/ports/nrf/bluetooth/s140_nrf52_7.0.1/s140_nrf52_7.0.1_API/doc/ble_api.dox
@@ -968,11 +968,11 @@
* |||;
* SD<-ADVERTISERS [label = "Scannable Advertisement (ADV_SCAN_IND)", textcolor="#000080", linecolor="#000080"];
* SD->ADVERTISERS [label = "Scan Request (SCAN_REQ)", textcolor="#000080", linecolor="#000080"];
- * SD<-ADVERTISERS [label = "Scan Response (SCAN_RSP)", textcolor="#000080", linecolor="#000080"];
+ * SD<-ADVERTISERS [label = "Scan Response (SCAN_RSP)", textcolor="#000080", linecolor="#000080"];
* APP<<=SD [label = "BLE_GAP_EVT_ADV_REPORT {bdaddr, rssi, data}"];
- * ...;
- * APP<<=SD [label = "BLE_GAP_EVT_TIMEOUT {BLE_GAP_TIMEOUT_SRC_SCAN}"];
- * |||;
+ * ...;
+ * APP<<=SD [label = "BLE_GAP_EVT_TIMEOUT {BLE_GAP_TIMEOUT_SRC_SCAN}"];
+ * |||;
* @endmsc
* @defgroup BLE_GAP_SCAN_MSC_AE Scanning for advertisers performing legacy and extended advertising
* @msc
@@ -1011,7 +1011,7 @@
* APP<<=SD [label = "BLE_GAP_EVT_ADV_REPORT {type : {extended_pdu = 1, scannable = 1, scan_response = 1}, data}"];
* APP=>SD [label = "sd_ble_gap_scan_start(params = NULL, adv_report_buffer)"];
* APP<<SD [label = "NRF_SUCCESS"];
- * SD<-ADVERTISERS [label = "Legacy Scannable Advertisement (ADV_SCAN_IND) with adv_data ", textcolor="#000080", linecolor="#000080"];
+ * SD<-ADVERTISERS [label = "Legacy Scannable Advertisement (ADV_SCAN_IND) with adv_data ", textcolor="#000080", linecolor="#000080"];
* SD->ADVERTISERS [label = "Legacy Scan Request (SCAN_REQ)", textcolor="#000080", linecolor="#000080"];
* APP<<=SD [label = "BLE_GAP_EVT_ADV_REPORT {type : {extended_pdu = 0, scannable = 1, scan_response = 0}, adv_data}"];
* APP=>SD [label = "sd_ble_gap_scan_start(params = NULL, adv_report_buffer)"];
@@ -1030,8 +1030,8 @@
* --- [label = " Variant #2 Reporting incomplete advertising reports"];
* |||;
* APP=>SD [label = "sd_ble_gap_scan_start(params : {extended = 1, report_incomplete_evts = 1}, adv_report_buffer)"];
- * APP<<SD [label = "NRF_SUCCESS"];
- * |||;
+ * APP<<SD [label = "NRF_SUCCESS"];
+ * |||;
* SD<-ADVERTISERS [label = "Advertisement (ADV_*_IND)", textcolor="#000080", linecolor="#000080"];
* APP<<=SD [label = "BLE_GAP_EVT_ADV_REPORT {type : status = BLE_GAP_ADV_DATA_STATUS_INCOMPLETE_MORE_DATA, aux_pointer}"];
* |||;
@@ -1052,7 +1052,7 @@
* @defgroup BLE_GAP_CENTRAL_CONN_MSC Central Connection Establishment and Termination
* @{
* @defgroup BLE_GAP_CENTRAL_CONN_MSC_LEGACY Connecting to legacy advertisers
-
+
* @msc
* hscale = "1.5";
* APP,SD,PERIPHERAL;
@@ -1114,9 +1114,9 @@
* SD rbox SD [label = "Connection timeout reached"];
* |||;
* APP<<=SD [label = "BLE_GAP_EVT_TIMEOUT {BLE_GAP_TIMEOUT_SRC_CONN}"];
- * @endmsc
+ * @endmsc
* @}
-
+
*
* @defgroup BLE_GAP_CENTRAL_CPU_MSC Central Connection Parameter Update
* @msc
@@ -1868,7 +1868,7 @@
* APP=>SD [label = "sd_ble_gap_privacy_set(params: {mode: DEVICE_PRIVACY, private_addr_type: RESOLVABLE } "];
* APP<<SD [label = "NRF_SUCCESS"];
* |||;
-
+
* APP=>SD [label = "sd_ble_gap_device_identities_set(pp_id_keys: {peer_addr1, peer_irk1}, pp_local_irks: {local_irk1}) "];
* APP<<SD [label = "NRF_SUCCESS"];
* |||;
@@ -1970,7 +1970,7 @@
* hscale = "1.5";
* APP,SD,ADVERTISERS;
* |||;
-
+
* APP=>SD [label = "sd_ble_gap_device_identities_set(pp_id_keys: {peer_addr1, peer_irk1}, pp_local_irks: NULL) "];
* APP<<SD [label = "NRF_SUCCESS"];
* |||;
@@ -2022,7 +2022,7 @@
* |||;
* --- [label = " Variant #4 Scan directed advertisers and resolve initiator address using local IRK in device identity list"];
* |||;
-
+
* APP=>SD [label = "sd_ble_gap_device_identities_set(pp_id_keys: {peer_addr1, peer_irk1}, pp_local_irks: local_irk1) "];
* APP<<SD [label = "NRF_SUCCESS"];
* |||;
@@ -2054,7 +2054,7 @@
* |||;
* --- [label = " Variant #1 Advertise directed to private peer"];
* |||;
-
+
* APP=>SD [label = "sd_ble_gap_device_identities_set(pp_id_keys: {peer_addr1, peer_irk1}, pp_local_irks: NULL) "];
* APP<<SD [label = "NRF_SUCCESS"];
* |||;
@@ -2070,7 +2070,7 @@
* |||;
* --- [label = " Variant #2 Private directed advertising to private peer using device IRK"];
* |||;
-
+
* APP=>SD [label = "sd_ble_gap_device_identities_set(pp_id_keys: {peer_addr1, peer_irk1}, pp_local_irks: NULL) "];
* APP<<SD [label = "NRF_SUCCESS"];
* |||;
@@ -2089,7 +2089,7 @@
* |||;
* --- [label = " Variant #3 Private directed advertising to private peer using local IRK in device identity list"];
* |||;
-
+
* APP=>SD [label = "sd_ble_gap_device_identities_set(pp_id_keys: {peer_addr1, peer_irk1}, pp_local_irks: {local_irk1}) "];
* APP<<SD [label = "NRF_SUCCESS"];
* |||;
@@ -2132,7 +2132,7 @@
* hscale = "1.5";
* APP,SD,CENTRAL;
* |||;
-
+
* APP=>SD [label = "sd_ble_gap_device_identities_set(pp_id_keys: {peer_addr1, peer_irk1}, pp_local_irks: NULL) "];
* APP<<SD [label = "NRF_SUCCESS"];
* |||;
@@ -2157,7 +2157,7 @@
* hscale = "1.5";
* APP,SD,PERIPHERAL;
* |||;
-
+
* APP=>SD [label = "sd_ble_gap_device_identities_set(pp_id_keys: {peer_addr1, peer_irk1}, pp_local_irks: NULL) "];
* APP<<SD [label = "NRF_SUCCESS"];
* |||;
@@ -2346,7 +2346,7 @@
* APP<<SD [label = "NRF_SUCCESS"];
* SD:>PEER [label = "LL Length Request (LL_LENGTH_REQ) {tx=251, rx=251}", textcolor="#000080", linecolor="#000080"];
* SD<:PEER [label = "LL Length Response (LL_LENGTH_RSP) {tx=251, rx=251}", textcolor="#000080", linecolor="#000080"];
-
+
* APP<<=SD [label = "BLE_GAP_EVT_DATA_LENGTH_UPDATE {.effective_params={.max_tx_octets=251, .max_rx_octets=251, .max_tx_time_us=2120, .max_rx_time_us=2120}}"];
* |||;
* ...;
@@ -3927,4 +3927,3 @@
* @}
* @}
*/
-
diff --git a/ports/nrf/bluetooth/s140_nrf52_7.0.1/s140_nrf52_7.0.1_API/include/ble.h b/ports/nrf/bluetooth/s140_nrf52_7.0.1/s140_nrf52_7.0.1_API/include/ble.h
index 39944854c..d17ac9a59 100644
--- a/ports/nrf/bluetooth/s140_nrf52_7.0.1/s140_nrf52_7.0.1_API/include/ble.h
+++ b/ports/nrf/bluetooth/s140_nrf52_7.0.1/s140_nrf52_7.0.1_API/include/ble.h
@@ -89,7 +89,7 @@ enum BLE_COMMON_SVCS
*/
enum BLE_COMMON_EVTS
{
- BLE_EVT_USER_MEM_REQUEST = BLE_EVT_BASE + 0, /**< User Memory request. See @ref ble_evt_user_mem_request_t
+ BLE_EVT_USER_MEM_REQUEST = BLE_EVT_BASE + 0, /**< User Memory request. See @ref ble_evt_user_mem_request_t
\n Reply with @ref sd_ble_user_mem_reply. */
BLE_EVT_USER_MEM_RELEASE = BLE_EVT_BASE + 1, /**< User Memory release. See @ref ble_evt_user_mem_release_t */
};
@@ -389,10 +389,10 @@ typedef union
* application RAM region (APP_RAM_BASE). On return, this will
* contain the minimum start address of the application RAM region
* required by the SoftDevice for this configuration.
- * @warning After this call, the SoftDevice may generate several events. The list of events provided
- * below require the application to initiate a SoftDevice API call. The corresponding API call
- * is referenced in the event documentation.
- * If the application fails to do so, the BLE connection may timeout, or the SoftDevice may stop
+ * @warning After this call, the SoftDevice may generate several events. The list of events provided
+ * below require the application to initiate a SoftDevice API call. The corresponding API call
+ * is referenced in the event documentation.
+ * If the application fails to do so, the BLE connection may timeout, or the SoftDevice may stop
* communicating with the peer device.
* - @ref BLE_GAP_EVT_CONN_PARAM_UPDATE_REQUEST
* - @ref BLE_GAP_EVT_DATA_LENGTH_UPDATE_REQUEST
@@ -537,7 +537,7 @@ SVCALL(SD_BLE_UUID_VS_ADD, uint32_t, sd_ble_uuid_vs_add(ble_uuid128_t const *p_v
/**@brief Remove a Vendor Specific base UUID.
- *
+ *
* @details This call removes a Vendor Specific base UUID that has been added with @ref sd_ble_uuid_vs_add. This function allows
* the application to reuse memory allocated for Vendor Specific base UUIDs.
*
diff --git a/ports/nrf/boards/common.template.ld b/ports/nrf/boards/common.template.ld
index 9a7df69a4..5982b8ba0 100644
--- a/ports/nrf/boards/common.template.ld
+++ b/ports/nrf/boards/common.template.ld
@@ -70,20 +70,6 @@ SECTIONS
_etext = .; /* define a global symbol at end of code */
} >FLASH_FIRMWARE
- /*
- .ARM.extab :
- {
- *(.ARM.extab* .gnu.linkonce.armextab.*)
- } >FLASH_FIRMWARE
-
- .ARM :
- {
- __exidx_start = .;
- *(.ARM.exidx*)
- __exidx_end = .;
- } >FLASH_FIRMWARE
- */
-
/* used by the startup to initialize data */
_sidata = .;
@@ -147,6 +133,14 @@ SECTIONS
. = ALIGN(4);
} >RAM
+ /* Remove exception unwinding information, since Circuit Python
+ does not support this GCC feature. */
+ /DISCARD/ :
+ {
+ *(.ARM.extab* .gnu.linkonce.armextab.*)
+ *(.ARM.exidx*)
+ }
+
/* Remove information from the standard libraries */
/*
/DISCARD/ :
diff --git a/ports/nrf/boards/electronut_labs_papyr/README.md b/ports/nrf/boards/electronut_labs_papyr/README.md
index fda390193..7e5c43cc8 100644
--- a/ports/nrf/boards/electronut_labs_papyr/README.md
+++ b/ports/nrf/boards/electronut_labs_papyr/README.md
@@ -4,7 +4,7 @@ The `Electronut Labs Papyr` board is based on the `nRF52840` SoC from
Nordic Semiconductors. It has an e-ink display on it, along with a CR2477
battery holder.
-Papyr can be programmed with the [`Adafruit nRF52 bootloader`](https://github.com/adafruit/Adafruit_nRF52_Bootloader) to
+Papyr can be programmed with the [`Adafruit nRF52 bootloader`](https://github.com/adafruit/Adafruit_nRF52_Bootloader) to
Schematic, datasheet default pin mapping etc. can be found over [here](https://docs.electronut.in/papyr/). The default pin mapping can be found in the board directory.
diff --git a/ports/nrf/boards/hiibot_bluefi/board.c b/ports/nrf/boards/hiibot_bluefi/board.c
new file mode 100644
index 000000000..6b53cab13
--- /dev/null
+++ b/ports/nrf/boards/hiibot_bluefi/board.c
@@ -0,0 +1,103 @@
+/*
+ * This file is part of the MicroPython project, http://micropython.org/
+ *
+ * The MIT License (MIT)
+ *
+ * Copyright (c) 2017 Scott Shawcroft for Adafruit Industries
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
+
+#include "boards/board.h"
+#include "mpconfigboard.h"
+
+#include "shared-bindings/busio/SPI.h"
+#include "shared-bindings/displayio/FourWire.h"
+#include "shared-module/displayio/__init__.h"
+#include "shared-module/displayio/mipi_constants.h"
+
+displayio_fourwire_obj_t board_display_obj;
+
+#define DELAY 0x80
+
+uint8_t display_init_sequence[] = {
+ 0x01, 0 | DELAY, 150, // SWRESET
+ 0x11, 0 | DELAY, 255, // SLPOUT
+ 0x36, 1, 0b10100000, // _MADCTL for rotation 0
+ 0x3a, 1, 0x55, // COLMOD - 16bit color
+ 0x21, 0 | DELAY, 10, // _INVON
+ 0x13, 0 | DELAY, 10, // _NORON
+ 0x29, 0 | DELAY, 255, // _DISPON
+};
+
+void board_init(void) {
+ busio_spi_obj_t* spi = &displays[0].fourwire_bus.inline_bus;
+ common_hal_busio_spi_construct(spi, &pin_P0_07, &pin_P1_08, NULL); // SCK, MOSI, MISO
+ common_hal_busio_spi_never_reset(spi);
+
+ displayio_fourwire_obj_t* bus = &displays[0].fourwire_bus;
+ bus->base.type = &displayio_fourwire_type;
+ common_hal_displayio_fourwire_construct(bus,
+ spi,
+ &pin_P0_27, // TFT_DC Command or data
+ &pin_P0_05, // TFT_CS Chip select
+ NULL, // no TFT_RST Reset
+ //&pin_P1_14, // TFT_RST Reset
+ 60000000, // Baudrate
+ 0, // Polarity
+ 0); // Phase
+
+ displayio_display_obj_t* display = &displays[0].display;
+ display->base.type = &displayio_display_type;
+ common_hal_displayio_display_construct(display,
+ bus,
+ 240, // Width (after rotation)
+ 240, // Height (after rotation)
+ 80, // column start
+ 0, // row start
+ 180, // rotation
+ 16, // Color depth
+ false, // Grayscale
+ false, // Pixels in a byte share a row. Only used for depth < 8
+ 1, // bytes per cell. Only valid for depths < 8
+ false, // reverse_pixels_in_byte. Only valid for depths < 8
+ true, // reverse_pixels_in_word
+ MIPI_COMMAND_SET_COLUMN_ADDRESS, // Set column command
+ MIPI_COMMAND_SET_PAGE_ADDRESS, // Set row command
+ MIPI_COMMAND_WRITE_MEMORY_START, // Write memory command
+ 0x37, // set vertical scroll command
+ display_init_sequence,
+ sizeof(display_init_sequence),
+ &pin_P1_13, // backlight pin
+ NO_BRIGHTNESS_COMMAND,
+ 1.0f, // brightness (ignored)
+ true, // auto_brightness
+ false, // single_byte_bounds
+ false, // data_as_commands
+ true, // auto_refresh
+ 60, // native_frames_per_second
+ true); // backlight_on_high
+}
+
+bool board_requests_safe_mode(void) {
+ return false;
+}
+
+void reset_board(void) {
+}
diff --git a/ports/nrf/boards/hiibot_bluefi/mpconfigboard.h b/ports/nrf/boards/hiibot_bluefi/mpconfigboard.h
new file mode 100644
index 000000000..4b7a884cf
--- /dev/null
+++ b/ports/nrf/boards/hiibot_bluefi/mpconfigboard.h
@@ -0,0 +1,64 @@
+/*
+ * This file is part of the MicroPython project, http://micropython.org/
+ *
+ * The MIT License (MIT)
+ *
+ * Copyright (c) 2016 Glenn Ruben Bakke
+ * Copyright (c) 2018 Dan Halbert for Adafruit Industries
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
+
+#include "nrfx/hal/nrf_gpio.h"
+
+#define MICROPY_HW_BOARD_NAME "HiiBot BlueFi"
+#define MICROPY_HW_MCU_NAME "nRF52840"
+
+#define MICROPY_HW_NEOPIXEL (&pin_P1_10) // P18 / D18
+
+#define MICROPY_HW_LED_STATUS (&pin_P1_12) // P17 / D17
+
+#if QSPI_FLASH_FILESYSTEM
+#define MICROPY_QSPI_DATA0 NRF_GPIO_PIN_MAP(1, 1)
+#define MICROPY_QSPI_DATA1 NRF_GPIO_PIN_MAP(1, 4)
+#define MICROPY_QSPI_DATA2 NRF_GPIO_PIN_MAP(1, 6)
+#define MICROPY_QSPI_DATA3 NRF_GPIO_PIN_MAP(1, 5)
+#define MICROPY_QSPI_SCK NRF_GPIO_PIN_MAP(1, 3)
+#define MICROPY_QSPI_CS NRF_GPIO_PIN_MAP(1, 2)
+#endif
+
+#if SPI_FLASH_FILESYSTEM
+#define SPI_FLASH_MOSI_PIN &pin_P1_01
+#define SPI_FLASH_MISO_PIN &pin_P1_04
+#define SPI_FLASH_SCK_PIN &pin_P1_03
+#define SPI_FLASH_CS_PIN &pin_P1_02
+#endif
+
+// No 32kHz crystal. THere's a 32MHz crystal in the nRF module.
+#define BOARD_HAS_32KHZ_XTAL (0)
+
+#define DEFAULT_I2C_BUS_SCL (&pin_P0_00)
+#define DEFAULT_I2C_BUS_SDA (&pin_P0_31)
+
+#define DEFAULT_SPI_BUS_SCK (&pin_P0_06)
+#define DEFAULT_SPI_BUS_MOSI (&pin_P0_26)
+#define DEFAULT_SPI_BUS_MISO (&pin_P0_04)
+
+#define DEFAULT_UART_BUS_RX (&pin_P0_28)
+#define DEFAULT_UART_BUS_TX (&pin_P0_02)
diff --git a/ports/nrf/boards/hiibot_bluefi/mpconfigboard.mk b/ports/nrf/boards/hiibot_bluefi/mpconfigboard.mk
new file mode 100644
index 000000000..e43639a89
--- /dev/null
+++ b/ports/nrf/boards/hiibot_bluefi/mpconfigboard.mk
@@ -0,0 +1,17 @@
+USB_VID = 0x239A
+USB_PID = 0x80B2
+USB_PRODUCT = "HiiBot BlueFi"
+USB_MANUFACTURER = "HiiBot"
+
+MCU_CHIP = nrf52840
+
+QSPI_FLASH_FILESYSTEM = 1
+EXTERNAL_FLASH_DEVICE_COUNT = 1
+EXTERNAL_FLASH_DEVICES = "W25Q16JV_IQ"
+
+# Allocate two, not just one I2C peripheral for Bluefi, so that we have both
+# on-board and off-board I2C available.
+# When SPIM3 becomes available we'll be able to have two I2C and two SPI peripherals.
+# We use a CFLAGS define here because there are include order issues
+# if we try to include "mpconfigport.h" into nrfx_config.h .
+CFLAGS += -DCIRCUITPY_NRF_NUM_I2C=2
diff --git a/ports/nrf/boards/hiibot_bluefi/pins.c b/ports/nrf/boards/hiibot_bluefi/pins.c
new file mode 100644
index 000000000..340ea948c
--- /dev/null
+++ b/ports/nrf/boards/hiibot_bluefi/pins.c
@@ -0,0 +1,180 @@
+#include "shared-bindings/board/__init__.h"
+
+#include "boards/board.h"
+#include "shared-module/displayio/__init__.h"
+
+STATIC const mp_rom_map_elem_t board_module_globals_table[] = {
+ { MP_ROM_QSTR(MP_QSTR_P0), MP_ROM_PTR(&pin_P0_28) },
+ { MP_ROM_QSTR(MP_QSTR_D0), MP_ROM_PTR(&pin_P0_28) },
+ { MP_ROM_QSTR(MP_QSTR_A0), MP_ROM_PTR(&pin_P0_28) },
+ { MP_ROM_QSTR(MP_QSTR_RX), MP_ROM_PTR(&pin_P0_28) },
+
+ { MP_ROM_QSTR(MP_QSTR_P1), MP_ROM_PTR(&pin_P0_02) },
+ { MP_ROM_QSTR(MP_QSTR_D1), MP_ROM_PTR(&pin_P0_02) },
+ { MP_ROM_QSTR(MP_QSTR_A1), MP_ROM_PTR(&pin_P0_02) },
+ { MP_ROM_QSTR(MP_QSTR_TX), MP_ROM_PTR(&pin_P0_02) },
+
+ { MP_ROM_QSTR(MP_QSTR_P2), MP_ROM_PTR(&pin_P0_29) },
+ { MP_ROM_QSTR(MP_QSTR_D2), MP_ROM_PTR(&pin_P0_29) },
+ { MP_ROM_QSTR(MP_QSTR_A2), MP_ROM_PTR(&pin_P0_29) },
+
+ { MP_ROM_QSTR(MP_QSTR_P3), MP_ROM_PTR(&pin_P0_30) },
+ { MP_ROM_QSTR(MP_QSTR_D3), MP_ROM_PTR(&pin_P0_30) },
+ { MP_ROM_QSTR(MP_QSTR_A3), MP_ROM_PTR(&pin_P0_30) },
+
+ { MP_ROM_QSTR(MP_QSTR_P4), MP_ROM_PTR(&pin_P0_03) },
+ { MP_ROM_QSTR(MP_QSTR_D4), MP_ROM_PTR(&pin_P0_03) },
+ { MP_ROM_QSTR(MP_QSTR_A4), MP_ROM_PTR(&pin_P0_03) },
+
+ { MP_ROM_QSTR(MP_QSTR_P5), MP_ROM_PTR(&pin_P1_07) },
+ { MP_ROM_QSTR(MP_QSTR_D5), MP_ROM_PTR(&pin_P1_07) },
+ { MP_ROM_QSTR(MP_QSTR_BUTTON_A), MP_ROM_PTR(&pin_P1_07) },
+
+ { MP_ROM_QSTR(MP_QSTR_P6), MP_ROM_PTR(&pin_P0_08) },
+ { MP_ROM_QSTR(MP_QSTR_D6), MP_ROM_PTR(&pin_P0_08) },
+
+ { MP_ROM_QSTR(MP_QSTR_P7), MP_ROM_PTR(&pin_P0_25) },
+ { MP_ROM_QSTR(MP_QSTR_D7), MP_ROM_PTR(&pin_P0_25) },
+
+ { MP_ROM_QSTR(MP_QSTR_P8), MP_ROM_PTR(&pin_P0_23) },
+ { MP_ROM_QSTR(MP_QSTR_D8), MP_ROM_PTR(&pin_P0_23) },
+
+ { MP_ROM_QSTR(MP_QSTR_P9), MP_ROM_PTR(&pin_P0_21) },
+ { MP_ROM_QSTR(MP_QSTR_D9), MP_ROM_PTR(&pin_P0_21) },
+
+ { MP_ROM_QSTR(MP_QSTR_P10), MP_ROM_PTR(&pin_P0_19) },
+ { MP_ROM_QSTR(MP_QSTR_D10), MP_ROM_PTR(&pin_P0_19) },
+
+ { MP_ROM_QSTR(MP_QSTR_P11), MP_ROM_PTR(&pin_P1_09) },
+ { MP_ROM_QSTR(MP_QSTR_D11), MP_ROM_PTR(&pin_P1_09) },
+ { MP_ROM_QSTR(MP_QSTR_BUTTON_B), MP_ROM_PTR(&pin_P1_09) },
+
+ { MP_ROM_QSTR(MP_QSTR_P12), MP_ROM_PTR(&pin_P0_16) },
+ { MP_ROM_QSTR(MP_QSTR_D12), MP_ROM_PTR(&pin_P0_16) },
+
+ { MP_ROM_QSTR(MP_QSTR_P13), MP_ROM_PTR(&pin_P0_06) },
+ { MP_ROM_QSTR(MP_QSTR_D13), MP_ROM_PTR(&pin_P0_06) },
+ { MP_ROM_QSTR(MP_QSTR_SCK), MP_ROM_PTR(&pin_P0_06) },
+
+ { MP_ROM_QSTR(MP_QSTR_P14), MP_ROM_PTR(&pin_P0_04) },
+ { MP_ROM_QSTR(MP_QSTR_D14), MP_ROM_PTR(&pin_P0_04) },
+ { MP_ROM_QSTR(MP_QSTR_A5), MP_ROM_PTR(&pin_P0_04) },
+ { MP_ROM_QSTR(MP_QSTR_MISO), MP_ROM_PTR(&pin_P0_04) },
+
+ { MP_ROM_QSTR(MP_QSTR_P15), MP_ROM_PTR(&pin_P0_26) },
+ { MP_ROM_QSTR(MP_QSTR_D15), MP_ROM_PTR(&pin_P0_26) },
+ { MP_ROM_QSTR(MP_QSTR_MOSI), MP_ROM_PTR(&pin_P0_26) },
+
+ { MP_ROM_QSTR(MP_QSTR_P16), MP_ROM_PTR(&pin_P0_01) },
+ { MP_ROM_QSTR(MP_QSTR_D16), MP_ROM_PTR(&pin_P0_01) },
+
+ { MP_ROM_QSTR(MP_QSTR_P17), MP_ROM_PTR(&pin_P1_12) },
+ { MP_ROM_QSTR(MP_QSTR_D17), MP_ROM_PTR(&pin_P1_12) },
+ { MP_ROM_QSTR(MP_QSTR_REDLED), MP_ROM_PTR(&pin_P1_12) },
+
+ { MP_ROM_QSTR(MP_QSTR_P18), MP_ROM_PTR(&pin_P1_10) },
+ { MP_ROM_QSTR(MP_QSTR_D18), MP_ROM_PTR(&pin_P1_10) },
+ { MP_ROM_QSTR(MP_QSTR_NEOPIXEL), MP_ROM_PTR(&pin_P1_10) },
+
+ { MP_ROM_QSTR(MP_QSTR_P19), MP_ROM_PTR(&pin_P0_00) },
+ { MP_ROM_QSTR(MP_QSTR_D19), MP_ROM_PTR(&pin_P0_00) },
+ { MP_ROM_QSTR(MP_QSTR_SCL), MP_ROM_PTR(&pin_P0_00) },
+
+ { MP_ROM_QSTR(MP_QSTR_P20), MP_ROM_PTR(&pin_P0_31) },
+ { MP_ROM_QSTR(MP_QSTR_D20), MP_ROM_PTR(&pin_P0_31) },
+ { MP_ROM_QSTR(MP_QSTR_A6), MP_ROM_PTR(&pin_P0_31) },
+ { MP_ROM_QSTR(MP_QSTR_SDA), MP_ROM_PTR(&pin_P0_31) },
+
+ { MP_ROM_QSTR(MP_QSTR_P21), MP_ROM_PTR(&pin_P0_09) },
+ { MP_ROM_QSTR(MP_QSTR_D21), MP_ROM_PTR(&pin_P0_09) },
+ { MP_ROM_QSTR(MP_QSTR_MICROPHONE_CLOCK), MP_ROM_PTR(&pin_P0_09) },
+
+ { MP_ROM_QSTR(MP_QSTR_P22), MP_ROM_PTR(&pin_P0_10) },
+ { MP_ROM_QSTR(MP_QSTR_D22), MP_ROM_PTR(&pin_P0_10) },
+ { MP_ROM_QSTR(MP_QSTR_MICROPHONE_DATA), MP_ROM_PTR(&pin_P0_10) },
+
+ { MP_ROM_QSTR(MP_QSTR_P23), MP_ROM_PTR(&pin_P0_07) },
+ { MP_ROM_QSTR(MP_QSTR_D23), MP_ROM_PTR(&pin_P0_07) },
+ { MP_ROM_QSTR(MP_QSTR_TFT_SCK), MP_ROM_PTR(&pin_P0_07) },
+
+ { MP_ROM_QSTR(MP_QSTR_P24), MP_ROM_PTR(&pin_P1_08) },
+ { MP_ROM_QSTR(MP_QSTR_D24), MP_ROM_PTR(&pin_P1_08) },
+ { MP_ROM_QSTR(MP_QSTR_TFT_MOSI), MP_ROM_PTR(&pin_P1_08) },
+
+ { MP_ROM_QSTR(MP_QSTR_P25), MP_ROM_PTR(&pin_P0_05) },
+ { MP_ROM_QSTR(MP_QSTR_D25), MP_ROM_PTR(&pin_P0_05) },
+ { MP_ROM_QSTR(MP_QSTR_TFT_CS), MP_ROM_PTR(&pin_P0_05) },
+
+ { MP_ROM_QSTR(MP_QSTR_P26), MP_ROM_PTR(&pin_P0_27) },
+ { MP_ROM_QSTR(MP_QSTR_D26), MP_ROM_PTR(&pin_P0_27) },
+ { MP_ROM_QSTR(MP_QSTR_TFT_DC), MP_ROM_PTR(&pin_P0_27) },
+
+ { MP_ROM_QSTR(MP_QSTR_P27), MP_ROM_PTR(&pin_P1_14) },
+ { MP_ROM_QSTR(MP_QSTR_D27), MP_ROM_PTR(&pin_P1_14) },
+ { MP_ROM_QSTR(MP_QSTR_TFT_RESET), MP_ROM_PTR(&pin_P1_14) },
+ { MP_ROM_QSTR(MP_QSTR_TFT_BACKLIGHT), MP_ROM_PTR(&pin_P1_14) },
+
+ // P28~P33/D28~D33 connecte into QSPI FlashROM (W25Q16JV_IQ)
+
+ { MP_ROM_QSTR(MP_QSTR_P34), MP_ROM_PTR(&pin_P0_22) },
+ { MP_ROM_QSTR(MP_QSTR_D34), MP_ROM_PTR(&pin_P0_22) },
+ { MP_ROM_QSTR(MP_QSTR_WIFI_SCK), MP_ROM_PTR(&pin_P0_22) },
+
+ { MP_ROM_QSTR(MP_QSTR_P35), MP_ROM_PTR(&pin_P0_17) },
+ { MP_ROM_QSTR(MP_QSTR_D35), MP_ROM_PTR(&pin_P0_17) },
+ { MP_ROM_QSTR(MP_QSTR_WIFI_MISO), MP_ROM_PTR(&pin_P0_17) },
+
+ { MP_ROM_QSTR(MP_QSTR_P36), MP_ROM_PTR(&pin_P0_20) },
+ { MP_ROM_QSTR(MP_QSTR_D36), MP_ROM_PTR(&pin_P0_20) },
+ { MP_ROM_QSTR(MP_QSTR_WIFI_MOSI), MP_ROM_PTR(&pin_P0_20) },
+
+ { MP_ROM_QSTR(MP_QSTR_P37), MP_ROM_PTR(&pin_P0_15) },
+ { MP_ROM_QSTR(MP_QSTR_D37), MP_ROM_PTR(&pin_P0_15) },
+ { MP_ROM_QSTR(MP_QSTR_WIFI_BUSY), MP_ROM_PTR(&pin_P0_15) },
+
+ { MP_ROM_QSTR(MP_QSTR_P38), MP_ROM_PTR(&pin_P0_24) },
+ { MP_ROM_QSTR(MP_QSTR_D38), MP_ROM_PTR(&pin_P0_24) },
+ { MP_ROM_QSTR(MP_QSTR_WIFI_CS), MP_ROM_PTR(&pin_P0_24) },
+
+ { MP_ROM_QSTR(MP_QSTR_P39), MP_ROM_PTR(&pin_P1_00) },
+ { MP_ROM_QSTR(MP_QSTR_D39), MP_ROM_PTR(&pin_P1_00) },
+ { MP_ROM_QSTR(MP_QSTR_WIFI_RESET), MP_ROM_PTR(&pin_P1_00) },
+
+ { MP_ROM_QSTR(MP_QSTR_P40), MP_ROM_PTR(&pin_P0_13) },
+ { MP_ROM_QSTR(MP_QSTR_D40), MP_ROM_PTR(&pin_P0_13) },
+ { MP_ROM_QSTR(MP_QSTR_WIFI_PWR), MP_ROM_PTR(&pin_P0_13) },
+
+ { MP_ROM_QSTR(MP_QSTR_P41), MP_ROM_PTR(&pin_P0_11) },
+ { MP_ROM_QSTR(MP_QSTR_D41), MP_ROM_PTR(&pin_P0_11) },
+ { MP_ROM_QSTR(MP_QSTR_SENSORS_SCL), MP_ROM_PTR(&pin_P0_11) },
+
+ { MP_ROM_QSTR(MP_QSTR_P42), MP_ROM_PTR(&pin_P0_12) },
+ { MP_ROM_QSTR(MP_QSTR_D42), MP_ROM_PTR(&pin_P0_12) },
+ { MP_ROM_QSTR(MP_QSTR_SENSORS_SDA), MP_ROM_PTR(&pin_P0_12) },
+
+ { MP_ROM_QSTR(MP_QSTR_P43), MP_ROM_PTR(&pin_P0_14) },
+ { MP_ROM_QSTR(MP_QSTR_D43), MP_ROM_PTR(&pin_P0_14) },
+ { MP_ROM_QSTR(MP_QSTR_IMU_IRQ), MP_ROM_PTR(&pin_P0_14) },
+ { MP_ROM_QSTR(MP_QSTR_ACCELEROMETER_INTERRUPT), MP_ROM_PTR(&pin_P0_14) },
+
+ { MP_ROM_QSTR(MP_QSTR_P44), MP_ROM_PTR(&pin_P1_14) },
+ { MP_ROM_QSTR(MP_QSTR_D44), MP_ROM_PTR(&pin_P1_14) },
+ { MP_ROM_QSTR(MP_QSTR_WHITELED), MP_ROM_PTR(&pin_P1_14) },
+
+ { MP_ROM_QSTR(MP_QSTR_P45), MP_ROM_PTR(&pin_P1_11) },
+ { MP_ROM_QSTR(MP_QSTR_D45), MP_ROM_PTR(&pin_P1_11) },
+ { MP_ROM_QSTR(MP_QSTR_SPEAKER_ENABLE), MP_ROM_PTR(&pin_P1_11) },
+
+ { MP_ROM_QSTR(MP_QSTR_P46), MP_ROM_PTR(&pin_P1_15) },
+ { MP_ROM_QSTR(MP_QSTR_D46), MP_ROM_PTR(&pin_P1_15) },
+ { MP_ROM_QSTR(MP_QSTR_SPEAKER), MP_ROM_PTR(&pin_P1_15) },
+ { MP_ROM_QSTR(MP_QSTR_AUDIO), MP_ROM_PTR(&pin_P1_15) },
+
+ { MP_ROM_QSTR(MP_QSTR_I2C), MP_ROM_PTR(&board_i2c_obj) },
+ { MP_ROM_QSTR(MP_QSTR_SPI), MP_ROM_PTR(&board_spi_obj) },
+ { MP_ROM_QSTR(MP_QSTR_UART), MP_ROM_PTR(&board_uart_obj) },
+
+ { MP_ROM_QSTR(MP_QSTR_DISPLAY), MP_ROM_PTR(&displays[0].display)}
+};
+
+MP_DEFINE_CONST_DICT(board_module_globals, board_module_globals_table);
diff --git a/ports/nrf/boards/particle_argon/mpconfigboard.mk b/ports/nrf/boards/particle_argon/mpconfigboard.mk
index a0edfda95..2ca08b982 100644
--- a/ports/nrf/boards/particle_argon/mpconfigboard.mk
+++ b/ports/nrf/boards/particle_argon/mpconfigboard.mk
@@ -11,4 +11,4 @@ EXTERNAL_FLASH_DEVICES = "MX25L3233F"
# Support for the Ethernet FeatherWing
CIRCUITPY_NETWORK = 1
-MICROPY_PY_WIZNET5K = 5500 \ No newline at end of file
+MICROPY_PY_WIZNET5K = 5500
diff --git a/ports/nrf/boards/particle_boron/mpconfigboard.mk b/ports/nrf/boards/particle_boron/mpconfigboard.mk
index ccb2d63a1..f03f43a7b 100644
--- a/ports/nrf/boards/particle_boron/mpconfigboard.mk
+++ b/ports/nrf/boards/particle_boron/mpconfigboard.mk
@@ -11,4 +11,4 @@ EXTERNAL_FLASH_DEVICES = "MX25L3233F"
# Support for the Ethernet FeatherWing
CIRCUITPY_NETWORK = 1
-MICROPY_PY_WIZNET5K = 5500 \ No newline at end of file
+MICROPY_PY_WIZNET5K = 5500
diff --git a/ports/nrf/boards/particle_xenon/mpconfigboard.mk b/ports/nrf/boards/particle_xenon/mpconfigboard.mk
index 3970b1d05..44309bbca 100644
--- a/ports/nrf/boards/particle_xenon/mpconfigboard.mk
+++ b/ports/nrf/boards/particle_xenon/mpconfigboard.mk
@@ -11,4 +11,4 @@ EXTERNAL_FLASH_DEVICES = "MX25L3233F"
# Support for the Ethernet FeatherWing
CIRCUITPY_NETWORK = 1
-MICROPY_PY_WIZNET5K = 5500 \ No newline at end of file
+MICROPY_PY_WIZNET5K = 5500
diff --git a/ports/nrf/boards/pca10100/mpconfigboard.mk b/ports/nrf/boards/pca10100/mpconfigboard.mk
index 1206c8fe5..715b65e63 100644
--- a/ports/nrf/boards/pca10100/mpconfigboard.mk
+++ b/ports/nrf/boards/pca10100/mpconfigboard.mk
@@ -8,9 +8,13 @@ MCU_CHIP = nrf52833
INTERNAL_FLASH_FILESYSTEM = 1
CIRCUITPY_AUDIOMP3 = 0
+CIRCUITPY_BITBANGIO = 0
CIRCUITPY_BUSIO = 1
+CIRCUITPY_COUNTIO = 0
CIRCUITPY_DISPLAYIO = 0
CIRCUITPY_FRAMEBUFFERIO = 0
+CIRCUITPY_FREQUENCYIO = 0
+CIRCUITPY_I2CSLAVE = 0
CIRCUITPY_NEOPIXEL_WRITE = 0
CIRCUITPY_NVM = 0
CIRCUITPY_PIXELBUF = 0
@@ -20,6 +24,8 @@ CIRCUITPY_RTC = 1
CIRCUITPY_TOUCHIO = 0
CIRCUITPY_ULAB = 0
+SUPEROPT_GC = 0
+
# These defines must be overridden before mpconfigboard.h is included, which is
# why they are passed on the command line.
CFLAGS += -DSPIM3_BUFFER_SIZE=0 -DSOFTDEVICE_RAM_SIZE='(32*1024)'
diff --git a/ports/nrf/boards/simmel/mpconfigboard.h b/ports/nrf/boards/simmel/mpconfigboard.h
index bcffb40ea..28c4ee7d9 100644
--- a/ports/nrf/boards/simmel/mpconfigboard.h
+++ b/ports/nrf/boards/simmel/mpconfigboard.h
@@ -40,7 +40,7 @@
#endif
#define CIRCUITPY_INTERNAL_NVM_SIZE 0
-#define CIRCUITPY_INTERNAL_FLASH_FILESYSTEM_SIZE (80*1024)
+#define CIRCUITPY_INTERNAL_FLASH_FILESYSTEM_SIZE (76*1024)
#define BOOTLOADER_SIZE (0x4000) // 12 kiB
#define CIRCUITPY_BLE_CONFIG_SIZE (12*1024)
diff --git a/ports/nrf/boards/simmel/mpconfigboard.mk b/ports/nrf/boards/simmel/mpconfigboard.mk
index 36a6fadda..2bca2492f 100644
--- a/ports/nrf/boards/simmel/mpconfigboard.mk
+++ b/ports/nrf/boards/simmel/mpconfigboard.mk
@@ -24,6 +24,7 @@ CIRCUITPY_ROTARYIO = 0
CIRCUITPY_RTC = 1
CIRCUITPY_TOUCHIO = 0
CIRCUITPY_ULAB = 0
+CIRCUITPY_WATCHDOG = 1
# Enable micropython.native
#CIRCUITPY_ENABLE_MPY_NATIVE = 1
diff --git a/ports/nrf/boards/sparkfun_nrf52840_mini/README.md b/ports/nrf/boards/sparkfun_nrf52840_mini/README.md
index f80f1c27c..396e169a1 100644
--- a/ports/nrf/boards/sparkfun_nrf52840_mini/README.md
+++ b/ports/nrf/boards/sparkfun_nrf52840_mini/README.md
@@ -45,4 +45,4 @@ The nRF52840 Mini hardware layout is open source:
* [Schematic](https://cdn.sparkfun.com/assets/learn_tutorials/8/2/0/nrf52840-breakout-mdbt50q-v10.pdf)
* [Eagle Files](https://cdn.sparkfun.com/assets/learn_tutorials/8/2/0/nrf52840-breakout-mdbt50q-v10.zip)
-* [Hookup Guide](https://learn.sparkfun.com/tutorials/sparkfun-pro-nrf52840-mini-hookup-guide) \ No newline at end of file
+* [Hookup Guide](https://learn.sparkfun.com/tutorials/sparkfun-pro-nrf52840-mini-hookup-guide)
diff --git a/ports/nrf/common-hal/audiobusio/I2SOut.c b/ports/nrf/common-hal/audiobusio/I2SOut.c
index 2fa28afac..34eecf8d5 100644
--- a/ports/nrf/common-hal/audiobusio/I2SOut.c
+++ b/ports/nrf/common-hal/audiobusio/I2SOut.c
@@ -31,6 +31,7 @@
#include "common-hal/audiobusio/I2SOut.h"
#include "shared-bindings/audiobusio/I2SOut.h"
#include "shared-module/audiocore/__init__.h"
+#include "supervisor/shared/tick.h"
#include "py/obj.h"
#include "py/runtime.h"
@@ -158,7 +159,7 @@ static void i2s_buffer_fill(audiobusio_i2sout_obj_t* self) {
// Find the last frame of real audio data and replicate its samples until
// you have 32 bits worth, which is the fundamental unit of nRF I2S DMA
- if(buffer != buffer_start) {
+ if (buffer != buffer_start) {
if (self->bytes_per_sample == 1 && self->channel_count == 1) {
// For 8-bit mono, 4 copies of the final sample are required
self->hold_value = 0x01010101 * *(uint8_t*)(buffer-1);
@@ -211,6 +212,8 @@ void common_hal_audiobusio_i2sout_construct(audiobusio_i2sout_obj_t* self,
NRF_I2S->CONFIG.ALIGN = I2S_CONFIG_ALIGN_ALIGN_Left;
NRF_I2S->CONFIG.FORMAT = left_justified ? I2S_CONFIG_FORMAT_FORMAT_Aligned
: I2S_CONFIG_FORMAT_FORMAT_I2S;
+
+ supervisor_enable_tick();
}
bool common_hal_audiobusio_i2sout_deinited(audiobusio_i2sout_obj_t* self) {
@@ -230,6 +233,7 @@ void common_hal_audiobusio_i2sout_deinit(audiobusio_i2sout_obj_t* self) {
reset_pin_number(self->data_pin_number);
self->data_pin_number = 0xff;
instance = NULL;
+ supervisor_disable_tick();
}
void common_hal_audiobusio_i2sout_play(audiobusio_i2sout_obj_t* self,
@@ -340,5 +344,8 @@ void i2s_reset(void) {
NRF_I2S->PSEL.LRCK = 0xFFFFFFFF;
NRF_I2S->PSEL.SDOUT = 0xFFFFFFFF;
NRF_I2S->PSEL.SDIN = 0xFFFFFFFF;
+ if (instance) {
+ supervisor_disable_tick();
+ }
instance = NULL;
}
diff --git a/ports/nrf/common-hal/audiopwmio/PWMAudioOut.c b/ports/nrf/common-hal/audiopwmio/PWMAudioOut.c
index 89966b7da..7fec766fb 100644
--- a/ports/nrf/common-hal/audiopwmio/PWMAudioOut.c
+++ b/ports/nrf/common-hal/audiopwmio/PWMAudioOut.c
@@ -36,6 +36,7 @@
#include "shared-bindings/audiopwmio/PWMAudioOut.h"
#include "shared-bindings/microcontroller/__init__.h"
#include "shared-bindings/microcontroller/Pin.h"
+#include "supervisor/shared/tick.h"
#include "supervisor/shared/translate.h"
// TODO: This should be the same size as PWMOut.c:pwms[], but there's no trivial way to accomplish that
@@ -67,6 +68,7 @@ STATIC void activate_audiopwmout_obj(audiopwmio_pwmaudioout_obj_t *self) {
for (size_t i=0; i < MP_ARRAY_SIZE(active_audio); i++) {
if (!active_audio[i]) {
active_audio[i] = self;
+ supervisor_enable_tick();
break;
}
}
@@ -77,12 +79,16 @@ STATIC void deactivate_audiopwmout_obj(audiopwmio_pwmaudioout_obj_t *self) {
for (size_t i=0; i < MP_ARRAY_SIZE(active_audio); i++) {
if (active_audio[i] == self) {
active_audio[i] = NULL;
+ supervisor_disable_tick();
}
}
}
void audiopwmout_reset() {
for (size_t i=0; i < MP_ARRAY_SIZE(active_audio); i++) {
+ if (active_audio[i]) {
+ supervisor_disable_tick();
+ }
active_audio[i] = NULL;
}
}
diff --git a/ports/nrf/common-hal/digitalio/DigitalInOut.c b/ports/nrf/common-hal/digitalio/DigitalInOut.c
index c5a7a7dfb..2a72151b7 100644
--- a/ports/nrf/common-hal/digitalio/DigitalInOut.c
+++ b/ports/nrf/common-hal/digitalio/DigitalInOut.c
@@ -65,12 +65,13 @@ void common_hal_digitalio_digitalinout_switch_to_input(
common_hal_digitalio_digitalinout_set_pull(self, pull);
}
-void common_hal_digitalio_digitalinout_switch_to_output(
+digitalinout_result_t common_hal_digitalio_digitalinout_switch_to_output(
digitalio_digitalinout_obj_t *self, bool value,
digitalio_drive_mode_t drive_mode) {
common_hal_digitalio_digitalinout_set_drive_mode(self, drive_mode);
common_hal_digitalio_digitalinout_set_value(self, value);
+ return DIGITALINOUT_OK;
}
digitalio_direction_t common_hal_digitalio_digitalinout_get_direction(
@@ -92,7 +93,7 @@ bool common_hal_digitalio_digitalinout_get_value(
: nrf_gpio_pin_out_read(self->pin->number);
}
-void common_hal_digitalio_digitalinout_set_drive_mode(
+digitalinout_result_t common_hal_digitalio_digitalinout_set_drive_mode(
digitalio_digitalinout_obj_t *self,
digitalio_drive_mode_t drive_mode) {
nrf_gpio_cfg(self->pin->number,
@@ -101,6 +102,7 @@ void common_hal_digitalio_digitalinout_set_drive_mode(
NRF_GPIO_PIN_NOPULL,
drive_mode == DRIVE_MODE_OPEN_DRAIN ? NRF_GPIO_PIN_H0D1 : NRF_GPIO_PIN_H0H1,
NRF_GPIO_PIN_NOSENSE);
+ return DIGITALINOUT_OK;
}
digitalio_drive_mode_t common_hal_digitalio_digitalinout_get_drive_mode(
diff --git a/ports/nrf/common-hal/microcontroller/__init__.c b/ports/nrf/common-hal/microcontroller/__init__.c
index 90d97f868..f5caf68ef 100644
--- a/ports/nrf/common-hal/microcontroller/__init__.c
+++ b/ports/nrf/common-hal/microcontroller/__init__.c
@@ -94,7 +94,7 @@ void common_hal_mcu_on_next_reset(mcu_runmode_t runmode) {
void common_hal_mcu_reset(void) {
filesystem_flush();
- NVIC_SystemReset();
+ reset_cpu();
}
// The singleton microcontroller.Processor object, bound to microcontroller.cpu
@@ -106,7 +106,6 @@ const mcu_processor_obj_t common_hal_mcu_processor_obj = {
};
#if CIRCUITPY_INTERNAL_NVM_SIZE > 0
-
// The singleton nvm.ByteArray object.
const nvm_bytearray_obj_t common_hal_mcu_nvm_obj = {
.base = {
@@ -117,6 +116,17 @@ const nvm_bytearray_obj_t common_hal_mcu_nvm_obj = {
};
#endif
+#if CIRCUITPY_WATCHDOG
+// The singleton watchdog.WatchDogTimer object.
+watchdog_watchdogtimer_obj_t common_hal_mcu_watchdogtimer_obj = {
+ .base = {
+ .type = &watchdog_watchdogtimer_type,
+ },
+ .timeout = 0.0f,
+ .mode = WATCHDOGMODE_NONE,
+};
+#endif
+
STATIC const mp_rom_map_elem_t mcu_pin_globals_table[] = {
{ MP_ROM_QSTR(MP_QSTR_P0_00), MP_ROM_PTR(&pin_P0_00) },
{ MP_ROM_QSTR(MP_QSTR_P0_01), MP_ROM_PTR(&pin_P0_01) },
diff --git a/ports/nrf/common-hal/neopixel_write/__init__.h b/ports/nrf/common-hal/neopixel_write/__init__.h
index b8dce85ad..9366235af 100644
--- a/ports/nrf/common-hal/neopixel_write/__init__.h
+++ b/ports/nrf/common-hal/neopixel_write/__init__.h
@@ -29,4 +29,4 @@
void neopixel_write_reset(void);
-#endif // MICROPY_INCLUDED_STM32F4_COMMON_HAL_NEOPIXEL_WRITE_INIT_H \ No newline at end of file
+#endif // MICROPY_INCLUDED_STM32F4_COMMON_HAL_NEOPIXEL_WRITE_INIT_H
diff --git a/ports/nrf/common-hal/rotaryio/IncrementalEncoder.c b/ports/nrf/common-hal/rotaryio/IncrementalEncoder.c
index a0cfd48d5..28f563da6 100644
--- a/ports/nrf/common-hal/rotaryio/IncrementalEncoder.c
+++ b/ports/nrf/common-hal/rotaryio/IncrementalEncoder.c
@@ -49,9 +49,9 @@ static void _intr_handler(nrfx_gpiote_pin_t pin, nrf_gpiote_polarity_t action) {
self->state = new_state;
- // logic from the atmel-samd port: provides some damping and scales movement
- // down by 4:1.
- if (self->quarter >= 4) {
+ // logic from the atmel-samd port: provides some damping and scales movement
+ // down by 4:1.
+ if (self->quarter >= 4) {
self->position++;
self->quarter = 0;
} else if (self->quarter <= -4) {
diff --git a/ports/nrf/common-hal/rtc/RTC.c b/ports/nrf/common-hal/rtc/RTC.c
index 06345f589..93ba007c8 100644
--- a/ports/nrf/common-hal/rtc/RTC.c
+++ b/ports/nrf/common-hal/rtc/RTC.c
@@ -79,4 +79,3 @@ int common_hal_rtc_get_calibration(void) {
void common_hal_rtc_set_calibration(int calibration) {
mp_raise_NotImplementedError(translate("RTC calibration is not supported on this board"));
}
-
diff --git a/ports/nrf/common-hal/supervisor/Runtime.c b/ports/nrf/common-hal/supervisor/Runtime.c
index feab6987d..ea663f897 100755
--- a/ports/nrf/common-hal/supervisor/Runtime.c
+++ b/ports/nrf/common-hal/supervisor/Runtime.c
@@ -35,4 +35,3 @@ bool common_hal_get_serial_connected(void) {
bool common_hal_get_serial_bytes_available(void) {
return (bool) serial_bytes_available();
}
-
diff --git a/ports/nrf/common-hal/supervisor/__init__.c b/ports/nrf/common-hal/supervisor/__init__.c
index ac88556b4..6dca35fb5 100755
--- a/ports/nrf/common-hal/supervisor/__init__.c
+++ b/ports/nrf/common-hal/supervisor/__init__.c
@@ -37,4 +37,4 @@ const super_runtime_obj_t common_hal_supervisor_runtime_obj = {
.base = {
.type = &supervisor_runtime_type,
},
-}; \ No newline at end of file
+};
diff --git a/ports/nrf/common-hal/watchdog/WatchDogMode.c b/ports/nrf/common-hal/watchdog/WatchDogMode.c
new file mode 100644
index 000000000..e69de29bb
--- /dev/null
+++ b/ports/nrf/common-hal/watchdog/WatchDogMode.c
diff --git a/ports/nrf/common-hal/watchdog/WatchDogTimer.c b/ports/nrf/common-hal/watchdog/WatchDogTimer.c
new file mode 100644
index 000000000..bec0ac473
--- /dev/null
+++ b/ports/nrf/common-hal/watchdog/WatchDogTimer.c
@@ -0,0 +1,189 @@
+/*
+ * This file is part of the MicroPython project, http://micropython.org/
+ *
+ * The MIT License (MIT)
+ *
+ * Copyright (c) 2019 Nick Moore for Adafruit Industries
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
+
+
+#include <math.h>
+#include <string.h>
+
+#include "py/obj.h"
+#include "py/objproperty.h"
+#include "py/runtime.h"
+
+#include "common-hal/watchdog/WatchDogTimer.h"
+
+#include "shared-bindings/microcontroller/__init__.h"
+#include "shared-bindings/watchdog/__init__.h"
+#include "shared-bindings/watchdog/WatchDogTimer.h"
+
+#include "supervisor/port.h"
+
+#include "nrf/timers.h"
+#include "nrf_wdt.h"
+#include "nrfx_wdt.h"
+#include "nrfx_timer.h"
+
+STATIC uint8_t timer_refcount = 0;
+STATIC nrfx_timer_t *timer = NULL;
+STATIC nrfx_wdt_t wdt = NRFX_WDT_INSTANCE(0);
+STATIC nrfx_wdt_channel_id wdt_channel_id;
+
+STATIC void watchdogtimer_timer_event_handler(nrf_timer_event_t event_type, void *p_context) {
+ watchdog_watchdogtimer_obj_t *self = MP_OBJ_TO_PTR(p_context);
+ if (event_type != NRF_TIMER_EVENT_COMPARE0) {
+ // Spurious event.
+ return;
+ }
+
+ // If the timer hits without being cleared, pause the timer and raise an exception.
+ nrfx_timer_pause(timer);
+ self->mode = WATCHDOGMODE_NONE;
+ mp_obj_exception_clear_traceback(MP_OBJ_FROM_PTR(&mp_watchdog_timeout_exception));
+ MP_STATE_VM(mp_pending_exception) = &mp_watchdog_timeout_exception;
+#if MICROPY_ENABLE_SCHEDULER
+ if (MP_STATE_VM(sched_state) == MP_SCHED_IDLE) {
+ MP_STATE_VM(sched_state) = MP_SCHED_PENDING;
+ }
+#endif
+}
+
+static void timer_free(void) {
+ timer_refcount--;
+ if (timer_refcount == 0) {
+ nrf_peripherals_free_timer(timer);
+ timer = NULL;
+ }
+}
+
+// This function is called if the timer expires. The system will reboot
+// in 1/16384 of a second. Issue a reboot ourselves so we can do any
+// cleanup necessary.
+STATIC void watchdogtimer_watchdog_event_handler(void) {
+ reset_cpu();
+}
+
+void common_hal_watchdog_feed(watchdog_watchdogtimer_obj_t *self) {
+ if (self->mode == WATCHDOGMODE_RESET) {
+ nrfx_wdt_feed(&wdt);
+ } else if (self->mode == WATCHDOGMODE_RAISE) {
+ nrfx_timer_clear(timer);
+ }
+}
+
+void common_hal_watchdog_deinit(watchdog_watchdogtimer_obj_t *self) {
+ if (timer) {
+ timer_free();
+ }
+ self->mode = WATCHDOGMODE_NONE;
+}
+
+void watchdog_reset(void) {
+ common_hal_watchdog_deinit(&common_hal_mcu_watchdogtimer_obj);
+}
+
+mp_float_t common_hal_watchdog_get_timeout(watchdog_watchdogtimer_obj_t *self) {
+ return self->timeout;
+}
+
+void common_hal_watchdog_set_timeout(watchdog_watchdogtimer_obj_t *self, mp_float_t timeout) {
+ if (self->mode == WATCHDOGMODE_RAISE) {
+ // If the WatchDogTimer is already running in "RAISE" mode, reset the timer
+ // with the new value.
+ uint64_t ticks = timeout * 31250ULL;
+ if (ticks > UINT32_MAX) {
+ mp_raise_ValueError(translate("timeout duration exceeded the maximum supported value"));
+ }
+ nrfx_timer_clear(timer);
+ nrfx_timer_compare(timer, NRF_TIMER_CC_CHANNEL0, ticks, true);
+ }
+
+ self->timeout = timeout;
+}
+
+watchdog_watchdogmode_t common_hal_watchdog_get_mode(watchdog_watchdogtimer_obj_t *self) {
+ return self->mode;
+}
+
+void common_hal_watchdog_set_mode(watchdog_watchdogtimer_obj_t *self, watchdog_watchdogmode_t new_mode) {
+ watchdog_watchdogmode_t current_mode = self->mode;
+
+ if (new_mode == WATCHDOGMODE_RAISE) {
+ if (timer_refcount == 0) {
+ timer = nrf_peripherals_allocate_timer_or_throw();
+ }
+ timer_refcount++;
+
+ nrfx_timer_config_t timer_config = {
+ .frequency = NRF_TIMER_FREQ_31250Hz,
+ .mode = NRF_TIMER_MODE_TIMER,
+ .bit_width = NRF_TIMER_BIT_WIDTH_32,
+ .interrupt_priority = NRFX_TIMER_DEFAULT_CONFIG_IRQ_PRIORITY,
+ .p_context = self,
+ };
+
+ nrfx_timer_init(timer, &timer_config, &watchdogtimer_timer_event_handler);
+
+ uint64_t ticks = nrfx_timer_ms_to_ticks(timer, self->timeout * 1000);
+ if (ticks > UINT32_MAX) {
+ mp_raise_ValueError(translate("timeout duration exceeded the maximum supported value"));
+ }
+
+ // true enables interrupt.
+ nrfx_timer_clear(timer);
+ nrfx_timer_compare(timer, NRF_TIMER_CC_CHANNEL0, ticks, true);
+ nrfx_timer_resume(timer);
+
+ } else if (new_mode == WATCHDOGMODE_RESET) {
+ uint64_t ticks = self->timeout * 1000.0f;
+ if (ticks > UINT32_MAX) {
+ mp_raise_ValueError(translate("timeout duration exceeded the maximum supported value"));
+ }
+
+ nrfx_wdt_config_t config = {
+ .reload_value = ticks, // in units of ms
+ .behaviour = NRF_WDT_BEHAVIOUR_RUN_SLEEP,
+ NRFX_WDT_IRQ_CONFIG
+ };
+
+ nrfx_err_t err_code;
+ err_code = nrfx_wdt_init(&wdt, &config, watchdogtimer_watchdog_event_handler);
+ if (err_code != NRFX_SUCCESS) {
+ mp_raise_OSError(1);
+ }
+ err_code = nrfx_wdt_channel_alloc(&wdt, &wdt_channel_id);
+ if (err_code != NRFX_SUCCESS) {
+ mp_raise_OSError(1);
+ }
+ nrfx_wdt_enable(&wdt);
+ nrfx_wdt_feed(&wdt);
+ }
+
+ // If we just switched away from RAISE, disable the timmer.
+ if (current_mode == WATCHDOGMODE_RAISE && new_mode != WATCHDOGMODE_RAISE) {
+ timer_free();
+ }
+
+ self->mode = new_mode;
+}
diff --git a/ports/nrf/common-hal/watchdog/WatchDogTimer.h b/ports/nrf/common-hal/watchdog/WatchDogTimer.h
new file mode 100644
index 000000000..8d6df934e
--- /dev/null
+++ b/ports/nrf/common-hal/watchdog/WatchDogTimer.h
@@ -0,0 +1,44 @@
+/*
+ * This file is part of the MicroPython project, http://micropython.org/
+ *
+ * The MIT License (MIT)
+ *
+ * Copyright (c) 2018 Noralf Trønnes
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
+
+#ifndef MICROPY_INCLUDED_NRF_COMMON_HAL_WATCHDOG_WATCHDOGTIMER_H
+#define MICROPY_INCLUDED_NRF_COMMON_HAL_WATCHDOG_WATCHDOGTIMER_H
+
+#include "py/obj.h"
+#include "shared-bindings/watchdog/WatchDogMode.h"
+#include "shared-bindings/watchdog/WatchDogTimer.h"
+
+struct _watchdog_watchdogtimer_obj_t {
+ mp_obj_base_t base;
+ mp_float_t timeout;
+ watchdog_watchdogmode_t mode;
+};
+
+// This needs to be called in order to disable the watchdog if it's set to
+// "RAISE". If set to "RESET", then the watchdog cannot be reset.
+void watchdog_reset(void);
+
+#endif // MICROPY_INCLUDED_NRF_COMMON_HAL_WATCHDOG_WATCHDOGTIMER_H
diff --git a/ports/nrf/common-hal/watchdog/__init__.c b/ports/nrf/common-hal/watchdog/__init__.c
new file mode 100644
index 000000000..79875d127
--- /dev/null
+++ b/ports/nrf/common-hal/watchdog/__init__.c
@@ -0,0 +1,25 @@
+/*
+ * This file is part of the MicroPython project, http://micropython.org/
+ *
+ * The MIT License (MIT)
+ *
+ * Copyright (c) 2019 Nick Moore for Adafruit Industries
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
diff --git a/ports/nrf/common-hal/watchdog/__init__.h b/ports/nrf/common-hal/watchdog/__init__.h
new file mode 100644
index 000000000..de19bdae4
--- /dev/null
+++ b/ports/nrf/common-hal/watchdog/__init__.h
@@ -0,0 +1,30 @@
+/*
+ * This file is part of the MicroPython project, http://micropython.org/
+ *
+ * The MIT License (MIT)
+ *
+ * Copyright (c) 2018 Noralf Trønnes
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
+
+#ifndef MICROPY_INCLUDED_NRF_COMMON_HAL_WATCHDOG___INIT___H
+#define MICROPY_INCLUDED_NRF_COMMON_HAL_WATCHDOG___INIT___H
+
+#endif // MICROPY_INCLUDED_NRF_COMMON_HAL_WATCHDOG___INIT___H
diff --git a/ports/nrf/examples/ubluepy_eddystone.py b/ports/nrf/examples/ubluepy_eddystone.py
index baf25ba4b..426a4aa55 100644
--- a/ports/nrf/examples/ubluepy_eddystone.py
+++ b/ports/nrf/examples/ubluepy_eddystone.py
@@ -53,6 +53,6 @@ def generate_eddystone_adv_packet(url):
return packet
def start():
- adv_packet = generate_eddystone_adv_packet("micropython")
+ adv_packet = generate_eddystone_adv_packet("micropython")
p = Peripheral()
- p.advertise(data=adv_packet, connectable=False) \ No newline at end of file
+ p.advertise(data=adv_packet, connectable=False)
diff --git a/ports/nrf/examples/ubluepy_scan.py b/ports/nrf/examples/ubluepy_scan.py
index ab11661cc..c0a7d05a3 100644
--- a/ports/nrf/examples/ubluepy_scan.py
+++ b/ports/nrf/examples/ubluepy_scan.py
@@ -19,7 +19,7 @@ def get_device_names(scan_entries):
def find_device_by_name(name):
s = Scanner()
scan_res = s.scan(100)
-
+
device_names = get_device_names(scan_res)
for dev in device_names:
if name == dev[1]:
@@ -30,9 +30,9 @@ def find_device_by_name(name):
# ... print("address:", res.addr())
# ... print("address type:", res.addr_type())
# ... print("rssi:", res.rssi())
-# ...
-# ...
-# ...
+# ...
+# ...
+# ...
# address: c2:73:61:89:24:45
# address type: 1
# rssi: -26
diff --git a/ports/nrf/examples/ubluepy_temp.py b/ports/nrf/examples/ubluepy_temp.py
index e5c157dbb..118407af5 100644
--- a/ports/nrf/examples/ubluepy_temp.py
+++ b/ports/nrf/examples/ubluepy_temp.py
@@ -31,7 +31,7 @@ def event_handler(id, handle, data):
global periph
global serv_env_sense
global notif_enabled
-
+
if id == constants.EVT_GAP_CONNECTED:
# indicated 'connected'
LED(1).on()
@@ -50,7 +50,7 @@ def event_handler(id, handle, data):
notif_enabled = True
# start low power timer
rtc.start()
- else:
+ else:
notif_enabled = False
# stop low power timer
rtc.stop()
@@ -68,7 +68,7 @@ def send_temp(timer_id):
# start off with LED(1) off
LED(1).off()
-# use RTC1 as RTC0 is used by bluetooth stack
+# use RTC1 as RTC0 is used by bluetooth stack
# set up RTC callback every 5 second
rtc = RTC(1, period=5, mode=RTC.PERIODIC, callback=send_temp)
@@ -76,7 +76,7 @@ notif_enabled = False
uuid_env_sense = UUID("0x181A") # Environmental Sensing service
uuid_temp = UUID("0x2A6E") # Temperature characteristic
-
+
serv_env_sense = Service(uuid_env_sense)
temp_props = Characteristic.PROP_NOTIFY | Characteristic.PROP_READ
@@ -89,4 +89,3 @@ periph = Peripheral()
periph.addService(serv_env_sense)
periph.setConnectionHandler(event_handler)
periph.advertise(device_name="micr_temp", services=[serv_env_sense])
-
diff --git a/ports/nrf/gccollect.c b/ports/nrf/gccollect.c
index b7aa57a55..3661daa53 100644
--- a/ports/nrf/gccollect.c
+++ b/ports/nrf/gccollect.c
@@ -43,7 +43,7 @@ void gc_collect(void) {
gc_collect_start();
mp_uint_t sp = get_msp(); // Get stack pointer
-
+
// trace the stack, including the registers (since they live on the stack in this function)
gc_collect_root((void**)sp, ((uint32_t)&_ram_end - sp) / sizeof(uint32_t));
diff --git a/ports/nrf/mpconfigport.mk b/ports/nrf/mpconfigport.mk
index a9ad11bd4..dda9b2436 100644
--- a/ports/nrf/mpconfigport.mk
+++ b/ports/nrf/mpconfigport.mk
@@ -37,6 +37,7 @@ CIRCUITPY_RGBMATRIX ?= 1
CIRCUITPY_FRAMEBUFFERIO ?= 1
CIRCUITPY_COUNTIO = 0
+CIRCUITPY_WATCHDOG ?= 1
# nRF52840-specific
@@ -45,6 +46,9 @@ MCU_SERIES = m4
MCU_VARIANT = nrf52
MCU_SUB_VARIANT = nrf52840
+# Fits on nrf52840 but space is tight on nrf52833.
+CIRCUITPY_AESIO ?= 1
+
SD ?= s140
SOFTDEV_VERSION ?= 6.1.0
diff --git a/ports/nrf/nrfx_config.h b/ports/nrf/nrfx_config.h
index 7a7f2e6d6..b528a6032 100644
--- a/ports/nrf/nrfx_config.h
+++ b/ports/nrf/nrfx_config.h
@@ -122,4 +122,11 @@
// NVM controller
#define NRFX_NVMC_ENABLED 1
+// Watchdog timer
+#define NRFX_WDT_ENABLED 1
+#define NRFX_WDT0_ENABLED 1
+// This IRQ indicates the system will reboot shortly, so give
+// it a high priority.
+#define NRFX_WDT_DEFAULT_CONFIG_IRQ_PRIORITY 2
+
#endif // NRFX_CONFIG_H__
diff --git a/ports/nrf/nrfx_glue.h b/ports/nrf/nrfx_glue.h
index 345de3870..9f91b72a1 100644
--- a/ports/nrf/nrfx_glue.h
+++ b/ports/nrf/nrfx_glue.h
@@ -180,17 +180,17 @@ static inline bool _NRFX_IRQ_IS_PENDING(IRQn_Type irq_number)
return (NVIC_GetPendingIRQ(irq_number) == 1);
}
-//#include <nordic_common.h>
-//#include <app_util_platform.h>
+void common_hal_mcu_disable_interrupts(void);
+void common_hal_mcu_enable_interrupts(void);
/**
* @brief Macro for entering into a critical section.
*/
-#define NRFX_CRITICAL_SECTION_ENTER() CRITICAL_REGION_ENTER()
+#define NRFX_CRITICAL_SECTION_ENTER() common_hal_mcu_disable_interrupts()
/**
* @brief Macro for exiting from a critical section.
*/
-#define NRFX_CRITICAL_SECTION_EXIT() CRITICAL_REGION_EXIT()
+#define NRFX_CRITICAL_SECTION_EXIT() common_hal_mcu_enable_interrupts()
//------------------------------------------------------------------------------
diff --git a/ports/nrf/peripherals/nrf/nvm.c b/ports/nrf/peripherals/nrf/nvm.c
index 63b168f14..dc50e2eef 100644
--- a/ports/nrf/peripherals/nrf/nvm.c
+++ b/ports/nrf/peripherals/nrf/nvm.c
@@ -40,6 +40,8 @@
STATIC bool sd_is_enabled(void) {
uint8_t sd_en = 0;
+ if (__get_PRIMASK())
+ return false;
(void) sd_softdevice_is_enabled(&sd_en);
return sd_en;
}
diff --git a/ports/nrf/supervisor/port.c b/ports/nrf/supervisor/port.c
index ea09115f7..aee2d63e1 100644
--- a/ports/nrf/supervisor/port.c
+++ b/ports/nrf/supervisor/port.c
@@ -50,9 +50,13 @@
#include "common-hal/pulseio/PulseIn.h"
#include "common-hal/rtc/RTC.h"
#include "common-hal/neopixel_write/__init__.h"
+#include "common-hal/watchdog/WatchDogTimer.h"
+#include "shared-bindings/microcontroller/__init__.h"
#include "shared-bindings/rtc/__init__.h"
+#include "lib/tinyusb/src/device/usbd.h"
+
#ifdef CIRCUITPY_AUDIOBUSIO
#include "common-hal/audiobusio/I2SOut.h"
#endif
@@ -74,13 +78,19 @@ const nrfx_rtc_config_t rtc_config = {
.interrupt_priority = 6
};
-static volatile uint64_t overflowed_ticks = 0;
+#define OVERFLOW_CHECK_PREFIX 0x2cad564f
+#define OVERFLOW_CHECK_SUFFIX 0x11343ef7
+static volatile struct {
+ uint32_t prefix;
+ uint64_t overflowed_ticks;
+ uint32_t suffix;
+} overflow_tracker __attribute__((section(".uninitialized")));
void rtc_handler(nrfx_rtc_int_type_t int_type) {
if (int_type == NRFX_RTC_INT_OVERFLOW) {
// Our RTC is 24 bits and we're clocking it at 32.768khz which is 32 (2 ** 5) subticks per
// tick.
- overflowed_ticks += (1L<< (24 - 5));
+ overflow_tracker.overflowed_ticks += (1L<< (24 - 5));
} else if (int_type == NRFX_RTC_INT_TICK && nrfx_rtc_counter_get(&rtc_instance) % 32 == 0) {
// Do things common to all ports when the tick occurs
supervisor_tick();
@@ -97,6 +107,17 @@ void tick_init(void) {
nrfx_rtc_init(&rtc_instance, &rtc_config, rtc_handler);
nrfx_rtc_enable(&rtc_instance);
nrfx_rtc_overflow_enable(&rtc_instance, true);
+
+ // If the check prefix and suffix aren't correct, then the structure
+ // in memory isn't correct and the clock will be wildly wrong. Initialize
+ // the prefix and suffix so that we know the value is correct, and reset
+ // the time to 0.
+ if (overflow_tracker.prefix != OVERFLOW_CHECK_PREFIX ||
+ overflow_tracker.suffix != OVERFLOW_CHECK_SUFFIX) {
+ overflow_tracker.prefix = OVERFLOW_CHECK_PREFIX;
+ overflow_tracker.suffix = OVERFLOW_CHECK_SUFFIX;
+ overflow_tracker.overflowed_ticks = 0;
+ }
}
safe_mode_t port_init(void) {
@@ -128,6 +149,21 @@ safe_mode_t port_init(void) {
analogin_init();
#endif
+ // If the board was reset by the WatchDogTimer, we may
+ // need to boot into safe mode. Reset the RESETREAS bit
+ // for the WatchDogTimer so we don't encounter this the
+ // next time we reboot.
+ if (NRF_POWER->RESETREAS & POWER_RESETREAS_DOG_Msk) {
+ NRF_POWER->RESETREAS = POWER_RESETREAS_DOG_Msk;
+ uint32_t usb_reg = NRF_POWER->USBREGSTATUS;
+
+ // If USB is connected, then the user might be editing `code.py`,
+ // in which case we should reboot into Safe Mode.
+ if (usb_reg & POWER_USBREGSTATUS_VBUSDETECT_Msk) {
+ return WATCHDOG_RESET;
+ }
+ }
+
return NO_SAFE_MODE;
}
@@ -171,6 +207,10 @@ void reset_port(void) {
bleio_reset();
#endif
+#if CIRCUITPY_WATCHDOG
+ watchdog_reset();
+#endif
+
reset_all_pins();
}
@@ -182,6 +222,10 @@ void reset_to_bootloader(void) {
}
void reset_cpu(void) {
+ // We're getting ready to reset, so save the counter off.
+ // This counter will get reset to zero during the reboot.
+ uint32_t ticks = nrfx_rtc_counter_get(&rtc_instance);
+ overflow_tracker.overflowed_ticks += ticks / 32;
NVIC_SystemReset();
}
@@ -225,7 +269,7 @@ uint64_t port_get_raw_ticks(uint8_t* subticks) {
if (subticks != NULL) {
*subticks = (rtc % 32);
}
- return overflowed_ticks + rtc / 32;
+ return overflow_tracker.overflowed_ticks + rtc / 32;
}
// Enable 1/1024 second tick.
@@ -264,7 +308,17 @@ void port_sleep_until_interrupt(void) {
sd_app_evt_wait();
} else {
// Call wait for interrupt ourselves if the SD isn't enabled.
- __WFI();
+ // Note that `wfi` should be called with interrupts disabled,
+ // to ensure that the queue is properly drained. The `wfi`
+ // instruction will returned as long as an interrupt is
+ // available, even though the actual handler won't fire until
+ // we re-enable interrupts.
+ common_hal_mcu_disable_interrupts();
+ if (!tud_task_event_ready()) {
+ __DSB();
+ __WFI();
+ }
+ common_hal_mcu_enable_interrupts();
}
}