Welcome to our new forum
All users of the legacy CODESYS Forums, please create a new account at account.codesys.com. But make sure to use the same E-Mail address as in the old Forum. Then your posts will be matched. Close

Problem With For Loop and Trig bug

omeo
2018-02-01
2023-08-17
  • omeo - 2018-02-01

    Hi
    I recently modified a project, but I found that when I changed the trig array value and the for loop did not change, it caused an error in the data:
    exp:

    PROGRAM PLC_PRG
    VAR
       ft_Ctrl: ARRAY [0..2] OF F_TRIG;
       rt_Ctrl: R_TRIG;
       
       index: INT;
       iState: INT;
       xCmd: BOOL;
       xAutoMode: BOOL;
       xDone: BOOL;
    END_VAR
    --------------------------------------------
    FOR index :=0 TO 3 DO
       IF ft_Ctrl[index].Q THEN
          iState:=90;
       END_IF
    END_FOR
    rt_ctrl(CLK:=xCmd);
    xAutoMode S= rt_Ctrl.Q;
    CASE iState OF
       0:
          IF xAutoMode THEN
             iState:=10;
          END_IF
       10:
          iState:=90;
          xAutoMode:=FALSE;
          xDone:=TRUE;
       90:
          iState:=0;
          xAutoMode:=FALSE;
    END_CASE
    

    Notice that in the definition I give f_trig [0..2] and call f_trig [3] in the for loop without error。

    In this program, I hope that when xCmd is the rising edge, iState followed by 10,90 and then back to 0.
    But in fact, I use a single loop to monitor, the first loop iState set to 10. in the second loop, ft_Ctrl [3]. Q actually call the value of rt_Ctrl.Q and iState set to 90,and then back to 0.

    This is very hard to find, because the actual project is large, I forgot to change the for statement after changing the definition of the variable, resulting in the emergence of this problem. I tested this on both somachine and twincat. So if this is the case, can the alarm be exceeded?

    sorry for google translate..and thanks for attention

     
  • omeo - 2018-02-01

    Make it simpler:

    PROGRAM PLC_PRG
    VAR
       ft_Ctrl: ARRAY[0..1] OF F_TRIG;
       rt_Ctrl: R_TRIG;
       
       index: INT;
       xCmd: BOOL;
       xDone:BOOL;
    END_VAR
    --------------------------
    FOR index := 0 TO 3 DO
       IF ft_Ctrl[index].Q THEN
          xDone:=TRUE;
       END_IF
    END_FOR
    rt_ctrl(CLK:=xCmd);
    

    At this program,when xCmd R_TRIG,xDone will be true.
    I think it may be coherent after compilation so the address is continuously pointed, but it is somewhat counterproductive..

     
  • eschwellinger

    eschwellinger - 2018-02-01

    Hi,
    So your question is basically :
    How to find in huge projects these kind of application errors?
    You need to add the implcit check function: check bounds.
    Then set brakepoints for upper and lower - then you will find the code in your application where you write below the array...

    Note: later you need to remove this implicit functions again... ( just for the application development they should be in the application due Performance issues)

    BR
    Edwin

    IMG: Setbrakepoints.jpg

    IMG: checkarrayboungs.jpg

    IMG: Pouforimplicitchecks.jpg

     
  • omeo - 2018-02-01

    Yes, this is perfect
    Thank you very much

     
  • eschwellinger

    eschwellinger - 2018-02-01

    Hi,

    Zitat:
    the future version can join this check function?

    every CODESYS Version has this checkfunctions build in!
    BR
    Edwin

     
  • omeo - 2018-02-01

    I think for some time, if you write the program should be able to avoid this problem:

    PROGRAM PLC_PRG
    VAR
       ft_Ctrl: ARRAY[0..iMax_ft_Number] OF F_TRIG;
       rt_Ctrl: R_TRIG;
       index: INT;
       xCmd: BOOL;
       xDone:BOOL;
    END_VAR
    VAR CONSTANT
       iMax_ft_Number:INT:=2;
    END_VAR
    ---------------
    FOR index := 0 TO 5 DO
       IF ft_Ctrl[LIMIT(0,index,iMax_ft_Number)].Q THEN
          xDone:=TRUE;
       END_IF
    END_FOR
    rt_ctrl(CLK:=xCmd);
    

    Uh, but writing like this adds to the complexity of the program. . I think I need to be cautious when I change the definition of an array.

     
  • Anonymous - 2018-02-01

    Originally created by: rickj

    Or you could just do this ...

    FOR index := 0 TO iMax_ft_Number DO
       IF ft_Ctrl[index].Q THEN
          xDone:=TRUE;
       END_IF
    END_FOR
    
     
  • josepmariarams - 2018-02-04

    Hi.

    For me is not a bad solution to wrapp an array with an FB with get, add, set ... Methods

    Enviat des del meu Aquaris M5.5 usant Tapatalk

     
  • Anonymous - 2018-02-05

    Originally created by: rickj

    Josep M. Rams hat geschrieben:
    Hi.
    For me is not a bad solution to wrapp an array with an FB with get, add, set ... Methods
    Enviat des del meu Aquaris M5.5 usant Tapatalk

    Agree Joseph.

     

Log in to post a comment.