Compiler opitimization

Strucc
2013-06-29
2013-07-17
  • Strucc - 2013-06-29

    I think it's a general issue, maybe a good idea to ask here:

    What kind of optimization CoDeSys compiler does?

    In some cases, designing an application the programmer has to decide between:
    - Easy to read, compact, structured code
    - Performance
    It's stupid. One should never write unreadable code for performance reasons. Advanced programming systems and compilers do high level optimization on the generated code. Some of the possible optimizations:

    1. Expressions containing CONSTANT values are pre-evaluated during compilation. Example:

    (SETTINGS.LOG_LEVEL AND LOG_DEBUG) > 0
    

    should be evaluated as constant TRUE or FALSE. Note: This is only true, when the "Replace constants" build option is enabled.

    2. Unreachable branches should be excluded from build Example:

    IF (SETTINGS.LOG_LEVEL AND LOG_DEBUG) > 0) THEN
    Β  LOG_MSG(CLS_MEMORY, ERR_NONE, INFO_DEBUG, CONCAT(strAction, ANY_TO_STRING(szSize)));
    END_IF
    

    As the condition evaluates to a constant, the entire LOG_MSG call can be excluded from the application. (or, to be precise: the entire code, including the evaluation should be excluded).

    3. Empty functions, methods, etc... should be excluded from build, or should not be called at all
    Example:

    FUNCTION DoesNothing
    VAR_INPUT
    Β  strString : STRING;
    END_VAR
    IF (FALSE) THEN
    Β  // Lot of string manipulation code here
    END_IF 
    

    Instead of the "FALSE" condition, naturally a constant or a constant expression can be used.
    As quite clear, that this function will not do anything, and will not manipulate the input variable, so the calling line

    DoesNothing('Some string');
    

    should be excluded as well. This way, building up the call stack (probably copying the string) could be spared. In a more complex case:

    DoesNothing(CONCAT(ANY_TO_STRING(uiCount),' still does nothing'));
    

    The entire line should be skipped as well.

    As I tested with debugging step-by-step, it seems, that the current compiler doesn't work this way. Or is it just because of debugging?

    What is the situation with "compiled" libraries? Can they use "Replace constants" option at all? Is it possible to use "Library settings" as global constants, and let the user (application) of the library decide on for example the "LOG_LEVEL", and let the compiler of the application build optimized code?

    I'd be very happy to hear the opinion of CODESYS developers...

    P.

     
  • TimvH

    TimvH - 2013-06-29

    Static Analysis could be interesting for you. This will do a lot of additional checks.
    You can get a demo version of this in the store http://store.codesys.com/codesys-static ... -demo.html.

    Other items which might be interesting for you to know:
    - You can add "parameters" to your library which can be changed in the library manager when you add this library to your project.
    - You can add "compiler defines" to your application, but this was not a what you were looking for: See l viewtopic.php?f=11&t=5085&hilit=defines l

    Maybe somebody else has better ideas.

     
  • Strucc - 2013-06-29

    I use Static Analysis, part of the questions comes from those results.

    And yes, I use library parameters - basically they are visible for the library as global constants, this is why I ask about the interpretation of constants, and interpretation of constant based expressions.

    The question is about the compiler - how deep does it optimize the code...

    About conditional defines: I did not manage to get them functional in a compiled library, and they are not very elegant... I was using them to determine if the system is 16/32/64bit.... I also understood: conditional defines and compilation is only working in the code part, not in the declaration part...

    I'd like to use the described features for logging and debugging purposes. The library itself is quite complex, sometimes it can be useful for the application developer to monitor the raw traffic, packets, connection, disconnection, also for days, maybe months in a deployed environment. But... naturally these calls produce extra load on the PLC CPU and storage, sometimes it's not permissible...

    I'm not just looking for a way to do this: I'm seeking for the best way

    P.

     
  • Anonymous - 2013-07-17

    Originally created by: M.Schaber

    Hi,

    Optimizations always come with side effects, some of them are:

    I'm not sure whether that pays off at the end.

    Additionally, in most of the cases in software engineering, architectural and algorithmical changes offer much better opportunities for optimization, sometimes one can even gain magnitudes, which is usually not possible with compiler optimizations.

     
  • Anonymous - 2013-07-17

    Originally created by: Bernhard Werner

    Hello all,

    it is not a secret, that the codesys compiler is not optimizing on a high level. To be more specific, we do:

    1. Expressions containing CONSTANT values are pre-evaluated during compilation.
      Yes

    2. Unreachable branches should be excluded from build Example:
      No

    3. Empty functions, methods, etc... should be excluded from build, or should not be called at all
      No. But if a function is not called at all, then it will not be compiled.

    1. and 3. should be reported by static analysis.
      Other possible optimizations like: identifying invariant parts in loops
      or identifying identical expressions
      will also be a feature of static analysis. So instead of doing complex optimizations directly, our approach will be to hint the programmer,
      where code could be optimized. If the analyzation is wrong, there is no harm, but if the optimization is wrong, severe damage could occur.

    Besides the optimizations mentioned: the codesys compiler reorders complex expressions for an optimal usage of registers.
    (Depth first evaluation).

    Bernhard Werner

     

Log in to post a comment.