Beagleboard GPIO Input (driverless)
The following example C program configures the beagleboard expansion header pins as GPIO inputs. the pins are configured all pull up. It then reads from these pins and output “1” if pin 3 ONLY is shorted to ground.
The code bypasses the kernel completely by mapping the memory containing the GPIO configuration registers directly. It does this by mmaping /dev/mem, to access system memory. You need to use O_SYNC when you do this to tell mmap the memory is uncacheable. It’ll work /a bit/ without but you’ll get weird artifacts.
Once you have access to memory you need to configure the pins to be used as GPIO. Each pin on the OMAP3530 can have up to 6 functions, by default the expansion header pins are configured for use as MMC and I2C ports. The pinconf code reconfigures these as GPIO, an input bit also needs to be set here. Next there another GPIO configuration register, which also needs setting to 1 for input. After this you can read GPIO data from the GPIO input register for bank 5. You can’t configure all the pins on bank 5 as input on the beagleboard, a couple of them are used for the main MMC port.
Bypassing the kernel isn’t the best way to access GPIO from userland. It’s possibly useful though if you’re planning to migrate the code in to a driver.
#include
#include
#include
#include
#include
#include
#include
#include
int main() {
int fd = open(“/dev/mem”, O_RDWR | O_SYNC);
if (fd < 0) { printf("Could not open memory\n"); return 0; } // Pad configuration volatile ulong *pinconf; pinconf = (ulong*) mmap(NULL, 0x10000, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0x48000000); if (pinconf == MAP_FAILED) { printf("Pinconf Mapping failed\n"); close(fd); return 0; } // Configure Expansion header pins as input. pinconf[0x2158/4] = 0x011C011C; pinconf[0x215C/4] = 0x011C011C; pinconf[0x2160/4] = 0x011C011C; pinconf[0x2164/4] = 0x011C011C; pinconf[0x2168/4] = 0x011C011C; pinconf[0x216C/4] = 0x011C011C; pinconf[0x2170/4] = 0x011C011C; pinconf[0x2188/4] = 0x011C011C; close(fd); fd = open("/dev/mem", O_RDWR | O_SYNC); // GPIO Configuration: configure are input volatile ulong *gpio; gpio = (ulong*) mmap(NULL, 0x10000, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0x49050000); if (gpio == MAP_FAILED) { printf("Gpio Mapping failed\n"); close(fd); return 0; } // Configure all GPIO pins on bank 5 as input. gpio[0x6034/4] = 0xFFFFFFFF; // Prints 1 when pin 3 of the Expansion header is Grounded. int c=0; for(;;) { if(gpio[0x6038/4] == 201390076) printf("1\n"); // printf("gpio5: %d \n",gpio[0x6038/4]); } } [/sourcecode]