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

📄 sql.c

📁 Exuberant Ctags is a multilanguage reimplementation of the much-underused ctags(1) program and is i
💻 C
📖 第 1 页 / 共 2 页
字号:
			const int initial = c;			int d = fileGetc ();			if (d == initial)			{				if (initial == '<')					token->type = TOKEN_BLOCK_LABEL_BEGIN;				else					token->type = TOKEN_BLOCK_LABEL_END;			}			else			{				fileUngetc (d);				token->type = TOKEN_UNDEFINED;			}			break;		}		case '/':		{			int d = fileGetc ();			if (d != '*')  /* is this the start of a comment? */				fileUngetc (d);			else			{				do				{					skipToCharacter ('*');					c = fileGetc ();					if (c == '/')						break;					else						fileUngetc (c);				} while (c != '\0');				goto getNextChar;			}			break;		}		default:			if (! isIdentChar1 (c))				token->type = TOKEN_UNDEFINED;			else			{				parseIdentifier (token->string, c);				token->lineNumber = getSourceLineNumber ();				token->filePosition = getInputFilePosition ();				token->keyword = analyzeToken (token->string);				if (isKeyword (token, KEYWORD_rem))				{					vStringClear (token->string);					skipToCharacter ('\n');					goto getNextChar;				}				else if (isKeyword (token, KEYWORD_NONE))					token->type = TOKEN_IDENTIFIER;				else					token->type = TOKEN_KEYWORD;			}			break;	}}/**   Scanning functions*/static void findToken (tokenInfo *const token, const tokenType type){	while (! isType (token, type))		readToken (token);}static void skipArgumentList (tokenInfo *const token){	if (isType (token, TOKEN_OPEN_PAREN))  /* arguments? */	{		findToken (token, TOKEN_CLOSE_PAREN);		readToken (token);	}}static void parseSubProgram (tokenInfo *const token){	tokenInfo *const name = newToken ();	const sqlKind kind = isKeyword (token, KEYWORD_function) ?			SQLTAG_FUNCTION : SQLTAG_PROCEDURE;	Assert (isKeyword (token, KEYWORD_function) ||			isKeyword (token, KEYWORD_procedure));	readToken (name);	readToken (token);	skipArgumentList (token);	if (isKeyword (token, KEYWORD_return))	{		do			readToken (token);  /* read return type */		while (!(isKeyword (token, KEYWORD_is) ||					isType (token, TOKEN_SEMICOLON)));	}	if (isKeyword (token, KEYWORD_is))	{		if (isType (name, TOKEN_IDENTIFIER))			makeSqlTag (name, kind);		readToken (token);		parseBlock (token, TRUE);	}	else if (isType (token, TOKEN_SEMICOLON))		makeSqlTag (name, SQLTAG_PROTOTYPE);	deleteToken (name);}static void parseRecord (tokenInfo *const token){	Assert (isType (token, TOKEN_OPEN_PAREN));	do	{		readToken (token);		if (isType (token, TOKEN_IDENTIFIER))			makeSqlTag (token, SQLTAG_FIELD);		while (!(isType (token, TOKEN_COMMA) ||				 isType (token, TOKEN_CLOSE_PAREN)))			readToken (token);	} while (! isType (token, TOKEN_CLOSE_PAREN));}static void parseType (tokenInfo *const token){	tokenInfo *const name = newToken ();	readToken (name);	if (isType (name, TOKEN_IDENTIFIER))	{		readToken (token);		if (isKeyword (token, KEYWORD_is))		{			readToken (token);			switch (token->keyword)			{				case KEYWORD_record:					makeSqlTag (name, SQLTAG_RECORD);					parseRecord (token);					break;				case KEYWORD_table:					makeSqlTag (name, SQLTAG_TABLE);					break;				case KEYWORD_ref:					readToken (token);					if (isKeyword (token, KEYWORD_cursor))						makeSqlTag (name, SQLTAG_CURSOR);					break;				default: break;			}		}	}	deleteToken (name);}static void parseSimple (tokenInfo *const token, const sqlKind kind){	readToken (token);	if (isType (token, TOKEN_IDENTIFIER))		makeSqlTag (token, kind);}static void parseDeclare (tokenInfo *const token, const boolean local){	if (isKeyword (token, KEYWORD_declare))		readToken (token);	while (! isKeyword (token, KEYWORD_begin) && ! isKeyword (token, KEYWORD_end))	{		switch (token->keyword)		{			case KEYWORD_cursor:    parseSimple (token, SQLTAG_CURSOR); break;			case KEYWORD_function:  parseSubProgram (token); break;			case KEYWORD_procedure: parseSubProgram (token); break;			case KEYWORD_subtype:   parseSimple (token, SQLTAG_SUBTYPE); break;			case KEYWORD_trigger:   parseSimple (token, SQLTAG_TRIGGER); break;			case KEYWORD_type:      parseType (token); break;			default:				if (isType (token, TOKEN_IDENTIFIER))				{					if (local)						makeSqlTag (token, SQLTAG_LOCAL_VARIABLE);					else						makeSqlTag (token, SQLTAG_VARIABLE);				}				break;		}		findToken (token, TOKEN_SEMICOLON);		readToken (token);	}}static void parseLabel (tokenInfo *const token){	Assert (isType (token, TOKEN_BLOCK_LABEL_BEGIN));	readToken (token);	if (isType (token, TOKEN_IDENTIFIER))	{		makeSqlTag (token, SQLTAG_BLOCK_LABEL);		readToken (token);  /* read end of label */	}}static void parseStatements (tokenInfo *const token){	do	{		if (isType (token, TOKEN_BLOCK_LABEL_BEGIN))			parseLabel (token);		else		{			switch (token->keyword)			{				case KEYWORD_if:				case KEYWORD_loop:					readToken (token);					parseStatements (token);					break;				case KEYWORD_declare:				case KEYWORD_begin:					parseBlock (token, TRUE);					break;				default:					readToken (token);					break;			}			findToken (token, TOKEN_SEMICOLON);		}		readToken (token);	} while (! isKeyword (token, KEYWORD_end));}static void parseBlock (tokenInfo *const token, const boolean local){	if (isType (token, TOKEN_BLOCK_LABEL_BEGIN))	{		parseLabel (token);		readToken (token);	}	if (! isKeyword (token, KEYWORD_begin))		parseDeclare (token, local);	if (isKeyword (token, KEYWORD_begin))	{		readToken (token);		while (! isKeyword (token, KEYWORD_end))			parseStatements (token);		findToken (token, TOKEN_SEMICOLON);	}}static void parsePackage (tokenInfo *const token){	tokenInfo *const name = newToken ();	readToken (name);	if (isKeyword (name, KEYWORD_body))		readToken (name);	readToken (token);	if (isKeyword (token, KEYWORD_is))	{		if (isType (name, TOKEN_IDENTIFIER))			makeSqlTag (name, SQLTAG_PACKAGE);		readToken (token);		parseBlock (token, FALSE);	}	findToken (token, TOKEN_SEMICOLON);	deleteToken (name);}static void parseTable (tokenInfo *const token){	tokenInfo *const name = newToken ();	readToken (name);	readToken (token);	if (isType (token, TOKEN_OPEN_PAREN))	{		if (isType (name, TOKEN_IDENTIFIER))		{			makeSqlTag (name, SQLTAG_TABLE);			parseRecord (token);		}	}	findToken (token, TOKEN_SEMICOLON);	deleteToken (name);}static void parseSqlFile (tokenInfo *const token){	do	{		readToken (token);		if (isType (token, TOKEN_BLOCK_LABEL_BEGIN))			parseLabel (token);		else switch (token->keyword)		{			case KEYWORD_begin:     parseBlock (token, FALSE); break;			case KEYWORD_cursor:    parseSimple (token, SQLTAG_CURSOR); break;			case KEYWORD_declare:   parseBlock (token, FALSE); break;			case KEYWORD_function:  parseSubProgram (token); break;			case KEYWORD_package:   parsePackage (token); break;			case KEYWORD_procedure: parseSubProgram (token); break;			case KEYWORD_subtype:   parseSimple (token, SQLTAG_SUBTYPE); break;			case KEYWORD_table:     parseTable (token); break;			case KEYWORD_trigger:   parseSimple (token, SQLTAG_TRIGGER); break;			case KEYWORD_type:      parseType (token); break;			default:                break;		}	} while (! isKeyword (token, KEYWORD_end));}static void initialize (const langType language){	Assert (sizeof (SqlKinds) / sizeof (SqlKinds [0]) == SQLTAG_COUNT);	Lang_sql = language;	buildSqlKeywordHash ();}static void findSqlTags (void){	tokenInfo *const token = newToken ();	exception_t exception = (exception_t) (setjmp (Exception));	while (exception == ExceptionNone)		parseSqlFile (token);	deleteToken (token);}extern parserDefinition* SqlParser (void){	static const char *const extensions [] = { "sql", NULL };	parserDefinition* def = parserNew ("SQL");	def->kinds      = SqlKinds;	def->kindCount  = KIND_COUNT (SqlKinds);	def->extensions = extensions;	def->parser     = findSqlTags;	def->initialize = initialize;	return def;}/* vi:set tabstop=4 shiftwidth=4: */

⌨️ 快捷键说明

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