⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ghttp.cpp

📁 一个由Mike Gashler完成的机器学习方面的includes neural net, naive bayesian classifier, decision tree, KNN, a genet
💻 CPP
📖 第 1 页 / 共 2 页
字号:
{	if(m_status != Done)	{		GimmeWhatYouGot();		if(m_status == Done)		{			//GAssert(false, "todo: why are we giving it out early?");		}			}		if(m_status != Done)	{		// it's really not done, so don't return anything [rdp]		*pnSize = 0;		return NULL;	}	*pnSize = m_nContentSize;	return m_pData;}unsigned char* GHttpClient::DropData(int* pnSize){	unsigned char* pData = GetData(pnSize);	if(!pData)		return NULL;	m_pData = NULL;	return pData;}// -----------------------------------------------------------------------class GHttpServerBuffer{public:	enum RequestType	{		None,		Get,		Head,		Post,	};	int m_nPos;	char m_szLine[MAX_SERVER_LINE_SIZE];	char m_szUrl[MAX_SERVER_LINE_SIZE];	char m_szParams[MAX_SERVER_LINE_SIZE];	char m_szDate[MAX_SERVER_LINE_SIZE];	char m_szCookie[MAX_COOKIE_SIZE];	unsigned char* m_pPostBuffer;	RequestType m_eRequestType;	int m_nContentLength;	GHttpServerBuffer()	{		m_eRequestType = None;		m_nPos = 0;		m_nContentLength = 0;		m_pPostBuffer = NULL;	}	~GHttpServerBuffer()	{		delete[] m_pPostBuffer;	}	void Reset()	{		m_szUrl[0] = '\0';		m_szParams[0] = '\0';		m_szDate[0] = '\0';		m_szCookie[0] = '\0';		m_nContentLength = 0;		delete[] m_pPostBuffer;		m_pPostBuffer = NULL;	}};GHttpServer::GHttpServer(int nPort){	m_pBuffers = new GPointerArray(16);	m_pSocket = GSocketServer::HostTCPSocket(nPort);	if(!m_pSocket)		throw("failed to open port");	m_pQ = new GQueue();	SetContentType("text/html");	SetCookie("", false);	m_time = 0;}GHttpServer::~GHttpServer(){	int nCount = m_pBuffers->GetSize();	int n;	for(n = 0; n < nCount; n++)		delete((GHttpServerBuffer*)m_pBuffers->GetPointer(n));	delete(m_pBuffers);	delete(m_pSocket);	delete(m_pQ);}bool GHttpServer::Process(){	int nMessageSize;	int nConnection;	unsigned char* pMessage;	unsigned char* pIn;	char c;	GHttpServerBuffer* pBuffer;	bool bDidSomething = false;	while(m_pSocket->GetMessageCount() > 0)	{		bDidSomething = true;		pMessage = m_pSocket->GetNextMessage(&nMessageSize, &nConnection);		pIn = pMessage;		while(m_pBuffers->GetSize() <= nConnection)			m_pBuffers->AddPointer(new GHttpServerBuffer());		pBuffer = (GHttpServerBuffer*)m_pBuffers->GetPointer(nConnection);		while(nMessageSize > 0)		{			if(pBuffer->m_pPostBuffer)			{				ProcessPostData(nConnection, pBuffer, pIn, nMessageSize);				break;			}			else			{				// Obtain a single header line				while(nMessageSize > 0)				{					c = *pIn;					pBuffer->m_szLine[pBuffer->m_nPos++] = c;					pIn++;					nMessageSize--;					if(c == '\n' || pBuffer->m_nPos >= MAX_SERVER_LINE_SIZE - 1)					{						pBuffer->m_szLine[pBuffer->m_nPos] = '\0';						ProcessHeaderLine(nConnection, pBuffer, pBuffer->m_szLine);						pBuffer->m_nPos = 0;						break;					}				}			}		}		delete(pMessage);	}	return bDidSomething;}void GHttpServer::BeginRequest(GHttpServerBuffer* pClient, int eType, const char* szIn){	pClient->Reset();	pClient->m_eRequestType = (GHttpServerBuffer::RequestType)eType;	char* szOut = pClient->m_szUrl;	while(*szIn > ' ' && *szIn != '?')	{		*szOut = *szIn;		szIn++;		szOut++;	}	*szOut = '\0';	if(eType == GHttpServerBuffer::Get && *szIn == '?')	{		szIn++;		szOut = pClient->m_szParams;		while(*szIn > ' ')		{			*szOut = *szIn;			szIn++;			szOut++;		}		*szOut = '\0';	}	else		pClient->m_szParams[0] = '\0';}void GHttpServer::ProcessPostData(int nConnection, GHttpServerBuffer* pClient, const unsigned char* pData, int nDataSize){	if(nDataSize > pClient->m_nContentLength - pClient->m_nPos)		nDataSize = pClient->m_nContentLength - pClient->m_nPos;	memcpy(pClient->m_pPostBuffer + pClient->m_nPos, pData, nDataSize);	pClient->m_nPos += nDataSize;	if(pClient->m_nPos >= pClient->m_nContentLength)	{		pClient->m_pPostBuffer[pClient->m_nContentLength] = '\0';		char* szCookie = NULL;		if(pClient->m_szCookie[0] != '\0')			szCookie = pClient->m_szCookie;		m_time = 0;		DoPost(pClient->m_szUrl, pClient->m_pPostBuffer, pClient->m_nContentLength, szCookie, m_pQ);		pClient->m_pPostBuffer = NULL;		pClient->m_nPos = 0;		SendResponse(pClient, nConnection);	}}#define MAX_POST_SIZE 49152void GHttpServer::ProcessHeaderLine(int nConnection, GHttpServerBuffer* pClient, const char* szLine){	OnProcessLine(nConnection, szLine);	// Skip whitespace	while(*szLine > '\0' && *szLine <= ' ')		szLine++;	if(*szLine == '\0')	{		if(pClient->m_eRequestType == GHttpServerBuffer::Get)		{			bool bModified = true;			if(pClient->m_szDate[0] != '\0')				bModified = HasBeenModifiedSince(pClient->m_szUrl, pClient->m_szDate);			if(bModified)			{				char* szCookie = NULL;				if(pClient->m_szCookie[0] != '\0')					szCookie = pClient->m_szCookie;				m_time = 0;				DoGet(pClient->m_szUrl, pClient->m_szParams, strlen(pClient->m_szParams), szCookie, m_pQ);				SendResponse(pClient, nConnection);			}			else				SendNotModifiedResponse(pClient, nConnection);		}		else if(pClient->m_eRequestType == GHttpServerBuffer::Head)		{			m_time = 0;			SetHeaders(pClient->m_szUrl, pClient->m_szParams);			SendResponse(pClient, nConnection);		}		else if(pClient->m_eRequestType == GHttpServerBuffer::Post)		{			if(pClient->m_nContentLength >= 0 && pClient->m_nContentLength <= MAX_POST_SIZE)			{				if(pClient->m_nContentLength > 0)					pClient->m_pPostBuffer = new unsigned char[pClient->m_nContentLength + 1];				else					pClient->m_pPostBuffer = NULL;				pClient->m_nPos = 0;			}			else			{				GAssert(false, "bad post data size");				m_pSocket->Disconnect(nConnection);			}		}	}	else if(strnicmp(szLine, "GET ", 4) == 0)		BeginRequest(pClient, GHttpServerBuffer::Get, szLine + 4);	else if(strnicmp(szLine, "HEAD ", 5) == 0)		BeginRequest(pClient, GHttpServerBuffer::Head, szLine + 5);	else if(strnicmp(szLine, "POST ", 5) == 0)		BeginRequest(pClient, GHttpServerBuffer::Post, szLine + 5);	else if(strnicmp(szLine, "Content-Length: ", 16) == 0)		pClient->m_nContentLength = atoi(szLine + 16);	else if(strnicmp(szLine, "Cookie: ", 8) == 0)	{		int i = 17; // strlen("Cookie: attribute")		while(szLine[i] != '=' && szLine[i] != '\0')			i++;		if(szLine[i] == '=')			i++;		strcpy(pClient->m_szCookie, szLine + i);	}	else if(strnicmp(szLine, "If-Modified-Since: ", 19) == 0)	{		const char* szIn = szLine + 19;		char* szOut = pClient->m_szDate;		while(*szIn >= ' ')		{			*szOut = *szIn;			szIn++;			szOut++;		}		*szOut = '\0';	}}void GHttpServer::SetContentType(const char* szContentType){	GString::StrCpy(m_szContentType, szContentType, 64);}void GHttpServer::SetCookie(const char* szPayload, bool bPersist){	m_bPersistCookie = bPersist;	GString::StrCpy(m_szCookie, szPayload, MAX_COOKIE_SIZE);}void AscTimeToGMT(const char* szIn, char* szOut){	// Copy the day	while(*szIn > ' ')		*(szOut++) = *(szIn++);	*(szOut++) = ',';	*(szOut++) = ' ';	while(*szIn == ' ')		szIn++;	// Copy the day of the month	const char* pMonth = szIn;	while(*szIn > ' ')		szIn++;	while(*szIn == ' ')		szIn++;	while(*szIn > ' ')		*(szOut++) = *(szIn++);	*(szOut++) = ' ';	while(*szIn == ' ')		szIn++;	const char* pTime = szIn;	// Copy the month	while(*pMonth > ' ')		*(szOut++) = *(pMonth++);	*(szOut++) = ' ';	// Copy the year	while(*szIn > ' ')		szIn++;	while(*szIn == ' ')		szIn++;	while(*szIn > ' ')		*(szOut++) = *(szIn++);	*(szOut++) = ' ';	// Copy the time	while(*pTime > ' ')		*(szOut++) = *(pTime++);	*(szOut++) = ' ';	// Add "GMT"	strcpy(szOut, "GMT");}void GHttpServer::SendResponse(GHttpServerBuffer* pClient, int nConnection){	// Make the header	GQueue q;	q.Push("HTTP/1.1 200 OK\r\nContent-Type: ");	q.Push(m_szContentType);	if(pClient->m_eRequestType != GHttpServerBuffer::Head)	{		q.Push("\r\nContent-Length: ");		char szPayloadSize[32];		itoa(m_pQ->GetSize(), szPayloadSize, 10);		q.Push(szPayloadSize);		q.Push("\r\n");	}	// Set the date header	if(m_time != 0)	{		q.Push("Date: ");		struct tm* pTime = gmtime(&m_time);		const char* szAscTime = asctime(pTime);		char szGMT[40];		AscTimeToGMT(szAscTime, szGMT);		q.Push(szGMT);		q.Push("\r\n");	}	// Set cookie	if(m_szCookie[0] != '\0')	{		q.Push("Set-Cookie: attribute=");		q.Push(m_szCookie);		q.Push("; path=/");		if(m_bPersistCookie)			q.Push("; expires=Sat, 01-Jan-2050 00:00:00 GMT");		q.Push("\r\n");	}	// Send it	q.Push("\r\n"); // blank line	int nHeaderSize = q.GetSize();	int nPayloadSize = (pClient->m_eRequestType == GHttpServerBuffer::Head ? 0 : m_pQ->GetSize());	char* pSendBuffer = new char[nHeaderSize + nPayloadSize];	ArrayHolder<char*> hSendBuffer(pSendBuffer);	q.Pop((unsigned char*)pSendBuffer, nHeaderSize);	if(pClient->m_eRequestType != GHttpServerBuffer::Head)		m_pQ->Pop((unsigned char*)pSendBuffer + nHeaderSize, nPayloadSize);	m_pSocket->Send(pSendBuffer, nHeaderSize + nPayloadSize, nConnection);}void GHttpServer::SendNotModifiedResponse(GHttpServerBuffer* pClient, int nConnection){	GQueue q;	q.Push("HTTP/1.1 304 Not Modified\r\nDate: ");	q.Push(pClient->m_szDate);	q.Push("\r\n\r\n");	int nSize = q.GetSize();	char* szHeader = q.DumpToString();	ArrayHolder<char*> hHeader(szHeader);	m_pSocket->Send(szHeader, nSize, nConnection);}/*static*/ void GHttpServer::UnescapeUrl(char* szOut, const char* szIn){	int c1, c2, n1, n2;	while(*szIn != '\0')	{		if(*szIn == '%')		{			szIn++;			n1 = *szIn;			szIn++;			n2 = *szIn;			if(n1 >= '0' && n1 <= '9')				c1 = n1 - '0';			else if(n1 >= 'a' && n1 <= 'z')				c1 = n1 - 'a' + 10;			else if(n1 >= 'A' && n1 <= 'Z')				c1 = n1 - 'A' + 10;			else				c1 = 2;			if(n2 >= '0' && n2 <= '9')				c2 = n2 - '0';			else if(n2 >= 'a' && n2 <= 'z')				c2 = n2 - 'a' + 10;			else if(n2 >= 'A' && n2 <= 'Z')				c2 = n2 - 'A' + 10;			else				c2 = 0;			*szOut = 16 * c1 + c2;		}		else if(*szIn == '+')			*szOut = ' ';		else			*szOut = *szIn;		szIn++;		szOut++;	}	*szOut = '\0';}/*static*/ void GHttpServer::ParseParams(GStringHeap* pStringHeap, GConstStringHashTable* pTable, const char* szParams){	GTEMPBUF(char, szTmp, strlen(szParams) + 1);	UnescapeUrl(szTmp, szParams);	int nNameStart = 0;	int nNameLen, nValueStart, nValueLen;	while(true)	{		for(nNameLen = 0; szTmp[nNameStart + nNameLen] != '=' && szTmp[nNameStart + nNameLen] != '\0'; nNameLen++)		{		}		if(szTmp[nNameStart + nNameLen] == '\0')			return;		nValueStart = nNameStart + nNameLen + 1;		for(nValueLen = 0; szTmp[nValueStart + nValueLen] != '&' && szTmp[nValueStart + nValueLen] != '\0'; nValueLen++)		{		}		const char* szName = pStringHeap->Add(&szTmp[nNameStart], nNameLen);		const char* szValue = pStringHeap->Add(&szTmp[nValueStart], nValueLen);		pTable->Add(szName, szValue);		if(szTmp[nValueStart + nValueLen] == '\0')			return;		nNameStart = nValueStart + nValueLen + 1;	}}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -