socket 怎么支持https

socket 如何支持https
本帖最后由 hkpsa007 于 2015-02-09 06:53:23 编辑
一个简单的http代理服务器 想在加上一个支持https的功能,请问怎么弄啊。
网上查了一下用openssl但是基础太差 没学过 搞了好久都不行,
请教大家帮忙指点一下 有没有别的简单的方式实现。或者谁能帮改程openssl的 学习一下。谢谢
代码
// s.cpp : Defines the entry point for the console application.
//

#include "stdafx.h"
#include "s.h"

#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif

/////////////////////////////////////////////////////////////////////////////
// The one and only application object

CWinApp theApp;

using namespace std;


#include <stdio.h>
#include <iostream>
#include <winsock2.h>
#include <process.h>
//#include "SockInit.h"
using namespace std;

#define MAX_REQUESTLINE_LEN  2048  // IE请求行长度

void __cdecl ServerThreadProc(void *param);
int TCPsend(SOCKET s,const char*buf,int len,int flags);
int TCPrecv(SOCKET s,const char*buf,int len,int flags);
/************************************************

 调试环境:Visual C++6.0 SP6+platform SDK 2003 R2

 程序名称:HTTP proxy Server(HttpProxySvr.cpp)

 功能    :IE通过设置代理方式上网,IE所有请求均
          先发到该代理服务器,代理服务器
          将请求直接转发给webserver, 
  后从webserver读取响应后发回IE
 
**************************************************/

int main()
{
USHORT uPort=9999;   // 通信端口
    
         WORD wVersionRequested;
       WSADATA wsaData;
      int err;
 
      wVersionRequested = MAKEWORD( 2, 2 );
 
      err = WSAStartup( wVersionRequested, &wsaData );
      if ( err != 0 ) 
      {
         return 0;
      }
 
                             
 
   if ( LOBYTE( wsaData.wVersion ) != 2 ||
        HIBYTE( wsaData.wVersion ) != 2 ) 
     {
                                 
    WSACleanup( );
    return  0; 
    }
SOCKET sListen = socket(AF_INET,SOCK_STREAM,0);
if(sListen == INVALID_SOCKET)
{
printf("Failed socket(),error code :%d",WSAGetLastError());
return 0;
}

sockaddr_in sin;
sin.sin_addr.S_un.S_addr = INADDR_ANY;
sin.sin_family =AF_INET;
sin.sin_port = htons(uPort);
 
if(bind(sListen,(sockaddr*)&sin,sizeof(sin))==SOCKET_ERROR)
{
    printf("Failed bind(),error code :%d",WSAGetLastError());
closesocket(sListen);
return 0;
}

int res =listen(sListen,200);

sockaddr_in addrRemote;
int len =sizeof(addrRemote);
while(true)
{
    SOCKET sNew = accept(sListen,(sockaddr*)&addrRemote,&len);
if(sNew == INVALID_SOCKET)
{
printf("Failed accept(),error code :%d",WSAGetLastError());
return 0;
}
    
printf("收到一个IE连接(IP:%s)\n",inet_ntoa(addrRemote.sin_addr));

// 创建一个线程处理该连接 (每客户单线程模式...)
_beginthread(ServerThreadProc,0,(void*)sNew);
}
   
closesocket(sListen);

return 0;
}

void __cdecl ServerThreadProc(void *param)
{
SOCKET sock = (SOCKET)param;   //与浏览器连接的套接口

char request[MAX_REQUESTLINE_LEN];
memset(request,0,MAX_REQUESTLINE_LEN);
int res =recv(sock,request,MAX_REQUESTLINE_LEN,0);  // 接收浏览器(客户端)发来的请求
if(res==0)
{

printf("连接断开\n");

closesocket(sock);
return;
}
shutdown(sock,SD_RECEIVE);
//  打印收到的请求
printf("header length :%d  header: %s\n",res,request);

// 分析请求行(分离出WebServer域名)
    char szAddrName[1024]={0}; //域名
int i =11;
while(request[i]!='/'&&i<res)
{
szAddrName[i-11] = request[i];
i++;

}
szAddrName[i-11]='\0';

printf("WebServer address: %s\n\n",szAddrName);

// 向WebServer提交请求
SOCKADDR_IN   saServer;   
LPHOSTENT     lphostent;     
SOCKET        hsocket;
int   nRet;   

lphostent=gethostbyname(szAddrName); // 通过域名获得目标WebServer的IP 
if(lphostent==NULL)
{
printf("Failed gethostbyname(),error code:%d\n",WSAGetLastError());
return ;   
}

hsocket = socket(AF_INET,SOCK_STREAM,0); 
if(hsocket==INVALID_SOCKET)
{
       printf("Failed socket(),error code:%d\n",WSAGetLastError());
   return ;   
}
saServer.sin_family = AF_INET;   
saServer.sin_port = htons(80);
saServer.sin_addr= *((LPIN_ADDR)*lphostent->h_addr_list);   

nRet = connect(hsocket,(LPSOCKADDR)&saServer,sizeof(SOCKADDR_IN));   
if(nRet==SOCKET_ERROR)   
{   
printf("Failed connect(),error code:%d\n",WSAGetLastError());
closesocket(hsocket);   
return;   


//  向webserver转发IE请求 
nRet = TCPsend(hsocket,request,strlen(request),0);

char   dest[1000];   
nRet=1; 
int senlen=0;
while(nRet>0)   
{   
memset(dest,0,1000);
nRet=recv(hsocket,dest,sizeof(dest)-1,0);  // 从webserver获取数据 
if(nRet==0)   
{
printf("与webserver(%s)的连接关闭\n",szAddrName);

break;
}
else  if(nRet==SOCKET_ERROR )
{
   printf("Failed recv(),error code:%d\n",WSAGetLastError());       
   break;
}
dest[nRet]='\0';

senlen = TCPsend(sock,dest,nRet,0);  //将数据转发给IE浏览器
if(senlen==0)
{
sockaddr_in sin;
int len = sizeof(sin);
if(getpeername(sock,(sockaddr*)&sin,&len)== SOCKET_ERROR)
{
printf("Failed getpeername(),error code:%d\n",WSAGetLastError());
break;
}
            printf("与浏览器(%s)的一个连接关闭...\n",inet_ntoa(sin.sin_addr));
break;
}
else if(senlen==SOCKET_ERROR)
{
   printf("Failed send(),error code:%d\n",WSAGetLastError());       
   break;
}

// printf("%s\n",dest);

} // end of while(nRet>0)   


closesocket(sock);
closesocket(hsocket);

}

int TCPsend(SOCKET s,const char*buf,int len,int flags)
{
int n=0,sendCount=0;
int length =len;
if(buf==NULL)
return 0;
while(length>0)
{
n=send(s,buf+sendCount,length,flags); //发送数据,
if(n==SOCKET_ERROR)//网络出现异常
{
printf("Failed send(),error code:%d\n",WSAGetLastError());
break;

}
length-=n;
sendCount+=n; 
}

return sendCount; // 返回已发送的字节数
}

int TCPrecv(SOCKET s,char *buf,int len,int flags)
{

int nRev=0,recvCount=0;
int length =len;

if(buf==NULL)
return 0;

// 循环接收数据
while(length>0)
{
nRev =recv(s,buf+recvCount,length,flags);
if(nRev==SOCKET_ERROR)//网络出现异常
{
printf("Failed recv(),error code:%d\n",WSAGetLastError());
break;
}
length-=nRev;
recvCount+=nRev;
}

return recvCount; //返回接收到的字节数
}


------解决思路----------------------
https还要证书等支持,TLS协议等,自己从头实现比较复杂
可以找一个web server框架,一般都支持https了
------解决思路----------------------
恐怕还是要使用OpenSSL
其实不那么难
下载一组程序包,通常为一个“openssl”目录
使用的例子网上非常多
具体的资源在MSDN的下载中心搜索一下