Пример #1
0
/*
 * Define a user named label to have the offset of the next opcode.
 *
 * given:
 *	name		label name
 */
void
definelabel(char *name)
{
	register LABEL *lp;		/* current label */
	long i;				/* current label index */

	i = findstr(&labelnames, name);
	if (i >= 0) {
		lp = &labels[i];
		if (lp->l_offset >= 0) {
			scanerror(T_NULL, "Label \"%s\" is multiply defined",
				name);
			return;
		}
		setlabel(lp);
		return;
	}
	if (labelcount >= MAXLABELS) {
		scanerror(T_NULL, "Too many labels in use");
		return;
	}
	lp = &labels[labelcount++];
	lp->l_chain = -1L;
	lp->l_offset = (long)curfunc->f_opcodecount;
	lp->l_name = addstr(&labelnames, name);
	clearopt();
}
Пример #2
0
/* Address of the source must already have been loaded in PRI, the
 * destination address in ALT.
 * This routine makes a loop that copies the minor dimension vector
 * by vector.
 */
SC_FUNC void copyarray2d(int majordim,int minordim)
{
  int looplbl=getlabel();

  stgwrite("\tpush.alt\n");
  stgwrite("\tpush.pri\n");
  stgwrite("\tzero.alt\n"); /* ALT = index = 0 */
  setlabel(looplbl);
  stgwrite("\tpush.alt\n"); /* save index */
  stgwrite("\tpick 8\n");   /* PRI = dest */
  stgwrite("\txchg\n");     /* ALT = dest, PRI = index */
  stgwrite("\tidxaddr\n");  /* PRI = dest + index * sizeof(cell) */
  stgwrite("\tmove.alt\n"); /* ALT = dest + index * sizeof(cell) */
  stgwrite("\tload.i\n");   /* PRI = dest[index * sizeof(cell)] */
  stgwrite("\tadd\n");      /* PRI = dest + index * sizeof(cell) + dest[index * sizeof(cell)] */
  stgwrite("\tpush.pri\n");
  stgwrite("\tpick 8\n");   /* PRI = source */
  stgwrite("\tmove.alt\n"); /* ALT = source */
  stgwrite("\tpick 4\n");   /* PRI = index */
  stgwrite("\tidxaddr\n");  /* PRI = source + index * sizeof(cell) */
  stgwrite("\tmove.alt\n"); /* ALT = source + index * sizeof(cell) */
  stgwrite("\tload.i\n");   /* PRI = source[index * sizeof(cell)] */
  stgwrite("\tadd\n");      /* PRI = source + index * sizeof(cell) + source[index * sizeof(cell)] */
  stgwrite("\tpop.alt\n");  /* ALT = source + index * sizeof(cell) + source[index * sizeof(cell)] */
  stgwrite("\tmovs "); outval(minordim*sizeof(cell),TRUE,TRUE);
  stgwrite("\tpop.alt\n");  /* ALT = saved index */
  stgwrite("\tinc.alt\n");  /* ALT = index + 1 */
  stgwrite("\teq.c.alt "); outval(majordim,TRUE,TRUE);
  stgwrite("\tjzer "); outval(looplbl,TRUE,TRUE);
  stgwrite("\tpop.pri\n");  /* restore stack & registers */
  stgwrite("\tpop.alt\n");

  code_idx+=opcodes(26)+opargs(6);
}
Пример #3
0
void Fl_Type::label(const char *n) 
{
	if(storestring(n,label_,1)) {
		setlabel(label_);
		widget_browser->redraw();
	}
}
Пример #4
0
/*
 * Always splhi()'ed.
 */
void
schedinit(void)		/* never returns */
{
	Edf *e;

	machp()->inidle = 1;
	machp()->proc = nil;
	ainc(&run.nmach);

	setlabel(&machp()->sched);

	Proc *up = externup();

	if(infected_with_std()){
		print("mach %d got an std from %s (pid %d)!\n",
			machp()->machno,
			up ? up->text : "*notext",
			up ? up->pid : -1
		);
		disinfect_std();
	}

	if(up) {
		if((e = up->edf) && (e->flags & Admitted))
			edfrecord(up);
		machp()->qstart = 0;
		machp()->qexpired = 0;
		coherence();
		machp()->proc = 0;
		switch(up->state) {
		case Running:
			ready(up);
			break;
		case Moribund:
			up->state = Dead;
			stopac();
			edfstop(up);
			if (up->edf)
				free(up->edf);
			up->edf = nil;

			/*
			 * Holding locks from pexit:
			 * 	procalloc
			 *	pga
			 */
			mmurelease(up);
			unlock(&pga.l);

			psrelease(up);
			unlock(&procalloc.l);
			break;
		}
		up->mach = nil;
		updatecpu(up);
		machp()->externup = nil;
	}
	sched();
}
Пример #5
0
/* initialization plot struct --------------------------------------------------
* set value to plot struct
* args   : sdrplt_t *acq    I/0 plot struct for acquisition
*          sdrplt_t *trk    I/0 plot struct for tracking
*          sdrch_t  *sdr    I   sdr channel struct
* return : int                  0:okay -1:error
*-----------------------------------------------------------------------------*/
extern int initpltstruct(sdrplt_t *acq, sdrplt_t *trk, sdrch_t *sdr)
{
    double scale=1.0;

    /* acquisition */
    if (sdrini.pltacq) {
        setsdrplotprm(acq,PLT_SURFZ,sdr->acq.nfreq,sdr->nsamp,3,OFF,1,
            PLT_H,PLT_W,PLT_MH,PLT_MW,sdr->no);
        if (initsdrplot(acq)<0) return -1;
        settitle(acq,sdr->satstr);
        setlabel(acq,"Frequency (Hz)","Code Offset (sample)");
    }
    /* tracking */
    if (sdrini.plttrk) {
        setsdrplotprm(trk,PLT_XY,1+2*sdr->trk.corrn,0,0,ON,0.001,
            PLT_H,PLT_W,PLT_MH,PLT_MW,sdr->no);
        if(initsdrplot(trk)<0) return -1;
        settitle(trk,sdr->satstr);
        setlabel(trk,"Code Offset (sample)","Correlation Output");
        
        switch (sdrini.fend) {
            case FEND_GN3SV2:
            case FEND_GN3SV3:
            case FEND_FGN3SV2:
            case FEND_FGN3SV3:
                scale=1.5; break;
            case FEND_BLADERF:
            case FEND_FBLADERF:
                scale=5.0; break;
            case FEND_RTLSDR:
            case FEND_FRTLSDR:
                scale=3.5; break;
        }
        setyrange(trk,0,sdr->trk.loop*sdr->nsamp/4000*scale);
    }

    if (sdrini.fend==FEND_FILE||sdrini.fend==FEND_FSTEREO||
        sdrini.fend==FEND_FGN3SV2||sdrini.fend==FEND_FGN3SV2||
        sdrini.fend==FEND_FRTLSDR||sdrini.fend==FEND_FBLADERF) {
        trk->pltms=PLT_MS_FILE;
    } else {
        trk->pltms=PLT_MS;
    }
    return 0;
}
Пример #6
0
void
error(char *err)
{
	spllo();

	assert(up->nerrlab < NERR);
	kstrcpy(up->errstr, err, ERRMAX);
	setlabel(&up->errlab[NERR-1]);
	nexterror();
}
Пример #7
0
void MainWindow::on_pushButton_clicked()
{
    gobj.init();
    setlabel();
    flag = 1;
    gobj.score = 0;
    step = 0;
    ui->lcdNumber->display(gobj.score);
    ui->lcdNumber_2->display(step);
}
Пример #8
0
MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);
    gobj.init();
    setlabel();
    flag = 1;
    step = 0;
    resWin = new Result;
}
Пример #9
0
Файл: proc.c Проект: npe9/harvey
void
error(char *err)
{
	Mach *m = machp();
	spllo();

	assert(m->externup->nerrlab < NERR);
	kstrcpy(m->externup->errstr, err, ERRMAX);
	setlabel(&m->externup->errlab[NERR-1]);
	nexterror();
}
Пример #10
0
Файл: proc.c Проект: 8l/inferno
void
error(char *err)
{
	if(up == nil)
		panic("error(%s) not in a process", err);
	spllo();
	if(up->nerrlab > NERR)
		panic("error stack too deep");
	if(err != up->env->errstr)
		kstrcpy(up->env->errstr, err, ERRMAX);
	setlabel(&up->errlab[NERR-1]);
	nexterror();
}
Пример #11
0
/*
 * Open an information (display) window.
 */
struct ww *
openiwin(int nrow, const char *label)
{
	struct ww *w;

	if ((w = wwopen(WWT_INTERNAL, 0, nrow, wwncol, 2, 0, 0)) == 0)
		return 0;
	SET(w->ww_wflags, WWW_MAPNL | WWW_NOINTR | WWW_NOUPDATE | WWW_UNCTRL);
	SET(w->ww_uflags, WWU_HASFRAME | WWU_CENTER);
	w->ww_id = -1;
	(void) setlabel(w, label);
	addwin(w, 1);
	reframe();
	return w;
}
Пример #12
0
Файл: proc.c Проект: npe9/harvey
/*
 * Always splhi()'ed.
 */
void
schedinit(void)		/* never returns */
{
	Mach *m = machp();
	Edf *e;

	m->inidle = 1;
	m->proc = nil;
	ainc(&run.nmach);

	setlabel(&m->sched);
	if(m->externup) {
		if((e = m->externup->edf) && (e->flags & Admitted))
			edfrecord(m->externup);
		m->qstart = 0;
		m->qexpired = 0;
		coherence();
		m->proc = 0;
		switch(m->externup->state) {
		case Running:
			ready(m->externup);
			break;
		case Moribund:
			m->externup->state = Dead;
			stopac();
			edfstop(m->externup);
			if (m->externup->edf)
				free(m->externup->edf);
			m->externup->edf = nil;

			/*
			 * Holding locks from pexit:
			 * 	procalloc
			 *	pga
			 */
			mmurelease(m->externup);
			unlock(&pga);

			psrelease(m->externup);
			unlock(&procalloc);
			break;
		}
		m->externup->mach = nil;
		updatecpu(m->externup);
		m->externup = nil;
	}
	sched();
}
Пример #13
0
/*
 * Always splhi()'ed.
 */
void
schedinit(void)		/* never returns */
{
	Edf *e;

	setlabel(&m->sched);
	if(up != nil) {
		if((e = up->edf) != nil && (e->flags & Admitted))
			edfrecord(up);
		m->proc = nil;
		switch(up->state) {
		case Running:
			ready(up);
			break;
		case Moribund:
			up->state = Dead;
			edfstop(up);
			if(up->edf != nil)
				free(up->edf);
			up->edf = nil;

			/*
			 * Holding locks from pexit:
			 * 	procalloc
			 *	palloc
			 */
			mmurelease(up);
			unlock(&palloc);

			up->mach = nil;
			updatecpu(up);

			up->qnext = procalloc.free;
			procalloc.free = up;

			/* proc is free now, make sure unlock() wont touch it */
			up = procalloc.Lock.p = nil;
			unlock(&procalloc);
			sched();
		}
		up->mach = nil;
		updatecpu(up);
		up = nil;
	}
	sched();
}
Пример #14
0
Файл: proc.c Проект: 8l/inferno
void
sched(void)
{
	if(up) {
		splhi();
		procsave(up);
		if(setlabel(&up->sched)) {
			/* procrestore(up); */
			spllo();
			return;
		}
		gotolabel(&m->sched);
	}
	up = runproc();
	up->state = Running;
	up->mach = MACHP(m->machno);	/* m might be a fixed address; use MACHP */
	m->proc = up;
	gotolabel(&up->sched);
}
Пример #15
0
/*
 * Open a user window.
 */
struct ww *
openwin(int id, int row, int col, int nrow, int ncol, int nline, char *label, int type, int uflags, char *shf, char **sh)
{
	struct ww *w;

	if (id < 0 && (id = findid()) < 0)
		return 0;
	if (row + nrow <= 0 || row > wwnrow - 1
	    || col + ncol <= 0 || col > wwncol - 1) {
		error("Illegal window position.");
		return 0;
	}
	w = wwopen(type, 0, nrow, ncol, row, col, nline);
	if (w == 0) {
		error("Can't open window: %s.", wwerror());
		return 0;
	}
	w->ww_id = id;
	window[id] = w;
	CLR(w->ww_uflags, WWU_ALLFLAGS);
	SET(w->ww_uflags, uflags);
	w->ww_alt = w->ww_w;
	if (label != 0 && setlabel(w, label) < 0)
		error("No memory for label.");
	wwcursor(w, 1);
	/*
	 * We have to do this little maneuver to make sure
	 * addwin() puts w at the top, so we don't waste an
	 * insert and delete operation.
	 */
	setselwin((struct ww *)0);
	addwin(w, 0);
	setselwin(w);
	if (wwspawn(w, shf, sh) < 0) {
		error("Can't execute %s: %s.", shf, wwerror());
		closewin(w);
		return 0;
	}
	return w;
}
Пример #16
0
Файл: proc.c Проект: 8l/inferno
/*
 * Always splhi()'ed.
 */
void
schedinit(void)		/* never returns */
{
	setlabel(&m->sched);
	if(up) {
/*
		if((e = up->edf) && (e->flags & Admitted))
			edfrecord(up);
*/
		m->proc = nil;
		switch(up->state) {
		case Running:
			ready(up);
			break;
		case Moribund:
			up->state = Dead;
/*
			edfstop(up);
			if(up->edf){
				free(up->edf);
				up->edf = nil;
			}
*/
			/*
			 * Holding locks from pexit:
			 * 	procalloc
			 */
			up->qnext = procalloc.free;
			procalloc.free = up;
			unlock(&procalloc);
			break;
		}
		up->mach = nil;
		up = nil;
	}
	sched();
}
Пример #17
0
/* writestatetables
 * Creates and dumps the state tables. Every function with states has a state
 * table that contains jump addresses (or overlay indices) the branch to the
 * appropriate function using the (hidden) state variable as the criterion.
 * Technically, this happens in a "switch" (or an "iswitch") instruction.
 * This function also creates the hidden state variables (one for each
 * automaton) in the data segment.
 */
SC_FUNC void writestatetables(symbol *root,int lbl_nostate,int lbl_ignorestate)
{
  int lbl_default,lbl_table,lbl_defnostate;
  int statecount;
  symbol *sym;
  constvalue *fsa, *state;
  statelist *stlist;
  int fsa_id,listid;

  assert(code_idx>0);   /* leader must already have been written */

  /* check whether there are any functions that have states */
  for (sym=root->next; sym!=NULL; sym=sym->next)
    if (sym->ident==iFUNCTN && (sym->usage & (uPUBLIC | uREAD))!=0 && sym->states!=NULL)
      break;
  if (sym==NULL)
    return;             /* no function has states, nothing to do next */

  assert(pc_ovl0size[ovlNO_STATE][0]>0); /* state exit point must already have been created */
  assert(pc_ovl0size[ovlNO_STATE][1]>0);

  /* write the "state-selectors" table with all automatons (update the
   * automatons structure too, as we are now assigning the address to
   * each automaton state-selector variable)
   */
  assert(glb_declared==0);
  begdseg();
  for (fsa=sc_automaton_tab.next; fsa!=NULL; fsa=fsa->next) {
    defstorage();
    stgwrite("0\t; automaton ");
    if (strlen(fsa->name)==0)
      stgwrite("(anonymous)");
    else
      stgwrite(fsa->name);
    stgwrite("\n");
    fsa->value=glb_declared*sizeof(cell);
    glb_declared++;
  } /* for */

  /* write stubs and jump tables for all state functions */
  begcseg();
  for (sym=root->next; sym!=NULL; sym=sym->next) {
    if (sym->ident==iFUNCTN && (sym->usage & (uPUBLIC | uREAD))!=0 && sym->states!=NULL) {
      stlist=sym->states->next;
      assert(stlist!=NULL);     /* there should be at least one state item */
      listid=stlist->id;
      assert(listid==-1 || listid>0);
      if (listid==-1 && stlist->next!=NULL) {
        /* first index is the "fallback", take the next one (if available) */
        stlist=stlist->next;
        listid=stlist->id;
      } /* if */
      if (listid==-1) {
        /* first index is the fallback, there is no second... */
        stlist->label=0;        /* insert dummy label number */
        /* this is an error, but we postpone adding the error message until the
         * function definition
         */
        continue;
      } /* if */
      /* generate label numbers for all statelist ids */
      for (stlist=sym->states->next; stlist!=NULL; stlist=stlist->next) {
        if (pc_overlays>0) {
          /* code overlay indices should already be set, see gen_ovlinfo() */
          assert(stlist->label>0);
        } else {
          assert(stlist->label==0);
          stlist->label=getlabel();
        } /* if */
      } /* for */
      if (strcmp(sym->name,uENTRYFUNC)==0)
        continue;               /* do not generate stubs for this special function */
      sym->addr=code_idx;       /* fix the function address now */
      /* get automaton id for this function */
      assert(listid>0);
      fsa_id=state_getfsa(listid);
      assert(fsa_id>=0);        /* automaton 0 exists */
      fsa=automaton_findid(fsa_id);
      /* count the number of states actually used; at the same time, check
       * whether there is a default (i.e. "fallback") state function
       */
      statecount=0;
      if (strcmp(sym->name,uEXITFUNC)==0) {
        lbl_default= (pc_overlays>0) ? ovlEXITSTATE : lbl_ignorestate;
      } else {
        lbl_defnostate= (pc_overlays>0) ? ovlNO_STATE : lbl_nostate;
        lbl_default=lbl_defnostate;
      } /* if */
      for (stlist=sym->states->next; stlist!=NULL; stlist=stlist->next) {
        if (stlist->id==-1) {
          lbl_default=stlist->label;
        } else {
          statecount+=state_count(stlist->id);
        } /* if */
      } /* for */
      /* generate a stub entry for the functions */
      stgwrite("\tload.pri ");
      outval(fsa->value,TRUE,FALSE);
      stgwrite("\t; ");
      stgwrite(sym->name);
      if (pc_overlays>0) {
        /* add overlay index */
        stgwrite("/");
        outval(sym->index,FALSE,FALSE);
      } /* if */
      stgwrite("\n");
      code_idx+=opcodes(1)+opargs(1);   /* calculate code length */
      lbl_table=getlabel();
      ffswitch(lbl_table,(pc_overlays>0));
      /* generate the jump table */
      setlabel(lbl_table);
      ffcase(statecount,lbl_default,TRUE,(pc_overlays>0));
      for (state=sc_state_tab.next; state!=NULL; state=state->next) {
        if (state->index==fsa_id) {
          /* find the label for this list id */
          for (stlist=sym->states->next; stlist!=NULL; stlist=stlist->next) {
            if (stlist->id!=-1 && state_inlist(stlist->id,(int)state->value)) {
              /* when overlays are used, the jump-label for the case statement
               * are overlay indices instead of code labels
               */
              ffcase(state->value,stlist->label,FALSE,(pc_overlays>0));
              break;
            } /* if */
          } /* for */
          if (stlist==NULL && lbl_default==lbl_defnostate)
            error(230,state->name,sym->name);  /* unimplemented state, no fallback */
        } /* if (state belongs to automaton of function) */
      } /* for (state) */
      stgwrite("\n");
      /* the jump table gets its own overlay index, and the size of the jump
       * table must therefore be known (i.e. update the codeaddr field of the
       * function with the address where the jump table ends)
       */
      sym->codeaddr=code_idx;
    } /* if (is function, used & having states) */
  } /* for (sym) */
}
Пример #18
0
/*
 *  sleep if a condition is not true.  Another process will
 *  awaken us after it sets the condition.  When we awaken
 *  the condition may no longer be true.
 *
 *  we lock both the process and the rendezvous to keep r->p
 *  and p->r synchronized.
 */
void
sleep(Rendez *r, int (*f)(void*), void *arg)
{
	int s;
	void (*pt)(Proc*, int, vlong);

	s = splhi();

	if(up->nlocks)
		print("process %lud sleeps with %d locks held, last lock %#p locked at pc %#p, sleep called from %#p\n",
			up->pid, up->nlocks, up->lastlock, up->lastlock->pc, getcallerpc(&r));
	lock(r);
	lock(&up->rlock);
	if(r->p != nil){
		print("double sleep called from %#p, %lud %lud\n", getcallerpc(&r), r->p->pid, up->pid);
		dumpstack();
	}

	/*
	 *  Wakeup only knows there may be something to do by testing
	 *  r->p in order to get something to lock on.
	 *  Flush that information out to memory in case the sleep is
	 *  committed.
	 */
	r->p = up;

	if((*f)(arg) || up->notepending){
		/*
		 *  if condition happened or a note is pending
		 *  never mind
		 */
		r->p = nil;
		unlock(&up->rlock);
		unlock(r);
	} else {
		/*
		 *  now we are committed to
		 *  change state and call scheduler
		 */
		pt = proctrace;
		if(pt != nil)
			pt(up, SSleep, 0);
		up->state = Wakeme;
		up->r = r;

		/* statistics */
		m->cs++;

		procsave(up);
		if(setlabel(&up->sched)) {
			/*
			 *  here when the process is awakened
			 */
			procrestore(up);
			spllo();
		} else {
			/*
			 *  here to go to sleep (i.e. stop Running)
			 */
			unlock(&up->rlock);
			unlock(r);
			gotolabel(&m->sched);
		}
	}

	if(up->notepending) {
		up->notepending = 0;
		splx(s);
		interrupted();
	}

	splx(s);
}
Пример #19
0
void
viewer(Document *dd)
{
	int i, fd, n, oldpage;
	int nxt;
	Menu menu, midmenu;
	Mouse m;
	Event e;
	Point dxy, oxy, xy0;
	Image *tmp;

	static char *fwditems[] = { "this page", "next page", "exit", 0 };
 	static char *miditems[] = {
 		"orig size",
 		"zoom in",
 		"fit window",
 		"rotate 90",
 		"upside down",
 		"",
 		"next",
 		"prev",
		"zerox",
 		"",
 		"reverse",
 		"discard",
 		"write",
 		"",
 		"quit",
 		0
 	};
	char *s;
	enum { Eplumb = 4 };
	Plumbmsg *pm;

	doc = dd;    /* save global for menuhit */
	ul = screen->r.min;
	einit(Emouse|Ekeyboard);
	if(doc->addpage != nil)
		eplumb(Eplumb, "image");

	esetcursor(&reading);

	/*
	 * im is a global pointer to the current image.
	 * eventually, i think we will have a layer between
	 * the display routines and the ps/pdf/whatever routines
	 * to perhaps cache and handle images of different
	 * sizes, etc.
	 */
	im = 0;
	page = reverse ? doc->npage-1 : 0;

	if(doc->fwdonly) {
		menu.item = fwditems;
		menu.gen = 0;
		menu.lasthit = 0;
	} else {
		menu.item = 0;
		menu.gen = menugen;
		menu.lasthit = 0;
	}

	midmenu.item = miditems;
	midmenu.gen = 0;
	midmenu.lasthit = Next;

	if(doc->docname != nil)
		setlabel(doc->docname);
	showpage(page, &menu);
	esetcursor(nil);

	nxt = 0;
	for(;;) {
		/*
		 * throughout, if doc->fwdonly is set, we restrict the functionality
		 * a fair amount.  we don't care about doc->npage anymore, and
		 * all that can be done is select the next page.
		 */
		unlockdisplay(display);
		i = eread(Emouse|Ekeyboard|Eplumb, &e);
		lockdisplay(display);
		switch(i){
		case Ekeyboard:
			if(e.kbdc <= 0xFF && isdigit(e.kbdc)) {
				nxt = nxt*10+e.kbdc-'0';
				break;
			} else if(e.kbdc != '\n')
				nxt = 0;
			switch(e.kbdc) {
			case 'r':	/* reverse page order */
				if(doc->fwdonly)
					break;
				reverse = !reverse;
				menu.lasthit = doc->npage-1-menu.lasthit;

				/*
				 * the theory is that if we are reversing the
				 * document order and are on the first or last
				 * page then we're just starting and really want
		 	 	 * to view the other end.  maybe the if
				 * should be dropped and this should happen always.
				 */
				if(page == 0 || page == doc->npage-1) {
					page = doc->npage-1-page;
					showpage(page, &menu);
				}
				break;
			case 'w':	/* write bitmap of current screen */
				esetcursor(&reading);
				s = writebitmap();
				if(s)
					string(screen, addpt(screen->r.min, Pt(5,5)), display->black, ZP,
						display->defaultfont, s);
				esetcursor(nil);
				flushimage(display, 1);
				break;
			case 'd':	/* remove image from working set */
				if(doc->rmpage && page < doc->npage) {
					if(doc->rmpage(doc, page) >= 0) {
						if(doc->npage < 0)
							wexits(0);
						if(page >= doc->npage)
							page = doc->npage-1;
						showpage(page, &menu);
					}
				}
				break;
			case 'q':
			case 0x04: /* ctrl-d */
				wexits(0);
			case 'u':
				if(im==nil)
					break;
				angle = (angle+180) % 360;
				showpage(page, &menu);
				break;
			case '-':
			case '\b':
			case Kleft:
				if(page > 0 && !doc->fwdonly) {
					--page;
					showpage(page, &menu);
				}
				break;
			case '\n':
				if(nxt) {
					nxt--;
					if(nxt >= 0 && nxt < doc->npage && !doc->fwdonly)
						showpage(page=nxt, &menu);
					nxt = 0;
					break;
				}
				goto Gotonext;
			case Kright:
			case ' ':
			Gotonext:
				if(doc->npage && ++page >= doc->npage && !doc->fwdonly)
					wexits(0);
				showpage(page, &menu);
				break;

			/*
			 * The upper y coordinate of the image is at ul.y in screen->r.
			 * Panning up means moving the upper left corner down.  If the
			 * upper left corner is currently visible, we need to go back a page.
			 */
			case Kup:
				if(screen->r.min.y <= ul.y && ul.y < screen->r.max.y){
					if(page > 0 && !doc->fwdonly){
						--page;
						showbottom = 1;
						showpage(page, &menu);
					}
				} else {
					i = Dy(screen->r)/2;
					if(i > 10)
						i -= 10;
					if(i+ul.y > screen->r.min.y)
						i = screen->r.min.y - ul.y;
					translate(Pt(0, i));
				}
				break;

			/*
			 * If the lower y coordinate is on the screen, we go to the next page.
			 * The lower y coordinate is at ul.y + Dy(im->r).
			 */
			case Kdown:
				i = ul.y + Dy(im->r);
				if(screen->r.min.y <= i && i <= screen->r.max.y){
					ul.y = screen->r.min.y;
					goto Gotonext;
				} else {
					i = -Dy(screen->r)/2;
					if(i < -10)
						i += 10;
					if(i+ul.y+Dy(im->r) <= screen->r.max.y)
						i = screen->r.max.y - Dy(im->r) - ul.y - 1;
					translate(Pt(0, i));
				}
				break;
			default:
				esetcursor(&query);
				sleep(1000);
				esetcursor(nil);
				break;
			}
			break;

		case Emouse:
			m = e.mouse;
			switch(m.buttons){
			case Left:
				oxy = m.xy;
				xy0 = oxy;
				do {
					dxy = subpt(m.xy, oxy);
					oxy = m.xy;
					translate(dxy);
					unlockdisplay(display);
					m = emouse();
					lockdisplay(display);
				} while(m.buttons == Left);
				if(m.buttons) {
					dxy = subpt(xy0, oxy);
					translate(dxy);
				}
				break;

			case Middle:
				if(doc->npage == 0)
					break;

				unlockdisplay(display);
				n = emenuhit(Middle, &m, &midmenu);
				lockdisplay(display);
				if(n == -1)
					break;
				switch(n){
				case Next: 	/* next */
					if(reverse)
						page--;
					else
						page++;
					if(page < 0) {
						if(reverse) return;
						else page = 0;
					}

					if((page >= doc->npage) && !doc->fwdonly)
						return;

					showpage(page, &menu);
					nxt = 0;
					break;
				case Prev:	/* prev */
					if(reverse)
						page++;
					else
						page--;
					if(page < 0) {
						if(reverse) return;
						else page = 0;
					}

					if((page >= doc->npage) && !doc->fwdonly && !reverse)
						return;

					showpage(page, &menu);
					nxt = 0;
					break;
				case Zerox:	/* prev */
					zerox();
					break;
				case Zin:	/* zoom in */
					{
						double delta;
						Rectangle r;

						r = egetrect(Middle, &m);
						if((rectclip(&r, rectaddpt(im->r, ul)) == 0) ||
							Dx(r) == 0 || Dy(r) == 0)
							break;
						/* use the smaller side to expand */
						if(Dx(r) < Dy(r))
							delta = (double)Dx(im->r)/(double)Dx(r);
						else
							delta = (double)Dy(im->r)/(double)Dy(r);

						esetcursor(&reading);
						tmp = xallocimage(display,
								Rect(0, 0, (int)((double)Dx(im->r)*delta), (int)((double)Dy(im->r)*delta)),
								im->chan, 0, DBlack);
						if(tmp == nil) {
							fprint(2, "out of memory during zoom: %r\n");
							wexits("memory");
						}
						resample(im, tmp);
						im = tmp;
						delayfreeimage(tmp);
						esetcursor(nil);
						ul = screen->r.min;
						redraw(screen);
						flushimage(display, 1);
						break;
					}
				case Fit:	/* fit */
					{
						double delta;
						Rectangle r;

						delta = (double)Dx(screen->r)/(double)Dx(im->r);
						if((double)Dy(im->r)*delta > Dy(screen->r))
							delta = (double)Dy(screen->r)/(double)Dy(im->r);

						r = Rect(0, 0, (int)((double)Dx(im->r)*delta), (int)((double)Dy(im->r)*delta));
						esetcursor(&reading);
						tmp = xallocimage(display, r, im->chan, 0, DBlack);
						if(tmp == nil) {
							fprint(2, "out of memory during fit: %r\n");
							wexits("memory");
						}
						resample(im, tmp);
						im = tmp;
						delayfreeimage(tmp);
						esetcursor(nil);
						ul = screen->r.min;
						redraw(screen);
						flushimage(display, 1);
						break;
					}
				case Rot:	/* rotate 90 */
					angle = (angle+90) % 360;
					showpage(page, &menu);
					break;
				case Upside: 	/* upside-down */
					angle = (angle+180) % 360;
					showpage(page, &menu);
					break;
				case Restore:	/* restore */
					showpage(page, &menu);
					break;
				case Reverse:	/* reverse */
					if(doc->fwdonly)
						break;
					reverse = !reverse;
					menu.lasthit = doc->npage-1-menu.lasthit;

					if(page == 0 || page == doc->npage-1) {
						page = doc->npage-1-page;
						showpage(page, &menu);
					}
					break;
				case Write: /* write */
					esetcursor(&reading);
					s = writebitmap();
					if(s)
						string(screen, addpt(screen->r.min, Pt(5,5)), display->black, ZP,
							display->defaultfont, s);
					esetcursor(nil);
					flushimage(display, 1);
					break;
				case Del: /* delete */
					if(doc->rmpage && page < doc->npage) {
						if(doc->rmpage(doc, page) >= 0) {
							if(doc->npage < 0)
								wexits(0);
							if(page >= doc->npage)
								page = doc->npage-1;
							showpage(page, &menu);
						}
					}
					break;
				case Exit:	/* exit */
					return;
				case Empty1:
				case Empty2:
				case Empty3:
					break;

				};



			case Right:
				if(doc->npage == 0)
					break;

				oldpage = page;
				unlockdisplay(display);
				n = emenuhit(RMenu, &m, &menu);
				lockdisplay(display);
				if(n == -1)
					break;

				if(doc->fwdonly) {
					switch(n){
					case 0:	/* this page */
						break;
					case 1:	/* next page */
						showpage(++page, &menu);
						break;
					case 2:	/* exit */
						return;
					}
					break;
				}

				if(n == doc->npage)
					return;
				else
					page = reverse ? doc->npage-1-n : n;

				if(oldpage != page)
					showpage(page, &menu);
				nxt = 0;
				break;
			}
			break;

		case Eplumb:
			pm = e.v;
			if(pm->ndata <= 0){
				plumbfree(pm);
				break;
			}
			if(plumbquit(pm))
				exits(nil);
			if(showdata(pm)) {
				s = estrdup("/tmp/pageplumbXXXXXXX");
				fd = opentemp(s);
				write(fd, pm->data, pm->ndata);
				/* lose fd reference on purpose; the file is open ORCLOSE */
			} else if(pm->data[0] == '/') {
				s = estrdup(pm->data);
			} else {
				s = emalloc(strlen(pm->wdir)+1+pm->ndata+1);
				sprint(s, "%s/%s", pm->wdir, pm->data);
				cleanname(s);
			}
			if((i = doc->addpage(doc, s)) >= 0) {
				page = i;
				unhide();
				showpage(page, &menu);
			}
			free(s);
			plumbfree(pm);
			break;
		}
	}
}
Пример #20
0
/*
 *  If changing this routine, look also at sleep().  It
 *  contains a copy of the guts of sched().
 */
void
sched(void)
{
	Proc *p;

	if(m->ilockdepth)
		panic("cpu%d: ilockdepth %d, last lock %#p at %#p, sched called from %#p",
			m->machno,
			m->ilockdepth,
			up != nil ? up->lastilock: nil,
			(up != nil && up->lastilock != nil) ? up->lastilock->pc: 0,
			getcallerpc(&p+2));
	if(up != nil) {
		/*
		 * Delay the sched until the process gives up the locks
		 * it is holding.  This avoids dumb lock loops.
		 * Don't delay if the process is Moribund.
		 * It called sched to die.
		 * But do sched eventually.  This avoids a missing unlock
		 * from hanging the entire kernel. 
		 * But don't reschedule procs holding palloc or procalloc.
		 * Those are far too important to be holding while asleep.
		 *
		 * This test is not exact.  There can still be a few instructions
		 * in the middle of taslock when a process holds a lock
		 * but Lock.p has not yet been initialized.
		 */
		if(up->nlocks)
		if(up->state != Moribund)
		if(up->delaysched < 20
		|| palloc.Lock.p == up
		|| procalloc.Lock.p == up){
			up->delaysched++;
 			delayedscheds++;
			return;
		}
		up->delaysched = 0;

		splhi();

		/* statistics */
		m->cs++;

		procsave(up);
		if(setlabel(&up->sched)){
			procrestore(up);
			spllo();
			return;
		}
		gotolabel(&m->sched);
	}
	p = runproc();
	if(p->edf == nil){
		updatecpu(p);
		p->priority = reprioritize(p);
	}
	if(p != m->readied)
		m->schedticks = m->ticks + HZ/10;
	m->readied = nil;
	up = p;
	up->state = Running;
	up->mach = MACHP(m->machno);
	m->proc = up;
	mmuswitch(up);
	gotolabel(&up->sched);
}
Пример #21
0
Файл: proc.c Проект: npe9/harvey
/*
 *  If changing this routine, look also at sleep().  It
 *  contains a copy of the guts of sched().
 */
void
sched(void)
{
	Mach *m = machp();
	Proc *p;

	if(m->ilockdepth)
		panic("cpu%d: ilockdepth %d, last lock %#p at %#p, sched called from %#p",
			m->machno,
			m->ilockdepth,
			m->externup? m->externup->lastilock: nil,
			(m->externup && m->externup->lastilock)? m->externup->lastilock->_pc: 0,
			getcallerpc(&p+2));

	kstackok();
	if(m->externup){
		/*
		 * Delay the sched until the process gives up the locks
		 * it is holding.  This avoids dumb lock loops.
		 * Don't delay if the process is Moribund.
		 * It called sched to die.
		 * But do sched eventually.  This avoids a missing unlock
		 * from hanging the entire kernel.
		 * But don't reschedule procs holding palloc or procalloc.
		 * Those are far too important to be holding while asleep.
		 *
		 * This test is not exact.  There can still be a few
		 * instructions in the middle of taslock when a process
		 * holds a lock but Lock.p has not yet been initialized.
		 */
		if(m->externup->nlocks)
		if(m->externup->state != Moribund)
		if(m->externup->delaysched < 20
		|| pga.Lock.p == m->externup
		|| procalloc.Lock.p == m->externup){
			m->externup->delaysched++;
 			run.delayedscheds++;
			return;
		}
		m->externup->delaysched = 0;

		splhi();
		/* statistics */
		if(m->externup->nqtrap == 0 && m->externup->nqsyscall == 0)
			m->externup->nfullq++;
		m->cs++;

		procsave(m->externup);
		mmuflushtlb(m->pml4->pa);
		if(setlabel(&m->externup->sched)){
			procrestore(m->externup);
			spllo();
			return;
		}
		/*debug*/gotolabel(&m->sched);
	}

	m->inidle = 1;
	p = runproc();	/* core 0 never returns */
	m->inidle = 0;

	if(!p->edf){
		updatecpu(p);
		p->priority = reprioritize(p);
	}
	if(nosmp){
		if(p != m->readied)
			m->schedticks = m->ticks + HZ/10;
	m->readied = 0;
	}
	m->externup = p;
	m->qstart = m->ticks;
	m->externup->nqtrap = 0;
	m->externup->nqsyscall = 0;
	m->externup->state = Running;
	//m->externup->mach = m;
	m->externup->mach = sys->machptr[m->machno];
	m->proc = m->externup;
//	iprint("m->externup->sched.sp %p * %p\n", up->sched.sp,
//		*(void **) m->externup->sched.sp);
	mmuswitch(m->externup);

	assert(!m->externup->wired || m->externup->wired == m);
	if (0) hi("gotolabel\n");
	/*debug*/gotolabel(&m->externup->sched);
}
Пример #22
0
Файл: proc.c Проект: npe9/harvey
/*
 *  sleep if a condition is not true.  Another process will
 *  awaken us after it sets the condition.  When we awaken
 *  the condition may no longer be true.
 *
 *  we lock both the process and the rendezvous to keep r->p
 *  and p->r synchronized.
 */
void
sleep(Rendez *r, int (*f)(void*), void *arg)
{
	Mach *m = machp();
	Mpl pl;

	pl = splhi();

	if(m->externup->nlocks)
		print("process %d sleeps with %d locks held, last lock %#p locked at pc %#p, sleep called from %#p\n",
			m->externup->pid, m->externup->nlocks, m->externup->lastlock, m->externup->lastlock->_pc, getcallerpc(&r));
	lock(r);
	lock(&m->externup->rlock);
	if(r->_p){
		print("double sleep called from %#p, %d %d\n",
			getcallerpc(&r), r->_p->pid, m->externup->pid);
		dumpstack();
	}

	/*
	 *  Wakeup only knows there may be something to do by testing
	 *  r->p in order to get something to lock on.
	 *  Flush that information out to memory in case the sleep is
	 *  committed.
	 */
	r->_p = m->externup;

	if((*f)(arg) || m->externup->notepending){
		/*
		 *  if condition happened or a note is pending
		 *  never mind
		 */
		r->_p = nil;
		unlock(&m->externup->rlock);
		unlock(r);
	} else {
		/*
		 *  now we are committed to
		 *  change state and call scheduler
		 */
		if(m->externup->trace)
			proctrace(m->externup, SSleep, 0);
		m->externup->state = Wakeme;
		m->externup->r = r;

		/* statistics */
		m->cs++;

		procsave(m->externup);
		mmuflushtlb(m->pml4->pa);
		if(setlabel(&m->externup->sched)) {
			/*
			 *  here when the process is awakened
			 */
			procrestore(m->externup);
			spllo();
		} else {
			/*
			 *  here to go to sleep (i.e. stop Running)
			 */
			unlock(&m->externup->rlock);
			unlock(r);
			/*debug*/gotolabel(&m->sched);
		}
	}

	if(m->externup->notepending) {
		m->externup->notepending = 0;
		splx(pl);
		if(m->externup->procctl == Proc_exitme && m->externup->closingfgrp)
			forceclosefgrp();
		error(Eintr);
	}

	splx(pl);
}
Пример #23
0
/* When a subroutine returns to address 0, the AMX must halt. In earlier
 * releases, the RET and RETN opcodes checked for the special case 0 address.
 * Today, the compiler simply generates a HALT instruction at address 0. So
 * a subroutine can savely return to 0, and then encounter a HALT.
 */
SC_FUNC void writeleader(symbol *root,int *lbl_nostate,int *lbl_ignorestate)
{
  symbol *sym;

  assert(code_idx==0);

  assert(lbl_nostate!=NULL);
  assert(lbl_ignorestate!=NULL);
  *lbl_nostate=0;
  *lbl_ignorestate=0;

  begcseg();
  pc_ovl0size[ovlEXIT][0]=code_idx;     /* store offset to the special overlay */
  stgwrite(";program exit point\n");
#if !defined AMX_NO_PACKED_OPC
  if (pc_optimize>sOPTIMIZE_NOMACRO) {
    stgwrite("\thalt.p 0\n\n");
    code_idx+=opcodes(1);
  } else {
#endif
    stgwrite("\thalt 0\n\n");
    code_idx+=opcodes(1)+opargs(1);     /* calculate code length */
#if !defined AMX_NO_PACKED_OPC
  } /* if */
#endif
  pc_ovl0size[ovlEXIT][1]=code_idx-pc_ovl0size[ovlEXIT][0]; /* store overlay code size */

  /* check whether there are any functions that have states */
  for (sym=root->next; sym!=NULL; sym=sym->next)
    if (sym->ident==iFUNCTN && (sym->usage & (uPUBLIC | uREAD))!=0 && sym->states!=NULL)
      break;
  if (sym==NULL)
    return;             /* no function has states, nothing to do next */

  /* generate an error function that is called for an undefined state */
  pc_ovl0size[ovlNO_STATE][0]=code_idx;
  stgwrite(";exit point for functions called from the wrong state\n");
  assert(lbl_nostate!=NULL);
  *lbl_nostate=getlabel();
  setlabel(*lbl_nostate);
#if !defined AMX_NO_PACKED_OPC
  if (pc_optimize>sOPTIMIZE_NOMACRO) {
    assert(AMX_ERR_INVSTATE<(1<<sizeof(cell)*4));
    stgwrite("\thalt.p ");
    outval(AMX_ERR_INVSTATE,TRUE,TRUE);
    code_idx+=opcodes(1);
  } else {
#endif
    stgwrite("\thalt ");
    outval(AMX_ERR_INVSTATE,TRUE,TRUE);
    code_idx+=opcodes(1)+opargs(1);     /* calculate code length */
#if !defined AMX_NO_PACKED_OPC
  } /* if */
#endif
  stgwrite("\n");
  pc_ovl0size[ovlNO_STATE][1]=code_idx-pc_ovl0size[ovlNO_STATE][0];

  /* check whether there are "exit state" functions */
  for (sym=root->next; sym!=NULL; sym=sym->next)
    if (strcmp(sym->name,uEXITFUNC)==0)
      break;
  if (sym!=NULL) {
    /* generate a stub function that is called for an undefined exit state and
     * that returns immediately to the caller (no error)
     */
    pc_ovl0size[ovlEXITSTATE][0]=code_idx;
    stgwrite(";catch-all for undefined exit states\n");
    assert(lbl_ignorestate!=NULL);
    *lbl_ignorestate=getlabel();
    setlabel(*lbl_ignorestate);
    /* the RET and IRETN instructions pop off the FRM register from the stack,
     * because they assume that a stack frame was set up; for this catch-all
     * routine (for exit states) we therefore need to set up a stack frame
     */
    stgwrite("\tproc\n");
    if (pc_overlays>0)
      stgwrite("\tiretn\n");
    else
      stgwrite("\tret\n");
    code_idx+=opcodes(2);
    pc_ovl0size[ovlEXITSTATE][1]=code_idx-pc_ovl0size[ovlEXITSTATE][0];
  } /* if */
}
Пример #24
0
Файл: sc4.c Проект: jte/pawn
/* When a subroutine returns to address 0, the AMX must halt. In earlier
 * releases, the RET and RETN opcodes checked for the special case 0 address.
 * Today, the compiler simply generates a HALT instruction at address 0. So
 * a subroutine can savely return to 0, and then encounter a HALT.
 */
SC_FUNC void writeleader(symbol *root)
{
  int lbl_nostate,lbl_table;
  int statecount;
  symbol *sym;
  constvalue *fsa, *state, *stlist;
  int fsa_id,listid;
  char lbl_default[sNAMEMAX+1];

  assert(code_idx==0);

  begcseg();
  stgwrite(";program exit point\n");
  stgwrite("\thalt 0\n\n");
  code_idx+=opcodes(1)+opargs(1);       /* calculate code length */

  /* check whether there are any functions that have states */
  for (sym=root->next; sym!=NULL; sym=sym->next)
    if (sym->ident==iFUNCTN && (sym->usage & (uPUBLIC | uREAD))!=0 && sym->states!=NULL)
      break;
  if (sym==NULL)
    return;             /* no function has states, nothing to do next */

  /* generate an error function that is called for an undefined state */
  stgwrite("\n;exit point for functions called from the wrong state\n");
  lbl_nostate=getlabel();
  setlabel(lbl_nostate);
  stgwrite("\thalt ");
  outval(AMX_ERR_INVSTATE,TRUE);
  code_idx+=opcodes(1)+opargs(1);       /* calculate code length */

  /* write the "state-selectors" table with all automatons (update the
   * automatons structure too, as we are now assigning the address to
   * each automaton state-selector variable)
   */
  assert(glb_declared==0);
  begdseg();
  for (fsa=sc_automaton_tab.next; fsa!=NULL; fsa=fsa->next) {
    defstorage();
    stgwrite("0\t; automaton ");
    if (strlen(fsa->name)==0)
      stgwrite("(anonymous)");
    else
      stgwrite(fsa->name);
    stgwrite("\n");
    fsa->value=glb_declared*sizeof(cell);
    glb_declared++;
  } /* for */

  /* write stubs and jump tables for all state functions */
  begcseg();
  for (sym=root->next; sym!=NULL; sym=sym->next) {
    if (sym->ident==iFUNCTN && (sym->usage & (uPUBLIC | uREAD))!=0 && sym->states!=NULL) {
      stlist=sym->states->next;
      assert(stlist!=NULL);     /* there should be at least one state item */
      listid=stlist->index;
      assert(listid==-1 || listid>0);
      if (listid==-1 && stlist->next!=NULL) {
        /* first index is the "fallback", take the next one (if available) */
        stlist=stlist->next;
        listid=stlist->index;
      } /* if */
      if (listid==-1) {
        /* first index is the fallback, there is no second... */
        strcpy(stlist->name,"0"); /* insert dummy label number */
        /* this is an error, but we postpone adding the error message until the
         * function definition
         */
        continue;
      } /* if */
      /* generate label numbers for all statelist ids */
      for (stlist=sym->states->next; stlist!=NULL; stlist=stlist->next) {
        assert(strlen(stlist->name)==0);
        strcpy(stlist->name,itoh(getlabel()));
      } /* for */
      if (strcmp(sym->name,uENTRYFUNC)==0)
        continue;               /* do not generate stubs for this special function */
      sym->addr=code_idx;       /* fix the function address now */
      /* get automaton id for this function */
      assert(listid>0);
      fsa_id=state_getfsa(listid);
      assert(fsa_id>=0);        /* automaton 0 exists */
      fsa=automaton_findid(fsa_id);
      /* count the number of states actually used; at the sane time, check
       * whether there is a default state function
       */
      statecount=0;
      strcpy(lbl_default,itoh(lbl_nostate));
      for (stlist=sym->states->next; stlist!=NULL; stlist=stlist->next) {
        if (stlist->index==-1) {
          assert(strlen(stlist->name)<sizeof lbl_default);
          strcpy(lbl_default,stlist->name);
        } else {
          statecount+=state_count(stlist->index);
        } /* if */
      } /* for */
      /* generate a stub entry for the functions */
      stgwrite("\tload.pri ");
      outval(fsa->value,FALSE);
      stgwrite("\t; ");
      stgwrite(sym->name);
      stgwrite("\n");
      code_idx+=opcodes(1)+opargs(1);   /* calculate code length */
      lbl_table=getlabel();
      ffswitch(lbl_table);
      /* generate the jump table */
      setlabel(lbl_table);
      ffcase(statecount,lbl_default,TRUE);
      for (state=sc_state_tab.next; state!=NULL; state=state->next) {
        if (state->index==fsa_id) {
          /* find the label for this list id */
          for (stlist=sym->states->next; stlist!=NULL; stlist=stlist->next) {
            if (stlist->index!=-1 && state_inlist(stlist->index,(int)state->value)) {
              ffcase(state->value,stlist->name,FALSE);
              break;
            } /* if */
          } /* for */
          if (stlist==NULL && strtol(lbl_default,NULL,16)==lbl_nostate)
            error(230,state->name,sym->name);  /* unimplemented state, no fallback */
        } /* if (state belongs to automaton of function) */
      } /* for (state) */
      stgwrite("\n");
    } /* if (is function, used & having states) */
  } /* for (sym) */
}
Пример #25
0
Файл: sc4.c Проект: Oukache/pawn
/* Address of the source must already have been loaded in PRI, the
 * destination address in ALT.
 * This routine makes a loop that copies the minor dimension vector
 * by vector.
 */
SC_FUNC void copyarray2d(int majordim,int minordim)
{
  int cellshift=(pc_cellsize==8) ? 3 : (pc_cellsize==4) ? 2 : 1;
  int looplbl=getlabel();

  stgwrite("\tpush.alt\n");
  stgwrite("\tpush.pri\n");
  code_idx+=opcodes(2);
  if (pc_optimize>=sOPTIMIZE_MACRO) {
    stgwrite("\tzero.alt\n");/* ALT = index = 0 */
    code_idx+=opcodes(1);
  } else {
    stgwrite("\tconst.alt 0\n");/* ALT = index = 0 */
    code_idx+=opcodes(1)+opargs(1);
  } /* if */
  setlabel(looplbl);
  stgwrite("\tpush.alt\n"); /* save index */
  stgwrite("\tpick 8\n");   /* PRI = dest */
  code_idx+=opcodes(2)+opargs(1);
  if (pc_optimize>=sOPTIMIZE_MACRO) {
    stgwrite("\txchg\n");   /* ALT = dest, PRI = index */
    stgwrite("\tidxaddr\n");/* PRI = dest + index * sizeof(cell) */
    code_idx+=opcodes(2);
  } else {
    stgwrite("\tshl.c.alt "); outval(cellshift,TRUE,TRUE); /* ALT = index * sizeof(cell) */
    stgwrite("\tadd\n");    /* PRI = dest + index * sizeof(cell) */
    code_idx+=opcodes(2)+opargs(1);
  } /* if */
  stgwrite("\tpush.pri\n");
  stgwrite("\tload.i\n");   /* PRI = dest[index * sizeof(cell)] */
  stgwrite("\tpop.alt\n");  /* ALT = dest + index * sizeof(cell) */
  stgwrite("\tadd\n");      /* PRI = dest + index * sizeof(cell) + dest[index * sizeof(cell)] */
  stgwrite("\tpush.pri\n");
  code_idx+=opcodes(5);
  if (pc_optimize>=sOPTIMIZE_MACRO) {
    stgwrite("\tpick 8\n"); /* PRI = source */
    stgwrite("\txchg\n");   /* ALT = source */
    stgwrite("\tpick 4\n"); /* PRI = index */
    stgwrite("\tidxaddr\n");/* PRI = source + index * sizeof(cell) */
    code_idx+=opcodes(4)+opargs(2);
  } else {
    stgwrite("\tpick 4\n"); /* PRI = index */
    stgwrite("\txchg\n");   /* ALT = index */
    stgwrite("\tshl.c.alt "); outval(cellshift,TRUE,TRUE); /* ALT = index * sizeof(cell) */
    stgwrite("\tpick 8\n"); /* PRI = source */
    stgwrite("\tadd\n");    /* PRI = source + index * sizeof(cell) */
    code_idx+=opcodes(5)+opargs(3);
  } /* if */
  stgwrite("\tpush.pri\n");
  stgwrite("\tload.i\n");   /* PRI = source[index * sizeof(cell)] */
  stgwrite("\tpop.alt\n");  /* ALT = source + index * sizeof(cell) */
  stgwrite("\tadd\n");      /* PRI = source + index * sizeof(cell) + source[index * sizeof(cell)] */
  stgwrite("\tpop.alt\n");  /* ALT = dest + index * sizeof(cell) + dest[index * sizeof(cell)] */
  stgwrite("\tmovs "); outval(minordim*pc_cellsize,TRUE,TRUE);
  stgwrite("\tpop.alt\n");  /* ALT = saved index */
  stgwrite("\tinc.alt\n");  /* ALT = index + 1 */
  code_idx+=opcodes(8)+opargs(1);
  if (pc_optimize>=sOPTIMIZE_MACRO) {
    stgwrite("\teq.c.alt "); outval(majordim,TRUE,TRUE);
    code_idx+=opcodes(1)+opargs(1);
  } else {
    stgwrite("\tconst.pri "); outval(majordim,TRUE,TRUE);
    stgwrite("\teq\n");     /* compare ALT with majordim */
    code_idx+=opcodes(2)+opargs(1);
  } /* if */
  stgwrite("\tjzer "); outval(looplbl,TRUE,TRUE);
  stgwrite("\tpop.pri\n");  /* restore stack & registers */
  stgwrite("\tpop.alt\n");
  code_idx+=opcodes(3)+opargs(1);
}
Пример #26
0
int
main(int argc, char **argv)
{
	int	sd, ch, changed;
	char	name[MAXPATHLEN];
	int	force;			/* force label update */
	int	raw;			/* update on-disk label as well */
	int	verbose;		/* verbose output */
	int	write_it;		/* update in-core label if changed */

	force = 0;
	raw = 0;
	verbose = 1;
	write_it = 0;
	while ((ch = getopt(argc, argv, "fqrw")) != -1) {
		switch (ch) {
		case 'f':
			force = 1;
			break;
		case 'q':
			verbose = 0;
			break;
		case 'r':
			raw = 1;
			break;
		case 'w':
			write_it = 1;
			break;
		default:
			usage();
		}
	}
	argc -= optind;
	argv += optind;
	if (argc != 1)
		usage();

	rawpart = getrawpartition();
	if (rawpart < 0)
		err(EXIT_FAILURE, "getrawpartition");

	if ((sd = opendisk(argv[0], write_it ? O_RDWR : O_RDONLY, name,
	    (size_t)MAXPATHLEN, 1)) < 0) {
		perror(argv[0]);
		exit(1);
	}
	getlabel(sd);
	changed = getparts(sd, verbose);

	if (verbose) {
		putchar('\n');
		showpartitions(stdout, &label, 0);
		putchar('\n');
	}
	if (write_it) {
		if (! changed && ! force)
			printf("No change; not updating disk label.\n");
		else {
			if (verbose)
				printf("Updating in-core %sdisk label.\n",
				    raw ? "and on-disk " : "");
raw = 0; /* XXX */
			setlabel(sd, raw);
		}
	} else {
		printf("Not updating disk label.\n");
	}
	close(sd);
	return (0);
}