【问题标题】:Twincat 3 Using FB_MBReadRegs ModbusTwincat 3 使用 FB_MBReadRegs Modbus
【发布时间】:2021-03-29 09:55:39
【问题描述】:

当工厂 IO 发送/接收输入和保持寄存器时,我无法让 FB_MBReadinputs 在 Twincat 中工作。

首先,这是我目前从 Factory IO 处理 Modbus 的工作片段:

VAR
    GAB_FactoryIO_Inputs    AT %I*  :   ARRAY [0..15] OF BYTE;
... 
END_VAR

LFB_MBReadInputs(
    sIPAddr := '192.168.0.109',
    nTCPPort := 505,
    nUnitID := 255,
    nQuantity := 64,
    nMBAddr := 0,
    cbLength := SIZEOF(IO.GAB_FactoryIO_Inputs),
    pDestAddr := ADR(IO.GAB_FactoryIO_Inputs),
    bExecute := TRUE,
    tTimeout := T#1S,
    bBusy => ,
    bError => ,
    nErrId => ,
    cbRead => ,
 );
LFB_MBReadInputs(bExecute := FALSE);

它在状态机中运行并愉快地生成字节,以再次由 MBWriteCoils 写入。

但我无法工作的是 FB_MBReadRegs。 Beckhoff 的示例在 MBReadInputs 和 MBReadRegs 之间看起来几乎相同,我首先遇到 ADS 错误 1794 并将 VAR 更改为 DINT 和 WORD,但现在没有任何反应,而是出现错误。 我期望 X、Y 和 Z 坐标指向寄存器上的任何字节、位或整数,但绝对没有任何反应。

我已经尝试简化并找出问题所在,这是目前正在发生的事情:

VAR
GAB_FactoryIO_RegsIN    AT %I*  :   ARRAY [0..5] OF DINT;
    
LFB_MBReadRegs(
        sIPAddr := '192.168.0.109',
        nTCPPort := 505,
        nUnitID := 255,
        nQuantity := 16,
        nMBAddr := 0,
        cbLength := 100,
        pDestAddr := ADR(IO.GAB_FactoryIO_RegsIN),
        bExecute := TRUE,
        tTimeout := T#1S,
        bBusy => ,
        bError => ,
        nErrId => ,
        cbRead => ,
     );
    LFB_MBReadRegs(bExecute := FALSE);

据我所知,添加@kolyur 的建议作为状态机的一部分。

显然现在我有一个新的尝试,如果 FB_MBReadRegs=bBusy THEN... 不起作用。 “错误功能块 'FB_MBReadRegs' 必须实例化才能被访问”。所以这是明天要弄清楚的项目。

玩了一段时间后,我仍然没有完全掌握使用或不使用 %I*,但 %M*(或 %MB0 和 %MB64)确实可以解决问题。在https://forge.codesys.com/forge/talk/CODESYS-V2/thread/cc22cd1dc1/ 找到部分解决方案 无论如何,我误解了 MBReadRegs 的作用,因为 MBReadInputRegs 是它在从 Factorio 接收位置信息/任何内容时所在的位置。

下面显然是有效的代码片段:

VAR_GLOBAL
    GAB_FactoryIO_Inputs    AT %I*  :   ARRAY [0..15] OF BYTE;  //I/O between Factory IO and TC
    GAB_FactoryIO_Outputs   AT %Q*  :   ARRAY [0..15] OF BYTE;
    GAB_FactoryIO_RegsIN    AT %MB0     :   ARRAY [0..5] OF WORD;  // %M* on both didnt work, coordinates spiraled to thousands
    GAB_FactoryIO_RegsOUT   AT %MB32    :   ARRAY [0..5] OF WORD;
    END_VAR


      
VAR;
    LFB_MBReadInputRegs     : FB_MBReadInputRegs  ;
END_VAR

    CASE iState OF
    //...other states in between
    10:  //next is in its own file

    LFB_MBReadInputRegs(
        sIPAddr := '192.168.0.109',
        nTCPPort := 505,
        nUnitID := 255,
        nQuantity := 12,
        nMBAddr := 0,
        cbLength := 100,
        pDestAddr := ADR(IO.GAB_FactoryIO_RegsIN),
        bExecute := TRUE,
        tTimeout := T#1S,
        bBusy => ,
        bError => ,
        nErrId => ,
        cbRead => ,
     );
    LFB_MBReadInputRegs(bExecute := FALSE);
    //5ms wait routine and jump to next iState

稍后再编辑:

bErr 1794 不会消失的新情况。

  • 出于某种原因,cbLength 不再喜欢 100,但必须读取其大小
  • 也重新启动。如果我只是切断 PLC 电源开关的电源,就可以避免无用的故障排除。尽管逻辑上认为软件重启同样好,但无论如何硬重置内存问题都会得到改善。
IF NOT bModbusBusy4 THEN
        bModbusBusy4    := TRUE;
fbMBReadInputRegs (
    sIPAddr := ipAddr,
    nTCPPort := 506,
    nUnitID := 255,
    nQuantity := 32,
    nMBAddr := 0,
    cbLength := SIZEOF(TIO.GAB_FactoryIO_RegsIN),
    pDestAddr := ADR(TIO.GAB_FactoryIO_RegsIN),
    bExecute := TRUE,
    tTimeout := T#1S,
    bBusy => ,
    bError => ,
    nErrId => ,
    cbRead => ,
 );
  ELSE
    IF NOT fbMBReadInputRegs.bBusy THEN
        bModbusBusy4    := FALSE;
    END_IF
fbMBReadInputRegs(bExecute := FALSE);
END_IF

【问题讨论】:

  • 欢迎来到 StackOverflow。你检查错误代码了吗?
  • 啊,忘了说。 “1794 无效索引组”。我猜 Twincat 不喜欢字节,而是 DINT

标签: twincat structured-text


【解决方案1】:

我注意到了一些事情:

  • MBReadRegs 将写入您的数组 GAB_FactoryIO_RegsIN 但您已在输入空间 %I* 中配置了此变量。有什么原因吗?
  • 在第二个示例中,您正在读取 16 个字,但目标变量只有 12 个字(ARRAY [0..5] OF DINT)。这可能是 ADS 错误 1794“无效索引组”的原因。在 MBReadRegs 中,nQuantity 指的是 16 位字,而 MBReadInputs 对位进行计数。
  • 您在每次扫描时触发 bExecute 位。一般应触发一次,等待 bBusy 位变为 false 后再触发。

【讨论】:

  • - 我是初学者,我认为 %I* 在处理虚拟输入/输出时会起作用。没有它实际上没有尝试过。 - 我将尝试将其更改为 12 - 让我们尝试一下,据我所知,我将使用建议的编辑来编辑问题。干杯队友
  • 除非您有特定原因,否则通常不需要在变量声明中包含地址。如果要将变量链接到物理 I/O,则需要 %I* 和 %Q*。在某些情况下,%M 是必需的,例如,如果您有一个外部通信驱动程序通过 ADS 访问特定地址。但除此之外,您可以将地址留空,TwinCAT 会自动分配它。
猜你喜欢
  • 2022-07-05
  • 2021-12-04
  • 1970-01-01
  • 2016-11-15
  • 1970-01-01
  • 2022-09-27
  • 1970-01-01
  • 2018-09-01
  • 1970-01-01
相关资源
最近更新 更多