我有一个脚本通过 SSH (libssh2
)连接我的10台服务器之一。该程序使用fork
作为线程系统。它正在进入服务器,执行命令(如free -m
或检查CPU USSAGE),并通过 HTTP REQUEST 将输出发送到另一台服务器。
它工作正常,但有时它不会将数据发送回HTTP SERVER。我用puts('DEBUG123 ...')
做了一点调试,看看它崩溃的地方。我这样做是因为我使用FORK
并且我无法看到它在哪里被删除。在那里,你看到了代码。
... code from the fork
puts("DEBUG 6");
sprintf(param,"%s%s",param,my_encode(info));
puts("DEBUG 6.5");
getContent(MY_HOST,HOST_IP,param);
puts("DEBUG 7");
... code from the fork
my_encode函数的代码,用于在将数据发送到 HTTP SERVER 之前对其进行加密:
char *my_encode(char* bytes_to_encode)
{
puts("S-DEBUG 1");
int in_len = strlen(bytes_to_encode);
puts("S-DEBUG 1.1");
char buf[5200];
char *res = (char *)malloc(3600);
puts("S-DEBUG 1.2");
memset(buf,0,1200);
puts("S-DEBUG 1.3");
memset(res,0,3600);
puts("S-DEBUG 2");
strcpy(buf,base64_encode(bytes_to_encode,in_len));
for(int i=0;i<strlen(buf);i++)
{
strcat(res,switch_encode(buf[i]));
}
puts("S-DEBUG 3");
return res;
}
这是我得到的输出:
Linux -> username password 1.2.3.4 22
DEBUG 2
DEBUG 3
DEBUG 4
DEBUG 5
DEBUG 6
S-DEBUG 1
S-DEBUG 1.1
S-DEBUG 1.2
S-DEBUG 1.3
S-DEBUG 2
S-DEBUG 3
DEBUG 6.5
DEBUG 7
DEBUG 1
-- SUCCESSFUL SEND
Linux -> username password 1.2.3.4 22
DEBUG 2
DEBUG 3
DEBUG 4
DEBUG 5
DEBUG 6
S-DEBUG 1
S-DEBUG 1.1
S-DEBUG 1.2
S-DEBUG 1.3
S-DEBUG 2
S-DEBUG 3
DEBUG 6.5
DEBUG 7
DEBUG 1
-- SUCCESSFUL SEND
Linux -> username password 1.2.3.4 22
DEBUG 2
DEBUG 3
DEBUG 4
DEBUG 5
DEBUG 6
S-DEBUG 1
S-DEBUG 1.1
S-DEBUG 1.2
S-DEBUG 1.3
S-DEBUG 2
S-DEBUG 3
DEBUG 6.5
DEBUG 7
DEBUG 1
-- SUCCESSFUL SEND
Linux -> username password 1.2.3.4 22
DEBUG 2
DEBUG 3
DEBUG 4
DEBUG 5
DEBUG 6
S-DEBUG 1
S-DEBUG 1.1 <--- HERE IT IS CRASHING
DEBUG 1
-- ERROR ON SEND
Linux -> username password 1.2.3.4 22
DEBUG 2
DEBUG 3
DEBUG 4
DEBUG 5
DEBUG 6
S-DEBUG 1
S-DEBUG 1.1
S-DEBUG 1.2
S-DEBUG 1.3
S-DEBUG 2
S-DEBUG 3
DEBUG 6.5
DEBUG 7
-- SUCCESSFUL SEND
Linux -> username password 1.2.3.4 22
DEBUG 2
DEBUG 3
DEBUG 4
DEBUG 5
DEBUG 6
S-DEBUG 1
S-DEBUG 1.1 <--- HERE IT IS CRASHING
DEBUG 1
-- ERROR ON SEND
所以根据我的理解,这里的malloc
功能崩溃了:
char *res = (char *)malloc(3600);
这是我发送的基本信息:
username:password:1.2.3.4:22:Linux:Intel(R) Core(TM)2 Duo CPU E8200 @ 2.77GHz:242 238 3 0 15 64:no_server_load]
有时会崩溃。
此外,我更改了行char *res = (char *)malloc(3600);
,原来是char *res = (char *)malloc(1200);
。我相信我没有足够的存储空间。
my_encode
函数以使其不再崩溃?如果是这样,怎么?? 感谢。
答案 0 :(得分:1)
你必须做这样的事情(释放你的缓冲区):
#include <string>
void my_encode(char* bytes_to_encode, std::string& encoded) {
puts("S-DEBUG 1");
int in_len = strlen(bytes_to_encode);
puts("S-DEBUG 1.1");
char buf[5200];
char *res = (char *)malloc(3600);
puts("S-DEBUG 1.2");
memset(buf,0,1200);
puts("S-DEBUG 1.3");
memset(res,0,3600);
puts("S-DEBUG 2");
strcpy(buf,base64_encode(bytes_to_encode,in_len));
for(int i=0;i<strlen(buf);i++)
{
strcat(res,switch_encode(buf[i]));
}
puts("S-DEBUG 3");
encoded = res;
free(res);
}
void main() {
char *s = new char[32];
strcpy(s, "hello");
std::string str;
my_encode (s, str);
const char* result = str.c_str();
}
答案 1 :(得分:1)
sprintf(param,"%s%s",param,my_encode(info));
是一个错误。 sprintf的输入和输出不能重叠,这会导致未定义的行为。
你可能意味着strcat(param, my_encode(info));
虽然最好包含一个缓冲区大小检查。
您的代码不包括任何阻止缓冲区溢出的方法。可能会发生溢出,但你不知道在哪里。这可能会也可能不会导致您的问题,您无从谈论。即使没有,但改变输入可能会导致一个输入。
这是一种糟糕的代码编写方式,您的生活很难尝试调试。我的建议是重写所有这些代码,包括严格检查缓冲区大小,并确保您永远不会读取或写入缓冲区的末尾。在C ++中,最简单的方法是使用可调整大小的容器。
答案 2 :(得分:0)
如果您使用的是C++
- 使用std::string
来管理内存并避免分配/解除分配问题。
//get base64.cpp and base64.h
//from here http://www.adp-gmbh.ch/cpp/common/base64.html
#include <base64.h>
std::string my_encode(const std::string& bytes_to_encode)
{
puts("S-DEBUG 1");
std::string output = base64_encode(bytes_to_encode.c_str(),bytes_to_encode.length());
puts("S-DEBUG 2");
return output;
}