Samd21 custom board and Arduino framework

Hi, actually i am designing a board with samd21g18 (the same microcontroller as arduino zero or sparkfun dev board).

I want program the microcontroller using the arduino framework and platformio but without bootloader, and i want upload the code using j-link programmer (SWD). Is it possible? or should i program the bootloader?

If it is possible, could anyone give me some steps?

Thanks,
Regards,

Yes the chip is supported (platform-atmelsam/samd21g18a.json at develop · platformio/platform-atmelsam · GitHub) with the Arduino and mbed-os frameworks. As you can see here it also uses a linkerscript that does not contain a bootlaoder. Also Jlink is supported for upload.

So you’d start off with a platformio.ini of

[env:samd21g18a]
platform = atmelsam
board = samd21g18a
framework = arduino
upload_protocol = jlink

And go from there.

Hi, thanks for your reply. I have followed your instructions but i have not success. Do i set any parameter more?

Thanks,
Regards.

I try upload a blink example, the upload code output is:

Processing samd21g18a (platform: atmelsam; board: samd21g18a; framework: arduino)

Verbose mode can be enabled via -v, --verbose option
CONFIGURATION: Redirecting...
PLATFORM: Atmel SAM 4.0.0 > Atmel ATSAMW25-XPRO
HARDWARE: SAMD21G18A 48MHz, 32KB RAM, 256KB Flash
DEBUG: Current (jlink) On-board (cmsis-dap) External (atmel-ice, blackmagic, jlink)
PACKAGES: toolchain-gccarmnoneeabi 1.70201.0 (7.2.1), framework-arduinosam 4.4.191002, tool-jlink 1.65200.0 (6.52.0)
LDF: Library Dependency Finder → Library Dependency Finder (LDF) — PlatformIO latest documentation
LDF Modes: Finder ~ chain, Compatibility ~ soft
Found 8 compatible libraries
Scanning dependencies…
No dependencies
Building in release mode
Checking size .pio\build\samd21g18a\firmware.elf
Advanced Memory Usage is available via “PlatformIO Home > Project Inspect”
DATA: [= ] 7.2% (used 2364 bytes from 32768 bytes)
PROGRAM: [ ] 4.3% (used 11324 bytes from 262144 bytes)
Configuring upload protocol…
AVAILABLE: atmel-ice, blackmagic, cmsis-dap, jlink
CURRENT: upload_protocol = jlink
Uploading .pio\build\samd21g18a\firmware.bin
SEGGER J-Link Commander V6.52 (Compiled Sep 27 2019 17:52:04)
DLL version V6.52, compiled Sep 27 2019 17:50:11

J-Link Command File read successfully.
Processing script file…

J-Link connection not established yet but required for command.
Connecting to J-Link via USB…O.K.
Firmware: J-Link OB-STM32F072-CortexM compiled Jan 7 2019 14:09:37
Hardware version: V1.00
S/N: -1
License(s): GDB, RDI, FlashBP, FlashDL, JFlash, RDDI
VTref=3.300V
Target connection not established yet but required for command.
Device “ATSAMD21G18” selected.

Connecting to target via SWD
InitTarget()
Found SW-DP with ID 0x0BC11477
Scanning AP map to find all available APs
AP[1]: Stopped AP scan as end of AP map has been reached
AP[0]: AHB-AP (IDR: 0x04770031)
Iterating through AP map to find AHB-AP to use
AP[0]: Core found
AP[0]: AHB-AP ROM base: 0x41003000
CPUID register: 0x410CC601. Implementer code: 0x41 (ARM)
Found Cortex-M0 r0p1, Little endian.
FPUnit: 4 code (BP) slots and 0 literal slots
CoreSight components:
ROMTbl[0] @ 41003000
ROMTbl[0][0]: E00FF000, CID: B105100D, PID: 000BB4C0 ROM Table
ROMTbl[1] @ E00FF000
ROMTbl[1][0]: E000E000, CID: B105E00D, PID: 000BB008 SCS
ROMTbl[1][1]: E0001000, CID: B105E00D, PID: 000BB00A DWT
ROMTbl[1][2]: E0002000, CID: B105E00D, PID: 000BB00B FPB
ROMTbl[0][1]: 41006000, CID: B105900D, PID: 001BB932 MTB-M0+
Cortex-M0 identified.
PC = 000008F4, CycleCnt = 00000000
R0 = 41004000, R1 = 40000400, R2 = 40000C00, R3 = 40000800
R4 = FFFFFF80, R5 = 00000000, R6 = 200006BC, R7 = 4BBFFDDF
R8 = EAFF74FF, R9 = B9EFFEF7, R10= 7BEBF6EF, R11= 8BFFEFEB
R12= 200005D8
SP(R13)= 20008000, MSP= 20008000, PSP= FCFFECF4, R14(LR) = 00000903
XPSR = A1000000: APSR = NzCvq, EPSR = 01000000, IPSR = 000 (NoException)
CFBP = 00000000, CONTROL = 00, FAULTMASK = 00, BASEPRI = 00, PRIMASK = 00
FPU regs: FPU not enabled / not implemented on connected CPU.

Downloading file [.pio\build\samd21g18a\firmware.bin]…
J-Link: Flash download: Bank 0 @ 0x00000000: Skipped. Contents already match
O.K.

Reset delay: 0 ms
Reset type NORMAL: Resets core & peripherals via SYSRESETREQ & VECTRESET bit.

Script processing completed.

=========================================================================================== [SUCCESS] Took 5.44 seconds ===========================================================================================

It already saw that the firmware didn’t change and upload was thus successful.

So please define success. What code are you running, what are your expected results, what are the actual results?

I upload again the code but before i have erased the chip. I want use an internal 8Mhz clock.

Thanks.

The output process is:

Processing samd21g18a (platform: atmelsam; board: samd21g18a; framework: arduino)

Verbose mode can be enabled via -v, --verbose option
CONFIGURATION: Redirecting...
PLATFORM: Atmel SAM 4.0.0 > Atmel ATSAMW25-XPRO
HARDWARE: SAMD21G18A 48MHz, 32KB RAM, 256KB Flash
DEBUG: Current (jlink) On-board (cmsis-dap) External (atmel-ice, blackmagic, jlink)
PACKAGES: toolchain-gccarmnoneeabi 1.70201.0 (7.2.1), framework-arduinosam 4.4.191002, tool-jlink 1.65200.0 (6.52.0)
LDF: Library Dependency Finder → Library Dependency Finder (LDF) — PlatformIO latest documentation
LDF Modes: Finder ~ chain, Compatibility ~ soft
Found 8 compatible libraries
Scanning dependencies…
No dependencies
Building in release mode
Checking size .pio\build\samd21g18a\firmware.elf
Advanced Memory Usage is available via “PlatformIO Home > Project Inspect”
DATA: [= ] 7.2% (used 2364 bytes from 32768 bytes)
PROGRAM: [ ] 4.3% (used 11184 bytes from 262144 bytes)
Configuring upload protocol…
AVAILABLE: atmel-ice, blackmagic, cmsis-dap, jlink
CURRENT: upload_protocol = jlink
Uploading .pio\build\samd21g18a\firmware.bin
SEGGER J-Link Commander V6.52 (Compiled Sep 27 2019 17:52:04)
DLL version V6.52, compiled Sep 27 2019 17:50:11

J-Link Command File read successfully.
Processing script file…

J-Link connection not established yet but required for command.
Connecting to J-Link via USB…O.K.
Firmware: J-Link OB-STM32F072-CortexM compiled Jan 7 2019 14:09:37
Hardware version: V1.00
S/N: -1
License(s): GDB, RDI, FlashBP, FlashDL, JFlash, RDDI
VTref=3.300V
Target connection not established yet but required for command.
Device “ATSAMD21G18” selected.

Connecting to target via SWD
InitTarget()
Found SW-DP with ID 0x0BC11477
Scanning AP map to find all available APs
AP[1]: Stopped AP scan as end of AP map has been reached
AP[0]: AHB-AP (IDR: 0x04770031)
Iterating through AP map to find AHB-AP to use
AP[0]: Core found
AP[0]: AHB-AP ROM base: 0x41003000
CPUID register: 0x410CC601. Implementer code: 0x41 (ARM)
Found Cortex-M0 r0p1, Little endian.
FPUnit: 4 code (BP) slots and 0 literal slots
CoreSight components:
ROMTbl[0] @ 41003000
ROMTbl[0][0]: E00FF000, CID: B105100D, PID: 000BB4C0 ROM Table
ROMTbl[1] @ E00FF000
ROMTbl[1][0]: E000E000, CID: B105E00D, PID: 000BB008 SCS
ROMTbl[1][1]: E0001000, CID: B105E00D, PID: 000BB00A DWT
ROMTbl[1][2]: E0002000, CID: B105E00D, PID: 000BB00B FPB
ROMTbl[0][1]: 41006000, CID: B105900D, PID: 001BB932 MTB-M0+
Cortex-M0 identified.
PC = FFFFFFFE, CycleCnt = 00000000
R0 = 41004000, R1 = 40000400, R2 = 40000C00, R3 = 40000800
R4 = FFFFFF80, R5 = 00000000, R6 = 00000080, R7 = 4BBFFFDF
R8 = EAFF74FF, R9 = B9EFFEF7, R10= F9EBF6EF, R11= 8BFFEFEB
R12= 200005D8
SP(R13)= FFFFFFFC, MSP= FFFFFFFC, PSP= FCFFECF4, R14(LR) = 00000153
XPSR = A1000000: APSR = NzCvq, EPSR = 01000000, IPSR = 000 (NoException)
CFBP = 00000000, CONTROL = 00, FAULTMASK = 00, BASEPRI = 00, PRIMASK = 00
FPU regs: FPU not enabled / not implemented on connected CPU.

Downloading file [.pio\build\samd21g18a\firmware.bin]…
J-Link: Flash download: Bank 0 @ 0x00000000: 1 range affected (11264 bytes)
J-Link: Flash download: Total time needed: 0.332s (Prepare: 0.059s, Compare: 0.031s, Erase: 0.000s, Program: 0.221s, Verify: 0.010s, Restore: 0.009s)
O.K.

Reset delay: 0 ms
Reset type NORMAL: Resets core & peripherals via SYSRESETREQ & VECTRESET bit.

Script processing completed.

=========================================================================================== [SUCCESS] Took 5.09 seconds ===========================================================================================

And the code it is simple:

#include <Arduino.h>

void setup() {
// put your setup code here, to run once:
pinMode(PIN_PA20, OUTPUT);
}

void loop() {
// put your main code here, to run repeatedly:
digitalWrite(PIN_PA20, HIGH);
delay(2000);
digitalWrite(PIN_PA20, LOW);
delay(2000);
}

my .ini file is:

[env:samd21g18a]
platform = atmelsam
board = samd21g18a
framework = arduino
; SWD interface
upload_protocol = jlink
debug_tool = jlink

So as you can see here

The used variant for the samd21g18a.json says w25_xplained_pro. The variants/w25_xplained_pro/variant.cpp says

/*
 +------------+------------------+--------+-----------------+--------+-----------------------+---------+---------+--------+--------+----------+----------+
 | Pin number |  MKR  Board pin  |  PIN   | Notes           | Peri.A |     Peripheral B      | Perip.C | Perip.D | Peri.E | Peri.F | Periph.G | Periph.H |
 |            |                  |        |                 |   EIC  | ADC |  AC | PTC | DAC | SERCOMx | SERCOMx |  TCCx  |  TCCx  |    COM   | AC/GLCK  |
 |            |                  |        |                 |(EXTINT)|(AIN)|(AIN)|     |     | (x/PAD) | (x/PAD) | (x/WO) | (x/WO) |          |          |
 +------------+------------------+--------+-----------------+--------+-----+-----+-----+-----+---------+---------+--------+--------+----------+----------+
 | 00         | D0               |  PA22  |                 |  *06   |     |     | X10 |     |   3/00  |   5/00  |* TC4/0 | TCC0/4 |          | GCLK_IO6 |
 | 01         | D1               |  PA23  |                 |  *07   |     |     | X11 |     |   3/01  |   5/01  |* TC4/1 | TCC0/5 | USB/SOF  | GCLK_IO7 |
 | 02         | D2               |  PA10  |                 |   10   | *18 |     | X02 |     |   0/02  |   2/02  |*TCC1/0 | TCC0/2 | I2S/SCK0 | GCLK_IO4 |
 | 03         | D3               |  PA11  |                 |   11   | *19 |     | X03 |     |   0/03  |   2/03  |*TCC1/1 | TCC0/3 | I2S/FS0  | GCLK_IO5 |
 | 04         | D4               |  PB10  |                 |  *10   |     |     |     |     |         |   4/02  |* TC5/0 | TCC0/4 | I2S/MCK1 | GCLK_IO4 |
 | 05         | D5               |  PB11  |                 |  *11   |     |     |     |     |         |   4/03  |* TC5/1 | TCC0/5 | I2S/SCK1 | GCLK_IO5 |
 | 06         | D6               |  PA20  |                 |  *04   |     |     | X08 |     |   5/02  |   3/02  |        |*TCC0/6 | I2S/SCK0 | GCLK_IO4 |

So you should be using pin number 6 for the pinMode() and digitalWrite() functions

I’m not 100% sure on this but the startup code (ArduinoCore-samd/cores/arduino/startup.c at master · arduino/ArduinoCore-samd · GitHub) understands the macro CRYSTALLESS with which it doesn’t attempt to use an external 32.768Khz oscillator and also an external high-speed one it seems.

So I’d add the build flag

build_flags = -D CRYSTALLESS

to the platformio.ini

1 Like

It´s works! I can develop the code over the microcontroller.

I dont understand well the crystal setup. I dont know if the microcontroller is running an intertar 32khz crystal and if the microcontroller is working on 1mhz, 8mhz or 48mhz.

If it is possible, i want not work with internar or external 32khz crystal.

Thanks for your help.
Regards,

A new question. The microcontroller have the UART (Serial1) port on pin PB10 and PB11 instead of PB22 and PB23 that i could see in variants.cpp (platformio-pkg-framework-arduinosam/variant.cpp at master · platformio/platformio-pkg-framework-arduinosam · GitHub)

I need remap this pins to have Serial1 on pins PA10 and PA11. Could i do this on my scketch or i need modify the variants.cpp file?

I think that i will need remap the SPI pins too.

Thanks,
Regards.

Yes you will have to modify the variants.cpp file if you want to change the mapping of Serials and the SPI pins. First though I’d check for other variants / boards with the SAMD21G18 chip which maybe have the mapping you want in the variant folder.

The Adafruit guide tells you how to add / modify the SERCOM peripheral mappings for SPI and UART etc: Overview | Using ATSAMD21 SERCOM for more SPI, I2C and Serial ports | Adafruit Learning System

If you want a custom board you can also create a new variant folder in the framework and tell PlatformIO

board_build.variant = new_variant_folder

as seen in the above linked documentation.

1 Like

Ok, it works. My design is based on sparkfun samd21 dev board and when i set this variant it works.

I read your link to learn about variant file modifications.

Thanks so much for your help.
Regards,