• We’re currently investigating an issue related to the forum theme and styling that is impacting page layout and visual formatting. The problem has been identified, and we are actively working on a resolution. There is no impact to user data or functionality, this is strictly a front-end display issue. We’ll post an update once the fix has been deployed. Thanks for your patience while we get this sorted.

How to get output of linux commands

Red Squirrel

No Lifer
Is there a way I can perform a linux command within C++, then get the output of that command? I'm looking for something like system() but that I get the actual screen output. It would also be nice if I can send data back to the same "session"

So something like this:

Code:
string output = LinuxCommand("passwd user");

if(output == "Changing new password for user testuser.")
{
   LinuxCommand("newpass");
   LinuxCommand("newpass");
}
else cout<<"Invalid user";

Is this something that is easily doable? I *could* write a function that uses system, then redirects output to a temp file, then reads that file, but I'm wondering if there's something already built in that I can use. Bonus if there's a flag that can tell me if it's STDOUT or STDERR but that's not a requirement in my case.
 
I'll play around with that. I will eventually want to use regex instead of just straight "ifs" in case command messages differ from distro to distro but I have not looked at c++ regex yet but I'm sure there must be libraries for it.
 
In some cases it's the only way, like if I want to interact with the shell programmaticly. I try to avoid it though since yeah, it could be prone for error.

Like in my example to check if a user exists all I have to do is open the user's file then check if there is an entry, so that's probably what I'll do, then again, would it be possible that some distros use a different format for the user list or even store it somewhere else? I've never seen it, but I've only dealt with maybe like 2 different distro classes (debian / RH).
 
I'm pretty sure that /etc/passwd and /etc/shadow are standard across distributions, but that doesn't take into account the countless other authentication methods like AD, LDAP, Kerberos, NIS, etc.
 
I believe popen might work for you, but this kind of thing is almost always buggy and a bad idea.

I disagree. Use of child processes in their various forms is a great practice for performance-insensitive code. Its the ultimate in reused code, encapsulation, protection, and fault tolerance.

It can be killed by portability issues, admittedly.

Gamingphreek said:
If it is a system command in the /bin folder, why could you not just use 'execve' or 'execvp' for the command?

I think Red wants to make some decision based on the success or failure of the target (hence why he wants the output in a file descriptor). The exec() family would blow away the current process and replace it with the target command -- which of course would at least run the command, but it would not be possible to analyze output.
 
I disagree. Use of child processes in their various forms is a great practice for performance-insensitive code. Its the ultimate in reused code, encapsulation, protection, and fault tolerance.

It can be killed by portability issues, admittedly.

I still think it would be better to just use the *pwent functions to update passwords. Sending and receiving strings to a random binary is going to be more error prone and another vector for attack. Especially with his password example below because in order to set other user's passwords the parent binary will have to be run as root.

And I don't get the fault-tolerance idea, unless you think starting a child binary is safer than calling the appropriate APIs.
 
I still think it would be better to just use the *pwent functions to update passwords. Sending and receiving strings to a random binary is going to be more error prone and another vector for attack. Especially with his password example below because in order to set other user's passwords the parent binary will have to be run as root.

And I don't get the fault-tolerance idea, unless you think starting a child binary is safer than calling the appropriate APIs.

Two separate topics in play here. From a security pov, as in the OP's password update scenario, I would agree that calling the appropriate APIs is the right thing to do. In a more general context degibson is right that child processes are a fine and robust way to compose complex behaviors in a system.

I'm pretty sure you aren't actually in disagreement.
 
I still think it would be better to just use the *pwent functions to update passwords. Sending and receiving strings to a random binary is going to be more error prone and another vector for attack. Especially with his password example below because in order to set other user's passwords the parent binary will have to be run as root.

And I don't get the fault-tolerance idea, unless you think starting a child binary is safer than calling the appropriate APIs.

I did not know there was a built in C++ function to change a password, that is definably better then. Though I'm sure I'll still need to perform commands directly for certain tasks so it's good to know that is doable in the way I wanted.

Is pwent only for perl? I can't seem to find much online about it. Everything seems to point to perl.
 
The User:😛went is coming up a lot because you just google'd pwent and it's named that way because the functions all end in pwent, i.e. getpwent to get a password entry.

Although, you'll also need to look at the shadow functions since just about every installation these days uses shadow passwords.

And if you want to support more than just local auth you'll probably want to look at using PAM.
 
Two separate topics in play here. From a security pov, as in the OP's password update scenario, I would agree that calling the appropriate APIs is the right thing to do. In a more general context degibson is right that child processes are a fine and robust way to compose complex behaviors in a system.

I'm pretty sure you aren't actually in disagreement.

I actually didn't read that he was trying to manipulate /etc/passwd. Laziness strikes again on my part. I didn't read his example code.

Use pwd.h to manipulate the user tables.
 
Last edited:
pwd.h sounds like the easiest route to do what I want, just googled it. Come to think of it, is there a site somewhere I can find out about system functions like this? That will help me a lot for the project I'm working on, and I might be able to avoid talking directly to the shell altogether if everything I want to do can be done through built in functions. I assume this header comes with the gcc compiler right?
 
pwd.h sounds like the easiest route to do what I want, just googled it. Come to think of it, is there a site somewhere I can find out about system functions like this? That will help me a lot for the project I'm working on, and I might be able to avoid talking directly to the shell altogether if everything I want to do can be done through built in functions. I assume this header comes with the gcc compiler right?

Reference #1 is the man page. If you do a man passwd, you'll find after following 2 references, you see a reference to 'getpwnam' on page 3.

Basic procedure for looking for functions:
1. Run man on what you know.
2. Follow all interesting links in the 'see also' section
3. Repeat 1-2 until you've exhausted everything.

The man pages are the original 'wikipedia' of references. You can start on 'man 2 gettimeofday', and in two referential clicks you can be on sched_getaffinity, socketpair, or swapcontext.
 
Interesting did nto figure the man page would get into the actual coding implimentation of said function. Also this may be a silly question but what does the 2 mean in your man command example? Is it just the page number?
 
The 2 is the section number. man pages are divided into sections that are on a similar topic. For example the 2 section is system C functions, I believe. It is used to disambiguate names like printf, which appears under multiple sections: C, shell, maybe others.

BTW, The right way to manipulate passwords on modern Linux systems is to use libpam.
 
What are you talking about, not everybody is as good as you and born with this knowledge. I had to be told in order to know. Woopi doo.

But one would think that as someone who develops on Linux you'd at least know where to find the documentation.
 
man 1 x - search for a command line program called x
man 2 x - search for a system call called x
man 3 x - search for a library call called x
I forget what the other sections are.
 
Back
Top