Skip to content

Commit 523dee3

Browse files
committed
get qspi work with Feather nrf52840
1 parent 6cb638c commit 523dee3

File tree

14 files changed

+105
-135
lines changed

14 files changed

+105
-135
lines changed

cores/nRF5/common_func.h

Lines changed: 21 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -115,7 +115,7 @@
115115
// DEBUG HELPER
116116
//--------------------------------------------------------------------+
117117
#if CFG_DEBUG == 2
118-
#define malloc_named( name, size ) ({ ::printf("[malloc] %s : %d\r\n", name, size); malloc(size); })
118+
#define malloc_named( name, size ) ({ PRINTF("[malloc] %s : %d\r\n", name, size); malloc(size); })
119119
#else
120120
#define malloc_named( name, size ) malloc ( size )
121121
#endif
@@ -140,38 +140,44 @@ const char* dbg_err_str(int32_t err_id); // TODO move to other place
140140

141141
#if CFG_DEBUG
142142

143-
#define PRINT_LOCATION() ::printf("%s: %d:\n", __PRETTY_FUNCTION__, __LINE__)
144-
#define PRINT_MESS(x) ::printf("%s: %d: %s \n" , __FUNCTION__, __LINE__, (char*)(x))
145-
#define PRTNT_HEAP() if (CFG_DEBUG == 3) ::printf("\n%s: %d: Heap free: %d\n", __FUNCTION__, __LINE__, util_heap_get_free_size())
146-
#define PRINT_STR(x) ::printf("%s: %d: " #x " = %s\n" , __FUNCTION__, __LINE__, (char*)(x) )
147-
#define PRINT_INT(x) ::printf("%s: %d: " #x " = %ld\n" , __FUNCTION__, __LINE__, (uint32_t) (x) )
143+
#if __cplusplus
144+
#define PRINTF ::printf
145+
#else
146+
#define PRINTF printf
147+
#endif
148+
149+
#define PRINT_LOCATION() PRINTF("%s: %d:\n", __PRETTY_FUNCTION__, __LINE__)
150+
#define PRINT_MESS(x) PRINTF("%s: %d: %s \n" , __FUNCTION__, __LINE__, (char*)(x))
151+
#define PRTNT_HEAP() if (CFG_DEBUG == 3) PRINTF("\n%s: %d: Heap free: %d\n", __FUNCTION__, __LINE__, util_heap_get_free_size())
152+
#define PRINT_STR(x) PRINTF("%s: %d: " #x " = %s\n" , __FUNCTION__, __LINE__, (char*)(x) )
153+
#define PRINT_INT(x) PRINTF("%s: %d: " #x " = %ld\n" , __FUNCTION__, __LINE__, (uint32_t) (x) )
148154

149155
#define PRINT_HEX(x) \
150156
do {\
151-
::printf("%s: %d: " #x " = 0x", __PRETTY_FUNCTION__, __LINE__);\
157+
PRINTF("%s: %d: " #x " = 0x", __PRETTY_FUNCTION__, __LINE__);\
152158
char fmt[] = "%00X\n";\
153159
fmt[2] += 2*sizeof(x); /* Hex with correct size */\
154-
::printf(fmt, (x) );\
160+
PRINTF(fmt, (x) );\
155161
}while(0)
156162

157163
#define PRINT_BUFFER(buf, n) \
158164
do {\
159165
uint8_t const* p8 = (uint8_t const*) (buf);\
160-
::printf(#buf ": ");\
161-
for(uint32_t i=0; i<(n); i++) ::printf("%02x ", p8[i]);\
162-
::printf("\n");\
166+
PRINTF(#buf ": ");\
167+
for(uint32_t i=0; i<(n); i++) PRINTF("%02x ", p8[i]);\
168+
PRINTF("\n");\
163169
}while(0)
164170

165171
#define ADALOG(tag, ...) \
166172
do { \
167-
if ( tag ) ::printf("[%-6s] ", tag);\
168-
::printf(__VA_ARGS__);\
169-
::printf("\n");\
173+
if ( tag ) PRINTF("[%-6s] ", tag);\
174+
PRINTF(__VA_ARGS__);\
175+
PRINTF("\n");\
170176
}while(0)
171177

172178
#define ADALOG_BUFFER(_tag, _buf, _n) \
173179
do {\
174-
if ( _tag ) ::printf("%-6s: len = %d\n", _tag, _n);\
180+
if ( _tag ) PRINTF("%-6s: len = %d\n", _tag, _n);\
175181
dbgDumpMemory(_buf, 1, _n, true);\
176182
}while(0)
177183

cores/nRF5/flash/flash_devices.h

Lines changed: 12 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,7 @@
11
/*
2-
* This file is part of the MicroPython project, http://micropython.org/
3-
*
42
* The MIT License (MIT)
53
*
6-
* Copyright (c) 2018 hathach for Adafruit Industries
4+
* Copyright (c) 2019 Ha Thach for Adafruit Industries
75
*
86
* Permission is hereby granted, free of charge, to any person obtaining a copy
97
* of this software and associated documentation files (the "Software"), to deal
@@ -37,29 +35,35 @@
3735
typedef struct {
3836
uint32_t total_size;
3937

40-
// Three response bytes to 0x90 JEDEC REMS ID command.
38+
// Response bytes to 0x90 JEDEC REMS ID command.
4139
uint8_t manufacturer_id;
4240
uint8_t device_id;
4341

44-
// Status register value enable quad mode
42+
// Status register value to enable quad mode
4543
uint16_t status_quad_enable;
4644

45+
// Working frequency
46+
uint8_t freq;
47+
4748
} qspi_flash_device_t;
4849

4950
// Settings for the Gigadevice GD25Q16C 2MiB SPI flash.
50-
// Datasheet: http://www.gigadevice.com/wp-content/uploads/2017/12/DS-00086-GD25Q16C-Rev2.6.pdf
51+
// Datasheet: http://www.gigadevice.com/datasheet/gd25q16c/
52+
// Can only work reliably with nrf5x at 16Mhz, even though it should work up to 104 MHz
5153
#define GD25Q16C {\
5254
.total_size = 2*1024*1024, \
5355
.manufacturer_id = 0xc8, \
5456
.device_id = 0x14, \
55-
.status_quad_enable = (1 << 9)\
57+
.status_quad_enable = (1 << 9),\
58+
.freq = NRF_QSPI_FREQ_32MDIV2 \
5659
}
5760

5861
#define MX25R6435F {\
5962
.total_size = 8*1024*1024, \
6063
.manufacturer_id = 0xc2, \
6164
.device_id = 0x17, \
62-
.status_quad_enable = (1 << 6)\
65+
.status_quad_enable = (1 << 6),\
66+
.freq = NRF_QSPI_FREQ_32MDIV1 \
6367
}
6468

6569
#ifdef __cplusplus

cores/nRF5/flash/flash_qspi.c

Lines changed: 58 additions & 94 deletions
Original file line numberDiff line numberDiff line change
@@ -1,38 +1,26 @@
1-
/**************************************************************************/
2-
/*!
3-
@file flash_qspi.c
4-
@author hathach (tinyusb.org)
5-
6-
@section LICENSE
7-
8-
Software License Agreement (BSD License)
9-
10-
Copyright (c) 2018, Adafruit Industries (adafruit.com)
11-
All rights reserved.
12-
13-
Redistribution and use in source and binary forms, with or without
14-
modification, are permitted provided that the following conditions are met:
15-
1. Redistributions of source code must retain the above copyright
16-
notice, this list of conditions and the following disclaimer.
17-
2. Redistributions in binary form must reproduce the above copyright
18-
notice, this list of conditions and the following disclaimer in the
19-
documentation and/or other materials provided with the distribution.
20-
3. Neither the name of the copyright holders nor the
21-
names of its contributors may be used to endorse or promote products
22-
derived from this software without specific prior written permission.
23-
24-
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS ''AS IS'' AND ANY
25-
EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
26-
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
27-
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY
28-
DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
29-
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
30-
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
31-
ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
32-
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
33-
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
34-
*/
35-
/**************************************************************************/
1+
/*
2+
* The MIT License (MIT)
3+
*
4+
* Copyright (c) 2019 Ha Thach for Adafruit Industries
5+
*
6+
* Permission is hereby granted, free of charge, to any person obtaining a copy
7+
* of this software and associated documentation files (the "Software"), to deal
8+
* in the Software without restriction, including without limitation the rights
9+
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10+
* copies of the Software, and to permit persons to whom the Software is
11+
* furnished to do so, subject to the following conditions:
12+
*
13+
* The above copyright notice and this permission notice shall be included in
14+
* all copies or substantial portions of the Software.
15+
*
16+
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17+
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18+
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19+
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20+
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21+
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
22+
* THE SOFTWARE.
23+
*/
3624

3725
#ifdef NRF52840_XXAA
3826

@@ -42,14 +30,7 @@
4230
#include "flash_cache.h"
4331
#include "nrfx_qspi.h"
4432

45-
#define _VALID_PIN(n) (defined(PIN_QSPI_DATA##n) && (PIN_QSPI_DATA##n != 0xff))
46-
47-
#define QSPI_FLASH_MODE \
48-
(( _VALID_PIN(0) && _VALID_PIN(1) && _VALID_PIN(2) && _VALID_PIN(3) ) ? 4 : \
49-
( _VALID_PIN(0) && _VALID_PIN(1) ) ? 2 : \
50-
( _VALID_PIN(0) ) ? 1 : 0)
51-
52-
#if QSPI_FLASH_MODE
33+
#ifdef EXTERNAL_FLASH_DEVICES
5334

5435
//--------------------------------------------------------------------+
5536
// MACRO TYPEDEF CONSTANT ENUM DECLARATION
@@ -59,20 +40,11 @@ enum
5940
QSPI_CMD_RSTEN = 0x66,
6041
QSPI_CMD_RST = 0x99,
6142
QSPI_CMD_WRSR = 0x01,
62-
QSPI_CMD_READID = 0x90
43+
QSPI_CMD_REMS = 0x90,
6344
};
6445

65-
// If Flash device is not specified, support all devices in flash_devices.h
66-
#ifdef EXTERNAL_FLASH_DEVICES
6746
const qspi_flash_device_t _flash_devices_arr[] = { EXTERNAL_FLASH_DEVICES };
68-
#else
69-
const qspi_flash_device_t _flash_devices_arr[] = { GD25Q16C, MX25R6435F };
70-
#endif
71-
72-
enum
73-
{
74-
FLASH_DEVICE_COUNT = arrcount(_flash_devices_arr)
75-
};
47+
enum { FLASH_DEVICE_COUNT = arrcount(_flash_devices_arr) };
7648

7749
const qspi_flash_device_t* _flash_dev = NULL;
7850

@@ -85,12 +57,12 @@ static bool fal_qspi_verify (uint32_t addr, void const * buf, uint32_t len);
8557
static uint8_t _cache_buffer[FLASH_CACHE_SIZE] __attribute__((aligned(4)));
8658

8759
static flash_cache_t _cache = {
88-
.erase = fal_qspi_erase,
89-
.program = fal_qspi_program,
90-
.read = fal_qspi_read,
91-
.verify = fal_qspi_verify,
60+
.erase = fal_qspi_erase,
61+
.program = fal_qspi_program,
62+
.read = fal_qspi_read,
63+
.verify = fal_qspi_verify,
9264
.cache_addr = FLASH_CACHE_INVALID_ADDR,
93-
.cache_buf = _cache_buffer
65+
.cache_buf = _cache_buffer
9466
};
9567

9668
static SemaphoreHandle_t _qspi_mutex;
@@ -155,38 +127,25 @@ void flash_qspi_init (void)
155127
.sck_pin = g_ADigitalPinMap[PIN_QSPI_SCK],
156128
.csn_pin = g_ADigitalPinMap[PIN_QSPI_CS],
157129
.io0_pin = g_ADigitalPinMap[PIN_QSPI_DATA0],
158-
.io1_pin = NRF_QSPI_PIN_NOT_CONNECTED,
159-
.io2_pin = NRF_QSPI_PIN_NOT_CONNECTED,
160-
.io3_pin = NRF_QSPI_PIN_NOT_CONNECTED,
161-
130+
.io1_pin = g_ADigitalPinMap[PIN_QSPI_DATA1],
131+
.io2_pin = g_ADigitalPinMap[PIN_QSPI_DATA2],
132+
.io3_pin = g_ADigitalPinMap[PIN_QSPI_DATA3],
162133
},
163134
.prot_if = {
164-
.readoc = NRF_QSPI_READOC_FASTREAD,
165-
.writeoc = NRF_QSPI_WRITEOC_PP,
135+
.readoc = NRF_QSPI_READOC_READ4IO,
136+
.writeoc = NRF_QSPI_WRITEOC_PP4O,
166137
.addrmode = NRF_QSPI_ADDRMODE_24BIT,
167138
.dpmconfig = false
168139
},
169140
.phy_if = {
170-
.sck_freq = NRF_QSPI_FREQ_32MDIV1,
171-
.sck_delay = 1, // min time CS must stay high before going low again. in unit of 62.5 ns
141+
.sck_freq = NRF_QSPI_FREQ_32MDIV16, // start with low 2 Mhz speed
142+
.sck_delay = 10, // min time CS must stay high before going low again. in unit of 62.5 ns
172143
.spi_mode = NRF_QSPI_MODE_0,
173144
.dpmen = false
174145
},
175146
.irq_priority = 7,
176147
};
177148

178-
#if QSPI_FLASH_MODE == 2
179-
qspi_cfg.pins.io1_pin = g_ADigitalPinMap[PIN_QSPI_DATA1];
180-
qspi_cfg.prot_if.readoc = NRF_QSPI_READOC_READ2IO;
181-
qspi_cfg.prot_if.writeoc = NRF_QSPI_WRITEOC_PP2O;
182-
#elif QSPI_FLASH_MODE == 4
183-
qspi_cfg.pins.io1_pin = g_ADigitalPinMap[PIN_QSPI_DATA1];
184-
qspi_cfg.pins.io2_pin = g_ADigitalPinMap[PIN_QSPI_DATA2];
185-
qspi_cfg.pins.io3_pin = g_ADigitalPinMap[PIN_QSPI_DATA3];
186-
qspi_cfg.prot_if.readoc = NRF_QSPI_READOC_READ4IO;
187-
qspi_cfg.prot_if.writeoc = NRF_QSPI_WRITEOC_PP4O;
188-
#endif
189-
190149
// No callback for blocking API
191150
nrfx_qspi_init(&qspi_cfg, NULL, NULL);
192151

@@ -212,25 +171,23 @@ void flash_qspi_init (void)
212171
NRFX_DELAY_US(100); // wait for flash device to reset
213172

214173
// Send (Read ID + 3 dummy bytes) + Receive 2 bytes of (Manufacture + Device ID)
215-
uint8_t dummy[6] = { 0 };
216-
uint8_t id_resp[6] = { 0 };
217-
cinstr_cfg.opcode = QSPI_CMD_READID;
174+
uint8_t dummy[5] = { 0 };
175+
uint8_t id_resp[5] = { 0 };
176+
cinstr_cfg.opcode = QSPI_CMD_REMS;
218177
cinstr_cfg.length = 6;
219178

220-
// Bug with -nrf_qspi_cinstrdata_get() didn't combine data.
221-
// https://devzone.nordicsemi.com/f/nordic-q-a/38540/bug-nrf_qspi_cinstrdata_get-didn-t-collect-data-from-both-cinstrdat1-and-cinstrdat0
222179
nrfx_qspi_cinstr_xfer(&cinstr_cfg, dummy, id_resp);
223180

224-
// Due to the bug, we collect data manually
225-
uint8_t dev_id = (uint8_t) NRF_QSPI->CINSTRDAT1;
226-
uint8_t mfgr_id = (uint8_t) ( NRF_QSPI->CINSTRDAT0 >> 24);
181+
uint8_t const mfgr_id = id_resp[3];
182+
uint8_t const dev_id = id_resp[4];
227183

228184
// quick hack
229-
//printf("qspi mfgr id : 0x%02X\n", mfgr_id);
230-
//printf("qspi device id: 0x%02X\n", dev_id);
185+
// printf("qspi mfgr id : 0x%02X\n", mfgr_id);
186+
// printf("qspi device id: 0x%02X\n", dev_id);
187+
// PRINT_BUFFER(id_resp, sizeof(id_resp));
231188

232189
// Look up the flash device in supported array
233-
for ( int i = 0; i < FLASH_DEVICE_COUNT; i++ )
190+
for ( uint32_t i = 0; i < FLASH_DEVICE_COUNT; i++ )
234191
{
235192
// Match ID
236193
if ( _flash_devices_arr[i].manufacturer_id == mfgr_id && _flash_devices_arr[i].device_id == dev_id )
@@ -242,13 +199,20 @@ void flash_qspi_init (void)
242199

243200
if ( _flash_dev )
244201
{
245-
// Enable quad mode if needed
246-
#if QSPI_FLASH_MODE == 4
202+
// Enable quad mode
247203
cinstr_cfg.opcode = QSPI_CMD_WRSR;
248204
cinstr_cfg.length = 3;
249205
cinstr_cfg.wipwait = cinstr_cfg.wren = true;
250206
nrfx_qspi_cinstr_xfer(&cinstr_cfg, &_flash_dev->status_quad_enable, NULL);
251-
#endif
207+
208+
// Speed up frequency
209+
nrf_qspi_phy_conf_t phy_if = {
210+
.sck_freq = _flash_dev->freq,
211+
.sck_delay = 10,
212+
.spi_mode = NRF_QSPI_MODE_0,
213+
.dpmen = false
214+
};
215+
nrf_qspi_ifconfig1_set(NRF_QSPI, &phy_if);
252216
}
253217

254218
// create mutex
@@ -284,6 +248,6 @@ static bool fal_qspi_verify (uint32_t addr, void const * buf, uint32_t len)
284248
return false;
285249
}
286250

287-
#endif // valid pin
251+
#endif // external flash
288252
#endif // nrf52840
289253

cores/nRF5/usb/Adafruit_USBDev_CDC.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,7 @@
1-
21
/*
32
* The MIT License (MIT)
43
*
5-
* Copyright (c) 2018, hathach for Adafruit
4+
* Copyright (c) 2019 Ha Thach for Adafruit Industries
65
*
76
* Permission is hereby granted, free of charge, to any person obtaining a copy
87
* of this software and associated documentation files (the "Software"), to deal
@@ -22,6 +21,7 @@
2221
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
2322
* THE SOFTWARE.
2423
*/
24+
2525
#ifdef NRF52840_XXAA
2626

2727
#include "Adafruit_USBDev_CDC.h"

cores/nRF5/usb/Adafruit_USBDev_CDC.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
/*
22
* The MIT License (MIT)
33
*
4-
* Copyright (c) 2018, hathach for Adafruit
4+
* Copyright (c) 2019 Ha Thach for Adafruit Industries
55
*
66
* Permission is hereby granted, free of charge, to any person obtaining a copy
77
* of this software and associated documentation files (the "Software"), to deal

cores/nRF5/usb/Adafruit_USBDevice.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
/*
22
* The MIT License (MIT)
33
*
4-
* Copyright (c) 2019 hathach for Adafruit Industries
4+
* Copyright (c) 2019 Ha Thach for Adafruit Industries
55
*
66
* Permission is hereby granted, free of charge, to any person obtaining a copy
77
* of this software and associated documentation files (the "Software"), to deal

cores/nRF5/usb/Adafruit_USBDevice.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
/*
22
* The MIT License (MIT)
33
*
4-
* Copyright (c) 2019 hathach for Adafruit Industries
4+
* Copyright (c) 2019 Ha Thach for Adafruit Industries
55
*
66
* Permission is hereby granted, free of charge, to any person obtaining a copy
77
* of this software and associated documentation files (the "Software"), to deal

0 commit comments

Comments
 (0)