Global Assignment Fail

This sequence (globals) fails on that 1st line on an EDGE 530 and EDGE 1030 (simulator and on real devices), but works fine on an EDGE 1040 and EDGE 1050 (simulator and real devices).

Moving the testval assignment under the enum and array works on all devices.

I get it - I guess. I've never seen ordering cause an issue before - but maybe I just never did this before. On newer devices it doesn't matter.

  • I've never seen ordering cause an issue before - but maybe I just never did this before

    Well, if you stop to think about it, those statements at the global scope have to be executed in *some* order, and that particular order is important for the proper functioning of your code. Are you expecting the compiler or runtime to automatically rearrange your code so it makes sense? You wouldn't expect that at the local scope, so why would you expect it at the global scope?

    In your screenshot, you've literally declared testval, which references MYTEST, before declaring MYTEST. I'm not sure why you think this shouldn't be a problem. Obviously if the line with the testval declaration executes before the line with the MYTEST declaration (as per the actual order of statements), your code will fail.

    If anything, it's surprising that this code ever works, not that it sometimes fails.

    I can think of a few possibilities for how the execution order is determined at the global scope:

    - the statements are executed in the order they appear in the source file (in which case I would expect your program to fail)

    - the statements are executed in some specific order based on compiler rules that we aren't privy to (in this case, your program may or may not run successfully)

    - the compiler or runtime intelligently arranges the statements in an attempt to prevent your program from failing (this seems to be the least likely possibility)

    Obviously you've found that different devices behave differently. But I just don't get why you would expect things to "magically" work no matter what order you put your statements in.

    Given your observation that different devices seem to follow different rules here, I wouldn't rely on global statements executing in any fixed order at all. In other words, instead of initializing one global based on another, at the global scope, I would probably initialize those globals in a function, where the order of execution could be controlled. Going further, in general I would avoid using globals wherever possible.

    Speaking of expected behaviour, the equivalent code in C does not compile (and I would not expect it to).

    #include <stdio.h>
    
    int testval = MYTEST[0]; // error: ‘MYTEST’ undeclared here (not in a function)
    int MYTEST[] = {100, 200};
    
    int main() {
      printf(testval);
      return 0;
    }
    

    The equivalent code in js does not work the way you want (as per your OP), either:

    let testval = MYTEST[0];
    let MYTEST = [100, 200];
    console.log(testval);

    If you compile with node.js, the 1st line produces this error:

    > Uncaught ReferenceError ReferenceError: Cannot access 'MYTEST' before initialization

    If you just type in that program line-by-line in node's REPL, you get a similar error:

    > Thrown:
    > ReferenceError: MYTEST is not defined

  • The code doesn't make much sense. That is, you shouldn't be writing it like that.

    In a strict sense, it's a programming error (referencing something that hasn't been defined).

    If so, there's not requirement from anybody for it to "work". It would be a mistake on your part to rely on it "working".

  • Totally agree. This was a barrel. Since I update those variables in the barrel and use them in several apps, global was easiest - defined in the barrel source. that is obviously just an example of the error, not my acutal code. But I added a new array to the logic and put that assignment near the top. Then I initialized it. But to a variable I define a little lower. I tested it on my EDGE 1050 and all was good. Yes, bad coding... bummer a user had to find it on their EDGE 830.

  • Thanks. Good insight. This compiled fine. But broke in CIQ < 5.0 at run time. Maybe because my compiler settings are not set to strict.

  • Type checking shouldn't have any effect on this IMHO.

    If something, then the optimization. Maybe. But even then, if the code compiles, it shouldn't fail at runtime. If it does then it is a compiler bug IMHO. It could've failed at compile time, but if it didn't (it could be called a feature) then it should work at run time.

    • The code is semi-interpreted.
    • It’s not a great compiler. 
    • The code doesn’t make much sense as it was written. 

    I suspect part of the problem is the compiler trying to guess the type.

    (I have no idea why people still created non-typed languages only to add types later. You’d think people would be aware of that headache.)