Author Topic: Passing environment variables as programs' arguments  (Read 10144 times)

Offline qweweng

  • Single posting newcomer
  • *
  • Posts: 3
Passing environment variables as programs' arguments
« on: November 12, 2013, 03:45:23 pm »
Hello everyone, I have a quick question. I would like to pass an environment variable to my executable in C::B. Can this be done under Project -> Set programs' arguments?

For example, suppose I have an environment variable %VAR% = abc, and a program PrintArgument.exe that prints the first command line argument (argv[1]). In command prompt, I can type "PrintArgument %VAR%" and the output will be "abc". Can I achieve this with C::B?

I've tried to set the programs' argument to %VAR% under Project -> Set programs' arguments, but it does not work and the program output is %VAR%. I'm not sure if I'm doing this correctly.

I've searched the forum for this issue but couldn't find anything similar. I apologize if this is a double post.

I'm using Windows 7 and Code::Blocks 12.11 binary release by the way. Thanks in advance for your help.

Offline ollydbg

  • Developer
  • Lives here!
  • *****
  • Posts: 6035
  • OpenCV and Robotics
    • Chinese OpenCV forum moderator
Re: Passing environment variables as programs' arguments
« Reply #1 on: November 12, 2013, 04:07:31 pm »
...In command prompt, I can type "PrintArgument %VAR%" and the output will be "abc". ....
Does this works already when you run your program under command line?

If the answer is Yes, this means your program can do the job which replace %VAR% to abc, and print the abc.

If the answer is No, this means your program can NOT do the job, then why do you ask C::B to do the job? In this case, It is definitely a problem of your program, not C::B.
If some piece of memory should be reused, turn them to variables (or const variables).
If some piece of operations should be reused, turn them to functions.
If they happened together, then turn them to classes.

Offline qweweng

  • Single posting newcomer
  • *
  • Posts: 3
Re: Passing environment variables as programs' arguments
« Reply #2 on: November 12, 2013, 04:48:00 pm »
...In command prompt, I can type "PrintArgument %VAR%" and the output will be "abc". ....
Does this works already when you run your program under command line?

Yes. The code for the PrintArgument program is just as follows:
Code
int main(int argc, char* argv[])
{
    cout << argv[1] << endl;
    return 0;
}
In other words, it's the command prompt that looks up the value of %VAR% (which is "abc") and passes the value into my program.

If the answer is Yes, this means your program can do the job which replace %VAR% to abc, and print the abc.

If the answer is No, this means your program can NOT do the job, then why do you ask C::B to do the job? In this case, It is definitely a problem of your program, not C::B.
PrintArgument is just my made-up program to help illustrate my question. I have a much larger program in which a value of an environment variable is required to be passed. Although I can compile the program in C::B and run it using command prompt, it would be more convenient if I can do both in C::B. Hence, I was wondering if C::B allows me to achieve this. I'll find other alternatives if this is not possible.

Thanks ollydbg for your speedy reply.  ;)

Offline ollydbg

  • Developer
  • Lives here!
  • *****
  • Posts: 6035
  • OpenCV and Robotics
    • Chinese OpenCV forum moderator
Re: Passing environment variables as programs' arguments
« Reply #3 on: November 13, 2013, 04:02:01 pm »
Quote
Although I can compile the program in C::B and run it using command prompt, it would be more convenient if I can do both in C::B. Hence, I was wondering if C::B allows me to achieve this. I'll find other alternatives if this is not possible.
Ok, I think C::B don't have this feature(expand the %VAR% string to its value in its argument settings)
You can enhance it by implement it, so patch are welcome.
Another way I think you can use is to use the Tool+ plugin, which you can use the command line tool, you can see a related discuss here:
http://developer.berlios.de/bugs/?func=detailbug&bug_id=19180&group_id=5358

So, write some command like (I don't try this yet, you can try it yourself)

Code
cmd /c $(TARGET_NAME) %VAR%

See: http://wiki.codeblocks.org/index.php?title=Variable_expansion as another reference.

EDIT:
Quote
Variables which are neither global user variables nor builtin types are replaced with a value provided in the project file, or with an environment variable if the latter should fail.
So, maybe, C::B already replace the %XXX% like string reference to Variable expansion - CodeBlocks, so just enable the macro replace feature for the argument input dialog?


« Last Edit: November 13, 2013, 04:04:53 pm by ollydbg »
If some piece of memory should be reused, turn them to variables (or const variables).
If some piece of operations should be reused, turn them to functions.
If they happened together, then turn them to classes.

Offline Jenna

  • Administrator
  • Lives here!
  • *****
  • Posts: 7256
Re: Passing environment variables as programs' arguments
« Reply #4 on: November 14, 2013, 07:27:54 am »
At least on linux, the environment variables get expanded:
Code
#include <iostream>

using namespace std;

int main(int argc, char* argv[])
{
    for (int i=0; i < argc; ++i)
        cout << argv[i] << endl;
    cout << "Hello world!" << endl;
    return 0;
}
called with argument $HOME (set in "Project -> Set programs's arguments..." gives the (expected) result:
Quote
/tmp/test/bin/Debug/test
/home/jens
Hello world!

Process returned 0 (0x0)   execution time : 0.002 s
Press ENTER to continue.
« Last Edit: November 14, 2013, 09:01:42 pm by jens »

Offline qweweng

  • Single posting newcomer
  • *
  • Posts: 3
Re: Passing environment variables as programs' arguments
« Reply #5 on: November 14, 2013, 02:49:29 pm »
Ok, I think C::B don't have this feature(expand the %VAR% string to its value in its argument settings)
You can enhance it by implement it, so patch are welcome.
Another way I think you can use is to use the Tool+ plugin, which you can use the command line tool, you can see a related discuss here:
http://developer.berlios.de/bugs/?func=detailbug&bug_id=19180&group_id=5358

So, write some command like (I don't try this yet, you can try it yourself)

Code
cmd /c $(TARGET_NAME) %VAR%

See: http://wiki.codeblocks.org/index.php?title=Variable_expansion as another reference.

Thanks to your suggestions, I got 2 workarounds to this problem:
1. Post-build Steps
    (a) Go to the Project's Build Options, select the "Pre/post build steps" tab.
    (b) Under Post-build step, type "$(TARGET_OUTPUT_FILE) %VAR%".
    (c) Check "Always execute, even if target is up-to-date"
    (d) Build the project. Due to (c), the executable will run regardless of whether it's up-to-date, which is what I want.
         * If we "Build and Run" the project, the executable will run twice.

2. External Tool
    (a) Go to Tools -> Configure tools, click Add to create a new tool.
    (b) Fill up the Edit tool dialog. For my case, the data is as follows:
         Name:            Whatever
         Executable:     ${TARGET_OUTPUT_FILE}
         Parementers:   %VAR%
         Working directory: ${PROJECT_DIR}
    (c) Go to Tools and click Whatever to run the program.

Though these are not the most desired ways, but it's good enough for me. ;)

EDIT:
So, maybe, C::B already replace the %XXX% like string reference to Variable expansion - CodeBlocks, so just enable the macro replace feature for the argument input dialog?

Somehow I couldn't find the "enable the macro replace feature" in the argument input dialog. Did I miss something?

At least on linux, the environment variables get expanded:
Code
#include <iostream>

using namespace std;

int main(int argc, char* argv[])
{
    for (int i; i < argc; ++i)
        cout << argv[i] << endl;
    cout << "Hello world!" << endl;
    return 0;
}
called with argument $HOME (set in "Project -> Set programs's arguments..." gives the (expected) result:
Quote
/tmp/test/bin/Debug/test
/home/jens
Hello world!

Process returned 0 (0x0)   execution time : 0.002 s
Press ENTER to continue.

Thanks. Too bad I'm not using Linux. Tried everything I could with the program's argument but it just doesn't work.

Offline ollydbg

  • Developer
  • Lives here!
  • *****
  • Posts: 6035
  • OpenCV and Robotics
    • Chinese OpenCV forum moderator
Re: Passing environment variables as programs' arguments
« Reply #6 on: November 14, 2013, 03:03:14 pm »
Glad you find at least two methods.
Somehow I couldn't find the "enable the macro replace feature" in the argument input dialog. Did I miss something?
No such option in C::B, as Jen's test shown that under Linux, environment variables get expanded correctly.

Quote
Too bad I'm not using Linux. Tried everything I could with the program's argument but it just doesn't work.
So, as your testing result, environment variables do not get expanded under Windows for C::B's program argument.
If some piece of memory should be reused, turn them to variables (or const variables).
If some piece of operations should be reused, turn them to functions.
If they happened together, then turn them to classes.