Arduino 控制USB设备(2)硬件测试篇

这篇文章目标是让你知道你买的USB Host Shield能否正常工作。

我们要运行一段代码来确保板子工作正常。从经验的角度来看,这个非常必要,对于很多卖家来说,板子之间的差别只有进货价格的高低,他们对于质量一无所知。

下面例子中的代码来自 http://www.circuitsathome.com/mcu/arduino-usb-host-part-2-classes

第一个代码是测试SPI通信是否正常

/* MAX3421E USB Host controller SPI test */
/* This sketch tests SPI communication between Arduino and MAX3421E USB host controller */
#include <spi.h>
#include "max3421e.h"
 
void setup();
void loop();
 
byte i;
byte j = 0;
byte gpinpol_copy;
 
MAX3421E Max;
 
void setup()
{
    Serial.begin( 9600 );
    Max.powerOn();
    delay(200);
}
 
void loop()
{
  gpinpol_copy = Max.regRd( rGPINPOL );
  Serial.println("SPI test. Each  '.' indicates 64K transferred. Press any key to stop.");
  while( Serial.available() == 0 ) {
    for( i = 0; i < 255; i++ ) {
      Max.regWr( rGPINPOL, i );
      if( Max.regRd( rGPINPOL ) != i ) {
        Serial.println("SPI transmit/receive mismatch");
      }
    }//for( i = 0; i < 255; i++
      j++;
      if( j == 0 ) {
        Serial.print(".");
      }
  }//while( Serial.available() == 0
  Max.regWr( rGPINPOL, gpinpol_copy );
  Serial.println("\r\nStopped.");
  while( 1 );    //stop here
}

 

运行结果

usbspitest1

下面这个代码测试的是 MAX3421E 寄存器是否正常

/* This sketch dumps MAX3421E registers */
#include <spi.h>
#include "max3421e.h"
 
MAX3421E Max;  //MAX3421E instance
 
/* Regiser names/numbers for MAX3421E register dump */
typedef struct {
  const char* name;
  char number;
}
REGISTER_OUTPUT;
 
REGISTER_OUTPUT max_register[] = {
  { "\r\nRCVFIFO:\t",   rRCVFIFO    },
  { "\r\nSNDFIFO:\t",   rSNDFIFO    },
  { "\r\nSUDFIFO:\t",   rSUDFIFO    },
  { "\r\nRCVBC:\t",     rRCVBC      },
  { "\r\nSNDBC:\t",     rSNDBC      },
  { "\r\nUSBIRQ:\t",    rUSBIRQ     },
  { "\r\nUSBIEN:\t",    rUSBIEN     },
  { "\r\nUSBCTL:\t",    rUSBCTL     },
  { "\r\nCPUCTL:\t",    rCPUCTL     },
  { "\r\nPINCTL:\t",    rPINCTL     },
  { "\r\nREVISION:\t",  rREVISION   },
  { "\r\nIOPINS1:\t",   rIOPINS1    },
  { "\r\nIOPINS2:\t",   rIOPINS2    },
  { "\r\nGPINIRQ:\t",   rGPINIRQ    },
  { "\r\nGPINIEN:\t",   rGPINIEN    },
  { "\r\nGPINPOL:\t",   rGPINPOL    },
  { "\r\nHIRQ:\t",      rHIRQ       },
  { "\r\nHIEN:\t",      rHIEN       },
  { "\r\nMODE:\t",      rMODE       },
  { "\r\nPERADDR:\t",   rPERADDR    },
  { "\r\nHCTL:\t",      rHCTL       },
  { "\r\nHXFR:\t",      rHXFR       },
  { "\r\nHRSL:\t",      rHRSL       }
};
 
 
void setup()
{
  Serial.begin( 9600 );
  Max.powerOn();
}
 
void loop()
{
  unsigned char i;
  unsigned char numregs = sizeof( max_register )/sizeof( REGISTER_OUTPUT);
  for( i = 0; i < numregs; i++ ) {
    Serial.print( max_register[ i ].name);
    print_hex( Max.regRd( max_register[ i ].number ), 8 );
  }
  while(1);
 
}
 
/* prints hex numbers with leading zeroes */
// copyright, Peter H Anderson, Baltimore, MD, Nov, '07
// source: http://www.phanderson.com/arduino/arduino_display.html
void print_hex(int v, int num_places)
{
  int mask=0, n, num_nibbles, digit;
 
  for (n=1; n<=num_places; n++)
  {
    mask = (mask << 1) | 0x0001;
  }
  v = v & mask; // truncate v to specified number of places
 
  num_nibbles = num_places / 4;
  if ((num_places % 4) != 0)
  {
    ++num_nibbles;
  }
 
  do
  {
    digit = ((v >> (num_nibbles-1) * 4)) & 0x0f;
    Serial.print(digit, HEX);
  }
  while(--num_nibbles);
 
}

 

运行结果

usbspitest2

下面这个代码测试的是 USB 当前状态

/* MAX3421E interrupt loop */
#include <spi.h>
#include "max3421e.h"
 
MAX3421E Max;
 
byte rcode;
byte vbus_state;
 
void setup()
{
  Serial.begin( 9600 );
  Serial.println("Start");
  Max.powerOn();
}
 
void loop()
{
  Max.Task();
  print_vbus_state();
}
 
void print_vbus_state( void )
{
  char* vbus_states[] = { "Disconnected", "Illegal", "Full speed", "Low speed" };
  byte tmpbyte;
  static byte last_state = 4;
    tmpbyte = Max.getVbusState();
    if( tmpbyte != last_state ) {
      last_state = tmpbyte;
      Serial.println( vbus_states[ tmpbyte ] );
    }
    return;
}

 

刚开始没有插任何设备,显示为 Disconnected 状态。之后插入一个USB鼠标,识别为Low Speed设备。拔掉之后再插入两个不同的U盘,因为IC本身不支持High Speed,所以都显示为Full Speed设备。

usbspitest3

最后,三个修改后的完整代码可以在这里下载:

usb2

经过上述测试,可以确定你的板子没问题。

《Arduino 控制USB设备(2)硬件测试篇》有4个想法

  1. 楼主您好,我用这三个程序测试,前两个都没问题,第三个当我插一个双飞燕的有线鼠标的时候它开始没反应,过会出现Disconnected 和 Full speed 之间来回跳,然后我换了一个罗技的无线鼠标的接收器插上去就只稳稳的一个Full speed,这说明有线鼠标带不动吗?还是说这个牌子的鼠标有问题呢?

    1. 双飞燕的我还真没测试过,有可能是供电不足,你检查一下电压看看?
      另外,你可以试试把有问题的鼠标放在独立供电的 USB Hub 后面看看。

发表回复

您的电子邮箱地址不会被公开。 必填项已用 * 标注