Weird I/O bug

  • Thread starter Spencer Rugaber
  • Start date
S

Spencer Rugaber

I ran across an interesting bug, which I have isolated to the
following:

/* 1*/ import java.io.*;
/* 2*/ public class WordCount {
/* 3*/ public static void main (String[] args) {
/* 4*/ InputStreamReader tr = new InputStreamReader(System.in);
/* 5*/ try {
/* 6*/ tr.read(); /* Input intentionally ignored */
/* 7*/ } catch (Exception e) {
/* 8*/ System.exit(-1);
/* 9*/ }
/*10*/ System.out.println(0);
/*11*/ System.exit(0);
/*12*/ }
/*13*/ }

When run with input consisting of an empty file from standard in,
the output is a line consisting only of "0D".

If input is from a file, rather than the command line, the program
works, printing only "0". If lines 4-9 are removed, the program
works.

The problems, occurs in Java 1.3, 1.4, 1.5. It occurs on Linux,
Solaris and Windows systems.

The only thoughts I have are 1) that somehow stdin and stdout both
being the terminal confuses things, or 2) somehow, conversion between
bytes and ints is a problem.

I can't be the first person to notice this problem. All suggestions
appreciated.

Thanks.

Spencer
--

Spencer
-------

Spencer Rugaber
2406 Klaus Advanced Computing Building
College of Computing, Georgia Tech, Atlanta GA 30332-0280
Internet: (e-mail address removed)
Phone: (404) 894-8450 Fax: (404) 894-9442
WWW: http://www.cc.gatech.edu/fac/Spencer.Rugaber
 
M

Mark Space

Spencer said:
When run with input consisting of an empty file from standard in,
the output is a line consisting only of "0D".

If input is from a file, rather than the command line, the program
works, printing only "0". If lines 4-9 are removed, the program
works.

For me it simply prints 0 both times, which I think is correct. What
output where you expecting?
 
R

Roedy Green

When run with input consisting of an empty file from standard in,
the output is a line consisting only of "0D".

that is as invalid file. It shoulds be either 0D 0A or 0A.

The problem is similar to having only half of a multibyte unicode
encoding.

There needs to be an InvalidDataException.
 
A

Arne Vajhøj

Roedy said:
that is as invalid file. It shoulds be either 0D 0A or 0A.

The problem is similar to having only half of a multibyte unicode
encoding.

Not at all.

CR is a valid line terminator in older versions of Mac OS.

0x0D is valid file content not being a line terminator with
counted record formats.

Arne
 
R

Roedy Green

When run with input consisting of an empty file from standard in,
the output is a line consisting only of "0D".

i presume you mean one 8-bit hex char 0d, not two chars 0 D
 
J

John B. Matthews

[...]
When run with input consisting of an empty file from standard in,
the output is a line consisting only of "0D".

If input is from a file, rather than the command line, the program
works, printing only "0". If lines 4-9 are removed, the program
works.
[...]

$ java -version
java version "1.5.0_13"
....
$ touch temp.txt
$ java WordCount < temp.txt
0
$ java WordCount
0D

The last result required control-D (EOT) to terminate input. Is that
what you're seeing?
 
T

Tom Anderson

[...]
When run with input consisting of an empty file from standard in,
the output is a line consisting only of "0D".

If input is from a file, rather than the command line, the program
works, printing only "0". If lines 4-9 are removed, the program
works.
[...]

$ java -version
java version "1.5.0_13"
...
$ touch temp.txt
$ java WordCount < temp.txt
0
$ java WordCount
0D

The last result required control-D (EOT) to terminate input. Is that
what you're seeing?

This is what i assumed he meant - i think this discussion of hex values is
off-beam. And i get the same result on MacOS X, FWIW.

I think what this is is the shell (or possibly the terminal driver, or
maybe even the java binary) echoing "^D" to the screen when you type that
escape sequence - that's standard behaviour. When the app then prints that
0, it overwrites the ^, and you see 0D.

If you modify the program to print the empty string, then what you see on
screen is "^D". If you modify it to print 99, you just see the 99. If you
modify it not to call print at all, then you very briefly see ^D, but this
is then overwritten by the prompt that appears after the program
terminates (or at least, i do - your console may be faster than mine!). If
you run the unmodified program, but redirect the output to a file, it just
contains 0. All this fits with the explanation i give above.

tom
 
S

Spencer Rugaber

i presume you mean one 8-bit hex char 0d, not two chars 0 D

What I see on the screen is a line by itself containing only the
characters 0 and D, adjacent to each other. This is not what I
expected to see, which was a 0 by itself on a line.

Spencer
--

Spencer
-------

Spencer Rugaber
2406 Klaus Advanced Computing Building
College of Computing, Georgia Tech, Atlanta GA 30332-0280
Internet: (e-mail address removed)
Phone: (404) 894-8450 Fax: (404) 894-9442
WWW: http://www.cc.gatech.edu/fac/Spencer.Rugaber
 
S

Spencer Rugaber

The last result required control-D (EOT) to terminate input. Is that
what you're seeing?

Exactly.

Spencer
--

Spencer
-------

Spencer Rugaber
2406 Klaus Advanced Computing Building
College of Computing, Georgia Tech, Atlanta GA 30332-0280
Internet: (e-mail address removed)
Phone: (404) 894-8450 Fax: (404) 894-9442
WWW: http://www.cc.gatech.edu/fac/Spencer.Rugaber
 
S

Spencer Rugaber

I think what this is is the shell (or possibly the terminal driver, or
maybe even the java binary) echoing "^D" to the screen when you type that
escape sequence - that's standard behaviour. When the app then prints that
0, it overwrites the ^, and you see 0D.
If you modify the program to print the empty string, then what you see on
screen is "^D". If you modify it to print 99, you just see the 99. If you
modify it not to call print at all, then you very briefly see ^D, but this
is then overwritten by the prompt that appears after the program
terminates (or at least, i do - your console may be faster than mine!). If
you run the unmodified program, but redirect the output to a file, it just
contains 0. All this fits with the explanation i give above.

This sounds reasonable, but why don't I see the ^D when I talk to the
shell directly, as with the command "cat" (by itself taking input from
the command line). If that input is only ^D, then nothing is echoed.

So Java's behavior still seems weird to me. Is this what I should
expect from Java? I could find no justification for it in the API
description.

Thanks.

Spencer
--

Spencer
-------

Spencer Rugaber
2406 Klaus Advanced Computing Building
College of Computing, Georgia Tech, Atlanta GA 30332-0280
Internet: (e-mail address removed)
Phone: (404) 894-8450 Fax: (404) 894-9442
WWW: http://www.cc.gatech.edu/fac/Spencer.Rugaber
 
T

Tom Anderson

This sounds reasonable, but why don't I see the ^D when I talk to the
shell directly, as with the command "cat" (by itself taking input from
the command line). If that input is only ^D, then nothing is echoed.

So Java's behavior still seems weird to me. Is this what I should
expect from Java? I could find no justification for it in the API
description.

Got a C compiler? Try this:

#include <stdio.h>
int main(int argc, char **argv) {
char buf[100] ;
gets(buf) ;
printf("%i\n", 0) ;
return 0 ;
}

tom
 
J

John B. Matthews

I agree. If I modify it to print " ", I get a fleeting "^" followed by "
D". The shell also echoes other control characters this way. Sorry if I
overlooked it, but I missed your post above in this thread:

<http://groups.google.com/group/comp.lang.java.programmer/browse_frm/thre
ad/dee2331e25a0c47a/e14f72c577449842?hl=en&lnk=st&q=#e14f72c577449842>

If cat echoes anything, it swallows the first ^D and the shell backs
over a second one.
So Java's behavior still seems weird to me. Is this what I should
expect from Java? I could find no justification for it in the API
description.

Got a C compiler? Try this:

#include <stdio.h>
int main(int argc, char **argv) {
char buf[100] ;
gets(buf) ;
printf("%i\n", 0) ;
return 0 ;
}

tom

FWIW, I get the same result in C on Mac OS, too.
 
R

RedGrittyBrick

Spencer said:
This sounds reasonable, but why don't I see the ^D when I talk to the
shell directly, as with the command "cat" (by itself taking input from
the command line). If that input is only ^D, then nothing is echoed.

So Java's behavior still seems weird to me. Is this what I should
expect from Java? I could find no justification for it in the API
description.

From what Tom and others have said, it isn't Java , it is your shell
which is responsible for the "D" which you are seeing.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,995
Messages
2,570,230
Members
46,817
Latest member
DicWeils

Latest Threads

Top