|
#define _CRT_SECURE_NO_WARNINGS |
|
#define _WINSOCK_DEPRECATED_NO_WARNINGS |
|
|
|
#include <stdio.h> |
|
#include <string.h> |
|
#include <string> |
|
#include <iostream> |
|
|
|
#include <winsock2.h> |
|
#pragma comment (lib, "Ws2_32.lib") |
|
#include <windows.h> |
|
|
|
#include "lua.hpp" |
|
|
|
#define LUA_PORT 8888 |
|
|
|
using namespace std; |
|
|
|
SOCKET m_socket; |
|
sockaddr_in server; |
|
sockaddr client_addr; |
|
int client_addr_len; |
|
|
|
int bytesSent = 0; |
|
int bytesRecv = 0; |
|
char sendBuff[16384]; |
|
char recvBuff[16384]; |
|
|
|
lua_State* luaState; |
|
|
|
// overload symbol for fwrite |
|
extern "C" |
|
{ |
|
size_t |
|
fwrite( const void * ptr, size_t size, size_t count, FILE * stream ) |
|
{ |
|
strcpy(sendBuff, (char *)ptr); |
|
bytesSent = sendto(m_socket, sendBuff, (int)strlen(sendBuff), 0, (const sockaddr *)&client_addr, client_addr_len); |
|
return bytesSent; |
|
} |
|
} |
|
|
|
void |
|
configNetwork(SOCKET & m_socket, sockaddr_in & serverService) |
|
{ |
|
WSAData wsaData; |
|
|
|
if (NO_ERROR != WSAStartup(MAKEWORD(2, 2), &wsaData)) |
|
{ |
|
cout << "Time Server: Error at WSAStartup()\n"; |
|
} |
|
|
|
m_socket = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP); |
|
|
|
if (INVALID_SOCKET == m_socket) |
|
{ |
|
cout << "Time Server: Error at socket(): " << WSAGetLastError() << endl; |
|
WSACleanup(); |
|
return; |
|
} |
|
|
|
serverService.sin_family = AF_INET; |
|
|
|
serverService.sin_addr.s_addr = inet_addr("127.0.0.1"); |
|
serverService.sin_port = htons(LUA_PORT); |
|
|
|
if (SOCKET_ERROR == bind(m_socket, (SOCKADDR *)&serverService, sizeof(serverService))) |
|
{ |
|
cout << "Time Server: Error at bind(): " << WSAGetLastError() << endl; |
|
closesocket(m_socket); |
|
WSACleanup(); |
|
return; |
|
} |
|
} |
|
|
|
char* |
|
processRequest(char* request) |
|
{ |
|
char* response = (char *)"> "; |
|
|
|
int result = luaL_loadbuffer(luaState, request, strlen(request), nullptr); |
|
|
|
if (result == LUA_OK) |
|
{ |
|
result = lua_pcall(luaState, 0, LUA_MULTRET, 0); |
|
if (result != LUA_OK) |
|
{ |
|
response = (char *)"Error.\n> "; // pcall failed |
|
} |
|
} |
|
else |
|
{ |
|
response = (char *)"Error.\n> "; // loadbuffer failed |
|
} |
|
|
|
return response; |
|
} |
|
|
|
DWORD WINAPI |
|
runMain(LPVOID lpParam) |
|
{ |
|
configNetwork(m_socket, server); |
|
|
|
client_addr_len = sizeof(client_addr); |
|
|
|
luaState = luaL_newstate(); |
|
luaL_openlibs(luaState); |
|
|
|
cout << "Lua Server: Wait for clients' requests.\n"; |
|
|
|
|
|
for (;;) |
|
{ |
|
memset(sendBuff, 0, sizeof(sendBuff)); |
|
memset(recvBuff, 0, sizeof(recvBuff)); |
|
|
|
bytesRecv = recvfrom(m_socket, recvBuff, 255, 0, &client_addr, &client_addr_len); |
|
if (SOCKET_ERROR == bytesRecv) |
|
{ |
|
cout << "Time Server: Error at recvfrom(): " << WSAGetLastError() << endl; |
|
closesocket(m_socket); |
|
WSACleanup(); |
|
return 0; |
|
} |
|
|
|
recvBuff[bytesRecv-1] = '\0'; |
|
cout << "Received: " << bytesRecv << " bytes of \"" << recvBuff << "\" message.\n"; |
|
|
|
if (strcmp(recvBuff,"quit") == 0 ) |
|
break; |
|
|
|
|
|
char* response = processRequest(recvBuff); |
|
strcpy(sendBuff, response); |
|
//delete response; |
|
|
|
bytesSent = sendto(m_socket, sendBuff, (int)strlen(sendBuff), 0, (const sockaddr *)&client_addr, client_addr_len); |
|
if (SOCKET_ERROR == bytesSent) |
|
{ |
|
cout << "Lua Server: Error at sendto(): " << WSAGetLastError() << endl; |
|
closesocket(m_socket); |
|
WSACleanup(); |
|
return 0; |
|
} |
|
|
|
cout << "Sent: " << bytesSent << "\\" << strlen(sendBuff) << " bytes of \"" << sendBuff << "\" message.\n"; |
|
|
|
Sleep(100); |
|
} |
|
|
|
closesocket(m_socket); |
|
WSACleanup(); |
|
lua_close(luaState); |
|
|
|
return 0; |
|
} |
|
|
|
BOOL APIENTRY DllMain( HMODULE hModule, |
|
DWORD dwReason, |
|
LPVOID lpReserved |
|
) |
|
{ |
|
switch (dwReason) |
|
{ |
|
case DLL_PROCESS_ATTACH: |
|
HANDLE hThread = CreateThread(NULL, 0, &runMain, NULL, 0, NULL); |
|
CloseHandle(hThread); |
|
break; |
|
} |
|
return TRUE; |
|
} |