Unix Programming - How does the shell interpret newline in this case?

This is Interesting: Free IT Magazines  
Home > Archive > Unix Programming > May 2007 > How does the shell interpret newline in this case?





You are viewing an archived Text-only version of the thread. To view this thread in it's original format and/or if you want to reply to this thread please [click here]

Author How does the shell interpret newline in this case?
K-mart Cashier

2007-05-30, 1:21 am

When I go
#include <unistd.h>
#include <stdlib.h>

int main(int argc,char **argv)
{
int s=0;
int pid=fork();
if (!pid) {
execlp("echo","echo", argv[1],NULL);
_exit(1);
}
waitpid(pid,&s,0);
return s;
}


I get:

[cda@localhost ~]$ ./test "la\nla\nla\n"
la\nla\nla\n

[cda@localhost ~]$ strace ./flood3 "la\nla\nla\n"
execve("./flood3", ["./test3", "la\\nla\\nla\\n"], [/* 36 vars */]) =
0
brk(0) = 0x9810000

As you can see, when "la\nla\nla\n" gets passed to the shell, the
newline doesn't get interpreted.


However, when I change the program to:
#include <unistd.h>
#include <stdlib.h>


int main(int argc,char **argv)
{
int s=0;
int pid=fork();
if (!pid) {
execlp("echo","echo", "la\nla\nla\n",NULL);
_exit(1);
}
waitpid(pid,&s,0);
return s;
}

I get the following:
[cda@localhost ~]$ ./test3
la
la
la

How come in one case, the shell doesn't interpret the newline, but in
the other case it does?

Frank Cusack

2007-05-30, 1:21 am

On 29 May 2007 20:59:46 -0700 K-mart Cashier <cdalten@gmail.com> wrote:
....
> However, when I change the program to:
> #include <unistd.h>
> #include <stdlib.h>

....
> execlp("echo","echo", "la\nla\nla\n",NULL);

....
> I get the following:
> [cda@localhost ~]$ ./test3
> la
> la
> la
>
> How come in one case, the shell doesn't interpret the newline, but in
> the other case it does?


In neither case does the shell interpret the newline. In the second
case, the compiler handles the escaping.

-frank
Chris F.A. Johnson

2007-05-30, 1:21 am

On 2007-05-30, K-mart Cashier wrote:
> When I go
> #include <unistd.h>
> #include <stdlib.h>
>
> int main(int argc,char **argv)
> {
> int s=0;
> int pid=fork();
> if (!pid) {
> execlp("echo","echo", argv[1],NULL);
> _exit(1);
> }
> waitpid(pid,&s,0);
> return s;
> }
>
>
> I get:
>
> [cda@localhost ~]$ ./test "la\nla\nla\n"
> la\nla\nla\n
>
> [cda@localhost ~]$ strace ./flood3 "la\nla\nla\n"
> execve("./flood3", ["./test3", "la\\nla\\nla\\n"], [/* 36 vars */]) =
> 0
> brk(0) = 0x9810000
>
> As you can see, when "la\nla\nla\n" gets passed to the shell, the
> newline doesn't get interpreted.
>
>
> However, when I change the program to:
> #include <unistd.h>
> #include <stdlib.h>
>
>
> int main(int argc,char **argv)
> {
> int s=0;
> int pid=fork();
> if (!pid) {
> execlp("echo","echo", "la\nla\nla\n",NULL);
> _exit(1);
> }
> waitpid(pid,&s,0);
> return s;
> }
>
> I get the following:
> [cda@localhost ~]$ ./test3
> la
> la
> la
>
> How come in one case, the shell doesn't interpret the newline, but in
> the other case it does?


The shell doesn't see the string in either case (not that it would
make any difference if it did). In the first program, you are
invoking the executable echo (/bin/echo), which may or may not
interpret escape sequences. In the second, the compiler is
interpreting \n as a newline.

Even if you use the shell's built-in echo command, it may or may
not interpret \n as a newline. In either case, the echo command
itself is (or is not) expanding the escape sequences.

--
Chris F.A. Johnson, author | <http://cfaj.freeshell.org>
Shell Scripting Recipes: | My code in this post, if any,
A Problem-Solution Approach | is released under the
2005, Apress | GNU General Public Licence
quarkLore

2007-05-30, 7:17 am

> > How come in one case, the shell doesn't interpret the newline, but in
>

When you have it as a string literal compiler converts two characters
'' 'n' to 0x0a (new line) but when you pass "\n" to shell it passes
it literally and C program passes it directly to exec as \ followed by
n.

> The shell doesn't see the string in either case (not that it would
> make any difference if it did). In the first program, you are
> invoking the executable echo (/bin/echo), which may or may not
> interpret escape sequences. In the second, the compiler is
> interpreting \n as a newline.
>
> Even if you use the shell's built-in echo command, it may or may
> not interpret \n as a newline. In either case, the echo command
> itself is (or is not) expanding the escape sequences.
>

With bash (GNU bash, version 2.05b.0(1)) echo has an option -e. It
will need change in one line:
____
execlp("echo","echo", "-e", argv[1],NULL);
with -e options echo recognizes other escape sequences also
Check man pages for echo in your distro

Chris F.A. Johnson

2007-05-30, 7:20 pm

On 2007-05-30, quarkLore wrote:
> When you have it as a string literal compiler converts two characters
> '' 'n' to 0x0a (new line) but when you pass "\n" to shell it passes
> it literally and C program passes it directly to exec as \ followed by
> n.
>
> With bash (GNU bash, version 2.05b.0(1)) echo has an option -e. It
> will need change in one line:
> ____
> execlp("echo","echo", "-e", argv[1],NULL);
> with -e options echo recognizes other escape sequences also
> Check man pages for echo in your distro


That will not invoke the bash built-in command, but the executable
echo command, which may or may not accept any options. On FreeBSD,
for example:

$ /bin/echo -e 'qwe\nrty'
-e qwe\nrty


--
Chris F.A. Johnson, author | <http://cfaj.freeshell.org>
Shell Scripting Recipes: | My code in this post, if any,
A Problem-Solution Approach | is released under the
2005, Apress | GNU General Public Licence
Sponsored Links






Free braindumps | Software forum | Database administration forum

Copyright 2003 - 2008 webservertalk.com