Contact me: hankecnc@gmail.com

与 GRBL 回波不同的发送行 #845

推推 grbl 3年前 (2023-01-23) 264次浏览
打开
109JB 开了这个issue 2015 年 11 月 14 日 · 67条评论
打开

与 GRBL 回波不同的发送行#845

109JB 开了这个issue 2015 年 11 月 14 日 · 67条评论

注释

与 GRBL 回波不同的发送行 #845

第一的。让我为这篇文章的篇幅道歉,但我觉得这是一个非常重要的问题。

我一直在做更多的测试来验证 GRBL 运行的 g 代码文件。我决定使用一个串行端口嗅探器程序来准确查看发送的内容和接收的内容,以验证这些未发现的错误是否来自我的 GUI 或其他内容。我确定发送到 GRBL 的数据是正确的,但回显返回不正确,这意味着错误发生在 arduino 或 GRBL 代码中的某处。看看下面的描述,看看我是如何得出这个结论的。

作为进一步测试,我制作了一个小程序用于测试。该程序的流代码非常精简,除了流和检测 GRBL 错误消息绝对必要的内容外,没有任何额外内容。没有其他的。发送响应和字符计数协议都可以使用,但都产生了错误。该程序唯一做的另一件事是记录 GRBL 回波,以便将它们与原始代码进行比较以找出差异。这些文件可以在没有任何定时状态请求的情况下流式传输到 GRBL,并且在关闭定时状态响应时遇到以下错误。

我正在使用 CAM 生成的 g 代码进行测试,该代码被修改为只有 G0 命令。这导致非常快速的流式传输。如果我通过在流代码中故意延迟来稍微减慢流速度,它会按预期工作而不会出现错误,但在全速运行时,GRBL 并不总是回显发送的同一行和/或抛出错误。我已经通过使用串口嗅探器程序验证了发送的行是正确的。

例如,在最近一次使用字符计数流的运行中,在运行开始时发送了以下行:

G01G21G90X-0.5375Y3.5375Z3.3598F4000
X3.8999Z1.0234
X3.896Z1.0262
X3.8645Z1.0475
X3.8566Z1.0527
X3.8212Z1.0742
X3.8173Z1.0765

上面的前 7 行是 GUI 立即发送的,字符计数,包括每行末尾的 LF 巧合地总共 127 个字符,填充了 RX 缓冲区,并使用串口嗅探器验证了发送的行。GRBL 的回应是:

[回显:G01G21G90X-0.5375Y3.5375Z3.3598F4000]

[回显:X3.8999Z1.0234]

[回显:X3.896Z1.0262]

[回显:X3.8645Z1.0475]

[回显:X3.8566Z1。 0527]
好的
[回显:X3.8999Z1.0742]
好的
[回显:X3.8173Z1.0765]
好的

注意第 6 行。来自 GRBL 的回波具有错误的 X 值但正确的 Z 值。请记住,以上所有信息均来自串行端口嗅探器,而不是我自己的程序。然而,当比较来自 GRBL 的回波与原始 G 代码文件时,我的测试程序显示完全相同的东西,表明第 6 行不匹配。同一文件的第二次运行顺利通过了这一点,没有出现错误。

在另一次测试运行期间,发送的行是:

X2.8811Z1.167
X2.889Z1.1702
X2.9362Z1.1889
X2.9441Z1.192

来自 GRBL 的这些回应

[echo: X2.8811Z1.167]
ok
[echo: X2.889Z1.1702]
ok
[echo:]
ok
[echo:]
ok
[echo: .9362Z1.1889]
错误:预期的命令字母
[echo: X2.9441Z1. 192]
好吧

这是在检查模式下使用发送响应协议运行的 90,000 行 G 代码文件的末尾。与之前一样,串行端口嗅探器确认生成错误的行已正确发送,并使用 LF 作为行尾字符。但请注意,GRBL 对该单行回显了 3 次,并在最后的回显中删除了“X2”。串口嗅探器在发送的数据流中没有检测到额外的行尾字符。

我不知道该怎么做。上面的错误,尤其是第一个例子很奇怪,让我觉得这可能是 GRBL 问题,但我不确定。我正在以可以运行的绝对最大速度运行这些测试,并且运行文件的时间可能比以前任何人都长,所以也许我只是超出了 GRBL 的能力,或者这可能仍然与我报告的波特率问题有关。正如我所说,如果我用插入的延迟减慢流循环,但波特率保持不变,错误就会消失。

上周我遇到了似乎与波特率有关的错误。事实上,当仅更改波特率时,这些错误确实消失了,并且使用我的 GUI 中的一个简单代码将原始文件与 GRBL 响应进行比较来验证这一点。我的新测试程序使用相同的比较,运行时的主要区别是新代码不包括我的 GUI 为固定循环、工具更改支持等实现的所有内容,因此运行循环与可能的。

在我的 Arduino Nano 克隆上,我仍然无法在 250000 波特或 76800 波特上生成错误,但在我的 Aruino Mega 克隆上,情况正好相反,错误出现在 250000 波特,但不是 115200 波特。Nano 使用 ch340G USB 转串口芯片,但 Mega 没有,所以也许 USB 芯片是罪魁祸首。我不确定如何进一步测试,但根据显示线路发送正确的串行端口嗅探器程序,在我看来,错误必须与 Arduino 硬件或 GRBL 代码有关。在这一点上,我不知道如何确定它是哪个,但在流式循环中添加一个轻微的延迟似乎工作正常,但会减慢速度。

有人有主意吗?

与 GRBL 回波不同的发送行 #845
贡献者

如何编写一个简单的 Arduino 草图来呼应一个角色,以查明它是一个 grbl 问题还是影响这些平台的更广泛的问题?

与 GRBL 回波不同的发送行 #845
成员

@109JB: 有趣的结果。特别是 Mega 和 Nano 之间的区别。Mega 数据表显示与 Uno 的 328 相同的串行时序错误,因此“应该”排除时序错误,但我认为这里的变量比我们可以肯定地隔离的要多得多。

只是好奇,将每毫米的步长降低一半或更多会如何改变行为?我想知道步进 ISR 是否花费了比预期更多的时间。理论上,执行时间应该相同,但步进 ISR 将以一半的速率触发。这有助于排除步进 ISR。

我也会做什么@kfoltman建议并尝试 Arduino 草图。这可能会告诉你一些事情,但很难复制一切的确切时间。也许在那里放置一个大约 1-4 毫秒的随机延迟,因为这大约是 Grbl 解析和计划 g 代码运动所花费的时间。

与 GRBL 回波不同的发送行 #845
作者

今天大部分时间我都不在,但我确实写了,或者更确切地说是修改了一个 arduino 代码,它只接收一个串行字符串,然后用“ok”回显它以模拟来自 GRBL 的响应。我将详细描述 Arduino 代码的工作原理:

1 – arduino 检测到串行事件并读取单个字符并将其缓冲在字符串变量中。
2 – 重复上述操作,直到检测到“\n”
3 – 一旦检测到 \n,存储的字符串将“[echo:”放在前面,“]”放在后面以模拟 GRBL 响应
4 – 然后使用 Serial.println() 命令发送字符串
5 – 使用附加的 Serial.println(“ok”) 命令来模拟 GRBL“ok”响应

这是一个 10,000 行 g 代码文件的前几行的示例,后面是返回的内容(去掉了“[echo:”和“]”)

G01G21G90X-0.5375Y3.5375Z3.3598F4000
X3.8999Z1.0234
X3.896Z1.0262
X3.8645Z1.0475
X3.8566Z1.0527
X3.8212Z1.0742

G01G21G90X-0.5375Y3.5375Z3.3598F4000
X3.8999Z1.0234X
3.896Z1.0262X
3.8645Z1.0475X
3.8566Z1.0527X3.8212Z1.07
42

我还发现,无论是使用 Arduino 测试代码还是 GRBL 固件,以及使用字符计数还是发送响应,我都可以通过在向 Arduino 发送数据的循环中插入一个小延迟来消除所有错误。

Arduino 测试代码中的延迟并不能消除错误。另外,根据要求@chamnit,在 GRBL 中更改步数/毫米不会影响是否生成错误,但更改最大速率会。steps/mm 会影响 GRBL 代码,但不会影响 GRBL 传输数据所需的速度。但是,更改最大速率将影响数据流传输的速度。所以错误与arduino需要多快从串行流中获取数据有关。此外,使用具有实际移动长度的代码可以消除错误,这也表明流速度是问题所在。

基于使用 GRBL 固件或使用 Arduino 测试代码得到的错误,我相信问题与我拥有的 Arduino 硬件有关。我所有的测试都是使用 Arduino 克隆,而不是真正的 Arduinos。我计划在未来得到一个真正的 Arduino Uno,看看是否同样适用于真正的 Arduinos,但我可能需要一段时间才能得到一个。

似乎所需的延迟也取决于我选择的波特率。对于某些使用发送响应的波特率,我不需要任何延迟就能让它们正常工作。对于其他波特率,即使发送响应也需要延迟,但延迟非常小(1 到 2 毫秒)。对于字符计数,所有波特率都需要这种延迟,但有些只需要 1-2 毫秒,而其他波特率需要大约 5-6 毫秒,还有一些波特率永远无法正常工作。

我确实想指出,仅仅因为 GRBL 没有抛出错误并不意味着没有错误。例如,我之前的帖子强调了一个示例,其中发送的内容与 GRBL 回显的内容不匹配并没有记录 GRBL 的错误,因为该行仍然采用正确的 G 代码格式,但坐标值是错误的。我发现的一些错误只是通过使用对 GRBL 回波与原始 G 代码进行逐行比较的代码才发现的。

与 GRBL 回波不同的发送行 #845

很久以前,我在 AT90S2313 和 max232 上有过这种行为,但在 16U2 和 Capa 1uF( Arduino Uno 图中的
Ucap / C8)上的振荡器侧面看一下,在 Arduino 的克隆上,最近的安装报废部件 以降低制造成本。 无论如何,最好的解决方案是在 GRBL 官方 Arduino 板上运行。

2015-11-15 9:33 GMT+01:00 109JB notifications@github.com

今天大部分时间我都不在,但我确实写了,或者更确切地说是修改了一个
arduino 代码,它只接收一个串行字符串,然后用“ok”回显它
以模拟来自 GRBL 的响应。我将
详细描述 Arduino 代码的工作原理:

1 – arduino 检测到串行事件并读取单个字符并将其
缓冲在字符串变量中。
2 – 重复上述操作,直到检测到“\n”
3 – 一旦检测到 \n,存储的字符串将“[echo:”放在
前面,“]”放在后面以模拟 GRBL 响应
4 – 然后使用 Serial.println() 命令发送字符串
5 – 使用附加的 Serial.println(“ok”) 命令来模拟
GRBL“ok”响应

这是一个 10,000 行 g 代码文件的前几行的示例,
后面是返回的内容(去掉了“[echo:”和“]”)

G01G21G90X-0.5375Y3.5375Z3.3598F4000
X3.8999Z1.0234
X3.896Z1.0262
X3.8645Z1.0475
X3.8566Z1.0527
X3.8212Z1.0742

G01G21G90X-0.5375Y3.5375Z3.3598F4000
X3.8999Z1.0234X
3.896Z1.0262X
3.8645Z1.0475X
3.8566Z1.0527X3.8212Z1.07
42

我还发现,无论是使用 Arduino
测试代码还是 GRBL 固件,以及使用字符计数还是发送
响应,我都可以通过在向 Arduino 发送数据的循环中插入一个小延迟来消除所有错误

Arduino 测试代码中的延迟并不能消除错误。另外,根据
要求@chamnit https://github.com/Chamnit,改变
GRBL 中的 steps/mm 不会影响是否产生错误,但改变
max rate 会。steps/mm 会影响 GRBL 代码,但不会影响 GRBL
传输数据所需的速度。但是,更改最大速率将
影响数据流传输的速度。所以错误与
arduino需要多快从串行流中获取数据有关。此外,使用
具有实际移动长度的代码可以消除错误,这也表明
流速度是问题所在。

基于使用 GRBL 固件或使用
Arduino 测试代码得到的错误,我相信问题与
我拥有的 Arduino 硬件有关。我所有的测试都是使用 Arduino 克隆,而不是真正的
Arduinos。我计划在未来得到一个真正的 Arduino Uno,看看是否
同样适用于真正的 Arduinos,但我可能需要一段时间
才能得到一个。

似乎所需的延迟也取决于我选择的波特率。对于某些使用发送响应的波特率,我不需要任何延迟就能让
它们正常工作。对于其他波特率,即使
发送响应也需要延迟,但延迟非常小(1 到 2 uS)。对于字符
计数,所有波特率都需要这种延迟,但有些只需要 1-2 uS,而
其他波特率需要大约 5-6uS,而其他波特率则永远无法正常工作。

我确实想指出,仅仅因为 GRBL 没有抛出
错误并不意味着没有错误。例如,我之前的帖子强调
了一个示例,其中发送的内容与 GRBL 回显的内容不匹配并
没有记录 GRBL 的错误,因为该行仍然采用正确的 G 代码
格式,但坐标值是错误的。我发现的一些错误只是通过使用 对 GRBL 回波与原始 G 代码
进行逐行比较的代码才发现的。


直接回复此电子邮件或在 GitHub
#845(评论)上查看。

与 GRBL 回波不同的发送行 #845
作者

@euchcat– 谢谢(你的)信息。克隆 Nano 板不使用 16U2,我认为将其归咎于克隆板可能有点为时过早,因为据我所知,没有人在真正的板上做过任何这样的测试。在真正的电路板上进行测试之前,他们仍然会怀疑。

我做了一些更多的测试,并对我的克隆板做出了更多的决定。我制作了一些不同的 Arduino 代码和一些简单的 visual basic 测试程序来检查各种东西。以下是亮点:

1:我尝试了两个Arduino代码来接收串口数据。第一个代码使用 Serial.read() 函数一次读取数据一个字符,直到收到“\n”,而第二个代码使用 Serail.readStringUntil() 函数将数据作为整个字符串读取。尽管功能等效,但使用 Serial.readStringUntil() 的第二个代码导致读取错误少得多并且可以容忍更快的流式传输。这是一个 Arduino 代码而不是 GRBL,但我不知道 GRBL 在这方面是如何工作的。

2:以上代码也回显了接收到的线路。在代码#1中,我使用 Serial.println() 函数发回字符串,依靠 println 函数将 \r\n 附加到末尾。在第二个代码中,我添加了一行以首先将 \r\n 附加到字符串,然后使用 Serial.print() 函数发送它。这导致更少的错误。我发现这个是因为我看到响应中的 \r\n 可能位于与它们应该位于的位置不同的位置。例如,在 \r\n 之前有 2 行响应延迟了几个字符,甚至丢失了几个字符。

3:虽然不确定,但我在 Internet 上阅读了一些内容,这些内容表明从 Serial.read() 到 Serial.print() 需要一些时间并且可能会导致错误。我读过的一些帖子表明,如果立即从阅读到打印,需要在 Arduino 代码中增加故意延迟。我还没有真正发现这是真的,但我想我应该提一下。

4:根据我的测试,我很明显,无论出于何种原因,我的 Arduinos 在连续的系列事件之间需要一段时间。我发现 GRBL 和我的测试 Arduino 代码都是如此。GRBL 似乎需要比发送前将 \r\n 放在末尾的测试代码有更长的延迟。

5:发送-响应协议是 100% 正常的。我发现只要关闭定时状态请求,我就无法使用发送响应生成任何错误。打开定时状态请求后,我认为可能会发生的情况是,可以发送定时请求,从而导致两个串行事件靠得太近,Arduino 无法处理。这是一个非常罕见的事件。我估计在使用完全不切实际的 g 代码程序和快速定时请求时,我大约每 300,000 行代码就可以执行一次此操作。对于现实的程序和较慢的请求(0.2 秒),我认为这甚至不是问题。

6:字符计数协议在发送事件之间使用 GRBL 需要大约 4 毫秒的延迟,以防止发送速度比这更快。在大多数情况下,这不会成为问题,但在发送开始时,前几行肯定可以发送得比这快,从而导致错误。这种延迟确实会减慢速度,但在实际使用中,我认为它不会真正影响实际 G 代码的运行时间。延迟仅在需要放慢速度以防止错误的情况下起作用。可以生成的错误类型是不会导致 GRBL 错误的类型。我的 GUI 在字符计数模式下似乎工作正常,但实际上并非如此,因为发送的行带有细微错误。直到我创建了一个例程来对发送的线路与回显的线路进行逐行比较时,才发现了这一点。

7: 在所有情况下,错误都取决于所选的波特率。Mega 克隆和 Nano 克隆在这方面也有点不同,但我的 Mega 克隆使用 Atmel 16U2 usb 串行芯片,而 Nanos 使用 ch340g 芯片。我认为这可能是这里出现差异的原因。我确实注意到 Nanos 有 2 个晶体,一个用于 USB,一个用于 MCU(12 MHz 对 16 MHz),而 Mega 只有一个 16 Mhz 振荡器。不知道这是怎么回事,但足以说明它们在使用的 USB 到串行硬件方面有所不同。

与 GRBL 回波不同的发送行 #845
成员

@109JB: 我以为我发表了这条评论,但我一定没有。隔离 USB 串行芯片的一种方法是直接嗅探 Arduino 上的 RX/TX 引脚。在 Uno 上,引脚 0 和 1 连接到 USB 串口和 328p。所以你将能够看到两者之间的流量。如果 Grbl 正确地通过 TX 线接收数据,这意味着它与 328p 和/或 Grbl 的串行通信有关。如果它在 328p 接收之前出现乱码,则可能是 USB 串行芯片或主机端 USB。

喜欢 (0)