Arduino USB host – Pre-prototyping.

Arduino USB Host Shield prototype

Arduino USB Host Shield prototype

I have been thinking about expanding ways to use my recently conceived USB Host controller based on MAX3421E. Nice and very popular AVR development platform called Arduino looked like logical target. After quick Internet search, I went to SparkFun to pick up an 3.3V 8 MHz Atmega168 Arduino Pro, a protoshield, and USB to serial cable. After checking that everything works fine together, I populated a MAX3421E breakout and soldered it on the top of protoshield ( see schematic ).

I wanted to make a quick prototype and not worry about level translation for now. Arduino Pro is 3.3V and is able to talk to MAX3421E directly. The circuitry to adapt this shield for 5V Arduinos will be added later. This is going to be interesting since MAX3421E is not only a USB controller but also a port expander. It provides 8 general purpose outputs and 8 inputs, which can be configured as interrupt sources, all accessible via SPI. I’m using 1 input and 1 output for Vbus tracking, the rest is available for general use.

In order to use Atmega’s SPI peripheral I imported SPI library from Arduino playground. The default initialization will work. Below is the quick sketch that I wrote to make sure that MAX3421E is talking. Here I’m defining pins, setting initial state, and configuring MAX3421E SPI to full-duplex mode. This is not the right way to initialize MAX3421E, however, the beauty of this controller is that its SPI subsystem is separate from the rest of the chip and will work in any state as long as power is applied. No fancy resets are necessary.

/* MAX3421E USB Host controller main routine */
#include <spi.h>
#include "WProgram.h"
#include "MAX3421E.h"
/* pin definitions */
#define MAX_SS    10
#define MAX_INT   9
#define MAX_GPX   8
#define MAX_RESET 7
void setup();
void loop();
void setup()
  /* setup pins */
  pinMode( MAX_INT, INPUT);
  pinMode( MAX_GPX, INPUT );
  pinMode( MAX_SS, OUTPUT );
  digitalWrite( MAX_SS, HIGH );    //deselect MAX3421E
  pinMode( MAX_RESET, OUTPUT );
  digitalWrite( MAX_RESET, HIGH );  //release MAX3421E from reset
  /* setup SPI */
  /* default is good */
  /* setting up USART */
  Serial.begin( 9600 );
  /* setup MAX3421 */
  digitalWrite( MAX_SS, LOW );                    //select MAX3421E
  Spi.transfer( rPINCTL + 2 );                    //set full-duplex
  Spi.transfer( bmFDUPSPI+bmINTLEVEL+bmGPXB );
  digitalWrite( MAX_SS, HIGH );
void loop()
 byte a;
  delay( 100 );
  digitalWrite( MAX_SS, LOW );    //select MAX3421E
  Spi.transfer( 0x90 );      //send REVISION register address
  a = Spi.transfer( 0x00 );  //read next byte
  digitalWrite( MAX_SS, HIGH );   //deselect MAX3421E
  Serial.print( a, HEX );

In the main loop I query REVISION register. This is the only register which will contain meaningful information even if not reset properly. The picture below is a screen shot of my logic analyzer output showing byte 0x90 sent to MAX3421E and 0x12( which means revision 2 ) sent back in the second transmission.

MAX3421E REVISION register query

MAX3421E REVISION register query

I will be posting my progress here. The next step is going to be writing classes for MAX3421E and low-level USB functions.


11 comments to Arduino USB host – Pre-prototyping.

  • usbspy


    I am trying to implement spi to usb with the max3420e. I am using a FPGA to talk to the max3420e.
    Do I need to check any USB interrupt registers or pins.
    These are the steps I am following –

    1. Make SS low and write command byte to register R17 (PINCTL) to enable Full duplex SPI
    2. Make SS low and select EP2INFIFO register and write data bytes
    3. Make SS low and select EP2INBC register and write the # of data bytes written

    This should make data appear on the PC, right?
    I had a notepad open. Nothing happened.
    But it doesn’t work. I tried writing to GP0 register and it works. So I am able to talk to the MAX3420.
    Any help would be great.


    • I’m not sure what you mean by “SPI to USB”, but if you are trying to send data to the PC via USB using MAX3420, you first need to perform enumeration and start appropriate driver on a PC.

  • keips

    hi im making a project which is USB/Flash drive as a door key,, my question is can i use arduino to read the code that is installed in my usb and then execute it? and also what software did you use in programming the arduino? pls help me ,,

    • It depends on what you want to read off of Flash drive. If you can use drive’s serial number, which is unique for the drive, this can be done with the code which is already written since it’s just a string descriptor. If you need full support for flash drive, then you would need to write it – currently, flash drives are not supported.

      As far as programming, it’s standard Arduino package from

  • SteveL

    I am wanting to create a simple USB Flash drive reader that essentially reads music files from a Flash drive allows me to programme the display of the name and track number on a simple LCD and transmit the music data from the flash drive to a TOSLINK whichit is connectedto a high quality DAC capable of decoding the data into an anaolgue feed. It seems your project will do most of this? Just need to add the TOSLINK I guess. Is there anywhere you recommend I can get help on how to build this device? Thanks, Steve

  • Sam

    Hi there,

    Basically i’m trying to use the max3421e to datalog to a USB memory stick whatever the arduino sends to it via SPI can this be accomplished? If so is there any code that could help me out?
    Also the GPX and Int pins what exactly do they do? after looking at the datasheet i still cant understand if they would be required for the above example?


  • Hi, great work on this project. I just wondered if you could share your thoughts on other USB controllers that might be added in the future. The Vinculum controller is cheaper than the Max3421e and could really get the cost of these interfaces down; do you think this is a feasible future project? Has there been any talk of building an Arduino-like platform around AT90 chips with USB host included or anything like that? I know the Vinculo dev board is an attempt to create an open firmware dev framework with just the Vinculum chip and no separate uC; this would be nice but it seems a few steps away from realization…

    Thanks for all your great work.

    • I’m not familiar with Vinculum but heard from other developers that it is hard to work with and poorly documented. There is USB Host stack for AT90 micros developed by Dean Camera (project ‘LUFA’). Another interesting micro is PIC24/PIC32 with USB OTG support, at present they have a couple of annoying bugs in silicon due to be fixed next year.

  • Ah, thanks very much for the info! I have heard the same Vinculum stuff about hard to work with and poor docs. Too bad since FTDI is such a standard for other USB chips. Maybe now that you are an expert with the Max chip you might have more luck deciphering the FTDI?

    I guess I am curious where there might be avenues to make these kinds of applications even more accessible, so I am asking about cheaper possibilities for a next generation version of Arduino USB Host. But already you have really opened a lot of doors, so thanks!

  • Richard

    I did try the Vinculum 2 and got it working OK. As you say documentation is limited, but I found FTDI support people good.
    The major limitation I found was that the source is not provided for the libraries. I wanted to make a minor change to how latency was handled in the FT232 slave driver which meant I had to completely rewrite the driver from scratch.
    Another pain is that the programming of the Vinculum 2 including Vinculo requires an addtional programming dongle. Seems hard to believe it cannot be programmed directly from USB port.
    I did like the RTOS and the two USB ports.
    Since Vinculo(Vinco) is not Arduino software compatible, you do not get the wide range of open software and the great support community, so I find the Arduino and USB Host shield far better for my projects.
    FTDI are doing drivers to support Android Accessory, so this may make more interest in the chip and Vinco due to the much lower cost than Microchip or Andoid designs.

  • Wow, lots of good info; thanks Richard!

    I found the FTDI announcement for Android Accessory support on FTDI’s press page. They consistently refer to the dev board as “vinco” whereas I have only seen it as “vinculo” before… Will probably take some time for this to develop, but I’ll keep an eye on it for sure.

    For programming the Vinculo and the other DIP dev boards, I have been wondering if it would be possible to use one of the existing USB/Serial boards, like the USB-BUB from Modern Device. It might take a little bit of hardware hacking to get the control pins talking to each other correctly, but I thought it should be possible. Modern Device didn’t have much help to offer on that though.

    That is cool that you managed to get the Vinculum working with FTDI’s firmware toolchain. In the context of USB Host shields though, I was wondering if it would be easy to use the Vinculum as only the USB controller, with FTDI’s canned firmware, and then pair that with an Arduino as the processor. In a way a waste since the Vinculum is equipped with GPIO and a tool chain, but on the other hand still potentially half the cost of the Max3421e?

    Thanks again!