Gordons Projects

--> Projects Top-Level GIT

461274f615815242cc9a1abd6215b594354e9175
[wiringPi] / gpio / gpio.c
1 /*
2  * gpio.c:
3  *      Swiss-Army-Knife, Set-UID command-line interface to the Raspberry
4  *      Pi's GPIO.
5  *      Copyright (c) 2012-2015 Gordon Henderson
6  ***********************************************************************
7  * This file is part of wiringPi:
8  *      https://projects.drogon.net/raspberry-pi/wiringpi/
9  *
10  *    wiringPi is free software: you can redistribute it and/or modify
11  *    it under the terms of the GNU Lesser General Public License as published by
12  *    the Free Software Foundation, either version 3 of the License, or
13  *    (at your option) any later version.
14  *
15  *    wiringPi is distributed in the hope that it will be useful,
16  *    but WITHOUT ANY WARRANTY; without even the implied warranty of
17  *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  *    GNU Lesser General Public License for more details.
19  *
20  *    You should have received a copy of the GNU Lesser General Public License
21  *    along with wiringPi.  If not, see <http://www.gnu.org/licenses/>.
22  ***********************************************************************
23  */
24
25
26 #include <stdio.h>
27 #include <stdlib.h>
28 #include <stdint.h>
29 #include <ctype.h>
30 #include <string.h>
31 #include <unistd.h>
32 #include <errno.h>
33 #include <fcntl.h>
34 #include <sys/types.h>
35 #include <sys/stat.h>
36
37 #include <wiringPi.h>
38 #include <wpiExtensions.h>
39
40 #include <gertboard.h>
41 #include <piFace.h>
42
43 #include "version.h"
44
45 extern int wiringPiDebug ;
46
47 // External functions I can't be bothered creating a separate .h file for:
48
49 extern void doReadall    (void) ;
50 extern void doPins       (void) ;
51
52 #ifndef TRUE
53 #  define       TRUE    (1==1)
54 #  define       FALSE   (1==2)
55 #endif
56
57 #define PI_USB_POWER_CONTROL    38
58 #define I2CDETECT               "/usr/sbin/i2cdetect"
59
60 int wpMode ;
61
62 char *usage = "Usage: gpio -v\n"
63               "       gpio -h\n"
64               "       gpio [-g|-1] [-x extension:params] ...\n"
65               "       gpio [-p] <read/write/wb> ...\n"
66               "       gpio <read/write/aread/awritewb/pwm/clock/mode> ...\n"
67               "       gpio readall/reset\n"
68               "       gpio unexportall/exports\n"
69               "       gpio export/edge/unexport ...\n"
70               "       gpio wfi <pin> <mode>\n"
71               "       gpio drive <group> <value>\n"
72               "       gpio pwm-bal/pwm-ms \n"
73               "       gpio pwmr <range> \n"
74               "       gpio pwmc <divider> \n"
75               "       gpio load spi/i2c\n"
76               "       gpio unload spi/i2c\n"
77               "       gpio i2cd/i2cdetect\n"
78               "       gpio usbp high/low\n"
79               "       gpio gbr <channel>\n"
80               "       gpio gbw <channel> <value>" ;     // No trailing newline needed here.
81
82
83 #ifdef  NOT_FOR_NOW
84 /*
85  * decodePin:
86  *      Decode a pin "number" which can actually be a pin name to represent
87  *      one of the Pi's on-board pins.
88  *********************************************************************************
89  */
90
91 static int decodePin (const char *str)
92 {
93
94 // The first case - see if it's a number:
95
96   if (isdigit (str [0]))
97     return atoi (str) ;
98
99   return 0 ;
100 }
101 #endif
102
103
104 /*
105  * changeOwner:
106  *      Change the ownership of the file to the real userId of the calling
107  *      program so we can access it.
108  *********************************************************************************
109  */
110
111 static void changeOwner (char *cmd, char *file)
112 {
113   uid_t uid = getuid () ;
114   uid_t gid = getgid () ;
115
116   if (chown (file, uid, gid) != 0)
117   {
118     if (errno == ENOENT)        // Warn that it's not there
119       fprintf (stderr, "%s: Warning (not an error): File not present: %s\n", cmd, file) ;
120     else
121       fprintf (stderr, "%s: Warning (not an error): Unable to change ownership of %s: %s\n", cmd, file, strerror (errno)) ;
122   }
123 }
124
125
126 /*
127  * moduleLoaded:
128  *      Return true/false if the supplied module is loaded
129  *********************************************************************************
130  */
131
132 static int moduleLoaded (char *modName)
133 {
134   int len   = strlen (modName) ;
135   int found = FALSE ;
136   FILE *fd = fopen ("/proc/modules", "r") ;
137   char line [80] ;
138
139   if (fd == NULL)
140   {
141     fprintf (stderr, "gpio: Unable to check modules: %s\n", strerror (errno)) ;
142     exit (1) ;
143   }
144
145   while (fgets (line, 80, fd) != NULL)
146   {
147     if (strncmp (line, modName, len) != 0)
148       continue ;
149
150     found = TRUE ;
151     break ;
152   }
153
154   fclose (fd) ;
155
156   return found ;
157 }
158
159
160 /*
161  * doLoad:
162  *      Load either the spi or i2c modules and change device ownerships, etc.
163  *********************************************************************************
164  */
165
166 static void _doLoadUsage (char *argv [])
167 {
168   fprintf (stderr, "Usage: %s load <spi/i2c> [I2C baudrate in Kb/sec]\n", argv [0]) ;
169   exit (1) ;
170 }
171
172 static void doLoad (int argc, char *argv [])
173 {
174   char *module1, *module2 ;
175   char cmd [80] ;
176   char *file1, *file2 ;
177   char args1 [32], args2 [32] ;
178
179   if (argc < 3)
180     _doLoadUsage (argv) ;
181
182   args1 [0] = args2 [0] = 0 ;
183
184   /**/ if (strcasecmp (argv [2], "spi") == 0)
185   {
186     module1 = "spidev" ;
187     module2 = "spi_bcm2708" ;
188     file1  = "/dev/spidev0.0" ;
189     file2  = "/dev/spidev0.1" ;
190     if (argc == 4)
191     {
192       fprintf (stderr, "%s: Unable to set the buffer size now. Load aborted. Please see the man page.\n", argv [0]) ;
193       exit (1) ;
194     }
195     else if (argc > 4)
196       _doLoadUsage (argv) ;
197   }
198   else if (strcasecmp (argv [2], "i2c") == 0)
199   {
200     module1 = "i2c_dev" ;
201     module2 = "i2c_bcm2708" ;
202     file1  = "/dev/i2c-0" ;
203     file2  = "/dev/i2c-1" ;
204     if (argc == 4)
205       sprintf (args2, " baudrate=%d", atoi (argv [3]) * 1000) ;
206     else if (argc > 4)
207       _doLoadUsage (argv) ;
208   }
209   else
210     _doLoadUsage (argv) ;
211
212   if (!moduleLoaded (module1))
213   {
214     sprintf (cmd, "/sbin/modprobe %s%s", module1, args1) ;
215     system (cmd) ;
216   }
217
218   if (!moduleLoaded (module2))
219   {
220     sprintf (cmd, "/sbin/modprobe %s%s", module2, args2) ;
221     system (cmd) ;
222   }
223
224   if (!moduleLoaded (module2))
225   {
226     fprintf (stderr, "%s: Unable to load %s\n", argv [0], module2) ;
227     exit (1) ;
228   }
229
230   sleep (1) ;   // To let things get settled
231
232   changeOwner (argv [0], file1) ;
233   changeOwner (argv [0], file2) ;
234 }
235
236
237 /*
238  * doUnLoad:
239  *      Un-Load either the spi or i2c modules and change device ownerships, etc.
240  *********************************************************************************
241  */
242
243 static void _doUnLoadUsage (char *argv [])
244 {
245   fprintf (stderr, "Usage: %s unload <spi/i2c>\n", argv [0]) ;
246   exit (1) ;
247 }
248
249 static void doUnLoad (int argc, char *argv [])
250 {
251   char *module1, *module2 ;
252   char cmd [80] ;
253
254   if (argc != 3)
255     _doUnLoadUsage (argv) ;
256
257   /**/ if (strcasecmp (argv [2], "spi") == 0)
258   {
259     module1 = "spidev" ;
260     module2 = "spi_bcm2708" ;
261   }
262   else if (strcasecmp (argv [2], "i2c") == 0)
263   {
264     module1 = "i2c_dev" ;
265     module2 = "i2c_bcm2708" ;
266   }
267   else
268     _doUnLoadUsage (argv) ;
269
270   if (moduleLoaded (module1))
271   {
272     sprintf (cmd, "/sbin/rmmod %s", module1) ;
273     system (cmd) ;
274   }
275
276   if (moduleLoaded (module2))
277   {
278     sprintf (cmd, "/sbin/rmmod %s", module2) ;
279     system (cmd) ;
280   }
281 }
282
283
284 /*
285  * doI2Cdetect:
286  *      Run the i2cdetect command with the right runes for this Pi revision
287  *********************************************************************************
288  */
289
290 static void doI2Cdetect (int argc, char *argv [])
291 {
292   int port = piBoardRev () == 1 ? 0 : 1 ;
293   char command [128] ;
294   struct stat statBuf ;
295
296   if (stat (I2CDETECT, &statBuf) < 0)
297   {
298     fprintf (stderr, "%s: Unable to find i2cdetect command: %s\n", argv [0], strerror (errno)) ;
299     return ;
300   }
301
302   if (!moduleLoaded ("i2c_dev"))
303   {
304     fprintf (stderr, "%s: The I2C kernel module(s) are not loaded.\n", argv [0]) ;
305     return ;
306   }
307
308   sprintf (command, "%s -y %d", I2CDETECT, port) ;
309   if (system (command) < 0)
310     fprintf (stderr, "%s: Unable to run i2cdetect: %s\n", argv [0], strerror (errno)) ;
311
312 }
313
314
315 /*
316  * doExports:
317  *      List all GPIO exports
318  *********************************************************************************
319  */
320
321 static void doExports (int argc, char *argv [])
322 {
323   int fd ;
324   int i, l, first ;
325   char fName [128] ;
326   char buf [16] ;
327
328   for (first = 0, i = 0 ; i < 64 ; ++i) // Crude, but effective
329   {
330
331 // Try to read the direction
332
333     sprintf (fName, "/sys/class/gpio/gpio%d/direction", i) ;
334     if ((fd = open (fName, O_RDONLY)) == -1)
335       continue ;
336
337     if (first == 0)
338     {
339       ++first ;
340       printf ("GPIO Pins exported:\n") ;
341     }
342
343     printf ("%4d: ", i) ;
344
345     if ((l = read (fd, buf, 16)) == 0)
346       sprintf (buf, "%s", "?") ;
347  
348     buf [l] = 0 ;
349     if ((buf [strlen (buf) - 1]) == '\n')
350       buf [strlen (buf) - 1] = 0 ;
351
352     printf ("%-3s", buf) ;
353
354     close (fd) ;
355
356 // Try to Read the value
357
358     sprintf (fName, "/sys/class/gpio/gpio%d/value", i) ;
359     if ((fd = open (fName, O_RDONLY)) == -1)
360     {
361       printf ("No Value file (huh?)\n") ;
362       continue ;
363     }
364
365     if ((l = read (fd, buf, 16)) == 0)
366       sprintf (buf, "%s", "?") ;
367
368     buf [l] = 0 ;
369     if ((buf [strlen (buf) - 1]) == '\n')
370       buf [strlen (buf) - 1] = 0 ;
371
372     printf ("  %s", buf) ;
373
374 // Read any edge trigger file
375
376     sprintf (fName, "/sys/class/gpio/gpio%d/edge", i) ;
377     if ((fd = open (fName, O_RDONLY)) == -1)
378     {
379       printf ("\n") ;
380       continue ;
381     }
382
383     if ((l = read (fd, buf, 16)) == 0)
384       sprintf (buf, "%s", "?") ;
385
386     buf [l] = 0 ;
387     if ((buf [strlen (buf) - 1]) == '\n')
388       buf [strlen (buf) - 1] = 0 ;
389
390     printf ("  %-8s\n", buf) ;
391
392     close (fd) ;
393   }
394 }
395
396
397 /*
398  * doExport:
399  *      gpio export pin mode
400  *      This uses the /sys/class/gpio device interface.
401  *********************************************************************************
402  */
403
404 void doExport (int argc, char *argv [])
405 {
406   FILE *fd ;
407   int pin ;
408   char *mode ;
409   char fName [128] ;
410
411   if (argc != 4)
412   {
413     fprintf (stderr, "Usage: %s export pin mode\n", argv [0]) ;
414     exit (1) ;
415   }
416
417   pin = atoi (argv [2]) ;
418
419   mode = argv [3] ;
420
421   if ((fd = fopen ("/sys/class/gpio/export", "w")) == NULL)
422   {
423     fprintf (stderr, "%s: Unable to open GPIO export interface: %s\n", argv [0], strerror (errno)) ;
424     exit (1) ;
425   }
426
427   fprintf (fd, "%d\n", pin) ;
428   fclose (fd) ;
429
430   sprintf (fName, "/sys/class/gpio/gpio%d/direction", pin) ;
431   if ((fd = fopen (fName, "w")) == NULL)
432   {
433     fprintf (stderr, "%s: Unable to open GPIO direction interface for pin %d: %s\n", argv [0], pin, strerror (errno)) ;
434     exit (1) ;
435   }
436
437   /**/ if ((strcasecmp (mode, "in")  == 0) || (strcasecmp (mode, "input")  == 0))
438     fprintf (fd, "in\n") ;
439   else if ((strcasecmp (mode, "out") == 0) || (strcasecmp (mode, "output") == 0))
440     fprintf (fd, "out\n") ;
441   else
442   {
443     fprintf (stderr, "%s: Invalid mode: %s. Should be in or out\n", argv [1], mode) ;
444     exit (1) ;
445   }
446
447   fclose (fd) ;
448
449 // Change ownership so the current user can actually use it!
450
451   sprintf (fName, "/sys/class/gpio/gpio%d/value", pin) ;
452   changeOwner (argv [0], fName) ;
453
454   sprintf (fName, "/sys/class/gpio/gpio%d/edge", pin) ;
455   changeOwner (argv [0], fName) ;
456
457 }
458
459
460 /*
461  * doWfi:
462  *      gpio wfi pin mode
463  *      Wait for Interrupt on a given pin.
464  *      Slight cheat here - it's easier to actually use ISR now (which calls
465  *      gpio to set the pin modes!) then we simply sleep, and expect the thread
466  *      to exit the program. Crude but effective.
467  *********************************************************************************
468  */
469
470 static void wfi (void)
471   { exit (0) ; }
472
473 void doWfi (int argc, char *argv [])
474 {
475   int pin, mode ;
476
477   if (argc != 4)
478   {
479     fprintf (stderr, "Usage: %s wfi pin mode\n", argv [0]) ;
480     exit (1) ;
481   }
482
483   pin  = atoi (argv [2]) ;
484
485   /**/ if (strcasecmp (argv [3], "rising")  == 0) mode = INT_EDGE_RISING ;
486   else if (strcasecmp (argv [3], "falling") == 0) mode = INT_EDGE_FALLING ;
487   else if (strcasecmp (argv [3], "both")    == 0) mode = INT_EDGE_BOTH ;
488   else
489   {
490     fprintf (stderr, "%s: wfi: Invalid mode: %s. Should be rising, falling or both\n", argv [1], argv [3]) ;
491     exit (1) ;
492   }
493
494   if (wiringPiISR (pin, mode, &wfi) < 0)
495   {
496     fprintf (stderr, "%s: wfi: Unable to setup ISR: %s\n", argv [1], strerror (errno)) ;
497     exit (1) ;
498   }
499
500   for (;;)
501     delay (9999) ;
502 }
503
504
505
506 /*
507  * doEdge:
508  *      gpio edge pin mode
509  *      Easy access to changing the edge trigger on a GPIO pin
510  *      This uses the /sys/class/gpio device interface.
511  *********************************************************************************
512  */
513
514 void doEdge (int argc, char *argv [])
515 {
516   FILE *fd ;
517   int pin ;
518   char *mode ;
519   char fName [128] ;
520
521   if (argc != 4)
522   {
523     fprintf (stderr, "Usage: %s edge pin mode\n", argv [0]) ;
524     exit (1) ;
525   }
526
527   pin  = atoi (argv [2]) ;
528   mode = argv [3] ;
529
530 // Export the pin and set direction to input
531
532   if ((fd = fopen ("/sys/class/gpio/export", "w")) == NULL)
533   {
534     fprintf (stderr, "%s: Unable to open GPIO export interface: %s\n", argv [0], strerror (errno)) ;
535     exit (1) ;
536   }
537
538   fprintf (fd, "%d\n", pin) ;
539   fclose (fd) ;
540
541   sprintf (fName, "/sys/class/gpio/gpio%d/direction", pin) ;
542   if ((fd = fopen (fName, "w")) == NULL)
543   {
544     fprintf (stderr, "%s: Unable to open GPIO direction interface for pin %d: %s\n", argv [0], pin, strerror (errno)) ;
545     exit (1) ;
546   }
547
548   fprintf (fd, "in\n") ;
549   fclose (fd) ;
550
551   sprintf (fName, "/sys/class/gpio/gpio%d/edge", pin) ;
552   if ((fd = fopen (fName, "w")) == NULL)
553   {
554     fprintf (stderr, "%s: Unable to open GPIO edge interface for pin %d: %s\n", argv [0], pin, strerror (errno)) ;
555     exit (1) ;
556   }
557
558   /**/ if (strcasecmp (mode, "none")    == 0) fprintf (fd, "none\n") ;
559   else if (strcasecmp (mode, "rising")  == 0) fprintf (fd, "rising\n") ;
560   else if (strcasecmp (mode, "falling") == 0) fprintf (fd, "falling\n") ;
561   else if (strcasecmp (mode, "both")    == 0) fprintf (fd, "both\n") ;
562   else
563   {
564     fprintf (stderr, "%s: Invalid mode: %s. Should be none, rising, falling or both\n", argv [1], mode) ;
565     exit (1) ;
566   }
567
568 // Change ownership of the value and edge files, so the current user can actually use it!
569
570   sprintf (fName, "/sys/class/gpio/gpio%d/value", pin) ;
571   changeOwner (argv [0], fName) ;
572
573   sprintf (fName, "/sys/class/gpio/gpio%d/edge", pin) ;
574   changeOwner (argv [0], fName) ;
575
576   fclose (fd) ;
577 }
578
579
580 /*
581  * doUnexport:
582  *      gpio unexport pin
583  *      This uses the /sys/class/gpio device interface.
584  *********************************************************************************
585  */
586
587 void doUnexport (int argc, char *argv [])
588 {
589   FILE *fd ;
590   int pin ;
591
592   if (argc != 3)
593   {
594     fprintf (stderr, "Usage: %s unexport pin\n", argv [0]) ;
595     exit (1) ;
596   }
597
598   pin = atoi (argv [2]) ;
599
600   if ((fd = fopen ("/sys/class/gpio/unexport", "w")) == NULL)
601   {
602     fprintf (stderr, "%s: Unable to open GPIO export interface\n", argv [0]) ;
603     exit (1) ;
604   }
605
606   fprintf (fd, "%d\n", pin) ;
607   fclose (fd) ;
608 }
609
610
611 /*
612  * doUnexportAll:
613  *      gpio unexportall
614  *      Un-Export all the GPIO pins.
615  *      This uses the /sys/class/gpio device interface.
616  *********************************************************************************
617  */
618
619 void doUnexportall (char *progName)
620 {
621   FILE *fd ;
622   int pin ;
623
624   for (pin = 0 ; pin < 63 ; ++pin)
625   {
626     if ((fd = fopen ("/sys/class/gpio/unexport", "w")) == NULL)
627     {
628       fprintf (stderr, "%s: Unable to open GPIO export interface\n", progName) ;
629       exit (1) ;
630     }
631     fprintf (fd, "%d\n", pin) ;
632     fclose (fd) ;
633   }
634 }
635
636
637 /*
638  * doReset:
639  *      Reset the GPIO pins - as much as we can do
640  *********************************************************************************
641  */
642
643 static void doReset (char *progName)
644 {
645   printf ("GPIO Reset is dangerous and has been removed from the gpio command.\n") ;
646   printf (" - Please write a shell-script to reset the GPIO pins into the state\n") ;
647   printf ("   that you need them in for your applications.\n") ;
648 }
649
650
651 /*
652  * doMode:
653  *      gpio mode pin mode ...
654  *********************************************************************************
655  */
656
657 void doMode (int argc, char *argv [])
658 {
659   int pin ;
660   char *mode ;
661
662   if (argc != 4)
663   {
664     fprintf (stderr, "Usage: %s mode pin mode\n", argv [0]) ;
665     exit (1) ;
666   }
667
668   pin = atoi (argv [2]) ;
669
670   mode = argv [3] ;
671
672   /**/ if (strcasecmp (mode, "in")      == 0) pinMode         (pin, INPUT) ;
673   else if (strcasecmp (mode, "input")   == 0) pinMode         (pin, INPUT) ;
674   else if (strcasecmp (mode, "out")     == 0) pinMode         (pin, OUTPUT) ;
675   else if (strcasecmp (mode, "output")  == 0) pinMode         (pin, OUTPUT) ;
676   else if (strcasecmp (mode, "pwm")     == 0) pinMode         (pin, PWM_OUTPUT) ;
677   else if (strcasecmp (mode, "pwmTone") == 0) pinMode         (pin, PWM_TONE_OUTPUT) ;
678   else if (strcasecmp (mode, "clock")   == 0) pinMode         (pin, GPIO_CLOCK) ;
679   else if (strcasecmp (mode, "up")      == 0) pullUpDnControl (pin, PUD_UP) ;
680   else if (strcasecmp (mode, "down")    == 0) pullUpDnControl (pin, PUD_DOWN) ;
681   else if (strcasecmp (mode, "tri")     == 0) pullUpDnControl (pin, PUD_OFF) ;
682   else if (strcasecmp (mode, "off")     == 0) pullUpDnControl (pin, PUD_OFF) ;
683   else if (strcasecmp (mode, "alt0")    == 0) pinModeAlt (pin, 0b100) ;
684   else if (strcasecmp (mode, "alt1")    == 0) pinModeAlt (pin, 0b101) ;
685   else if (strcasecmp (mode, "alt2")    == 0) pinModeAlt (pin, 0b110) ;
686   else if (strcasecmp (mode, "alt3")    == 0) pinModeAlt (pin, 0b111) ;
687   else if (strcasecmp (mode, "alt4")    == 0) pinModeAlt (pin, 0b011) ;
688   else if (strcasecmp (mode, "alt5")    == 0) pinModeAlt (pin, 0b010) ;
689   else
690   {
691     fprintf (stderr, "%s: Invalid mode: %s. Should be in/out/pwm/clock/up/down/tri\n", argv [1], mode) ;
692     exit (1) ;
693   }
694 }
695
696
697 /*
698  * doPadDrive:
699  *      gpio drive group value
700  *********************************************************************************
701  */
702
703 static void doPadDrive (int argc, char *argv [])
704 {
705   int group, val ;
706
707   if (argc != 4)
708   {
709     fprintf (stderr, "Usage: %s drive group value\n", argv [0]) ;
710     exit (1) ;
711   }
712
713   group = atoi (argv [2]) ;
714   val   = atoi (argv [3]) ;
715
716   if ((group < 0) || (group > 2))
717   {
718     fprintf (stderr, "%s: drive group not 0, 1 or 2: %d\n", argv [0], group) ;
719     exit (1) ;
720   }
721
722   if ((val < 0) || (val > 7))
723   {
724     fprintf (stderr, "%s: drive value not 0-7: %d\n", argv [0], val) ;
725     exit (1) ;
726   }
727
728   setPadDrive (group, val) ;
729 }
730
731
732 /*
733  * doUsbP:
734  *      Control USB Power - High (1.2A) or Low (600mA)
735  *      gpio usbp high/low
736  *********************************************************************************
737  */
738
739 static void doUsbP (int argc, char *argv [])
740 {
741   int model, rev, mem, maker, overVolted ;
742
743   if (argc != 3)
744   {
745     fprintf (stderr, "Usage: %s usbp high|low\n", argv [0]) ;
746     exit (1) ;
747   }
748
749 // Make sure we're on a B+
750
751   piBoardId (&model, &rev, &mem, &maker, &overVolted) ;
752
753   if (model != PI_MODEL_BP)
754   {
755     fprintf (stderr, "USB power contol is applicable to B+ boards only.\n") ;
756     exit (1) ;
757   }
758     
759 // Need to force BCM_GPIO mode:
760
761   wiringPiSetupGpio () ;
762
763   if ((strcasecmp (argv [2], "high") == 0) || (strcasecmp (argv [2], "hi") == 0))
764   {
765     digitalWrite (PI_USB_POWER_CONTROL, 1) ;
766     pinMode (PI_USB_POWER_CONTROL, OUTPUT) ;
767     printf ("Switched to HIGH current USB (1.2A)\n") ;
768     return ;
769   }
770
771   if ((strcasecmp (argv [2], "low") == 0) || (strcasecmp (argv [2], "lo") == 0))
772   {
773     digitalWrite (PI_USB_POWER_CONTROL, 0) ;
774     pinMode (PI_USB_POWER_CONTROL, OUTPUT) ;
775     printf ("Switched to LOW current USB (600mA)\n") ;
776     return ;
777   }
778
779   fprintf (stderr, "Usage: %s usbp high|low\n", argv [0]) ;
780   exit (1) ;
781 }
782
783
784 /*
785  * doGbw:
786  *      gpio gbw channel value
787  *      Gertboard Write - To the Analog output
788  *********************************************************************************
789  */
790
791 static void doGbw (int argc, char *argv [])
792 {
793   int channel, value ;
794
795   if (argc != 4)
796   {
797     fprintf (stderr, "Usage: %s gbw <channel> <value>\n", argv [0]) ;
798     exit (1) ;
799   }
800
801   channel = atoi (argv [2]) ;
802   value   = atoi (argv [3]) ;
803
804   if ((channel < 0) || (channel > 1))
805   {
806     fprintf (stderr, "%s: gbw: Channel number must be 0 or 1\n", argv [0]) ;
807     exit (1) ;
808   }
809
810   if ((value < 0) || (value > 255))
811   {
812     fprintf (stderr, "%s: gbw: Value must be from 0 to 255\n", argv [0]) ;
813     exit (1) ;
814   }
815
816   if (gertboardAnalogSetup (64) < 0)
817   {
818     fprintf (stderr, "Unable to initialise the Gertboard SPI interface: %s\n", strerror (errno)) ;
819     exit (1) ;
820   }
821
822   analogWrite (64 + channel, value) ;
823 }
824
825
826 /*
827  * doGbr:
828  *      gpio gbr channel
829  *      From the analog input
830  *********************************************************************************
831  */
832
833 static void doGbr (int argc, char *argv [])
834 {
835   int channel ;
836
837   if (argc != 3)
838   {
839     fprintf (stderr, "Usage: %s gbr <channel>\n", argv [0]) ;
840     exit (1) ;
841   }
842
843   channel = atoi (argv [2]) ;
844
845   if ((channel < 0) || (channel > 1))
846   {
847     fprintf (stderr, "%s: gbr: Channel number must be 0 or 1\n", argv [0]) ;
848     exit (1) ;
849   }
850
851   if (gertboardAnalogSetup (64) < 0)
852   {
853     fprintf (stderr, "Unable to initialise the Gertboard SPI interface: %s\n", strerror (errno)) ;
854     exit (1) ;
855   }
856
857   printf ("%d\n", analogRead (64 + channel)) ;
858 }
859
860
861 /*
862  * doWrite:
863  *      gpio write pin value
864  *********************************************************************************
865  */
866
867 static void doWrite (int argc, char *argv [])
868 {
869   int pin, val ;
870
871   if (argc != 4)
872   {
873     fprintf (stderr, "Usage: %s write pin value\n", argv [0]) ;
874     exit (1) ;
875   }
876
877   pin = atoi (argv [2]) ;
878
879   /**/ if ((strcasecmp (argv [3], "up") == 0) || (strcasecmp (argv [3], "on") == 0))
880     val = 1 ;
881   else if ((strcasecmp (argv [3], "down") == 0) || (strcasecmp (argv [3], "off") == 0))
882     val = 0 ;
883   else
884     val = atoi (argv [3]) ;
885
886   /**/ if (val == 0)
887     digitalWrite (pin, LOW) ;
888   else
889     digitalWrite (pin, HIGH) ;
890 }
891
892
893 /*
894  * doAwriterite:
895  *      gpio awrite pin value
896  *********************************************************************************
897  */
898
899 static void doAwrite (int argc, char *argv [])
900 {
901   int pin, val ;
902
903   if (argc != 4)
904   {
905     fprintf (stderr, "Usage: %s awrite pin value\n", argv [0]) ;
906     exit (1) ;
907   }
908
909   pin = atoi (argv [2]) ;
910
911   val = atoi (argv [3]) ;
912
913   analogWrite (pin, val) ;
914 }
915
916
917 /*
918  * doWriteByte:
919  *      gpio write value
920  *********************************************************************************
921  */
922
923 static void doWriteByte (int argc, char *argv [])
924 {
925   int val ;
926
927   if (argc != 3)
928   {
929     fprintf (stderr, "Usage: %s wb value\n", argv [0]) ;
930     exit (1) ;
931   }
932
933   val = (int)strtol (argv [2], NULL, 0) ;
934
935   digitalWriteByte (val) ;
936 }
937
938
939 /*
940  * doRead:
941  *      Read a pin and return the value
942  *********************************************************************************
943  */
944
945 void doRead (int argc, char *argv []) 
946 {
947   int pin, val ;
948
949   if (argc != 3)
950   {
951     fprintf (stderr, "Usage: %s read pin\n", argv [0]) ;
952     exit (1) ;
953   }
954
955   pin = atoi (argv [2]) ;
956   val = digitalRead (pin) ;
957
958   printf ("%s\n", val == 0 ? "0" : "1") ;
959 }
960
961
962 /*
963  * doAread:
964  *      Read an analog pin and return the value
965  *********************************************************************************
966  */
967
968 void doAread (int argc, char *argv []) 
969 {
970   if (argc != 3)
971   {
972     fprintf (stderr, "Usage: %s aread pin\n", argv [0]) ;
973     exit (1) ;
974   }
975
976   printf ("%d\n", analogRead (atoi (argv [2]))) ;
977 }
978
979
980 /*
981  * doToggle:
982  *      Toggle an IO pin
983  *********************************************************************************
984  */
985
986 void doToggle (int argc, char *argv [])
987 {
988   int pin ;
989
990   if (argc != 3)
991   {
992     fprintf (stderr, "Usage: %s toggle pin\n", argv [0]) ;
993     exit (1) ;
994   }
995
996   pin = atoi (argv [2]) ;
997
998   digitalWrite (pin, !digitalRead (pin)) ;
999 }
1000
1001
1002 /*
1003  * doPwmTone:
1004  *      Output a tone in a PWM pin
1005  *********************************************************************************
1006  */
1007
1008 void doPwmTone (int argc, char *argv [])
1009 {
1010   int pin, freq ;
1011
1012   if (argc != 4)
1013   {
1014     fprintf (stderr, "Usage: %s pwmTone <pin> <freq>\n", argv [0]) ;
1015     exit (1) ;
1016   }
1017
1018   pin = atoi (argv [2]) ;
1019   freq = atoi (argv [3]) ;
1020
1021   pwmToneWrite (pin, freq) ;
1022 }
1023
1024
1025 /*
1026  * doClock:
1027  *      Output a clock on a pin
1028  *********************************************************************************
1029  */
1030
1031 void doClock (int argc, char *argv [])
1032 {
1033   int pin, freq ;
1034
1035   if (argc != 4)
1036   {
1037     fprintf (stderr, "Usage: %s clock <pin> <freq>\n", argv [0]) ;
1038     exit (1) ;
1039   }
1040
1041   pin = atoi (argv [2]) ;
1042
1043   freq = atoi (argv [3]) ;
1044
1045   gpioClockSet (pin, freq) ;
1046 }
1047
1048
1049 /*
1050  * doPwm:
1051  *      Output a PWM value on a pin
1052  *********************************************************************************
1053  */
1054
1055 void doPwm (int argc, char *argv [])
1056 {
1057   int pin, val ;
1058
1059   if (argc != 4)
1060   {
1061     fprintf (stderr, "Usage: %s pwm <pin> <value>\n", argv [0]) ;
1062     exit (1) ;
1063   }
1064
1065   pin = atoi (argv [2]) ;
1066
1067   val = atoi (argv [3]) ;
1068
1069   pwmWrite (pin, val) ;
1070 }
1071
1072
1073 /*
1074  * doPwmMode: doPwmRange: doPwmClock:
1075  *      Change the PWM mode, range and clock divider values
1076  *********************************************************************************
1077  */
1078
1079 static void doPwmMode (int mode)
1080 {
1081   pwmSetMode (mode) ;
1082 }
1083
1084 static void doPwmRange (int argc, char *argv [])
1085 {
1086   unsigned int range ;
1087
1088   if (argc != 3)
1089   {
1090     fprintf (stderr, "Usage: %s pwmr <range>\n", argv [0]) ;
1091     exit (1) ;
1092   }
1093
1094   range = (unsigned int)strtoul (argv [2], NULL, 10) ;
1095
1096   if (range == 0)
1097   {
1098     fprintf (stderr, "%s: range must be > 0\n", argv [0]) ;
1099     exit (1) ;
1100   }
1101
1102   pwmSetRange (range) ;
1103 }
1104
1105 static void doPwmClock (int argc, char *argv [])
1106 {
1107   unsigned int clock ;
1108
1109   if (argc != 3)
1110   {
1111     fprintf (stderr, "Usage: %s pwmc <clock>\n", argv [0]) ;
1112     exit (1) ;
1113   }
1114
1115   clock = (unsigned int)strtoul (argv [2], NULL, 10) ;
1116
1117   if ((clock < 1) || (clock > 4095))
1118   {
1119     fprintf (stderr, "%s: clock must be between 0 and 4096\n", argv [0]) ;
1120     exit (1) ;
1121   }
1122
1123   pwmSetClock (clock) ;
1124 }
1125
1126
1127 /*
1128  * main:
1129  *      Start here
1130  *********************************************************************************
1131  */
1132
1133 int main (int argc, char *argv [])
1134 {
1135   int i ;
1136   int model, rev, mem, maker, overVolted ;
1137
1138   if (getenv ("WIRINGPI_DEBUG") != NULL)
1139   {
1140     printf ("gpio: wiringPi debug mode enabled\n") ;
1141     wiringPiDebug = TRUE ;
1142   }
1143
1144   if (argc == 1)
1145   {
1146     fprintf (stderr, "%s\n", usage) ;
1147     return 1 ;
1148   }
1149
1150 // Help
1151
1152   if (strcasecmp (argv [1], "-h") == 0)
1153   {
1154     printf ("%s: %s\n", argv [0], usage) ;
1155     return 0 ;
1156   }
1157
1158 // Sort of a special:
1159
1160   if (strcmp (argv [1], "-R") == 0)
1161   {
1162     printf ("%d\n", piBoardRev ()) ;
1163     return 0 ;
1164   }
1165
1166 // Version & Warranty
1167
1168   if (strcmp (argv [1], "-V") == 0)
1169   {
1170     printf ("%d\n", piBoardRev ()) ;
1171     return 0 ;
1172   }
1173
1174   if (strcmp (argv [1], "-v") == 0)
1175   {
1176     printf ("gpio version: %s\n", VERSION) ;
1177     printf ("Copyright (c) 2012-2015 Gordon Henderson\n") ;
1178     printf ("This is free software with ABSOLUTELY NO WARRANTY.\n") ;
1179     printf ("For details type: %s -warranty\n", argv [0]) ;
1180     printf ("\n") ;
1181     piBoardId (&model, &rev, &mem, &maker, &overVolted) ;
1182     if (model == PI_MODEL_UNKNOWN)
1183     {
1184       printf ("Your Raspberry Pi has an unknown model type. Please report this to\n") ;
1185       printf ("    projects@drogon.net\n") ;
1186       printf ("with a copy of your /proc/cpuinfo if possible\n") ;
1187     }
1188     else
1189     {
1190       printf ("Raspberry Pi Details:\n") ;
1191       printf ("  Type: %s, Revision: %s, Memory: %dMB, Maker: %s %s\n", 
1192           piModelNames [model], piRevisionNames [rev], mem, piMakerNames [maker], overVolted ? "[OV]" : "") ;
1193     }
1194     return 0 ;
1195   }
1196
1197   if (strcasecmp (argv [1], "-warranty") == 0)
1198   {
1199     printf ("gpio version: %s\n", VERSION) ;
1200     printf ("Copyright (c) 2012-2015 Gordon Henderson\n") ;
1201     printf ("\n") ;
1202     printf ("    This program is free software; you can redistribute it and/or modify\n") ;
1203     printf ("    it under the terms of the GNU Leser General Public License as published\n") ;
1204     printf ("    by the Free Software Foundation, either version 3 of the License, or\n") ;
1205     printf ("    (at your option) any later version.\n") ;
1206     printf ("\n") ;
1207     printf ("    This program is distributed in the hope that it will be useful,\n") ;
1208     printf ("    but WITHOUT ANY WARRANTY; without even the implied warranty of\n") ;
1209     printf ("    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n") ;
1210     printf ("    GNU Lesser General Public License for more details.\n") ;
1211     printf ("\n") ;
1212     printf ("    You should have received a copy of the GNU Lesser General Public License\n") ;
1213     printf ("    along with this program. If not, see <http://www.gnu.org/licenses/>.\n") ;
1214     printf ("\n") ;
1215     return 0 ;
1216   }
1217
1218   if (geteuid () != 0)
1219   {
1220     fprintf (stderr, "%s: Must be root to run. Program should be suid root. This is an error.\n", argv [0]) ;
1221     return 1 ;
1222   }
1223
1224 // Initial test for /sys/class/gpio operations:
1225
1226   /**/ if (strcasecmp (argv [1], "exports"    ) == 0)   { doExports     (argc, argv) ;  return 0 ; }
1227   else if (strcasecmp (argv [1], "export"     ) == 0)   { doExport      (argc, argv) ;  return 0 ; }
1228   else if (strcasecmp (argv [1], "edge"       ) == 0)   { doEdge        (argc, argv) ;  return 0 ; }
1229   else if (strcasecmp (argv [1], "unexport"   ) == 0)   { doUnexport    (argc, argv) ;  return 0 ; }
1230   else if (strcasecmp (argv [1], "unexportall") == 0)   { doUnexportall (argv [0]) ;    return 0 ; }
1231
1232 // Check for load command:
1233
1234   if (strcasecmp (argv [1], "load"   ) == 0)    { doLoad   (argc, argv) ; return 0 ; }
1235   if (strcasecmp (argv [1], "unload" ) == 0)    { doUnLoad (argc, argv) ; return 0 ; }
1236
1237 // Gertboard commands
1238
1239   if (strcasecmp (argv [1], "gbr" ) == 0)       { doGbr (argc, argv) ; return 0 ; }
1240   if (strcasecmp (argv [1], "gbw" ) == 0)       { doGbw (argc, argv) ; return 0 ; }
1241
1242 // Check for -g argument
1243
1244   /**/ if (strcasecmp (argv [1], "-g") == 0)
1245   {
1246     wiringPiSetupGpio () ;
1247
1248     for (i = 2 ; i < argc ; ++i)
1249       argv [i - 1] = argv [i] ;
1250     --argc ;
1251     wpMode = WPI_MODE_GPIO ;
1252   }
1253
1254 // Check for -1 argument
1255
1256   else if (strcasecmp (argv [1], "-1") == 0)
1257   {
1258     wiringPiSetupPhys () ;
1259
1260     for (i = 2 ; i < argc ; ++i)
1261       argv [i - 1] = argv [i] ;
1262     --argc ;
1263     wpMode = WPI_MODE_PHYS ;
1264   }
1265
1266 // Check for -p argument for PiFace
1267
1268   else if (strcasecmp (argv [1], "-p") == 0)
1269   {
1270     piFaceSetup (200) ;
1271
1272     for (i = 2 ; i < argc ; ++i)
1273       argv [i - 1] = argv [i] ;
1274     --argc ;
1275     wpMode = WPI_MODE_PIFACE ;
1276   }
1277
1278 // Default to wiringPi mode
1279
1280   else
1281   {
1282     wiringPiSetup () ;
1283     wpMode = WPI_MODE_PINS ;
1284   }
1285
1286 // Check for -x argument to load in a new extension
1287
1288   if (strcasecmp (argv [1], "-x") == 0)
1289   {
1290     if (argc < 3)
1291     {
1292       fprintf (stderr, "%s: -x missing extension specification.\n", argv [0]) ;
1293       exit (EXIT_FAILURE) ;
1294     }
1295
1296     if (!loadWPiExtension (argv [0], argv [2], TRUE))   // Prints its own error messages
1297       exit (EXIT_FAILURE) ;
1298
1299     for (i = 3 ; i < argc ; ++i)
1300       argv [i - 2] = argv [i] ;
1301     argc -= 2 ;
1302   }
1303
1304   if (argc <= 1)
1305   {
1306     fprintf (stderr, "%s: no command given\n", argv [0]) ;
1307     exit (EXIT_FAILURE) ;
1308   }
1309
1310 // Core wiringPi functions
1311
1312   /**/ if (strcasecmp (argv [1], "mode"   ) == 0) doMode      (argc, argv) ;
1313   else if (strcasecmp (argv [1], "read"   ) == 0) doRead      (argc, argv) ;
1314   else if (strcasecmp (argv [1], "write"  ) == 0) doWrite     (argc, argv) ;
1315   else if (strcasecmp (argv [1], "pwm"    ) == 0) doPwm       (argc, argv) ;
1316   else if (strcasecmp (argv [1], "awrite" ) == 0) doAwrite    (argc, argv) ;
1317   else if (strcasecmp (argv [1], "aread"  ) == 0) doAread     (argc, argv) ;
1318
1319 // GPIO Nicies
1320
1321   else if (strcasecmp (argv [1], "toggle" ) == 0) doToggle    (argc, argv) ;
1322
1323 // Pi Specifics
1324
1325   else if (strcasecmp (argv [1], "pwm-bal"  ) == 0) doPwmMode    (PWM_MODE_BAL) ;
1326   else if (strcasecmp (argv [1], "pwm-ms"   ) == 0) doPwmMode    (PWM_MODE_MS) ;
1327   else if (strcasecmp (argv [1], "pwmr"     ) == 0) doPwmRange   (argc, argv) ;
1328   else if (strcasecmp (argv [1], "pwmc"     ) == 0) doPwmClock   (argc, argv) ;
1329   else if (strcasecmp (argv [1], "pwmTone"  ) == 0) doPwmTone    (argc, argv) ;
1330   else if (strcasecmp (argv [1], "drive"    ) == 0) doPadDrive   (argc, argv) ;
1331   else if (strcasecmp (argv [1], "usbp"     ) == 0) doUsbP       (argc, argv) ;
1332   else if (strcasecmp (argv [1], "readall"  ) == 0) doReadall    () ;
1333   else if (strcasecmp (argv [1], "nreadall" ) == 0) doReadall    () ;
1334   else if (strcasecmp (argv [1], "pins"     ) == 0) doPins       () ;
1335   else if (strcasecmp (argv [1], "i2cdetect") == 0) doI2Cdetect  (argc, argv) ;
1336   else if (strcasecmp (argv [1], "i2cd"     ) == 0) doI2Cdetect  (argc, argv) ;
1337   else if (strcasecmp (argv [1], "reset"    ) == 0) doReset      (argv [0]) ;
1338   else if (strcasecmp (argv [1], "wb"       ) == 0) doWriteByte  (argc, argv) ;
1339   else if (strcasecmp (argv [1], "clock"    ) == 0) doClock      (argc, argv) ;
1340   else if (strcasecmp (argv [1], "wfi"      ) == 0) doWfi        (argc, argv) ;
1341   else
1342   {
1343     fprintf (stderr, "%s: Unknown command: %s.\n", argv [0], argv [1]) ;
1344     exit (EXIT_FAILURE) ;
1345   }
1346   return 0 ;
1347 }