Ai
1 Star 0 Fork 0

Shawy/2023Linux

加入 Gitee
与超过 1200万 开发者一起发现、参与优秀开源项目,私有仓库也完全免费 :)
免费加入
文件
克隆/下载
UdpServer.hpp 3.30 KB
一键复制 编辑 原始数据 按行查看 历史
Shawy 提交于 2023-05-01 00:05 +08:00 . command version UdpServer
#pragma once
#include <iostream>
#include <string>
#include "Log.hpp"
#include <cerrno>
#include <cstring>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <unistd.h>
#include <cstdio>
#define SIZE 1024
class UdpServer
{
public:
UdpServer(uint16_t port, std::string ip = "")
: _port(port), _ip(ip), _sockfd(-1)
{
}
~UdpServer()
{
if (_sockfd >= 0)
close(_sockfd);
}
bool initServer()
{
// 1. 创建套接字
_sockfd = socket(AF_INET, SOCK_DGRAM, 0);
if (_sockfd < 0)
{
logMessage(FATAL, "%d:%s", errno, strerror(errno));
exit(2);
}
logMessage(DEBUG, "%s: %d", "create socket success, sockfd", _sockfd);
// 2. 绑定:将用户设置的IP和PORT在内核中与当前进程强关联
// 2.1 填充属性
struct sockaddr_in local;
bzero(&local, sizeof(local));
local.sin_family = AF_INET;
local.sin_port = htons(_port);
local.sin_addr.s_addr = _ip.empty() ? INADDR_ANY : inet_addr(_ip.c_str());
if (bind(_sockfd, (struct sockaddr *)&(local), sizeof(local)) < 0)
{
logMessage(FATAL, "bind():errno:%d:%s", errno, strerror(errno));
exit(2);
}
logMessage(NORMAL, "initialize udp server...%s", strerror(errno));
return true;
}
void Start()
{
char buffer[SIZE]; // 用来存放读取的数据
char result[256]; // 保存处理结果
std::string cmd; // 保存命令, 用于回写
for (;;)
{
memset(buffer, 0, sizeof(buffer));
memset(result, 0, sizeof(result));
struct sockaddr_in peer; // 客户端属性集合[输出型参数]
bzero(&peer, sizeof(peer)); // 初始化空间
socklen_t len = sizeof(peer);
// 1. 读取数据
ssize_t s = recvfrom(_sockfd, buffer, sizeof(buffer), 0,
(struct sockaddr *)&peer, &len);
// 2. 处理数据:提取缓冲区中的命令
if (s > 0)
{
buffer[s] = '\0';
FILE *fp = popen(buffer, "r");
if (fp == nullptr) // 读取失败
{
logMessage(ERROR, "popen: %d:%s", errno, strerror(errno));
continue; // 继续读取
}
// 过滤非法指令
if (strcasestr(buffer, "rm") != nullptr || strcasestr(buffer, "rmdir") != nullptr)
{
std::string err_msg = "非法指令: rm/rmdir...";
std::cout << err_msg << buffer << std::endl;
sendto(_sockfd, err_msg.c_str(), err_msg.size(), 0,
(struct sockaddr *)&peer, len);
}
while (fgets(result, sizeof(result), fp) != nullptr)
{
cmd += result;
}
pclose(fp);
}
// 3. 写回数据
sendto(_sockfd, cmd.c_str(), cmd.size(), 0,
(struct sockaddr *)&peer, len);
}
}
private:
uint16_t _port; // 端口号
std::string _ip; // IP地址
int _sockfd; // 套接字文件描述符
};
Loading...
马建仓 AI 助手
尝试更多
代码解读
代码找茬
代码优化
C++
1
https://gitee.com/shawyxy/2023-linux.git
git@gitee.com:shawyxy/2023-linux.git
shawyxy
2023-linux
2023Linux
main

搜索帮助