Skip to main content

Seeed Studio XIAO SAMD21 入门指南 By Nanase

这是一份由 @nanase_coder 编写的文档。(由 Seeed 从原始日文文档翻译:コインサイズ Arduino互換機 Seeed Studio XIAO SAMD21 を使ってみた)。感谢 Nanase 与我们分享这份文档!

文档

关于 Seeeduino XIAO 的使用有两份文档,它们专注于不同的领域,请参考下表:

Seeed 官方文档Nanase 文档
引脚图接口
Seeed Studio XIAO SAMD21 入门指南Seeed Studio XIAO SAMD21 与 MicroSD 卡(SPI)
Seeed Studio XIAO SAMD21 GPIO 使用Seeed Studio XIAO SAMD21 与 GPS(UART)
Seeed Studio XIAO SAMD21 资源单周期 IOBUS

特性

  • ARM Cortex M0 + CPU (SAMD21G18) 48MHz
  • 256 KB Flash,32 KB SRAM
  • USB Type-C
  • SPI、I2C、UART、DMA 可用
  • 硬币大小(21mm x 17.8mm)
  • 逻辑电平:3.3V

板子背面没有元件,所有引脚都有半孔设计,便于焊接到其他板子上。

零件清单

  • 1 x Seeeduino XIAO
  • 2 x 7针排针
  • 4 x 贴纸

pir

半孔设计:

pir

规格

规格
CPUARM Cortex-M0+ CPU(SAMD21G18) 运行频率高达 48MHz(从 32.768 kHz 倍频)
存储256KB Flash,32KB SRAM
I/O 引脚14 个 GPIO 引脚,11 个模拟引脚,11 个数字引脚,1 个 DAC 输出引脚
引脚功能SPI、I2C、UART、PWM、外部中断、SWD(电源焊盘)
逻辑电平3.3V
LED:1 个用户 LED,1 个电源 LED,两个用于串口下载的 LED
电源USB Type-C 接口,背面电源焊盘
尺寸21x17.8x3.5mm

如您所见,这是一个 SAMD 类型的 Arduino,类似于 Arduino MKR 系列,因此从技术上讲,为它们编写的任何库都可以在 Seeed Studio XIAO SAMD21 上使用。另一方面,由于它与 Arduino Uno 等 ATmega 类型的 Arduino 不同,依赖于 ATmega 某些特定寄存器的库无法使用。

GPIO 14 引脚是指侧面的 11 个引脚、复位引脚和背面的 SWD(SWDIO、SWCLK)。

引脚功能中的 UART 与通过 USB 的串口不同,可以通过 Serial1 操作。

重置您的开发板

查看这里并了解如何将 Seeed Studio XIAO SAMD21 添加到您的 Arduino IDE 中。

pir

Seeed Studio XIAO SAMD21 没有重置按钮。相反,它有一个重置焊盘。 短接这个重置焊盘并接地来重置您的开发板。

引导加载程序模式

pir

有时程序可能会崩溃或无法上传代码。您可以重置开发板两次进入引导加载程序模式。在此模式下,LED 缓慢闪烁,Seeed Studio XIAO SAMD21 被识别为 USB 存储设备。串口与正常模式分离,始终处于代码写入模式,不会运行开发板上的先前程序。

要从引导加载程序模式返回到正常模式,请上传一个代码或再次快速重置两次。

如果当 Seeed Studio XIAO SAMD21 未被 PC 识别为 USB 设备时进入引导加载程序模式,LED 将快速闪烁。

LCD

就像原始的 Arduino 一样,从示例代码中选择 Basics> Blink 并上传。

void setup() {
pinMode(LED_BUILTIN, OUTPUT);
}

void loop() {
digitalWrite(LED_BUILTIN, HIGH);
delay(1000);
digitalWrite(LED_BUILTIN, LOW);
delay(1000);
}

与原始 Arduino 相反,它在 LOW 时点亮,在 HIGH 时熄灭。

两个可闪烁的内置 LED

官方网站将另外两个内置 LED 描述为用于串口下载的两个 LED。但是,查看原理图,这些 RX 和 TX LED 没有连接到物理引脚。

如果您查看这里的 USBCore.cpp,您可以看到每次发生串口 USB 传输/接收时,它们都会通过 digitalWrite 点亮,这意味着这两个 LED 是可编程的。

uint32_t USBDeviceClass::recv(uint32_t ep, void *_data, uint32_t len)
{
if (!_usbConfiguration)
return -1;

#ifdef PIN_LED_RXL
if (rxLEDPulse == 0)
digitalWrite(PIN_LED_RXL, LOW);

rxLEDPulse = TX_RX_LED_PULSE_MS;
#endif

具体的引脚号码在 variant.h / variant.cpp 中定义,就像 SAMD Arduino 一样,在 Seeeduino XIAO 的情况下,它们被分配给 11 和 12,如下所示。

#define PIN_LED_13  (13u)
#define PIN_LED PIN_LED_13
#define LED_BUILTIN PIN_LED

#define PIN_LED_RXL (12u)
#define PIN_LED_TXL (11u)
#define PIN_LED2 PIN_LED_RXL
#define PIN_LED3 PIN_LED_TXL

下面是一个闪烁三个 LED 的代码。RX 和 TX 的 LED 是蓝色的。

void setup() {
pinMode(LED_BUILTIN, OUTPUT);
pinMode(PIN_LED2, OUTPUT);
pinMode(PIN_LED3, OUTPUT);
}

void loop() {
digitalWrite(LED_BUILTIN, HIGH);
digitalWrite(PIN_LED2, HIGH);
digitalWrite(PIN_LED3, HIGH);
delay(1000);
digitalWrite(LED_BUILTIN, LOW);
digitalWrite(PIN_LED2, LOW);
digitalWrite(PIN_LED3, LOW);
delay(1000);
}

pir

接口

通过 USB CDC 进行串行通信

与 ATmega 类型的 Arduino 不同,Seeed Studio XIAO SAMD21 串行通信的实际状态是 USB CDC。换句话说,它可以比普通串行通信执行得更快。

因此,通过 Serial.begin (speed) 指定波特率没有意义,但除此之外,它可以像普通串行通信一样使用。

测量速度

pir

我使用这个代码来测量从 Seeed Studio XIAO SAMD21 到 PC 的传输速度,从 PC 到 Seeed Studio XIAO SAMD21 的传输速率应该是相同的。

横轴是缓冲区大小(使用 Serial.write (buf, len) 一次发送)。 如果一次发送 1 字节,只能获得 0.11 Mbps(14.53 KB / s),但如果发送 64 字节,速度会显著提高到 6.30 Mbps(805.86 KB / s)。您可以推断内部缓冲区的大小是 64 字节。

如上所述,LED 在串行通信中会闪烁,但由于这个原因几乎没有速度下降。

SPI(MicroSD 卡)

Seeed Studio XIAO SAMD21 的逻辑电平为 3.3V。换句话说,可以通过 SPI 处理 microSD 卡而无需电平转换器。 SPI 的某些功能与 ATmega 类型的 Arduino 不同,请查看这里获取更多信息。

这里我们将使用秋月电子的 micro SD 卡插槽 DIP 套件读取 microSD 卡。

我们在这里使用 Arduino 示例代码,但 SD.begin (cs_pin) 的参数指定为 SS。根据 variant.h,SS = 4,这与 D4 / A4 / SDA 引脚相同。当然,您可以指定其他引脚。

pir

pir

#include <SPI.h>
#include <SD.h>

File myFile;

void setup() {
Serial.begin(9600);
while (!Serial) ;

Serial.print("Initializing SD card... ");

if (!SD.begin(SS)) { // <-------------------------------- SS = D4/A4/SDA pin
Serial.println("initialization failed!");
while (1) ;
}
Serial.println("initialization done.");

myFile = SD.open("test.txt", FILE_WRITE);

if (myFile) {
Serial.print("Writing to test.txt...");
myFile.println("testing 1, 2, 3.");

myFile.close();
Serial.println("done.");
}
else
Serial.println("error opening test.txt");

myFile = SD.open("test.txt");
if (myFile) {
Serial.println("test.txt:");

while (myFile.available())
Serial.write(myFile.read());

myFile.close();
}
else
Serial.println("error opening test.txt");
}

void loop() { }

结果:

Initializing SD card...initialization done.
Writing to test.txt...done.
test.txt:
testing 1, 2, 3.

I2C

I2C 也可用。3.3V 设备可以直接连接而无需电平转换器。

这次,我们使用 BME280 来测量温度、湿度和大气压力。BME280 在 3.3V 下工作,因此可以在不使用电平转换器的情况下连接。查看这里获取 Arduino 和 BME280 之间连接的详细说明。

pir

pir

#include <Wire.h>
#include "SparkFunBME280.h"

BME280 sensor;

void setup() {
Serial.begin(9600);
Wire.begin();
sensor.beginI2C(); // 使用 Wire 开始 I2C 连接
}

void loop() {
Serial.print("Temp: ");
Serial.print(sensor.readTempC(), 2);

Serial.print(" °C, Humidity: ");
Serial.print(sensor.readFloatHumidity(), 2);

Serial.print(" %, Pressure: ");
Serial.print(sensor.readFloatPressure() / 100.0, 1);
Serial.println(" hPa");

delay(5000);
}
Temp: 22.05 °C, Humidity: 44.99 %, Pressure: 1009.0 hPa
Temp: 22.05 °C, Humidity: 44.72 %, Pressure: 1008.9 hPa
Temp: 22.06 °C, Humidity: 44.81 %, Pressure: 1008.9 hPa

UART

如前所述,物理 UART 引脚与 USB CDC 上的引脚不同。Serial1 用于使用 TX 和 RX 引脚进行串行通信。

这次,我们将 Seeed Studio XIAO SAMD21 连接到 GPS 接收器套件,并从 PC 获取 NMEA 信息。使用 Xiao 时这是一个非常简单的工作,它只是 GPS 套件和 PC 串口之间的桥梁。

pir

pir

void setup() {
Serial.begin(9600);
Serial1.begin(9600);
}

void loop() {
if (Serial.available()) {
char c = (char)Serial.read();
Serial1.write(c);
}

if (Serial1.available()) {
char c = (char)Serial1.read();
Serial.write(c);
}
}

这次我们使用 GPSFox 来浏览 NMEA 信息。可以轻松测量坐标。

pir

其他

DMA

作为 SAMD 类型 Arduino 的功能之一,您可以在 Xiao 上使用 DMA。查看这里了解更多关于 DMA 的信息。

单周期 IOBUS

Cortex M0+ 具有一个称为单周期 IOBUS的功能,可以在一个时钟周期内操作GPIO输出。写入特定寄存器可以反转逻辑、禁用引脚或更改引脚驱动电流。

DigitalWrite

您可以使用 digitalWrite 创建脉冲,这是一种适用于任何 Arduino 板的方法 - 只是重复开销。

void setup() {
pinMode(PIN_A7, OUTPUT);
}

#define P \
digitalWrite(PIN_A7, HIGH); \
digitalWrite(PIN_A7, LOW);

#define W P P P P P P P P P P P P P P P P
void loop() { W W W W W W W W W W W W W W W W }

使用寄存器

您也可以通过直接操作寄存器而不使用 digitalWrite 来创建脉冲。

void setup() {
pinMode(PIN_A7, OUTPUT);
}

#define P \
digitalPinToPort(PIN_A7)->OUTSET.reg = digitalPinToBitMask(PIN_A7); \
digitalPinToPort(PIN_A7)->OUTCLR.reg = digitalPinToBitMask(PIN_A7);

#define W P P P P P P P P P P P P P P P P
void loop() { W W W W W W W W W W W W W W W W }

使用单周期 IOBUS

我们使用这里介绍的 IOBUS.h

#include "IOBUS.h"

#define digitalPinToIOPin(P) ((g_APinDescription[P].ulPort << 5) + g_APinDescription[P].ulPin)
#define PIN_NUM digitalPinToIOPin(PIN_A7)

void setup() {
IOBUS::pinMode(PIN_NUM, OUTPUT, true);
}

#define P IOBUS::toggleOutput(PIN_NUM);

#define W P P P P P P P P P P P P P P P P
void loop() { W W W W W W W W W W W W W W W W }
DigitalWrite寄存器单周期 IOBUS
波形

pir

pir

pir

频率333 kHz6 MHz24 MHz
创建脉冲所需的时钟周期数14482

逻辑确实可以在一个周期内反转(48MHz)。

技术支持与产品讨论

感谢您选择我们的产品!我们在这里为您提供不同的支持,以确保您使用我们产品的体验尽可能顺畅。我们提供多种沟通渠道,以满足不同的偏好和需求。

Loading Comments...