+++ /dev/null
-P8_07,66
-P8_08,67
-P8_09,69
-P8_10,68
-P8_11,45
-P8_12,44
-P8_13,23
-P8_14,26
-P8_15,47
-P8_16,46
-P8_17,27
-P8_18,65
-P8_19,22
-P8_26,61
-P8_27,86
-P8_28,88
-P8_29,87
-P8_30,89
-P8_31,10
-P8_32,11
-P8_33,9
-P8_34,81
-P8_35,8
-P8_36,80
-P8_37,78
-P8_38,79
-P8_39,76
-P8_40,77
-P8_41,74
-P8_42,75
-P8_43,72
-P8_44,73
-P8_45,70
-P8_46,71
-P9_11,30
-P9_12,60
-P9_13,31
-P9_14,50
-P9_15,48
-P9_16,51
-P9_17,5
-P9_18,4
-P9_21,3
-P9_22,2
-P9_23,49
-P9_24,15
-P9_25,117
-P9_26,14
-P9_27,115
-P9_30,112
+++ /dev/null
-P8_03,38
-P8_04,39
-P8_05,34
-P8_06,35
-P8_07,66
-P8_08,67
-P8_09,69
-P8_10,68
-P8_11,45
-P8_12,44
-P8_13,23
-P8_14,26
-P8_15,47
-P8_16,46
-P8_17,27
-P8_18,65
-P8_19,22
-P8_20,63
-P8_21,62
-P8_22,37
-P8_23,36
-P8_24,33
-P8_25,1
-P8_26,61
-P8_27,86
-P8_28,88
-P8_29,87
-P8_30,89
-P8_31,10
-P8_32,11
-P8_33,9
-P8_34,81
-P8_35,8
-P8_36,80
-P8_37,78
-P8_38,79
-P8_39,76
-P8_40,77
-P8_41,74
-P8_42,75
-P8_43,72
-P8_44,73
-P8_45,70
-P8_46,71
-P9_11,30
-P9_12,60
-P9_13,31
-P9_14,50
-P9_15,48
-P9_16,51
-P9_17,5
-P9_18,4
-P9_19,13
-P9_20,12
-P9_21,3
-P9_22,2
-P9_23,49
-P9_24,15
-P9_25,117
-P9_26,14
-P9_27,115
-P9_28,113
-P9_29,111
-P9_30,112
-P9_31,110
--- /dev/null
+P8_07,66
+P8_08,67
+P8_09,69
+P8_10,68
+P8_11,45
+P8_12,44
+P8_14,26
+P8_15,47
+P8_16,46
+P8_17,27
+P8_18,65
+P8_26,61
+P8_27,86
+P8_28,88
+P8_29,87
+P8_30,89
+P8_31,10
+P8_32,11
+P8_33,9
+P8_34,81
+P8_35,8
+P8_36,80
+P8_37,78
+P8_38,79
+P8_39,76
+P8_40,77
+P8_41,74
+P8_42,75
+P8_43,72
+P8_44,73
+P8_45,70
+P8_46,71
+P9_11,30
+P9_12,60
+P9_13,31
+P9_15,48
+P9_17,5
+P9_18,4
+P9_23,49
+P9_24,15
+P9_25,117
+P9_26,14
+P9_27,115
+P9_30,112
--- /dev/null
+import sys, re, os
+from parseit import printlut
+
+def doit2(x):
+ with open(x) as f:
+ lut = {}
+ rlut = {}
+ i = 0
+ for line in f:
+ gpionum = int(line)
+ lut[gpionum] = i
+ rlut[i] = gpionum
+ i += 1
+
+ lutarr = []
+ reverse = []
+ for i in range(118): #Max safe gpio is 117
+ lutarr.append(lut.get(i, 128))
+ for i in range(len(rlut)):
+ reverse.append(rlut[i])
+ return (lutarr, reverse)
+
--- /dev/null
+4
+5
+8
+9
+10
+11
+14
+15
+26
+27
+30
+31
+44
+45
+46
+47
+48
+49
+60
+61
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+86
+87
+88
+89
+112
+115
+117
--- /dev/null
+import sys, re, os
+#lut size of 93 (46 pins/header; 2 headers; padding for 1-indexed)
+
+def doit(x):
+ '''generate the lut from the csv'''
+ lut = {}
+ reverselut = {}
+
+ with open(x) as f:
+ for line in f:
+ m = re.search("P(\d)_(\d+),(\d+)", line)
+ header = int(m.group(1))
+ pin = int(m.group(2))
+ gpionum = int(m.group(3))
+
+ if header==8:
+ header = 0
+ else:
+ header = 1
+
+ lut[header*46+pin] = gpionum
+ reverselut[gpionum] = header*46+pin
+ lutarr = []
+ reverselutarr =[]
+
+ for i in range(0, 93):
+ lutarr.append(lut.get(i, 0))
+
+ for i in range(0, 118): #Max safe GPIO is 117
+ reverselutarr.append(reverselut.get(i, 0))
+
+ return (lutarr, reverselutarr)
+
+def printlut(lut, name="g_gpio_lut"):
+ '''print the lut for C'''
+ rowsize = 14
+ print("const unsigned char %s[%d] = {" % (name, len(lut)))
+ low = 0
+ high = rowsize
+ for i in range(0, len(lut), rowsize):
+ print("\t", end="")
+ print(*("%3d" % g for g in lut[low:high]), sep=', ', end="")
+ low = high
+ high += rowsize
+ if low < len(lut):
+ print(",")
+ else:
+ print("")
+ print("}")
+
+
+
--- /dev/null
+GPIO Pin correspondence.xls - all maps with descriptions
+GPIO pin correspondence unrestricted.csv - all unused pins + hdmi pins
+GPIO pin correspondence.csv - all gpio pins
+
+max usable gpio: 117
\ No newline at end of file
+++ /dev/null
-import sys, re, os
-from parseit import printlut
-
-def doit2(x):
- with open(x) as f:
- lut = {}
- rlut = {}
- i = 0
- for line in f:
- gpionum = int(line)
- lut[gpionum] = i
- rlut[i] = gpionum
- i += 1
-
- lutarr = []
- reverse = []
- for i in range(128):
- lutarr.append(lut.get(i, 128))
- for i in range(len(rlut)):
- reverse.append(rlut[i])
- return (lutarr, reverse)
-
+++ /dev/null
-2
-3
-4
-5
-8
-9
-10
-11
-14
-15
-22
-23
-26
-27
-30
-31
-44
-45
-46
-47
-48
-49
-50
-51
-60
-61
-65
-66
-67
-68
-69
-70
-71
-72
-73
-74
-75
-76
-77
-78
-79
-80
-81
-86
-87
-88
-89
-112
-115
-117
+++ /dev/null
-import sys, re, os
-#lut size of 93 (46 pins/header; 2 headers; padding for 1-indexed)
-
-def doit(x):
- '''generate the lut from the csv'''
- lut = {}
- reverselut = {}
-
- with open(x) as f:
- for line in f:
- m = re.search("P(\d)_(\d+),(\d+)", line)
- header = int(m.group(1))
- pin = int(m.group(2))
- gpionum = int(m.group(3))
-
- if header==8:
- header = 0
- else:
- header = 1
-
- lut[header*46+pin] = gpionum
- reverselut[gpionum] = header*46+pin
- lutarr = []
- reverselutarr =[]
-
- for i in range(0, 93):
- lutarr.append(lut.get(i, 0))
-
- for i in range(0, 128):
- reverselutarr.append(reverselut.get(i, 0))
-
- return (lutarr, reverselutarr)
-
-def printlut(lut, name="g_gpio_lut"):
- '''print the lut for C'''
- rowsize = 14
- print("const unsigned char %s[%d] = {" % (name, len(lut)))
- low = 0
- high = rowsize
- for i in range(0, len(lut), rowsize):
- print("\t", end="")
- print(*("%3d" % g for g in lut[low:high]), sep=', ', end="")
- low = high
- high += rowsize
- if low < len(lut):
- print(",")
- else:
- print("")
- print("}")
-
-
-
+++ /dev/null
-GPIO Pin correspondence.xls - all maps with descriptions
-GPIO pin correspondence unrestricted.csv - all unused pins + hdmi pins
-GPIO pin correspondence.csv - all gpio pins
\ No newline at end of file
*/
typedef struct
{
+ bool initialised;
int fd_value;
int fd_direction;
} GPIO_Pin;
*/
typedef struct
{
+ bool initialised;
int fd_value;
} ADC_Pin;
*/
typedef struct
{
+ bool initialised;
int fd_run;
FILE * file_duty;
FILE * file_period;
/** Array of PWM pins **/
static PWM_Pin g_pwm[PWM_NUM_PINS] = {{0}};
-static char g_buffer[BUFSIZ] = "";
-
+static char g_buffer[BUFSIZ] = {0};
/**
* Export a GPIO pin and open the file descriptors
+ * @param pin The GPIO number to be exported
+ * @return true on success, false otherwise
*/
-void GPIO_Export(int pin)
+bool GPIO_Export(int pin)
{
- if (pin < 0 || pin >= GPIO_INDEX_SIZE || g_gpio_to_index[pin] == 128)
+ if (pin < 0 || pin > GPIO_MAX_NUMBER || g_pin_gpio_to_index[pin] == 128)
{
- Abort("Not a useable pin number: %d", pin);
+ AbortBool("Not a useable pin number: %d", pin);
+ }
+
+ GPIO_Pin *gpio = &g_gpio[g_pin_gpio_to_index[pin]];
+ if (gpio->initialised)
+ {
+ Log(LOGNOTE, "GPIO %d already initialised.", pin);
+ return true;
}
- GPIO_Pin *gpio = &g_gpio[g_gpio_to_index[pin]];
// Export the pin
sprintf(g_buffer, "%s/export", GPIO_DEVICE_PATH);
- FILE * export = fopen(g_buffer, "w");
- if (export == NULL)
+ FILE * file_export = fopen(g_buffer, "w");
+ if (file_export == NULL)
{
- Abort("Couldn't open %s to export GPIO pin %d - %s", g_buffer, pin, strerror(errno));
+ AbortBool("Couldn't open %s to export GPIO pin %d - %s", g_buffer, pin, strerror(errno));
}
-
- fprintf(export, "%d", pin);
- fclose(export);
+ fprintf(file_export, "%d", pin);
+ fclose(file_export);
// Setup direction file descriptor
sprintf(g_buffer, "%s/gpio%d/direction", GPIO_DEVICE_PATH, pin);
gpio->fd_direction = open(g_buffer, O_RDWR);
if (gpio->fd_direction < 0)
{
- Abort("Couldn't open %s for GPIO pin %d - %s", g_buffer, pin, strerror(errno));
+ AbortBool("Couldn't open %s for GPIO pin %d - %s", g_buffer, pin, strerror(errno));
}
-
// Setup value file descriptor
sprintf(g_buffer, "%s/gpio%d/value", GPIO_DEVICE_PATH, pin);
gpio->fd_value = open(g_buffer, O_RDWR);
if (gpio->fd_value < 0)
{
- Abort("Couldn't open %s for GPIO pin %d - %s", g_buffer, pin, strerror(errno));
+ close(gpio->fd_direction);
+ AbortBool("Couldn't open %s for GPIO pin %d - %s", g_buffer, pin, strerror(errno));
}
+ gpio->initialised = true;
Log(LOGDEBUG, "Exported GPIO%d", pin);
- //sleep(1);
+ return true;
}
/**
*/
void GPIO_Unexport(int pin)
{
- if (pin < 0 || pin >= GPIO_INDEX_SIZE || g_gpio_to_index[pin] == 128)
+ if (pin < 0 || pin > GPIO_MAX_NUMBER || g_pin_gpio_to_index[pin] == 128)
{
Abort("Not a useable pin number: %d", pin);
}
- GPIO_Pin *gpio = &g_gpio[g_gpio_to_index[pin]];
+ GPIO_Pin *gpio = &g_gpio[g_pin_gpio_to_index[pin]];
+ if (!gpio->initialised)
+ {
+ Abort("GPIO %d is already uninitialised", pin);
+ }
+
// Close file descriptors
close(gpio->fd_value);
close(gpio->fd_direction);
+ // Uninitialise this one
+ gpio->initialised = false;
// Unexport the pin
-
if (g_buffer[0] == '\0')
sprintf(g_buffer, "%s/unexport", GPIO_DEVICE_PATH);
- FILE * export = fopen(g_buffer, "w");
- if (export == NULL)
+ FILE * file_export = fopen(g_buffer, "w");
+ if (file_export == NULL)
{
Abort("Couldn't open %s to export GPIO pin %d - %s", g_buffer, pin, strerror(errno));
}
- fprintf(export, "%d", pin);
- fclose(export);
+ fprintf(file_export, "%d", pin);
+ fclose(file_export);
}
-
/**
* Initialise all PWM pins and open file descriptors
* @param pin - The sysfs pin number
+ * @return true if exported, false otherwise
*/
-void PWM_Export(int pin)
+bool PWM_Export(int pin)
{
+ //goto would make this easier...
if (pin < 0 || pin >= PWM_NUM_PINS)
{
- Abort("Invalid PWM pin number %d specified.", pin);
+ AbortBool("Invalid PWM pin %d specified.", pin);
}
PWM_Pin *pwm = &g_pwm[pin];
+ if (pwm->initialised)
+ {
+ Log(LOGNOTE, "PWM %d already exported.", pin);
+ return true;
+ }
- if (pwm->file_duty != NULL)
+ // Try export the pin, doesn't matter if it's already exported.
+ sprintf(g_buffer, "%s/export", PWM_DEVICE_PATH);
+ FILE * file_export = fopen(g_buffer, "w");
+ if (file_export == NULL)
{
- Abort("PWM %d already exported.", pin);
+ AbortBool("Couldn't open %s to export PWM pin %d - %s",
+ g_buffer, pin, strerror(errno));
}
+ fprintf(file_export, "%d\n", pin);
+ fclose(file_export);
// Open file descriptors
sprintf(g_buffer, "%s/pwm%d/run", PWM_DEVICE_PATH, pin);
pwm->fd_run = open(g_buffer, O_WRONLY);
if (pwm->fd_run < 0)
{
- Abort("Couldn't open %s for PWM%d - %s", g_buffer, pin, strerror(errno));
+ AbortBool("Couldn't open %s for PWM%d - %s", g_buffer, pin, strerror(errno));
}
sprintf(g_buffer, "%s/pwm%d/polarity", PWM_DEVICE_PATH, pin);
pwm->fd_polarity = open(g_buffer, O_WRONLY);
if (pwm->fd_polarity < 0)
{
- Abort("Couldn't open %s for PWM%d - %s", g_buffer, pin, strerror(errno));
+ close(pwm->fd_run);
+ AbortBool("Couldn't open %s for PWM%d - %s", g_buffer, pin, strerror(errno));
}
sprintf(g_buffer, "%s/pwm%d/period_ns", PWM_DEVICE_PATH, pin);
pwm->file_period = fopen(g_buffer, "w");
if (pwm->file_period == NULL)
{
- Abort("Couldn't open %s for PWM%d - %s", g_buffer, pin, strerror(errno));
+ close(pwm->fd_run);
+ close(pwm->fd_polarity);
+ AbortBool("Couldn't open %s for PWM%d - %s", g_buffer, pin, strerror(errno));
}
sprintf(g_buffer, "%s/pwm%d/duty_ns", PWM_DEVICE_PATH, pin);
pwm->file_duty = fopen(g_buffer, "w");
if (pwm->file_duty == NULL)
{
- Abort("Couldn't open %s for PWM%d - %s", g_buffer, pin, strerror(errno));
+ close(pwm->fd_run);
+ close(pwm->fd_polarity);
+ fclose(pwm->file_period);
+ AbortBool("Couldn't open %s for PWM%d - %s", g_buffer, pin, strerror(errno));
}
// Don't buffer the streams
setbuf(pwm->file_period, NULL);
setbuf(pwm->file_duty, NULL);
+ pwm->initialised = true;
Log(LOGDEBUG, "Exported PWM%d", pin);
+ return true;
}
+
/**
* Unexport a PWM pin and close its file descriptors
* @param pin - The sysfs pin number
}
PWM_Pin *pwm = &g_pwm[pin];
- // Close the file descriptors
- if (pwm->fd_polarity != -1)
- close(pwm->fd_polarity);
- if (pwm->fd_run != -1)
- close(pwm->fd_run);
- if (pwm->file_period != NULL)
- fclose(pwm->file_period);
- if (pwm->file_duty != NULL)
- fclose(pwm->file_duty);
+ if (!pwm->initialised)
+ {
+ Abort("PWM %d not initialised", pin);
+ }
- //So that another call to PWM_Unexport is OK.
- pwm->fd_polarity = pwm->fd_run = -1;
- pwm->file_period = pwm->file_duty = NULL;
+ // Close the file descriptors
+ close(pwm->fd_polarity);
+ //Stop it, if it's still running
+ pwrite(pwm->fd_run, "0", 1, 0);
+ close(pwm->fd_run);
+ fclose(pwm->file_period);
+ fclose(pwm->file_duty);
+
+ pwm->initialised = false;
+
+ // Try unexport the pin, doesn't matter if it's already unexported.
+ sprintf(g_buffer, "%s/unexport", PWM_DEVICE_PATH);
+ FILE * file_unexport = fopen(g_buffer, "w");
+ if (file_unexport == NULL)
+ {
+ Abort("Couldn't open %s to unexport PWM pin %d - %s", g_buffer, pin, strerror(errno));
+ }
+ fprintf(file_unexport, "%d\n", pin);
+ fclose(file_unexport);
}
-
/**
* Initialise ADC structures
* @param pin The ADC pin number
*/
-void ADC_Export(int pin)
+bool ADC_Export(int pin)
{
if (pin < 0 || pin >= ADC_NUM_PINS)
{
- Abort("Invalid ADC pin %d specified.", pin);
+ AbortBool("Invalid ADC pin %d specified.", pin);
+ }
+ else if (g_adc[pin].initialised)
+ {
+ Log(LOGNOTE, "ADC %d already initialised", pin);
+ return true;
}
sprintf(g_buffer, "%s/in_voltage%d_raw", g_options.adc_device_path, pin);
g_adc[pin].fd_value = open(g_buffer, O_RDONLY);
if (g_adc[pin].fd_value <0)
{
- Abort("Couldn't open ADC %d device file %s - %s", pin, g_buffer, strerror(errno));
+ AbortBool("Couldn't open ADC %d device file %s - %s", pin, g_buffer, strerror(errno));
}
+
+ g_adc[pin].initialised = true;
Log(LOGDEBUG, "Opened ADC %d", pin);
+ return true;
}
/**
{
Abort("Invalid ADC pin %d specified.", pin);
}
- if (pin != -1)
- close(g_adc[pin].fd_value);
+ else if (!g_adc[pin].initialised)
+ {
+ Abort("ADC %d already uninitialised", pin);
+ }
+ close(g_adc[pin].fd_value);
g_adc[pin].fd_value = -1;
+ g_adc[pin].initialised = false;
}
/**
* Set a GPIO pin
* @param pin - The pin to set. MUST have been exported before calling this function.
*/
-void GPIO_Set(int pin, bool value)
+bool GPIO_Set(int pin, bool value)
{
- if (pin < 0 || pin >= GPIO_INDEX_SIZE || g_gpio_to_index[pin] == 128)
+ if (pin < 0 || pin > GPIO_MAX_NUMBER || g_pin_gpio_to_index[pin] == 128)
{
- Abort("Not a useable pin number: %d", pin);
+ AbortBool("Not a useable pin number: %d", pin);
}
- GPIO_Pin *gpio = &g_gpio[g_gpio_to_index[pin]];
-
+ GPIO_Pin *gpio = &g_gpio[g_pin_gpio_to_index[pin]];
+ if (gpio->initialised)
+ {
+ AbortBool("GPIO %d is not initialised.", pin);
+ }
+ //Set the pin direction
if (pwrite(gpio->fd_direction, "out", 3, 0) != 3)
{
- Abort("Couldn't set GPIO %d direction - %s", pin, strerror(errno));
+ AbortBool("Couldn't set GPIO %d direction - %s", pin, strerror(errno));
}
- char c = '0' + (value);
+ char c = value ? '1' : '0';
if (pwrite(gpio->fd_value, &c, 1, 0) != 1)
{
- Abort("Couldn't read GPIO %d value - %s", pin, strerror(errno));
+ AbortBool("Couldn't read GPIO %d value - %s", pin, strerror(errno));
}
+ return true;
}
/**
* Read from a GPIO Pin
* @param pin - The pin to read
+ * @param result A pointer to store the result
+ * @return true on success, false otherwise
*/
-bool GPIO_Read(int pin)
+bool GPIO_Read(int pin, bool *result)
{
- if (pin < 0 || pin >= GPIO_INDEX_SIZE || g_gpio_to_index[pin] == 128)
+ if (pin < 0 || pin > GPIO_MAX_NUMBER || g_pin_gpio_to_index[pin] == 128)
{
- Log(LOGERR, "Not a useable pin number: %d", pin);
- return false;
+ AbortBool("Not a useable pin number: %d", pin);
}
- GPIO_Pin *gpio = &g_gpio[g_gpio_to_index[pin]];
+ GPIO_Pin *gpio = &g_gpio[g_pin_gpio_to_index[pin]];
if (pwrite(gpio->fd_direction, "in", 2, 0) != 2)
- Log(LOGERR,"Couldn't set GPIO %d direction - %s", pin, strerror(errno));
+ AbortBool("Couldn't set GPIO %d direction - %s", pin, strerror(errno));
+
char c = '0';
if (pread(gpio->fd_value, &c, 1, 0) != 1)
- Log(LOGERR,"Couldn't read GPIO %d value - %s", pin, strerror(errno));
-
- return (c == '1');
+ AbortBool("Couldn't read GPIO %d value - %s", pin, strerror(errno));
+ *result = (c == '1');
+ return true;
}
/**
* @param period - The period in ns
* @param duty - The time the pin is active in ns
*/
-void PWM_Set(int pin, bool polarity, long period, long duty)
+bool PWM_Set(int pin, bool polarity, long period, long duty)
{
Log(LOGDEBUG, "Pin %d, pol %d, period: %lu, duty: %lu", pin, polarity, period, duty);
if (pin < 0 || pin >= PWM_NUM_PINS)
{
- Abort("Invalid PWM pin number %d specified.", pin);
+ AbortBool("Invalid PWM pin number %d specified.", pin);
}
PWM_Pin *pwm = &g_pwm[pin];
+ if (!pwm->initialised)
+ {
+ AbortBool("PWM %d is not initialised.", pin);
+ }
// Have to stop PWM before changing it
if (pwrite(pwm->fd_run, "0", 1, 0) != 1)
{
- Abort("Couldn't stop PWM%d - %s", pin, strerror(errno));
+ AbortBool("Couldn't stop PWM%d - %s", pin, strerror(errno));
}
char c = polarity ? '1' : '0';
if (pwrite(pwm->fd_polarity, &c, 1, 0) != 1)
{
- Abort("Couldn't set PWM%d polarity - %s", pin, strerror(errno));
+ AbortBool("Couldn't set PWM%d polarity - %s", pin, strerror(errno));
+ }
+
+ //This must be done first, otherwise period/duty settings can conflict
+ if (fwrite("0", 1, 1, pwm->file_duty) < 1)
+ {
+ AbortBool("Couldn't zero the duty for PWM%d - %s", pin, strerror(errno));
}
if (fprintf(pwm->file_period, "%lu", period) < 0)
{
- Abort("Couldn't set period for PWM%d - %s", pin, strerror(errno));
+ AbortBool("Couldn't set period for PWM%d - %s", pin, strerror(errno));
}
+
if (fprintf(pwm->file_duty, "%lu", duty) < 0)
{
- Abort("Couldn't set duty cycle for PWM%d - %s", pin, strerror(errno));
+ AbortBool("Couldn't set duty cycle for PWM%d - %s", pin, strerror(errno));
}
+
if (pwrite(pwm->fd_run, "1", 1, 0) != 1)
{
- Abort("Couldn't start PWM%d - %s", pin, strerror(errno));
+ AbortBool("Couldn't start PWM%d - %s", pin, strerror(errno));
}
+
+ return true;
}
/**
/**
* Read an ADC value
* @param id - The ID of the ADC pin to read
- * @returns - The reading of the ADC channel
+ * @param value - A pointer to store the value read from the ADC
+ * @returns - The true if succeeded, false otherwise.
*/
-int ADC_Read(int id)
+bool ADC_Read(int id, int *value)
{
char adc_str[ADC_DIGITS] = {0};
- if (pread(g_adc[id].fd_value, adc_str, ADC_DIGITS-1, 0) == -1)
+ if (id < 0 || id >= ADC_NUM_PINS)
+ {
+ AbortBool("Invalid ADC pin %d specified.", id);
+ }
+ else if (!g_adc[id].initialised)
{
- Log(LOGERR, "ADC %d read failed: %s", id, strerror(errno));
- return 0;
+ AbortBool("ADC %d is not initialised.", id);
}
- return strtol(adc_str, NULL, 10);
-}
+ if (pread(g_adc[id].fd_value, adc_str, ADC_DIGITS-1, 0) == -1)
+ {
+ AbortBool("ADC %d read failed: %s", id, strerror(errno));
+ }
+ *value = strtol(adc_str, NULL, 10);
+ return true;
+}
\ No newline at end of file
#if defined(_BBB) || defined(_BBB_PIN_SRC)
// Initialise / Deinitialise functions
-extern void GPIO_Export(int pin);
+extern bool GPIO_Export(int pin);
extern void GPIO_Unexport(int pin);
-extern void PWM_Export(int pin);
+extern bool PWM_Export(int pin);
extern void PWM_Unexport(int pin);
-extern void ADC_Export(int pin);
+extern bool ADC_Export(int pin);
extern void ADC_Unexport(int pin);
// Pin reading/setting functions
-extern bool GPIO_Read(int pin);
-extern void GPIO_Set(int pin, bool value);
+extern bool GPIO_Read(int pin, bool *result);
+extern bool GPIO_Set(int pin, bool value);
-extern int ADC_Read(int pin);
+extern bool ADC_Read(int id, int *value);
-extern void PWM_Set(int pin, bool polarity, long period, long duty); // period and duty are in ns
+extern bool PWM_Set(int pin, bool polarity, long period, long duty); // period and duty are in ns
extern void PWM_Stop(int pin);
+
#else
//Empty defines so it compiles on any platform that's not the BBB
-#define GPIO_Export(pin)
+
+extern bool GPIO_Export(int pin);
+extern void GPIO_Unexport(int pin);
+
+#define GPIO_Export(pin) true
#define GPIO_Unexport(pin)
-#define PWM_Export(pin)
+#define PWM_Export(pin) true
#define PWM_Unexport(pin)
-#define ADC_Export(pin)
+#define ADC_Export(pin) true
#define ADC_Unexport(pin)
-#define GPIO_Read(pin) 0
-#define GPIO_Set(pin, value)
-
-#define ADC_Read(pin) 0
+#define GPIO_Read(pin, result) ((*(result) = 0) == 0)
+#define GPIO_Set(pin, value) true
-#define PWM_Set(pin, polarity, period, duty)
-#define PWM_Stop(Pin)
+#define ADC_Read(id, value) ((*(value) = 0) == 0)
+#define PWM_Set(pin, polarity, period, duty) true
+#define PWM_Stop(pin)
#endif //_BBB
#include "bbb_pin_defines.h"
/**
- * A lookup table from header number to GPIO pin number.
- * e.g P8_13 is g_gpio_lut[0*46+13] = g_gpio_lut[13]
- * e.g P9_13 is g_gpio_lut[1*46+13] = g_gpio_lut[59]
+ * A lookup table from the actual pin number to GPIO number.
+ * e.g P8_13 is g_pin_real_to_gpio[0*46+13] = g_pin_real_to_gpio[13]
+ * e.g P9_13 is g_pin_real_to_gpio[1*46+13] = g_pin_real_to_gpio[59]
*
* Where the returned value is 0, there is no GPIO pin
* at that location.
*/
-const unsigned char g_pin_to_gpio[GPIO_LUT_SIZE] = {
- 0, 0, 0, 0, 0, 0, 0, 66, 67, 69, 68, 45, 44, 23,
- 26, 47, 46, 27, 65, 22, 0, 0, 0, 0, 0, 0, 61, 86,
+const unsigned char g_pin_real_to_gpio[BBB_PIN_COUNT+1] = {
+ 0, 0, 0, 0, 0, 0, 0, 66, 67, 69, 68, 45, 44, 0,
+ 26, 47, 46, 27, 65, 0, 0, 0, 0, 0, 0, 0, 61, 86,
88, 87, 89, 10, 11, 9, 81, 8, 80, 78, 79, 76, 77, 74,
75, 72, 73, 70, 71, 0, 0, 0, 0, 0, 0, 0, 0, 0,
- 0, 30, 60, 31, 50, 48, 51, 5, 4, 0, 0, 3, 2, 49,
+ 0, 30, 60, 31, 0, 48, 0, 5, 4, 0, 0, 0, 0, 49,
15, 117, 14, 115, 0, 0, 112, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0
};
/**
- * Converts GPIO number to index for g_gpio, or 128 if no map.
+ * Maps a GPIO number to an index into g_gpio (only for use in bbb_pin.c)
+ * If there is no index for that GPIO number, 128 is returned.
*/
-const unsigned char g_gpio_to_index[GPIO_INDEX_SIZE] = {
- 128, 128, 0, 1, 2, 3, 128, 128, 4, 5, 6, 7, 128, 128,
- 8, 9, 128, 128, 128, 128, 128, 128, 10, 11, 128, 128, 12, 13,
- 128, 128, 14, 15, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
- 128, 128, 16, 17, 18, 19, 20, 21, 22, 23, 128, 128, 128, 128,
- 128, 128, 128, 128, 24, 25, 128, 128, 128, 26, 27, 28, 29, 30,
- 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 128, 128,
- 128, 128, 43, 44, 45, 46, 128, 128, 128, 128, 128, 128, 128, 128,
+const unsigned char g_pin_gpio_to_index[GPIO_MAX_NUMBER+1] = {
+ 128, 128, 128, 128, 0, 1, 128, 128, 2, 3, 4, 5, 128, 128,
+ 6, 7, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 8, 9,
+ 128, 128, 10, 11, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
+ 128, 128, 12, 13, 14, 15, 16, 17, 128, 128, 128, 128, 128, 128,
+ 128, 128, 128, 128, 18, 19, 128, 128, 128, 20, 21, 22, 23, 24,
+ 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 128, 128,
+ 128, 128, 37, 38, 39, 40, 128, 128, 128, 128, 128, 128, 128, 128,
128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
- 47, 128, 128, 48, 128, 49, 128, 128, 128, 128, 128, 128, 128, 128,
- 128, 128
+ 41, 128, 128, 42, 128, 43
};
/**
- * Converts index number of g_gpio into the gpio number
+ * Maps an index in g_gpio to the corresponding GPIO number.
*/
-const unsigned char g_index_to_gpio[GPIO_NUM_PINS] = {
- 2, 3, 4, 5, 8, 9, 10, 11, 14, 15, 22, 23, 26, 27,
- 30, 31, 44, 45, 46, 47, 48, 49, 50, 51, 60, 61, 65, 66,
- 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80,
- 81, 86, 87, 88, 89, 112, 115, 117
+const unsigned char g_pin_index_to_gpio[GPIO_NUM_PINS] = {
+ 4, 5, 8, 9, 10, 11, 14, 15, 26, 27, 30, 31, 44, 45,
+ 46, 47, 48, 49, 60, 61, 65, 66, 67, 68, 69, 70, 71, 72,
+ 73, 74, 75, 76, 77, 78, 79, 80, 81, 86, 87, 88, 89, 112,
+ 115, 117
};
/**
#ifndef _BBB_PIN_DEFINES_H
#define _BBB_PIN_DEFINES_H
+/** The number of expansion pins on the BBB **/
+#define BBB_PIN_COUNT 92
+
/** GPIO0 defines **/
#define GPIO0_1 1
#define GPIO2_31 95
#define GPIO2_32 96
+/* Luts */
/** Number of useable GPIO pins **/
-#define GPIO_NUM_PINS 50
+#define GPIO_NUM_PINS 44
+/** The max usable GPIO number **/
+#define GPIO_MAX_NUMBER 117
-/* Luts */
-#define GPIO_LUT_SIZE 93
-#define GPIO_INDEX_SIZE 128
-extern const unsigned char g_pin_to_gpio[GPIO_LUT_SIZE];
-extern const unsigned char g_gpio_to_index[GPIO_INDEX_SIZE];
-extern const unsigned char g_index_to_gpio[GPIO_NUM_PINS];
+extern const unsigned char g_pin_real_to_gpio[BBB_PIN_COUNT+1];
+extern const unsigned char g_pin_gpio_to_index[GPIO_MAX_NUMBER+1];
+extern const unsigned char g_pin_index_to_gpio[GPIO_NUM_PINS];
/** Export path **/
#define GPIO_DEVICE_PATH "/sys/class/gpio"
#define Fatal(...) FatalEx(__func__, __FILE__, __LINE__, __VA_ARGS__)
/*** Macro to abort function ***/
-#define Abort(...) LogEx(LOGERR, __func__, __FILE__, __LINE__, __VA_ARGS__); return
+#define Abort(...) { LogEx(LOGERR, __func__, __FILE__, __LINE__, __VA_ARGS__); return; }
+#define AbortBool(...) { LogEx(LOGERR, __func__, __FILE__, __LINE__, __VA_ARGS__); return false; }
// An enum to make the severity of log messages human readable in code
enum {LOGERR=0, LOGWARN=1, LOGNOTE=2, LOGINFO=3,LOGDEBUG=4};
#include "sensor.h"
#include "actuator.h"
#include "control.h"
+#include "pin_test.h"
#include "bbb_pin_defines.h"
// --- Standard headers --- //
*/
void Pin_Init()
{
- for (int i = 0; i < GPIO_NUM_PINS; ++i)
+ //Don't export anything; make the user do it.
+ /*for (int i = 0; i < GPIO_NUM_PINS; ++i)
GPIO_Export(g_index_to_gpio[i]);
for (int i = 0; i < ADC_NUM_PINS; ++i)
ADC_Export(i);
//Only export 'safe' PWM pins that don't interfere with one another
- for (int i = 0; i < PWM_NUM_PINS; ++i)
- PWM_Export(g_pin_safe_pwm[i]);
+ for (int i = 0; i < PWM_NUM_SAFE_PINS; ++i)
+ PWM_Export(g_pin_safe_pwm[i]);*/
}
/**
void Pin_Close()
{
for (int i = 0; i < GPIO_NUM_PINS; ++i)
- GPIO_Unexport(g_index_to_gpio[i]);
+ GPIO_Unexport(g_pin_index_to_gpio[i]);
for (int i = 0; i < ADC_NUM_PINS; ++i)
ADC_Unexport(i);
}
Log(LOGDEBUG, "Reading GPIO%d", num);
FCGI_PrintRaw("Content-type: text/plain\r\n\r\n");
- FCGI_PrintRaw("GPIO%d reads %d\n", num, GPIO_Read(num));
+ bool ret;
+ if (!GPIO_Read(num, &ret))
+ FCGI_PrintRaw("GPIO%d read failed. Is it exported?", num);
+ else
+ FCGI_PrintRaw("GPIO%d reads %d\n", num, ret);
}
else if (strcmp(type, "adc") == 0)
}
Log(LOGDEBUG, "Reading ADC%d", num, set);
FCGI_PrintRaw("Content-type: text/plain\r\n\r\n");
- FCGI_PrintRaw("ADC%d reads %d\n", num, ADC_Read(num));
+ int raw_adc;
+ if (!ADC_Read(num, &raw_adc))
+ {
+ FCGI_PrintRaw("ADC%d read failed. Is it initialised?", num);
+ }
+ else
+ {
+ FCGI_PrintRaw("ADC%d reads %d\n", num, raw_adc);
+ }
}
else if (strcmp(type, "pwm") == 0)
{
FCGI_RejectJSON(context, "Invalid pin type");
}
-
-
-}
-
-//EOF
+}
\ No newline at end of file
Data_Init(&(g_sensors[i].data_file));
}
- // Get the ADCs
- //ADC_Export();
+ // Get the required ADCs
+ ADC_Export(0);
// GPIO1_28 used as a pulse for sampling
//GPIO_Export(GPIO1_28);
case 2:
{
static bool set = false;
-
+ int raw_adc = 0;
//GPIO_Set(GPIO0_30, true);
- d->value = (double)ADC_Read(ADC0); //ADC #0 on the Beaglebone
+ ADC_Read(ADC0, &raw_adc);
+ d->value = (double)raw_adc; //ADC #0 on the Beaglebone
//Log(LOGDEBUG, "Got value %f from ADC0", d->value);
//GPIO_Set(GPIO0_30, false);
set = !set;