get wifi beacons going
This commit is contained in:
parent
139ab069f5
commit
49fd6b1576
|
@ -391,10 +391,12 @@ void Reset()
|
|||
{
|
||||
u32 gamecode = *(u32*)&NDSCart::CartROM[0xC];
|
||||
gamecode &= 0xFFFFFF;
|
||||
if (gamecode == 0x4D5341) // ASMx / Super Mario 64 DS
|
||||
if (gamecode == 0x4D5341) // ASMx / Super Mario 64 DS
|
||||
Version = 1;
|
||||
else if (gamecode == 0x595241) // ARYx / Rayman DS
|
||||
Version = 2;
|
||||
else if (gamecode == 0x475541) // AUGx / Need for Speed Underground
|
||||
Version = 2;
|
||||
}
|
||||
|
||||
NDS::ScheduleEvent(NDS::Event_HLE_SoundCmd, true, 174592, Process, 1);
|
||||
|
|
|
@ -21,6 +21,7 @@
|
|||
#include "../HLE.h"
|
||||
#include "../FIFO.h"
|
||||
#include "../SPI.h"
|
||||
#include "../GPU.h"
|
||||
|
||||
#include "IPC.h"
|
||||
#include "Wifi.h"
|
||||
|
@ -43,13 +44,26 @@ struct IPCReply
|
|||
|
||||
FIFO<IPCReply, 16> IPCReplyQueue;
|
||||
|
||||
s32 TimerError;
|
||||
|
||||
u32 SharedMem[2];
|
||||
|
||||
u8 MAC[6];
|
||||
u16 TXSeqNo;
|
||||
u64 Timestamp;
|
||||
u16 Channel;
|
||||
|
||||
u8 RXBuffer[2048];
|
||||
|
||||
u16 BeaconCount;
|
||||
u16 BeaconInterval;
|
||||
u8 BeaconFrame[1024];
|
||||
u8* BeaconTagDD;
|
||||
|
||||
u16 HostScanCount;
|
||||
u32 HostScanBuffer;
|
||||
|
||||
void ScheduleTimer(bool first);
|
||||
void WifiIPCReply(u16 cmd, u16 status, int numextra=0, u16* extra=nullptr);
|
||||
|
||||
|
||||
|
@ -57,20 +71,271 @@ void Reset()
|
|||
{
|
||||
IPCReplyQueue.Clear();
|
||||
|
||||
TimerError = 0;
|
||||
|
||||
SharedMem[0] = 0;
|
||||
SharedMem[1] = 0;
|
||||
|
||||
u8* mac = SPI_Firmware::GetWifiMAC();
|
||||
memcpy(MAC, mac, 6);
|
||||
TXSeqNo = 0;
|
||||
Timestamp = 0;
|
||||
Channel = 0;
|
||||
|
||||
memset(RXBuffer, 0, sizeof(RXBuffer));
|
||||
|
||||
BeaconCount = 0;
|
||||
BeaconInterval = 0;
|
||||
memset(BeaconFrame, 0, sizeof(BeaconFrame));
|
||||
BeaconTagDD = nullptr;
|
||||
|
||||
HostScanCount = 0;
|
||||
HostScanBuffer = 0;
|
||||
|
||||
u16 chanmask = 0x2082;
|
||||
NDS::ARM7Write16(0x027FFCFA, chanmask);
|
||||
}
|
||||
|
||||
|
||||
void SendHostBeacon()
|
||||
{printf("HOST BEACON\n");
|
||||
*(u16*)&BeaconFrame[12 + 22] = (TXSeqNo << 4);
|
||||
TXSeqNo++;
|
||||
|
||||
*(u64*)&BeaconFrame[12 + 24] = Timestamp;
|
||||
|
||||
u16 syncval = ((GPU::VCount * 0x7F) - (Timestamp * 2)) >> 7;
|
||||
*(u16*)&BeaconTagDD[8] = syncval;
|
||||
|
||||
Platform::MP_SendPacket(BeaconFrame, 12+*(u16*)&BeaconFrame[10], Timestamp);
|
||||
}
|
||||
|
||||
bool ReceiveHostBeacon()
|
||||
{
|
||||
int rxlen = Platform::MP_RecvPacket(RXBuffer, nullptr);
|
||||
if (rxlen <= (12+24)) return false;
|
||||
|
||||
u16 framelen = *(u16*)&RXBuffer[10];
|
||||
if (framelen != rxlen-12)
|
||||
{
|
||||
//Log(LogLevel::Error, "bad frame length %d/%d\n", framelen, rxlen-12);
|
||||
return false;
|
||||
}
|
||||
|
||||
u16 framectl = *(u16*)&RXBuffer[12+0];
|
||||
if ((framectl & 0xE7FF) != 0x0080) return false;
|
||||
|
||||
u8* tagpos = &RXBuffer[12+24+8+2+2];
|
||||
u8* frameend = &RXBuffer[rxlen];
|
||||
while (tagpos < frameend)
|
||||
{
|
||||
u8 tag = *tagpos++;
|
||||
u8 len = *tagpos++;
|
||||
|
||||
if (tag == 0xDD)
|
||||
{
|
||||
u32 oui = *(u32*)tagpos;
|
||||
if (oui == 0x00BF0900)
|
||||
return true;
|
||||
}
|
||||
|
||||
tagpos += len;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
void HostScan()
|
||||
{
|
||||
bool res = ReceiveHostBeacon();
|
||||
if (res)
|
||||
{
|
||||
// fill beacon info buffer
|
||||
|
||||
u16 buf_len = 0x41;
|
||||
|
||||
u8* dd_offset = nullptr;
|
||||
u16 dd_len = 0;
|
||||
|
||||
NDS::ARM7Write16(HostScanBuffer+0x02, RXBuffer[12]); // CHECKME
|
||||
NDS::ARM7Write16(HostScanBuffer+0x04, RXBuffer[12+10]);
|
||||
NDS::ARM7Write16(HostScanBuffer+0x06, RXBuffer[12+12]);
|
||||
NDS::ARM7Write16(HostScanBuffer+0x08, RXBuffer[12+14]);
|
||||
NDS::ARM7Write16(HostScanBuffer+0x2C, RXBuffer[12+24+8+2]);
|
||||
NDS::ARM7Write16(HostScanBuffer+0x32, RXBuffer[12+24+8]);
|
||||
|
||||
NDS::ARM7Write16(HostScanBuffer+0x0A, 0);
|
||||
NDS::ARM7Write16(HostScanBuffer+0x34, 0);
|
||||
NDS::ARM7Write16(HostScanBuffer+0x38, 0);
|
||||
NDS::ARM7Write16(HostScanBuffer+0x3C, 0);
|
||||
NDS::ARM7Write16(HostScanBuffer+0x3E, 0);
|
||||
|
||||
u16 rxlen = *(u16*)&RXBuffer[10] + 12;
|
||||
u8* tagpos = &RXBuffer[12+24+8+2+2];
|
||||
u8* frameend = &RXBuffer[rxlen];
|
||||
while (tagpos < frameend)
|
||||
{
|
||||
u8 tag = *tagpos++;
|
||||
u8 len = *tagpos++;
|
||||
|
||||
switch (tag)
|
||||
{
|
||||
case 0x00: // SSID
|
||||
{
|
||||
u8 ssidlen = len;
|
||||
if (ssidlen > 0x20) ssidlen = 0x20;
|
||||
|
||||
NDS::ARM7Write16(HostScanBuffer+0x0A, ssidlen);
|
||||
for (int i = 0; i < ssidlen; i++)
|
||||
NDS::ARM7Write8(HostScanBuffer+0xC+i, tagpos[i]);
|
||||
}
|
||||
break;
|
||||
|
||||
case 0x01: // supported rates
|
||||
{
|
||||
u16 mask1 = 0;
|
||||
u16 mask2 = 0;
|
||||
|
||||
for (int i = 0; i < len; i++)
|
||||
{
|
||||
u8 val = tagpos[i];
|
||||
u16 bit;
|
||||
switch (val & 0x7F)
|
||||
{
|
||||
case 0x02: bit = (1<<0); break;
|
||||
case 0x04: bit = (1<<1); break;
|
||||
case 0x0B: bit = (1<<2); break;
|
||||
case 0x0C: bit = (1<<3); break;
|
||||
case 0x12: bit = (1<<4); break;
|
||||
case 0x16: bit = (1<<5); break;
|
||||
case 0x30: bit = (1<<6); break;
|
||||
case 0x48: bit = (1<<7); break;
|
||||
case 0x60: bit = (1<<8); break;
|
||||
case 0x6C: bit = (1<<9); break;
|
||||
default: bit = (1<<15); break;
|
||||
}
|
||||
|
||||
if (val & 0x80) mask1 |= bit;
|
||||
mask2 |= bit;
|
||||
}
|
||||
|
||||
NDS::ARM7Write16(HostScanBuffer+0x2E, mask1);
|
||||
NDS::ARM7Write16(HostScanBuffer+0x30, mask2);
|
||||
}
|
||||
break;
|
||||
|
||||
case 0x03: // channel
|
||||
{
|
||||
if (len != 1) break;
|
||||
|
||||
NDS::ARM7Write16(HostScanBuffer+0x36, tagpos[0]);
|
||||
}
|
||||
break;
|
||||
|
||||
case 0x04: // CF parameters
|
||||
{
|
||||
if (len != 6) break;
|
||||
|
||||
NDS::ARM7Write16(HostScanBuffer+0x38, tagpos[1]);
|
||||
}
|
||||
break;
|
||||
|
||||
case 0x05: // TIM
|
||||
{
|
||||
if (len < 4) break;
|
||||
|
||||
NDS::ARM7Write16(HostScanBuffer+0x34, tagpos[1]);
|
||||
}
|
||||
break;
|
||||
|
||||
case 0xDD: // tag DD
|
||||
{
|
||||
// TODO count bad tag DD's
|
||||
if (len < 8) break;
|
||||
if (*(u32*)&tagpos[0] != 0x00BF0900) break;
|
||||
|
||||
dd_offset = &tagpos[8];
|
||||
dd_len = len - 8;
|
||||
|
||||
NDS::ARM7Write16(HostScanBuffer+0x3C, dd_len);
|
||||
for (int i = 0; i < dd_len; i++)
|
||||
NDS::ARM7Write8(HostScanBuffer+0x40+i, tagpos[8+i]);
|
||||
|
||||
buf_len += dd_len;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
tagpos += len;
|
||||
}
|
||||
|
||||
NDS::ARM7Write16(HostScanBuffer+0x00, (buf_len >> 1));
|
||||
|
||||
// fill reply buffer
|
||||
|
||||
WifiIPCReply(0xA, 0, dd_len, (u16*)dd_offset);
|
||||
}
|
||||
else if (HostScanCount == 0)
|
||||
{
|
||||
WifiIPCReply(0xA, 0);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void MSTimer(u32 param)
|
||||
{
|
||||
u16 status = NDS::ARM7Read16(SharedMem[1]);
|
||||
|
||||
Timestamp += 1024;
|
||||
|
||||
switch (status)
|
||||
{
|
||||
case 5: // scanning for host beacons
|
||||
{
|
||||
if (HostScanCount > 0)
|
||||
{
|
||||
HostScanCount--;
|
||||
HostScan();
|
||||
}
|
||||
|
||||
if (HostScanCount > 0)
|
||||
ScheduleTimer(false);
|
||||
}
|
||||
break;
|
||||
|
||||
case 7:
|
||||
case 9: // host comm
|
||||
{
|
||||
BeaconCount++;
|
||||
if (BeaconCount >= BeaconInterval)
|
||||
{
|
||||
BeaconCount = 0;
|
||||
SendHostBeacon();
|
||||
}
|
||||
|
||||
ScheduleTimer(false);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void ScheduleTimer(bool first)
|
||||
{
|
||||
if (first)
|
||||
{
|
||||
NDS::CancelEvent(NDS::Event_Wifi);
|
||||
TimerError = 0;
|
||||
}
|
||||
|
||||
s64 cycles = 33513982LL * 1024LL;
|
||||
cycles -= TimerError;
|
||||
s64 delay = (cycles + 999999LL) / 1000000LL;
|
||||
TimerError = (s32)((delay * 1000000LL) - cycles);
|
||||
|
||||
NDS::ScheduleEvent(NDS::Event_Wifi, !first, (s32)delay, MSTimer, 0);
|
||||
}
|
||||
|
||||
|
||||
void StartHostComm()
|
||||
{
|
||||
memset(BeaconFrame, 0xFF, sizeof(BeaconFrame));
|
||||
|
@ -84,6 +349,7 @@ void StartHostComm()
|
|||
u32 gameid = NDS::ARM7Read32(paramblock + 0x08);
|
||||
u16 streamcode = NDS::ARM7Read16(paramblock + 0x0C);
|
||||
|
||||
BeaconCount = 0;
|
||||
BeaconInterval = NDS::ARM7Read16(paramblock + 0x18);
|
||||
u16 channel = NDS::ARM7Read16(paramblock + 0x32);
|
||||
|
||||
|
@ -142,6 +408,7 @@ void StartHostComm()
|
|||
*ptr++ = 0x00;
|
||||
|
||||
// tag DD
|
||||
BeaconTagDD = ptr;
|
||||
*ptr++ = 0xDD; *ptr++ = (0x18 + dd_len);
|
||||
*(u32*)ptr = 0x00BF0900; ptr += 4;
|
||||
*(u16*)ptr = 0x000A; ptr += 2; // stepping (checkme)
|
||||
|
@ -167,7 +434,7 @@ void StartHostComm()
|
|||
len += 4;
|
||||
|
||||
// frame length
|
||||
*(u16*&)BeaconFrame[0xA] = len;
|
||||
*(u16*)&BeaconFrame[0xA] = len;
|
||||
}
|
||||
|
||||
|
||||
|
@ -215,6 +482,38 @@ void WifiIPCReply(u16 cmd, u16 status, int numextra, u16* extra)
|
|||
NDS::ARM7Write16(replybuf+0x2E, extra[2]);
|
||||
}
|
||||
}
|
||||
else if (cmd == 0xA)
|
||||
{
|
||||
if (numextra > 0)
|
||||
{
|
||||
NDS::ARM7Write16(replybuf+0x8, 5);
|
||||
NDS::ARM7Write16(replybuf+0x10, Channel);
|
||||
NDS::ARM7Write16(replybuf+0x12, 0);
|
||||
|
||||
// source MAC
|
||||
NDS::ARM7Write16(replybuf+0xA, *(u16*)&RXBuffer[12+10]);
|
||||
NDS::ARM7Write16(replybuf+0xC, *(u16*)&RXBuffer[12+12]);
|
||||
NDS::ARM7Write16(replybuf+0xE, *(u16*)&RXBuffer[12+14]);
|
||||
|
||||
NDS::ARM7Write16(replybuf+0x14, 0); // ???
|
||||
|
||||
NDS::ARM7Write16(replybuf+0x36, numextra);
|
||||
for (int i = 0; i < numextra; i+=2)
|
||||
{
|
||||
NDS::ARM7Write16(replybuf+0x38+i, extra[i>>1]);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
NDS::ARM7Write16(replybuf+0x8, 4);
|
||||
NDS::ARM7Write16(replybuf+0x10, Channel);
|
||||
NDS::ARM7Write16(replybuf+0x12, 0);
|
||||
}
|
||||
}
|
||||
else if (cmd == 0xE && status == 0)
|
||||
{
|
||||
NDS::ARM7Write16(replybuf+0x04, 0xA);
|
||||
}
|
||||
else
|
||||
{
|
||||
for (int i = 0; i < numextra; i++)
|
||||
|
@ -232,224 +531,262 @@ void WifiIPCReply(u16 cmd, u16 status, int numextra, u16* extra)
|
|||
void OnIPCRequest(u32 addr)
|
||||
{
|
||||
u16 cmd = NDS::ARM7Read16(addr);
|
||||
cmd &= ~0x8000;
|
||||
|
||||
/*printf("WIFI HLE: cmd %04X\n", cmd);
|
||||
for (u32 i = 0; i < 16; i++)
|
||||
if (cmd < 0x2E)
|
||||
{
|
||||
for (u32 j = 0; j < 16; j+=4)
|
||||
NDS::ARM7Write32(SharedMem[1]+0x4, 1);
|
||||
NDS::ARM7Write16(SharedMem[1]+0x2, cmd);
|
||||
|
||||
switch (cmd)
|
||||
{
|
||||
u32 varp = NDS::ARM7Read32(addr+(i*16)+j);
|
||||
printf("%08X ", varp);
|
||||
}
|
||||
printf("\n");
|
||||
}*/
|
||||
|
||||
switch (cmd)
|
||||
{
|
||||
case 0x0: // init
|
||||
{
|
||||
SharedMem[0] = NDS::ARM7Read32(addr+0x4);
|
||||
SharedMem[1] = NDS::ARM7Read32(addr+0x8);
|
||||
u32 respbuf = NDS::ARM7Read32(addr+0xC);
|
||||
|
||||
NDS::ARM7Write32(SharedMem[0], SharedMem[1]);
|
||||
NDS::ARM7Write32(SharedMem[0]+0x8, respbuf);
|
||||
|
||||
// TODO init the sharedmem buffers
|
||||
// TODO other shito too!!
|
||||
|
||||
NDS::ARM7Write16(SharedMem[1], 2);
|
||||
|
||||
WifiIPCReply(0x0, 0);
|
||||
}
|
||||
break;
|
||||
|
||||
case 0x2: // deinit
|
||||
{
|
||||
u16 status = NDS::ARM7Read16(SharedMem[1]);
|
||||
if (status == 2)
|
||||
case 0x0: // init
|
||||
{
|
||||
NDS::ARM7Write16(SharedMem[1], 0);
|
||||
WifiIPCReply(0x2, 0);
|
||||
SharedMem[0] = NDS::ARM7Read32(addr+0x4);
|
||||
SharedMem[1] = NDS::ARM7Read32(addr+0x8);
|
||||
u32 respbuf = NDS::ARM7Read32(addr+0xC);
|
||||
|
||||
NDS::ARM7Write32(SharedMem[0], SharedMem[1]);
|
||||
NDS::ARM7Write32(SharedMem[0]+0x8, respbuf);
|
||||
|
||||
// TODO init the sharedmem buffers
|
||||
// TODO other shito too!!
|
||||
|
||||
NDS::ARM7Write16(SharedMem[1], 2);
|
||||
Platform::MP_Begin();
|
||||
|
||||
WifiIPCReply(0x0, 0);
|
||||
}
|
||||
else
|
||||
break;
|
||||
|
||||
case 0x2: // deinit
|
||||
{
|
||||
WifiIPCReply(0x2, 3);
|
||||
u16 status = NDS::ARM7Read16(SharedMem[1]);
|
||||
if (status == 2)
|
||||
{
|
||||
NDS::ARM7Write16(SharedMem[1], 0);
|
||||
Platform::MP_End();
|
||||
WifiIPCReply(0x2, 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
WifiIPCReply(0x2, 3);
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
break;
|
||||
|
||||
case 0x3: // enable
|
||||
{
|
||||
SharedMem[0] = NDS::ARM7Read32(addr+0x4);
|
||||
SharedMem[1] = NDS::ARM7Read32(addr+0x8);
|
||||
u32 respbuf = NDS::ARM7Read32(addr+0xC);
|
||||
|
||||
NDS::ARM7Write32(SharedMem[0], SharedMem[1]);
|
||||
NDS::ARM7Write32(SharedMem[0]+0x8, respbuf);
|
||||
|
||||
// TODO init the sharedmem buffers
|
||||
|
||||
NDS::ARM7Write16(SharedMem[1], 1);
|
||||
|
||||
WifiIPCReply(0x3, 0);
|
||||
}
|
||||
break;
|
||||
|
||||
case 0x4: // disable
|
||||
{
|
||||
u16 status = NDS::ARM7Read16(SharedMem[1]);
|
||||
if (status == 1)
|
||||
case 0x3: // enable
|
||||
{
|
||||
NDS::ARM7Write16(SharedMem[1], 0);
|
||||
WifiIPCReply(0x4, 0);
|
||||
SharedMem[0] = NDS::ARM7Read32(addr+0x4);
|
||||
SharedMem[1] = NDS::ARM7Read32(addr+0x8);
|
||||
u32 respbuf = NDS::ARM7Read32(addr+0xC);
|
||||
|
||||
NDS::ARM7Write32(SharedMem[0], SharedMem[1]);
|
||||
NDS::ARM7Write32(SharedMem[0]+0x8, respbuf);
|
||||
|
||||
// TODO init the sharedmem buffers
|
||||
|
||||
NDS::ARM7Write16(SharedMem[1], 1);
|
||||
|
||||
WifiIPCReply(0x3, 0);
|
||||
}
|
||||
else
|
||||
break;
|
||||
|
||||
case 0x4: // disable
|
||||
{
|
||||
WifiIPCReply(0x4, 3);
|
||||
u16 status = NDS::ARM7Read16(SharedMem[1]);
|
||||
if (status == 1)
|
||||
{
|
||||
NDS::ARM7Write16(SharedMem[1], 0);
|
||||
WifiIPCReply(0x4, 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
WifiIPCReply(0x4, 3);
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
break;
|
||||
|
||||
case 0x7: // set host param
|
||||
{
|
||||
// PARAM BLOCK FORMAT
|
||||
// offset size desc.
|
||||
// 00 4 tag DD: pointer to extra data
|
||||
// 04 2 tag DD: length of extra data (tag DD length minus 0x18)
|
||||
// 06 2
|
||||
// 08 6 SSID bytes 0..5 (SSID is 32 bytes, rest is all zeroes)
|
||||
// 08 4 tag DD: game ID
|
||||
// 0C 2 tag DD: stream code
|
||||
// 0E 2 tag DD: beacon type bit0
|
||||
// 10 2 ???
|
||||
// 12 2 tag DD: beacon type bit1
|
||||
// 14 2 tag DD: beacon type bit2
|
||||
// 16 2 tag DD: beacon type bit3
|
||||
// 18 2 beacon interval
|
||||
// 32 2 channel #
|
||||
// 34 2 tag DD: CMD data length
|
||||
// 36 2 tag DD: REPLY data length
|
||||
|
||||
// for now, the param block is just copied to sharedmem
|
||||
|
||||
u32 paramblock = NDS::ARM7Read32(addr+0x4);
|
||||
u32 dst = SharedMem[1] + 0xE8;
|
||||
for (u32 i = 0; i < 0x40; i+=4)
|
||||
case 0x7: // set host param
|
||||
{
|
||||
NDS::ARM7Write32(dst+i, NDS::ARM7Read32(paramblock+i));
|
||||
// PARAM BLOCK FORMAT
|
||||
// offset size desc.
|
||||
// 00 4 tag DD: pointer to extra data
|
||||
// 04 2 tag DD: length of extra data (tag DD length minus 0x18)
|
||||
// 06 2
|
||||
// 08 6 SSID bytes 0..5 (SSID is 32 bytes, rest is all zeroes)
|
||||
// 08 4 tag DD: game ID
|
||||
// 0C 2 tag DD: stream code
|
||||
// 0E 2 tag DD: beacon type bit0
|
||||
// 10 2 ???
|
||||
// 12 2 tag DD: beacon type bit1
|
||||
// 14 2 tag DD: beacon type bit2
|
||||
// 16 2 tag DD: beacon type bit3
|
||||
// 18 2 beacon interval
|
||||
// 32 2 channel #
|
||||
// 34 2 tag DD: CMD data length
|
||||
// 36 2 tag DD: REPLY data length
|
||||
|
||||
// for now, the param block is just copied to sharedmem
|
||||
|
||||
u32 paramblock = NDS::ARM7Read32(addr+0x4);
|
||||
u32 dst = SharedMem[1] + 0xE8;
|
||||
for (u32 i = 0; i < 0x40; i+=4)
|
||||
{
|
||||
NDS::ARM7Write32(dst+i, NDS::ARM7Read32(paramblock+i));
|
||||
}
|
||||
|
||||
WifiIPCReply(0x7, 0);
|
||||
}
|
||||
break;
|
||||
|
||||
WifiIPCReply(0x7, 0);
|
||||
}
|
||||
break;
|
||||
|
||||
case 0x8: // start host comm
|
||||
{
|
||||
u16 status = NDS::ARM7Read16(SharedMem[1]);
|
||||
if (status != 2)
|
||||
case 0x8: // start host comm
|
||||
{
|
||||
u16 ext = 0;
|
||||
WifiIPCReply(0x8, 3, 1, &ext);
|
||||
break;
|
||||
u16 status = NDS::ARM7Read16(SharedMem[1]);
|
||||
if (status != 2)
|
||||
{
|
||||
u16 ext = 0;
|
||||
WifiIPCReply(0x8, 3, 1, &ext);
|
||||
break;
|
||||
}
|
||||
|
||||
StartHostComm();
|
||||
|
||||
NDS::ARM7Write16(SharedMem[1], 7);
|
||||
|
||||
u16 extra[3];
|
||||
extra[0] = 0;
|
||||
extra[1] = NDS::ARM7Read16(SharedMem[1]+0xE8+0x34);
|
||||
extra[2] = NDS::ARM7Read16(SharedMem[1]+0xE8+0x36);
|
||||
WifiIPCReply(0x8, 0, 3, extra);
|
||||
|
||||
NDS::ARM7Write16(SharedMem[1]+0xC2, 1);
|
||||
ScheduleTimer(true);
|
||||
}
|
||||
break;
|
||||
|
||||
StartHostComm();
|
||||
|
||||
NDS::ARM7Write16(SharedMem[1], 7);
|
||||
|
||||
u16 extra[3];
|
||||
extra[0] = 0;
|
||||
extra[1] = NDS::ARM7Read16(SharedMem[1]+0xE8+0x34);
|
||||
extra[2] = NDS::ARM7Read16(SharedMem[1]+0xE8+0x36);
|
||||
WifiIPCReply(0x8, 0, 3, extra);
|
||||
|
||||
NDS::ARM7Write16(SharedMem[1]+0xC2, 1);
|
||||
}
|
||||
break;
|
||||
|
||||
case 0xA: // start host scan
|
||||
{
|
||||
// scan for viable host beacons
|
||||
// timeout: ~20480*64 cycles (with value 0x22)
|
||||
//
|
||||
// COMMAND BUFFER
|
||||
// offset size desc.
|
||||
// 04 4 pointer to beacon data buffer
|
||||
// 08 2 timeout in milliseconds
|
||||
// 0A 6 desired source MAC? seen set to FFFFFFFFFFFF
|
||||
//
|
||||
// REPLY BUFFER
|
||||
// offset size desc.
|
||||
// 08 2 ??? seen set to 4
|
||||
// 0A 6 source MAC from beacon (zero if none)
|
||||
// 10 ? channel
|
||||
// 36 2 length of tag DD data (minus first 8 bytes) (zero if none)
|
||||
// 38 X tag DD data (minus first 8 bytes)
|
||||
//
|
||||
// BEACON DATA BUFFER
|
||||
// offset size desc.
|
||||
// 00 2 buffer length in halfwords ((tag DD length - 8 + 0x41) >> 1)
|
||||
// 02 2 frame control? AND 0xFF -- 0080
|
||||
// 04 6 source MAC
|
||||
// 0A 2 SSID length (0 if none)
|
||||
// 0C 32 SSID (if present)
|
||||
// 2C 2 beacon capability field
|
||||
// 2E 2 supported rate bitmask (when bit7=1)
|
||||
// bit0 = 82 / 1Mbps
|
||||
// bit1 = 84 / 2Mbps
|
||||
// bit2 = 8B
|
||||
// bit3 = 8C
|
||||
// bit4 = 92
|
||||
// bit5 = 96
|
||||
// bit6 = B0
|
||||
// bit7 = C8
|
||||
// bit8 = E0
|
||||
// bit9 = EC
|
||||
// bit15 = any other rate (with bit7=1)
|
||||
// 30 2 supported rate bitmask
|
||||
// bit0 = 02/82 / 1Mbps
|
||||
// bit1 = 04/84 / 2Mbps
|
||||
// bit2 = 0B/8B
|
||||
// bit3 = 0C/8C
|
||||
// bit4 = 12/92
|
||||
// bit5 = 16/96
|
||||
// bit6 = 30/B0
|
||||
// bit7 = 48/C8
|
||||
// bit8 = 60/E0
|
||||
// bit9 = 6C/EC
|
||||
// bit15 = any other rate
|
||||
// 32 2 beacon interval
|
||||
// 34 2 beacon TIM period field (0 if none)
|
||||
// 36 2 beacon channel field
|
||||
// 38 2 beacon CF period field (0 if none)
|
||||
// 3A 2 ??
|
||||
// 3C 2 length of tag DD data (minus first 8 bytes)
|
||||
// 3E 2 number of bad tag DD's (when first 4 bytes are =/= 00:09:BF:00)
|
||||
// 40 X tag DD data (minus first 8 bytes)
|
||||
}
|
||||
break;
|
||||
|
||||
case 0x1E: // measure channel
|
||||
{
|
||||
u16 status = NDS::ARM7Read16(SharedMem[1]);
|
||||
if (status != 2)
|
||||
case 0xA: // start host scan
|
||||
{
|
||||
WifiIPCReply(0x1E, 3);
|
||||
break;
|
||||
// scan for viable host beacons
|
||||
// timeout: ~20480*64 cycles (with value 0x22)
|
||||
//
|
||||
// COMMAND BUFFER
|
||||
// offset size desc.
|
||||
// 02 2 channel
|
||||
// 04 4 pointer to beacon data buffer
|
||||
// 08 2 timeout in milliseconds
|
||||
// 0A 6 desired source MAC? seen set to FFFFFFFFFFFF
|
||||
//
|
||||
// REPLY BUFFER
|
||||
// offset size desc.
|
||||
// 08 2 5 to indicate a new beacon, 4 otherwise
|
||||
// 0A 6 source MAC from beacon (zero if none)
|
||||
// 10 ? channel
|
||||
// 36 2 length of tag DD data (minus first 8 bytes) (zero if none)
|
||||
// 38 X tag DD data (minus first 8 bytes)
|
||||
//
|
||||
// BEACON DATA BUFFER
|
||||
// offset size desc.
|
||||
// 00 2 buffer length in halfwords ((tag DD length - 8 + 0x41) >> 1)
|
||||
// 02 2 frame control? AND 0xFF -- 0080
|
||||
// 04 6 source MAC
|
||||
// 0A 2 SSID length (0 if none)
|
||||
// 0C 32 SSID (if present)
|
||||
// 2C 2 beacon capability field
|
||||
// 2E 2 supported rate bitmask (when bit7=1)
|
||||
// bit0 = 82 / 1Mbps
|
||||
// bit1 = 84 / 2Mbps
|
||||
// bit2 = 8B
|
||||
// bit3 = 8C
|
||||
// bit4 = 92
|
||||
// bit5 = 96
|
||||
// bit6 = B0
|
||||
// bit7 = C8
|
||||
// bit8 = E0
|
||||
// bit9 = EC
|
||||
// bit15 = any other rate (with bit7=1)
|
||||
// 30 2 supported rate bitmask
|
||||
// bit0 = 02/82 / 1Mbps
|
||||
// bit1 = 04/84 / 2Mbps
|
||||
// bit2 = 0B/8B
|
||||
// bit3 = 0C/8C
|
||||
// bit4 = 12/92
|
||||
// bit5 = 16/96
|
||||
// bit6 = 30/B0
|
||||
// bit7 = 48/C8
|
||||
// bit8 = 60/E0
|
||||
// bit9 = 6C/EC
|
||||
// bit15 = any other rate
|
||||
// 32 2 beacon interval
|
||||
// 34 2 beacon TIM period field (0 if none)
|
||||
// 36 2 beacon channel field
|
||||
// 38 2 beacon CF period field (0 if none)
|
||||
// 3A 2 ??
|
||||
// 3C 2 length of tag DD data (minus first 8 bytes)
|
||||
// 3E 2 number of bad tag DD's (when first 4 bytes are =/= 00:09:BF:00)
|
||||
// 40 X tag DD data (minus first 8 bytes)
|
||||
|
||||
u16 status = NDS::ARM7Read16(SharedMem[1]);
|
||||
if (status != 2 && status != 3 && status != 5)
|
||||
{
|
||||
u16 ext = 4;
|
||||
WifiIPCReply(0xA, 3, 1, &ext);
|
||||
break;
|
||||
}
|
||||
|
||||
// TODO: check incoming parameters
|
||||
|
||||
Channel = NDS::ARM7Read16(addr+0x2);
|
||||
HostScanCount = NDS::ARM7Read16(addr+0x8);
|
||||
HostScanBuffer = NDS::ARM7Read32(addr+0x4);
|
||||
|
||||
NDS::ARM7Write16(SharedMem[1], 5);
|
||||
ScheduleTimer(true);
|
||||
}
|
||||
break;
|
||||
|
||||
u16 chan = NDS::ARM7Read16(addr+0x6);
|
||||
u16 extra[2] = {chan, 1};
|
||||
case 0xE: // start local MP
|
||||
{
|
||||
// TODO!!
|
||||
|
||||
WifiIPCReply(0x1E, 0, 2, extra);
|
||||
u16 status = NDS::ARM7Read16(SharedMem[1]);
|
||||
if (status == 8)
|
||||
NDS::ARM7Write16(SharedMem[1], 10);
|
||||
else if (status == 7)
|
||||
NDS::ARM7Write16(SharedMem[1], 9);
|
||||
|
||||
printf("WIFI HLE: START MP\n");
|
||||
|
||||
WifiIPCReply(0xE, 0);
|
||||
}
|
||||
break;
|
||||
|
||||
case 0x1E: // measure channel
|
||||
{
|
||||
u16 status = NDS::ARM7Read16(SharedMem[1]);
|
||||
if (status != 2)
|
||||
{
|
||||
WifiIPCReply(0x1E, 3);
|
||||
break;
|
||||
}
|
||||
|
||||
u16 chan = NDS::ARM7Read16(addr+0x6);
|
||||
u16 extra[2] = {chan, 1};
|
||||
|
||||
WifiIPCReply(0x1E, 0, 2, extra);
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
printf("WIFI HLE: unknown command %04X\n", cmd);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
printf("WIFI HLE: unknown command %04X\n", cmd);
|
||||
break;
|
||||
NDS::ARM7Write32(SharedMem[1]+0x4, 0);
|
||||
}
|
||||
|
||||
cmd |= 0x8000;
|
||||
NDS::ARM7Write16(addr, cmd);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue