![](/img/trans.png)
[英]using c++ wss server with websocket++ or other c++ websocket lib
[英]making the Websocket using the c++ server
我在用c ++制作服務器以連接到WebSocket,但是不知何故,它沒有與websocket連接。 WebSocket顯示連接已關閉,並且在c ++服務器中也存在一些問題,因為從WebSocket第二次調用服務器時,它顯示以下錯誤-兩次釋放或損壞(輸出)。 我花了很多時間。 這是代碼:c ++
#include<iostream>
#include <string>
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <errno.h>
#include <string.h>
#include <time.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <netdb.h>
using namespace std;
string getConnectionKey(char*);
void acceptConnection(int, const char*);
void readConnection(int);
void bail(char*);
string executeShellCommand(const string&);
string getBase64Encoded(string);
char *getClientKey(char*);
string getSHA1Hash(string);
int main()
{
char srvr_adr[] = "127.0.0.1";
char srvr_port[] = "9099";
struct sockaddr_in adr_srvr;
struct sockaddr_in adr_clnt;
socklen_t len_inet;
int s; // Server Socket
int c; // Client Socket
int z;
char *data;
char readdata[256];
int count = 2;
data = (char*)malloc(sizeof(char)*128);
s = socket(PF_INET, SOCK_STREAM, 0);
if(s == -1)
bail("socket()");
memset(&adr_srvr,0,sizeof(adr_srvr));
adr_srvr.sin_family = AF_INET;
adr_srvr.sin_port = htons(atoi(srvr_port));
if( strcmp(srvr_adr,"*")!=0)
{
adr_srvr.sin_addr.s_addr = inet_addr(srvr_adr);
if(adr_srvr.sin_addr.s_addr == INADDR_NONE)
bail(" INVALID ADRESS \n");
}
else /* WILD ADDRESS*/
adr_srvr.sin_addr.s_addr = INADDR_ANY;
len_inet = sizeof adr_srvr;
z = bind(s,(struct sockaddr*)&adr_srvr, len_inet);
if(z==-1)
bail("bind(2)");
z = listen(s,10);
if(z==-1)
bail("listen(2)");
for(;;)
{
len_inet = sizeof(adr_clnt);
c = accept(s, (struct sockaddr*)&adr_clnt,&len_inet);
if(c==-1)
bail("accept(2)");
readConnection(c);
close(c);
}
return 0;
}
void readConnection(int c)
{
int z;
char readdata[256];
// READING
z = read(c,readdata, sizeof(readdata)-1);
if(z==-1)
bail("read(2)");
else if(strlen(readdata)>0)
printf(" READ \n%s\n", readdata);
string key = getConnectionKey(readdata);
cout<<" KEY "<<key<<endl;
acceptConnection(c, key.c_str());
}
void acceptConnection(int c, const char *key)
{
int z;
char response[] = "HTTP/1.1 101 Switching Protocols\nUpgrade: websocket\nConnection: Upgrade\nSec-WebSocket-Accept: ";
char *output;
output = (char*)malloc( sizeof(char) * ( strlen(key) + strlen(response) + 1) );
strcat(output, response);
strcat(output, key);
cout<<" output "<<output<<endl;
// WRITING
z = write(c, output, strlen(output));
if(z == -1)
bail("write(2)");
printf(" Connection Done \n");
}
string getConnectionKey(char *str)
{
char *start,*end,*key;
int len;
string s("258EAFA5-E914-47DA-95CA-C5AB0DC85B11");
// GET CLIENT KEY
key = getClientKey(str);
// Appending the key
s = key + s;
// SHA1 HASH
string out = getSHA1Hash(s);
//hashwrapper *h = new sha1wrapper();
//string out = h->getHashFromString(s);
// BASE 64 ENCODING
string encoded = getBase64Encoded(out);
//encoded = (char*)malloc(sizeof(char)*256);
//strcpy(encoded, getBase64Encoded(out) );
free(key);
//delete h;
return encoded;
}
char *getClientKey(char *str)
{
int len;
char *start,*end,*key;
start = strstr(str, "Sec-WebSocket-Key:");
if(start == NULL)
return false;
start += 17;
end = strstr(start, "==");
if(end == NULL)
return false;
end++;
while( !(*start>=65 && *start<=90 || *start >= 97 && *start<=122 || *start>=48 && *start<=57 || *start == '+' || *start=='/') )
start++;
len = end - start + 1;
key = (char*) malloc( sizeof(char) * (len+1) );
strncpy(key,start,len);
return key;
}
string getBase64Encoded(string s)
{
int len;
string str="";
len = s.length();
char *command;
for(int i=len-1 ; i>=1; i=i-2)
{
str = s.substr(i-1,2) + str;
str = "\\x" + str;
}
if(len%2==1)
{
str = s[0] + str;
str = "\\x" + str;
}
// making the command to be send to shell
str = "printf \"" + str ;
str = str + "\" | base64";
cout<<endl<<" STRING "<<str<<endl;
return executeShellCommand(str);
}
string getSHA1Hash(string str)
{
int len ;
string output;
str = "printf \""+str;
str = str +"\" | sha1sum";
cout<<str<<endl;
output = executeShellCommand(str);
return output.substr(0,output.length()-4);;
}
string executeShellCommand(const string& cmd)
{
FILE *fpipe;
if ( !(fpipe = (FILE*)popen(cmd.c_str(),"r")) )
{ // If fpipe is NULL
perror("Problems with pipe");
exit(1);
}
char buf[256] = "";
string line="";
while ( fgets( buf, sizeof buf, fpipe) )
{
if(strlen(buf)>0)
line.append(buf);
memset(buf, 0, sizeof(buf));
}
// CLOSE THE PIPE
pclose(fpipe);
return line;
}
void bail(char *on_what)
{
if(errno!=0)
{
fputs( strerror(errno), stderr);
fputs( ":", stderr);
}
fputs( on_what, stderr);
fputs("\n",stderr);
}
這是Websocket代碼:
<!doctype html>
<html>
<head>
<meta charset="UTF-8">
<title>WebSocket Chat</title>
</head>
<body>
<h1>WebSocket Chat</h1>
<section id="content"></section>
<input id="message" type="text" tabindex="1"/>
<textarea id="show">
</textarea>
<script src="http://www.google.com/jsapi"></script>
<script>google.load("jquery", "1.3")</script>
<script src="http://jquery-json.googlecode.com/files/jquery.json-2.2.min.js"></script>
<!--script src="http://jquery-websocket.googlecode.com/files/jquery.websocket-0.0.1.js"></script-->
<script src="/js/jquery.websocket-0.0.1.js"></script>
<script type="text/javascript">
/*var ws = $.websocket("ws://127.0.0.1:9099/",
{
events: {
message: function(e)
{
alert("e.data");
$('#content').append(e.data + '<br>')
}
}
});*/
var websocketConnection = new WebSocket("ws://127.0.0.1:9099/");
websocketConnection.onopen = function(ev)
{
showmsg('Connected to the echo service');
};
websocketConnection.onerror = function(ev)
{
showmsg(" ERROR : ".ev.data);
}
websocketConnection.onclose = function(ev)
{
showmsg(" Connection Closed");
};
websocketConnection.onmessage = function(event)
{
showmsg(event.data);
$('#content').append(event.data+"<br>");
};
showmsg(" CURRENT STATE "+websocketConnection.readyState);
if(!websocketConnection)
showmsg(" object null ");
websocketConnection.send("Hello Echo Server");
$('#message').change(function(){
flag = ws.send('message', this.value);
if(!flag)
alert("not send");
this.value = '';
});
function showmsg(content)
{
$('#show').val(content+"<br>");
}
</script>
</body>
</html>
請幫幫我,C ++中的問題是什么以及要發送到WebScoket的響應是什么。
這是一個問題(在executeShellCommand()
函數中):
command = (char*) malloc( sizeof(char) * cmd.length() );
line = (char*)malloc(sizeof(char)*256);
line[0] = '\0';
//cout<<" COMMAND "<<cmd<<endl;
strcpy(command, cmd.c_str() ); // Writes one beyond the end of the
// 'command' buffer as no space allocated
// for null terminator
您可以直接將cmd.c_str()
傳遞給popen()
而不是為此目的分配和填充command
緩沖區:
if ( !(fpipe = (FILE*)popen(cmd.c_str(),"r")) )
我建議在可能的情況下用std::string
替換char*
,並允許它為您管理內存,並在不適合使用std::string
情況下使用堆棧分配的緩沖區而不是動態分配緩沖區。 例如:
std::string executeShellCommand(const std::string& cmd)
{
FILE *fpipe;
if ( !(fpipe = (FILE*)popen(cmd.c_str(),"r")) )
{ // If fpipe is NULL
perror("Problems with pipe");
exit(1);
}
char buf[256] = "";
std::string line;
while ( fgets( buf, sizeof buf, fpipe) )
{
line += buf;
memset(buf, 0, sizeof(buf));
}
// CLOSE THE PIPE
pclose(fpipe);
return line;
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.