can i start actually making the game pls
thank youi
This commit is contained in:
parent
80a732a371
commit
ebe6fff43f
4 changed files with 91 additions and 48 deletions
|
@ -27,7 +27,7 @@ namespace Kneesocks {
|
||||||
|
|
||||||
ReadBuffer Buffer;
|
ReadBuffer Buffer;
|
||||||
private byte[] FirstTwoBytes = null;
|
private byte[] FirstTwoBytes = null;
|
||||||
private int ExtraHeaderSize = 2;
|
private int ExtraHeaderSize = 0;
|
||||||
private byte[] FrameHeader = null;
|
private byte[] FrameHeader = null;
|
||||||
private List<Frame> FrameBuffer = new List<Frame>();
|
private List<Frame> FrameBuffer = new List<Frame>();
|
||||||
|
|
||||||
|
@ -68,7 +68,22 @@ namespace Kneesocks {
|
||||||
ClientHandshake = conn.ClientHandshake;
|
ClientHandshake = conn.ClientHandshake;
|
||||||
}
|
}
|
||||||
|
|
||||||
public byte[] Parse() {
|
public void ReadIfNotNull(ref byte[] buffer, int length) {
|
||||||
|
buffer = buffer == null ? Buffer.AttemptRead(length)
|
||||||
|
: buffer;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void ReadIfNotNull(ref byte[] buffer, string terminator) {
|
||||||
|
buffer = buffer == null ? Buffer.AttemptRead(terminator)
|
||||||
|
: buffer;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Parse() {
|
||||||
|
if(!Stream.CanRead) {
|
||||||
|
Disconnected = true;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
byte[] readBuffer = null;
|
byte[] readBuffer = null;
|
||||||
if(Buffer.IsReading) {
|
if(Buffer.IsReading) {
|
||||||
readBuffer = Buffer.AttemptRead();
|
readBuffer = Buffer.AttemptRead();
|
||||||
|
@ -76,16 +91,14 @@ namespace Kneesocks {
|
||||||
if(Buffer.ElapsedReadTime.Seconds > (Handshaked ? 300 : 30))
|
if(Buffer.ElapsedReadTime.Seconds > (Handshaked ? 300 : 30))
|
||||||
Disconnect(Frame.kClosingReason.ProtocolError, "Timed out waiting for a full response");
|
Disconnect(Frame.kClosingReason.ProtocolError, "Timed out waiting for a full response");
|
||||||
|
|
||||||
return null;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!Handshaked) {
|
if(!Handshaked) {
|
||||||
if(readBuffer == null) {
|
ReadIfNotNull(ref readBuffer, "\r\n\r\n");
|
||||||
readBuffer = Buffer.AttemptRead("\r\n\r\n");
|
if(readBuffer == null)
|
||||||
if(readBuffer == null)
|
return;
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
try {
|
try {
|
||||||
Handshake request = new Handshake(Encoding.ASCII.GetString(readBuffer));
|
Handshake request = new Handshake(Encoding.ASCII.GetString(readBuffer));
|
||||||
|
@ -95,24 +108,23 @@ namespace Kneesocks {
|
||||||
Handshaked = true;
|
Handshaked = true;
|
||||||
} catch(Exception e) {
|
} catch(Exception e) {
|
||||||
Disconnect(Frame.kClosingReason.ProtocolError, e.Message);
|
Disconnect(Frame.kClosingReason.ProtocolError, e.Message);
|
||||||
return null;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
OnOpen();
|
OnOpen();
|
||||||
return null;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
OnParse();
|
OnParse();
|
||||||
|
|
||||||
if(FirstTwoBytes == null) {
|
if(FirstTwoBytes == null) {
|
||||||
if(readBuffer == null) {
|
ReadIfNotNull(ref readBuffer, 2);
|
||||||
readBuffer = Buffer.AttemptRead(2);
|
if(readBuffer == null)
|
||||||
if(readBuffer == null)
|
return;
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
FirstTwoBytes = readBuffer;
|
FirstTwoBytes = readBuffer;
|
||||||
ExtraHeaderSize = Frame.HeaderSizeFromBytes(FirstTwoBytes) - 2;
|
ExtraHeaderSize = Frame.HeaderLengthFromBytes(FirstTwoBytes) - 2;
|
||||||
|
|
||||||
readBuffer = null;
|
readBuffer = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -120,11 +132,9 @@ namespace Kneesocks {
|
||||||
if(ExtraHeaderSize == 0)
|
if(ExtraHeaderSize == 0)
|
||||||
FrameHeader = FirstTwoBytes;
|
FrameHeader = FirstTwoBytes;
|
||||||
else {
|
else {
|
||||||
if(readBuffer == null) {
|
ReadIfNotNull(ref readBuffer, ExtraHeaderSize);
|
||||||
readBuffer = Buffer.AttemptRead(ExtraHeaderSize);
|
if(readBuffer == null)
|
||||||
if(readBuffer == null)
|
return;
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
FrameHeader = FirstTwoBytes.Concat(readBuffer).ToArray();
|
FrameHeader = FirstTwoBytes.Concat(readBuffer).ToArray();
|
||||||
}
|
}
|
||||||
|
@ -133,18 +143,44 @@ namespace Kneesocks {
|
||||||
}
|
}
|
||||||
|
|
||||||
if(FrameHeader != null) {
|
if(FrameHeader != null) {
|
||||||
var check = Frame.HeaderFromBytes()
|
Frame tempFrame;
|
||||||
|
|
||||||
if()
|
if(readBuffer == null) {
|
||||||
|
try {
|
||||||
|
tempFrame = Frame.HeaderFromBytes(FrameHeader);
|
||||||
|
} catch(Exception e) {
|
||||||
|
Disconnect(Frame.kClosingReason.ProtocolError, e.Message);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
readBuffer = Buffer.AttemptRead(tempFrame.BodyLength);
|
||||||
|
if(readBuffer == null)
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
tempFrame = Frame.FromBytes(FrameHeader.Concat(readBuffer).ToArray());
|
||||||
|
} catch(Exception e) {
|
||||||
|
Disconnect(Frame.kClosingReason.ProtocolError, e.Message);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
FrameBuffer.Add(tempFrame);
|
||||||
|
FirstTwoBytes = null;
|
||||||
|
ExtraHeaderSize = 0;
|
||||||
|
FrameHeader = null;
|
||||||
|
|
||||||
|
if(tempFrame.IsFinal) {
|
||||||
|
byte[] byteBuffer = new byte[0];
|
||||||
|
foreach(var frame in FrameBuffer)
|
||||||
|
byteBuffer = byteBuffer.Concat(frame.Content).ToArray();
|
||||||
|
|
||||||
|
FrameBuffer = new List<Frame>();
|
||||||
|
OnReceive(byteBuffer);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*if(!Buffer.IsReading) {
|
return;
|
||||||
readBuffer = Buffer.AttemptRead("\r\n\r\n");
|
|
||||||
if(readBuffer == null)
|
|
||||||
return null;
|
|
||||||
}*/
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public void Disconnect(string reason = null) {
|
public void Disconnect(string reason = null) {
|
||||||
|
|
|
@ -41,7 +41,7 @@ namespace Kneesocks {
|
||||||
|
|
||||||
int length = 2
|
int length = 2
|
||||||
+ (BodyLength >= 0x7E && BodyLength <= 0xFFFF ? 2 : 0)
|
+ (BodyLength >= 0x7E && BodyLength <= 0xFFFF ? 2 : 0)
|
||||||
+ (BodyLength > 0xFFFF ? 4 : 0)
|
+ (BodyLength > 0xFFFF ? 8 : 0)
|
||||||
+ (IsMasked ? 4 : 0);
|
+ (IsMasked ? 4 : 0);
|
||||||
|
|
||||||
return (_HeaderLength = length);
|
return (_HeaderLength = length);
|
||||||
|
@ -99,7 +99,7 @@ namespace Kneesocks {
|
||||||
return returnValue;
|
return returnValue;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static int HeaderSizeFromBytes(byte[] raw) {
|
public static int HeaderLengthFromBytes(byte[] raw) {
|
||||||
if(raw.Length < 2)
|
if(raw.Length < 2)
|
||||||
throw new FormatException("Need first two bytes to analyze");
|
throw new FormatException("Need first two bytes to analyze");
|
||||||
|
|
||||||
|
@ -107,7 +107,7 @@ namespace Kneesocks {
|
||||||
return 2
|
return 2
|
||||||
+ ((raw[1] & 0x80) != 0 ? 4: 0)
|
+ ((raw[1] & 0x80) != 0 ? 4: 0)
|
||||||
+ (lengthByte == 0x7E ? 2 : 0)
|
+ (lengthByte == 0x7E ? 2 : 0)
|
||||||
+ (lengthByte == 0x7F ? 4 : 0);
|
+ (lengthByte == 0x7F ? 8 : 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Frame HeaderFromBytes(byte[] raw) {
|
public static Frame HeaderFromBytes(byte[] raw) {
|
||||||
|
@ -131,12 +131,12 @@ namespace Kneesocks {
|
||||||
? 1
|
? 1
|
||||||
: (bodyLength == 0x7E ? 3 : 9);
|
: (bodyLength == 0x7E ? 3 : 9);
|
||||||
|
|
||||||
if(raw.Length < headerOffset + 1)
|
if(raw.Length < headerOffset + 1 + (returnFrame.IsMasked ? 4 : 0))
|
||||||
throw new FormatException("Websocket frame is smaller than expected header size");
|
throw new FormatException("Websocket frame is smaller than expected header size");
|
||||||
|
|
||||||
bodyLength = bodyLength < 0x7E ? 0 : bodyLength;
|
if(bodyLength >= 0x7E)
|
||||||
for(var i = headerOffset - 1; i > 0; --i)
|
bodyLength = bodyLength == 0x7E ? raw.Subset(2, 2).UnpackUInt16()
|
||||||
bodyLength |= (ulong)raw[2 + i] << (8 * (headerOffset - 1 - i));
|
: raw.Subset(2, 8).UnpackUInt64();
|
||||||
|
|
||||||
if(bodyLength > Int32.MaxValue)
|
if(bodyLength > Int32.MaxValue)
|
||||||
throw new FormatException("Frame is too large to interpret");
|
throw new FormatException("Frame is too large to interpret");
|
||||||
|
@ -153,7 +153,7 @@ namespace Kneesocks {
|
||||||
var returnFrame = HeaderFromBytes(raw);
|
var returnFrame = HeaderFromBytes(raw);
|
||||||
|
|
||||||
uint expectedFrameLength = (uint)returnFrame.BodyLength + (uint)returnFrame.HeaderLength;
|
uint expectedFrameLength = (uint)returnFrame.BodyLength + (uint)returnFrame.HeaderLength;
|
||||||
if(expectedFrameLength < (uint)raw.Length)
|
if((uint)raw.Length < expectedFrameLength)
|
||||||
throw new FormatException("Raw frame length ("+ (uint)raw.Length + ") is less than described size ("+ expectedFrameLength + ")");
|
throw new FormatException("Raw frame length ("+ (uint)raw.Length + ") is less than described size ("+ expectedFrameLength + ")");
|
||||||
|
|
||||||
returnFrame.Content = new byte[returnFrame.BodyLength];
|
returnFrame.Content = new byte[returnFrame.BodyLength];
|
||||||
|
|
|
@ -7,6 +7,8 @@ using System.Threading.Tasks;
|
||||||
|
|
||||||
namespace Kneesocks {
|
namespace Kneesocks {
|
||||||
class ReadBuffer {
|
class ReadBuffer {
|
||||||
|
private const int BufferSize = 1024;
|
||||||
|
|
||||||
private List<byte> Buffer;
|
private List<byte> Buffer;
|
||||||
private int ExpectedLength;
|
private int ExpectedLength;
|
||||||
private string ExpectedString;
|
private string ExpectedString;
|
||||||
|
@ -52,21 +54,21 @@ namespace Kneesocks {
|
||||||
if(!IsReading)
|
if(!IsReading)
|
||||||
return null;
|
return null;
|
||||||
|
|
||||||
|
if(!Source.CanRead)
|
||||||
|
return null;
|
||||||
|
|
||||||
byte[] returnValue;
|
byte[] returnValue;
|
||||||
if((returnValue = CheckBuffer()) != null)
|
if((returnValue = CheckBuffer()) != null)
|
||||||
return returnValue;
|
return returnValue;
|
||||||
|
|
||||||
var buffer = new byte[1024];
|
var buffer = new byte[BufferSize];
|
||||||
while(Source.DataAvailable) {
|
while(Source.DataAvailable) {
|
||||||
var readAmount = ExpectedString == null
|
var readAmount = ExpectedString == null
|
||||||
? Math.Min(1024, ExpectedLength - Buffer.Count)
|
? Math.Min(BufferSize, ExpectedLength - Buffer.Count)
|
||||||
: 1024;
|
: BufferSize;
|
||||||
|
|
||||||
var bytesRead = Source.Read(buffer, 0, readAmount);
|
var bytesRead = Source.Read(buffer, 0, readAmount);
|
||||||
if(bytesRead == readAmount)
|
Buffer.AddRange(bytesRead == BufferSize ? buffer : buffer.Take(bytesRead));
|
||||||
Buffer.AddRange(buffer);
|
|
||||||
else
|
|
||||||
Buffer.AddRange(buffer.Take(readAmount));
|
|
||||||
|
|
||||||
if((returnValue = CheckBuffer()) != null)
|
if((returnValue = CheckBuffer()) != null)
|
||||||
return returnValue;
|
return returnValue;
|
||||||
|
|
|
@ -11,7 +11,6 @@ namespace Kneesocks {
|
||||||
private List<Connection> Clients = new List<Connection>();
|
private List<Connection> Clients = new List<Connection>();
|
||||||
private bool RunWithNoClients = false;
|
private bool RunWithNoClients = false;
|
||||||
private bool Running = true;
|
private bool Running = true;
|
||||||
private bool _finished = false;
|
|
||||||
|
|
||||||
public Stack(Pool<T> poolRef, Connection initialConnection = null) {
|
public Stack(Pool<T> poolRef, Connection initialConnection = null) {
|
||||||
PoolRef = poolRef;
|
PoolRef = poolRef;
|
||||||
|
@ -48,7 +47,13 @@ namespace Kneesocks {
|
||||||
while(Running && (Count > 0 || RunWithNoClients)) {
|
while(Running && (Count > 0 || RunWithNoClients)) {
|
||||||
for(var i = Count - 1; i >= 0 && Running; --i) {
|
for(var i = Count - 1; i >= 0 && Running; --i) {
|
||||||
var client = Clients[i];
|
var client = Clients[i];
|
||||||
client.Parse();
|
if(!client.Disconnected)
|
||||||
|
client.Parse();
|
||||||
|
else {
|
||||||
|
lock(Clients) {
|
||||||
|
Clients.RemoveAt(i);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue