I/O Redirection: how can I redirect error msgs to a temp file

Hi there,

I just want to know how can I redirect error msgs returned from running a command (e.g. nslookup) and then only print out the correct output using an if statement?.

I've tried the following:

where $a is a list of IPs.

but I got all the error msgs printed out to screen and the corret values hasn't enhanced :frowning:

any help is apprieciated

You might find it easier to do one at a time, since nslookup dos not do lists as I recall:

for i in $a
do
 ... $i ....
done

You might use "ping" or "ping -s $i 100 1" if they are supposed to be live and accessible, and get the name from that.

1 Like

You can try to redirect the output to:

2>/dev/null

2 Likes

nslookup does not produce an error message on stderr or produce a return status when a host is not found. It just reports on stdout that a host could not be found.
You might want to try host instead if available, but host only works with a single name, not with a list of names...

1 Like

thanks for your help and input guys,

what I need is to give the nslookup an IP address each time using a while loop (done)

and than, check if a host name was returned.. if it does then great! and it will be added to a temporary file. if it is not, than I want a customized error msg to appear.

what I am doing now is taking only the host name part of the nslookup output.. which can has something like "ns9.google.com" or sometimes.. nothing!

I want to replace the "nothing" with an error msg that I wrote.

---------- Post updated at 06:21 PM ---------- Previous update was at 05:25 PM ----------

here is the part I am trying to do that through:

what I'm trying to achieve here is that, when ever that value of print $2 is null, than print an error mssage, otherwise print the value in print $2

this should make things clearer to you I wish

---------- Post updated at 07:41 PM ---------- Previous update was at 06:21 PM ----------

this code seems to be partially working:

but I am getting no "Error" messages. any suggestions please.

Some messages are on stdout (1), some on stderr (2) (in bits!), none on /dev/tty, for my HPUX system:

$ truss -o /tmp/nsl.tr nslookup 12.23.34.45 ; grep write /tmp/nsl.tr          
Using /etc/hosts on:  hideme
looking up FILES
Trying DNS
Trying NIS
*** No hostname information is available for "12.23.34.45"
write(1, "U s i n g   / e t c / h o s t s ".., 32) ....... = 32
write(1, "l o o k i n g   u p   F I L E S ".., 17) ....... = 17
write(1, "T r y i n g   D N S \n", 11) ................... = 11
write(1, "T r y i n g   N I S \n", 11) ................... = 11
write(2, "* * *   N o   h ", 8) .......................... = 8
write(2, "o s t n a m e ", 7) ............................ = 7
write(2, "  i n f o r m a ", 8) .......................... = 8
write(2, "t ", 1) ........................................ = 1
write(2, "i o n   i s   a ", 8) .......................... = 8
write(2, "v ", 1) ........................................ = 1
write(2, "a i l a b l e   ", 8) .......................... = 8
write(2, "f ", 1) ........................................ = 1
write(2, "o r   " 1 2 . 2 ", 8) .......................... = 8
write(2, "3 . 3 4 . 4 5 ", 7) ............................ = 7
write(2, "" \n", 2) ...................................... = 2
$ 
 
 
 
Good IP:
 
$ truss -o /tmp/nsl.tr nslookup 89.67.45.123 ; grep write /tmp/nsl.tr
Using /etc/hosts on:  hideme
looking up FILES
Name:    hideme
Address:  89.67.45.123
Aliases:  hideme.somedomain.com
write(1, "U s i n g   / e t c / h o s t s ".., 32) ....... = 32
write(1, "l o o k i n g   u p   F I L E S ".., 17) ....... = 17
write(1, "N a m e :         h i d e m e \n".., 26) ....... = 26
write(1, "    8 9 . 6 7 . 4 5 . 1 2 3 ".., 26) ....... = 26
write(1, "    h i d e m e . s o m e d o ".., 34) ....... = 34
$
 
 
Good IP, PTR specific query for pointer-reverse = ip to name:
 
$ truss -o /tmp/nsl.tr nslookup -q=PTR 89.67.45.123 ; grep write /tmp/nsl.tr
Using /etc/hosts on:  hideme
looking up FILES
Trying DNS
123.45.67.89.in-addr.arpa    name = hideme.somedomain.com
write(1, "U s i n g   / e t c / h o s t s ".., 32) ....... = 32
write(1, "l o o k i n g   u p   F I L E S ".., 17) ....... = 17
write(1, "T r y i n g   D N S \n", 11) ................... = 11
write(1, "1 2 3 . 4 5 . 6 7 . 8 9 . i n - ".., 28) ....... = 28
write(1, "\tn a m e   =   h i d e m e . s ".., 34) ....... = 34
write(1, "\n", 1) ........................................ = 1
$
 
 
Good IP, specific DNS server:
 
$ truss -o /tmp/nsl.tr nslookup 89.67.45.123 89.123.45.67 ; grep write /tmp/nsl.tr 
Name Server:  nameserver1.somedomain.com
Address:  89.123.45.67
Trying DNS
Name:    hideme.somedomain.com
Address:  89.67.45.123 
write(1, "N a m e   S e r v e r :     n a ".., 50) ....... = 50
write(1, "    8 9 . 1 2 3 . 4 5 . 6 7 \n".., 17) ....... = 17
write(1, "T r y i n g   D N S \n", 11) ................... = 11
write(1, "N a m e :         h i d e m e ".., 44) ....... = 44
write(1, "    8 9 . 6 7 . 4 5 . 1 2 3 ".., 19) ....... = 19
$ 

Tools like this, called truss, tusc or strace, can tell you what you are seeing in more detail.

This thread seems to be a repeat of a previous thread:
http://www.unix.com/shell-programming-scripting/151610-nslookup-am-i-doing-right.html
In the previous thread the O/P posted sample output from a version of "nslookup" which I do not recognise.

Anybody worked out what Operating System and TCP/IP package this is?

Just for interest, unix versions of "nslookup" do use the output channels in a strange manner. I use an unusual (but portable) method to capture the whole output of one enquiry to a file having failed to get the combined output to a pipe by normal means.

>mylogfile
nslookup server_name 2>>mylogfile 1>>mylogfile

It is then possible to search "mylogfile" for error messages such as "No hostname information is available".
If anybody recognises the O/P version of "nslookup" can they try various techniques to capture the whole output from one enquiry?

The general rule is " >> file 2>&1 " to capture both, one (stdout) first, then 2 (stderr).

Very occasionally, you will see/do these in the opposite order, and it is not always a mistake (just usually), to send stdout to a file and stderr down a pipeline. If the app writes to (or reads from) an fd opened on /dev/tty, then you are into the land of expect/rsh/ssh to create a pseudo/remote tty you can recapture onto stdout.

Keeping the controlling terminal mapped to /dev/tty, FILE*'s: stdin, stdout, stderr, fd's: 0, 1, 2 ; cooked and uncooked tty input and output all straight and separate is one of those classic initial UNIX learning tasks.

Putting both into one file is popular: you do no care which wrote what, no research, one or no files, and you can grep or otherwise process the output to see if you got what you wanted and discard the rest. You might do something like this for simplicity and volume efficiency:

for ip in $ip_list
do
 echo ==== $ip
 nslookup $ip $DNS_SERVER
 echo ====
done 2>&1 | sed '
  /^==== /{
    :loop
    /\n====$/!N
    b loop
   }
 . . .
 ' > output_file

This way, you do an nslookup for each ip and frame the output for each. One sed can collect all the lines for one ip into the buffer using that framing, and then ( . . . = depends on what your nslookup writes and what you want) you can make it into whatever you want. The only file you make is the output file -- no cleanup, no old data, no file name creation or collisions, no running out of space with big data sets.

---------- Post updated at 03:35 PM ---------- Previous update was at 02:41 PM ----------

PS: nslookup has an interactive command mode, so you can use one nslookup if you generate commands to it equivalent to the command line args, and avoid calling it so many times.

@DGPickett
Under what unix O/S does nslookup react correctly to the Shell redirects like "2>&1". It is one of the very few programs where I had to use unusual techniques.
Imho unix "nslookup" just ignores unix I/O conventions.

Btw. Scripting a unix "nslookup" global enquiry and saving the results is not hard work. The secret there is not to try to redirect the output in Shell but to use the output functions in "nslookup" itself.
There almost certainly will be issues with listing the contents of a remote Internet Name Server because most of them block such enquiries.

Yes, zone inquiry is no longer considered innocent!

nslookup is not a mainstream tool, and like many somewhat admin-level tools, it not so user friendly. For the casual user, learning the various query methods and output formats is a bit of a pain. They might be better served doing getpeername, gethostbyname and such in C, JAVA or PERL.