pigpioj is a Java wrapper around the excellent Raspberry Pi C library pigpio. Note that the primary driver for developing pigpioj was to provide an optimised hardware interface library for the platform and device independent library diozero.
Make sure pigpio is installed on your Raspberry Pi:
sudo apt update && sudo apt -y install pigpio pigpiod pigpio-tools
pigpioj has two modes of operation:
- JNI
- Remote sockets
The JNI mode requires a small system library to be loaded at runtime that allows Java to invoke the pigpio C interface. This library is packaged in the pigpioj JAR file and is loaded automatically when uk.pigpioj.PigpioJ.getImplementation() is invoked.
pigpioj provides native libraries that are compiled for ARMv6, ARMv7 and AArch64 CPU architectures which are bundled within the pigpioj JAR file itself. At startup, pigpioj will detect the CPU architecture and dynamically load the appropriate JNI library. It will first look for libpigpioj.so on the Java library path, if not found it will extract the library from within the JAR file itself via a temporary file that is automatically deleted once loaded.
The optimisations within pigpio (using /dev/mem
) unfortunately requires root access.
Because of this all pigpioj applications that use the default JNI mode must be run as root.
In addition, the pigpio shared library must be installed on the Raspberry Pi; it can be installed by
running:
sudo apt update && sudo apt -y install libpigpio1 libpigpiod-if2-1
In addition, the pigpiod daemon process must not be running:
sudo systemctl stop pigpiod.service
The pigpiod daemon process can be disabled from automatically starting on a reboot:
sudo systemctl disable pigpiod.service
At the time of writing, the Ubuntu 64-bit operating system for Raspberry Pi didn't include the pigpio packages, hence must be built and installed from source code. Clone the pigpio GitHub repository, build and install it.
sudo apt update && sudo apt -y install git make gcc
git clone https://github.com/joan2937/pigpio.git --depth=1
cd pigpio
make
sudo make install
As per this pigpio issue, by default pigpio uses the
Pi's PCM hardware to time DMA transfers. pigpio can be configured to use the PWM hardware instead of
the PCM hardware by calling gpioCfgClock
before gpioInitialise
. To enable this in pigpioj, the
following variables must be set, either via command line or as environment variables:
- PIGPIO_CLOCK_CFG_MICROS
- PIGPIO_CLOCK_CFG_PERIPHERAL
If you need to compile the JNI library yourself you can do so either using a physical Raspberry Pi, or via the pigpioj Docker based cross compiler.
Clone pigpioj, build the Docker image and initiate the docker build process:
git clone git@github.com:mattjlewis/pigpioj.git
cd pigpioj/pigpioj-native/docker
docker build -t diozero/pigpioj-cc .
cd ..
./docker_build.sh
Once successful, this will result in the following folder structure:
lib
├── linux-aarch64
│ └── libpigpioj.so
├── linux-armv6
│ └── libpigpioj.so
└── linux-armv7
└── libpigpioj.so
Make sure that the pigpio development tools are installed:
sudo apt update && sudo apt -y install libpigpiod-if-dev
Unfortunately pigpio.h
is not included in any of the Raspberry Pi OS packages, first of all run
this command in the Pi user's home directory (the Makefile assumes the header files are in
/home/pi/pigpio
):
sudo apt update && sudo apt -y install git make gcc
git clone https://github.com/joan2937/pigpio.git --depth=1
cd pigpio
make
Copy the pigpioj-native source files to the Raspberry Pi and compile with make
.
git clone git@github.com:mattjlewis/pigpioj.git
cd pigpioj/pigpioj-native/src/main/native
make
This will produce a libpigpioj.so shared object library that needs to be made available on the Java library path at runtime.
By default pigpioj uses JNI mode; to switch to the remote socket mode you must set the PIGPIOD_HOST
variable, either via environment property or Java command line property. Examples:
Command line:
java -DPIGPIOD_HOST=«your-pigpiod-host» -cp pigpioj-2.5.11.jar:«your-app.jar» «your-main-class»
Environment variable:
export PIGPIOD_HOST=<your-pigpiod-host»
java -cp pigpioj-2.5.11.jar:«your-app.jar» «your-main-class»
The pigpiod daemon must be running on the Raspberry Pi for this to work.
sudo apt update && sudo apt -y install pigpio pigpio-tools pigpiod
sudo systemctl enable pigpiod.service
sudo systemctl start pigpiod.service
If pigpiod is configured to listen on a non-default port (the default is 8888) you will need to
set the PIGPIOD_PORT
property.
One key benefit of sockets mode is to enable remote communication - this means that you can use the exact same APIs to run applications on another machine, including a any laptop or desktop that can run Java.
For security reasons, the pigpiod daemon process can be limited to allow only local connections.
Check the ExecStart
parameter in /etc/systemd/system/pigpiod.service.d/public.conf
. If it has the -l
option then it will only allow connections from the local machine, e.g.:
ExecStart=/usr/bin/pigpiod -l
To change this behaviour, simply remove the -l
parameter from this file and restart the process:
sudo systemctl restart pigpiod.service
If the file doesn't exist, run the raspi-config
application and choose "3 Interface Options",
"P8 Remote GPIO" and select "Yes". This will make the appropriate changes and create that file if
it didn't already exist.
import uk.pigpioj.*;
public class PigpioTest {
public static void main(String[] args) throws InterruptedException {
int gpio = 16;
try (PigpioInterface pigpio_impl = PigpioJ.getImplementation()) {
pigpio_impl.setMode(gpio, PigpioConstants.MODE_PI_OUTPUT);
pigpio_impl.write(gpio, true);
Thread.sleep(1000);
pigpio_impl.write(gpio, false);
Thread.sleep(1000);
}
}
}
This library is used as a provider for the Raspberry Pi by the platform agnostic diozero Java library diozero.