我正在尝试编写一个简单的Android聊天应用程序.我创建了一个处理所有网络通信的服务类.DatagramSocket绑定在一个单独的线程中.一旦进入,我收到此错误并且应用程序崩溃:
java.net.BindException: bind failed: EADDRINUSE (Address already in use)
at libcore.io.IoBridge.bind(IoBridge.java:89)
at java.net.PlainDatagramSocketImpl.bind(PlainDatagramSocketImpl.java:68)
at java.net.DatagramSocket.createSocket(DatagramSocket.java:133)
at java.net.DatagramSocket.<init>(DatagramSocket.java:78)
Run Code Online (Sandbox Code Playgroud)
这是推测它的代码.使用新DatagramSocket的行发生错误如何避免此错误?谢谢.
private class ComThread extends Thread {
private static final int BCAST_PORT = 8779;
DatagramSocket mSocket;
InetAddress myBcastIP, myLocalIP;
public ComThread() {
try {
myBcastIP = getBroadcastAddress();
if (D)
Log.d(TAG, "my bcast ip : " + myBcastIP);
myLocalIP = getLocalAddress();
if (D)
Log.d(TAG, "my local ip : " + myLocalIP);
if (mSocket == null) {
mSocket = new DatagramSocket(BCAST_PORT);
mSocket.setReuseAddress(true);
mSocket.setBroadcast(true); …Run Code Online (Sandbox Code Playgroud) 我一直试图找到一种方法来优雅地停止Go中的监听服务器.因为listen.Accept有必要关闭侦听套接字来发出结束信号,但是由于没有导出相关错误,我无法分辨出任何其他错误.
我能做得比这更好吗?请参阅FIXME下面的代码serve()
package main
import (
"io"
"log"
"net"
"time"
)
// Echo server struct
type EchoServer struct {
listen net.Listener
done chan bool
}
// Respond to incoming connection
//
// Write the address connected to then echo
func (es *EchoServer) respond(remote *net.TCPConn) {
defer remote.Close()
_, err := io.Copy(remote, remote)
if err != nil {
log.Printf("Error: %s", err)
}
}
// Listen for incoming connections
func (es *EchoServer) serve() {
for {
conn, …Run Code Online (Sandbox Code Playgroud) 我一直在阅读很多关于如何实现UDP打孔的内容但是出于某些原因我无法使其工作.
对于那些不熟悉udp打孔的人来说,这是我自己的定义:
目标是能够在服务器的帮助下在两个客户端(客户端A和客户端B)之间传输数据.因此,客户端A连接到服务器并发送其信息.客户B也这样做.服务器具有必要的信息,以便客户端A能够向客户端B发送数据,反之亦然.因此,服务器将该信息提供给两个客户端.一旦两个客户端都有关于彼此的信息,就可以在没有服务器帮助的情况下开始在这些客户端之间发送和接收数据.
我的目标是能够做我刚才描述的(udp打孔).在此之前,我认为能够从服务器连接到客户端会很有帮助.为此,我计划向服务器发送有关客户端的信息.一旦服务器收到该信息尝试从头开始连接到客户端.一旦我能够执行,我应该拥有开始实现真正的udp打孔所需的一切.
以下是我设置的方法:

顶级路由器的服务器和底部路由器连接到LAN端口.底部路由器(NAT)通过其WAN端口连接到顶级路由器.并且客户端计算机连接到底部路由器到其LAN端口之一.
因此,在该连接中,客户端能够看到服务器,但服务器无法看到客户端.
所以我在伪代码中完成的算法是:
服务器:
static void Main()
{
/* Part 1 receive data from client */
UdpClient listener = new UdpClient(11000);
IPEndPoint groupEP = new IPEndPoint(IPAddress.Any, 11000);
string received_data;
byte[] receive_byte_array = listener.Receive(ref groupEP);
received_data = Encoding.ASCII.GetString(receive_byte_array, 0, receive_byte_array.Length);
// get info
var ip = groupEP.Address.ToString();
var port = groupEP.Port;
/* Part 2 atempt to connect to client from scratch */
// now atempt to send data to …Run Code Online (Sandbox Code Playgroud) 我正在使用典型的套接字API在Linux平台上用C++编写网络应用程序,我正在研究将字节数组写入TCP流的两种替代方法:通过调用write()或调用send( ).我知道,因为这是Linux,套接字句柄只是一个文件描述符,因此在套接字上执行read()和write()调用是有效的,但套接字API也提供了send()和recv( )执行相同任务的功能.
因此,我想知道是否有任何特殊原因选择一类功能而不是另一类功能 - 是针对网络写入/读取优化的发送/接收功能,它们是否表现更好等等?或者我使用哪些功能真的是武断的?read()和write()在所有情况下都能正常运行吗?
感谢您的任何见解!
我试图推理用 C 语言实现的带有套接字的简单服务器如何处理并发客户端。假设一个简单的服务器等待客户端连接,然后读取客户端发送的消息。read() 是一个阻塞函数,因此服务器将阻塞,直到客户端写入它。如果我们假设两个客户端同时向服务器写入数据。服务器会唤醒其中一个,但另一个会发生什么?在处理来自第一个客户端的请求时,服务器是否仍在“监听”?我知道绑定函数采用 int 作为第二个参数来指定积压(默认为 5)。这是否意味着只有 5 个客户端可以同时连接到服务器?如果这是真的,处理多个并发连接的服务器是如何实现的?
出于性能原因,我使用Curiously Reoccuring模板模式来避免虚函数.我有很多执行数百万次的小命令.我试图将其纳入命令模式.我想在队列中添加大量命令,然后迭代执行每个命令.每个命令使用CRTP来避免虚函数.我遇到的问题是Command模式通常使用指针向量来实现.但是当Command类被模板化时,很难传递通用的Command指针.我不是C++专家,所以也许有一种显而易见的方法来存储模板化命令对象的向量?我一直试图使用类似的东西:
boost:ptr_vector commands;
AddCommand(Command* command) {
commands.push_back(command);
}
Run Code Online (Sandbox Code Playgroud)
问题是Command不是类型,因此Command* command给出了编译错误.我需要使用Command<CommandType>,但这不起作用,因为我需要队列来保存不同类型的命令.
任何解决方案的想法?或者虚拟功能是我唯一的选择吗?
增加:命令对象是蒙特卡罗模拟算法的一部分.所以你可能有,Command是来自正态分布的随机数,其中正态分布的参数是类的一部分.所以命令模式非常合适.我按特定顺序对需要维护状态的函数进行了大量调用.
当我在gcc编译器(www.codepad.org)中运行上述程序时,我得到输出为禁止系统调用:SYS_socketcall任何人都可以清楚为什么会出现此错误/输出?
int main() {
int i=8;
int *p=&i;
printf("\n%d",*p);
*++p=2;
printf("\n%d",i);
printf("\n%d",*p);
printf("\n%d",*(&i+1));
return 0;
}
Run Code Online (Sandbox Code Playgroud)
我所观察到的是,在执行*++ p = 2后,我变得无法访问;为什么?
每帧我需要分配一些需要坚持到框架结束的数据.
目前,我正在从不同的内存池中分配数据,这允许我用帧计数标记它.在帧结束时,我遍历内存池并删除在特定帧中分配的内存.
我遇到的问题是,为了保持数据,我必须将它放在一个结构中:
struct FrameMemory
{
uint32 frameIndex;
bool allocatedType; //0 = new(), 1 = new[]
void* pMemPtr;
}
Run Code Online (Sandbox Code Playgroud)
所以后来,当我开始释放内存时,它看起来像这样:
{
for(all blocks)
if(block[i].frameIndex == targetIndex)
if(block[i].allocatedType == 0)
delete block[i].pMemPtr;
else if (block[i].allocatedType ==1)
delete[] block[i].pMemPtr;
}
Run Code Online (Sandbox Code Playgroud)
问题在于,因为我必须将指向内存的指针重载为void*,所以DELETE运算符不能正确地将内存作为其"本机基类型"删除.IE析构函数NEVER为对象调用.
我试图找到使用智能指针模板化对象的方法,但为了做到这一点,我必须将模板化的类重载为非模板化的基类型,这使得删除更加困难.
有没有人能解决这样的问题?
有什么办法可以让一个线程分支到它自己的独立进程中吗?我知道有 CreateProcess 函数,但据我所知,您只能用它运行外部应用程序。我所要求的到底有可能吗?
我正在尝试在连接时自动向客户端发送服务器请求,但我一直得到10057的WSAGetLastError.我已经设置了从客户端到服务器的请求没有问题所以我不明白为什么我不能反过来?也许服务器必须等待来自客户端的第一个'发送',但我不明白为什么会这样?
我使用的是:
-asynchronous插座
-TCP
-s是一个有效的套接字
-i'v循环RequestInfo了若干遍,但没有任何变化
-选择()返回0
-datasize返回-1,ERRCODE 10057
谢谢 !!!
服务器:
//first - following the debugger
FD_ACCEPT
int acc = accept(s, (struct sockaddr*)&fromm, &fromlenn); //success
if(acc <= 0)
{
eLOGG << "\nFAIL FD_ACCEPT: " << WSAGetLastError();
}
RequestInfo();
//then
RequestInfo()
{
stringstream ssConverter;
ssConverter.clear(); ssConverter.str(string());
ssConverter << "00aa"; //request signal
bool blogin = false;
eLOG << "signal is: *" << ssConverter.str() << "*";
int bufSize = ssConverter.str().length();
fd_set writefds;
struct timeval timeout;
timeout.tv_sec = 3;
timeout.tv_usec = 0;
FD_ZERO(&writefds); …Run Code Online (Sandbox Code Playgroud) 我正在开发一个应用程序,它将通过UDP从另一个本地服务接收RTP数据包.在协议的早期,我收到一条带有IP地址的消息,我将从中接收这些RTP数据包,但端口号将被赋予为0(零)...我将使用短暂的打开我的UDP套接字港口.我对给定消息的响应将包含我打开的实际端口,以便发送方可以知道在哪里引导数据包.
我的网络库是套接字的实现boost::asio.我在哪里可以找到关于如何在不指定非零端口的情况下打开这种套接字的明确信息,即使用临时端口?在boost文档中搜索"ephemeral"并没有给我提供网络结果.
当然,我很乐意看到一个实际的例子,但找到好的文档也可以.
谢谢.