示例#1
0
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;
	}
}
示例#2
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;
}
示例#3
0
文件: main.c 项目: BackupGGCode/lyos
/**
 * <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);
		}
	}
}
示例#4
0
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);
}
示例#5
0
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
}