这个例程在 AVR 上读取 uart 数据我缺少什么
What am I missing with this routine to read uart data on AVR
我可以很好地读取数据。数据是一系列记录,每条记录以“\r\n”作为终止符结束,然后数据流以“\r\n”结束。第一条记录是完美的,但其余记录缺少前 X 个字符。 X 也没有改变。数据来自调制解调器。
c = UART0_RxChar();
response[0]=c;
i=0;
rec=0;
while((c=UART0_RxChar()) != CR)
{
response[i++]=c;
while ((c=UART0_RxChar()) != CR)
{
response[i++]=c;
}
rec++;
UART1_Printf("Record %d %s", rec, response);
UART1_Printf("\n\n");
memset(response,0,strlen(response));
i=0;
AT_ASSERT(UART0_RxChar() == LF)
}
AT_ASSERT(UART0_RxChar() == LF)
// Finished
收到错误数据
Record 1 7854122,4,2017-04-11 00:00,2017-04-11 8:09,29342441,,,,,,,0,0,0,0,
Record 2 705-03 13:15,18958737,TRK 23564,,,,BOL 327867,,0,0,0,0,
Record 3 7,BOL 327867,,0,0,0,0,
Record 4 717-05-03 23:59,38580000,TRK 23564,,,,BOL 327867,,0,0,0,0,
Record 5 7,BOL 327867,,0,0,0,0,
Record 6 717-05-05 23:59,86340000,TRK 23564,,,,BOL 327867,,0,0,0,0,
Record 7 7,BOL 327867,,0,0,0,0,
实际数据
7854122,4,2017-04-11 00:00,2017-04-11 08:09,29342441,,,,,,,0,0,0,0,
7854122,1,2017-04-11 08:09,,0,,,,,,,0,0,0,0,
7854122,4,2017-05-03 08:00,2017-05-03 13:15,18958737,TRK 23564,,,,BOL 327867,,0,0,0,0,
7854122,1,2017-05-03 13:15,2017-05-03 13:16,70332,TRK 23564,,,,BOL 327867,,0,0,0,0,
7854122,3,2017-05-03 13:16,2017-05-03 23:59,38580000,TRK 23564,,,,BOL 327867,,0,0,0,0,
7854122,3,2017-05-04 00:00,2017-05-04 23:59,86340000,TRK 23564,,,,BOL 327867,,0,0,0,0,
UART 读取数据的速度可能不够快,无法捕获所有数据,因此正在丢弃数据
如果 UART_RxChar 函数正在使用来自中断写入缓冲区的缓冲区,您可以增加缓冲区的大小。
您有一个差一错误导致缓冲区中的第一个字符保持第一次读取时的状态,在本例中为“7”。
主要问题是 printf()
语句花费的时间太长,并且不允许 UART0_RxChar()
函数接收字符,所以它们被简单地覆盖了。
更好的方法可能是使用中断处理程序将传入的字符保存到缓冲区,然后在主循环中缓冲区已满时打印消息。您可能需要在两个缓冲区之间交替,以便您可以在打印另一个缓冲区的内容时填充一个缓冲区。
中断处理程序将具有与您现在所拥有的相似的逻辑:填充缓冲区直到 \cr\lf
,然后设置用于打印的标志并切换到另一个缓冲区。在主循环中忙于等待标志,并在设置时打印。
我可以很好地读取数据。数据是一系列记录,每条记录以“\r\n”作为终止符结束,然后数据流以“\r\n”结束。第一条记录是完美的,但其余记录缺少前 X 个字符。 X 也没有改变。数据来自调制解调器。
c = UART0_RxChar();
response[0]=c;
i=0;
rec=0;
while((c=UART0_RxChar()) != CR)
{
response[i++]=c;
while ((c=UART0_RxChar()) != CR)
{
response[i++]=c;
}
rec++;
UART1_Printf("Record %d %s", rec, response);
UART1_Printf("\n\n");
memset(response,0,strlen(response));
i=0;
AT_ASSERT(UART0_RxChar() == LF)
}
AT_ASSERT(UART0_RxChar() == LF)
// Finished
收到错误数据
Record 1 7854122,4,2017-04-11 00:00,2017-04-11 8:09,29342441,,,,,,,0,0,0,0,
Record 2 705-03 13:15,18958737,TRK 23564,,,,BOL 327867,,0,0,0,0,
Record 3 7,BOL 327867,,0,0,0,0,
Record 4 717-05-03 23:59,38580000,TRK 23564,,,,BOL 327867,,0,0,0,0,
Record 5 7,BOL 327867,,0,0,0,0,
Record 6 717-05-05 23:59,86340000,TRK 23564,,,,BOL 327867,,0,0,0,0,
Record 7 7,BOL 327867,,0,0,0,0,
实际数据
7854122,4,2017-04-11 00:00,2017-04-11 08:09,29342441,,,,,,,0,0,0,0,
7854122,1,2017-04-11 08:09,,0,,,,,,,0,0,0,0,
7854122,4,2017-05-03 08:00,2017-05-03 13:15,18958737,TRK 23564,,,,BOL 327867,,0,0,0,0,
7854122,1,2017-05-03 13:15,2017-05-03 13:16,70332,TRK 23564,,,,BOL 327867,,0,0,0,0,
7854122,3,2017-05-03 13:16,2017-05-03 23:59,38580000,TRK 23564,,,,BOL 327867,,0,0,0,0,
7854122,3,2017-05-04 00:00,2017-05-04 23:59,86340000,TRK 23564,,,,BOL 327867,,0,0,0,0,
UART 读取数据的速度可能不够快,无法捕获所有数据,因此正在丢弃数据
如果 UART_RxChar 函数正在使用来自中断写入缓冲区的缓冲区,您可以增加缓冲区的大小。
您有一个差一错误导致缓冲区中的第一个字符保持第一次读取时的状态,在本例中为“7”。
主要问题是 printf()
语句花费的时间太长,并且不允许 UART0_RxChar()
函数接收字符,所以它们被简单地覆盖了。
更好的方法可能是使用中断处理程序将传入的字符保存到缓冲区,然后在主循环中缓冲区已满时打印消息。您可能需要在两个缓冲区之间交替,以便您可以在打印另一个缓冲区的内容时填充一个缓冲区。
中断处理程序将具有与您现在所拥有的相似的逻辑:填充缓冲区直到 \cr\lf
,然后设置用于打印的标志并切换到另一个缓冲区。在主循环中忙于等待标志,并在设置时打印。