File indexing completed on 2025-05-11 08:24:06
0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028
0029
0030 #include <stdlib.h>
0031 #include <stdio.h>
0032 #include <string.h>
0033
0034 #include <grlib/gpiolib.h>
0035
0036 #include <grlib/grlib_impl.h>
0037
0038 struct gpiolib_port;
0039
0040 struct gpiolib_port {
0041 struct gpiolib_port *next;
0042 int minor;
0043 struct gpiolib_drv *drv;
0044 void *handle;
0045
0046 int open;
0047 };
0048
0049
0050 struct gpiolib_port *gpiolib_ports;
0051
0052
0053 static int port_nr;
0054
0055
0056 static int gpiolib_initied = 0;
0057
0058
0059 static void gpiolib_list_add(struct gpiolib_port *port)
0060 {
0061 port->next = gpiolib_ports;
0062 gpiolib_ports = port;
0063 }
0064
0065 static struct gpiolib_port *gpiolib_find(int minor)
0066 {
0067 struct gpiolib_port *p;
0068
0069 p = gpiolib_ports;
0070 while ( p && (p->minor != minor) ) {
0071 p = p->next;
0072 }
0073 return p;
0074 }
0075
0076 static struct gpiolib_port *gpiolib_find_by_name(char *name)
0077 {
0078 struct gpiolib_port *p;
0079 struct gpiolib_info info;
0080 int (*get_info)(void *, struct gpiolib_info *);
0081
0082 p = gpiolib_ports;
0083 while ( p ) {
0084 get_info = p->drv->ops->get_info;
0085 if ( get_info && (get_info(p->handle, &info) == 0) ) {
0086 if ( strncmp(name, (char *)&info.devName[0], 64) == 0 ) {
0087 break;
0088 }
0089 }
0090 p = p->next;
0091 }
0092 return p;
0093 }
0094
0095 int gpiolib_drv_register(struct gpiolib_drv *drv, void *handle)
0096 {
0097 struct gpiolib_port *port;
0098
0099 if ( !drv || !drv->ops )
0100 return -1;
0101
0102 port = grlib_calloc(1, sizeof(*port));
0103 if ( port == NULL )
0104 return -1;
0105
0106 port->handle = handle;
0107 port->minor = port_nr++;
0108 port->drv = drv;
0109
0110 gpiolib_list_add(port);
0111
0112 return 0;
0113 }
0114
0115 void gpiolib_show(int port, void *handle)
0116 {
0117 struct gpiolib_port *p;
0118
0119 if ( port == -1 ) {
0120 p = gpiolib_ports;
0121 while (p != NULL) {
0122 if ( p->drv->ops->show )
0123 p->drv->ops->show(p->handle);
0124 p = p->next;
0125 }
0126 } else {
0127 if ( handle ) {
0128 p = handle;
0129 } else {
0130 p = gpiolib_find(port);
0131 }
0132 if ( p == NULL ) {
0133 printf("PORT %d NOT FOUND\n", port);
0134 return;
0135 }
0136 if ( p->drv->ops->show )
0137 p->drv->ops->show(p->handle);
0138 }
0139 }
0140
0141 static void *gpiolib_open_internal(int port, char *devName)
0142 {
0143 struct gpiolib_port *p;
0144
0145 if ( gpiolib_initied == 0 )
0146 return NULL;
0147
0148
0149 if ( port >= 0 ) {
0150 p = gpiolib_find(port);
0151 } else {
0152 p = gpiolib_find_by_name(devName);
0153 }
0154 if ( p == NULL )
0155 return NULL;
0156
0157 if ( p->open )
0158 return NULL;
0159
0160 p->open = 1;
0161 return p;
0162 }
0163
0164 void *gpiolib_open(int port)
0165 {
0166 return gpiolib_open_internal(port, NULL);
0167 }
0168
0169 void *gpiolib_open_by_name(char *devName)
0170 {
0171 return gpiolib_open_internal(-1, devName);
0172 }
0173
0174 void gpiolib_close(void *handle)
0175 {
0176 struct gpiolib_port *p = handle;
0177
0178 if ( p && p->open ) {
0179 p->open = 0;
0180 }
0181 }
0182
0183 int gpiolib_set_config(void *handle, struct gpiolib_config *cfg)
0184 {
0185 struct gpiolib_port *port = handle;
0186
0187 if ( !port || !cfg )
0188 return -1;
0189
0190 if ( !port->drv->ops->config )
0191 return -1;
0192
0193 return port->drv->ops->config(port->handle, cfg);
0194 }
0195
0196 int gpiolib_set(void *handle, int dir, int outval)
0197 {
0198 struct gpiolib_port *port = handle;
0199
0200 if ( !port )
0201 return -1;
0202
0203 if ( !port->drv->ops->set )
0204 return -1;
0205
0206 return port->drv->ops->set(port->handle, dir, outval);
0207 }
0208
0209 int gpiolib_get(void *handle, int *inval)
0210 {
0211 struct gpiolib_port *port = handle;
0212
0213 if ( !port || !inval)
0214 return -1;
0215
0216 if ( !port->drv->ops->get )
0217 return -1;
0218
0219 return port->drv->ops->get(port->handle, inval);
0220 }
0221
0222
0223 int gpiolib_irq_register(void *handle, void *func, void *arg)
0224 {
0225 struct gpiolib_port *port = handle;
0226
0227 if ( !port )
0228 return -1;
0229
0230 if ( !port->drv->ops->irq_register )
0231 return -1;
0232
0233 return port->drv->ops->irq_register(port->handle, func, arg);
0234 }
0235
0236 static int gpiolib_irq_opts(void *handle, unsigned int options)
0237 {
0238 struct gpiolib_port *port = handle;
0239
0240 if ( !port )
0241 return -1;
0242
0243 if ( !port->drv->ops->irq_opts )
0244 return -1;
0245
0246 return port->drv->ops->irq_opts(port->handle, options);
0247 }
0248
0249 int gpiolib_irq_clear(void *handle)
0250 {
0251 return gpiolib_irq_opts(handle, GPIOLIB_IRQ_CLEAR);
0252 }
0253
0254 int gpiolib_irq_force(void *handle)
0255 {
0256 return gpiolib_irq_opts(handle, GPIOLIB_IRQ_FORCE);
0257 }
0258
0259 int gpiolib_irq_enable(void *handle)
0260 {
0261 return gpiolib_irq_opts(handle, GPIOLIB_IRQ_ENABLE);
0262 }
0263
0264 int gpiolib_irq_disable(void *handle)
0265 {
0266 return gpiolib_irq_opts(handle, GPIOLIB_IRQ_DISABLE);
0267 }
0268
0269 int gpiolib_irq_mask(void *handle)
0270 {
0271 return gpiolib_irq_opts(handle, GPIOLIB_IRQ_MASK);
0272 }
0273
0274 int gpiolib_irq_unmask(void *handle)
0275 {
0276 return gpiolib_irq_opts(handle, GPIOLIB_IRQ_UNMASK);
0277 }
0278
0279
0280
0281 int gpiolib_initialize(void)
0282 {
0283 if ( gpiolib_initied != 0 )
0284 return 0;
0285
0286
0287 port_nr = 0;
0288 gpiolib_ports = 0;
0289 gpiolib_initied = 1;
0290 return 0;
0291 }