aboutsummaryrefslogtreecommitdiffstats
path: root/sshlib/src/main/java/com/trilead/ssh2/packets/TypesReader.java
blob: 28f5363202cfa6a002d36c7bfbdca2dec091dd59 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
package com.trilead.ssh2.packets;

import java.io.IOException;
import java.math.BigInteger;

import com.trilead.ssh2.util.Tokenizer;


/**
 * TypesReader.
 * 
 * @author Christian Plattner, plattner@trilead.com
 * @version $Id: TypesReader.java,v 1.2 2008/04/01 12:38:09 cplattne Exp $
 */
public class TypesReader
{
	byte[] arr;
	int pos = 0;
	int max = 0;

	public TypesReader(byte[] arr)
	{
		this.arr = arr;
		pos = 0;
		max = arr.length;
	}

	public TypesReader(byte[] arr, int off)
	{
		this.arr = arr;
		this.pos = off;
		this.max = arr.length;

		if ((pos < 0) || (pos > arr.length))
			throw new IllegalArgumentException("Illegal offset.");
	}

	public TypesReader(byte[] arr, int off, int len)
	{
		this.arr = arr;
		this.pos = off;
		this.max = off + len;

		if ((pos < 0) || (pos > arr.length))
			throw new IllegalArgumentException("Illegal offset.");

		if ((max < 0) || (max > arr.length))
			throw new IllegalArgumentException("Illegal length.");
	}

	public int readByte() throws IOException
	{
		if (pos >= max)
			throw new IOException("Packet too short.");

		return (arr[pos++] & 0xff);
	}

	public byte[] readBytes(int len) throws IOException
	{
		if ((pos + len) > max)
			throw new IOException("Packet too short.");

		byte[] res = new byte[len];

		System.arraycopy(arr, pos, res, 0, len);
		pos += len;

		return res;
	}

	public void readBytes(byte[] dst, int off, int len) throws IOException
	{
		if ((pos + len) > max)
			throw new IOException("Packet too short.");

		System.arraycopy(arr, pos, dst, off, len);
		pos += len;
	}

	public boolean readBoolean() throws IOException
	{
		if (pos >= max)
			throw new IOException("Packet too short.");

		return (arr[pos++] != 0);
	}

	public int readUINT32() throws IOException
	{
		if ((pos + 4) > max)
			throw new IOException("Packet too short.");

		return ((arr[pos++] & 0xff) << 24) | ((arr[pos++] & 0xff) << 16) | ((arr[pos++] & 0xff) << 8)
				| (arr[pos++] & 0xff);
	}

	public long readUINT64() throws IOException
	{
		if ((pos + 8) > max)
			throw new IOException("Packet too short.");

		long high = ((arr[pos++] & 0xff) << 24) | ((arr[pos++] & 0xff) << 16) | ((arr[pos++] & 0xff) << 8)
				| (arr[pos++] & 0xff); /* sign extension may take place - will be shifted away =) */

		long low = ((arr[pos++] & 0xff) << 24) | ((arr[pos++] & 0xff) << 16) | ((arr[pos++] & 0xff) << 8)
				| (arr[pos++] & 0xff); /* sign extension may take place - handle below */

		return (high << 32) | (low & 0xffffffffl); /* see Java language spec (15.22.1, 5.6.2) */
	}

	public BigInteger readMPINT() throws IOException
	{
		BigInteger b;

		byte raw[] = readByteString();

		if (raw.length == 0)
			b = BigInteger.ZERO;
		else
			b = new BigInteger(raw);

		return b;
	}

	public byte[] readByteString() throws IOException
	{
		int len = readUINT32();

		if ((len + pos) > max)
			throw new IOException("Malformed SSH byte string.");

		byte[] res = new byte[len];
		System.arraycopy(arr, pos, res, 0, len);
		pos += len;
		return res;
	}

	public String readString(String charsetName) throws IOException
	{
		int len = readUINT32();

		if ((len + pos) > max)
			throw new IOException("Malformed SSH string.");

		String res = (charsetName == null) ? new String(arr, pos, len) : new String(arr, pos, len, charsetName);
		pos += len;

		return res;
	}

	public String readString() throws IOException
	{
		int len = readUINT32();

		if ((len + pos) > max)
			throw new IOException("Malformed SSH string.");

		String res = new String(arr, pos, len, "ISO-8859-1");
		
		pos += len;

		return res;
	}

	public String[] readNameList() throws IOException
	{
		return Tokenizer.parseTokens(readString(), ',');
	}

	public int remain()
	{
		return max - pos;
	}

}