GEMS parallel lua connection
/* | |
* Copyright (C) 2002-2013 The DOSBox Team | |
* | |
* This program is free software; you can redistribute it and/or modify | |
* it under the terms of the GNU General Public License as published by | |
* the Free Software Foundation; either version 2 of the License, or | |
* (at your option) any later version. | |
* | |
* This program is distributed in the hope that it will be useful, | |
* but WITHOUT ANY WARRANTY; without even the implied warranty of | |
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
* GNU General Public License for more details. | |
* | |
* You should have received a copy of the GNU General Public License | |
* along with this program; if not, write to the Free Software | |
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. | |
*/ | |
// include guard | |
#ifndef DOSBOX_GEMSLPT_H | |
#define DOSBOX_GEMSLPT_H | |
#include "dosbox.h" | |
#include "parport.h" | |
#include <winsock2.h> | |
class CGemsLPT : public CParallel { | |
public: | |
CGemsLPT (Bitu nr, Bit8u initIrq, CommandLine* cmd); | |
~CGemsLPT(); | |
bool InstallationSuccessful; // check after constructing. If | |
// something was wrong, delete it right away. | |
bool socketOpen; | |
SOCKET socket; | |
std::string name; // name of the thing to open | |
bool OpenFile(); | |
Bitu Read_PR(); | |
Bitu Read_COM(); | |
Bitu Read_SR(); | |
Bit8u datareg; | |
Bit8u controlreg; | |
void Write_PR(Bitu); | |
void Write_CON(Bitu); | |
void Write_IOSEL(Bitu); | |
bool Putchar(Bit8u); | |
virtual void handleUpperEvent(Bit16u type); | |
}; | |
#endif // include guard |
/* | |
* Copyright (C) 2002-2013 The DOSBox Team | |
* | |
* This program is free software; you can redistribute it and/or modify | |
* it under the terms of the GNU General Public License as published by | |
* the Free Software Foundation; either version 2 of the License, or | |
* (at your option) any later version. | |
* | |
* This program is distributed in the hope that it will be useful, | |
* but WITHOUT ANY WARRANTY; without even the implied warranty of | |
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
* GNU General Public License for more details. | |
* | |
* You should have received a copy of the GNU General Public License | |
* along with this program; if not, write to the Free Software | |
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. | |
*/ | |
#include "dosbox.h" | |
#include "parport.h" | |
#include "gemslpt.h" | |
#include "callback.h" | |
#include "pic.h" | |
#include "hardware.h" //OpenCaptureFile | |
#include <stdio.h> | |
#include <windows.h> | |
#include <winsock2.h> | |
#include <ws2tcpip.h> | |
SOCKET OpenSocket() | |
{ | |
WSADATA wsaData; | |
SOCKET ConnectSocket = INVALID_SOCKET; | |
struct addrinfo *result = NULL, | |
*ptr = NULL, | |
hints; | |
int iResult; | |
// Initialize Winsock | |
iResult = WSAStartup(MAKEWORD(2,2), &wsaData); | |
if (iResult != 0) { | |
LOG_MSG("GEMS parallel: WSAStartup failed with error: %d", iResult); | |
return INVALID_SOCKET; | |
} | |
ZeroMemory( &hints, sizeof(hints) ); | |
hints.ai_family = AF_UNSPEC; | |
hints.ai_socktype = SOCK_STREAM; | |
hints.ai_protocol = IPPROTO_TCP; | |
// Resolve the server address and port | |
iResult = getaddrinfo("127.0.0.1", "5000", &hints, &result); | |
if ( iResult != 0 ) { | |
LOG_MSG("GEMS parallel: getaddrinfo failed with error: %d", iResult); | |
WSACleanup(); | |
return INVALID_SOCKET; | |
} | |
// Attempt to connect to an address until one succeeds | |
for(ptr=result; ptr != NULL ;ptr=ptr->ai_next) { | |
// Create a SOCKET for connecting to server | |
ConnectSocket = socket(ptr->ai_family, ptr->ai_socktype, | |
ptr->ai_protocol); | |
if (ConnectSocket == INVALID_SOCKET) { | |
LOG_MSG("GEMS parallel: socket failed with error: %ld", WSAGetLastError()); | |
freeaddrinfo(result); | |
WSACleanup(); | |
return INVALID_SOCKET; | |
} | |
// Connect to server. | |
iResult = connect( ConnectSocket, ptr->ai_addr, (int)ptr->ai_addrlen); | |
if (iResult == SOCKET_ERROR) { | |
closesocket(ConnectSocket); | |
ConnectSocket = INVALID_SOCKET; | |
continue; | |
} | |
break; | |
} | |
freeaddrinfo(result); | |
if (ConnectSocket == INVALID_SOCKET) { | |
LOG_MSG("GEMS parallel: Unable to connect to server!"); | |
WSACleanup(); | |
return INVALID_SOCKET; | |
} | |
return ConnectSocket; | |
} | |
CGemsLPT::CGemsLPT (Bitu nr, Bit8u initIrq, CommandLine* cmd) | |
:CParallel (cmd, nr,initIrq) { | |
socketOpen = false; | |
InstallationSuccessful = true; | |
controlreg=0; | |
LOG_MSG("GEMS Parallel port started %08X",nr); | |
} | |
CGemsLPT::~CGemsLPT () | |
{ | |
// close socket | |
if(socketOpen) | |
{ | |
closesocket(socket); | |
WSACleanup(); | |
} | |
// remove tick handler | |
removeEvent(0); | |
} | |
bool CGemsLPT::Putchar(Bit8u val) | |
{ | |
// write to file (or not) | |
if(!socketOpen) | |
{ | |
socket = OpenSocket(); | |
if (socket != INVALID_SOCKET) | |
socketOpen = true; | |
} | |
if (!socketOpen) | |
return false; | |
int iResult = send( socket, (const char*)&val, 1, 0 ); | |
if (iResult == SOCKET_ERROR) | |
{ | |
LOG_MSG("GEMS parallel: send failed with error: %d", WSAGetLastError()); | |
closesocket(socket); | |
WSACleanup(); | |
socketOpen = false; | |
return 0; | |
} | |
return 1; | |
} | |
Bitu CGemsLPT::Read_PR() | |
{ | |
return datareg; | |
} | |
Bitu CGemsLPT::Read_COM() | |
{ | |
return 0; | |
} | |
Bitu CGemsLPT::Read_SR() | |
{ | |
return 0; | |
} | |
void CGemsLPT::Write_PR(Bitu val) | |
{ | |
datareg = (Bit8u)val; | |
} | |
void CGemsLPT::Write_CON(Bitu val) | |
{ | |
controlreg=val; | |
} | |
void CGemsLPT::Write_IOSEL(Bitu val) | |
{ | |
} | |
void CGemsLPT::handleUpperEvent(Bit16u type) | |
{ | |
} | |
local socket = require("socket"); | |
local s = socket.bind("*",5000); | |
--local rep = io.open("gems_connection.log","wb"); | |
s:settimeout(0); | |
local clients = {}; | |
local byte = 0; | |
local readed = 0; | |
gens.speedmode("normal"); | |
gens.registerbefore(function() | |
s:settimeout(0); | |
local o = s:accept(); | |
if (o ~= nil )then | |
oc = {}; | |
oc.socket = o; | |
o:settimeout(0); | |
oc.status = 0; | |
local i,p = o:getpeername(); | |
print("Connected: "..i..":"..p); | |
table.insert(clients,oc); | |
end | |
local was = true; | |
while was do | |
was = false; | |
n = table.getn(clients); | |
for i=1,n do | |
if (clients[i].status == 2) then | |
local ip, p = clients[i].socket:getpeername(); | |
table.remove(clients,i); | |
print ("Disconected: "..ip..":"..p); | |
was = true; | |
break; | |
end | |
end | |
end | |
end) | |
memory.registerexec(0x2F26,1, function(address,size) | |
local n = table.getn(clients); | |
local i; | |
if (readed == 0) then | |
for i=1,n do | |
clients[i].socket:settimeout(0); | |
byte = clients[i].socket:receive(1); | |
if (byte ~= nil) then | |
--rep:write(string.format("%02X",string.byte(byte)).."\n"); | |
--rep:flush(); | |
readed = 1; | |
break; | |
end | |
end | |
end | |
local v = memory.getregister('d0'); | |
if (readed == 0) then | |
memory.setregister('d0',AND(v,0xFFFFFF00)+0x10); | |
else | |
memory.setregister('d0',AND(v,0xFFFFFF00)); | |
end | |
end) | |
memory.registerexec(0x1192,1, function(address,size) | |
local v = memory.getregister('d0'); | |
memory.setregister('d0',AND(v,0xFFFFFF00)+string.byte(byte)); | |
readed = 0; | |
end) | |
--[[memory.registerexec(0x1248,1, function(address,size) | |
rep:write(string.format("Result: %02X",memory.getregister('d0')).."\n"); | |
end) | |
memory.registerwrite(0,0x200000, function(address,size) | |
rep:write(string.format("Write at: %06X PC: %06X",address,memory.getregister('pc')).."\n"); | |
rep:flush(); | |
end) | |
local cmds = { | |
[0] = 'cmdnoteon', | |
[1] = 'cmdnoteoff', | |
[2] = 'cmdpchange', | |
[3] = 'cmdpupdate', | |
[4] = 'cmdpbend', | |
[5] = 'cmdtempo', | |
[6] = 'cmdenv', | |
[7] = 'cmdretrig', | |
[8] = '?', | |
[9] = '?', | |
[10] = '?', | |
[11] = '?', | |
[12] = 'cmdpause', | |
[13] = 'cmdresume', | |
[14] = 'cmdsussw', | |
[15] = '?', | |
[16] = 'cmdstartseq', | |
[17] = '?', | |
[18] = 'cmdstopseq', | |
[19] = 'cmdreload', | |
[20] = 'cmdsetprio', | |
[21] = '?', | |
[22] = 'cmdstopall', | |
[23] = '?', | |
[24] = '?', | |
[25] = '?', | |
[26] = 'cmdsamprate', | |
[27] = 'cmdstore', | |
[28] = 'cmdlockch', | |
[29] = 'cmdunlockch', | |
[30] = '?', | |
[31] = 'cmdvolume', | |
[254] = 'drawalltext' | |
}; | |
memory.registerexec(0x1AEE,1,function(address,size) | |
local d1 = memory.getregister('d1'); | |
rep:write(string.format("CMD: %d ",d1)..cmds[d1].."\n"); | |
end) | |
]] |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment