/*! * \file main.c * This is the main file of the RTES final task. * * \author Christos Choutouridis AEM:8997 */ #include #include #include #include #include #include #include "listener.h" #include "client.h" /*! * Global data */ //! @{ settings_t settings_init (settings); //!< Application settings devList_t devList[AEMLIST_SIZE]; //!< Device list stats_t stats; //!< Statistical data //! @} /*! * CLI short options */ const char *short_opt = "v:i:m:M:p:s:w:th"; /*! * CLI long options */ const struct option long_opt[] = { {"outlevel", required_argument, NULL, 'v'}, {"interval", required_argument, NULL, 'i'}, {"msgintervalmin", required_argument, NULL, 'm'}, {"msgintervalmax", required_argument, NULL, 'M'}, {"pingtimeout", required_argument, NULL, 'p'}, {"sendtimeout", required_argument, NULL, 's'}, {"who", required_argument, NULL, 'w'}, {"tracktime", no_argument, NULL, 't'}, {"help", no_argument, NULL, 'h'}, {NULL, 0, NULL, 0} }; /*! * \brief * Parse input argument and fill the kcli_input_t struct * \param s Pointer to settings_t data to fill * \param argc The argument count as passed to the main() * \param argv Argument array as passed to the main() * \return The status of the operation * \arg 0 Success * \arg 1 Fail */ int parse_args (settings_t *s, int argc, char const *argv[]) { int c; while ((c = getopt_long (argc, (char *const *)argv, short_opt, long_opt, NULL)) != -1) { switch (c) { case -1: /* no more arguments */ case 0: /* long options toggles */ break; case 'v': s->outLevel = atoi (optarg); if (s->outLevel >= OUTLEVEL_2) s->outLevel = OUTLEVEL_2; if (s->outLevel < OUTLEVEL_0) s->outLevel = OUTLEVEL_0; break; case 'i': s->seekerInterval = atoi (optarg); break; case 'm': s->msgIntervalMin = atoi (optarg); break; case 'M': s->msgIntervalMax = atoi (optarg); break; case 'p': s->pingTimeout = atoi (optarg); break; case 's': s->sendTimeout.tv_sec = atoi (optarg); break; case 'w': s->me = atoi (optarg); break; case 't': s->trackTime = true; break; case 'h': printf ("Syntax:\n"); printf ("rtes_final [-t] [-h] [-v num] [-i num] [-m num] [-M num] [-p num] [-s num] [-w num]\n\n"); printf ("-v, --outlevel num: Change the verbosity of the program, num can be 0, 1 or 2\n"); printf ("-i, --interval sec: Set the interval of the seeker in [sec]\n"); printf ("-m, --msgintervalmin sec: Set the interval of the client in [sec]\n"); printf ("-M, --msgintervalmax sec: Set the interval of the client in [sec]\n"); printf ("-p, --pingtimeout sec: Set the ping timeout in [sec]\n"); printf ("-s, --sendtimeout sec: Set the connect/send timeout in [sec]\n"); printf ("-w, --who AEM: Select the AEM of the device\n"); printf ("-t, --tracktime: Enables time tracking in statistics\n"); printf ("-h, --help: Print this and exit\n"); exit(1); case ':': default: case '?': fprintf (stderr, "%s: invalid option -- %c\n", argv[0], c); fprintf (stderr, "Try `%s --help' for more information.\n", argv[0]); exit(1); } } return 0; } /*! * Main function */ int main (int argc, char const *argv[]) { // get command line arguments parse_args (&settings, argc, argv); // Initialize all subsystems log_init (); stats_init (&stats); devList_init (devList); msgList_init (&msgList); // Create threads pthread_t ptL, ptS, ptC; pthread_create (&ptL, NULL, pthListener, NULL); pthread_create (&ptS, NULL, pthSeeker, NULL); pthread_create (&ptC, NULL, pthClient, NULL); // block here pthread_join (ptL, NULL); pthread_join (ptS, NULL); pthread_join (ptC, NULL); return 0; }