comparison app/src/main/java/net/sourceforge/jsocks/CProxy.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/CProxy.java@3c16508419fe
children
comparison
equal deleted inserted replaced
437:208b31032318 438:d29cce60f393
1 package net.sourceforge.jsocks;
2 import java.net.*;
3 import java.io.*;
4 import java.util.Hashtable;
5 import java.util.Enumeration;
6
7 /**
8 Abstract class CProxy, base for classes Socks4Proxy and Socks5Proxy.
9 Defines methods for specifying default proxy, to be
10 used by all classes of this package.
11 */
12
13 public abstract class CProxy{
14
15 //Data members
16 protected InetRange directHosts = new InetRange();
17
18 protected InetAddress proxyIP = null;
19 protected String proxyHost = null;
20 protected int proxyPort;
21 protected Socket proxySocket = null;
22
23 protected InputStream in;
24 protected OutputStream out;
25
26 protected int version;
27
28 protected CProxy chainProxy = null;
29
30
31 //Protected static/class variables
32 protected static CProxy defaultProxy = null;
33
34 //Constructors
35 //====================
36 CProxy(CProxy chainProxy,
37 String proxyHost,int proxyPort)throws UnknownHostException{
38 this.chainProxy = chainProxy;
39 this.proxyHost = proxyHost;
40
41 if(chainProxy == null)
42 this.proxyIP = InetAddress.getByName(proxyHost);
43
44 this.proxyPort = proxyPort;
45 }
46
47
48 CProxy(String proxyHost,int proxyPort)throws UnknownHostException{
49 this(null,proxyHost,proxyPort);
50 }
51
52 CProxy(CProxy chainProxy,InetAddress proxyIP,int proxyPort){
53 this.chainProxy = chainProxy;
54 this.proxyIP = proxyIP;
55 this.proxyPort = proxyPort;
56 }
57
58 CProxy(InetAddress proxyIP,int proxyPort){
59 this(null,proxyIP,proxyPort);
60 }
61
62 CProxy(CProxy p){
63 this.proxyIP = p.proxyIP;
64 this.proxyPort = p.proxyPort;
65 this.version = p.version;
66 this.directHosts = p.directHosts;
67 }
68
69 //Public instance methods
70 //========================
71
72 /**
73 Get the port on which proxy server is running.
74 * @return CProxy port.
75 */
76 public int getPort(){
77 return proxyPort;
78 }
79 /**
80 Get the ip address of the proxy server host.
81 * @return CProxy InetAddress.
82 */
83 public InetAddress getInetAddress(){
84 return proxyIP;
85 }
86 /**
87 * Adds given ip to the list of direct addresses.
88 * This machine will be accessed without using proxy.
89 */
90 public void addDirect(InetAddress ip){
91 directHosts.add(ip);
92 }
93 /**
94 * Adds host to the list of direct addresses.
95 * This machine will be accessed without using proxy.
96 */
97 public boolean addDirect(String host){
98 return directHosts.add(host);
99 }
100 /**
101 * Adds given range of addresses to the lsit of direct addresses,
102 * machines within this range will be accessed without using proxy.
103 */
104 public void addDirect(InetAddress from,InetAddress to){
105 directHosts.add(from,to);
106 }
107 /**
108 * Sets given InetRange as the list of direct address, previous
109 * list will be discarded, any changes done previously with
110 * addDirect(Inetaddress) will be lost.
111 * The machines in this range will be accessed without using proxy.
112 * @param ir InetRange which should be used to look up direct addresses.
113 * @see InetRange
114 */
115 public void setDirect(InetRange ir){
116 directHosts = ir;
117 }
118
119 /**
120 Get the list of direct hosts.
121 * @return Current range of direct address as InetRange object.
122 * @see InetRange
123 */
124 public InetRange getDirect(){
125 return directHosts;
126 }
127 /**
128 Check wether the given host is on the list of direct address.
129 @param host Host name to check.
130 * @return true if the given host is specified as the direct addresses.
131 */
132 public boolean isDirect(String host){
133 return directHosts.contains(host);
134 }
135 /**
136 Check wether the given host is on the list of direct addresses.
137 @param host Host address to check.
138 * @return true if the given host is specified as the direct address.
139 */
140 public boolean isDirect(InetAddress host){
141 return directHosts.contains(host);
142 }
143 /**
144 Set the proxy which should be used to connect to given proxy.
145 @param chainProxy CProxy to use to connect to this proxy.
146 */
147 public void setChainProxy(CProxy chainProxy){
148 this.chainProxy = chainProxy;
149 }
150
151 /**
152 Get proxy which is used to connect to this proxy.
153 @return CProxy which is used to connect to this proxy, or null
154 if proxy is to be contacted directly.
155 */
156 public CProxy getChainProxy(){
157 return chainProxy;
158 }
159
160 /**
161 Get string representation of this proxy.
162 * @returns string in the form:proxyHost:proxyPort \t Version versionNumber
163 */
164 public String toString(){
165 return (""+proxyIP.getHostName()+":"+proxyPort+"\tVersion "+version);
166 }
167
168
169 //Public Static(Class) Methods
170 //==============================
171
172 /**
173 * Sets SOCKS4 proxy as default.
174 @param hostName Host name on which SOCKS4 server is running.
175 @param port Port on which SOCKS4 server is running.
176 @param user Username to use for communications with proxy.
177 */
178 public static void setDefaultProxy(String hostName,int port,String user)
179 throws UnknownHostException{
180 defaultProxy = new Socks4Proxy(hostName,port,user);
181 }
182
183 /**
184 * Sets SOCKS4 proxy as default.
185 @param ipAddress Host address on which SOCKS4 server is running.
186 @param port Port on which SOCKS4 server is running.
187 @param user Username to use for communications with proxy.
188 */
189 public static void setDefaultProxy(InetAddress ipAddress,int port,
190 String user){
191 defaultProxy = new Socks4Proxy(ipAddress,port,user);
192 }
193 /**
194 * Sets SOCKS5 proxy as default.
195 * Default proxy only supports no-authentication.
196 @param hostName Host name on which SOCKS5 server is running.
197 @param port Port on which SOCKS5 server is running.
198 */
199 public static void setDefaultProxy(String hostName,int port)
200 throws UnknownHostException{
201 defaultProxy = new Socks5Proxy(hostName,port);
202 }
203 /**
204 * Sets SOCKS5 proxy as default.
205 * Default proxy only supports no-authentication.
206 @param ipAddress Host address on which SOCKS5 server is running.
207 @param port Port on which SOCKS5 server is running.
208 */
209 public static void setDefaultProxy(InetAddress ipAddress,int port){
210 defaultProxy = new Socks5Proxy(ipAddress,port);
211 }
212 /**
213 * Sets default proxy.
214 @param p CProxy to use as default proxy.
215 */
216 public static void setDefaultProxy(CProxy p){
217 defaultProxy = p;
218 }
219
220 /**
221 Get current default proxy.
222 * @return Current default proxy, or null if none is set.
223 */
224 public static CProxy getDefaultProxy(){
225 return defaultProxy;
226 }
227
228 /**
229 Parses strings in the form: host[:port:user:password], and creates
230 proxy from information obtained from parsing.
231 <p>
232 Defaults: port = 1080.<br>
233 If user specified but not password, creates Socks4Proxy, if user
234 not specified creates Socks5Proxy, if both user and password are
235 speciefied creates Socks5Proxy with user/password authentication.
236 @param proxy_entry String in the form host[:port:user:password]
237 @return CProxy created from the string, null if entry was somehow
238 invalid(host unknown for example, or empty string)
239 */
240 public static CProxy parseProxy(String proxy_entry){
241
242 String proxy_host;
243 int proxy_port = 1080;
244 String proxy_user = null;
245 String proxy_password = null;
246 CProxy proxy;
247
248 java.util.StringTokenizer st = new java.util.StringTokenizer(
249 proxy_entry,":");
250 if(st.countTokens() < 1) return null;
251
252 proxy_host = st.nextToken();
253 if(st.hasMoreTokens())
254 try{
255 proxy_port = Integer.parseInt(st.nextToken().trim());
256 }catch(NumberFormatException nfe){}
257
258 if(st.hasMoreTokens())
259 proxy_user = st.nextToken();
260
261 if(st.hasMoreTokens())
262 proxy_password = st.nextToken();
263
264 try{
265 if(proxy_user == null)
266 proxy = new Socks5Proxy(proxy_host,proxy_port);
267 else if(proxy_password == null)
268 proxy = new Socks4Proxy(proxy_host,proxy_port,proxy_user);
269 else{
270 proxy = new Socks5Proxy(proxy_host,proxy_port);
271 UserPasswordAuthentication upa = new UserPasswordAuthentication(
272 proxy_user, proxy_password);
273
274 ((Socks5Proxy)proxy).setAuthenticationMethod(upa.METHOD_ID,upa);
275 }
276 }catch(UnknownHostException uhe){
277 return null;
278 }
279
280 return proxy;
281 }
282
283
284 //Protected Methods
285 //=================
286
287 protected void startSession()throws SocksException{
288 try{
289 if(chainProxy == null)
290 proxySocket = new Socket(proxyIP,proxyPort);
291 else if(proxyIP != null)
292 proxySocket = new SocksSocket(chainProxy,proxyIP,proxyPort);
293 else
294 proxySocket = new SocksSocket(chainProxy,proxyHost,proxyPort);
295
296 in = proxySocket.getInputStream();
297 out = proxySocket.getOutputStream();
298 }catch(SocksException se){
299 throw se;
300 }catch(IOException io_ex){
301 throw new SocksException(SOCKS_PROXY_IO_ERROR,""+io_ex);
302 }
303 }
304
305 protected abstract CProxy copy();
306 protected abstract ProxyMessage formMessage(int cmd,InetAddress ip,int port);
307 protected abstract ProxyMessage formMessage(int cmd,String host,int port)
308 throws UnknownHostException;
309 protected abstract ProxyMessage formMessage(InputStream in)
310 throws SocksException,
311 IOException;
312
313
314 protected ProxyMessage connect(InetAddress ip,int port)
315 throws SocksException{
316 try{
317 startSession();
318 ProxyMessage request = formMessage(SOCKS_CMD_CONNECT,
319 ip,port);
320 return exchange(request);
321 }catch(SocksException se){
322 endSession();
323 throw se;
324 }
325 }
326 protected ProxyMessage connect(String host,int port)
327 throws UnknownHostException,SocksException{
328 try{
329 startSession();
330 ProxyMessage request = formMessage(SOCKS_CMD_CONNECT,
331 host,port);
332 return exchange(request);
333 }catch(SocksException se){
334 endSession();
335 throw se;
336 }
337 }
338
339 protected ProxyMessage bind(InetAddress ip,int port)
340 throws SocksException{
341 try{
342 startSession();
343 ProxyMessage request = formMessage(SOCKS_CMD_BIND,
344 ip,port);
345 return exchange(request);
346 }catch(SocksException se){
347 endSession();
348 throw se;
349 }
350 }
351 protected ProxyMessage bind(String host,int port)
352 throws UnknownHostException,SocksException{
353 try{
354 startSession();
355 ProxyMessage request = formMessage(SOCKS_CMD_BIND,
356 host,port);
357 return exchange(request);
358 }catch(SocksException se){
359 endSession();
360 throw se;
361 }
362 }
363
364 protected ProxyMessage accept()
365 throws IOException,SocksException{
366 ProxyMessage msg;
367 try{
368 msg = formMessage(in);
369 }catch(InterruptedIOException iioe){
370 throw iioe;
371 }catch(IOException io_ex){
372 endSession();
373 throw new SocksException(SOCKS_PROXY_IO_ERROR,"While Trying accept:"
374 +io_ex);
375 }
376 return msg;
377 }
378
379 protected ProxyMessage udpAssociate(InetAddress ip,int port)
380 throws SocksException{
381 try{
382 startSession();
383 ProxyMessage request = formMessage(SOCKS_CMD_UDP_ASSOCIATE,
384 ip,port);
385 if(request != null)
386 return exchange(request);
387 }catch(SocksException se){
388 endSession();
389 throw se;
390 }
391 //Only get here if request was null
392 endSession();
393 throw new SocksException(SOCKS_METHOD_NOTSUPPORTED,
394 "This version of proxy does not support UDP associate, use version 5");
395 }
396 protected ProxyMessage udpAssociate(String host,int port)
397 throws UnknownHostException,SocksException{
398 try{
399 startSession();
400 ProxyMessage request = formMessage(SOCKS_CMD_UDP_ASSOCIATE,
401 host,port);
402 if(request != null) return exchange(request);
403 }catch(SocksException se){
404 endSession();
405 throw se;
406 }
407 //Only get here if request was null
408 endSession();
409 throw new SocksException(SOCKS_METHOD_NOTSUPPORTED,
410 "This version of proxy does not support UDP associate, use version 5");
411 }
412
413
414 protected void endSession(){
415 try{
416 if(proxySocket!=null) proxySocket.close();
417 proxySocket = null;
418 }catch(IOException io_ex){
419 }
420 }
421
422 /**
423 *Sends the request to SOCKS server
424 */
425 protected void sendMsg(ProxyMessage msg)throws SocksException,
426 IOException{
427 msg.write(out);
428 }
429
430 /**
431 * Reads the reply from the SOCKS server
432 */
433 protected ProxyMessage readMsg()throws SocksException,
434 IOException{
435 return formMessage(in);
436 }
437 /**
438 *Sends the request reads reply and returns it
439 *throws exception if something wrong with IO
440 *or the reply code is not zero
441 */
442 protected ProxyMessage exchange(ProxyMessage request)
443 throws SocksException{
444 ProxyMessage reply;
445 try{
446 request.write(out);
447 reply = formMessage(in);
448 }catch(SocksException s_ex){
449 throw s_ex;
450 }catch(IOException ioe){
451 throw(new SocksException(SOCKS_PROXY_IO_ERROR,""+ioe));
452 }
453 return reply;
454 }
455
456
457 //Private methods
458 //===============
459
460
461 //Constants
462
463 public static final int SOCKS_SUCCESS =0;
464 public static final int SOCKS_FAILURE =1;
465 public static final int SOCKS_BADCONNECT =2;
466 public static final int SOCKS_BADNETWORK =3;
467 public static final int SOCKS_HOST_UNREACHABLE =4;
468 public static final int SOCKS_CONNECTION_REFUSED =5;
469 public static final int SOCKS_TTL_EXPIRE =6;
470 public static final int SOCKS_CMD_NOT_SUPPORTED =7;
471 public static final int SOCKS_ADDR_NOT_SUPPORTED =8;
472
473 public static final int SOCKS_NO_PROXY =1<<16;
474 public static final int SOCKS_PROXY_NO_CONNECT =2<<16;
475 public static final int SOCKS_PROXY_IO_ERROR =3<<16;
476 public static final int SOCKS_AUTH_NOT_SUPPORTED =4<<16;
477 public static final int SOCKS_AUTH_FAILURE =5<<16;
478 public static final int SOCKS_JUST_ERROR =6<<16;
479
480 public static final int SOCKS_DIRECT_FAILED =7<<16;
481 public static final int SOCKS_METHOD_NOTSUPPORTED =8<<16;
482
483
484 public static final int SOCKS_CMD_CONNECT =0x1;
485 static final int SOCKS_CMD_BIND =0x2;
486 static final int SOCKS_CMD_UDP_ASSOCIATE =0x3;
487
488 }