111e995b1SMatthias Ringwald #include "btstack_control.h"
211e995b1SMatthias Ringwald #include "btstack_debug.h"
311e995b1SMatthias Ringwald
411e995b1SMatthias Ringwald #include <stdlib.h>
511e995b1SMatthias Ringwald #include <unistd.h>
611e995b1SMatthias Ringwald #include <fcntl.h>
711e995b1SMatthias Ringwald #include <errno.h>
811e995b1SMatthias Ringwald #include <sys/ioctl.h>
911e995b1SMatthias Ringwald
1011e995b1SMatthias Ringwald // constansts for firmware interface
1111e995b1SMatthias Ringwald #define RPI_FIRMWARE_DEV "/dev/vcio"
1211e995b1SMatthias Ringwald #define IOCTL_RPI_FIRMWARE_PROPERTY _IOWR(100, 0, char*)
1311e995b1SMatthias Ringwald
1411e995b1SMatthias Ringwald // firmware request messages
1511e995b1SMatthias Ringwald #define RPI_FIRMWARE_STATUS_REQUEST (0)
1611e995b1SMatthias Ringwald #define RPI_FIRMWARE_PROPERTY_END (0)
1711e995b1SMatthias Ringwald #define RPI_FIRMWARE_SET_GPIO_STATE (0x00038041)
1811e995b1SMatthias Ringwald
1911e995b1SMatthias Ringwald // results
2011e995b1SMatthias Ringwald #define RPI_FIRMWARE_STATUS_SUCCESS (0x80000000)
2111e995b1SMatthias Ringwald #define RPI_FIRMWARE_STATUS_ERROR (0x80000001)
2211e995b1SMatthias Ringwald
23*55250ca2SMatthias Ringwald static uint8_t bt_reg_en;
24*55250ca2SMatthias Ringwald
btstack_control_raspi_set_bt_reg_en_pin(uint8_t bt_reg_en_pin)25*55250ca2SMatthias Ringwald void btstack_control_raspi_set_bt_reg_en_pin(uint8_t bt_reg_en_pin){
26*55250ca2SMatthias Ringwald bt_reg_en = bt_reg_en_pin;
27*55250ca2SMatthias Ringwald }
2811e995b1SMatthias Ringwald
2911e995b1SMatthias Ringwald // fd for firmware interface
3011e995b1SMatthias Ringwald static int fd = -1;
3111e995b1SMatthias Ringwald
raspi_gpio_set(int gpio,int state)3211e995b1SMatthias Ringwald static void raspi_gpio_set(int gpio, int state){
3311e995b1SMatthias Ringwald uint32_t m[8];
3411e995b1SMatthias Ringwald m[0] = sizeof(m); // total len in bytes
3511e995b1SMatthias Ringwald m[1] = RPI_FIRMWARE_STATUS_REQUEST;
3611e995b1SMatthias Ringwald m[2] = RPI_FIRMWARE_SET_GPIO_STATE;
3711e995b1SMatthias Ringwald m[3] = 8; // request size in bytes
3811e995b1SMatthias Ringwald m[4] = 0; // request response size
3911e995b1SMatthias Ringwald m[5] = gpio;
4011e995b1SMatthias Ringwald m[6] = state ? 1 : 0;
4111e995b1SMatthias Ringwald m[7] = RPI_FIRMWARE_PROPERTY_END;;
4211e995b1SMatthias Ringwald
4311e995b1SMatthias Ringwald int ioctl_result = ioctl(fd, IOCTL_RPI_FIRMWARE_PROPERTY, m);
4411e995b1SMatthias Ringwald if (ioctl_result == -1) {
4511e995b1SMatthias Ringwald log_error("ioctl: IOCTL_RPI_FIRMWARE_PROPERTY: %s", strerror(errno));
4611e995b1SMatthias Ringwald return;
4711e995b1SMatthias Ringwald }
4811e995b1SMatthias Ringwald
4911e995b1SMatthias Ringwald uint32_t result = m[1];
5011e995b1SMatthias Ringwald if (result != RPI_FIRMWARE_STATUS_SUCCESS) {
5111e995b1SMatthias Ringwald log_error("ioctl: firmware result 0x%08x\n", result);
5211e995b1SMatthias Ringwald }
5311e995b1SMatthias Ringwald }
5411e995b1SMatthias Ringwald
raspi_init(const void * config)5511e995b1SMatthias Ringwald static void raspi_init (const void *config) {
5611e995b1SMatthias Ringwald UNUSED(config);
5711e995b1SMatthias Ringwald
5811e995b1SMatthias Ringwald fd = open(RPI_FIRMWARE_DEV, O_NONBLOCK);
5911e995b1SMatthias Ringwald if (fd == -1) {
6011e995b1SMatthias Ringwald log_error("cannot open: %s: %s", RPI_FIRMWARE_DEV, strerror(errno));
6111e995b1SMatthias Ringwald return;
6211e995b1SMatthias Ringwald }
6311e995b1SMatthias Ringwald }
6411e995b1SMatthias Ringwald
raspi_on()6511e995b1SMatthias Ringwald static int raspi_on (){
6611e995b1SMatthias Ringwald log_info("raspi_on");
67*55250ca2SMatthias Ringwald raspi_gpio_set( bt_reg_en, 1 );
6811e995b1SMatthias Ringwald return 0;
6911e995b1SMatthias Ringwald }
7011e995b1SMatthias Ringwald
raspi_off(void)7111e995b1SMatthias Ringwald static int raspi_off(void){
7211e995b1SMatthias Ringwald log_info("raspi_off");
73*55250ca2SMatthias Ringwald raspi_gpio_set( bt_reg_en, 0 );
7411e995b1SMatthias Ringwald return 0;
7511e995b1SMatthias Ringwald }
7611e995b1SMatthias Ringwald
7711e995b1SMatthias Ringwald static btstack_control_t control = {
7811e995b1SMatthias Ringwald raspi_init,
7911e995b1SMatthias Ringwald raspi_on,
8011e995b1SMatthias Ringwald raspi_off,
8111e995b1SMatthias Ringwald NULL,
8211e995b1SMatthias Ringwald NULL,
8311e995b1SMatthias Ringwald NULL
8411e995b1SMatthias Ringwald };
8511e995b1SMatthias Ringwald
btstack_control_raspi_get_instance()8611e995b1SMatthias Ringwald btstack_control_t *btstack_control_raspi_get_instance(){
8711e995b1SMatthias Ringwald return &control;
8811e995b1SMatthias Ringwald }
89