#region Copyright 2010-2014 by Roger Knapp, Licensed under the Apache License, Version 2.0
/* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#endregion
using System;
using System.IO;
using System.Text;
namespace CSharpTest.Net.Crypto
{
///
/// Bufferless stream reader for Unicode data
///
public class UnicodeReader : TextReader
{
readonly Encoding _encoding;
readonly Stream _stream;
int _peek = -1;
///
/// Bufferless stream reader for Unicode data
///
public UnicodeReader(Stream stream) : this(stream, Encoding.Unicode) { }
///
/// Bufferless stream reader for Unicode data
///
public UnicodeReader(Stream stream, Encoding encoding)
{
Check.Assert(
Object.ReferenceEquals(encoding, Encoding.Unicode) ||
Object.ReferenceEquals(encoding, Encoding.BigEndianUnicode)
);
_encoding = encoding;
_stream = stream;
}
///
/// Disposes the underlying stream
///
protected override void Dispose(bool disposing)
{
_peek = -1;
_stream.Dispose();
base.Dispose(disposing);
}
int Next()
{
if (_peek >= 0)
{
int ch = _peek;
_peek = -1;
return ch;
}
byte[] tmp = new byte[2];
Char[] chars = new Char[1];
try
{
if (_stream.Read(tmp, 0, 2) != 2 || _encoding.GetChars(tmp, 0, 2, chars, 0) != 1)
return -1;
return chars[0];
}
finally
{
tmp[0] = tmp[1] = 0;
chars[0] = Char.MinValue;
}
}
/// Returns the next character
public override int Peek()
{
return _peek = Next();
}
/// Returns the next character
public override int Read()
{
return Next();
}
/// Reads one character
public override int Read(char[] buffer, int index, int count)
{
Check.ArraySize(buffer, index + count, int.MaxValue);
int next;
if (count > 0 && -1 != (next = Next()))
{
buffer[index] = (Char)next;
return 1;
}
return 0;
}
/// Reads one character
public override int ReadBlock(char[] buffer, int index, int count)
{ return Read(buffer, index, count); }
}
}