My doubt is when we do System.out.println() in our code, why it ends up in writing to console?
In any POSIX compliant shell, each process gets three "standard" streams when the shell starts it:
- The "standard input" stream is for reading input.
- The "standard output" stream is for writing ordinary output.
- The "standard error" stream is for writing error output.
(The same idea is also used in many non-POSIX compliant shells as well.)
For an interactive POSIX shell, the default is for these streams to read from and write to the shell's "console" ... which could be a physical console, but is more likely to be a "terminal emulator" on the user's (ultimate) desktop machine. (Details vary.)
A POSIX shell allows you to redirect the standard streams in various ways; e.g.
$ some-command < file # read stdin from 'file' $ some-command > file # write stdout to 'file' $ some-command 2> file # write stderr to 'file' $ some-command << EOF # read stdin from a 'here' document lines of input ... EOF $ some-command | another # connect stdout for one command to # stdin for the next one in a pipeline
and so on. If you do this, one or more of the standard streams is NOT connected to the console.
Further reading:
So how does this relate to the question?
When a Java program start, the System.in/out/err streams are connected to the standard input / output / error streams specified by the parent process; typically a shell.
In the case of System.out, that could be the console (however you define that) or it could be a file, or another program or ... /dev/null. But where the output goes is determined by how the JVM was launched.
So, the literal answer is "because that is what the parent process has told the Java program to do".
How internally shell communicates with jvm to set standard input / output in both Windows and Linux?
This is what happens with Linux, UNIX, Mac OSX and similar. (I don't know for Windows ... but I imagine it is similar.)
Suppose that the shell is going to run aaa > bbb.txt.
- The parent shell forks a child process ... sharing the parent shell's address space.
- The child process closes file descriptor 1 (the standard output file descriptor)
- The child process opens "bbb.txt" for writing on file descriptor 1.
- The child process execs the "aaa" command, and it becomes the "aaa" command process. The file descriptors 0, 1, and 2 are preserved by the exec call.
- The "aaa" command starts ...
When the "aaa" command starts, it finds that file descriptors 0 and 2 (stdin and stderr) refer to the same "file" as the parent shell. File descriptor 1 (stdout) refers to "bbb.txt".
The same thing happens when "aaa" is the java command.
fdoutactually output to console. I suppose it isFileOutputStreamas in Linux/Unix system, io device is also treated as file.outinitially set?" and "From where is it set?" This is how I read your Question, but it seems to me that answers are answering something else.