Arduino USB Host 2.0 library progress report

[EDIT] r2.0-compatible PTP code has been released, see here [/EDIT]
A significant progress has recently been made in Arduino USB Host 2.0 library development. The estimated release date is still several months away; however, I just can’t wait that long to share my excitement. A hub support is now fully incorporated into the library, as well as all necessary multi-device support – connect/disconnect, initialization and event handling. The very first device class implemented for the new library is ever-popular PTP digital camera control. A short Youtube video shows Arduino controlling two different camera systems simultaneously.

Some interesting numbers: a sketch used to drive cameras in the video takes 19K and contains one instance of USB, one instance of hub, one instance of EOS and one instance of Powershot class. The same sketch with only one camera instance takes 17K, which means one camera instance occupies roughly 2K. Since ~30K of program memory is available on Atmega328P-based Arduino board, it should be possible to drive seven cameras with a single Arduino! Also, I’m using development version of code with lots of debug strings and other less-than-necessary stuff – release version will definitely be smaller.

Watch the video, stay tuned to the code development and please let me know what you think about all that! Multi-camera control opens new exciting possibilities – anyone interested in (relatively) cheap 3D video rig?

38 comments to Arduino USB Host 2.0 library progress report

  • Dmitry

    Thats great!

    Yes! We are building 3d camera rig. Now we use two shields and two arduino synchonized by serial.

    Of course, materials and cameras we use cost significantly more than arduino and another one shield, but releaseing usb hub support will make electronic things more simple.

  • Fernando

    WOW…. You are going to make me buy another camera 😉

    Keep up the excellent work…

  • Keep up the great work. I can’t wait till everything is ready… !

  • Nils

    Hey, very nice.

    Oleg, I have a question: do you have some experience with a movement sensor? My girlfriend has a little fish pond, but some thing has stolen at least six fishes out of 21… and this was not the first time, so I thought a Canon PowerShot and an Arduino with a movement sensor could help us to make some pictures.

    One open question is the darkness, but a movement sensor might help me… a relay could be triggered from the Arduino and could switch a pocket lamp on. A photoconductive cell could help to detect if an additional light is needed.

    Should not be to difficult to code and build, or?

    Regards, Nils.

    • Nils

      One thing I forgot: is it possible to turn a PowerShot on just using USB? Oris there a wake up signal?

    • There are many types of motion sensors. The simple ones can be attached to Arduino quite easily, see this ->

      You can’t turn on power to Powershot via USB. Check your camera – my A640 can stay on for 3 days on a fresh set of batteries. It also have external power input.

      You can set it to manual with manual focus and flash on. This way camera will shoot instantly.

  • Pookycade

    I’m just thrilled beyond belief that someone is tackling this. I have a very specific question on the potential to control the “Image Comment” field on a Nikon D5000 DSLR with your code. Under gphoto/gtkam on Ubuntu I can fill the field “Image Comment” with a standard gphoto2 –set-config d090=’abcd’ command.

    On camera properties for the D5000 it lists the following:

    Image Comment String(0xd090):(readwrite) (type=0xffff) ‘ ‘
    Image Comment Enable(0xd091):(readwrite) (type=0x2) Range [0 – 1, step 1] value: Off (0)

    Label: Image Comment String
    Type: TEXT
    Label: Image Comment Enable
    Type: MENU
    Current: 0
    Choice: 0 0
    Choice: 1 1

    I realize that these are device specific properties for Nikon and that right now your control of Nikon cameras is generic PTP. However, for my purposes I need to be able to tag photos taken by the camera with an Image Comment before they get uploaded via an Eye-fi card in the camera.

    With all that preamble, and without spending days digging thru your code, how hard is to implement Nikon specific PTP commands like that in your code and is it even possible at this time ?

    If I can help implement Nikon specific camera properties after some schooling in your code base, I’d be happy to try.

    • I don’t see any problems implementing Nikon-specific commands – most likely the mechanism is similar to Powershot’s; however, I don’t have Nikon DSLR to play with so can’t check this.

      • Pookycade

        I’d be happy to send a Nikon D5000 out to you if you are interested in testing out, and if you’d be willing to work with me on developing a Nikon specific implementation I’d provide it gratis for permanent use. I think given the major users of this Arduino solution are likely to be Nikon and Canon photographers that would round out your offering. You can email directly at my email address if you’d like to discuss further.

  • sk

    The MAX3421E seem usable as an slave or master device. It’s can be possible to see the shield act as a peripheral with library 2.0 ?
    With a custom usb AA cable it can be a awesome feature.

    • The USB Host is very different from USB device; there is almost no code to reuse. Besides, there are plenty of USB devices already, you can run device code on USB to serial converter chip of modern Arduinos (UNO and 2560). I’m not planning on developing device code for MAX3421E, host keeps me pretty busy already:-).

  • hugo1456

    what about the use of kinect?, If you use directly kinect you will have a 3d vision system fully functional

  • Richard

    I think interfacing the kinect is intentionally left as an excercise for the user.

    The USB Descriptor for the kinect is here:

    If you examine the descriptor you will find it it a high speed hub and multiple high speed devices. High speed is not supported by the host shield and MAX3421e. Additionally kinect uses isochronous transfers which are not supported in the host software.

    Finally the quantity and rate of the kinect data is massive, being multiple 320 * 240 video streams + audio streams. The memory and processing power of any Arduino could not cope with this. I even heard that 1.6GHz Intel Atom processor struggles.

    • Randy

      @Richard, Hugo1456,
      Connecting to the kinect is possible with the USBHost and you can at least control the leds. I’ve managed to do this although I haven’t had any luck yet reading data from the depth camera.

      I don’t see the reference to the high speed hub and high speed devices you’re referring to. I wonder if perhaps the led is slow but the camera (which is the useful device) is fast and thus I might be at a dead end.

  • Santiago

    This is very exciting. Is the hub code complicated? Do you have a development branch on github where this new code is located? Its very exciting stuff, and I’m too excited to wait a few months for completion.

    • The main challenge in hub code development was to run directly from hub events without saving states. As a side effect, there is no restriction on device addressing; given enough memory, you can have all 127(some of them hubs, obviously). The main USB code has been changed quite a bit as well; is not stable enough to publish it even as development version since I’m planning to make many changes to the interface. I will probably have several class drivers (HID, CDC, video, and mass storage) developed prior to release just to see how new code behaves and make more changes if necessary.

  • Santiago Saldana

    Thank you for your quick reply, and I understand the need to wait til the code stabilizes. I just have a project that would greatly benefit from hub code, and I wanted to express my excitement. As a side note, I’ve referred to the LUFA project before, how does the USB 2.0 code or your code in general differ when you are developing it, are you focusing more on memory conservation, or are they entirely different idealogies, i.e. LGPL vs GPL. Reason I ask is I was able to use the LUFA HID descriptor parsing routine to save myself some coding headache when developing my application using your arduino usb sheild, and was just curious how the projects compare.

  • Sandro Benigno

    Wooow… Oleg, PSRemote is very very cool!
    I did almost all the things with it to test: changed Mode, Speed, Aperture, Exposure, Zoom… It’s amazing!
    The bad news is that sometimes it freezes showing this message forever (Canon S3is):

    Transaction: Response recieve error: 00F0
    EOSEventCheck error: : 2002
    Fatal USB Error

    I tried to find the cause, but I have no success until now. 🙁
    Do you saw something like this already?

    • This may happen because you camera doesn’t support certain properties. You may want to study your camera with PSDevProp to see what is available.

  • Sandro Benigno

    The problem above were an issue related to another chip at Arduino SPI bus, with CS pin level floating.
    I just forgot to add a line on PSRemote code to set that other pin level to high. It was my fault.

    So, Oleg, it’s fantastic!!! All is working pretty fine here too.

    As user, here go two guesses about resources which could be nice to implement:

    *open/close session by command, not only auto start-up (maybe arming and retracting lenses by a push button on the kit);
    *setup session for Zoom, with given discrete range and step, like percent from 0-100% by 5% per step (user just need to set absolute max range depending on camera model).

    Your work was stunning here, as always. Thank you!

  • I’m attempting to use the Circuits@Home USB Host Shield with an Arduino clone (Boarduino – As a hardware newbie, I’ve read as much as I can find about the host shield and Boarduino interfaces, but am still confused about something and I’m hoping you can clarify.

    The USB Host Shield Hardware Manual page ( indicates SPI is used to communicate with the Arduino. My understanding is that the host shield is using what would be Arduino Pins 9, 10, 11, 12, and 13 (INT, SS, MOSI, MISO, and SCK respectively) and that the USB Host library is expecting to use those same pin numbers by default. Is this correct? Are there other connections that must be made between the host shield and the Arduino?

    Thank you,


    • Hi Steve,

      If you’re using usb host shield rev.1.xx, pins are correct; you may also want to connect RESET line. If you are using rev.2.0, available since Feb.9, then INT and SS are in the same place and SPI is on ICSP connector.

      Let me know if you need anything else.


      • Hi Oleg,

        Thanks for the info. I’m using Revision 2.0. I’ve pulled a generic ICSP pinout and it looks like it’s pretty straightforward, although the ICSP block on the shield doesn’t seem to have an orientation indicator. If it doesn’t work one way I’ll reverse my connections and try again. Thanks again – I’ll be linking back to you when my project is complete 🙂

  • Mike

    Hi Oleg,
    I have a USB GPS device from which I want to log the serial data (in binary). Will your USB Host do this with no changes and will I be able to control and send the data to an SD card shield or other logging device such as OpenLog without too much trouble?


  • Hi Oleg,

    Any word on when the new 2.0 host library code will become available? I am working on a project that requires me to access devices through a HUB!

    P.S. Thanks for your hard work. Having looked into the details of USB programming now I can really appreciate the difficulty involved.

  • Great works! I really can’t wait to see news from you..
    Thank you so much Oleg

  • Steffen


    Thx for your great work! I just tried the USB host shield with your PTP library and it works great 🙂 I already tested it with my Nikon D2X and if I find the USB adapter cable, I will also test it with the Nikon D5100.

    Here is the D2X DeviceInformation log for your archive:

    0000: 3B 02 00 00 02 00 01 10 02 00 00 00 64 00 0A 00
    0010: 00 00 64 00 15 4E 00 69 00 6B 00 6F 00 6E 00 20
    0020: 00 50 00 54 00 50 00 20 00 45 00 78 00 74 00 65
    0030: 00 6E 00 73 00 69 00 6F 00 6E 00 73 00 00 00 00
    0040: 00 1D 00 00 00 01 10 02 10 03 10 04 10 05 10 06
    0050: 10 07 10 08 10 09 10 0A 10 0B 10 0C 10 0D 10 0E
    0060: 10 0F 10 14 10 15 10 16 10 1B 10 C0 90 C1 90 C2
    0070: 90 C3 90 C4 90 C5 90 C6 90 C7 90 C8 90 C9 90 0B
    0080: 00 00 00 01 40 02 40 04 40 05 40 06 40 09 40 0A
    0090: 40 0C 40 0D 40 01 C1 02 C1 9A 00 00 00 01 50 03
    00A0: 50 04 50 05 50 07 50 08 50 0A 50 0B 50 0C 50 0D
    00B0: 50 0E 50 0F 50 10 50 11 50 13 50 18 50 1C 50 10
    00C0: D0 11 D0 12 D0 13 D0 14 D0 15 D0 16 D0 17 D0 18
    00D0: D0 19 D0 1A D0 1B D0 1C D0 1D D0 1E D0 1F D0 20
    00E0: D0 21 D0 22 D0 23 D0 24 D0 25 D0 26 D0 27 D0 28
    00F0: D0 29 D0 2A D0 2B D0 2C D0 2D D0 2E D0 2F D0 30
    0100: D0 31 D0 32 D0 40 D0 41 D0 42 D0 43 D0 44 D0 45
    0110: D0 48 D0 49 D0 4A D0 4B D0 4C D0 4D D0 4E D0 4F
    0120: D0 50 D0 51 D0 54 D0 55 D0 56 D0 57 D0 58 D0 59
    0130: D0 5A D0 5B D0 5C D0 5E D0 5F D0 62 D0 63 D0 64
    0140: D0 68 D0 69 D0 6A D0 6B D0 6C D0 6D D0 6E D0 6F
    0150: D0 70 D0 74 D0 75 D0 76 D0 77 D0 78 D0 79 D0 7A
    0160: D0 7B D0 80 D0 81 D0 82 D0 83 D0 84 D0 85 D0 86
    0170: D0 87 D0 88 D0 89 D0 8A D0 8B D0 8C D0 90 D0 91
    0180: D0 92 D0 C0 D0 C1 D0 C2 D0 C3 D0 C4 D0 C5 D0 E0
    0190: D0 E1 D0 E2 D0 E3 D0 E4 D0 E5 D0 E6 D0 00 D1 01
    01A0: D1 02 D1 03 D1 04 D1 05 D1 06 D1 07 D1 08 D1 09
    01B0: D1 0A D1 0B D1 0C D1 0D D1 0E D1 0F D1 10 D1 11
    01C0: D1 20 D1 21 D1 22 D1 23 D1 24 D1 25 D1 64 D1 83
    01D0: D1 03 00 00 00 01 38 0D 38 00 30 08 00 00 00 00
    01E0: 30 01 30 0D 38 01 38 08 38 08 30 06 30 02 30 12
    01F0: 4E 00 69 00 6B 00 6F 00 6E 00 20 00 43 00 6F 00
    0200: 72 00 70 00 6F 00 72 00 61 00 74 00 69 00 6F 00
    0210: 6E 00 00 00 04 44 00 32 00 58 00 00 00 06 56 00
    0220: 32 00 2E 00 30 00 30 00 00 00 08 35 00 30 00 30
    0230: 00 32 00 30 00 35 00 34 00 00 00

    Std.Ver.: 0x100
    Vendor Ext. ID: 0xA(Nikon)

    Vend.Ext.Ver.: 0x64
    Nikon PTP Extensions
    Func.Mode: 0x8E0

    Operations supported:
    1001 GetDeviceInfo
    1002 OpenSession
    1003 CloseSession
    1004 GetStorageIDs
    1005 GetStorageInfo
    1006 GetNumObjects
    1007 GetObjectHandles
    1008 GetObjectInfo
    1009 GetObject
    100A GetThumb
    100B DeleteObject
    100C SendObjectInfo
    100D SendObject
    100E InitiateCapture
    100F FormatStore
    1014 GetDevicePropDesc
    1015 GetDevicePropValue
    1016 SetDevicePropValue
    101B GetPartialObject
    90C0 Vendor defined
    90C1 Vendor defined
    90C2 Vendor defined
    90C3 Vendor defined
    90C4 Vendor defined
    90C5 Vendor defined
    90C6 Vendor defined
    90C7 Vendor defined
    90C8 Vendor defined
    90C9 Vendor defined

    Events supported:
    4001 CancelTransaction
    4002 ObjectAdded
    4004 StoreAdded
    4005 StoreRemoved
    4006 DevicePropChanged
    4009 RequestObjectTransfer
    400A StoreFull
    400C StorageInfoChanged
    400D CaptureComplete
    C101 Vendor defined
    C102 Vendor defined

    Device properties supported:
    5001 BatteryLevel
    5003 ImageSize
    5004 CompressionSetting
    5005 WhiteBalance
    5007 FNumber
    5008 FocalLength
    500A FocusMode
    500B ExposureMeteringMode
    500C FlashMode
    500D ExposureTime
    500E ExposureProgramMode
    500F ExposureIndex
    5010 ExposureBiasCompensation
    5011 DateTime
    5013 StillCaptureMode
    5018 BurstNumber
    501C FocusMeteringMode
    D010 Vendor defined
    D011 Vendor defined
    D012 Vendor defined
    D013 Vendor defined
    D014 Vendor defined
    D015 Vendor defined
    D016 Vendor defined
    D017 Vendor defined
    D018 Vendor defined
    D019 Vendor defined
    D01A Vendor defined
    D01B Vendor defined
    D01C Vendor defined
    D01D Vendor defined
    D01E Vendor defined
    D01F Vendor defined
    D020 Vendor defined
    D021 Vendor defined
    D022 Vendor defined
    D023 Vendor defined
    D024 Vendor defined
    D025 Vendor defined
    D026 Vendor defined
    D027 Vendor defined
    D028 Vendor defined
    D029 Vendor defined
    D02A Vendor defined
    D02B Vendor defined
    D02C Vendor defined
    D02D Vendor defined
    D02E Vendor defined
    D02F Vendor defined
    D030 Vendor defined
    D031 Vendor defined
    D032 Vendor defined
    D040 Vendor defined
    D041 Vendor defined
    D042 Vendor defined
    D043 Vendor defined
    D044 Vendor defined
    D045 Vendor defined
    D048 Vendor defined
    D049 Vendor defined
    D04A Vendor defined
    D04B Vendor defined
    D04C Vendor defined
    D04D Vendor defined
    D04E Vendor defined
    D04F Vendor defined
    D050 Vendor defined
    D051 Vendor defined
    D054 Vendor defined
    D055 Vendor defined
    D056 Vendor defined
    D057 Vendor defined
    D058 Vendor defined
    D059 Vendor defined
    D05A Vendor defined
    D05B Vendor defined
    D05C Vendor defined
    D05E Vendor defined
    D05F Vendor defined
    D062 Vendor defined
    D063 Vendor defined
    D064 Vendor defined
    D068 Vendor defined
    D069 Vendor defined
    D06A Vendor defined
    D06B Vendor defined
    D06C Vendor defined
    D06D Vendor defined
    D06E Vendor defined
    D06F Vendor defined
    D070 Vendor defined
    D074 Vendor defined
    D075 Vendor defined
    D076 Vendor defined
    D077 Vendor defined
    D078 Vendor defined
    D079 Vendor defined
    D07A Vendor defined
    D07B Vendor defined
    D080 Vendor defined
    D081 Vendor defined
    D082 Vendor defined
    D083 Vendor defined
    D084 Vendor defined
    D085 Vendor defined
    D086 Vendor defined
    D087 Vendor defined
    D088 Vendor defined
    D089 Vendor defined
    D08A Vendor defined
    D08B Vendor defined
    D08C Vendor defined
    D090 Vendor defined
    D091 Vendor defined
    D092 Vendor defined
    D0C0 Vendor defined
    D0C1 Vendor defined
    D0C2 Vendor defined
    D0C3 Vendor defined
    D0C4 Vendor defined
    D0C5 Vendor defined
    D0E0 Vendor defined
    D0E1 Vendor defined
    D0E2 Vendor defined
    D0E3 Vendor defined
    D0E4 Vendor defined
    D0E5 Vendor defined
    D0E6 Vendor defined
    D100 Vendor defined
    D101 Vendor defined
    D102 Vendor defined
    D103 Vendor defined
    D104 Vendor defined
    D105 Vendor defined
    D106 Vendor defined
    D107 Vendor defined
    D108 Vendor defined
    D109 Vendor defined
    D10A Vendor defined
    D10B Vendor defined
    D10C Vendor defined
    D10D Vendor defined
    D10E Vendor defined
    D10F Vendor defined
    D110 Vendor defined
    D111 Vendor defined
    D120 Vendor defined
    D121 Vendor defined
    D122 Vendor defined
    D123 Vendor defined
    D124 Vendor defined
    D125 Vendor defined
    D164 Vendor defined
    D183 Vendor defined

    Capture formats:
    3801 EXIF_JPEG
    380D TIFF
    3000 Undefined

    Image Formats:
    3000 Undefined
    3001 Association
    380D TIFF
    3801 EXIF_JPEG
    3808 JFIF
    3008 WAV
    3006 DPOF
    3002 Script

    Manufacturer: Nikon Corporation
    Model: D2X
    Device ver.: V2.00
    Serial num.: 5002054

  • Kevin

    Did you have a chance to test with the 5100?

  • Supports even 7D? Awesome!
    Does it needs to be tuned for each camera specifically?
    I see DIY pro grade motorized cranes and dollies coming 🙂

  • AP

    Hi, I’m really excited about these stuffs.
    I read the info page for Nikon D70 but I don’t see what parameters I can set for this camera (focus distance, rear flash etc).

    There is a way to read images via usb and forward to a bluetooth/wifi tablet?

  • Arduinizer

    Hi, I have got work Max 3421 on arduino mega ADK but its posible with library 2.0, I have been trying but nothing, what its need to get working??

    There is any plan to making a library for PS3 Controller over Bluetooth? It doesnt need L2CAP like Wiimote?

    (Im not english talker)

  • Jens

    Hi Oleg,
    i had checked out your coding sample eosFocus. But some strange errors occured.
    The first check runs without any problems. The camera blocked. It makes one picture and stopped. Switch off/switch on. No chance. I am not sure if my sparkfun shield is defect or is there an error in the code.
    Do you have any idea?

    EOS 5d II/Sparkfun USB Host Shield/ OS X
    EOS Init
    PTP Init
    Addr:: 0001
    NI:: 0001
    PTP configured
    Session opened
    Init complete
    Fatal USB Error
    Transaction: Response recieve error: 00FF

  • I found one typo error in your library that is in avrpins.h. The error is in line 423 which say “#define P5 Pe5” but a few line above say “#define P3 Pe5″(same pin assignment?). I have checked the arduino mega pin assignment and conclude that instead of “#define P5 Pe5” it should be “#define P5 Pe3”.