Reading the fault pin
FLT goes low for an overcurrent trip or overheating. It is open drain with no pull-up on this board, and a single trip holds it low for only 1.35 ms before the driver retries, which is gone before a slow loop looks.
One pin, open drain
FLT is driven low by the chip when it has switched a bridge off to protect itself. It only ever pulls low — open drain — and this board fits no pull-up, so until your code enables one the pin floats and reads as noise. With a pull-up it reads high when all is well and low, at 0.5 V at most with 5 mA flowing, during a fault.
What pulls it low
Overcurrent. Each switch limits its own current. If that limit is still acting a few microseconds later, the chip switches off the bridge it happened in, drives FLT low, waits the retry period of 1.35 ms, then switches the bridge back on and releases FLT. The other bridge carries on throughout. The trip is somewhere between 2 and 3.3 A, and it does not use the sense resistors, so it works on this board with them at 0 Ω.
Overheating. Past a die temperature of 150 °C at the least (160 °C typical), the chip switches its outputs off and drives FLT low. It recovers by itself once it has cooled.
Undervoltage is the odd one. The datasheet's text says FLT is driven low when VM falls below the lockout; its own protection table says the lockout reports nothing. Do not rely on FLT to tell you the supply sagged. Measure VM.
A trip is short, a stuck fault is not
If the fault is still there at the retry, the bridge trips again almost at once. So a fault that stays, like a shorted motor lead, holds FLT low for all but a blip of every 1.35 ms, and a loop that polls the pin sees LOW nearly every time.
The one a polling loop misses is the single trip: a reversal at speed, a stiff motor starting from rest. FLT is low for 1.35 ms, the driver comes back, and a loop that looks every few milliseconds lands on either side of it. That is the trip worth knowing about, because it says the load is near the limit.
Catch the edge
Attach an interrupt on the falling edge and set a flag. loop() decides what to
do about it: pull SLP low, back the duty cycle off, report it, wait for a human.
Keep the handler to the flag. A fault that stays calls it about 740 times a
second, and a Serial.println in there takes the whole sketch down rather than
just missing a fault.
The code
A falling-edge interrupt sets a flag, loop() acts on it. The interrupt handler does nothing but write a volatile bool, because a fault that stays re-trips about 740 times a second and anything slower than a flag will not keep up. ESP32-S3; IRAM_ATTR is ESP32-specific.
// DRV8833 wiring for this sketch (ESP32-S3).
//
// GND -> GND common with the motor supply's ground
// VM -> 2.7-10.8 V motor supply. There is no logic supply pin.
// SLP -> GPIO 4 high to run; pulled low in the chip, so not optional
// FLT -> GPIO 16 open drain, needs INPUT_PULLUP
// AIN1 -> GPIO 5 channel A
// AIN2 -> GPIO 6 channel A
// Motor A across AOUT1 and AOUT2.
//
// Arduino IDE, Tools menu (esp32 core 3.x):
// Board ESP32S3 Dev Module
// USB CDC On Boot Enabled (Disabled if your USB goes through a
// USB-serial chip)
// Flash Size 16MB (128Mb)
// PSRAM OPI PSRAM
// Serial Monitor at 115200. No library needed.
const int SLP = 4;
const int FLT = 16;
const int AIN1 = 5;
const int AIN2 = 6;
volatile bool faulted = false;
void IRAM_ATTR onFault() {
faulted = true; // a flag, and nothing else
}
void setup() {
Serial.begin(115200);
pinMode(SLP, OUTPUT);
pinMode(AIN1, OUTPUT);
pinMode(AIN2, OUTPUT);
pinMode(FLT, INPUT_PULLUP); // the board fits no pull-up of its own
attachInterrupt(digitalPinToInterrupt(FLT), onFault, FALLING);
digitalWrite(SLP, HIGH);
delay(1); // up to 1 ms to wake
}
void loop() {
digitalWrite(AIN2, LOW); // forward, full speed
digitalWrite(AIN1, HIGH);
if (faulted) {
digitalWrite(SLP, LOW); // both bridges off
Serial.println("fault - driver asleep, fix the load before resuming");
delay(2000);
faulted = false;
digitalWrite(SLP, HIGH);
delay(1);
}
}Serial.println inside an ISR is the classic version of this bug: it blocks, and at hundreds of interrupts a second it will take the sketch down. Set the flag, print in loop().
When it does not work
First the pull-up: FLT is open drain with none fitted, so without INPUT_PULLUP it floats. Then the arithmetic: the trip is at 2 to 3.3 A, and a small motor's stall current, VM divided by its winding resistance, is often well under that. A stall below the trip is not a fault to this chip, and FLT stays high.
An un-pulled open-drain pin reads as noise, and an interrupt attached to noise fires on noise. Confirm INPUT_PULLUP is set on that pin and that the pin is not shared with anything else on the board.
That is how overcurrent protection works on this chip: only the bridge that tripped is switched off, and the other carries on. FLT is shared, so the pin alone does not say which channel it was. The motor that stopped does.
The same four pins, a different order of the same commands, and one motor that holds a position instead of two that do not.
A bipolar stepper instead →Edit this page — content/books/drv8833/reading-the-fault-pin.mdx
Questions about this product
See what other owners have asked, and read their solutions.
DRV8833 Dual Motor Driver
Loading discussions…
Discuss this article
Ask about this page. The answer stays here, on the page it belongs to, for whoever hits the same wall next.