Quick Charge 3.0

An device-side implementation of the new modes from the Quick Charge 3.0 protocol to provide voltages from 3.6-20V in 0.2V increments

Similar projects worth following
This project aims to provide simple microcontroller code and circuit schematics that will perform the appropriate handshake and signalling with a Quick Charge 3.0 compatible power source to induce it to output the desired voltage. Quick Charge 3.0 specs support discrete voltage levels of 5V, 9V, 12V, and 20V, and a special "Continuous Mode" which allows any voltage between 3.6V and 20V in 0.2V increments.
This builds upon the previous work by [Hugatry], who demonstrated an easy way to speak the Quick Charge 2.0 protocol.

  • TL;DR: Troubleshooting

    dracode08/08/2017 at 21:06 0 comments

    There's really nothing in this post that you'll need in order to replicate the QC3.0 hack, it's mainly just describing some of the silly problems I ran into.


    A couple of days later, my new power bank arrived!  I plugged it in to ensure it was ready to go before I began experimenting.

    Using C to program a microcontroller permanently is great, but for quick development and testing, I greatly prefer something like Python.  It's great to be able to use the command line to try out an idea in one or two lines as opposed to write, compile, reflash...  So I chose to use an ESP8266 module with MicroPython for my experiment.  I got it on eBay for around $5.  I have a few of this particular dev board and I think they're great.  The pins are broken out to standard 0.1" headers, indicator LED for each GPIO, voltage regulator onboard, a jumper block for setting the flash into programming mode.  One little improvement I make is to remove the little battery box and replace it with a standard USB connector; just plug it into any USB socket and your board is powered up.  

    First, I did a quick and dirty re-implementation Hugatry's QC2.0 code in Python.  Hit my first major problem: it didn't work.  All I could get out of the power bank was the normal 5V.  Was the problem with my code?  My circuit?  The power bank itself?  Time to troubleshoot.  I stepped through Hugatry's QC2.0 video and decided to validate my circuit by disconnecting the ESP8266 and doing the handshake by hand with jumper wires.  Nope, didn't work.  His document said "Device should allow the voltage on D- -line to drop below 0.325V, for example by keeping D- disconnected."  When building my circuit, I had interpreted that as "D- needs to go low" with the "keeping D- disconnected" as just a suggestion.  In my implementation, I was tying D- to ground.  Turns out, that doesn't work -- it must be left floating.  After correcting that, the voltmeter showed 12V now.  The circuit and power bank worked.

    But it still didn't work when hooked up to the microcontroller.  There must be a bug in my code.  I pored over the code, tweaked some things, still no success.  I hooked the voltmeter into the circuit to observe it in action.  Bmm, that's weird: when I'm trying to set the D- pin to high impedence ("disconnected"), I'm actually getting a residual voltage of 0.1V.  That's when I realized: those nice LEDs on my dev board hooked up to each GPIO, they were also providing another path for current from my GPIO pin.  I desoldered the current-limiting resistors from the two GPIOs I'm using for control of D- and...  it works!  I've replicated the existing QC2.0 hack, finally, with a bit extra logic to allow for a new state that Hugatry was not using (3.3V on D-) that was required for the two new modes.

    Now to move on to the new features contained in QC3.0.  At this point, I wasn't really hopeful that it would work.  The CHY103 datasheet says "At this point the Quick Charge 2.0 handshake followed by the Quick Charge 3.0 handshake can take place", and I haven't found any documentation of this new handshake for QC3.0.  But what the heck, I'll try the new entries in the state table for the two new modes anyway, with only the QC2.0 handshake.  The 20V mode: failure.  Continuous mode: no obvious signs of success or failure.  Try out an "increment" pulse on D+, with my wild guess of 200us pulse width.  And, shockingly, it WORKED!  I can't guarantee that this works for all QC3.0 power sources, but it worked on this one.

    I incremented and decremented until the voltage stopped changing.  My particular device accepted decrement pulses until it should be (nominally) 3.6V, though the voltmeter continued to display 4.27V.  I suspect that's the actual output voltage of the LiPo cells inside the device,...

    Read more »

  • Research

    dracode08/07/2017 at 18:43 0 comments

    While I waited for it to arrive, I tried to hunt down the technical details about how the QC3.0 protocol worked.  Hugatry's blog was a great starting point for QC2.0, but I needed to learn how to set the other voltages as well.  Given his success in mining the protocol info from datasheets, I went looking for the same.  I found the datasheets for NCP4271-D and CHY103, which gave me the additional info that I needed.

    The NCP4371-D datasheet shows the appropriate states to put onto D+ and D- to enable both the new discrete 20V mode, and "Continuous Mode" where the voltage is adjustable in 0.2V increments.  These appeared to be relatively straightforward -- just previously unused voltage states for the same table that Hugatry used for QC2.0.  While in Continuous Mode, the voltage is adjusted up or down in 0.2V increments by briefly pulsing the D+ line high (to increment up) or pulsing the D- line low (to increment down).  The pulse times are given as T_ACTIVE, T_V_CONT_CHANGE_SINGLE, and so on, but the actual values are not given anywhere.  The CHY103 datasheet mentions a value for "Continuous Mode Glitch Filter Time" of between 100 and 200 us, so that's what I decided to try.

    Here's the table of states for Quick Charge 3.0 from the NCP4371 datasheet, page 9:

    D+ LineD- LineOutput Voltage
    0.6 V0.6 V12 V
    3.3 V0.6 V9 V
    0.6 V3.3 VContinuous Mode
    3.3 V3.3 V20 V
    0.6 VGND5 V

    As you can see for Continuous Mode, D+ is held at a low voltage and D- is held at a high voltage. Continuous Mode is the state wherein we can adjust the voltage in 0.2V increments. Again per the NCP4371 datasheet, page 9, The method to do this is to briefly pulse D+ high to increment, or to pulse D- low to decrement.

  • The genesis of the idea

    dracode08/07/2017 at 18:29 0 comments

    After recently reading about a hack to get a Quick Charge 2.0 (QC2.0) USB device to output 9V and 12V instead of the typical USB voltage of 5V, I read up more on the standard and (along with several others) noticed that Quick Charge 3.0 (QC3.0) offered support for many more voltages.

    QC3.0 will supposedly supply any voltage asked for between 3.6V and 20.0V in 0.2V increments.  I have an old boom box radio that takes 10x D Cell batteries, which are now quite expensive (and also heavy!), so I thought QC3.0 would let me easily get the equivalent 15V required to be a drop-in replacement.  I ordered a QC3.0 power bank on Amazon to give it a shot.

View all 3 project logs

  • 1
    Step 1: Set up the ESP8266

    Get the MicroPython firmware running on your ESP8266.  Here are some instructions if you've never done that before.  You will need a module with at least 1 MB of flash and 3 free GPIOs.  Your old ESP-01 probably isn't going to cut it, sorry.

    Download the Python code from my GitHub: dracode

    Once you've got the firmware running, upload the Python code.  I use to upload my files.

  • 2
    Step 2: Build voltage dividers

    I used a standard USB-A connector that would plug into the QC3.0 port on my power bank.  I just cut an old cord and re-used it.  The black wire is ground, red is positive, white is the "D-" line and green is the "D+" line.

    I used 1kΩ and 4.7kΩ resistors to create voltage dividers that I could control with a microcontroller.  With a voltage of 3.3V on top of the bridge, that would give me right around 0.6V in the middle.  According to the data sheet I used, the signals levels we need are: 3.3V, 0.6V, 0V, or disconnected.

    I used a 3.3V microcontroller in the project.  It's VERY IMPORTANT that you do NOT hook the microcontroller up to the positive wire coming out of your QC3.0 USB connector!  We're about to ask the power bank to provide up to 20V on that line, which will surely fry your microcontroller.  I used a separate 3.3V power source in this proof of concept project, but in real use you would probably want to use a 3.3V voltage regulator to safely get power from the variable-voltage QC3.0 source.

  • 3
    Step 3: Try it out

    Plug in your QC3.0 power bank/charger/whatever and turn it on (if it has an on button).

    Run the script you downloaded from GitHub.


View all 3 instructions

Enjoy this project?



cyrus104 wrote 02/25/2019 at 23:24 point

I wanted to see if you have worked on this project in awhile? I have several newer USB-C PD power supplies and would like to work on a converter from a USB-C PD source to maybe a NCP4371 chip that can charge a phone / tablet device with QC 2/3 tech only.

  Are you sure? yes | no

Techman83 wrote 02/20/2018 at 14:25 point

Using the Voltage Dividers with GPIOs like that is really clever!

  Are you sure? yes | no

Similar Projects

Does this project spark your interest?

Become a member to follow this project and never miss any updates