我有一个用Java编写的简单服务器,它只是将一个Integer发送到一个连接的客户端。我有一个用C编写的客户端,它连接到服务器并打印出收到的Integer。
我的问题是结果有所不同。大约一半时间执行客户端我得到正确的结果(234),但有时我得到8323072。
这是服务器:
class TCPServer {
public static void main(String args[]) throws Exception {
ServerSocket welcomeSocket = new ServerSocket(6789);
while(true)
{
Socket connectionSocket = welcomeSocket.accept();
System.out.println("welcomeSocket.accept() called");
DataInputStream inFromClient = new DataInputStream(connectionSocket.getInputStream());
DataOutputStream outToClient = new DataOutputStream(connectionSocket.getOutputStream());
outToClient.writeInt(234);
}
}
}
这是客户:
int main(int argc, char *argv[])
{
if(argc != 4){
printUsage();
return;
}
char* serverIP = argv[1];
char* serverPortC = argv[2];
char* integerToSendC = argv[3];
int serverPort = atoi(serverPortC);
int integerToSend = atoi(integerToSendC);
int socketDesc = socket(AF_INET, SOCK_STREAM, 0);
if(socketDesc < 0) {
printf("Error when creating socket\n");
return;
}
struct sockaddr_in serverAddr;
serverAddr.sin_family = AF_INET;
serverAddr.sin_port = htons(serverPort);
inet_pton(AF_INET, serverIP, &serverAddr.sin_addr);
int connection = connect(socketDesc, (struct sockaddr*) &serverAddr, sizeof serverAddr);
if(connection < 0) {
printf("Error when establishing connection\n");
return;
}
char intBuffer[4];
if(recv(socketDesc, intBuffer, sizeof intBuffer, 0) == -1){
printf("Error while receiving Integer\n");
}
int receivedInt = ntohl(*((int *) &intBuffer));
printf("Received int: %d\n", receivedInt);
close(socketDesc);
}
提前感谢您的帮助!
编辑: 所以最后我做了类似的事情,只针对遇到同样问题的人:
while(receivedBytes < 4){
int readBytes = read(receiverSocket, &intBuffer, (sizeof intBuffer) - receivedBytes, receivedBytes);
receivedInteger += (intBuffer << (8*receivedBytes));
receivedBytes += readBytes;
}
答案 0 :(得分:1)
您能确定在客户端收到sizeof intBuffer
个字节吗?不,你不能,因为recv()
可能会返回更少的字节然后请求。
修改代码以循环recv()
,只要接收到的请求字节数更少且没有错误发生。
请注意,recv()
0
个字节表示连接已被另一方关闭。
还要确保服务器端以网络字节顺序发送。
另外^ 2:最好初始化变量(这里是intBuffer
),至少在开发阶段,会说:在调整阶段之前。
答案 1 :(得分:-1)
您的问题可能是由于各种数据类型的子边界。
在Java中,4个字节分配给int
,2个字节分配给short
在C中,4个字节用于long
,2个字节用于int
。
这意味着Java int
- &gt; C long
和Java short
- &gt; C int
。
现在,这取决于您的优先事项所在。
如果您想在Java中执行激烈的数学计算并将结果通过套接字发送到C,我建议您执行Java int -> C long
或
如果您只想发送小数字并在C中完成密集计算,请执行Java short
- &gt; C int
次转化。
希望有所帮助。