UART如何知道数据位和开始/停止位之间的区别?

电器工程 串行 UART
2022-01-13 00:18:37

我了解 UART 方案通常使用 8N1,即 1 个起始位、8 个数据位和 1 个停止位。像这样的东西:

0 xxxxxxx 1

其中 0 是起始位,x 是数据,1 是停止位。在连续发送多个帧的情况下,您将拥有以下内容:

0 xxxxxxx 10 xxxxxxx 10 xxxxxxx 1

我的问题是:接收器如何分辨开始/停止位和数据位之间的区别?为了说明这一点,假设数据字节 0xAA 一遍又一遍。这看起来像:

0 10101010 10 10101010 10 10101010 10 10101010 10 10101010 1

我将开始/停止位加粗以强调,但在我看来,确实没有办法将这些与数据位区分开来。

当然,如果接收器自很久以前就与发射器建立了可靠的无差错连接,那么我可以看到这不会成为问题。或者,如果字节没有被背靠背发送,那么这不会是一个问题。但是我使用过一个接一个地连续传输字节的 8N1 电路,我可以在传输过程中断开/重新连接电线,接收器总是会立即跳回正确接收。这怎么可能?

4个回答

它正在检测起始位。这正是它的目的。空闲线将如下所示:

...1111111111111111111111111111111...

一旦接收器0在很长一段时间后看到(或在停止位之后,我们将很快看到),它就知道传输已开始并开始计数位。它知道8起始位之后的位(或由配置定义)是数据。第 9 个是停止位,应该是1如果不是 - 发生帧错误并且需要重新同步。

接收到停止位后,它又开始等待开始位。等等。

从理论上讲,如果该行如下所示,则同步可能会出现问题:

..1010101010101010101.... 

或类似的,所以在这种情况下接收器不会看到从哪里开始,但在这种情况下它并不重要,因为开始位置不会有任何区别。但是为了避免这样的问题,一些协议为停止位定义了 1.5(一个半)位长度以使其唯一。或者,在实践中,两个数据包之间总是存在一些时间延迟,因此线路空闲的时间足够长,以允许接收器进行同步。

这听起来像是有人试图在软件或 FPGA 中模拟 UART 接收器的问题。对于 RS-232,他们使用术语markspace但这些通常在数字化后分别对应为“1”和“0”。

UART 接收器通常将每个位时间(必须先验地知道)分成至少 4 个,但通常是 16 个或更多的子周期。它以期望串行接收器线处于标记状态的状态开始(上电/复位时)。如果此时线路不在标记中,则它知道它在传输帧的中间,并且必须等待直到它可以同步。如果该行处于标记状态,则它可能会可能不会在某事中间,将不得不拭目以待。这是 RS-232 的一个问题,如果只是在串行通信发生时插入另一个设备,或者如果部分水龙头监控其他两个播放器之间的异步串行通信并且刚刚被重置。可以肯定的是,无论如何,当退出复位时,UART 需要观察至少 N 位时间(其中 N 是每个字的位数,通常是 7 或 8,并且假设这里没有奇偶校验选项)值标记后跟一位空间时间以重新同步(或者 N+1 位空间时间.) 许多没有携带那么多状态,因此如果在流中间开始,它们可能会错误地同步。您经常会遇到帧错误和偶尔的数据字节,直到它意外地再次正确地重新同步。这通常也是可以接受的价格。通常,电缆已连接并且设备以特定的操作顺序通电,因此很少有任何问题。

但是,一旦同步,UART 就知道会发生什么。它总是以接收线从一个标记到一个空格开始,所需的起始位持续一个完整的位时间,然后是数据位,然后是至少一个位时间的标记(或更长)作为停止少量。如果它保持同步,那么它将看到该模式一遍又一遍地重复。

将比特时间缩短到 4X 或 16X 的部分原因是发送器和接收器使用的时钟不一定完全准确,否则它们只是彼此异步。因此,接收器中进行的部分同步是将其分割的周期与发射器的时序对齐。完成的粒度越细,接收器的对齐就越好。

UART 在开始时需要静音以捕获第一个起始位。然后它只是根据预定义的位数进行计数,到达停止位并再次等待开始位。如果 UART 在长消息的中间开始接收 - 很容易它可能只是垃圾。

它可以分辨出差异,因为它知道它们应该在比特流中的哪个位置(因为你告诉了它)。

请记住,在达成一致的意义之前,任何符号都是没有意义的。