comparison app/src/main/java/net/sourceforge/jsocks/Socks5Message.java @ 438:d29cce60f393

migrate from Eclipse to Android Studio
author Carl Byington <carl@five-ten-sg.com>
date Thu, 03 Dec 2015 11:23:55 -0800
parents src/net/sourceforge/jsocks/Socks5Message.java@2bc6805cbc91
children
comparison
equal deleted inserted replaced
437:208b31032318 438:d29cce60f393
1 package net.sourceforge.jsocks;
2
3 import java.io.IOException;
4 import java.io.InputStream;
5 import java.io.OutputStream;
6 import java.io.DataInputStream;
7 import java.net.InetAddress;
8 import java.net.UnknownHostException;
9
10 /**
11 SOCKS5 request/response message.
12 */
13
14 public class Socks5Message extends ProxyMessage{
15 /** Address type of given message*/
16 public int addrType;
17
18 byte[] data;
19
20 /**
21 Server error response.
22 @param cmd Error code.
23 */
24 public Socks5Message(int cmd){
25 super(cmd,null,0);
26 data = new byte[3];
27 data[0] = SOCKS_VERSION; //Version.
28 data[1] = (byte)cmd; //Reply code for some kind of failure.
29 data[2] = 0; //Reserved byte.
30 }
31
32 /**
33 Construct client request or server response.
34 @param cmd - Request/Response code.
35 @param ip - IP field.
36 @paarm port - port field.
37 */
38 public Socks5Message(int cmd,InetAddress ip,int port){
39 super(cmd,ip,port);
40 this.host = ip==null?"0.0.0.0":ip.getHostName();
41 this.version = SOCKS_VERSION;
42
43 byte[] addr;
44
45 if(ip == null){
46 addr = new byte[4];
47 addr[0]=addr[1]=addr[2]=addr[3]=0;
48 }else
49 addr = ip.getAddress();
50
51 addrType = addr.length == 4 ? SOCKS_ATYP_IPV4
52 : SOCKS_ATYP_IPV6;
53
54 data = new byte[6+addr.length];
55 data[0] = (byte) SOCKS_VERSION; //Version
56 data[1] = (byte) command; //Command
57 data[2] = (byte) 0; //Reserved byte
58 data[3] = (byte) addrType; //Address type
59
60 //Put Address
61 System.arraycopy(addr,0,data,4,addr.length);
62 //Put port
63 data[data.length-2] = (byte)(port>>8);
64 data[data.length-1] = (byte)(port);
65 }
66
67
68 /**
69 Construct client request or server response.
70 @param cmd - Request/Response code.
71 @param hostName - IP field as hostName, uses ADDR_TYPE of HOSTNAME.
72 @paarm port - port field.
73 */
74 public Socks5Message(int cmd,String hostName,int port){
75 super(cmd,null,port);
76 this.host = hostName;
77 this.version = SOCKS_VERSION;
78
79 //System.out.println("Doing ATYP_DOMAINNAME");
80
81 addrType = SOCKS_ATYP_DOMAINNAME;
82 byte addr[] = hostName.getBytes();
83
84 data =new byte[7+addr.length];
85 data[0] = (byte) SOCKS_VERSION; //Version
86 data[1] = (byte) command; //Command
87 data[2] = (byte) 0; //Reserved byte
88 data[3] = (byte) SOCKS_ATYP_DOMAINNAME; //Address type
89 data[4] = (byte) addr.length; //Length of the address
90
91 //Put Address
92 System.arraycopy(addr,0,data,5,addr.length);
93 //Put port
94 data[data.length-2] = (byte)(port >>8);
95 data[data.length-1] = (byte)(port);
96 }
97
98 /**
99 Initialises Message from the stream. Reads server response from
100 given stream.
101 @param in Input stream to read response from.
102 @throws SocksException If server response code is not SOCKS_SUCCESS(0), or
103 if any error with protocol occurs.
104 @throws IOException If any error happens with I/O.
105 */
106 public Socks5Message(InputStream in) throws SocksException,
107 IOException{
108 this(in,true);
109 }
110
111 /**
112 Initialises Message from the stream. Reads server response or client
113 request from given stream.
114
115 @param in Input stream to read response from.
116 @param clinetMode If true read server response, else read client request.
117 @throws SocksException If server response code is not SOCKS_SUCCESS(0) and
118 reading in client mode, or if any error with protocol occurs.
119 @throws IOException If any error happens with I/O.
120 */
121 public Socks5Message(InputStream in,boolean clientMode)throws SocksException,
122 IOException{
123 read(in,clientMode);
124 }
125
126
127 /**
128 Initialises Message from the stream. Reads server response from
129 given stream.
130 @param in Input stream to read response from.
131 @throws SocksException If server response code is not SOCKS_SUCCESS(0), or
132 if any error with protocol occurs.
133 @throws IOException If any error happens with I/O.
134 */
135 public void read(InputStream in) throws SocksException,
136 IOException{
137 read(in,true);
138 }
139
140
141 /**
142 Initialises Message from the stream. Reads server response or client
143 request from given stream.
144
145 @param in Input stream to read response from.
146 @param clinetMode If true read server response, else read client request.
147 @throws SocksException If server response code is not SOCKS_SUCCESS(0) and
148 reading in client mode, or if any error with protocol occurs.
149 @throws IOException If any error happens with I/O.
150 */
151 public void read(InputStream in,boolean clientMode) throws SocksException,
152 IOException{
153 data = null;
154 ip = null;
155
156 DataInputStream di = new DataInputStream(in);
157
158 version = di.readUnsignedByte();
159 command = di.readUnsignedByte();
160 if(clientMode && command != 0)
161 throw new SocksException(command);
162
163 int reserved = di.readUnsignedByte();
164 addrType = di.readUnsignedByte();
165
166 byte addr[];
167
168 switch(addrType){
169 case SOCKS_ATYP_IPV4:
170 addr = new byte[4];
171 di.readFully(addr);
172 host = bytes2IPV4(addr,0);
173 break;
174 case SOCKS_ATYP_IPV6:
175 addr = new byte[SOCKS_IPV6_LENGTH];//I believe it is 16 bytes,huge!
176 di.readFully(addr);
177 host = bytes2IPV6(addr,0);
178 break;
179 case SOCKS_ATYP_DOMAINNAME:
180 //System.out.println("Reading ATYP_DOMAINNAME");
181 addr = new byte[di.readUnsignedByte()];//Next byte shows the length
182 di.readFully(addr);
183 host = new String(addr);
184 break;
185 default:
186 throw(new SocksException(CProxy.SOCKS_JUST_ERROR));
187 }
188
189 port = di.readUnsignedShort();
190
191 if(addrType != SOCKS_ATYP_DOMAINNAME && doResolveIP){
192 try{
193 ip = InetAddress.getByName(host);
194 }catch(UnknownHostException uh_ex){
195 }
196 }
197 }
198
199 /**
200 Writes the message to the stream.
201 @param out Output stream to which message should be written.
202 */
203 public void write(OutputStream out)throws SocksException,
204 IOException{
205 if(data == null){
206 Socks5Message msg;
207
208 if(addrType == SOCKS_ATYP_DOMAINNAME)
209 msg = new Socks5Message(command,host,port);
210 else{
211 if(ip == null){
212 try{
213 ip = InetAddress.getByName(host);
214 }catch(UnknownHostException uh_ex){
215 throw new SocksException(CProxy.SOCKS_JUST_ERROR);
216 }
217 }
218 msg = new Socks5Message(command,ip,port);
219 }
220 data = msg.data;
221 }
222 out.write(data);
223 }
224
225 /**
226 Returns IP field of the message as IP, if the message was created
227 with ATYP of HOSTNAME, it will attempt to resolve the hostname,
228 which might fail.
229 @throws UnknownHostException if host can't be resolved.
230 */
231 public InetAddress getInetAddress() throws UnknownHostException{
232 if(ip!=null) return ip;
233
234 return (ip=InetAddress.getByName(host));
235 }
236
237 /**
238 Returns string representation of the message.
239 */
240 public String toString(){
241 String s=
242 "Socks5Message:"+"\n"+
243 "VN "+version+"\n"+
244 "CMD "+command+"\n"+
245 "ATYP "+addrType+"\n"+
246 "ADDR "+host+"\n"+
247 "PORT "+port+"\n";
248 return s;
249 }
250
251
252 /**
253 *Wether to resolve hostIP returned from SOCKS server
254 *that is wether to create InetAddress object from the
255 *hostName string
256 */
257 static public boolean resolveIP(){ return doResolveIP;}
258
259 /**
260 *Wether to resolve hostIP returned from SOCKS server
261 *that is wether to create InetAddress object from the
262 *hostName string
263 *@param doResolve Wether to resolve hostIP from SOCKS server.
264 *@return Previous value.
265 */
266 static public boolean resolveIP(boolean doResolve){
267 boolean old = doResolveIP;
268 doResolveIP = doResolve;
269 return old;
270 }
271
272 /*
273 private static final void debug(String s){
274 if(DEBUG)
275 System.out.print(s);
276 }
277 private static final boolean DEBUG = false;
278 */
279
280 //SOCKS5 constants
281 public static final int SOCKS_VERSION =5;
282
283 public static final int SOCKS_ATYP_IPV4 =0x1; //Where is 2??
284 public static final int SOCKS_ATYP_DOMAINNAME =0x3; //!!!!rfc1928
285 public static final int SOCKS_ATYP_IPV6 =0x4;
286
287 public static final int SOCKS_IPV6_LENGTH =16;
288
289 static boolean doResolveIP = true;
290
291 }