Converting a raw analog to digital converter ADC reading of 512 to physical voltage depends entirely on your microcontroller's bit-depth and reference voltage. On a standard 5V, 10-bit Arduino Uno (ATmega328P), a raw value of 512 equals exactly 2.50V. On a 3.3V, 12-bit ESP32, that exact same raw value of 512 translates to just 0.41V.

The universal formula to convert a raw digital integer back to an analog voltage is:

V_in = ADC_raw × (V_ref / (2^n - 1))

Substituting the values for a 10-bit Arduino Uno with a 5.0V reference:

V_in = 512 × (5.0 / 1023) = 2.502V

The Core Conversion Formula and Assumptions

The mathematical conversion above assumes two fixed hardware states. The primary assumption that fixes this answer is a stable, noise-free reference voltage (V_ref) and a known bit-resolution (n). If your USB cable suffers from voltage drop and your Arduino's 5V rail is actually delivering 4.7V, your calculated 2.50V is physically wrong, even if the math is right.

Least Significant Bit (LSB) Step Size: On a 10-bit ADC with a 5V reference, each raw integer step represents 4.88mV (5V / 1023). On a 12-bit ESP32 with a 3.3V reference, each step represents 0.80mV (3.3V / 4095).

The second assumption is that the input signal impedance is low enough to fully charge the microcontroller's internal sample-and-hold capacitor during the acquisition time. According to the official Arduino analogRead() documentation, the source impedance should be kept under 10kΩ. If you use a 1MΩ voltage divider without a buffer op-amp, the ADC will read a lower voltage than reality because the internal 14pF capacitor cannot charge fully before the conversion completes.

How the Answer Shifts: 120V vs 230V vs 3-Phase Mains

An analog to digital converter ADC cannot directly read mains voltage; doing so will instantly destroy the microcontroller and pose a lethal shock hazard. To measure 120V AC, 230V AC, or 3-phase lines, you must step the voltage down using a transformer (like the ZMPT101B module) or a high-impedance resistor divider, then rectify and scale it to fit within your V_ref.

WARNING: Never connect mains voltage directly to a microcontroller pin. Always use isolated sensors or properly rated step-down modules, and verify local electrical codes before tapping into service panels.

Mains SystemNominal RMSPeak VoltageRequired Divider Ratio (for 3.3V ADC)Expected ADC Raw (12-bit)
US Residential120V AC~170V100:1 (Yields 1.70V peak)2112
EU/UK Residential230V AC~325V100:1 (Yields 3.25V peak)4042
Industrial 3-Phase400V AC (L-L)~565V200:1 (Yields 2.82V peak)3507

For 3-phase systems, the ADC reads phase-to-neutral voltage. You must measure each phase individually and apply a √3 multiplier in your firmware to calculate the phase-to-phase voltage. If your V_ref drifts due to thermal noise on the PCB, your mains calculations will compound the error, which is why precision metrology uses external dedicated ADC ICs (like the ADS1115) rather than internal microcontroller ADCs for mains monitoring.

When the Conversion is Meaningless

The raw-to-voltage conversion becomes mathematically meaningless in three scenarios:

  • Floating Pins: If the ADC pin is disconnected, it acts as an antenna, reading thermal noise and capacitive coupling. The raw value will fluctuate wildly.
  • Rail Clipping: If the input voltage exceeds V_ref, the ADC saturates. A 10-bit ADC will output 1023 whether the input is 5.0V or 12.0V, making it impossible to determine the actual voltage.
  • ESP32 ADC2 with WiFi: As noted in the Espressif ESP-IDF ADC documentation, the ADC2 peripheral is shared with the WiFi subsystem. If WiFi is active, ADC2 reads will fail or return garbage data.

Neighboring Values Lookup (±20% Range around 512)

When debugging sensor arrays or potentiometer sweeps, it helps to visualize the voltage curve around your target reading. Below is a lookup table showing a ±20% range around a raw ADC value of 512, calculated for both a 5V 10-bit system and a 3.3V 12-bit system.

Raw ADC ValueVoltage (5V, 10-bit Arduino)Voltage (3.3V, 12-bit ESP32)
410 (-20%)2.00V0.33V
4352.12V0.35V
4602.25V0.37V
4862.37V0.39V
512 (Base)2.50V0.41V
5382.63V0.43V
5632.75V0.45V
5892.88V0.47V
614 (+20%)3.00V0.49V

Frequently Asked Questions

Why does my ESP32 analog to digital converter ADC read erratic values when WiFi is on?

The ESP32 features two ADC units: ADC1 and ADC2. ADC2 shares internal hardware routing with the WiFi and Bluetooth radios. When the WiFi stack initializes, it takes control of ADC2, causing analogRead() on those specific pins (GPIO 0, 2, 4, 12-15, 25-27) to fail or return highly erratic data. To fix this, always route your critical analog sensors to ADC1 pins (GPIO 32-39) when building WiFi-connected IoT nodes.

How does source impedance affect my analog to digital converter ADC accuracy?

Inside the microcontroller, the ADC uses a tiny internal capacitor (typically 10pF to 14pF) to sample the incoming voltage. If your external circuit has a high resistance (e.g., a voltage divider using 1MΩ resistors), the RC time constant becomes too slow. The internal capacitor won't charge to the true voltage before the ADC takes its snapshot, resulting in a reading that is artificially low. Always keep source impedance below 10kΩ, or use an op-amp voltage follower to buffer the signal.

Can I increase the analog to digital converter ADC bit resolution on an Arduino Uno?

You cannot change the hardware resolution of the ATmega328P's internal ADC; it is physically limited to 10 bits (1024 steps). However, you can achieve pseudo-higher resolution (12-bit or 14-bit) through a technique called oversampling. By taking multiple rapid readings of a stable signal and averaging them, you can mathematically reduce noise and extract sub-LSB voltage changes. Alternatively, wire an external I2C ADC like the 16-bit ADS1115 to bypass the internal hardware entirely.