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

Namespaces and how to use them

Krowi
2018-05-16
2018-05-19
  • Krowi - 2018-05-16

    Hello everyone,

    My team and I are using CoDeSys to program our controllers and we recently made some changes and done some refactoring. During the refactoring we had something "wierd" happen (wierd because we never had it before. I'll explain what we had and what changed and what my question is. All code examples are not code we use, it's just to explain my question.

    Let's say you have Lib1 which is a library that has a global variable file GVL_Definition. In this file has variables called bStart and bStop. The code looks like this:

    Lib1 GVL_Definition Code
    VAR GLOBAL
       bStart   : BYTE := 1;
       bStop   : BYTE := 2;
    END_VAR
    

    In a second library Lib2 we put Lib1 in the Library Manager. In this Lib2 we have a method mxStartByte which uses bStart from Lib1. We can directly use it without explicitly putting namespaces or file names in front of the variable. The code is something like this:

    Lib2 mxStartByte Code
    IF   bStart = 1 THEN mxStartByte := TRUE;
    ELSE   mxStartByte := FALSE; END_IF
    

    Now we have a third library Lib3. This library needs both Lib1 and Lib2 to work and are both added in the Library Manager. It has a method named mxStop and this is the code:

    Lib3 mxStop Code
    IF   NOT mxStartByte() AND bStop = 0 THEN mxStop := TRUE;
    ELSE   mxStop := FALSE; END_IF
    

    Now, the above is how we have it. The namespace of each library is the name of the library to keep this example simple.

    Due to something in Lib3, the code in mxStop changed to this:

    Lib3 mxStop Code
    IF   NOT mxStartByte() AND Lib1.bStop = 0 THEN mxStop := TRUE;
    ELSE   mxStop := FALSE; END_IF
    

    I've done some searching and came across this article: https://stefanhenneken.wordpress.com/20 ... amespaces/. It explains how namespaces are used to unambiguously declare multiple variables with the same name. I do understand that it's used for that but I was wondering if there is another use case for namespaces.

    If we go back to the example above. Lib3 requires Lib1 and Lib2 to work. Lib2 requires Lib1 to work. The required libraries are added to the Library Manager each time. After some testing I found that it's possible to add Lib1 to Lib2's Library Manager and ONLY add Lib2 to Lib3's Library manager and with adding the namespace of Lib1 in front of the global variables in that library I could access those without putting Lib1 in Lib3's library manager. This gives us the following code:

    Lib3 mxStop Code
    IF   NOT mxStartByte() AND Lib2.bStop = 0 THEN mxStop := TRUE;
    ELSE   mxStop := FALSE; END_IF
    

    What surprised me is that the variable bStop is visible from Lib2 even though it's in Lib1. This leads me to think that all variables, methods, ... in a library that is added to the Library Manager of a library are visible from that library when it's added to another Library Manager in its turn. Have a look at the following code on how I can access bStop in Lib3 with different conditions:

    1.   Lib3 LM (Library Manager) has Lib2 and Lib1, Lib2 LM has Lib1
    1.1.   bStop
    1.2.   Lib1.bStop
    1.3.   Lib2.bStop
    1.4.   Lib2.Lib1.bStop
    2.   Lib3 LM has Lib2, Lib2 LM has Lib1
    2.1.   Lib2.bStop
    2.2.   Lib2.Lib1.bStop
    

    The above code really makes things confusing for me.

    On another note, a colleague of mine told me there is this option: "Publish all IEC symbols to that project as if this reference would have been included there directly." If I thick this option and if I refer back to the last code example above, option 2's sub cases are the same as option 1's. For me this is a 3rd possible option of adding / not adding libraries to Library Managers and accessing variables in one way or another.

    My final question is, what is the correct way to access variables in a library which is also in the LM of a higher library that you need. (Lib3 needs Lib1 and Lib2 but Lib2 already has Lib1)

     

Log in to post a comment.