MCP2221 HID Library

This is a library for interfacing with the HID features of the MCP2221 USB to UART and I2C/SMBus serial converter from Microchip and the newer MCP2221A. The converter includes 4 GPIO pins, 3x 10-bit ADCs, 1x 5-bit DAC and more.
Microchip does provide a library for interfacing with the chip, however it is supplied as proprietary DLLs. This project aims to be an open-source and multi-platform alternative.
This library also makes use of HIDAPI.

Supported features
Feature Status
ADC Supported
DAC Supported
GPIO Supported
Interrupt input Supported
Clock reference output Supported
USB Descriptors
(Manufacturer, product, serial, VID, PID)
I2C/SMB Limited support, WIP
Flash password protection Not yet implemented
C++ and C# wrappers Not yet implemented
Download from GitHub

Bits of info about the MCP2221

  • Doesn’t use a crystal, only requires 1 small capacitor when powered with 3.3V or 2 capacitors when powered with 5V.
  • Available in a hacker friendly DIP package.
  • Has a remote wake function which when used in conjunction with the interrupt input can be used to wakeup the USB host (usually a PC), just like waking up from a keyboard or mouse press.
  • The raw value of the I2C pins can also be read, allowing them to be used as an additional 2 general purpose input pins.
  • Unfortunately there are no options for enabling any internal pull-up/down resistors.
  • The MCP2221 seems to be a PIC16F1455. [Source]
  • Current consumption @ 3.3V with USB disconnected can be anywhere between 20uA and 70uA, not sure what causes such a difference. Remote wakeup needs to be disabled (default) otherwise current consumption will be about 5mA.
  • Kinda slow compared to other USB/UART converters. Even with the baud rate set to 1,000,000 its overall throughput is only about 250,000 bps. More about this below.

Unconnected pins
The usual way to deal with unconnected pins are to enable their internal pull-up/down resistors, but this chip doesn’t support them. Instead it’s probably best to set unconnected pins as output high or low.
The I2C pins are a little different since they can’t be set to outputs, though there’s still few options:

I2C Pin Description
Unconnected Bad, floating inputs will cause excessive power consumption
Connect to VDD Bad, if the I2C bus is accidentally used then a short circuit will occur
Connect to ground OK, but may cause the I2C bus to hang if used, not much of an issue though
External pull-up resistors Best option, but requires additional components

UART Throughput
The main UART function seems to be really slow, maxing out at about 250,000 bps throughput when set to 1,000,000 baud due to a gap of about 30us after each byte transmitted. This isn’t much of a problem at lower bauds, but as the baud rate increases it creates a huge overhead (75% @ 1Mbaud!). Attempting to receive data without a sufficient gap will also corrupt the data. Here are some screen shots comparing the MCP2221 and CH340 UART converter ICs transmitting data at 1,000,000 baud. The MCP2221 has a gap of about 30us between each byte, while the CH340 has a gap of just 1us.

MCP2221 @ 1Mbaud

MCP2221 @ 1Mbaud

CH340 @ 1Mbaud

CH340 @ 1Mbaud

Other issues
If the MCP2221 receives too much UART data too soon after powering up it will have trouble enumerating with the USB host.

The MCP2221A replaces the MCP2221 and is fully compatible with this library. The new chip appears to have fixed the USB enumeration issue described above and the gap between each transmitted UART byte now varies from 4us to 18us, but usually around 6us.

A breakout module for the MCP2221, design available on the GitHub repo

A breakout module for the MCP2221, design available on the GitHub repo


1 ping

Skip to comment form

    • richard payne on September 23, 2015 at 9:46 am
    • Reply

    Wow, that look like good work.

    What kind of timescale for C# wrapper to be beta released?

    Have you tried C# code under Visual Studio, how they performed?


    1. Hey, the C# wrapper will probably be made when I start working on a project that needs it. There is currently such a project on my to do list, but I’ve still got a number of other things happening before I can start on it. So I can’t really say when, sorry.
      VS is the only IDE I’ve used for C# stuff. It performs alright, but can be a bit clunky at times.

    • Andrea on December 2, 2015 at 1:04 pm
    • Reply

    I confirm MCP2221 is a PIC16F1455, naturally CP is ON.
    This is the dump of config*

    8007 CONFIG1 F44 FOSC INTOSC Oscillator Selection Bits INTOSC oscillator: I/O function on CLKIN pin
    WDTE OFF Watchdog Timer Enable WDT disabled
    PWRTE ON Power-up Timer Enable PWRT enabled
    MCLRE ON MCLR Pin Function Select MCLR/VPP pin function is MCLR
    CP ON Flash Program Memory Code Protection Program memory code protection is enabled
    BOREN ON Brown-out Reset Enable Brown-out Reset enabled
    CLKOUTEN OFF Clock Out Enable CLKOUT function is disabled. I/O or oscillator function on the CLKOUT pin
    IESO OFF Internal/External Switchover Mode Internal/External Switchover Mode is disabled
    FCMEN OFF Fail-Safe Clock Monitor Enable Fail-Safe Clock Monitor is disabled
    8008 CONFIG2 1FCD WRT HALF Flash Memory Self-Write Protection 000h to 0FFFh write protected, 1000h to 1FFFh may be modified by PMCON control
    CPUDIV NOCLKDIV CPU System Clock Selection Bit NO CPU system divide
    USBLSCLK 48MHz USB Low SPeed Clock Selection bit System clock expects 48 MHz, FS/LS USB CLKENs divide-by is set to 8.
    PLLMULT 3x PLL Multipler Selection Bit 3x Output Frequency Selected
    PLLEN ENABLED PLL Enable Bit 3x or 4x PLL Enabled
    STVREN ON Stack Overflow/Underflow Reset Enable Stack Overflow or Underflow will cause a Reset
    BORV LO Brown-out Reset Voltage Selection Brown-out Reset Voltage (Vbor), low trip point selected.
    LPBOR OFF Low-Power Brown Out Reset Low-Power BOR is disabled
    LVP OFF Low-Voltage Programming Enable High-voltage on MCLR/VPP must be used for programming

    Maybe a day we can got also the firmware

    • Josh on January 16, 2020 at 12:21 pm
    • Reply

    I have a question

    What are the function

    GPIO_init() ADC_Init() , API is not cleared

    If I call GPIO_Init() does it mean all pins are now GPIO

    what If I want PIN1 to be GPIO, and PIN2 to Be ADC


    1. Hey Josh, there are no API functions named GPIO_init() or ADC_Init() in this library.

    • John Dang on May 21, 2021 at 5:02 pm
    • Reply

    Hi, I want to change to i2c clock speed up to 1MHz.
    Could it be possible?

    1. The MCP2221 is only spec’d for 400KHz I2C. There is a register for setting the clock speed in the “Status/Set Parameters” (0x10) HID command which I think if set to 0x0A will make it run at 1MHz, you’ll have to see if it works or not.

  1. […] MCP2221 HID Library – [Link] […]

Leave a Reply

Your email address will not be published.

Are you human? *