SetEnviron troubles

Linux specific questions.
Fox
Posts: 353
Joined: Aug 08, 2006 13:39
Location: Lille, France
Contact:

SetEnviron troubles

Postby Fox » Nov 25, 2008 20:24

Hello!

Sorry for the lame post (ie. not having any concrete facts)...

I'm writing a program which is setting some environment variables, then launch (open pipe) a third program which will read these variables.

I noticed some strange behaviors of the SETENVIRON statement. For example, if I use the following one:

SETENVIRON("QUERY_STRING=blah")

The third program is reading it okay - "blah". But if I use such form:

DIM SHARED TempVar AS STRING
TempVar = "blah"
SETENVIRON("QUERY_STRING=" + TempVar)

Then the third program is not showing up the variable...

Again, sorry for the lack of example stuff, I can't reproduce that on a simple program :(

Have anyone ran into such (or similar) troubles using env variables on Linux? How could I possibly troubleshoot such problems?
Fox
Posts: 353
Joined: Aug 08, 2006 13:39
Location: Lille, France
Contact:

Postby Fox » Nov 26, 2008 11:48

Hi again :)

It seems that it does matter how much environment variables are set up.

I have noticed such (example) behavior: if I set 3 variables, only the first one is really set. If I set 8 variables, then no one of them us set up in reality...

So, there comes my question: Are there any known limits on how much variables can I set using FreeBASIC, and what are the internal limits (length) of these variables?
Sisophon2001
Posts: 1704
Joined: May 27, 2005 6:34
Location: Cambodia, Thailand, Lao, Ireland etc.
Contact:

Postby Sisophon2001 » Nov 26, 2008 12:49

I think you should report this on sourceforge as a bug. This is an all in one file example.

Code: Select all

DIM TempVar AS STRING
''This works
TempVar = "QUERY_STRING=blah"
SETENVIRON(TempVar)
print Environ( "QUERY_STRING" )
'' This fails
TempVar = "blah"
SETENVIRON("QUERY_STRING=" + TempVar)
print Environ( "QUERY_STRING" )
sleep


tested using the Linux compiler 0.20.

Garvan
stylin
Posts: 1253
Joined: Nov 06, 2005 5:19

Postby stylin » Nov 26, 2008 13:44

SetEnviron (rtlib/libfb_sys_environ.c:80) uses C's putenv(), and on Linux:

The libc4 and libc5 and glibc 2.1.2 versions conform to SUSv2: the pointer string given to putenv() is used. In particular, this string becomes part of the environment; changing it later will change the environment. (Thus, it is an error is to call putenv() with an automatic variable as the argument, then return from the calling function while string is still part of the environment.) However, glibc 2.0-2.1.1 differs: a copy of the string is used. On the one hand this causes a memory leak, and on the other hand it violates SUSv2. This has been fixed in glibc2.1.2.


As you can see there's undefined behavior if you pass a temporary. So, it may be wise to use setenv() on these machines, as I think it makes a copy. I'm not on Linux atm the test it, but it seems to make sense. The code snippet works fine here on Vista.
Fox
Posts: 353
Joined: Aug 08, 2006 13:39
Location: Lille, France
Contact:

Postby Fox » Nov 26, 2008 17:01

stylin wrote:SetEnviron (rtlib/libfb_sys_environ.c:80) uses C's putenv(), and on Linux:


Wunderbar!!!

Thank you all, guys, for your help. It's solved now :-)

What have I done? I made a small SUB which I am using for wrapping SetEnviron():

Code: Select all

DECLARE SUB SetEnv(EnvString AS STRING)
DIM SHARED EnvVariables(1 TO 30) AS STRING
DIM AS STRING TempVar

REM ****
REM Here is my program
TempVar = "blah"
SetEnv("QUERY_STRING" + TempVar)
END
REM ****

SUB SetEnv(EnvString AS STRING)
  DIM AS BYTE x
  DO
    x += 1
  LOOP UNTIL LEN(EnvVariables(x)) = 0 OR x = UBOUND(EnvVariables)

  IF LEN(EnvVariables(x)) = 0 THEN
    EnvVariables(x) = EnvString
    SETENVIRON(EnvVariables(x))
  END IF
END SUB   


This stuff is working like a charm :-)

Return to “Linux”

Who is online

Users browsing this forum: No registered users and 2 guests