Operating System - HP-UX
1819926 Members
2891 Online
109607 Solutions
New Discussion юеВ

C++: Redirecting stdout to a file and back to the console again

 
SOLVED
Go to solution
Peter Hug
Advisor

C++: Redirecting stdout to a file and back to the console again

In Windows I can temporarily redirect console (stdout) output to a file and then back to the console again as follows:

// redirect console output to a file
freopen("logfile.txt", "a+", stdout);

std::cout << "This goes to logfile.txt\m";

// reset console output
freopen("con", "w", stdout);

std::cout << "This goes to console\m";

Unfortunately, under HP-UX the line "freopen("con", "w", stdout);" doesn't redirect output back to the console and instead redirects output to the file "con" instead. Unlike Windows it seems HP-UX is not treating the file "con" as something special.

Does anyone know how how the desired effect is achieved?
12 REPLIES 12
Devender Khatana
Honored Contributor

Re: C++: Redirecting stdout to a file and back to the console again

Hi,

Are u trying to redirect output only to system console or to some other terminal. For system console device file is '/dev/console'. Any thing you redirect to it will be displayed on your systems's console.

For ex.
#cat /etc/passwd >/dev/console

It will type the passwd file on console.

HTH,
Devender
Impossible itself mentions "I m possible"
Peter Hug
Advisor

Re: C++: Redirecting stdout to a file and back to the console again

Hi Devendar,

I tried what you suggested but I din't have any luck :(. This program doesn't produce any output (or at oleast I didn't find it):

#include

int main(int argc, char* argv[])
{
FILE* f = fopen("/dev/console", "w");
char* msg="blah blah blah";

fwrite(msg, sizeof(char), strlen(msg), f);
fclose(f);

return 0;
}
Amit Agarwal_1
Trusted Contributor

Re: C++: Redirecting stdout to a file and back to the console again

Its possible that you don't have proper priviledges to write to console. Check the return value of fopen().
Biswajit Tripathy
Honored Contributor

Re: C++: Redirecting stdout to a file and back to the console again

Your code should do what you want; but, as Amit
said, you probably do not have permission to write
on console (not a good idea to ignore fopen()
return value) . Modify your code as follows:

#include
#include

int main(int argc, char* argv[])
{
char* msg="blah blah blah";
FILE* f = fopen("/dev/console", "w");
if (!f) {
perror ("fopen fail");
return 1;
}

fwrite(msg, sizeof(char), strlen(msg), f);
fclose(f);

return 0;
}

This should print the error if it can't write to console.
An easy way to findout if you have permission
to write to console is to execute following command:

# echo "Just testing" > /dev/console

This should either print the mesg on console or give
you the error.

- Biswajit
:-)
Peter Hug
Advisor

Re: C++: Redirecting stdout to a file and back to the console again

I've made some changes along these lines and below is tyhe code and it's output. I've also included output from "ls -l /dev/console" and "echo 'string" > /dev/console. I don't understand what is going on - maybe /dev/console is not the console output?

#include

int main(int argc, char* argv[])
{
FILE* f = fopen("/dev/console", "w");

if (!f)
std::cout << "Failed opening /dev/console\n";
else
{
char* msg="blah blah blah";
int nCount;

std::cout << "Succeeded opening /dev/console\n";

std::cout << "Trying to write \"" << msg << "\" to /dev/console\n";
nCount = fwrite(msg, sizeof(char), strlen(msg), f);
std::cout << "Wrote " << nCount << " characters to /dev/console\n";

fclose(f);
}

return 0;
}
"gaga.cpp" 25 lines, 510 characters
live3-v53:ae7545@bdhp4234 /opt/apal3/gaga:g++ gaga.cpp -o gaga
live3-v53:ae7545@bdhp4234 /opt/apal3/gaga:./gaga
Succeeded opening /dev/console
Trying to write "blah blah blah" to /dev/console
Wrote 14 characters to /dev/console
live3-v53:ae7545@bdhp4234 /opt/apal3/gaga:ls -l /dev/console
crw--w--w- 1 root tty 0 0x000000 Mar 20 16:38 /dev/console
live3-v53:ae7545@bdhp4234 /opt/apal3/gaga:echo "I want to see this"
I want to see this
live3-v53:ae7545@bdhp4234 /opt/apal3/gaga:echo "I want to see this" > /dev/console
live3-v53:ae7545@bdhp4234 /opt/apal3/gaga:
Amit Agarwal_1
Trusted Contributor

Re: C++: Redirecting stdout to a file and back to the console again

Hi Peter,

Since there was no error from echo, I tend to believe that the output is getting redirected to /dev/console.
Are you on console or a terminal? You can check this by running 'tty' command. It will tell if your stdout is attached to console or not.

On a console:
# tty
/dev/console

On a terminal:
# tty
/dev/pts/0

Peter Hug
Advisor

Re: C++: Redirecting stdout to a file and back to the console again

tty returns /dev/pts/tY

So while it is easy in a C++ program to redirect all output to stdout to the console/terminal, reverting this operation is not possible in UNIX?

Why does UNIX drive me nuts?
Biswajit Tripathy
Honored Contributor

Re: C++: Redirecting stdout to a file and back to the console again

Could you explain what exactly you want to do?
It appears that the code is doing what you _said_
you want to do.

- Biswajit
:-)
A. Clay Stephenson
Acclaimed Contributor
Solution

Re: C++: Redirecting stdout to a file and back to the console again

Unfortunately primitive UNIX is just not as good as that super advanced operating system that you are used to. It's really amazing that stupid UNIX didn't know "con" meant the console. It's also amazing that stupid UNIX isn't able to translate your intentions into code; that's probably what's driving you crazy. The other thing is that "console" means something very specific to a UNIX box and it's not normally available for regular users. You probably mean your terminal and that is always the pseudodevice /dev/tty whether you are on a telnet session, the system console, or a serially connected terminal.



The key to doing what you are trying to do is the dup() system call. It is able to duplicate an existing file descriptor AND it returns the lowest available file descriptor. This means that if you close stdout (fdes 1, assuming stdin (fdes 0) is open) then dup will always return 1 (stdout).

We can leverage this behavior in the attached 3-minute code intentionally done in C rather than C++ for clarity but C++ will work just as well.

You should also get into the habit of test function results. You call freopen and blindly assume all is well.



If it ain't broke, I can fix that.
Peter Hug
Advisor

Re: C++: Redirecting stdout to a file and back to the console again

Many thanks Clay for your most useful answer!

I didn't mean to offend you or the Unix community and can quite easily answer my own question [why is Unix driving me nuts?]: everything in Unix is done through geeky, unimaginative commands - even online help.

However, with that I don't mean (let alone say) that Unix is a worse OS than Windows. In fact I think Unix is a great OS - it just lacks uniformity and a common user-friendly interface and that makes it a pain in the butt to learn.

Cheers
Pete
Biswajit Tripathy
Honored Contributor

Re: C++: Redirecting stdout to a file and back to the console again

Peter,
Unix treats console/terminal/stdout/stdin etc. etc.
as files. Everytime you open a new hpterm / xterm
/ dtterm on hp-ux, you are opening a new terminal.
When you invoke a program from the terminal, that
terminal (by default) becomes the stdout, stdin and
stderr for that program. Every system typically
has one console which is _like_ any other terminal,
but a little special. Typically, users on hp-ux (or any
unix) don't write to console and it's only reserved for
system messages.

The advantage is, if your C/C++ program code is
reading from stdin and writing to stdout/stderr, then
you could redirect them using '<' and '>' char in the
shell that invokes your program. You don't even
have to modify and compile your program!
For ex:

1) read from tty01 terminal and write to tty02
terminal:

# ./my_prog < /dev/tty01 > /dev/tty02

2) read from file /tmp/my_input and write to
console terminal:

# ./my_prog < /tmp/my_input > /dev/console

3) read from file this terminal, write output to
/tmp/out and write error to system log file
/var/adm/syslog/syslog.log:

# ./my_prog > /tmp/out 2> /dev/log

That's pretty cool, actually. And once you get used
to it, it's pretty intuitive.

- Biswajit
:-)
Amit Agarwal_1
Trusted Contributor

Re: C++: Redirecting stdout to a file and back to the console again

Peter,

You can use /dev/tty instead of /dev/console in your C program. It should work as you want it to.

-Amit