Why does Arduino Nano Every generates 4.5V on TX1, RX1

Hello,
I am trying to establlish HC-12 link between two Arduino Nano Every. The Nano is currently is fed from the USB, while the HC-12 is fed from the Nano 3.3V output (with bypass tantalum 22uF cap). Its consuption is a little more than 50mA' well within the Nano capabilities.

The sketch contains currently only the SETUP method, that sends also some AT commands using HC-12 standard library (https://github.com/PowerBroker2/SerialTransfer).

When I connect loopback across the TX1-RX1 and print the received text - all is good. However, as soon as I connect the RX and TX line (the SET line is grounded in this test configuration) I start reading 4.52V on +5V output, RX1 and TX1 and the l\HC-12 does not respond. The 4.52V remains after disconnecting the TX1 and RX1 lines. In spite the high voltage, the loopback TX1-RX1 works. The same happens on two sets of components.

The 3.3V output is exact if the HC-12 is connected or disconnect, meaning the on-board regulator is not loaded.

void setup() {
  Serial.begin();
  Serial.println("Init started");

  pinMode(LED_BUILTIN, OUTPUT);
  digitalWrite(LED_BUILTIN, false);
  Comm.begin();
}
void loop() {
  Serial1.println("");
  Serial.println ("transmitted");
  delay(20);
  if(Serial1.available())
    Serial.println(Serial1.read());
}

HC-12.h

#ifndef hc12_h
#define hc12_h

#include "src\radio\SerialTransfer.h"

class comm {
public:
  uint16_t machineStationRx();
  uint16_t txData(const String &txStr);
  String remoteControllerTxRx(uint16_t txCommand);
  void begin();
  const uint16_t rxMmachineStationError = 0xffff;
  bool stationType;  // low - machine, high - remote control mode
  uint8_t available () {return myTransfer.available(); };

private:
#define comVerbose
#define txRxPin  15  // MPU D15
#define hc12Mode 16  // MPU D16
#define txDelay 500
#define txInterval 1000
#define txPower '3'

  SerialTransfer myTransfer;
  long intervalCounter;
  uint16_t rxBuffer[4];
  uint16_t msgCount = 1;
  uint16_t previousPacketCounter;
};
#endif

HC-12.cpp

#include "HC12.h"

uint16_t comm::txData (const String &txStr)
{
  uint16_t sendSize = 0;
  sendSize = myTransfer.txObj(txStr.c_str());
  return myTransfer.sendData(sendSize);
}
/************************************************/
void comm::begin() {
  Serial1.begin(9600);
  while (!Serial1)
    ;  // Before actually need the serial ports

  pinMode(txRxPin, INPUT_PULLUP);
  stationType = digitalRead(txRxPin);
  pinMode(hc12Mode, OUTPUT);
  digitalWrite(hc12Mode, false);  // Set commands mode

  intervalCounter = millis();
  configST setUpConfig;
  setUpConfig.debug = false;
  setUpConfig.callbacksLen = 0;
  myTransfer.begin(Serial1, setUpConfig);

  bool hc12error = false;

  uint16_t txLen = txData("AT+P" + txPower);
  delay(10);
  String rxMsg = "";
  uint16_t rxLen = 0;
Serial.print("TX power reply = (1)");  // For debug
Serial.print(String(rxMsg) + " (2) "); // For debug
  rxLen = myTransfer.rxObj(rxMsg, rxLen);
Serial.print(String(rxMsg + " (3) ")); // For debug
  rxLen = myTransfer.rxObj(rxMsg, rxLen);
Serial.print(String(rxMsg));           // For debug
Serial.println();                      // For debug

  char rep[] = { 'O', 'K', '+', 'P', txPower };
  hc12error |= (rxLen != sizeof(rep)) | (rxMsg != rep);
//#ifdef comVerbose
  Serial.println(String(rxMsg));
//#endif

  txLen = txData("AT+B9600");
  delay(10);
  rxLen = myTransfer.rxObj(rxMsg, 0, txLen);
  char rep1[] = "OK+B9600";
  hc12error |= (rxMsg != rep1);
//#ifdef comVerbose
  Serial.print("Baud rate reply = ");
  Serial.println(String(rxMsg));
//#endif
  myTransfer.reset();
  digitalWrite(hc12Mode, true);  // Set transmission mode
  previousPacketCounter = 0;
}
/************************************************/
uint16_t comm::machineStationRx() {
  uint8_t recSize = 0;
  recSize = myTransfer.rxObj(rxBuffer, 0, recSize);
#ifdef comVerbose
  Serial.println("First reception len=" + String(recSize) + "\nbuffer[0], [1]m [2], counter" + String(rxBuffer[0], HEX) + "/" + String(rxBuffer[1], HEX) + "/" + String(rxBuffer[2], HEX) + "/" + String(rxBuffer[3], HEX));
#endif
  recSize = myTransfer.rxObj(rxBuffer, 0, recSize);
  uint16_t tempMsgId = rxMmachineStationError;
  previousPacketCounter = rxBuffer[3];
  // Verify that the message counter is either the the previous message; one skipped message is allowed.
  if ((rxBuffer[3] != tempMsgId - 2) && (rxBuffer[3] != tempMsgId - 1))
    return rxMmachineStationError;

  myTransfer.reset();
  // Voting - 2 items out of 3 should be equal
  if ((rxBuffer[0] != rxBuffer[1]) && (rxBuffer[0] != rxBuffer[2])) {
    if (rxBuffer[1] == rxBuffer[2])
      return rxBuffer[1];
    return rxMmachineStationError;
  }
  return rxBuffer[0];
}
/************************************************/
String comm::remoteControllerTxRx(uint16_t txCommand) {
  //  txPackageId++;
  if ((millis() - intervalCounter) < txInterval)
    return "";
  intervalCounter = millis();
  String txBuffer = String(txCommand, HEX);
  txBuffer += txBuffer + txBuffer + String(msgCount++, HEX);
  uint16_t i = txData(txBuffer);
  if(i != txBuffer.length())
    return "?S tx error";
  long txTimer = millis();
  while (!myTransfer.available() && ((millis() - txTimer) < txDelay))
    ;
  if (!myTransfer.available())  // Analyze loop exit condition
    return "Communication loop timeout";

  uint8_t recSize = 0;
  String receiveData;
  recSize = myTransfer.rxObj(receiveData, recSize);
  if (recSize == 0)
    return "Communication package length error";
  else
    return receiveData;
}

The HC-12 is a 3.3V device. It is not a good idea to power it with 5V or, use it with 5V I/O, although people do so.

You will have better performance and longer component lifetime, using a 3.3V processor with the HC-12.

If you connect the pins of a 5v device to the pins of a 3.3v device (or a device powered by 3.3v) you should use a level shifter. The voltage drop you have reported on the Nano Every is probably due to the pin protection diodes of the chip on the HC-12 board.

I can't find a schematic of the HC-12 module so it is not clear to me if the chip is 5v pin compatible or if there is a regulator on board. Clearly you have a reason for powering it at 3.3 volts.

This HC-12 datasheet indicates that the I/O pins have 1K series resistors, which is a bandaid at best. They should have used level shifters, but resistors are cheaper. It also recommends the power supply be 4.5 V or less, so the on board regulator is the wrong choice.

OK. Thanks for the link. If there is a 1k resistor in the chain between the TX of the Nano Every and the RX of the HC-12 then, assuming the resistor is after the pin protection diodes, it is difficult to explain the significant drop in voltage of the Every's 5v pin down to 4.52. That should be investigated.

Were it not for that observation, I'd have followed the data sheet suggestion to power the HC-12 modules from a 5v supply but with a 1N4007 resistor in series (to lose 0.7v)

This english version of the factory data sheet from HC01 indicates that the UART works at either 3.3 or 5v TTL.

https://www.hc01.com/downloads/HC-12%20english%20datasheets.pdf

RXD input, with pull up resistor
to internal power supply
UART input, 3.3V to 5V TTL level,internal10K resistor to 3.3V power supply4 TXD Output, with pull up resistor
to external VCC
UART output, 3.3V to 5V TTL level,internal200R resistor in series

This topic was automatically closed 180 days after the last reply. New replies are no longer allowed.