Developing in C for the ATmega328P: Function - pinMode()

2 minute read

Where I describe the function - pinMode().


The function, pinMode() is one of the most important and one of the most forgotten of all of the Arduino framework. It is important, as it sets the function of the pin in question. And when its forgotten, hours of debugging may occur before the programmer realizes “the program works, I forgot to setup the pin”.

The Arduino Reference: Digital Pins also has a good description as to how pins and pinMode() works.


The ATmega328P datasheet provides the following details in regards to the pin functionality on a 28 pin dual-inline package (DIP):

  • 23 Programmable I/O Lines
  • Six PWM Channels
  • 6-channel 10-bit ADC in SPDIP Package
  • Programmable Serial USART
  • Master/Slave SPI Serial Interface
  • Byte-oriented 2-wire Serial Interface (Philips I2C compatible)
  • On-chip Analog Compactor
  • Interrupt and Wake-up on Pin Change

If you count the input and output lines separately, there are approximately 68 different pin functions provided. The only way this happens on a 28-pin DIP is to provide a mechanism to specify how the pins will be used. From an input/output (I/O) perspective, that mechanism is called pinMode().

Using pinMode()

For each one of the 20 I/O pints (D0-D13 and A0-A5), pinMode() is used to set one of the three functions, OUTPUT, INPUT and INPUT_PULLUP. The method to set the functionality is *pinMode(pin number, function)

  • OUTPUT: The pin functions as it is described in digitalWrite(). When the pin is set as OUTPUT, using digitalWrite(pin, HIGH), will set the pin HIGH and conversely when using digitalWrite(pin, LOW).
  • INPUT: The pin functions as it is described in digitalRead(). When the pin is set as INPUT, using digitalRead(pin), will return the value on the pin, HIGH if the voltage on the pin is near 5V and LOW, if near 0V. There is an in-determinant state if the voltage is not close to either 0V or 5V, and the behavior is beyond the scope of this explanation. Its best to use signals, where you feel comfortable they will completely switch between 0V and 5V. If this can’t happen, consider using analogRead().
  • INPUT_PULLUP: The pin functions almost the same as INPUT, however, if the pin isn’t grounded, it will be pulled-up to 5V by the virtue of an internal resistor. This too can help solve the issues described in INPUT with the in-determinant state. INPUT-PULLUP is typically used for interfaces such as buttons, where the button is pulled high when at rest, then connected to ground when pressed. This does provide an Active-low signal, meaning its 0, when active.

Comments powered by Talkyard.