/* $Id: netsprinkle.c,v 1.6 2020/05/10 01:29:39 grog Exp $ */ /* * Run sprinklers connected via network relay board. * Derived from sprinkle.c,v 1.2 2005/01/25 23:25:10. * * This attempt should work, but is based on almost complete lack of * documentation. Much needs improvement. * */ #include #include #include #include #include #include #include #include #include #include #include #include #include int verbose = 0; /* set to display progress */ int logging = 0; /* set to log progress */ int fakeit = 0; /* Default values, may be overridden on command line */ char *host = "sprinkler.lemis.com"; char *user = "admin"; char *password = "12345678"; FILE *timefactorfile; /* for reading in time factor */ float timefactor = 1.0; /* factor by which to modify specified times */ void usage (char *me) { fprintf (stderr, "Usage:\n" "%s [-h hostname] [-u user] [-p password] [-f factorfile] [-F factor] [-l] [-v] relaytimes...\n\n" " -f factorfile: read modification factor from file\n" " -F factor: set modification factor directly\n" " -l: log status\n" " -v: be verbose\n" " relaytimes (up to 8 times): times in minutes for each relay, modified by modification factor\n", me ); exit (1); } void setrelay (int relay) { int i; char command [128]; /* "128 bytes should be enogh for anybody" */ /* * Explicitly set all relays one way or another. There's almost certainly a * cleaner way, but the implementers have hidden it well. * */ for (i = 1; i < 9; i++) { if (i == relay) /* turn it on */ sprintf (command, "curl --user %s:%s --data \"saida%don\" http://%s/relay_en.cgi 2> /dev/null", user, password, i, host ); else sprintf (command, "curl --user %s:%s --data \"saida%doff\" http://%s/relay_en.cgi 2> /dev/null", user, password, i, host ); if (fakeit) puts (command); else { if (verbose) puts (command); system (command); } } } /* $0 relayline valve valve ... */ int main (int argc, char *argv []) { int i; int duration; int relay; int relaycount; i = 1; if (argc < 2) { syslog (LOG_ERR, "No parameters specified\n"); return 1; } while (argv [i] [0] == '-') { switch (argv [i] [1]) { case 'f': /* read in time factor */ timefactorfile = fopen (argv [++i], "r"); fscanf (timefactorfile, "%f", &timefactor); if (timefactor == 0.0) /* nothing to do, */ exit (0); else if ((timefactor > 100.0) || (timefactor < 0.001)) { fprintf (stderr, "Improbable time factor: %f\n", timefactor); exit (2); } fclose (timefactorfile); break; case 'F': /* time factor directly */ timefactor = atof (argv [++i]); if (timefactor == 0.0) /* nothing to do, */ exit (0); else if ((timefactor > 100.0) || (timefactor < 0.001)) { fprintf (stderr, "Improbable time factor: %f\n", timefactor); exit (2); } break; case 'h': host = argv [++i]; break; case 'l': logging = 1; break; case 'n': fakeit = 1; break; case 'p': password = argv [++i]; break; case 'u': user = argv [++i]; break; case 'v': verbose = 1; break; default: syslog (LOG_ERR, "Invalid parameter: %c\n", argv [i] [1]); usage (argv [0]); return 1; } i++; if (i == argc) { syslog (LOG_ERR, "All parameters are options\n"); return 1; } } if (i == argc) { syslog (LOG_ERR, "No sprinklers specified\n"); return 1; } if ((argc - i) > 8) { /* * Invalid number of valves. We'll do what we can anyway. */ syslog (LOG_WARNING, "Too many valves: %d (must be between 1 and 8)\n", argc - i ); relaycount = 8; } else relaycount = argc - i; argv = &argv [i - 1]; for (relay = 1; relay <= relaycount; relay++) /* each valve */ { duration = atoi (argv [relay]); /* duration in minutes */ if (duration) { duration = (int) (duration * 60 * timefactor); if (logging) syslog (LOG_INFO, "Starting circuit %d for %d minutes\n", relay - i + 1, duration / 60); setrelay (relay); sleep (duration); if (logging) syslog (LOG_INFO, "Finishing circuit %d for %d minutes\n", relay - i + 1, duration / 60); } } setrelay (0); /* all off now, including pump */ return 0; }