Thread: Can not use popen()

  1. #1
    Registered User
    Join Date
    Oct 2007
    Posts
    12

    Can not use popen()

    Hi, all
    I try this code, but can not compile and debug

    Code:
    #include <stdio.h>
    
    main()
       {
    	   FILE *fp;
    	   char line[130];			
       
    	   fp = popen("netstat -n", "r");
    					
    	   while ( fgets( line, sizeof line, fp))
    		{
    		  printf("%s", line);
    		}
    	   pclose(fp);
       }
    when i compile, console such as
    Compiling...
    OCMStart.c
    D:\OCMStart\OCMStart.c(8) : warning C4013: 'popen' undefined; assuming extern returning int
    D:\OCMStart\OCMStart.c(8) : warning C4047: '=' : 'struct _iobuf *' differs in levels of indirection from 'int '
    D:\OCMStart\OCMStart.c(14) : warning C4013: 'pclose' undefined; assuming extern returning int

    OCMStart.obj - 0 error(s), 3 warning(s)

    When i debug, console such as

    Linking...
    OCMStart.obj : error LNK2001: unresolved external symbol _pclose
    OCMStart.obj : error LNK2001: unresolved external symbol _popen
    Debug/OCMStart.exe : fatal error LNK1120: 2 unresolved externals
    Error executing link.exe.

    OCMStart.exe - 3 error(s), 0 warning(s)


    please help me to run this code

    many thanks

  2. #2
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,659
    Since you seem to be using a Microsoft compiler, then try using
    _popen
    _pclose
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  3. #3
    Registered User
    Join Date
    Oct 2007
    Posts
    12
    Quote Originally Posted by Salem View Post
    Since you seem to be using a Microsoft compiler, then try using
    _popen
    _pclose
    If i use _popen and _pclose then this code can run on unix ?

  4. #4
    Officially An Architect brewbuck's Avatar
    Join Date
    Mar 2007
    Location
    Portland, OR
    Posts
    7,396
    Quote Originally Posted by sistem View Post
    If i use _popen and _pclose then this code can run on unix ?
    No. Thank Microsoft.

  5. #5
    Registered User
    Join Date
    Oct 2007
    Posts
    12
    Thanks you very much,

    please help me one again

    When I use

    #include <stdio.h>
    Code:
    main()
       {
    	   FILE *fp;
    	   char line[130];			
       
    	   fp = _popen("netstat -n", "r");
    					
    	   while ( fgets( line, sizeof line, fp))
    		{
    		  printf("Output: %s", line);
    		}
    	   _pclose(fp);
       }
    The result out put is correct :

    Output :
    Output : Active Connections
    Output :
    Output : Proto Local Address Foreign Address State
    Output : TCP 127.0.0.1:1377 127.0.0.1:1378 ESTABLISHED
    Output : TCP 127.0.0.1:1378 127.0.0.1:1377 ESTABLISHED
    Output : TCP 127.0.0.1:1379 127.0.0.1:1380 ESTABLISHED
    Output : TCP 127.0.0.1:1380 127.0.0.1:1379 ESTABLISHED
    Output : TCP 127.0.0.1:1436 127.0.0.1:2628 ESTABLISHED
    Output : TCP 127.0.0.1:2628 127.0.0.1:1436 ESTABLISHED
    Output : TCP 172.16.2.89:1111 172.16.0.31:1745 ESTABLISHED
    Output : TCP 172.16.2.89:1116 172.16.0.31:1498 CLOSE_WAIT
    Output : TCP 172.16.2.89:1125 172.16.48.20:1026 ESTABLISHED
    .................................................. .............

    But I use java -version as below

    Code:
    main()
       {
    	   FILE *fp;
    	   char line[130];			
       
    	   fp = _popen("java -version", "r");
    					
    	   while ( fgets( line, sizeof line, fp))
    		{
    		  printf("OUT PUT : %s", line);
    		}
    	   _pclose(fp);
       }
    Result only : (do not run in while loop, have not string Output)

    java version "1.4.2_12"
    Java(TM) 2 Runtime Environment, Standard Edition (build 1.4.2_12-b03)
    Java HotSpot(TM) Client VM (build 1.4.2_12-b03, mixed mode)

    Why when i use java -version, while loop do not run, seem that it is redundance

  6. #6
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    It may be that the "java -version" is writing the output to "stderr", which means that it goes to the console, not the pipe.

    If you want your code to compile on both Linux and Windows, you could do something like this:
    Code:
    #if WINDOWS
    #define popen _popen
    #endif
    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  7. #7
    Registered User
    Join Date
    Oct 2007
    Posts
    12
    Quote Originally Posted by matsp View Post
    It may be that the "java -version" is writing the output to "stderr", which means that it goes to the console, not the pipe.

    If you want your code to compile on both Linux and Windows, you could do something like this:
    Code:
    #if WINDOWS
    #define popen _popen
    #endif
    --
    Mats
    Could you please help me to put java -version command to a string ?

  8. #8
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Not sure that's trivial, since if what I proposed is true [that it uses stderr], then you'd need to join the stdout with stderr (or capture stderr INSTEAD of stdout). I think this can be done, but it requires more effort.

    I think I posted not so long ago, a post on how to do this in Windows. Search for "_popen" on the MSDN web-site and check out the part where it says "_popen()" only works with console applications, and there's a link to another page that describes how to capture in a windows app - that will also give you a hint on how to do stderr capture, I seem to remember. You may find that you can find the link by searching for posts by me and scanning the subject title - but I'm not sure.

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  9. #9
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,659
    _popen("java -version 2>&1", "r");
    Seems to work for windows via cmd.exe and also works in cygwin as well.

    It redirects stderr to stdout, which can then be read with popen.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  10. #10
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Quote Originally Posted by Salem View Post
    _popen("java -version 2>&1", "r");
    Seems to work for windows via cmd.exe and also works in cygwin as well.

    It redirects stderr to stdout, which can then be read with popen.
    Ah, of course.

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  11. #11
    Devil™
    Join Date
    Oct 2007
    Location
    IIT-Kharagpur, India
    Posts
    104
    map your stderr of your prog to stdout..
    since its called from your prog it ill use your programs fd's..
    I hope this works..
    else switch to execvp() it will definitely work fine..

  12. #12
    Registered User
    Join Date
    Oct 2007
    Posts
    12
    Quote Originally Posted by gibsosmat View Post
    map your stderr of your prog to stdout..
    since its called from your prog it ill use your programs fd's..
    I hope this works..
    else switch to execvp() it will definitely work fine..
    thanks you so much, I did as you and run ok on Windows

    If i use _popen("java -version 2>&1", "r"); in my code and I build this code to abc.sh

    Can this file run well on linux & mac OS ?

    thanks

  13. #13
    Officially An Architect brewbuck's Avatar
    Join Date
    Mar 2007
    Location
    Portland, OR
    Posts
    7,396
    Can this file run well on linux & mac OS ?
    If you have some program called "java" on Linux/Mac and you call popen() instead of _popen(), then yes.

  14. #14
    Registered User
    Join Date
    Oct 2007
    Posts
    12
    Quote Originally Posted by brewbuck View Post
    If you have some program called "java" on Linux/Mac and you call popen() instead of _popen(), then yes.
    execvp(), can run all OS (Windows, Linux, Mac, Vista) ?

  15. #15
    Officially An Architect brewbuck's Avatar
    Join Date
    Mar 2007
    Location
    Portland, OR
    Posts
    7,396
    Quote Originally Posted by sistem View Post
    execvp(), can run all OS (Windows, Linux, Mac, Vista) ?
    Sure, but Windows has _popen(), others have popen(), so why not use it. If you use execvp() you have to deal with forking a new process, creating the pipes, reaping the process, etc, all of which popen() takes care of for you.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. popen and fgets, underflow!
    By henrikstolpe in forum Linux Programming
    Replies: 0
    Last Post: 02-06-2009, 03:39 AM
  2. popen takes too long?
    By Largo in forum C Programming
    Replies: 2
    Last Post: 11-20-2006, 06:46 AM
  3. popen()
    By Cactus_Hugger in forum Windows Programming
    Replies: 2
    Last Post: 10-22-2005, 03:16 PM
  4. popen vs fopen
    By esme in forum Linux Programming
    Replies: 1
    Last Post: 11-25-2002, 10:37 AM