HOME
  Security
   Software
    Hardware
  
FPGA
  CPU
   Android
    Raspberry Pi
  
nLite
  Xcode
   etc.
    ALL
  
LINK
BACK
 

2023/03/27

RP2040で I2Cの Masterと Slaveをサクッと使う方法、TalkingToMyself.ino RP2040で I2Cの Masterと Slaveをサクッと使う方法、TalkingToMyself.ino

(RP2040-YD Raspberry Pi Pico RP2040で I2Cの Masterと Slaveを同居させて同時に使う方法)

Tags: [ワンチップCPU]




●前書き

 Raspberry Pi Pico RP2040で I2Cの Masterと Slaveを同居させて同時に使う方法。

 STM32の Arduinoで Masterと Slaveを同居させたプログラムを作ったら意図通りに動かないクソッタレでした。

 では GD32Vの Arduinoはどうか?と言うと、そもそもで I2C(TWI)の Wire.hが無いと言う惨状に開いた口がふさがりませんでした。

 同じ作りで ESP32での試験実装では何の問題も無かったのですが、+5Vトレラントの関係で STM32を候補に上げていたのでした。

 AVR系を +5V電源で動かせば大丈夫ですが、I2Cの転送の最大長が 32バイトという点で捨てました。

 と言う訳で STM32を捨てて ESP32か RP2040に I2Cレベルコンバーターを咬ませて設計する事にしました。

 ESP32は I2Cが素直に動く事を確認していたので RP2040でも I2Cの動作具合を確認する事にしました。

 ※ ESP32の場合は Espressif公式の Arduino-ESP32の I2Cの説明ページのプログラムを使用しました。
Espressif公式の Arduino-ESP32の I2Cの説明ページ

 >> 結論としては RP2040でも何の問題も無くアッサリ動きました。

 ※ 世の中では XIAO RP2040では使用できる GPIOが限定されているので苦労している模様。


●使用した RP2040の Arduino環境

Arduino IDE 2.0.4
Arduino-Pico Release 3.1.0 2023/03/11
● Additional Boards Manager URLs
https://github.com/earlephilhower/arduino-pico/releases/download/global/package_rp2040_index.json


●使用した RP2040のボード、RP2040-YD Raspberry Pi Pico

 RP2040-YD Raspberry Pi Pico 4MB版

源地工作室 VCC-GND Studioの公式

 源地工作室 VCC-GND Studioの公式 YD-RP2040の資料
源地工作室 VCC-GND Studio YD-RP2040

ピン配置 YD-2040
・ピン配置 YD-2040
ピン配置 YD-2040



回路図 YD-2040-2022-V1.1-SCH.pdf
・回路図 YD-2040
回路図 YD-2040


回路図 YD-2040



 ここに YD-RP2040のサンプルプログラムが色々有る。
RP2040-YD Raspberry Pi Pico, 16MB Flash, USB Type-C

 私が購入したのは源地工作室 VCC-GND Studioの YD-RP2040の模倣品。

・YD-RP2040の模倣品
YD-RP2040の模倣品



 その後、源地工作室 VCC-GND Studioの YD-RP2040の正規品を購入しました。

・YD-RP2040の正規品
YD-RP2040の正規品





● RP2040で I2Cの Masterと Slaveをサクッと使う方法、TalkingToMyself.ino

 I2Cの Masterと Slaveを同居させたテストプログラムで有名な TalkingToMyself.inoです。

 黄色のラインの
    Wire.setSDA(D0); // GPIO 0
    Wire.setSCL(D1); // GPIO 1

    Wire1.setSDA(D2); // GPIO 2
    Wire1.setSCL(D3); // GPIO 3
 を追加して、RP2040の I2Cで使用する GPIOピンを指定します。

 GPIO 0を GPIO 2に、
 GPIO 1を GPIO 3に接続します。
 I2Cバスのプルアップ抵抗は不要です。
 ※ これで YD-RP2040でサクッと動きました。
 ※ ESP32でもプルアップ抵抗は不要でサクッと動きました。

RP2040 Datasheet 2.1 03 Mar 2023
・1.4.3. GPIO Functionsの Function F3列を参照
1.4.3. GPIO Functionsの Function F3列を参照


 I2C0と I2C1に定義できる GPIOが交互に並んでいるのがわかると思います。
 (とても見やすい GPIO機能一覧の表です!)

 RP2040は I2Cを 2系統持っており、I2C0と I2C1になります。
 I2C0と I2C1に指定できる GPIOピンは決まっています。
 ※ 使用できないピンを指定すると RP2040がハングアップします(笑
 ハングアップの例
 ・SDAと SCLが逆
    Wire.setSDA(D1);
    Wire.setSCL(D0);

 ・I2C0に I2C1の GPIOを指定
    Wire.setSDA(D2);
    Wire.setSCL(D3);

・RP2040で I2Cの Masterと Slaveをサクッと使う方法、TalkingToMyself.inoの配線例
RP2040で I2Cの Masterと Slaveをサクッと使う方法、TalkingToMyself.inoの配線例



・RP2040で I2Cの Masterと Slaveをサクッと使う方法、TalkingToMyself.inoの実行例
RP2040で I2Cの Masterと Slaveをサクッと使う方法、TalkingToMyself.inoの実行例


Sending...
Slave recv buff: 'pass 40' << マスターが送信してスレーブが受信した文字列

Master recv: '000316' << マスターが要求してスレーブが送信した文字列

 オリジナルの TalkingToMyself.inoから、下記の改善をしています。
 ・GPIO Pin指定を define定義にして汎用性と可読性を向上
 ・WireMasterと WireSlaveを定義して可読性を向上
 ・Slaveのコールバックの設定を beginの前に移動(これは ESP32の場合に必要)

TalkingToMyself.ino
// Simple I2C master and slave demo - Earle F. Philhower, III
// Released into the public domain
//
// Using both onboard I2C interfaces, have one master and one slave
// and send data both ways between them
//
// To run, connect GPIO0 to GPIO2, GPIO1 to GPIO3 on a single Pico

// GPIO0 to GPIO2
// GPIO1 to GPIO3

#include <Wire.h>

// I2C
#define I2C_LOW_SPEED_MODE    10000 /*  10kbps */
#define I2C_STANDARD_MODE    100000 /* 100kbps */
#define I2C_FAST_MODE        400000 /* 400kbps */
#define I2C_FAST_MODE_PLUS  1000000 /* 1.0Mbps */
#define I2C_HIGH_SPEED_MODE 3400000 /* 3.4Mbps */
// #define I2C_FREQ I2C_STANDARD_MODE
// OK RP2040 10000 - 4600000
// #define I2C_FREQ 4600000 // OK RP2040
// #define I2C_FREQ 4800000 // NG RP2040

// Wire = I2C0
#define I2C0_SDA D0 /* GPIO 0 */
#define I2C0_SCL D1 /* GPIO 1 */

// Wire1 = I2C1
#define I2C1_SDA D2 /* GPIO 2 */
#define I2C1_SCL D3 /* GPIO 3 */

// Test Address
#define I2C_ADDRESS 0x30

// Master - Slave
#define WireMaster Wire
#define WireSlave  Wire1
// #define WireMaster Wire1
// #define WireSlave  Wire

void setup() {
  Serial.begin(115200);
  while(!Serial && (millis() < 5000));
  Serial.println("setup()");

  // Wire = I2C0
  Wire.setSDA(I2C0_SDA);
  Wire.setSCL(I2C0_SCL);

  // Wire1 = I2C1
  Wire1.setSDA(I2C1_SDA);
  Wire1.setSCL(I2C1_SCL);

#if defined(I2C_FREQ)
  WireMaster.setClock(I2C_FREQ);
  WireSlave.setClock(I2C_FREQ);
#endif

  WireMaster.begin();

#if defined(ARDUINO_ARCH_ESP32)
  // ESP32 Before calling `begin()` two callback functions
  // https://espressif-docs.readthedocs-hosted.com/projects/arduino-esp32/en/latest/api/i2c.html
  // https://github.com/espressif/arduino-esp32/blob/master/libraries/Wire/examples/WireSlave/WireSlave.ino
  WireSlave.onReceive(recv);
  WireSlave.onRequest(req);
  WireSlave.begin(I2C_ADDRESS);
#else
  // RP2040, STM32, ESP8266
  // https://github.com/earlephilhower/arduino-pico/blob/master/libraries/Wire/examples/TalkingToMyself/TalkingToMyself.ino
  // https://github.com/stm32duino/Arduino_Core_STM32/blob/main/libraries/Wire/examples/slave_sender/slave_sender.ino
  // https://github.com/esp8266/Arduino/blob/master/libraries/Wire/examples/slave_sender/slave_sender.ino
  WireSlave.begin(I2C_ADDRESS);
  WireSlave.onReceive(recv);
  WireSlave.onRequest(req);
#endif
}

static char buff[100];
void loop() {
  static int p;
  char b[90];

  // Write a value over I2C to the slave
  Serial.println("Sending...");
  WireMaster.beginTransmission(I2C_ADDRESS);
  sprintf(b, "pass %d", p++);
  WireMaster.write(b, strlen(b));
  WireMaster.endTransmission();

  // Ensure the slave processing is done and print it out
  delay(1000);
  Serial.printf("Slave recv buff: '%s'\r\n", buff);

  // Read from the slave and print out
  WireMaster.requestFrom(I2C_ADDRESS, 6);
  Serial.print("\nMaster recv: '");
  while(WireMaster.available()) {
    Serial.print((char)WireMaster.read());
    // Serial.printf("%02X ", (byte)WireMaster.read());
  }
  Serial.println("'");
  delay(1000);
}

// These are called in an **INTERRUPT CONTEXT** which means NO serial port
// access (i.e. Serial.print is illegal) and no memory allocations, etc.

// Called when the I2C slave gets written to
void recv(int len) {
  int i;
  // Just stuff the sent bytes into a global the main routine can pick up and use
  for (i=0; i<len; i++) buff[i] = WireSlave.read();
  buff[i] = 0;
}

// Called when the I2C slave is read from
void req() {
  static int ctr = 765;
  char buff[7];
  // Return a simple incrementing hex value
  sprintf(buff, "%06X", (ctr++) % 65535);
  WireSlave.write(buff, 6);
}

 Board "Generic RP2040"を指定時。
 こんな感じで GPIOの定数が定義されています。
common.hの抜粋
static const uint8_t D0 = (0u);
static const uint8_t D1 = (1u);
static const uint8_t D2 = (2u);
static const uint8_t D3 = (3u);
static const uint8_t D4 = (4u);
static const uint8_t D5 = (5u);
static const uint8_t D6 = (6u);
static const uint8_t D7 = (7u);
static const uint8_t D8 = (8u);
static const uint8_t D9 = (9u);
static const uint8_t D10 = (10u);
static const uint8_t D11 = (11u);
static const uint8_t D12 = (12u);
static const uint8_t D13 = (13u);
static const uint8_t D14 = (14u);
static const uint8_t D15 = (15u);
static const uint8_t D16 = (16u);
static const uint8_t D17 = (17u);
static const uint8_t D18 = (18u);
static const uint8_t D19 = (19u);
static const uint8_t D20 = (20u);
static const uint8_t D21 = (21u);
static const uint8_t D22 = (22u);
static const uint8_t D23 = (23u);
static const uint8_t D24 = (24u);
static const uint8_t D25 = (25u);
static const uint8_t D26 = (26u);
static const uint8_t D27 = (27u);
static const uint8_t D28 = (28u);
static const uint8_t D29 = (29u);


Raspberry Pi Pico ラズベリーパイピコ マイコンRP2040(Arm Cortex-M0+デュアルコア@133MHz (1個)
ASIN: B0972DTW7S

Seeed Studio XIAO RP2040 マイクロコントローラー デュアルコア ARM Cortex M0+ プロセッサ Arduino、MicroPython、サーキットパイソンをサポートし、豊富なインターフェースを備えています。
ASIN: B09NNVNW7M

Thinaokii Pico 用 RP2040 開発ボード 0.42インチLCD付き /prython用
ASIN: B0BYSDG55L

Type-C USB-C RP2040-Plus マイコン ボード for ラズパイ ピコ ラズベリーパイピコ RPI Raspberry Pi PICO MCU ボード ピンヘッダ実装済
ASIN: B09MC3YHD7



Tags: [ワンチップCPU]

●関連するコンテンツ(この記事を読んだ人は、次の記事も読んでいます)

STM32 STM32F103C8T6マイコンボードを ST-Link V2(中華製の互換ドングル)を使って開発
STM32 STM32F103C8T6マイコンボードを ST-Link V2(中華製の互換ドングル)を使って開発

  STM32F103C8 ARM Cortex-M3 72MHz CPU、ST-LINK Utilityでファームのアップデート

STM32 STM32F103C8T6の Windows用の開発環境を無料で構築する方法。CubeMX True STUDIO ST-LINK V2
STM32 STM32F103C8T6の Windows用の開発環境を無料で構築する方法。CubeMX True STUDIO ST-LINK V2

  Windows用の STM32F103C8 ARM Cortex-M3 72MHzの開発環境を無料で作る、STM32CubeMX、TrueSTUDIO、ST-LINK V2

STM32 STM32F103C8T6の USB CDC Virtual COM portドライバを Windows 7に組み込む方法
STM32 STM32F103C8T6の USB CDC Virtual COM portドライバを Windows 7に組み込む方法

  Windows 7で VCPドライバを組み込む時に「INFファイルが無効です」の解決方法、COMポート増殖を防ぐ方法(増えすぎた COMポートを削除)

STM32 STM32F103C8T6の USB CDC Virtual COM portデバイスを実装する
STM32 STM32F103C8T6の USB CDC Virtual COM portデバイスを実装する

  STM32 STM32F103C8T6に STCubeで CDC VCPデバイスを組み込み、動作試験のループバックを実装する

STM32 STM32F103C8T6で ARM GCCの Cソース中にインラインアセンブラを記述する方法
STM32 STM32F103C8T6で ARM GCCの Cソース中にインラインアセンブラを記述する方法

  ARM GCCの Cソース中にインラインアセンブラを記述する方法

STM32 STM32F103C8T6で SPI接続の 1.8インチ TFT液晶を使用する方法
STM32 STM32F103C8T6で SPI接続の 1.8インチ TFT液晶を使用する方法

  STM32に 128x160 ST7735 TFT 1.8インチ LCDを SPI接続して自前アプリから文字列を描画する方法。

STM32 STM32F103C8T6マイコンボード開発、CubeMX STM32CubeMXの使い方
STM32 STM32F103C8T6マイコンボード開発、CubeMX STM32CubeMXの使い方

  STM32マイコン用の初期設定コード生成ツール STM32CubeMXの使い方、USBデバイスの作成方法

STM32 STM32F103C8のクローン(複製品) 108MHz動作の GD32F103C8、CS32F103C8
STM32 STM32F103C8のクローン(複製品) 108MHz動作の GD32F103C8、CS32F103C8

  STM32クローン GigaDevice GD32F103C8T6 108MHz、CKS CS32F103C8T6 72MHz

ラズパイを意識した別物製品 Orange Pi Zeroを買ってみた、Allwinner H2+ Cortex-A7 4core
ラズパイを意識した別物製品 Orange Pi Zeroを買ってみた、Allwinner H2+ Cortex-A7 4core

  オレンジパイはラズパイよりもコスパは良いが情報が無いので利用者側に一定のスキルが必要

Orange Pi PC 2を買ってみた、Allwinner H5 Cortex-A53 4core ARM64
Orange Pi PC 2を買ってみた、Allwinner H5 Cortex-A53 4core ARM64

  ラズパイを意識した別物製品、オレンジパイはラズパイよりもコスパが良い、でも情報が無い

Raspberry Pi Zero Wを海外通販の Pimoroni等での購入方法、購入できる通販ショップ一覧まとめ
Raspberry Pi Zero Wを海外通販の Pimoroni等での購入方法、購入できる通販ショップ一覧まとめ

  ラズパイゼロW ワイヤレスモデルを海外通販でサクッと簡単に個人輸入で入手。技適通過でも国内販売は常に品切れ

大人気の CPUボード、Raspberry Pi 3 Model Bで作ってみよう
大人気の CPUボード、Raspberry Pi 3 Model Bで作ってみよう

  Raspberry Piの開発環境の構築やタッチパネル付き液晶ディスプレイや各種センサーの使い方まとめ

Espressif ESP32 Arduino互換でスケッチが使える WROOM32開発基板
Espressif ESP32 Arduino互換でスケッチが使える WROOM32開発基板

  Espressif ESP32 32ビット Arduino互換マイコンボードをお手軽に開発する方法

Espressif ESP8266 Arduino互換でスケッチが使える ESP-12Eモジュール基板
Espressif ESP8266 Arduino互換でスケッチが使える ESP-12Eモジュール基板

  Espressif ESP8266 ESP-12-E NodeMCU V1 ESP12 CP2102

BangGood通販はドローン以外にも面白い商品がまだまだ有った(電子工作編)
BangGood通販はドローン以外にも面白い商品がまだまだ有った(電子工作編)

  レーザー彫刻機、カラー液晶の DIYオシロ、Arduinoや Raspberry Pi用の小型カラー液晶




[HOME] | [BACK]
リンクフリー(連絡不要、ただしトップページ以外は Web構成の変更で移動する場合があります)
Copyright (c) 2023 FREE WING,Y.Sakamoto
Powered by 猫屋敷工房 & HTML Generator

http://www.neko.ne.jp/~freewing/cpu/rp2040_i2c_master_slave/