|
@@ -30,84 +30,6 @@ private class SocketInput extends haxe.io.Input {
|
|
|
|
|
|
}
|
|
}
|
|
|
|
|
|
-#if flash
|
|
|
|
-private class FlashSocketOutput extends SocketOutput {
|
|
|
|
- var s : flash.net.Socket;
|
|
|
|
- var autoFlush = true;
|
|
|
|
-
|
|
|
|
- public function new(s) {
|
|
|
|
- super();
|
|
|
|
- this.s = s;
|
|
|
|
- s.endian = flash.utils.Endian.LITTLE_ENDIAN;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- inline function f() if( autoFlush ) s.flush();
|
|
|
|
-
|
|
|
|
- override function wait() {
|
|
|
|
- autoFlush = false;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- override function flush() {
|
|
|
|
- autoFlush = true;
|
|
|
|
- s.flush();
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- override function writeByte( c : Int ) {
|
|
|
|
- s.writeByte(c);
|
|
|
|
- f();
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- override function writeBytes( b : haxe.io.Bytes, pos : Int, len : Int ) : Int {
|
|
|
|
- if( len > 0 ) {
|
|
|
|
- s.writeBytes(b.getData(), pos, len);
|
|
|
|
- f();
|
|
|
|
- }
|
|
|
|
- return len;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- override function writeInt32( i : Int ) {
|
|
|
|
- s.writeInt(i);
|
|
|
|
- f();
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- override function writeString( str : String ) {
|
|
|
|
- s.writeUTFBytes(str);
|
|
|
|
- f();
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
-}
|
|
|
|
-
|
|
|
|
-private class FlashSocketInput extends SocketInput {
|
|
|
|
-
|
|
|
|
- var sock : flash.net.Socket;
|
|
|
|
-
|
|
|
|
- public function new(s) {
|
|
|
|
- sock = s;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- override function get_available() {
|
|
|
|
- return sock.bytesAvailable;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- override function readBytes( bytes : haxe.io.Bytes, pos : Int, len : Int ) {
|
|
|
|
- if( len > (sock.bytesAvailable : Int) ) {
|
|
|
|
- len = sock.bytesAvailable;
|
|
|
|
- if( len == 0 ) throw new haxe.io.Eof();
|
|
|
|
- }
|
|
|
|
- if( len > 0 )
|
|
|
|
- sock.readBytes(bytes.getData(), pos, len);
|
|
|
|
- return len;
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
- override function readByte() {
|
|
|
|
- if( sock.bytesAvailable == 0 )
|
|
|
|
- throw new haxe.io.Eof();
|
|
|
|
- return sock.readUnsignedByte();
|
|
|
|
- }
|
|
|
|
-
|
|
|
|
-}
|
|
|
|
-#end
|
|
|
|
-
|
|
|
|
class Socket {
|
|
class Socket {
|
|
|
|
|
|
static var openedSocks = [];
|
|
static var openedSocks = [];
|
|
@@ -117,12 +39,16 @@ class Socket {
|
|
#if (flash && air3)
|
|
#if (flash && air3)
|
|
var serv : flash.net.ServerSocket;
|
|
var serv : flash.net.ServerSocket;
|
|
#end
|
|
#end
|
|
|
|
+ #if hl
|
|
|
|
+ var s : hl.uv.Stream;
|
|
|
|
+ #end
|
|
public var out(default, null) : SocketOutput;
|
|
public var out(default, null) : SocketOutput;
|
|
public var input(default, null) : SocketInput;
|
|
public var input(default, null) : SocketInput;
|
|
public var timeout(default, set) : Null<Float>;
|
|
public var timeout(default, set) : Null<Float>;
|
|
|
|
|
|
public function new() {
|
|
public function new() {
|
|
out = new SocketOutput();
|
|
out = new SocketOutput();
|
|
|
|
+ hl.uv.Loop.register();
|
|
}
|
|
}
|
|
|
|
|
|
public function set_timeout(t:Null<Float>) {
|
|
public function set_timeout(t:Null<Float>) {
|
|
@@ -145,13 +71,26 @@ class Socket {
|
|
});
|
|
});
|
|
bindEvents();
|
|
bindEvents();
|
|
s.connect(host, port);
|
|
s.connect(host, port);
|
|
|
|
+ #elseif hl
|
|
|
|
+ var tcp = new hl.uv.Tcp();
|
|
|
|
+ s = tcp;
|
|
|
|
+ tcp.connect(new sys.net.Host(host), port, function(b) {
|
|
|
|
+ if( !b ) {
|
|
|
|
+ close();
|
|
|
|
+ onError("Failed to connect");
|
|
|
|
+ return;
|
|
|
|
+ }
|
|
|
|
+ out = new HLSocketOutput(this);
|
|
|
|
+ input = new HLSocketInput(this);
|
|
|
|
+ onConnect();
|
|
|
|
+ });
|
|
#else
|
|
#else
|
|
throw "Not implemented";
|
|
throw "Not implemented";
|
|
#end
|
|
#end
|
|
}
|
|
}
|
|
|
|
|
|
|
|
+ #if flash
|
|
function bindEvents() {
|
|
function bindEvents() {
|
|
- #if flash
|
|
|
|
s.addEventListener(flash.events.IOErrorEvent.IO_ERROR, function(e:flash.events.IOErrorEvent) {
|
|
s.addEventListener(flash.events.IOErrorEvent.IO_ERROR, function(e:flash.events.IOErrorEvent) {
|
|
close();
|
|
close();
|
|
onError(e.text);
|
|
onError(e.text);
|
|
@@ -163,8 +102,8 @@ class Socket {
|
|
s.addEventListener(flash.events.ProgressEvent.SOCKET_DATA, function(e:flash.events.ProgressEvent) {
|
|
s.addEventListener(flash.events.ProgressEvent.SOCKET_DATA, function(e:flash.events.ProgressEvent) {
|
|
onData();
|
|
onData();
|
|
});
|
|
});
|
|
- #end
|
|
|
|
}
|
|
}
|
|
|
|
+ #end
|
|
|
|
|
|
public static inline var ALLOW_BIND = #if (flash && air3) true #else false #end;
|
|
public static inline var ALLOW_BIND = #if (flash && air3) true #else false #end;
|
|
|
|
|
|
@@ -188,6 +127,24 @@ class Socket {
|
|
openedSocks.push(s);
|
|
openedSocks.push(s);
|
|
onConnect(s);
|
|
onConnect(s);
|
|
});
|
|
});
|
|
|
|
+ #elseif hl
|
|
|
|
+ var tcp = new hl.uv.Tcp();
|
|
|
|
+ s = tcp;
|
|
|
|
+ try {
|
|
|
|
+ tcp.bind(new sys.net.Host(host), port);
|
|
|
|
+ tcp.listen(10, function() {
|
|
|
|
+ var sock = tcp.accept();
|
|
|
|
+ var s = new Socket();
|
|
|
|
+ s.s = sock;
|
|
|
|
+ s.out = new HLSocketOutput(s);
|
|
|
|
+ s.input = new HLSocketInput(s);
|
|
|
|
+ openedSocks.push(s);
|
|
|
|
+ onConnect(s);
|
|
|
|
+ });
|
|
|
|
+ } catch( e : Dynamic ) {
|
|
|
|
+ close();
|
|
|
|
+ throw e;
|
|
|
|
+ }
|
|
#else
|
|
#else
|
|
throw "Not implemented";
|
|
throw "Not implemented";
|
|
#end
|
|
#end
|
|
@@ -201,14 +158,12 @@ class Socket {
|
|
serv = null;
|
|
serv = null;
|
|
}
|
|
}
|
|
#end
|
|
#end
|
|
- #if flash
|
|
|
|
|
|
+ #if (flash || hl)
|
|
if( s != null ) {
|
|
if( s != null ) {
|
|
try s.close() catch( e : Dynamic ) { };
|
|
try s.close() catch( e : Dynamic ) { };
|
|
out = new SocketOutput();
|
|
out = new SocketOutput();
|
|
s = null;
|
|
s = null;
|
|
}
|
|
}
|
|
- #else
|
|
|
|
- throw "Not implemented";
|
|
|
|
#end
|
|
#end
|
|
}
|
|
}
|
|
|
|
|
|
@@ -219,4 +174,182 @@ class Socket {
|
|
public dynamic function onData() {
|
|
public dynamic function onData() {
|
|
}
|
|
}
|
|
|
|
|
|
-}
|
|
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+
|
|
|
|
+#if flash
|
|
|
|
+private class FlashSocketOutput extends SocketOutput {
|
|
|
|
+ var s : flash.net.Socket;
|
|
|
|
+ var autoFlush = true;
|
|
|
|
+
|
|
|
|
+ public function new(s) {
|
|
|
|
+ super();
|
|
|
|
+ this.s = s;
|
|
|
|
+ s.endian = flash.utils.Endian.LITTLE_ENDIAN;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ inline function f() if( autoFlush ) s.flush();
|
|
|
|
+
|
|
|
|
+ override function wait() {
|
|
|
|
+ autoFlush = false;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ override function flush() {
|
|
|
|
+ autoFlush = true;
|
|
|
|
+ s.flush();
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ override function writeByte( c : Int ) {
|
|
|
|
+ s.writeByte(c);
|
|
|
|
+ f();
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ override function writeBytes( b : haxe.io.Bytes, pos : Int, len : Int ) : Int {
|
|
|
|
+ if( len > 0 ) {
|
|
|
|
+ s.writeBytes(b.getData(), pos, len);
|
|
|
|
+ f();
|
|
|
|
+ }
|
|
|
|
+ return len;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ override function writeInt32( i : Int ) {
|
|
|
|
+ s.writeInt(i);
|
|
|
|
+ f();
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ override function writeString( str : String ) {
|
|
|
|
+ s.writeUTFBytes(str);
|
|
|
|
+ f();
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+private class FlashSocketInput extends SocketInput {
|
|
|
|
+
|
|
|
|
+ var sock : flash.net.Socket;
|
|
|
|
+
|
|
|
|
+ public function new(s) {
|
|
|
|
+ sock = s;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ override function get_available() {
|
|
|
|
+ return sock.bytesAvailable;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ override function readBytes( bytes : haxe.io.Bytes, pos : Int, len : Int ) {
|
|
|
|
+ if( len > (sock.bytesAvailable : Int) ) {
|
|
|
|
+ len = sock.bytesAvailable;
|
|
|
|
+ if( len == 0 ) throw new haxe.io.Eof();
|
|
|
|
+ }
|
|
|
|
+ if( len > 0 )
|
|
|
|
+ sock.readBytes(bytes.getData(), pos, len);
|
|
|
|
+ return len;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ override function readByte() {
|
|
|
|
+ if( sock.bytesAvailable == 0 )
|
|
|
|
+ throw new haxe.io.Eof();
|
|
|
|
+ return sock.readUnsignedByte();
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+#elseif hl
|
|
|
|
+
|
|
|
|
+class HLSocketOutput extends SocketOutput {
|
|
|
|
+
|
|
|
|
+ var tmpBuf : haxe.io.Bytes;
|
|
|
|
+ var s : Socket;
|
|
|
|
+ var onWriteResult : Bool -> Void;
|
|
|
|
+
|
|
|
|
+ public function new(s) {
|
|
|
|
+ super();
|
|
|
|
+ this.s = s;
|
|
|
|
+ onWriteResult = writeResult;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ function writeResult(b) {
|
|
|
|
+ if( !b ) {
|
|
|
|
+ s.close();
|
|
|
|
+ s.onError("Failed to write data");
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ override function writeByte(c:Int) {
|
|
|
|
+ if( tmpBuf == null )
|
|
|
|
+ tmpBuf = haxe.io.Bytes.alloc(1);
|
|
|
|
+ tmpBuf.set(0, c);
|
|
|
|
+ @:privateAccess s.s.write(tmpBuf, onWriteResult);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ override function writeBytes(buf:haxe.io.Bytes, pos:Int, len:Int):Int {
|
|
|
|
+ @:privateAccess s.s.write(buf, onWriteResult, pos, len);
|
|
|
|
+ return len;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+class HLSocketInput extends SocketInput {
|
|
|
|
+
|
|
|
|
+ var s : Socket;
|
|
|
|
+ var data : hl.Bytes;
|
|
|
|
+ var pos : Int;
|
|
|
|
+ var len : Int;
|
|
|
|
+ var size : Int;
|
|
|
|
+
|
|
|
|
+ public function new(sock) {
|
|
|
|
+ this.s = sock;
|
|
|
|
+ @:privateAccess s.s.readStartRaw(onData);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ function onData(recvData:hl.Bytes, recv:Int) {
|
|
|
|
+ if( recv < 0 ) {
|
|
|
|
+ s.close();
|
|
|
|
+ s.onError("Connection closed");
|
|
|
|
+ return;
|
|
|
|
+ }
|
|
|
|
+ //trace(">" + recvData.toBytes(recv).toHex());
|
|
|
|
+ var req = pos + len + recv;
|
|
|
|
+ if( req > size && pos >= (size >> 1) ) {
|
|
|
|
+ data.blit(0, data, pos, len);
|
|
|
|
+ pos = 0;
|
|
|
|
+ req -= pos;
|
|
|
|
+ }
|
|
|
|
+ if( req > size ) {
|
|
|
|
+ var nsize = size == 0 ? 1024 : size;
|
|
|
|
+ while( nsize < req ) nsize = (nsize * 3) >> 1;
|
|
|
|
+ var ndata = new hl.Bytes(nsize);
|
|
|
|
+ ndata.blit(0, data, pos, len);
|
|
|
|
+ data = ndata;
|
|
|
|
+ size = nsize;
|
|
|
|
+ pos = 0;
|
|
|
|
+ }
|
|
|
|
+ data.blit(pos + len, recvData, 0, recv);
|
|
|
|
+ len += recv;
|
|
|
|
+ s.onData();
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ override function get_available() {
|
|
|
|
+ return len;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ override function readByte():Int {
|
|
|
|
+ if( len == 0 ) throw new haxe.io.Eof();
|
|
|
|
+ var c = data[pos++];
|
|
|
|
+ len--;
|
|
|
|
+ return c;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ override function readBytes(s:haxe.io.Bytes, pos:Int, len:Int):Int {
|
|
|
|
+ if( pos < 0 || len < 0 || pos + len > s.length ) throw haxe.io.Error.OutsideBounds;
|
|
|
|
+ var max = len < this.len ? len : this.len;
|
|
|
|
+ @:privateAccess s.b.blit(pos, data, pos, max);
|
|
|
|
+ //trace("<" + s.sub(pos,len).toHex());
|
|
|
|
+ pos += max;
|
|
|
|
+ len -= max;
|
|
|
|
+ return max;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+#end
|