Пример #1
0
int
read_event_notify(int descr, dbref player, const char* cmd)
{
	timequeue ptr;

	if (muf_event_read_notify(descr, player, cmd)) {
		return 1;
	}

	ptr = tqhead;
	while (ptr) {
		if (ptr->uid == player) {
			if (ptr->fr && ptr->fr->multitask != BACKGROUND) {
				if (*cmd || ptr->fr->wantsblanks) {
					struct inst temp;

					temp.type = PROG_INTEGER;
					temp.data.number = descr;
					muf_event_add(ptr->fr, "READ", &temp, 1);
					return 1;
				}
			}
		}
		ptr = ptr->next;
	}
	return 0;
}
Пример #2
0
void
prim_watchpid(PRIM_PROTOTYPE)
{
	struct frame *frame;

	CHECKOP(1);
	oper1 = POP();

	if (mlev < 3) {
		abort_interp("Mucker level 3 required.");
	}

	if (oper1->type != PROG_INTEGER) {
		abort_interp("Process PID expected.");
	}

/* Lets see if the batbat catches this one. */
/* Heh.  - Revar */
	if (oper1->data.number == fr->pid) {
		abort_interp("Narcissistic processes not allowed.");
	}

	frame = timequeue_pid_frame (oper1->data.number);
	if (frame) {
		struct mufwatchpidlist **cur;
		struct mufwatchpidlist *waitee;

		for (cur = &frame->waiters; *cur; cur = &(*cur)->next) {
			if ((*cur)->pid == oper1->data.number) {
				break;
			}
		}

		if (!*cur) {
			*cur = (struct mufwatchpidlist*) malloc (sizeof (**cur));
			if (!*cur) {
				abort_interp ("Internal memory error.\n");
			}
			(*cur)->next = 0;
			(*cur)->pid = fr->pid;

			waitee = (struct mufwatchpidlist*) malloc (sizeof (*waitee));
			if (!waitee) {
				abort_interp ("Internal memory error.\n");
			}
			waitee->next = fr->waitees;
			waitee->pid = oper1->data.number;
			fr->waitees = waitee;
		}
	} else {
		char buf[64];

		snprintf (buf, sizeof(buf), "PROC.EXIT.%d", oper1->data.number);
		muf_event_add(fr, buf, oper1, 0);
	}

	CLEAR (oper1);
}
Пример #3
0
/* clean up lists from watchpid and sends event */
void
watchpid_process(struct frame *fr)
{
	if (!fr) {
		log_status("WARNING: watchpid_process(): NULL frame passed !  Ignored.");
		return;
	}

	struct frame *frame;
	struct mufwatchpidlist *cur;
	struct mufwatchpidlist **curptr;
	struct inst temp1;
	temp1.type = PROG_INTEGER;
	temp1.data.number = fr->pid;

	while (fr->waitees) {
		cur = fr->waitees;
		fr->waitees = cur->next;

		frame = timequeue_pid_frame (cur->pid);
		free (cur);
		if (frame) {
			for (curptr = &frame->waiters; *curptr; curptr = &(*curptr)->next) {
				if ((*curptr)->pid == fr->pid) {
					cur = *curptr;
					*curptr = (*curptr)->next;
					free (cur);
					break;
				}
			}
		}
	}

	while (fr->waiters) {
		char buf[64];

		snprintf (buf, sizeof(buf), "PROC.EXIT.%d", fr->pid);

		cur = fr->waiters;
		fr->waiters = cur->next;

		frame = timequeue_pid_frame (cur->pid);
		free (cur);
		if (frame) {
			muf_event_add(frame, buf, &temp1, 0);
			for (curptr = &frame->waitees; *curptr; curptr = &(*curptr)->next) {
				if ((*curptr)->pid == fr->pid) {
					cur = *curptr;
					*curptr = (*curptr)->next;
					free (cur);
					break;
				}
			}
		}
	}
}
Пример #4
0
void
prim_event_send(PRIM_PROTOTYPE)
{
    struct frame *destfr;
    stk_array *arr;
    struct inst temp1;

    CHECKOP(3);
    oper3 = POP();		/* any: data to pass */
    oper2 = POP();		/* string: event id */
    oper1 = POP();		/* int: process id to send to */

    if (mlev < 3)
	abort_interp("Requires Mucker level 3 or better.");
    if (oper1->type != PROG_INTEGER)
	abort_interp("Expected an integer process id. (1)");
    if (oper2->type != PROG_STRING)
	abort_interp("Expected a string event id. (2)");

    if (oper1->data.number == fr->pid)
	destfr = fr;
    else
	destfr = timequeue_pid_frame(oper1->data.number);

    if (destfr) {
        stk_array_active_list = &destfr->array_active_list;
        struct inst data_copy;
        deep_copyinst(oper3, &data_copy, destfr->pinning);
	arr = new_array_dictionary(destfr->pinning);
	array_set_strkey(&arr, "data", &data_copy);
	array_set_strkey_intval(&arr, "caller_pid", fr->pid);
	array_set_strkey_intval(&arr, "descr", fr->descr);
	array_set_strkey_refval(&arr, "caller_prog", program);
	array_set_strkey_refval(&arr, "trigger", fr->trig);
	array_set_strkey_refval(&arr, "prog_uid", ProgUID);
	array_set_strkey_refval(&arr, "player", player);

	temp1.type = PROG_ARRAY;
	temp1.data.array = arr;

	snprintf(buf, sizeof(buf), "USER.%.32s", DoNullInd(oper2->data.string));
	muf_event_add(destfr, buf, &temp1, 0);

        stk_array_active_list = &fr->array_active_list;

	CLEAR(&temp1);
        CLEAR(&data_copy);
    }

    CLEAR(oper1);
    CLEAR(oper2);
    CLEAR(oper3);
}
Пример #5
0
void
prim_event_send(PRIM_PROTOTYPE)
{
      struct frame *destfr;
      stk_array *arr;
      struct inst temp1;

	CHECKOP(3);
	oper3 = POP();				/* any: data to pass */
	oper2 = POP();				/* string: event id */
	oper1 = POP();				/* int: process id to send to */

	if (mlev < 3)
		abort_interp("Requires Mucker level 3 or better.");
	if (oper1->type != PROG_INTEGER)
		abort_interp("Expected an integer process id. (1)");
	if (oper2->type != PROG_STRING)
		abort_interp("Expected a string event id. (2)");

      destfr = (struct frame*) timequeue_pid_frame(oper1->data.number);
	if (destfr) {
		arr = new_array_dictionary();
		array_set_strkey(&arr, "data", oper3);
		array_set_strkey_intval(&arr, "caller_pid", fr->pid);
		array_set_strkey_refval(&arr, "caller_prog", program);

		temp1.type = PROG_ARRAY;
		temp1.data.array = arr; 

		sprintf(buf, "USER.%.32s", DoNullInd(oper2->data.string));
		muf_event_add(destfr, buf, oper3);
	}

      CLEAR(oper1);
	CLEAR(oper2);
	CLEAR(oper3);
}
Пример #6
0
void
next_timequeue_event(void)
{
	struct frame *tmpfr;
	int tmpbl, tmpfg;
	timequeue lastevent, event;
	int maxruns = 0;
	int forced_pid = 0;
	time_t rtime;

	time(&rtime);

	lastevent = tqhead;
	while ((lastevent) && (rtime >= lastevent->when) && (maxruns < 10)) {
		lastevent = lastevent->next;
		maxruns++;
	}

	while (tqhead && (tqhead != lastevent) && (maxruns--)) {
		if (tqhead->typ == TQ_MUF_TYP && tqhead->subtyp == TQ_MUF_READ) {
			break;
		}
		event = tqhead;
		tqhead = tqhead->next;
		process_count--;
		forced_pid = event->eventnum;
		event->eventnum = 0;
		if (event->typ == TQ_MPI_TYP) {
			char cbuf[BUFFER_LEN];
			int ival;

			strcpyn(match_args, sizeof(match_args), event->str3 ? event->str3 : "");
			strcpyn(match_cmdname, sizeof(match_cmdname), event->command ? event->command : "");
			ival = (event->subtyp & TQ_MPI_OMESG) ? MPI_ISPUBLIC : MPI_ISPRIVATE;
			if (event->subtyp & TQ_MPI_BLESSED) {
				ival |= MPI_ISBLESSED;
			}
			if (event->subtyp & TQ_MPI_LISTEN) {
				ival |= MPI_ISLISTENER;
				do_parse_mesg(event->descr, event->uid, event->trig, event->called_data,
							  "(MPIlisten)", cbuf, sizeof(cbuf), ival);
			} else if ((event->subtyp & TQ_MPI_SUBMASK) == TQ_MPI_DELAY) {
				do_parse_mesg(event->descr, event->uid, event->trig, event->called_data,
							  "(MPIdelay)", cbuf, sizeof(cbuf), ival);
			} else {
				do_parse_mesg(event->descr, event->uid, event->trig, event->called_data,
							  "(MPIqueue)", cbuf, sizeof(cbuf), ival);
			}
			if (*cbuf) {
				if (!(event->subtyp & TQ_MPI_OMESG)) {
					notify_filtered(event->uid, event->uid, cbuf, 1);
				} else {
					char bbuf[BUFFER_LEN];
					dbref plyr;

					snprintf(bbuf, sizeof(bbuf), ">> %.4000s %.*s",
							NAME(event->uid),
							(int)(4000 - strlen(NAME(event->uid))),
							pronoun_substitute(event->descr, event->uid, cbuf));
					plyr = DBFETCH(event->loc)->contents;
					for (; plyr != NOTHING; plyr = DBFETCH(plyr)->next) {
						if (Typeof(plyr) == TYPE_PLAYER && plyr != event->uid)
							notify_filtered(event->uid, plyr, bbuf, 0);
					}
				}
			}
		} else if (event->typ == TQ_MUF_TYP) {
			if (Typeof(event->called_prog) == TYPE_PROGRAM) {
				if (event->subtyp == TQ_MUF_DELAY) {
					/* Uncomment when DBFETCH "does" something */
					/* FIXME: DBFETCH(event->uid); */
					tmpbl = PLAYER_BLOCK(event->uid);
					tmpfg = (event->fr->multitask != BACKGROUND);
					interp_loop(event->uid, event->called_prog, event->fr, 0);
					if (!tmpfg) {
						PLAYER_SET_BLOCK(event->uid, tmpbl);
					}
				} else if (event->subtyp == TQ_MUF_TIMER) {
					struct inst temp;

					temp.type = PROG_INTEGER;
					temp.data.number = event->when;
					event->fr->timercount--;
					muf_event_add(event->fr, event->called_data, &temp, 0);
				} else if (event->subtyp == TQ_MUF_TREAD) {
					handle_read_event(event->descr, event->uid, NULL);
				} else {
					strcpyn(match_args, sizeof(match_args), event->called_data ? event->called_data : "");
					strcpyn(match_cmdname, sizeof(match_cmdname), event->command ? event->command : "");
					tmpfr = interp(event->descr, event->uid, event->loc, event->called_prog,
								   event->trig, BACKGROUND, STD_HARDUID, forced_pid);
					if (tmpfr) {
						interp_loop(event->uid, event->called_prog, tmpfr, 0);
					}
				}
			}
		}
		event->fr = NULL;
		free_timenode(event);
	}
}