gpt4 book ai didi

tcp - 似乎无法获得 C TCP 服务器-客户端通信的权利

转载 作者:行者123 更新时间:2023-11-30 17:56:15 25 4
gpt4 key购买 nike

我在这里需要一些认真的帮助。我必须制作一个 TCP 服务器客户端。当客户端使用三阶段握手连接到服务器时。之后,当客户端在终端中运行时,用户输入 Linux shell 命令,例如 xinput list、ls -1 等 - 使用标准输出的命令。服务器接受命令并使用 system() (在无限循环中的 fork() 中)运行命令,标准输出被重定向到客户端,其中客户端打印出每一行。

随后服务器发送完成信号“\377\n”。其中客户端返回到命令提示符,请求新命令,并在输入“quit”时关闭其连接和 exit()。

我知道您必须将 STDOUT_FILENO 和 STDERR_FILENO 都 dup2() 到客户端的文件描述符 {dup2(client_FD, STDOUT_FILENO)。一切正常,除非客户端检索系统()的标准输出并将其打印出来......我得到的只是一个带有闪烁光标的空行(客户端等待标准输入)。我尝试了各种不同的路线都无济于事...如果有人可以提供帮助,我将不胜感激

TCP 服务器代码

#include <sys/types.h>
#include <sys/socket.h>
#include <stdio.h>
#include <string.h>
#include <netinet/in.h>
#include <signal.h>
#include <unistd.h>
#include <stdlib.h>
#include <errno.h>

//Prototype
void handle_client(int connect_fd);

int main()
{
int server_sockfd, client_sockfd;
socklen_t server_len, client_len;
struct sockaddr_in server_address;
struct sockaddr_in client_address;

server_sockfd = socket(AF_INET, SOCK_STREAM, 0);

server_address.sin_family = AF_INET;
server_address.sin_addr.s_addr = htonl(INADDR_ANY);
server_address.sin_port = htons(9734);
server_len = sizeof(server_address);
bind(server_sockfd, (struct sockaddr *)&server_address, server_len);

/* Create a connection queue, ignore child exit details and wait for clients. */

listen(server_sockfd, 10);

signal(SIGCHLD, SIG_IGN);

while(1) {

printf("server waiting\n");

client_len = sizeof(client_address);
client_sockfd = accept(server_sockfd,
(struct sockaddr *)&client_address, &client_len);

if(fork() == 0)
handle_client(client_sockfd);
else
close(client_sockfd);
}
}

void handle_client(int connect_fd) {

const char* remsh = "<remsh>\n";
const char* ready = "<ready>\n";
const char* ok = "<ok>\n";
const char* command = "<command>\n";
const char* complete = "<\377\n";
const char* shared_secret = "<shapoopi>\n";

static char server_msg[201];
static char client_msg[201];
static char commands[201];

int sys_return;

//memset client_msg, server_msg, commands
memset(&client_msg, 0, sizeof(client_msg));
memset(&server_msg, 0, sizeof(client_msg));
memset(&commands, 0, sizeof(commands));
//read remsh from client
read(connect_fd, &client_msg, 200);
//check remsh validity from client
if(strcmp(client_msg, remsh) != 0) {
errno++;
perror("Error Establishing Handshake");
close(connect_fd);
exit(1);
}
//memset client_msg
memset(&client_msg, 0, sizeof(client_msg));
//write remsh to client
write(connect_fd, remsh, strlen(remsh));
//read shared_secret from client
read(connect_fd, &client_msg, 200);
//check shared_secret validity from client
if(strcmp(client_msg, shared_secret) != 0) {
errno++;
perror("Invalid Security Passphrase");
write(connect_fd, "no", 2);
close(connect_fd);
exit(1);
}
//memset client_msg
memset(&client_msg, 0, sizeof(client_msg));
//write ok to client
write(connect_fd, ok, strlen(ok));
// dup2 STDOUT_FILENO <= client fd, STDERR_FILENO <= client fd
dup2(connect_fd, STDOUT_FILENO);
dup2(connect_fd, STDERR_FILENO);
//begin while... while read (client_msg) from server and >0
while(read(connect_fd, &client_msg, 200) > 0) {
//check command validity from client
if(strcmp(client_msg, command) != 0) {
errno++;
perror("Error, unable to retrieve data");
close(connect_fd);
exit(1);
}
//memset client_msg
memset(&client_msg, 0, sizeof(client_msg));
//write ready to client
write(connect_fd, ready, strlen(ready));
//read commands from client
read(connect_fd, &commands, 200);
//run commands using system( )
sys_return = system(commands);
//check success of system( )
if(sys_return < 0) {
perror("Invalid Commands");
errno++;
}
//memset commands
memset(commands, 0, sizeof(commands));
//write complete to client
write(connect_fd, complete, sizeof(complete));

}
}

TCP 客户端代码

#include <sys/types.h>
#include <sys/socket.h>
#include <stdio.h>
#include <string.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <unistd.h>
#include <stdlib.h>
#include <errno.h>
#include "readline.c"

int main(int argc, char *argv[])
{
int sockfd;
int len;
struct sockaddr_in address;
int result;

const char* remsh = "<remsh>\n";
const char* ready = "<ready>\n";
const char* ok = "<ok>\n";
const char* command = "<command>\n";
const char* complete = "<\377\n";
const char* shared_secret = "<shapoopi>\n";

static char server_msg[201];
static char client_msg[201];

memset(&client_msg, 0, sizeof(client_msg));
memset(&server_msg, 0, sizeof(server_msg));

/* Create a socket for the client. */

sockfd = socket(AF_INET, SOCK_STREAM, 0);

/* Name the socket, as agreed with the server. */
memset(&address, 0, sizeof(address));

address.sin_family = AF_INET;
address.sin_addr.s_addr = inet_addr(argv[1]);
address.sin_port = htons(9734);
len = sizeof(address);

/* Now connect our socket to the server's socket. */

result = connect(sockfd, (struct sockaddr *)&address, len);

if(result == -1) {
perror("ACCESS DENIED");
exit(1);
}

//write remsh to server
write(sockfd, remsh, strlen(remsh));
//read remsh from server
read(sockfd, &server_msg, 200);
//check remsh validity from server
if(strcmp(server_msg, remsh) != 0) {
errno++;
perror("Error Establishing Initial Handshake");
close(sockfd);
exit(1);
}
//memset server_msg
memset(&server_msg, 0, sizeof(server_msg));
//write shared secret text to server
write(sockfd, shared_secret, strlen(shared_secret));
//read ok from server
read(sockfd, &server_msg, 200);
//check ok velidity from server
if(strcmp(server_msg, ok) != 0 ) {
errno++;
perror("Incorrect security phrase");
close(sockfd);
exit(1);
}
//? dup2 STDIN_FILENO = server socket fd?
//dup2(sockfd, STDIN_FILENO);
//begin while(1)///////////////////////////////////////
while(1){
//memset both msg arrays
memset(&client_msg, 0, sizeof(client_msg));
memset(&server_msg, 0, sizeof(server_msg));
//print Enter Command, scan input, fflush to stdout
printf("<<Enter Command>> ");
scanf("%s", client_msg);
fflush(stdout);
//check quit input, if true close and exit successfully
if(strcmp(client_msg, "quit") == 0) {
printf("Exiting\n");
close(sockfd);
exit(EXIT_SUCCESS);
}
//write command to server
write(sockfd, command, strlen(command));
//read ready from server
read(sockfd, &server_msg, 200);
//check ready validity from server
if(strcmp(server_msg, ready) != 0) {
errno++;
perror("Failed Server Communications");
close(sockfd);
exit(1);
}
//memset server_msg
memset(&server_msg, 0, sizeof(server_msg));
//begin looping and retrieving from stdin,
//break loop at EOF or complete
while((read(sockfd, server_msg, 200) != 0) && (strcmp(server_msg, complete) != 0)) {
//while((fgets(server_msg, 4096, stdin) != EOF) || (strcmp(server_msg, complete) == 0)) {
printf("%s", server_msg);
memset(&server_msg, 0, sizeof(server_msg));
}
}
}

最佳答案

system() 生成的子进程的输出未连接到调用父进程。尝试popen()

关于tcp - 似乎无法获得 C TCP 服务器-客户端通信的权利,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13717329/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com