1 package be
.nikiroo
.utils
.serial
;
3 import java
.io
.IOException
;
4 import java
.net
.ServerSocket
;
5 import java
.net
.Socket
;
6 import java
.util
.ArrayList
;
9 import javax
.net
.ssl
.SSLServerSocket
;
10 import javax
.net
.ssl
.SSLServerSocketFactory
;
11 import javax
.net
.ssl
.SSLSocket
;
12 import javax
.net
.ssl
.SSLSocketFactory
;
14 import be
.nikiroo
.utils
.Version
;
16 abstract public class Server
implements Runnable
{
17 static private final String
[] ANON_CIPHERS
= getAnonCiphers();
21 private ServerSocket ss
;
22 private boolean started
;
23 private boolean exiting
= false;
25 private Object lock
= new Object();
26 private Object counterLock
= new Object();
29 public Server(@SuppressWarnings("unused") Version notUsed
, int port
,
30 boolean ssl
) throws IOException
{
34 public Server(int port
, boolean ssl
) throws IOException
{
37 this.ss
= createSocketServer(port
, ssl
);
44 new Thread(this).start();
53 // wait = wait before returning (sync VS async) timeout in ms, 0 or -1 for
55 public void stop(final long timeout
, final boolean wait
) {
59 new Thread(new Runnable() {
68 // timeout in ms, 0 or -1 or never
69 private void stop(long timeout
) {
71 if (started
&& !exiting
) {
75 new ConnectActionClient(createSocket(null, port
, ssl
)) {
77 public void action(Version serverVersion
)
83 while (ss
!= null && timeout
> 0 && timeout
> time
) {
87 } catch (Exception e
) {
89 counter
= 0; // will stop the main thread
95 // only return when stopped
96 while (started
|| exiting
) {
99 } catch (InterruptedException e
) {
108 while (started
&& !exiting
) {
110 Socket s
= ss
.accept();
111 new ConnectActionServer(s
) {
112 private Version clientVersion
= new Version();
115 public void action(Version dummy
) throws Exception
{
117 for (Object data
= flush(); true; data
= flush()) {
120 rep
= onRequest(this, clientVersion
, data
);
121 } catch (Exception e
) {
126 } catch (NullPointerException e
) {
127 // Client has no data any more, we quit
132 public void connect() {
141 protected void onClientVersionReceived(Version clientVersion
) {
142 this.clientVersion
= clientVersion
;
147 // Will be covered by @link{Server#stop(long)} for timeouts
148 while (counter
> 0) {
151 } catch (Exception e
) {
158 } catch (Exception e
) {
170 abstract protected Object
onRequest(ConnectActionServer action
,
171 Version clientVersion
, Object data
) throws Exception
;
173 protected void onError(Exception e
) {
175 e
= new Exception("Unknown error");
181 private int count(int change
) {
182 synchronized (counterLock
) {
188 static Socket
createSocket(String host
, int port
, boolean ssl
)
192 s
= SSLSocketFactory
.getDefault().createSocket(host
, port
);
193 ((SSLSocket
) s
).setEnabledCipherSuites(ANON_CIPHERS
);
195 s
= new Socket(host
, port
);
201 static ServerSocket
createSocketServer(int port
, boolean ssl
)
205 ss
= SSLServerSocketFactory
.getDefault().createServerSocket(port
);
206 ((SSLServerSocket
) ss
).setEnabledCipherSuites(ANON_CIPHERS
);
208 ss
= new ServerSocket(port
);
214 private static String
[] getAnonCiphers() {
215 List
<String
> anonCiphers
= new ArrayList
<String
>();
216 for (String cipher
: ((SSLSocketFactory
) SSLSocketFactory
.getDefault())
217 .getSupportedCipherSuites()) {
218 if (cipher
.contains("_anon_")) {
219 anonCiphers
.add(cipher
);
223 return anonCiphers
.toArray(new String
[] {});