void do_lock(struct response *resp) { int rc; struct flock lock; int cmd; if (resp->r_cmd == CMD_LOCKW) cmd = F_SETLKW; else cmd = F_SETLK; if (resp->r_fpos != 0 && fno[resp->r_fpos] == 0) { strcpy(errdetail, "Invalid file number"); sprintf(badtoken, "%ld", resp->r_fpos); resp->r_status = STATUS_ERRNO; resp->r_errno = EBADF; return; } lock.l_whence = SEEK_SET; lock.l_type = resp->r_lock_type; lock.l_start = resp->r_start; lock.l_len = resp->r_length; if (cmd == F_SETLKW && alarmtag == 0) { /* Don't let a blocking lock block hang us * Test case can set an alarm before LOCKW to specify * a different time */ resp->r_secs = 30; do_alarm(resp); } rc = fcntl(fno[resp->r_fpos], cmd, &lock); if (rc == -1) { if (errno == EAGAIN) { resp->r_status = STATUS_DENIED; } else if (errno == EINTR) { resp->r_status = STATUS_CANCELED; } else if (errno == EDEADLK) { resp->r_status = STATUS_DEADLOCK; } else { strcpy(errdetail, "Lock failed"); sprintf(badtoken, "%s %lld %lld", str_lock_type(lock.l_type), resp->r_start, resp->r_length); resp->r_status = STATUS_ERRNO; resp->r_errno = errno; } } else resp->r_status = STATUS_GRANTED; if (cmd == F_SETLKW && alarmtag == resp->r_tag) { /* cancel the alarm we set */ alarm(0); alarmtag = 0; } }
int main(int argc, char **argv) { int opt; int len, rc; struct sigaction sigact; char *rest; int oflags = 0; int no_tag; memset(&sigact, 0, sizeof(sigact)); sigact.sa_handler = sighandler; if (sigaction(SIGALRM, &sigact, NULL) == -1) return 1; if (sigaction(SIGPIPE, &sigact, NULL) == -1) return 1; input = stdin; output = stdout; /* now parsing options with getopt */ while ((opt = getopt(argc, argv, options)) != EOF) { switch (opt) { case 'c': rc = chdir(optarg); if (rc == -1) { fprintf(stderr, "Can not change dir to %s errno = %d \"%s\"\n", optarg, errno, strerror(errno)); exit(1); } break; case 'q': quiet = true; break; case 'd': duperrors = true; break; case 's': if (oflags > 7) show_usage(1, "Can not combine -x and -s\n"); oflags |= 1; script = true; strncpy(server, optarg, MAXSTR); break; case 'x': if ((oflags & 7) != 0) show_usage(1, "Can not combine -x and -s/-p/-n\n"); oflags |= 8; script = true; input = fopen(optarg, "r"); if (input == NULL) fatal("Could not open %s\n", optarg); break; case 'n': if (oflags > 7) show_usage(1, "Can not combine -x and -n\n"); oflags |= 2; strncpy(name, optarg, MAXSTR); break; case 'p': if (oflags > 7) show_usage(1, "Can not combine -x and -p\n"); oflags |= 4; strncpy(portstr, optarg, MAXSTR); port = atoi(optarg); break; case '?': case 'h': default: /* display the help */ show_usage(0, "Help\n"); } } if (oflags > 0 && oflags < 7) show_usage(1, "Must specify -s, -p, and -n together\n"); if (oflags == 7) openserver(); while (1) { len = readln(input, line, MAXSTR * 2); if (len < 0) { if (script) fatal("End of file on input\n"); else break; } else { struct response resp; lno++; memset(&resp, 0, sizeof(resp)); rest = SkipWhite(line, REQUIRES_MORE, "Invalid line"); /* Skip totally blank line */ if (rest == NULL) continue; if (script && !quiet) fprintf(stdout, "%s\n", rest); /* If line doesn't start with a tag, that's ok */ no_tag = (!isdigit(*rest) && (*rest != '$')); /* Parse request into response structure */ rest = parse_request(rest, &resp, no_tag); if (rest == NULL) { resp.r_status = STATUS_ERRNO; resp.r_errno = errno; } else { /* Make sure default status is ok */ resp.r_status = STATUS_OK; if (*rest != '\0' && *rest != '#') fprintf_stderr( "Command line not consumed, rest=\"%s\"\n", rest); switch (resp.r_cmd) { case CMD_OPEN: do_open(&resp); break; case CMD_CLOSE: do_close(&resp); break; case CMD_LOCKW: do_lock(&resp); break; case CMD_LOCK: do_lock(&resp); break; case CMD_UNLOCK: do_unlock(&resp); break; case CMD_TEST: do_test(&resp); break; case CMD_LIST: do_list(&resp); break; case CMD_HOP: do_hop(&resp); break; case CMD_UNHOP: do_unhop(&resp); break; case CMD_SEEK: do_seek(&resp); break; case CMD_READ: do_read(&resp); break; case CMD_WRITE: do_write(&resp); break; case CMD_ALARM: do_alarm(&resp); break; case CMD_HELLO: case CMD_COMMENT: case CMD_QUIT: resp.r_status = STATUS_OK; break; case NUM_COMMANDS: fprintf_stderr("Invalid command %s\n", line); continue; } } respond(&resp); if (resp.r_cmd == CMD_QUIT) exit(0); } } return 0; }
/** * <Ring 1> The main loop of TASK MM. * *****************************************************************************/ PUBLIC void task_mm() { init_mm(); while (1) { send_recv(RECEIVE, ANY, &mm_msg); int src = mm_msg.source; int reply = 1; int msgtype = mm_msg.type; switch (msgtype) { case FORK: mm_msg.RETVAL = do_fork(); break; case EXIT: do_exit(mm_msg.STATUS); reply = 0; break; case EXEC: mm_msg.RETVAL = do_exec(); break; case WAIT: do_wait(); reply = 0; break; case KILL: mm_msg.RETVAL = do_kill(); break; case RAISE: mm_msg.RETVAL = do_raise(); break; case BRK: mm_msg.RETVAL = do_brk(); break; case ACCT: mm_msg.RETVAL = do_acct(); break; case GETUID: mm_msg.RETVAL = do_getuid(); break; case SETUID: mm_msg.RETVAL = do_setuid(); break; case GETGID: mm_msg.RETVAL = do_getgid(); break; case SETGID: mm_msg.RETVAL = do_setgid(); break; case GETEUID: mm_msg.RETVAL = do_geteuid(); break; case GETEGID: mm_msg.RETVAL = do_getegid(); break; case SIGACTION: mm_msg.RETVAL = do_sigaction(); break; case ALARM: mm_msg.RETVAL = do_alarm(); break; default: dump_msg("MM::unknown msg", &mm_msg); assert(0); break; } if (reply) { mm_msg.type = SYSCALL_RET; send_recv(SEND, src, &mm_msg); } } }
static void alarm_send(void) { mongoc_client_t *curclient = mongoc_client_new ("mongodb://172.16.0.7:27017/"); mongoc_collection_t *collection; mongoc_collection_t *sensorcoll; mongoc_collection_t *alarmcoll; mongoc_collection_t *contactcoll; mongoc_collection_t *alarmlogcoll; collection = mongoc_client_get_collection (curclient, "smart_trash_development", "devices"); sensorcoll = mongoc_client_get_collection (curclient, "smart_trash_development", "sensors"); alarmcoll = mongoc_client_get_collection (curclient, "smart_trash_development", "alarms"); alarmlogcoll = mongoc_client_get_collection (curclient, "smart_trash_development", "alarmlogs"); contactcoll = mongoc_client_get_collection (curclient, "smart_trash_development", "contacts"); mongoc_cursor_t *cursor; bson_t *doc; bson_t *query; char *str; query = bson_new (); cursor = mongoc_collection_find (alarmcoll, MONGOC_QUERY_NONE, 0, 0, 0, query, NULL, NULL); bson_oid_t se_oid; char se_id[1024]; memset(se_id,0,1024); char de_id[1024]; memset(de_id,'\0',1024); char alarmType[1024]; memset(alarmType,0,1024); char lowerBoundC[1024]; memset(lowerBoundC,0,1024); char upperBoundC[1024]; memset(upperBoundC,0,1024); char duration[1024]; memset(duration,0,1024); char target[1024]; memset(target,0,1024); char contactId[1024]; memset(contactId,0,1024); char userId[1024]; memset(userId,0,1024); while (mongoc_cursor_next (cursor, &doc)) { str = bson_as_json (doc, NULL); bson_free (str); bson_iter_t iter; bson_iter_t sub_iter; if (bson_iter_init (&iter, doc)) { while (bson_iter_next (&iter)) { bson_value_t *value; value = bson_iter_value (&iter); if (value->value_type == BSON_TYPE_UTF8) { if(strcmp(bson_iter_key (&iter),"sensorId")==0){ strcpy(se_id,value->value.v_utf8.str); }else if (strcmp(bson_iter_key (&iter),"alarmType")==0){ strcpy(alarmType,value->value.v_utf8.str); }else if (strcmp(bson_iter_key (&iter),"lowerBoundC")==0){ strcpy(lowerBoundC,value->value.v_utf8.str); }else if (strcmp(bson_iter_key (&iter),"upperBoundC")==0){ strcpy(upperBoundC,value->value.v_utf8.str); }else if (strcmp(bson_iter_key (&iter),"duration")==0){ strcpy(duration,value->value.v_utf8.str); }else if (strcmp(bson_iter_key (&iter),"target")==0){ strcpy(target,value->value.v_utf8.str); }else if (strcmp(bson_iter_key (&iter),"contactId")==0){ strcpy(contactId,value->value.v_utf8.str); }else if (strcmp(bson_iter_key (&iter),"userId")==0){ strcpy(userId,value->value.v_utf8.str); }else if (strcmp(bson_iter_key (&iter),"deviceId")==0){ strcpy(de_id,value->value.v_utf8.str); } } } } char mobile[256]; char addr[1024]; char device_name[2048]; memset(mobile,'\0',256); memset(addr,'\0',1024); memset(device_name,'\0',2048); getPhone(contactcoll,contactId,mobile); printf("\ndev_id:%s,lowerBoundC:%s,upperBoundC:%s\n",de_id,lowerBoundC,upperBoundC); getaddressbyID(addr,collection,de_id,device_name); do_alarm(sensorcoll,se_id,alarmType,upperBoundC,lowerBoundC,duration,target,mobile,addr,alarmlogcoll,userId,device_name,de_id); } bson_destroy (query); mongoc_collection_destroy (collection); mongoc_collection_destroy (sensorcoll); mongoc_collection_destroy (alarmcoll); mongoc_collection_destroy (alarmlogcoll); mongoc_client_destroy (curclient); }
static void doit() { iopause_fd x[2]; struct taia deadline; struct taia stamp; int wstat; long int time_cmp = 0; int r; char ch; char warn_message[2048]; int coredumped = 0; char restart_cmd[2048]; announce(); x[0].fd = selfpipe[0]; x[0].events = IOPAUSE_READ; x[1].fd = fdcontrol; x[1].events = IOPAUSE_READ; while (1) { if (flagexit && !pid) break; taia_now(&stamp); taia_uint(&deadline, 3600); taia_add(&deadline, &stamp, &deadline); sig_unblock(sig_child); iopause(x, 2, &deadline, &stamp); sig_block(sig_child); while (read(selfpipe[0], &ch, 1) == 1); while (1) { //waitpid(-1,&wstat,WNOHANG);WNOHANG : return immediately if no child has exited r = wait_nohang(&wstat); //r==0 if one or more child(ren) exit(s) but have not yet changed state if (!r) break; //r == -1 && errno == error_intr means waitpid is interrupted by a signal, we should call waitpid again. //here is not necessary cause we call waitpid with a WNOHANG argument. if (r == -1 && errno != error_intr) break; if (r == pid) { pid = 0; pidchange(); announce(); time_now = time((time_t *)0); if(time_old) { time_cmp = time_now - time_old; if(time_cmp >= time_alarm) //cmp { num = 0; } time_old = time_now; } else { time_cmp = 0; time_old = time_now; } if (0 != restart_sh[0]) { if (num == INT_MAX) num = 0; num++; if (snprintf(restart_cmd, sizeof(restart_cmd), "%s %d", restart_sh, num) > 1) { system(restart_cmd); write_log(fdlog, NOTICE, "restart_cmd: ", restart_cmd, " is called.\n"); } } else { if (WCOREDUMP(wstat)) { have_coredumped++; coredumped = 1; } bzero(warn_message, 2048); create_warn_message(warn_message, coredumped); write_log(fdlog, NOTICE, "service exited", coredumped ? " with coredump" : "", "!\n"); coredumped = 0; if (!closealarm && alarm_interval > 0 && have_tried++ == 0) { alarm(alarm_interval); do_alarm(warn_message); } if (flagexit || (alarm_interval > 0 && have_tried > max_tries && max_tries > 0) || (alarm_interval > 0 && have_coredumped > max_tries_if_coredumped && max_tries_if_coredumped > 0)) { write_log(fdlog, NOTICE, "supervise refused to restart ", service, " any more and exited itself!\n"); alarm(0); return; } } if (flagwant && flagwantup) { write_log(fdlog, NOTICE, "supervise is trying to restart ", service, "...\n"); trystart(); } break; } } if (read(fdcontrol, &ch, 1) != 1) continue; switch(ch) { // -s: Silent. Do not alarm any more. case 's': closealarm = 1; announce(); break; case 'n': closealarm = 0; announce(); break; case 'r': parse_conf(); break; // -d: Down. If the service is running, send it a TERM signal and then a CONT signal. // After it stops, do not restart it. case 'd': flagwant = 1; flagwantup = 0; if (pid) { kill(pid, SIGTERM); kill(pid, SIGCONT); flagpaused = 0; } announce(); break; // -u: Up. If the service is not running, start it. If the service stops, restart it. case 'u': flagwant = 1; flagwantup = 1; announce(); if (!pid) trystart(); break; // -o: Once. If the service is not running, start it. Do not restart it if it stops. case 'o': flagwant = 0; announce(); if (!pid) trystart(); break; // -a: Alarm. Send the service an ALRM signal. case 'a': if (pid) kill(pid, SIGALRM); break; // -h: Hangup. Send the service a HUP signal. case 'h': if (pid) kill(pid, SIGHUP); break; // -k: Kill. Send the service a KILL signal. case 'k': if (pid) kill(pid, SIGKILL); break; //* -t: Terminate. Send the service a TERM signal. case 't': if (pid) kill(pid, SIGTERM); break; // -i: Interrupt. Send the service an INT signal. case 'i': if (pid) kill(pid, SIGINT); break; // -p: Pause. Send the service a STOP signal. case 'p': flagpaused = 1; announce(); if (pid) kill(pid, SIGSTOP); break; // -c: Continue. Send the service a CONT signal. case 'c': flagpaused = 0; announce(); if (pid) kill(pid, SIGCONT); break; // -x: Exit. supervise will exit as soon as the service is down. If you use this option on a //stable system, you're doing something wrong; supervise is designed to run forever. case 'x': flagexit = 1; announce(); break; } //end switch } //end while }