jhg023 / simplenet Goto Github PK
View Code? Open in Web Editor NEWAn easy-to-use, event-driven, asynchronous network application framework compiled with Java 11.
License: MIT License
An easy-to-use, event-driven, asynchronous network application framework compiled with Java 11.
License: MIT License
Should allow for RSA encryption :)
Hi,
in the server/client application the server send 49678 byte (the error also occurs with smaller sizes )
In the client application:
java.lang.NegativeArraySizeException: -15858
at com.simplenet.utility.exposed.data.StringReader.lambda$processBytes$4(StringReader.java:169)
at com.simplenet.utility.exposed.data.DataReader.lambda$read$0(DataReader.java:76)
at com.simplenet.Client.lambda$readUntil$4(Client.java:529)
at com.simplenet.Client$Listener.completed(Client.java:137)
at com.simplenet.Client$Listener.completed(Client.java:83)
at java.base/sun.nio.ch.Invoker.invokeUnchecked(Invoker.java:127)
at java.base/sun.nio.ch.Invoker$2.run(Invoker.java:219)
at java.base/sun.nio.ch.AsynchronousChannelGroupImpl$1.run(AsynchronousChannelGroupImpl.java:112)
at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1130)
at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:630)
at java.base/java.lang.Thread.run(Thread.java:831)
Following the function in error:
private void processBytes(short n, Consumer consumer, Charset charset, ByteOrder order) {
int length = order == ByteOrder.LITTLE_ENDIAN ? Short.reverseBytes(n) : n;
read(Byte.BYTES * (length & 0xFFFF), buffer -> {
var b = new byte[length];
buffer.get(b);
consumer.accept(new String(b, charset));
}, order);
}
Which is the problem?
Many Thanks
I'm not sure if I understood the FAQ correctly, but it's not immediately obvious to me where the overload for setting the size of the buffer. Can you please confirm that the ability is there, and maybe give a bit of guidance on how to implement it? Thank you.
There is a problem with Encryption when there are more than 2 clients connected to the same server.
By using the below code, the first client connect to the server without any issues, and there is encryption, but second client onward throwing the below error.
FYI, I am just sending a small amount of bytes, and I am not sure where the below number (e.g. 1892643530) is coming from.
My machine has enough ram and I set "XX:MaxDirectMemorySize=4096m" but it didn't help.
java.lang.OutOfMemoryError: Cannot reserve 1892643530 bytes of direct buffer memory (allocated: 75700, limit: 536870912)
at java.base/java.nio.Bits.reserveMemory(Unknown Source)
at java.base/java.nio.DirectByteBuffer.<init>(Unknown Source)
at java.base/java.nio.ByteBuffer.allocateDirect(Unknown Source)
at com.github.pbbl.direct.DirectByteBufferPool.allocate(DirectByteBufferPool.java:39)
at com.github.pbbl.direct.DirectByteBufferPool.allocate(DirectByteBufferPool.java:35)
at com.github.pbbl.AbstractBufferPool.lambda$take$1(AbstractBufferPool.java:92)
at java.base/java.util.Optional.orElseGet(Unknown Source)
at com.github.pbbl.AbstractBufferPool.take(AbstractBufferPool.java:92)
at net.simplenet.Client$Listener.completed(Client.java:172)
at net.simplenet.Client$Listener.completed(Client.java:78)
at java.base/sun.nio.ch.Invoker.invokeUnchecked(Unknown Source)
at java.base/sun.nio.ch.Invoker.invokeDirect(Unknown Source)
at java.base/sun.nio.ch.UnixAsynchronousSocketChannelImpl.implRead(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/java.nio.channels.AsynchronousSocketChannel.read(Unknown Source)
at net.simplenet.Client$Listener.completed(Client.java:173)
at net.simplenet.Client$Listener.completed(Client.java:78)
at java.base/sun.nio.ch.Invoker.invokeUnchecked(Unknown Source)
at java.base/sun.nio.ch.Invoker.invokeDirect(Unknown Source)
at java.base/sun.nio.ch.UnixAsynchronousSocketChannelImpl.implRead(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/java.nio.channels.AsynchronousSocketChannel.read(Unknown Source)
at net.simplenet.Client$Listener.completed(Client.java:173)
at net.simplenet.Client$Listener.completed(Client.java:78)
at java.base/sun.nio.ch.Invoker.invokeUnchecked(Unknown Source)
at java.base/sun.nio.ch.Invoker.invokeDirect(Unknown Source)
at java.base/sun.nio.ch.UnixAsynchronousSocketChannelImpl.implRead(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/java.nio.channels.AsynchronousSocketChannel.read(Unknown Source)
at net.simplenet.Client$Listener.completed(Client.java:173)
at net.simplenet.Client$Listener.completed(Client.java:78)
at java.base/sun.nio.ch.Invoker.invokeUnchecked(Unknown Source)
at java.base/sun.nio.ch.Invoker.invokeDirect(Unknown Source)
at java.base/sun.nio.ch.UnixAsynchronousSocketChannelImpl.implRead(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/java.nio.channels.AsynchronousSocketChannel.read(Unknown Source)
at net.simplenet.Client$Listener.completed(Client.java:173)
at net.simplenet.Client$Listener.completed(Client.java:78)
at java.base/sun.nio.ch.Invoker.invokeUnchecked(Unknown Source)
at java.base/sun.nio.ch.Invoker.invokeDirect(Unknown Source)
at java.base/sun.nio.ch.UnixAsynchronousSocketChannelImpl.implRead(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/java.nio.channels.AsynchronousSocketChannel.read(Unknown Source)
at net.simplenet.Client$Listener.completed(Client.java:173)
at net.simplenet.Client$Listener.completed(Client.java:78)
at java.base/sun.nio.ch.Invoker.invokeUnchecked(Unknown Source)
at java.base/sun.nio.ch.Invoker.invokeDirect(Unknown Source)
at java.base/sun.nio.ch.UnixAsynchronousSocketChannelImpl.implRead(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/java.nio.channels.AsynchronousSocketChannel.read(Unknown Source)
at net.simplenet.Client$Listener.completed(Client.java:173)
at net.simplenet.Client$Listener.completed(Client.java:78)
at java.base/sun.nio.ch.Invoker.invokeUnchecked(Unknown Source)
at java.base/sun.nio.ch.Invoker.invokeDirect(Unknown Source)
at java.base/sun.nio.ch.UnixAsynchronousSocketChannelImpl.implRead(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/java.nio.channels.AsynchronousSocketChannel.read(Unknown Source)
at net.simplenet.Client$Listener.completed(Client.java:173)
at net.simplenet.Client$Listener.completed(Client.java:78)
at java.base/sun.nio.ch.Invoker.invokeUnchecked(Unknown Source)
at java.base/sun.nio.ch.Invoker.invokeDirect(Unknown Source)
at java.base/sun.nio.ch.UnixAsynchronousSocketChannelImpl.implRead(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/java.nio.channels.AsynchronousSocketChannel.read(Unknown Source)
at net.simplenet.Client$Listener.completed(Client.java:173)
at net.simplenet.Client$Listener.completed(Client.java:78)
at java.base/sun.nio.ch.Invoker.invokeUnchecked(Unknown Source)
at java.base/sun.nio.ch.Invoker.invokeDirect(Unknown Source)
at java.base/sun.nio.ch.UnixAsynchronousSocketChannelImpl.implRead(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/sun.nio.ch.AsynchronousSocketChannelImpl.read(Unknown Source)
at java.base/java.nio.channels.AsynchronousSocketChannel.read(Unknown Source)
at net.simplenet.Client$Listener.completed(Client.java:173)
at net.simplenet.Client$Listener.completed(Client.java:78)
at java.base/sun.nio.ch.Invoker.invokeUnchecked(Unknown Source)
at java.base/sun.nio.ch.Invoker$2.run(Unknown Source)
at java.base/sun.nio.ch.AsynchronousChannelGroupImpl$1.run(Unknown Source)
at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(Unknown Source)
at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(Unknown Source)
at java.base/java.lang.Thread.run(Unknown Source)
Server.java:
private Cipher[] initCiphers(String cipher) throws GeneralSecurityException {
byte[] raw = { (byte) 0xA5, (byte) 0x01, (byte) 0x7B, (byte) 0xE5,
(byte) 0x23, (byte) 0xCA, (byte) 0xD4, (byte) 0xD2,
(byte) 0x23, (byte) 0xCA, (byte) 0xD4, (byte) 0xD2,
(byte) 0x23, (byte) 0xCA, (byte) 0xD4, (byte) 0xD2,
};
var ivSpec = new IvParameterSpec(raw);
var keySpec = new SecretKeySpec(raw, "AES");
var serverEncryption = Cipher.getInstance(cipher);
var serverDecryption = Cipher.getInstance(cipher);
serverEncryption.init(Cipher.ENCRYPT_MODE, keySpec,ivSpec);
serverDecryption.init(Cipher.DECRYPT_MODE, keySpec,ivSpec);
return new Cipher[] { serverEncryption, serverDecryption };
}
public void startServer() {
var ciphers = initCiphers("AES/CFB8/NoPadding");
server.onConnect(client -> {
client.setEncryption(ciphers[0], UPDATE);
client.setDecryption(ciphers[1], UPDATE);
client.readByteAlways(opcode -> {
switch (opcode) {
..........
}
}
}
Client:
private Cipher[] initCiphers(String cipher) throws GeneralSecurityException {
byte[] raw = {(byte) 0xA5, (byte) 0x01, (byte) 0x7B, (byte) 0xE5,
(byte) 0x23, (byte) 0xCA, (byte) 0xD4, (byte) 0xD2,
(byte) 0x23, (byte) 0xCA, (byte) 0xD4, (byte) 0xD2,
(byte) 0x23, (byte) 0xCA, (byte) 0xD4, (byte) 0xD2,
};
var ivSpec = new IvParameterSpec(raw);
var keySpec = new SecretKeySpec(raw, "AES");
var clientEncryption = Cipher.getInstance(cipher);
var clientDecryption = Cipher.getInstance(cipher);
clientEncryption.init(Cipher.ENCRYPT_MODE, keySpec,ivSpec);
clientDecryption.init(Cipher.DECRYPT_MODE, keySpec,ivSpec);
return new Cipher[]{clientEncryption, clientDecryption};
}
var ciphers = initCiphers("AES/CFB8/NoPadding");
client.onConnect(() -> {
client.setEncryption(ciphers[0], UPDATE);
client.setDecryption(ciphers[1], UPDATE);
client.readByteAlways(opcode -> {
switch (opcode) {
.........
}
}
}
We have the events connection, pre-disconnection and disconnection.
Is it planned to give a user a way to add custom / more advanced types of events?
I think of events such as:
*A message / data packet with specific content received, treat it elsewhere different from everything else.
Great project! Only nitpick I have is that currently the connectListeners
is an ArrayList
. New elements are added to this list via the onConnect
method which does not specify any thread-safety guarantees.
However, adding listeners from different threads may be desirable (even after calling bind
), and this list could be changed to a CopyOnWriteArrayList
since it will rarely be mutated and will be heavily traversed.
Hi,
How can I simulate hundreds of concurrent connections?
What is the correct sequence of instructions on both client and server side?
Many Thanks
Hi,
Im wondering if this code supports a one-way client callbacks? Meaning the client connect to server. Then the server adds the client to a Map, and at some point, the server uses the client that has been added to the Map, and sends client data to it, and the client will handle the received data and print it out.
Thanks.
Stock price, weather, something to do with TODO-lists?
I am not sure how to elaborate this one. but when there is many frequent concurrent connections from both sides, server to client, and client to server. Sometimes the following error showing up.
java.lang.IllegalArgumentException: newLimit < 0: (-33395131 < 0)
at java.base/java.nio.Buffer.createLimitException(Buffer.java:388)
at java.base/java.nio.Buffer.limit(Buffer.java:362)
at java.base/java.nio.ByteBuffer.limit(ByteBuffer.java:1322)
at java.base/java.nio.MappedByteBuffer.limit(MappedByteBuffer.java:383)
at java.base/java.nio.MappedByteBuffer.limit(MappedByteBuffer.java:70)
at net.simplenet.Client$Listener.completed(Client.java:608)
at net.simplenet.Client$Listener.completed(Client.java:567)
at java.base/sun.nio.ch.Invoker.invokeUnchecked(Invoker.java:127)
at java.base/sun.nio.ch.Invoker$2.run(Invoker.java:219)
at java.base/sun.nio.ch.AsynchronousChannelGroupImpl$1.run(AsynchronousChannelGroupImpl.java:112)
at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1130)
at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:630)
at java.base/java.lang.Thread.run(Thread.java:832)
Client.Java:608
while (buffer.remaining() >= (key = peek.getKey())) {
var wrappedBuffer = buffer.duplicate().mark().limit(buffer.position() + key); //Line 608 is here
if (shouldDecrypt) {
try {
wrappedBuffer = client.decryptionFunction.apply(client.decryptionCipher, wrappedBuffer)
Any idea what can cause the issue? and how to fix?
Steps to reproduce :
Pseudocode:
Packet packet = Packet.builder().putInt(100).putInt(200);
packet.queueAndFlush(client);
client.close();
I just want to ask if there is any implmentation of Simplenet with SSL? I have searched a lot and didnt find anything. Appreciate any hints.
Hello,
I am wondering if there is anyway to send a request to the server with the below, and get the result output back.
Example:
var result = Packet.builder().putByte(2).putString(message).queueAndFlush(client);
Any hint appreciated.
Thanks.
When testing the following code i came to the conclusion that only ever one element is returned for Client#readStringUntil
client.readByteAlways(opCode -> {
if (opCode == 2) {
List<String> tempWarps = new ArrayList<>();
client.readString(s -> {
client.readInt(warpSize -> {
AtomicInteger count = new AtomicInteger(0);
//this part
client.readStringUntil(s1 -> {
tempWarps.add(s1);
return warpSize < count.getAndIncrement();
});
});
serverWarps.put(s, tempWarps);
});
}
});
it seems to ignore the return value. if i swap < for > the result is the same.
I also tried using client.readStringAlways
but this messes up when new packets are received as they're still getting handled in the readStringAlways
A declarative, efficient, and flexible JavaScript library for building user interfaces.
๐ Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. ๐๐๐
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google โค๏ธ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.