add pcap code for Linux. fix bugs.

This commit is contained in:
StapleButter 2019-03-26 02:53:17 +01:00
parent f86782cc2e
commit c43574207a
4 changed files with 89 additions and 34 deletions

View File

@ -168,7 +168,7 @@ void Open()
}
LAN_Socket::Init();
haspcap = LAN_PCap::Init();
haspcap = LAN_PCap::Init(false);
opened = true;
win = uiNewWindow("Wifi settings - melonDS", 400, 100, 0, 0, 0);
@ -253,10 +253,10 @@ void Open()
}
uiComboboxSetSelected(cmAdapterList, sel);
UpdateAdapterInfo();
UpdateAdapterControls();
uiCheckboxSetChecked(cbDirectLAN, Config::DirectLAN);
if (!haspcap) uiControlDisable(uiControl(cbDirectLAN));
UpdateAdapterControls();
uiControlShow(uiControl(win));
}

View File

@ -30,7 +30,10 @@
#ifdef __WIN32__
#include <iphlpapi.h>
#else
// Linux includes go here
#include <sys/types.h>
#include <ifaddrs.h>
#include <netinet/in.h>
#include <linux/if_packet.h>
#endif
@ -101,40 +104,42 @@ bool TryLoadPCap(void* lib)
return true;
}
bool Init()
bool Init(bool open_adapter)
{
// TODO: how to deal with cases where an adapter is unplugged or changes config??
if (PCapLib) return true;
if (!PCapLib)
{
PCapLib = NULL;
for (int i = 0; PCapLibNames[i]; i++)
{
void* lib = SDL_LoadObject(PCapLibNames[i]);
if (!lib) continue;
if (!TryLoadPCap(lib))
{
SDL_UnloadObject(lib);
continue;
}
printf("PCap: lib %s, init successful\n", PCapLibNames[i]);
PCapLib = lib;
break;
}
if (PCapLib == NULL)
{
printf("PCap: init failed\n");
return false;
}
}
PCapLib = NULL;
PCapAdapter = NULL;
PacketLen = 0;
RXNum = 0;
NumAdapters = 0;
for (int i = 0; PCapLibNames[i]; i++)
{
void* lib = SDL_LoadObject(PCapLibNames[i]);
if (!lib) continue;
if (!TryLoadPCap(lib))
{
SDL_UnloadObject(lib);
continue;
}
printf("PCap: lib %s, init successful\n", PCapLibNames[i]);
PCapLib = lib;
break;
}
if (PCapLib == NULL)
{
printf("PCap: init failed\n");
return false;
}
char errbuf[PCAP_ERRBUF_SIZE];
int ret;
@ -158,11 +163,19 @@ bool Init()
{
adata->Internal = dev;
#ifdef __WIN32__
// hax
int len = strlen(dev->name);
len -= 12; if (len > 127) len = 127;
strncpy(adata->DeviceName, &dev->name[12], len);
adata->DeviceName[len] = '\0';
#else
strncpy(adata->DeviceName, dev->name, 127);
adata->DeviceName[127] = '\0';
strncpy(adata->FriendlyName, adata->DeviceName, 127);
adata->FriendlyName[127] = '\0';
#endif // __WIN32__
dev = dev->next;
adata++;
@ -181,7 +194,7 @@ bool Init()
}
if (uret != ERROR_SUCCESS)
{
printf("GetAdaptersAddresses() shat itself: %08X\n", ret);
printf("GetAdaptersAddresses() shat itself: %08X\n", uret);
return false;
}
@ -217,7 +230,7 @@ bool Init()
if (sa->sa_family == AF_INET)
{
struct in_addr sa4 = ((sockaddr_in*)sa)->sin_addr;
memcpy(adata->IP_v4, &sa4.S_un.S_addr, 4);
memcpy(adata->IP_v4, &sa4, 4);
}
ipaddr = ipaddr->Next;
@ -231,10 +244,52 @@ bool Init()
#else
// TODO
struct ifaddrs* addrs;
if (getifaddrs(&addrs) != 0)
{
printf("getifaddrs() shat itself :(\n");
return false;
}
for (int i = 0; i < NumAdapters; i++)
{
adata = &Adapters[i];
struct ifaddrs* curaddr = addrs;
while (curaddr)
{
if (strcmp(curaddr->ifa_name, adata->DeviceName))
{
curaddr = curaddr->ifa_next;
continue;
}
if (!curaddr->ifa_addr) continue;
u16 af = curaddr->ifa_addr->sa_family;
if (af == AF_INET)
{
struct sockaddr_in* sa = (sockaddr_in*)curaddr->ifa_addr;
memcpy(adata->IP_v4, &sa->sin_addr, 4);
}
else if (af == AF_PACKET)
{
struct sockaddr_ll* sa = (sockaddr_ll*)curaddr->ifa_addr;
if (sa->sll_halen != 6)
printf("weird MAC length %d for %s\n", sa->sll_halen, curaddr->ifa_name);
else
memcpy(adata->MAC, sa->sll_addr, 6);
}
curaddr = curaddr->ifa_next;
}
}
freeifaddrs(addrs);
#endif // __WIN32__
if (!open_adapter) return true;
if (PCapAdapter) pcap_close(PCapAdapter);
// open pcap device
PCapAdapterData = &Adapters[0];
for (int i = 0; i < NumAdapters; i++)
@ -247,7 +302,7 @@ bool Init()
PCapAdapter = pcap_open_live(dev->name, 2048, PCAP_OPENFLAG_PROMISCUOUS, 1, errbuf);
if (!PCapAdapter)
{
printf("PCap: failed to open adapter\n");
printf("PCap: failed to open adapter %s\n", errbuf);
return false;
}

View File

@ -42,7 +42,7 @@ extern AdapterData* Adapters;
extern int NumAdapters;
bool Init();
bool Init(bool open_adapter);
void DeInit();
int SendPacket(u8* data, int len);

View File

@ -264,7 +264,7 @@ bool LAN_Init()
{
if (Config::DirectLAN)
{
if (!LAN_PCap::Init())
if (!LAN_PCap::Init(true))
return false;
}
else