STM32のFreeRTOSを使ってみる

シリアルオブジェクト


STM32F103RBやSTM32F103VCなど、64ピン以上のコアでは5個のUARTを使うことができます。
STM32F407VGでは、6個のUARTを使うことができます。
以下のコードは、STM32F407VGRTのコードですが、Serial1からSerail6にメッセージを表示します。
STM32F407VGRTの場合、Serial4はSerailにマッピングされているので、Serial.printlnと Serial4.printlnは、同じ結果となります。
各ボードのピンマップはこ ちらに公開されています。
/*
 * genericSTM32F407VGT6
 * https://www.stm32duino.com/viewtopic.php?f=12&t=824
 */

#if 0
WEAK const PinMap PinMap_UART_TX[] = {
  {PA_0,       UART4,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART4)},
  {PA_2,       USART2, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART2)},
  {PA_9,       USART1, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART1)},
  {PB_6,       USART1, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART1)},
  {PB_10,      USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {PC_6,       USART6, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_USART6)},
  {PC_10,      UART4,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART4)},
  {PC_10_ALT1, USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {PC_12,      UART5,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART5)},
  {PD_5,       USART2, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART2)},
  {PD_8,       USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {NC,         NP,     0}
};

WEAK const PinMap PinMap_UART_RX[] = {
  {PA_1,       UART4,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART4)},
  {PA_3,       USART2, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART2)},
  {PA_10,      USART1, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART1)},
  {PB_7,       USART1, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART1)},
  {PB_11,      USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {PC_7,       USART6, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_USART6)},
  {PC_11,      UART4,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART4)},
  {PC_11_ALT1, USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {PD_2,       UART5,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART5)},
  {PD_6,       USART2, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART2)},
  {PD_9,       USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {NC,         NP,     0}
};
#endif

#include <Arduino.h>
HardwareSerial Serial1(USART1);
HardwareSerial Serial2(USART2);
HardwareSerial Serial3(USART3);
//HardwareSerial Serial4(UART4);
HardwareSerial Serial5(UART5);
HardwareSerial Serial6(USART6);

#define BAUDRATE 115200

void setup() {
  Serial6.begin(BAUDRATE); Serial6.println("serial 6"); // PC6/PC7
  Serial5.begin(BAUDRATE); Serial5.println("serial 5"); // PC12/PD2
  Serial4.begin(BAUDRATE); Serial4.println("serial 4"); // PA0/PA1
  Serial3.begin(BAUDRATE); Serial3.println("serial 3"); // PB10/PC5
  Serial2.begin(BAUDRATE); Serial2.println("serial 2"); // PA2/PA3
  Serial1.begin(BAUDRATE); Serial1.println("serial 1"); // PA9/PA10
  /* Serial.begin(BAUDRATE); */
  Serial.println("serial (same as 4)");
  Serial.println("*****");
}

void loop() {
  Serial6.println("serial 6");
  Serial5.println("serial 5");
  Serial4.println("serial 4");
  Serial3.println("serial 3");
  Serial2.println("serial 2");
  Serial1.println("serial 1");
  Serial.println("serial (same as 4)");
  Serial.println("*****");
  delay(1000);
}



シリアルオブジェクトを変数として扱うことで、コードを共通化することができます。
シリアルオブジェクトを変数として扱う方法は、こ ちらこ ちら公開されています。
こちらのコードは上のコードと同じ結果となります。
/*
 * genericSTM32F407VGT6
 * https://www.stm32duino.com/viewtopic.php?f=12&t=824
 */

#if 0
WEAK const PinMap PinMap_UART_TX[] = {
  {PA_0,       UART4,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART4)},
  {PA_2,       USART2, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART2)},
  {PA_9,       USART1, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART1)},
  {PB_6,       USART1, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART1)},
  {PB_10,      USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {PC_6,       USART6, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_USART6)},
  {PC_10,      UART4,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART4)},
  {PC_10_ALT1, USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {PC_12,      UART5,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART5)},
  {PD_5,       USART2, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART2)},
  {PD_8,       USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {NC,         NP,     0}
};

WEAK const PinMap PinMap_UART_RX[] = {
  {PA_1,       UART4,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART4)},
  {PA_3,       USART2, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART2)},
  {PA_10,      USART1, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART1)},
  {PB_7,       USART1, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART1)},
  {PB_11,      USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {PC_7,       USART6, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_USART6)},
  {PC_11,      UART4,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART4)},
  {PC_11_ALT1, USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {PD_2,       UART5,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART5)},
  {PD_6,       USART2, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART2)},
  {PD_9,       USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {NC,         NP,     0}
};
#endif

#include <Arduino.h>
HardwareSerial Serial1(USART1);
HardwareSerial Serial2(USART2);
HardwareSerial Serial3(USART3);
//HardwareSerial Serial4(UART4);
HardwareSerial Serial5(UART5);
HardwareSerial Serial6(USART6);

#define BAUDRATE 115200

void setup() {
  Serial6.begin(BAUDRATE); Serial6.println("serial 6"); // PC6/PC7
  Serial5.begin(BAUDRATE); Serial5.println("serial 5"); // PC12/PD2
  Serial4.begin(BAUDRATE); Serial4.println("serial 4"); // PA0/PA1
  Serial3.begin(BAUDRATE); Serial3.println("serial 3"); // PB10/PC5
  Serial2.begin(BAUDRATE); Serial2.println("serial 2"); // PA2/PA3
  Serial1.begin(BAUDRATE); Serial1.println("serial 1"); // PA9/PA10
  /* Serial.begin(BAUDRATE); */
  Serial.println("serial (same as 4)");
  Serial.println("*****");
}

void SerialHandler(HardwareSerial *port, char * text)
{
  port->println(text);
}

void loop() {
  SerialHandler(&Serial6, (char *)"serial 6");
  SerialHandler(&Serial5, (char *)"serial 5");
  SerialHandler(&Serial4, (char *)"serial 4");
  SerialHandler(&Serial3, (char *)"serial 3");
  SerialHandler(&Serial2, (char *)"serial 2");
  SerialHandler(&Serial1, (char *)"serial 1");
  Serial.println("serial (same as 4)");
  Serial.println("*****");
  delay(1000);
}

複数のUARTから入力を行う場合、このように書くと入力処理を共通化することができます。
/*
 * genericSTM32F407VGT6
 * https://www.stm32duino.com/viewtopic.php?f=12&t=824
 */

#if 0
WEAK const PinMap PinMap_UART_TX[] = {
  {PA_0,       UART4,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART4)},
  {PA_2,       USART2, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART2)},
  {PA_9,       USART1, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART1)},
  {PB_6,       USART1, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART1)},
  {PB_10,      USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {PC_6,       USART6, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_USART6)},
  {PC_10,      UART4,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART4)},
  {PC_10_ALT1, USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {PC_12,      UART5,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART5)},
  {PD_5,       USART2, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART2)},
  {PD_8,       USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {NC,         NP,     0}
};

WEAK const PinMap PinMap_UART_RX[] = {
  {PA_1,       UART4,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART4)},
  {PA_3,       USART2, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART2)},
  {PA_10,      USART1, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART1)},
  {PB_7,       USART1, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART1)},
  {PB_11,      USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {PC_7,       USART6, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_USART6)},
  {PC_11,      UART4,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART4)},
  {PC_11_ALT1, USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {PD_2,       UART5,  STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF8_UART5)},
  {PD_6,       USART2, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART2)},
  {PD_9,       USART3, STM_PIN_DATA(STM_MODE_AF_PP, GPIO_PULLUP, GPIO_AF7_USART3)},
  {NC,         NP,     0}
};
#endif

#include <Arduino.h>
HardwareSerial Serial1(USART1);
HardwareSerial Serial2(USART2);
HardwareSerial Serial3(USART3);
//HardwareSerial Serial4(UART4);
HardwareSerial Serial5(UART5);
HardwareSerial Serial6(USART6);

#define BAUDRATE 115200

har buffer1[64];
char buffer2[64];
char buffer3[64];
char buffer4[64];
char buffer5[64];
char buffer6[64];

int index1;
int index2;
int index3;
int index4;
int index5;
int index6;

void setup() {
  Serial6.begin(BAUDRATE); Serial6.println("serial 6"); // PC6/PC7
  Serial5.begin(BAUDRATE); Serial5.println("serial 5"); // PC12/PD2
  Serial4.begin(BAUDRATE); Serial4.println("serial 4"); // PA0/PA1
  Serial3.begin(BAUDRATE); Serial3.println("serial 3"); // PB10/PC5
  Serial2.begin(BAUDRATE); Serial2.println("serial 2"); // PA2/PA3
  Serial1.begin(BAUDRATE); Serial1.println("serial 1"); // PA9/PA10
  /* Serial.begin(BAUDRATE); */
  Serial.println("serial (same as 4)");
  Serial.println("*****");
}

int SerialHandler(HardwareSerial *port, int *index, char * buffer)
{
  if (port->available() > 0) {
    // read the incoming byte:
    unsigned char c = port->read();

    if (c == 0x0d) {

    } else if (c == 0x0a) {
      buffer[*index] = c;
      *index++;
      buffer[*index] = 0;
      return *index;
    } else {
      buffer[*index] = c;
      *index++;
      buffer[*index] = 0;
    }

  } // end if
  return 0;
}

void loop() {
  if (SerialHandler(&Serial6, &index6, buffer6)) {
    Serial.print(buffer6);
    index6 = 0;
  }
  if (SerialHandler(&Serial5, &index5, buffer5)) {
    Serial.print(buffer6);
    index5 = 0;
  }
  if (SerialHandler(&Serial3, &index3, buffer3)) {
    Serial.print(buffer3);
    index3 = 0;
  }
  Serial.println("serial (same as 4)");
  Serial.println("*****");
  delay(1000);
}

残念ながらFreeRTOS環境で、ArduinoのSerialオブジェクトは使えません。
Arduinoのオブジェクトは、スレッドセーフに作られていないのが原因です。

続く...