Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

为什么test中的实例 和netty的UDP或者TCP直接发送相比,每秒钟发送消息数不如后者多? #10

Open
tidus5 opened this issue Dec 7, 2017 · 7 comments

Comments

@tidus5
Copy link
Contributor

tidus5 commented Dec 7, 2017

TestServer 和 TestClient 的 handleRecieve 都改为类似
@OverRide
public void handleReceive(ByteBuf bb, KcpOnUdp kcp) {
String content = bb.toString(Charset.forName("utf-8"));
System.out.println("KCP "+ content +System.currentTimeMillis());
kcp.send(bb);// echo
}
互相回发,Client的main函数中 sleep 1s 后调用close() 方法,测试下来Server端可以打印100行左右。
而用Netty直接写UDP测试1s可以打印出近2000行消息,TCP 1s 也可以打印近1800行消息。

造成这种差异的原因,是KCP算法本身调度,和增加了流量大小所致,还是别的原因?

测试DUP 用例:
public class Server {
private static Logger logger = LoggerFactory.getLogger(Server.class);

/**
 * udp服务端,接受客户端发送的广播
 */
public static void initServer() {
	EventLoopGroup group = new NioEventLoopGroup();
	try {
		Bootstrap bootstrap = new Bootstrap();
		bootstrap.group(group).channel(NioDatagramChannel.class).option(ChannelOption.SO_BROADCAST, true)
				.handler(new UdpServerHandler());
		Channel channel = bootstrap.bind(AppConstants.SEARCH_PORT).sync().channel();
		channel.closeFuture().await();
	} catch (InterruptedException e) {
		e.printStackTrace();
	} finally {
		group.shutdownGracefully();
	}
}

private static class UdpServerHandler extends SimpleChannelInboundHandler<DatagramPacket> {
	@Override
	protected void channelRead0(ChannelHandlerContext ctx, DatagramPacket msg) throws Exception {
		System.out.println("UDP "+ req +System.currentTimeMillis());
		ctx.writeAndFlush(new DatagramPacket(Unpooled.copiedBuffer(req, CharsetUtil.UTF_8), msg.sender()));
	}
}

public static void main(String args[]) {
	Server.initServer();
}

}

public class Client {
private static Logger logger = LoggerFactory.getLogger(Client.class);
private int scanPort;

public Client(int scanPort) {
	this.scanPort = scanPort;
}

private static class ClientHandler extends SimpleChannelInboundHandler<DatagramPacket> {

	@Override
	protected void channelRead0(ChannelHandlerContext ctx, DatagramPacket msg) throws Exception {
		String response = msg.content().toString(CharsetUtil.UTF_8);
		System.out.println("UDP "+ response +System.currentTimeMillis());
		ctx.writeAndFlush(new DatagramPacket(Unpooled.copiedBuffer(response, CharsetUtil.UTF_8), msg.sender()));
	}
}

public void sendPackage() {
	EventLoopGroup group = new NioEventLoopGroup();
	try {
		Bootstrap b = new Bootstrap();
		b.group(group).channel(NioDatagramChannel.class).option(ChannelOption.SO_BROADCAST, true)
				.handler(new ClientHandler());

		Channel ch = b.bind(0).sync().channel();

		ch.writeAndFlush(new DatagramPacket(Unpooled.copiedBuffer("hello!!!", CharsetUtil.UTF_8),
				new InetSocketAddress("255.255.255.255", scanPort))).sync();
	} catch (Exception e) {
		e.printStackTrace();
	} finally {
		group.shutdownGracefully();
	}
}

public static void main(String args[]) {
	Client client = new Client(AppConstants.SEARCH_PORT);
	client.sendPackage();
}

}

public class AppConstants {

public static final int SEARCH_PORT = 22023;

}

@beykery
Copy link
Owner

beykery commented Dec 14, 2017

这个地方是因为update的时候并没有真的发出去,send后需要等到10ms以后才发。
现在还没有想好怎么改。

@tidus5
Copy link
Contributor Author

tidus5 commented Dec 14, 2017

@beykery 那么可否这样理解:
send 的时候,可以把list 里堆积的消息全部发出去么。 就算更新频率慢些,但发送消息条数应该不会差太多才对。另外更新频率参数我试着修改到 1ms, 数量还是没有明显提高。

@beykery
Copy link
Owner

beykery commented Dec 15, 2017

你改成1ms是没用的,因为最小就是10ms;
另外,send的时候会先保存到queue里面,等下一个调度,10ms后才能发出去,那么,对端也就是10ms以后才能收到,收到后echo回去,还是要等10ms才能真正发出去;这就是为何你的测试echo的时候很慢。
但我还没想好怎么改。

@tidus5
Copy link
Contributor Author

tidus5 commented Dec 15, 2017

noDelay(int nodelay, int interval, int resend, int nc)
这个方法的的 interval 参数,是否就算这个调度时长? 我是把这个参数。。。额,看到内部代码了,包内部最小设置了是10ms。
那么,C#的原版的代码是否也有这个问题呢,就是互发频率不够高的问题?

@beykery
Copy link
Owner

beykery commented Dec 15, 2017

你说的哪个c#原版?

@tidus5
Copy link
Contributor Author

tidus5 commented Dec 15, 2017

https://github.com/skywind3000/kcp

这个啊,kcp的原版。 哦,原版是C++的,记错了

@beykery
Copy link
Owner

beykery commented Oct 10, 2018

这个问题,可以参考原作的这个issue:
skywind3000/kcp#105
看来也没有特别的办法了。

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants