src/org/sonews/util/io/CRLFOutputStream.java
author František Kučera <franta-hg@frantovo.cz>
Tue Oct 25 10:16:13 2011 +0200 (2011-10-25)
changeset 107 b723308e1359
child 108 fdc075324ef3
permissions -rw-r--r--
SMTP: dot escaping – imported GNU code.
franta-hg@107
     1
/* CRLFOutputStream.java --
franta-hg@107
     2
Copyright (C) 2002, 2003, 2004  Free Software Foundation, Inc.
franta-hg@107
     3
franta-hg@107
     4
This file is part of GNU Classpath.
franta-hg@107
     5
franta-hg@107
     6
GNU Classpath is free software; you can redistribute it and/or modify
franta-hg@107
     7
it under the terms of the GNU General Public License as published by
franta-hg@107
     8
the Free Software Foundation; either version 2, or (at your option)
franta-hg@107
     9
any later version.
franta-hg@107
    10
franta-hg@107
    11
GNU Classpath is distributed in the hope that it will be useful, but
franta-hg@107
    12
WITHOUT ANY WARRANTY; without even the implied warranty of
franta-hg@107
    13
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
franta-hg@107
    14
General Public License for more details.
franta-hg@107
    15
franta-hg@107
    16
You should have received a copy of the GNU General Public License
franta-hg@107
    17
along with GNU Classpath; see the file COPYING.  If not, write to the
franta-hg@107
    18
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
franta-hg@107
    19
02110-1301 USA.
franta-hg@107
    20
franta-hg@107
    21
Linking this library statically or dynamically with other modules is
franta-hg@107
    22
making a combined work based on this library.  Thus, the terms and
franta-hg@107
    23
conditions of the GNU General Public License cover the whole
franta-hg@107
    24
combination.
franta-hg@107
    25
franta-hg@107
    26
As a special exception, the copyright holders of this library give you
franta-hg@107
    27
permission to link this library with independent modules to produce an
franta-hg@107
    28
executable, regardless of the license terms of these independent
franta-hg@107
    29
modules, and to copy and distribute the resulting executable under
franta-hg@107
    30
terms of your choice, provided that you also meet, for each linked
franta-hg@107
    31
independent module, the terms and conditions of the license of that
franta-hg@107
    32
module.  An independent module is a module which is not derived from
franta-hg@107
    33
or based on this library.  If you modify this library, you may extend
franta-hg@107
    34
this exception to your version of the library, but you are not
franta-hg@107
    35
obligated to do so.  If you do not wish to do so, delete this
franta-hg@107
    36
exception statement from your version. 
franta-hg@107
    37
 */
franta-hg@107
    38
package org.sonews.util.io; // original package: gnu.java.net
franta-hg@107
    39
franta-hg@107
    40
import java.io.FilterOutputStream;
franta-hg@107
    41
import java.io.IOException;
franta-hg@107
    42
import java.io.OutputStream;
franta-hg@107
    43
import java.io.UnsupportedEncodingException;
franta-hg@107
    44
franta-hg@107
    45
/** 
franta-hg@107
    46
 * An output stream that filters LFs into CR/LF pairs.
franta-hg@107
    47
 *
franta-hg@107
    48
 * @author Chris Burdess (dog@gnu.org)
franta-hg@107
    49
 */
franta-hg@107
    50
public class CRLFOutputStream extends FilterOutputStream {
franta-hg@107
    51
franta-hg@107
    52
	static final String US_ASCII = "US-ASCII";
franta-hg@107
    53
	/**
franta-hg@107
    54
	 * The CR octet.
franta-hg@107
    55
	 */
franta-hg@107
    56
	public static final int CR = 13;
franta-hg@107
    57
	/**
franta-hg@107
    58
	 * The LF octet.
franta-hg@107
    59
	 */
franta-hg@107
    60
	public static final int LF = 10;
franta-hg@107
    61
	/**
franta-hg@107
    62
	 * The CR/LF pair.
franta-hg@107
    63
	 */
franta-hg@107
    64
	public static final byte[] CRLF = {CR, LF};
franta-hg@107
    65
	/**
franta-hg@107
    66
	 * The last byte read.
franta-hg@107
    67
	 */
franta-hg@107
    68
	protected int last;
franta-hg@107
    69
franta-hg@107
    70
	/**
franta-hg@107
    71
	 * Constructs a CR/LF output stream connected to the specified output stream.
franta-hg@107
    72
	 */
franta-hg@107
    73
	public CRLFOutputStream(OutputStream out) {
franta-hg@107
    74
		super(out);
franta-hg@107
    75
		last = -1;
franta-hg@107
    76
	}
franta-hg@107
    77
franta-hg@107
    78
	/**
franta-hg@107
    79
	 * Writes a character to the underlying stream.
franta-hg@107
    80
	 * @exception IOException if an I/O error occurred
franta-hg@107
    81
	 */
franta-hg@107
    82
	@Override
franta-hg@107
    83
	public void write(int ch) throws IOException {
franta-hg@107
    84
		if (ch == CR) {
franta-hg@107
    85
			out.write(CRLF);
franta-hg@107
    86
		} else if (ch == LF) {
franta-hg@107
    87
			if (last != CR) {
franta-hg@107
    88
				out.write(CRLF);
franta-hg@107
    89
			}
franta-hg@107
    90
		} else {
franta-hg@107
    91
			out.write(ch);
franta-hg@107
    92
		}
franta-hg@107
    93
		last = ch;
franta-hg@107
    94
	}
franta-hg@107
    95
franta-hg@107
    96
	/**
franta-hg@107
    97
	 * Writes a byte array to the underlying stream.
franta-hg@107
    98
	 * @exception IOException if an I/O error occurred
franta-hg@107
    99
	 */
franta-hg@107
   100
	@Override
franta-hg@107
   101
	public void write(byte[] b) throws IOException {
franta-hg@107
   102
		write(b, 0, b.length);
franta-hg@107
   103
	}
franta-hg@107
   104
franta-hg@107
   105
	/**
franta-hg@107
   106
	 * Writes a portion of a byte array to the underlying stream.
franta-hg@107
   107
	 * @exception IOException if an I/O error occurred
franta-hg@107
   108
	 */
franta-hg@107
   109
	@Override
franta-hg@107
   110
	public void write(byte[] b, int off, int len) throws IOException {
franta-hg@107
   111
		int d = off;
franta-hg@107
   112
		len += off;
franta-hg@107
   113
		for (int i = off; i < len; i++) {
franta-hg@107
   114
			switch (b[i]) {
franta-hg@107
   115
				case CR:
franta-hg@107
   116
					out.write(b, d, i - d);
franta-hg@107
   117
					out.write(CRLF, 0, 2);
franta-hg@107
   118
					d = i + 1;
franta-hg@107
   119
					break;
franta-hg@107
   120
				case LF:
franta-hg@107
   121
					if (last != CR) {
franta-hg@107
   122
						out.write(b, d, i - d);
franta-hg@107
   123
						out.write(CRLF, 0, 2);
franta-hg@107
   124
					}
franta-hg@107
   125
					d = i + 1;
franta-hg@107
   126
					break;
franta-hg@107
   127
			}
franta-hg@107
   128
			last = b[i];
franta-hg@107
   129
		}
franta-hg@107
   130
		if (len - d > 0) {
franta-hg@107
   131
			out.write(b, d, len - d);
franta-hg@107
   132
		}
franta-hg@107
   133
	}
franta-hg@107
   134
franta-hg@107
   135
	/**
franta-hg@107
   136
	 * Writes the specified ASCII string to the underlying stream.
franta-hg@107
   137
	 * @exception IOException if an I/O error occurred
franta-hg@107
   138
	 */
franta-hg@107
   139
	public void write(String text) throws IOException {
franta-hg@107
   140
		try {
franta-hg@107
   141
			byte[] bytes = text.getBytes(US_ASCII);
franta-hg@107
   142
			write(bytes, 0, bytes.length);
franta-hg@107
   143
		} catch (UnsupportedEncodingException e) {
franta-hg@107
   144
			throw new IOException("The US-ASCII encoding is not supported on this system", e);
franta-hg@107
   145
		}
franta-hg@107
   146
	}
franta-hg@107
   147
franta-hg@107
   148
	/**
franta-hg@107
   149
	 * Writes a newline to the underlying stream.
franta-hg@107
   150
	 * @exception IOException if an I/O error occurred
franta-hg@107
   151
	 */
franta-hg@107
   152
	public void writeln() throws IOException {
franta-hg@107
   153
		out.write(CRLF, 0, 2);
franta-hg@107
   154
	}
franta-hg@107
   155
}