Arduino - garbled serial output
我已经将ADH8066(Sparkfun)GSM模块连接到了我的Arduino Uno,并试图在Arduino和GSM模块之间进行一些正确的串行连接。当我直接连接(通过USB或仅通过TTL线)连接到Arduino时,它工作正常。某些文本将正确输出,其余文本将显示乱码,几乎就像波特率是错误的一样,但是我只是使用与从PC连接时相同的波特率(115200)。
这是我正在使用的Arduino代码:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 | #include <SoftwareSerial.h> #define rxPin 7 #define txPin 8 SoftwareSerial mySerial = SoftwareSerial(rxPin, txPin); // EN: String buffer for the GPRS shield message String SmsStorePos = String(""); String msg = String(""); String snTmp = String(""); String snFull = String(""); // EN: Set to 1 when the next GPRS shield message will contains the SMS message int SmsContentFlag = 0; // EN: Pin of the LED to turn ON and OFF depending on the received message int ledPin = 5; int powerPin = 6; void setup() { mySerial.begin(115200); // the GPRS baud rate mySerial.print("\ "); delay(1000); Serial.begin(115200); // the Arduino IDE serial Serial.println("Started!"); pinMode( ledPin, OUTPUT ); digitalWrite( ledPin, LOW ); pinMode( powerPin, OUTPUT); digitalWrite(powerPin, LOW); // brings ONKEY low to turn on the modem (aka pressing the ONKEY) delay(3000); digitalWrite(powerPin, HIGH); // sets the pin HIGH again (restore 5V) delay(5000); // test LED pin digitalWrite ( ledPin, HIGH); delay(1000); digitalWrite( ledPin, LOW); } void loop() { char SerialInByte; // Send anything we receive from the IDE to the modem if(Serial.available()) { mySerial.print((unsigned char)Serial.read()); } else if(mySerial.available()) { char SerialInByte; SerialInByte = (unsigned char)mySerial.read(); //SerialInByte = mySerial.read(); // EN: Relay to Arduino IDE Monitor Serial.print( SerialInByte ); // ------------------------------------------------------------------- // EN: Program also listen to the GPRS shield message. // ------------------------------------------------------------------- // EN: If the message ends with <CR> then process the message if( SerialInByte == 13 ){ // EN: Store the char into the message buffer ProcessGprsMsg(); } if( SerialInByte == 10 ){ // EN: Skip Line feed } else { // EN: store the current character in the message string buffer msg += String(SerialInByte); } } } // EN: Make action based on the content of the SMS. // Notice than SMS content is the result of the processing of several GPRS shield messages. void ProcessSms( String sms ){ sms.toLowerCase(); Serial.print("ProcessSms for [" ); Serial.print( sms ); Serial.println("]" ); if( sms.indexOf("on") >= 0 ){ digitalWrite( ledPin, HIGH ); Serial.println("LED IS ON" ); return; } if( sms.indexOf("off") >= 0 ){ digitalWrite( ledPin, LOW ); Serial.println("LED IS OFF" ); return; } else { mySerial.print("AT+CMGF=1\ "); //Because we want to send the SMS in text mode delay(1000); mySerial.print("AT+CMGS=""); mySerial.print(snFull); mySerial.print(""\ "); delay(1000); mySerial.print("Unknown Command:"); mySerial.print(sms); mySerial.print("\ "); delay(1000); mySerial.write(0x1A); //Equivalent to sending Ctrl+Z return; } } // EN: Request Text Mode for SMS messaging void GprsTextModeSMS(){ mySerial.println("AT+CMGF=1" ); } void GprsReadSmsStore( String SmsStorePos ){ // Serial.print("GprsReadSmsStore for storePos" ); // Serial.println( SmsStorePos ); mySerial.print("AT+CMGR=" ); mySerial.println( SmsStorePos ); } // EN: Clear the GPRS shield message buffer void ClearGprsMsg(){ msg =""; } // EN: interpret the GPRS shield message and act appropiately void ProcessGprsMsg() { Serial.println(""); Serial.print("GPRS Message: [" ); Serial.print( msg ); Serial.println("]" ); if( msg.indexOf("Call Ready" ) >= 0 ){ Serial.println("*** GPRS Shield registered on Mobile Network ***" ); GprsTextModeSMS(); } // EN: unsolicited message received when getting a SMS message if( msg.indexOf("+CMTI" ) >= 0 ){ Serial.println("*** SMS Received ***" ); // EN: Look for the coma in the full message (+CMTI:"SM",6) // In the sample, the SMS is stored at position 6 int iPos = msg.indexOf("," ); SmsStorePos = msg.substring( iPos+1 ); Serial.print("SMS stored at" ); Serial.println( SmsStorePos ); // EN: Ask to read the SMS store GprsReadSmsStore( SmsStorePos ); } // EN: SMS store read via UART (result of GprsReadSmsStore request) if( msg.indexOf("+CMGR:" ) >= 0 ){ // get number of sender int snPos = msg.indexOf("+1"); Serial.print("SMS From:"); snTmp = msg.substring(snPos+1); snFull =""; for (int i = 0; i < 11; i++){ snFull += snTmp[i]; } Serial.println(snFull); // EN: Next message will contains the BODY of SMS SmsContentFlag = 1; // EN: Following lines are essentiel to not clear the flag! ClearGprsMsg(); return; } // EN: +CMGR message just before indicate that the following GRPS Shield message // (this message) will contains the SMS body if( SmsContentFlag == 1 ){ Serial.println("*** SMS MESSAGE CONTENT ***" ); Serial.println( msg ); Serial.println("*** END OF SMS MESSAGE ***" ); ProcessSms( msg ); delSMS(); } ClearGprsMsg(); // EN: Always clear the flag SmsContentFlag = 0; } void delSMS() { mySerial.print("AT+CMGD="); mySerial.println(SmsStorePos); } |
下面是我在串行监视器中看到的内容:
确保" baud "设置与您的草图匹配。
例如:Serial.begin(115200); >>>> 115200在控制台中的波特率。
我是从kunalbhat上面的评论中得到这个解决方案的。但是我想将其作为独立答案发布,因为它解决了我的问题,而且对我而言从来没有发生过。因此,我认为这会对很多其他人有所帮助。
众所周知,SoftwareSerial在时间上会挑剔,并且会在您同时描述"太多"时引起问题。由于您正在一边做其他事情,所以它可能不同步。
我热烈推荐AltSoftSerial(http://www.pjrc.com/teensy/td_libs_AltSoftSerial.html),它的性能要好得多,但我仍然建议您使用稍低的波特率来提高可靠性。太高的波特率将需要非常精确的时序以确保不会丢失任何一位,并且硬件的功能不足以在软件中进行串行通信而不会出现问题。
原因是,您需要设置命令AT UART_DEF = 9600,8,1,0,0将ESP的波特率重置为9600,或者也可以使用AT CIOBAUD = 9600!试试吧,它对我有用!我曾在某些ESP-01和ESP-12模块上尝试过AT IPR,有时它可以工作,有时却不行(在非常糟糕的情况下,波特率会完全改变)!
如前所述,问题在于" baud"设置(与串行通信有关,这是另一个答案)。可以(通常)在草图的顶部找到它,并且可能看起来像这样:
1 | Serial.begin(9600); |
或者这个:
1 | Serial.begin(115200); |
对于Arduino Uno,9600以外的" baud "设置将导致文本乱码。因此,请确保在草图的开头具有以下行:
1 | Serial.begin(9600); |
随时询问您是否需要任何进一步的帮助。
我正在使用Arduino编程ATtiny84,但是在第一行之后出现乱码输出或串行停止,直到重置Arduino。
问题是Arduino加载了\\'Arduino as ISP \\'草图,这干扰了来自ATtiny84的串行数据。
将空白草图上传到Arduino进行了修复。
您应该使用串行库,而不是软件串行。串行是Arduino IDE中的官方版本,默认包含在每个程序中。确保显示器和程序上的波特率相等,这是乱码的常见错误。建议使用9600的波特率,并且可以使用Serial.begin(9600),Serial.read(),Serial.print(")和Serial.println(")之类的命令。
我不得不回到我的超级硬件上才能使它工作。从未与sw serial
交好运
硬件串行sim900到mega:
// sim900上的中间rx / tx引脚与mega
上的tx1 / rx1引脚
我必须将" baud "设置更改为9600。
1 | Serial.begin(9600); |