Order of include file parameters influence DEFINED() value - Forum - OpenEdge Development - Progress Community

Order of include file parameters influence DEFINED() value


Order of include file parameters influence DEFINED() value

This question is not answered

In one of our include files I came across some interesting behaviour.

First, create the following include file:

/* c:\temp\1.i */
&IF DEFINED(myParam) = 0 &THEN

Then run this:

/* 1 */ {c:\temp\1.i            &myParam } /* defined */
/* 2 */ {c:\temp\1.i &abc=1     &myParam } /* defined */
/* 3 */ {c:\temp\1.i &myParam=* &abc     } /* defined */
/* 4 */ {c:\temp\1.i &myParam=* &abc=1   } /* defined */
/* 5 */ {c:\temp\1.i &abc       &myParam } /* not defined */
/* 6 */ {c:\temp\1.i &myParam   &abc     } /* not defined */
/* 7 */ {c:\temp\1.i &myParam   &abc=1   } /* not defined */

I already added the outcome, but what strikes me are the cases where it says "Not Defined". It looks like the order of the parameters influence the value of DEFINED.

Case #1 - #4 are as expected. Even if the parameter has no value, it /is/ defined.  
Starting at #5 things are going downhill for me. Why is the parameter "Not defined" there?

Is this a bug in the compiler or is this expected (and documented somewhere)?

Tested in 10.1C / 11.2 / 11.7

All Replies
  • If I read documentation.progress.com/.../index.html correctly it's a bug that progress allows named parameters without equility sign.

    The syntax diagram allows for either a list of positional parameters or a list of name/value pairs.

  • Hmm, yes, if you look at the structure of an include file:

    { include-file
    [ argument ... | {&argument-name = "argument-value" } ... ] }

    It looks as if it should not be allowed to pass in a parameter without a value, otherwise the description should have read:

    { include-file
    [ argument ... | {&argument-name [ = "argument-value" ] } ... ] }

    So its behaviour is not a bug, but the fact that the compiler accepts it, is.

    BTW, these 'tips' on the page you linked should really be removed:

    • When you have a base procedure and want to make several copies of it, changing it slightly each time, use include files with parameters. For example, at times you might only want to change the name of some files or fields used by the procedure.

    • Instead of maintaining duplicate source files, create a single include file with the variable portions (such as the names of files and fields) replaced by {1}, {2}, etc. Then each procedure you write can use that include file, passing file and field names as arguments.

    One should really not be doing this anymore now. 

  • And apart from the notes that are nowadays irrelevant (Sequent platform has not been supported for how long exactly?) or bad practice, the one that really identifies current behavior as a bug is of course the first one:

    "You can pass a series of positional arguments or a series of named arguments to an include file, but you cannot pass a combination of positional and named arguments to an include file."

    So in the example, case 2,3 and 7 should raise a compile-time error.

    And in cases 1,5 and 6, I'd say what you *should* see is that myParam is not defined as a preprocessor name, and the positional arguments resolve to the literal string "&myParam" -> without the "=" those don't follow the syntax for named arguments so they should not be parsed as such.

  • I don't think that a parameter whose name starts with an ampersand, but has no value identifies as an unnamed parameter.

    Try this:

    /* c:\temp\1.i 
    MESSAGE 'Param 1: {1}'
      SKIP 'Param 2: {&hello}'

    then run:

    {c:\temp\1.i hello }
    {c:\temp\1.i &hello }

    You will see:

    /* message 1 */
    Param 1: hello 
    Param 2: 
    /* message 2 */
    Param 1: 
    Param 2: 

    So the parameter &hello is not recognized as an unnamed parameter.