Skip to main content
added 352 characters in body
Source Link
Stéphane Chazelas
  • 585.1k
  • 96
  • 1.1k
  • 1.7k

php will inherit the stdin of the shell (a tty device if invoked at the prompt of an interactive shell) and nano will inherit it as well (while stdout is a pipe used by php to retrieve the output of nano and pass it through, so I don't think that's whatnano seems to be happy with it, not all editors would, you may want to douse system() instead here).

php will inherit the stdin of the shell (a tty device if invoked at the prompt of an interactive shell) and nano will inherit it as well (while stdout is a pipe used by php to retrieve the output of nano, so I don't think that's what you want to do).

php will inherit the stdin of the shell (a tty device if invoked at the prompt of an interactive shell) and nano will inherit it as well (while stdout is a pipe used by php to retrieve the output of nano and pass it through, nano seems to be happy with it, not all editors would, you may want to use system() instead here).

added 352 characters in body
Source Link
Stéphane Chazelas
  • 585.1k
  • 96
  • 1.1k
  • 1.7k

So here, you need to change your php script to:

<?php
foreach(file("php://stdin") as $name) {
  echo "Hello $name";
  passthru("nano <&3 3<&-");
}
?>

And call it as:

{ printf '%s\n' World Everybody | php script.php; } 3<&0

To pass both resources (the pipe from printf and the original stdin) to php.

If you expect that php script to always be called from within a terminal and that nano should then always interact with the terminal (but then again, note that php makes its stdout not the terminal), you could change it instead to:

<?php
foreach(file("php://stdin") as $name) {
  echo "Hello $name";
  passthru("nano < /dev/tty");
}
?>

Where we hard-code nano's stdin to be the controlling terminal.

So here, you need to change your php script to:

<?php
foreach(file("php://stdin") as $name) {
  echo "Hello $name";
  passthru("nano <&3 3<&-");
}
?>

And call it as:

{ printf '%s\n' World Everybody | php script.php; } 3<&0

To pass both resources (the pipe from printf and the original stdin) to php.

If you expect that php script to always be called from within a terminal and that nano should then always interact with the terminal (but then again, note that php makes its stdout not the terminal), you could change it instead to:

<?php
foreach(file("php://stdin") as $name) {
  echo "Hello $name";
  passthru("nano < /dev/tty");
}
?>

Where we hard-code nano's stdin to be the controlling terminal.

added 1634 characters in body
Source Link
Stéphane Chazelas
  • 585.1k
  • 96
  • 1.1k
  • 1.7k

Example:

$ php -r 'passthru("ls -l /proc/self/fd");'
total 0
lrwx------ 1 stephane stephane 64 Mar 19 15:12 0 -> /dev/pts/38
l-wx------ 1 stephane stephane 64 Mar 19 15:12 1 -> pipe:[22538485]
lrwx------ 1 stephane stephane 64 Mar 19 15:12 2 -> /dev/pts/38

fd 0 is a tty device for terminal interaction.

$ echo hello | php -r 'passthru("ls -l /proc/self/fd");'
total 0
lr-x------ 1 stephane stephane 64 Mar 19 15:12 0 -> pipe:[22539326]
l-wx------ 1 stephane stephane 64 Mar 19 15:12 1 -> pipe:[22530020]
lrwx------ 1 stephane stephane 64 Mar 19 15:12 2 -> /dev/pts/38

Now ls's stdin is a pipe (the one echo is feeding).

$ { echo hello 3<&- | php -r 'passthru("ls -l /proc/\$PPID/fd /proc/self/fd <&3 3<&-");';} 3<&0
/proc/9202/fd:
total 0
lr-x------ 1 stephane stephane 64 Mar 19 15:17 0 -> pipe:[22544619]
lrwx------ 1 stephane stephane 64 Mar 19 15:17 1 -> /dev/pts/38
lrwx------ 1 stephane stephane 64 Mar 19 15:17 2 -> /dev/pts/38
lrwx------ 1 stephane stephane 64 Mar 19 15:17 3 -> /dev/pts/38
lr-x------ 1 stephane stephane 64 Mar 19 15:17 4 -> pipe:[22544623]

/proc/self/fd:
total 0
lrwx------ 1 stephane stephane 64 Mar 19 15:17 0 -> /dev/pts/38
l-wx------ 1 stephane stephane 64 Mar 19 15:17 1 -> pipe:[22544623]
lrwx------ 1 stephane stephane 64 Mar 19 15:17 2 -> /dev/pts/38

ls's stdin has been made the tty device again, while its parent (php) still has the pipe on stdin (see also the tty on fd 3 and another pipe on fd 4, probably the one it is reading the output of ls with).

Example:

$ php -r 'passthru("ls -l /proc/self/fd");'
total 0
lrwx------ 1 stephane stephane 64 Mar 19 15:12 0 -> /dev/pts/38
l-wx------ 1 stephane stephane 64 Mar 19 15:12 1 -> pipe:[22538485]
lrwx------ 1 stephane stephane 64 Mar 19 15:12 2 -> /dev/pts/38

fd 0 is a tty device for terminal interaction.

$ echo hello | php -r 'passthru("ls -l /proc/self/fd");'
total 0
lr-x------ 1 stephane stephane 64 Mar 19 15:12 0 -> pipe:[22539326]
l-wx------ 1 stephane stephane 64 Mar 19 15:12 1 -> pipe:[22530020]
lrwx------ 1 stephane stephane 64 Mar 19 15:12 2 -> /dev/pts/38

Now ls's stdin is a pipe (the one echo is feeding).

$ { echo hello 3<&- | php -r 'passthru("ls -l /proc/\$PPID/fd /proc/self/fd <&3 3<&-");';} 3<&0
/proc/9202/fd:
total 0
lr-x------ 1 stephane stephane 64 Mar 19 15:17 0 -> pipe:[22544619]
lrwx------ 1 stephane stephane 64 Mar 19 15:17 1 -> /dev/pts/38
lrwx------ 1 stephane stephane 64 Mar 19 15:17 2 -> /dev/pts/38
lrwx------ 1 stephane stephane 64 Mar 19 15:17 3 -> /dev/pts/38
lr-x------ 1 stephane stephane 64 Mar 19 15:17 4 -> pipe:[22544623]

/proc/self/fd:
total 0
lrwx------ 1 stephane stephane 64 Mar 19 15:17 0 -> /dev/pts/38
l-wx------ 1 stephane stephane 64 Mar 19 15:17 1 -> pipe:[22544623]
lrwx------ 1 stephane stephane 64 Mar 19 15:17 2 -> /dev/pts/38

ls's stdin has been made the tty device again, while its parent (php) still has the pipe on stdin (see also the tty on fd 3 and another pipe on fd 4, probably the one it is reading the output of ls with).

Source Link
Stéphane Chazelas
  • 585.1k
  • 96
  • 1.1k
  • 1.7k
Loading