So I'm attempting to use my Arduino Due to act as a PS2 controller, and to start with I broke out an extension cable and have the Arduino listening in to the SPI host commands (a PS2 to USB adaptor for initial testing). Chip select, clock and data lines are all connected per the reference materials I found (e.g. Interfacing a PS2 (PlayStation 2) Controller - Curious Inventor), and all registers appear configured properly per the SAM3X/A specification document via the libsam functions/globals. However, the data I'm getting is kinda garbage and I'm unsure what else to try next.
Here's my code:
uint32_t databuf[10][64];
int recordlen[10];
int count = 0;
int record = 0;
int modefault = 0;
int overrun = 0;
void setup() {
// Configure the pins for SPI in peripheral mode
PIO_Configure(
g_APinDescription[PIN_SPI_SS0].pPort,
g_APinDescription[PIN_SPI_SS0].ulPinType,
g_APinDescription[PIN_SPI_SS0].ulPin,
g_APinDescription[PIN_SPI_SS0].ulPinConfiguration);
PIO_Configure(
g_APinDescription[PIN_SPI_MOSI].pPort,
g_APinDescription[PIN_SPI_MOSI].ulPinType,
g_APinDescription[PIN_SPI_MOSI].ulPin,
g_APinDescription[PIN_SPI_MOSI].ulPinConfiguration);
PIO_Configure(
g_APinDescription[PIN_SPI_MISO].pPort,
g_APinDescription[PIN_SPI_MISO].ulPinType,
g_APinDescription[PIN_SPI_MISO].ulPin,
g_APinDescription[PIN_SPI_MISO].ulPinConfiguration);
PIO_Configure(
g_APinDescription[PIN_SPI_SCK].pPort,
g_APinDescription[PIN_SPI_SCK].ulPinType,
g_APinDescription[PIN_SPI_SCK].ulPin,
g_APinDescription[PIN_SPI_SCK].ulPinConfiguration);
SPI_Configure(SPI0, ID_SPI0, SPI_MR_PS | SPI_MR_MODFDIS);
SPI_ConfigureNPCS(SPI0, 0, SPI_CSR_NCPHA);
//SPI_ConfigureNPCS(SPI0, 0, SPI_CSR_CPOL);
//SPI_ConfigureNPCS(SPI0, 0, SPI_CSR_CPOL | SPI_CSR_NCPHA);
SPI_Enable(SPI0);
Serial.begin(57600);
printf("Start\r\n");
}
void loop() {
uint32_t StatusReg = SPI0->SPI_SR;
// Count mode faults and overruns
if (StatusReg & SPI_SR_MODF)
modefault++;
if (StatusReg & SPI_SR_OVRES)
overrun++;
// Rising edge on slave select (e.g. new message!)
if (StatusReg & SPI_SR_NSSR)
{
recordlen[record] = count;
count = 0;
record++;
}
// If we have recorded 10 messages, print them.
if (record >= 10)
{
for (int j=0; j<10; j++)
{
printf("[%d]:", recordlen[j]);
for (int i=0; i<recordlen[j]; i++)
{
printf("%02X ", databuf[j][i]);
}
printf("\r\n");
}
printf("Mode Fault: %d; Overrun: %d\r\n", modefault, overrun);
record = 0;
count = 0;
modefault = 0;
overrun = 0;
}
if (count < 64)
{
// Receive data is available. Log it.
if (StatusReg & SPI_SR_RDRF)
{
uint32_t readval = SPI0->SPI_RDR & 0xFFFF;
databuf[record][count] = readval;
count++;
}
}
}
Sample output:
[0]:
[21]:00 0C 00 00 0C 06 00 00 60 00 03 00 00 00 00 00 00 F0 63 1E 01
[19]:8F 00 01 9E 0C 00 00 00 00 60 00 07 FF FF FF FF FF FF FF
[19]:FE 00 07 F8 30 00 01 FF FF FF FF F0 00 00 00 00 00 00 00
[19]:01 80 00 3C 03 00 00 00 00 00 00 00 00 00 00 00 00 00 00
[43]:01 80 00 60 06 00 00 00 00 00 00 7F FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
[43]:FF 00 00 C0 18 00 00 00 00 00 01 FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
[43]:E0 00 0C 00 C0 00 00 00 00 00 00 FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
[43]:FC 00 03 00 60 00 00 00 00 00 00 FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
[43]:FC 00 01 80 30 00 00 00 00 00 01 FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
Mode Fault: 0; Overrun: 1
[0]:
[45]:FF FE 00 00 60 0C 00 00 00 00 00 00 07 FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
[43]:C0 00 06 00 C0 00 00 00 00 00 00 1F FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
[44]:FE 00 00 30 06 00 00 00 00 00 00 03 FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
[43]:C0 00 0C 01 80 00 00 00 00 00 01 FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
[43]:FC 00 00 C0 0C 00 00 00 00 00 00 07 FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
[43]:FF 80 00 30 0C 00 00 00 00 00 00 1F FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
[44]:FC 00 00 C0 18 00 00 00 00 00 00 07 FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
[42]:C0 00 18 06 00 00 00 00 00 00 1F FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
[44]:FE 00 00 60 18 00 00 00 00 00 00 07 FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF
Mode Fault: 0; Overrun: 1
And some sample output of what it SHOULD be giving me per some SPI captures I downloaded from Procrastineering - Project blog for Johnny Chung Lee: Simulated PS2 Controller for Autonomously playing Guitar Hero
01 42 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
01 42 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
01 42 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
Or at least something with the same structure (01 followed by 4-something).
Here's a photo of my setup:
I also had the thought that I could be running into EMI issues, but the controller itself is still fully functional through the breakout interface, so this seems unlikely.