⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ncpp.c

📁 window下的c编译器。
💻 C
📖 第 1 页 / 共 5 页
字号:
	/* saw a letter or _ */
	ID1, {C_XX}, ACT(NAME, S_NAME),
	ID1, {C_ALPH, C_NUM}, ID1,
	/* saw L (start of wide string?) */
	ST1, {C_XX}, ACT(NAME, S_NAME),
	ST1, {C_ALPH, C_NUM}, ID1,
	ST1, {'"'}, ST2,
	ST1, {'\''}, CC1,
	/* saw " beginning string */
	ST2, {C_XX}, ST2,
	ST2, {'"'}, ACT(STRING, S_SELF),
	ST2, {'\\'}, ST3,
	ST2, {'\n'}, S_STNL,
	ST2, {EOFC}, S_EOFSTR,
	/* saw \ in string */
	ST3, {C_XX}, ST2,
	ST3, {'\n'}, S_STNL,
	ST3, {EOFC}, S_EOFSTR,
	/* saw ' beginning character const */
	CC1, {C_XX}, CC1,
	CC1, {'\''}, ACT(CCON, S_SELF),
	CC1, {'\\'}, CC2,
	CC1, {'\n'}, S_STNL,
	CC1, {EOFC}, S_EOFSTR,
	/* saw \ in ccon */
	CC2, {C_XX}, CC1,
	CC2, {'\n'}, S_STNL,
	CC2, {EOFC}, S_EOFSTR,
	/* saw /, perhaps start of comment */
	COM1, {C_XX}, ACT(SLASH, S_SELFB),
	COM1, {'='}, ACT(ASSLASH, S_SELF),
	COM1, {'*'}, COM2,
	COM1, {'/'}, COM4,
	/* saw "/ *", start of comment */
	COM2, {C_XX}, COM2,
	COM2, {'\n'}, S_COMNL,
	COM2, {'*'}, COM3,
	COM2, {EOFC}, S_EOFCOM,
	/* saw the * possibly ending a comment */
	COM3, {C_XX}, COM2,
	COM3, {'\n'}, S_COMNL,
	COM3, {'*'}, COM3,
	COM3, {'/'}, S_COMMENT,
	/* // comment */
	COM4, {C_XX}, COM4,
	COM4, {'\n'}, S_NL,
	COM4, {EOFC}, S_EOFCOM,
	/* saw white space, eat it up */
	WS1, {C_XX}, S_WS,
	WS1, {' ', '\t', '\v'}, WS1,
	/* saw -, check --, -=, -> */
	MINUS1, {C_XX}, ACT(MINUS, S_SELFB),
	MINUS1, {'-'}, ACT(MMINUS, S_SELF),
	MINUS1, {'='}, ACT(ASMINUS, S_SELF),
	MINUS1, {'>'}, ACT(ARROW, S_SELF),
	/* saw +, check ++, += */
	PLUS1, {C_XX}, ACT(PLUS, S_SELFB),
	PLUS1, {'+'}, ACT(PPLUS, S_SELF),
	PLUS1, {'='}, ACT(ASPLUS, S_SELF),
	/* saw <, check <<, <<=, <= */
	LT1, {C_XX}, ACT(LT, S_SELFB),
	LT1, {'<'}, LT2,
	LT1, {'='}, ACT(LEQ, S_SELF),
	LT2, {C_XX}, ACT(LSH, S_SELFB),
	LT2, {'='}, ACT(ASLSH, S_SELF),
	/* saw >, check >>, >>=, >= */
	GT1, {C_XX}, ACT(GT, S_SELFB),
	GT1, {'>'}, GT2,
	GT1, {'='}, ACT(GEQ, S_SELF),
	GT2, {C_XX}, ACT(RSH, S_SELFB),
	GT2, {'='}, ACT(ASRSH, S_SELF),
	/* = */
	ASG1, {C_XX}, ACT(ASGN, S_SELFB),
	ASG1, {'='}, ACT(EQ, S_SELF),
	/* ! */
	NOT1, {C_XX}, ACT(NOT, S_SELFB),
	NOT1, {'='}, ACT(NEQ, S_SELF),
	/* & */
	AND1, {C_XX}, ACT(AND, S_SELFB),
	AND1, {'&'}, ACT(LAND, S_SELF),
	AND1, {'='}, ACT(ASAND, S_SELF),
	/* | */
	OR1, {C_XX}, ACT(OR, S_SELFB),
	OR1, {'|'}, ACT(LOR, S_SELF),
	OR1, {'='}, ACT(ASOR, S_SELF),
	/* # */
	SHARP1, {C_XX}, ACT(SHARP, S_SELFB),
	SHARP1, {'#'}, ACT(DSHARP, S_SELF),
	/* % */
	PCT1, {C_XX}, ACT(PCT, S_SELFB),
	PCT1, {'='}, ACT(ASPCT, S_SELF),
	/* * */
	STAR1, {C_XX}, ACT(STAR, S_SELFB),
	STAR1, {'='}, ACT(ASSTAR, S_SELF),
	/* ^ */
	CIRC1, {C_XX}, ACT(CIRC, S_SELFB),
	CIRC1, {'='}, ACT(ASCIRC, S_SELF),
	-1
};
/* first index is char, second is state */
/* increase #states to power of 2 to encourage use of shift */
static short bigfsm[256][MAXSTATE];
static void expandlex(void)
{
	/* const */ struct fsm *fp;
	int i, j, nstate;
	for (fp = fsm; fp->state >= 0; fp++) {
		for (i = 0; fp->ch[i]; i++) {
			nstate = fp->nextstate;
			if (nstate >= S_SELF)
				nstate = ~nstate;
			switch (fp->ch[i]) {
			case C_XX:         /* random characters */
				for (j = 0; j < 256; j++)
					bigfsm[j][fp->state] = (short) nstate;
				continue;
			case C_ALPH:
				for (j = 0; j <= 256; j++)
					if ('a' <= j && j <= 'z' || 'A' <= j && j <= 'Z'
							|| j == '_')
						bigfsm[j][fp->state] = (short) nstate;
				continue;
			case C_NUM:
				for (j = '0'; j <= '9'; j++)
					bigfsm[j][fp->state] = (short) nstate;
				continue;
			default:
				bigfsm[fp->ch[i]][fp->state] = (short) nstate;
			}
		}
	}
	/* install special cases for ? (trigraphs),  \ (splicing), runes, and
	EOB */
	for (i = 0; i < MAXSTATE; i++) {
		for (j = 0; j < 0xFF; j++)
			if (j == '?' || j == '\\') {
				if (bigfsm[j][i] > 0)
					bigfsm[j][i] = (short) ~bigfsm[j][i];
				bigfsm[j][i] &= ~QBSBIT;
			}
		bigfsm[EOB][i] = ~S_EOB;
		if (bigfsm[EOFC][i] >= 0)
			bigfsm[EOFC][i] = ~S_EOF;
	}
}
static void fixlex(void)
{
	/* do C++ comments? */
	if (Cplusplus == 0)
		bigfsm['/'][COM1] = bigfsm['x'][COM1];
}
/*
 * fill in a row of tokens from input, terminated by NL or END
 * First token is put at trp->lp.
 * Reset is non-zero when the input buffer can be "rewound."
 * The value is a flag indicating that possible macros have
 * been seen in the row.
 */
static int gettokens(Tokenrow * trp, int reset)
{
	register unsigned int c;
	int state, oldstate;
	register uchar *ip;
	register Token *tp, *maxp;
	int runelen;
	Source *s = cursource;
	int nmac = 0;
	tp = trp->lp;
	ip = s->inp;
	if (reset) {
		s->lineinc = 0;
		if (ip >= s->inl) {     /* nothing in buffer */
			s->inl = s->inb;
			fillbuf(s);
			ip = s->inp = s->inb;
		}
		else if (ip >= s->inb + (3 * INS / 4)) {
			memmove(s->inb, ip, 4 + s->inl - ip);
			s->inl = s->inb + (s->inl - ip);
			ip = s->inp = s->inb;
		}
	}
	maxp = &trp->bp[trp->max];
	runelen = 1;
	for (;;) {
continue2:
		if (tp >= maxp) {
			trp->lp = tp;
			tp = growtokenrow(trp);
			maxp = &trp->bp[trp->max];
		}
		tp->type = UNCLASS;
		tp->hideset = 0;
		tp->t = ip;
		tp->wslen = 0;
		tp->flag = 0;
		state = START;
		for (;;) {
			oldstate = state;
			c = *ip;
			if (c == EOB && ip[1] != EOB) {
				state = bigfsm['a'][state];
			}
			else
				state = bigfsm[c][state];
			if (state >= 0) {
				ip += runelen;
				runelen = 1;
				continue;
			}
			state = ~state;
	reswitch:
			switch (state & 0177) {
			case S_SELF:
				ip += runelen;
				runelen = 1;
			case S_SELFB:
				tp->type = (unsigned char) GETACT(state);
				tp->len = ip - tp->t;
				tp++;
				goto continue2;
			case S_NAME:       /* like S_SELFB but with nmac check */
				tp->type = NAME;
				tp->len = ip - tp->t;
				nmac |= quicklook(tp->t[0], tp->len > 1 ? tp->t[1] : 0);
				tp++;
				goto continue2;
			case S_WS:
				tp->wslen = ip - tp->t;
				tp->t = ip;
				state = START;
				continue;
			default:
				if ((state & QBSBIT) == 0) {
					ip += runelen;
					runelen = 1;
					continue;
				}
				state &= ~QBSBIT;
				s->inp = ip;
				if (c == '?') { /* check trigraph */
					if (trigraph(s)) {
						state = oldstate;
						continue;
					}
					goto reswitch;
				}
				if (c == '\\') {/* line-folding */
					if (foldline(s)) {
						s->lineinc++;
						state = oldstate;
						continue;
					}
					goto reswitch;
				}
				error(CPPWARNING, StrTab[141]); // <Lexical botch in cpp>
				ip += runelen;
				runelen = 1;
				continue;
			case S_EOB:
				s->inp = ip;
				fillbuf(cursource);
				state = oldstate;
				continue;
			case S_EOF:
				tp->type = END;
				tp->len = 0;
				s->inp = ip;
				if (tp != trp->bp && (tp - 1)->type != NL && cursource->fd != -1)
					error(CPPWARNING, StrTab[142]); // <No newline at end of file>
				trp->lp = tp + 1;
				return nmac;
			case S_STNL:
				error(CPPERROR, StrTab[143]);   // <Unterminated string or char const>
			case S_NL:
				tp->t = ip;
				tp->type = NL;
				tp->len = 1;
				tp->wslen = 0;
				s->lineinc++;
				s->inp = ip + 1;
				trp->lp = tp + 1;
				return nmac;
			case S_EOFSTR:
				error(CPPFATAL, StrTab[144]);   // <EOF in string or char constant>
				break;
			case S_COMNL:
				s->lineinc++;
				state = COM2;
				ip += runelen;
				runelen = 1;
				/* patch proposed by dave hanson an 3 June 1998 */
				if (ip >= s->inb+(7*INS/8)) { /* very long comment */
					memmove(tp->t,ip,4+s->inl-ip);
					s->inl -= ip-tp->t; 
					ip = tp->t+1;
				}
				continue;
			case S_EOFCOM:
				error(CPPWARNING, StrTab[145]); // <EOF inside comment>
				--ip;
			case S_COMMENT:
				++ip;
				tp->t = ip;
				tp->t[-1] = ' ';
				tp->wslen = 1;
				state = START;
				continue;
			}
			break;
		}
		ip += runelen;
		runelen = 1;
		tp->len = ip - tp->t;
		tp++;
	}
}
/* have seen ?; handle the trigraph it starts (if any) else 0 */
static int trigraph(Source * s)
{
	int c;
	while (s->inp + 2 >= s->inl && fillbuf(s) != EOF);
	if (s->inp[1] != '?')
		return 0;
	c = 0;
	switch (s->inp[2]) {
	case '=':
		c = '#';
		break;
	case '(':
		c = '[';
		break;
	case '/':
		c = '\\';
		break;
	case ')':
		c = ']';
		break;
	case '\'':
		c = '^';
		break;
	case '<':
		c = '{';
		break;
	case '!':
		c = '|';
		break;
	case '>':
		c = '}';
		break;
	case '-':
		c = '~';
		break;
	}
	if (c) {
		*s->inp = (unsigned char) c;
		memmove(s->inp + 1, s->inp + 3, s->inl - s->inp + 2);
		s->inl -= 2;
	}
	return c;
}
static int foldline(Source * s)
{
	while (s->inp + 1 >= s->inl && fillbuf(s) != EOF);
	if (s->inp[1] == '\n') {
		memmove(s->inp, s->inp + 2, s->inl - s->inp + 3);
		s->inl -= 2;
		return 1;
	}
	return 0;
}
static int fillbuf(Source * s)
{
	int n;
	if (s->fd < 0 || (n = DoRead(s->fd, (char *) s->inl, INS / 8)) <= 0)
		n = 0;
	s->inl += n;
	s->inl[0] = s->inl[1] = s->inl[2] = s->inl[3] = EOB;
	if (n == 0) {
		s->inl[0] = s->inl[1] = s->inl[2] = s->inl[3] = EOFC;
		return EOF;
	}
	return 0;
}
/*
 * Push down to new source of characters.
 * If fd>0 and str==NULL, then from a file `name';
 * if fd==-1 and str, then from the string.
 */
static Source *setsource(unsigned char *name, int fd, char *str)
{
	Source *s = new(Source);
	int len;
	s->line = 1;
	s->lineinc = 0;
	s->fd = fd;
	s->filename = name;
	s->next = cursource;
	s->ifdepth = 0;
	cursource = s;
	/* slop at right for EOB */
	if (str) {
		len = strlen(str);
		s->inb = domalloc(len + 4);
		s->inp = s->inb;
		strncpy((char *) s->inp, str, len);
	}
	else {
		s->inb = domalloc(INS + 4);
		s->inp = s->inb;
		len = 0;
	}
	s->inl = s->inp + len;
	s->inl[0] = s->inl[1] = EOB;
#ifndef LRC
	if (fd >= 0 && xrefFile) {
		fprintf(xrefFile, "f %s\n", name);
		AddToFileTable(name);
	}
#endif
	return s;
}
static void unsetsource(void)
{
	Source *s = cursource;
	if (s->fd >= 0) {
		DoClose(s->fd);
		dofree(s->inb);
		if (Mflag > 1) {
			fprintf(TraceIncludesFile,"closing %s\n",cursource->filename);
		}
	}
	cursource = s->next;
	dofree(s);
}
#define MAXMACROARGS 256
/*
 * do a macro definition.  tp points to the name being defined in the line
 */
static Nlist *dodefine(Tokenrow * trp)
{
	Token *tp;
	Nlist *np;
	Tokenrow *def, args,*pargs;
	Token tmpTokenRow[MAXMACROARGS];

	tp = trp->tp + 1;
	if (tp >= trp->lp || tp->type != NAME) {
		error(CPPERROR, StrTab[146]);   // <#defined token is not a name>
		return NULL;
	}
	np = InstallToken(tp);
	if (np->flag & ISUNCHANGE) {
		error(CPPWARNING, StrTab[147], tp); // <#defined token %t can't be redefined>
		return NULL;
	}
	/* collect arguments */
	tp += 1;
	pargs = NULL;
	if (tp < trp->lp && tp->type == LP && tp->wslen == 0) {
		/* macro with args */
		int narg = 0;
		tp += 1;
		memset(tmpTokenRow,0,sizeof(tmpTokenRow));
		args.bp = tmpTokenRow;
		args.max = MAXMACROARGS;
		args.tp = tmpTokenRow;
		args.lp = tmpTokenRow;
		pargs = &args;
		if (tp->type != RP) {
			int err = 0;
			for (;;) {
				Token *atp;
				if (tp->type != NAME) {
					err++;
					break;
				}
				if (narg >= args.max) {
					error(CPPFATAL,"Maximum number of macro arguments exceeded");
					exit(1);
				}
				for (atp = args.bp; atp < args.lp; atp++)
					if (atp->len == tp->len
							&& strncmp((char *) atp->t, (char *) tp->t, tp->len) == 0)
						error(CPPERROR, StrTab[148]);   // <Duplicate macro argument>
				*args.lp++ = *tp;
				narg++;
				tp += 1;
				if (tp->type == RP)
					break;
				if (tp->type != COMMA) {
					err++;
					break;
				}
				tp += 1;
			}
			if (err) {
				error(CPPERROR, StrTab[149]);   // <Syntax error in macro parameters>
				return NULL;
			}
		}
		tp += 1;
	}
	trp->tp = tp;
	if (((trp->lp) - 1)->type == NL)
		trp->lp -= 1;
	def = normtokenrow(trp);
	if (np->flag & ISDEFINED) {
		if (comparetokens(def, np->vp)
				|| (np->ap == NULL) != (pargs == NULL)
				|| np->ap && comparetokens(pargs, np->ap))
			error(CPPERROR, StrTab[150], trp->bp + 2);  // <Macro redefinition of %t>
	}
	if (pargs) {
		Tokenrow *tap;
		tap = normtokenrow(pargs);
		pargs = tap;
	}
	np->ap = pargs;
	np->vp = def;
	np->flag |= ISDEFINED;
	np->srcline = (unsigned short) cursource->line;
	np->filename = cursource->filename;
	return np;
}
/*
 * Definition received via -D or -U
 */
static Nlist *doadefine(Tokenrow * trp, int type)
{
	Nlist *np;
	static Token onetoken[1] = {{NUMBER, 0, 0, 0, 1, (uchar *) "1"}};
	static Tokenrow onetr = {onetoken, onetoken, onetoken + 1, 1};
	trp->tp = trp->bp;
	if (type == 'U') {
		if (trp->lp - trp->tp != 2 || trp->tp->type != NAME)
			goto syntax;
		if ((np = cpplookup(trp->tp)) == NULL)
			return NULL;
		np->flag &= ~ISDEFINED;
		return NULL;
	}
	if (trp->tp >= trp->lp || trp->tp->type != NAME)

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -