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

📄 parser.c

📁 bind 9.3结合mysql数据库
💻 C
📖 第 1 页 / 共 4 页
字号:
cfg_lookingat_netaddr(cfg_parser_t *pctx, unsigned int flags) {	isc_result_t result;	isc_netaddr_t na_dummy;	result = token_addr(pctx, flags, &na_dummy);	return (ISC_TF(result == ISC_R_SUCCESS));}isc_result_tcfg_parse_rawport(cfg_parser_t *pctx, unsigned int flags, in_port_t *port) {	isc_result_t result;	CHECK(cfg_gettoken(pctx, ISC_LEXOPT_NUMBER));	if ((flags & CFG_ADDR_WILDOK) != 0 &&	    pctx->token.type == isc_tokentype_string &&	    strcmp(TOKEN_STRING(pctx), "*") == 0) {		*port = 0;		return (ISC_R_SUCCESS);	}	if (pctx->token.type != isc_tokentype_number) {		cfg_parser_error(pctx, CFG_LOG_NEAR,			     "expected port number or '*'");		return (ISC_R_UNEXPECTEDTOKEN);	}	if (pctx->token.value.as_ulong >= 65536U) {		cfg_parser_error(pctx, CFG_LOG_NEAR,			     "port number out of range");		return (ISC_R_UNEXPECTEDTOKEN);	}	*port = (in_port_t)(pctx->token.value.as_ulong);	return (ISC_R_SUCCESS); cleanup:	return (result);}voidcfg_print_rawaddr(cfg_printer_t *pctx, isc_netaddr_t *na) {	isc_result_t result;	char text[128];	isc_buffer_t buf;	isc_buffer_init(&buf, text, sizeof(text));	result = isc_netaddr_totext(na, &buf);	RUNTIME_CHECK(result == ISC_R_SUCCESS);	cfg_print_chars(pctx, isc_buffer_base(&buf), isc_buffer_usedlength(&buf));}/* netaddr */static isc_result_tparse_netaddr(cfg_parser_t *pctx, const cfg_type_t *type, cfg_obj_t **ret) {	isc_result_t result;	cfg_obj_t *obj = NULL;	isc_netaddr_t netaddr;	UNUSED(type);	CHECK(cfg_create_obj(pctx, type, &obj));	CHECK(cfg_parse_rawaddr(pctx, CFG_ADDR_V4OK | CFG_ADDR_V6OK, &netaddr));	isc_sockaddr_fromnetaddr(&obj->value.sockaddr, &netaddr, 0);	*ret = obj;	return (ISC_R_SUCCESS); cleanup:	CLEANUP_OBJ(obj);	return (result);}cfg_type_t cfg_type_netaddr = {	"netaddr", parse_netaddr, cfg_print_sockaddr, cfg_doc_terminal,	&cfg_rep_sockaddr, NULL};/* netprefix */isc_result_tcfg_parse_netprefix(cfg_parser_t *pctx, const cfg_type_t *type,		    cfg_obj_t **ret){	cfg_obj_t *obj = NULL;	isc_result_t result;	isc_netaddr_t netaddr;	unsigned int addrlen, prefixlen;	UNUSED(type);	CHECK(cfg_parse_rawaddr(pctx, CFG_ADDR_V4OK | CFG_ADDR_V4PREFIXOK |				CFG_ADDR_V6OK, &netaddr));	switch (netaddr.family) {	case AF_INET:		addrlen = 32;		break;	case AF_INET6:		addrlen = 128;		break;	default:		addrlen = 0;		INSIST(0);		break;	}	CHECK(cfg_peektoken(pctx, 0));	if (pctx->token.type == isc_tokentype_special &&	    pctx->token.value.as_char == '/') {		CHECK(cfg_gettoken(pctx, 0)); /* read "/" */		CHECK(cfg_gettoken(pctx, ISC_LEXOPT_NUMBER));		if (pctx->token.type != isc_tokentype_number) {			cfg_parser_error(pctx, CFG_LOG_NEAR,				     "expected prefix length");			return (ISC_R_UNEXPECTEDTOKEN);		}		prefixlen = pctx->token.value.as_ulong;		if (prefixlen > addrlen) {			cfg_parser_error(pctx, CFG_LOG_NOPREP,				     "invalid prefix length");			return (ISC_R_RANGE);		}	} else {		prefixlen = addrlen;	}	CHECK(cfg_create_obj(pctx, &cfg_type_netprefix, &obj));	obj->value.netprefix.address = netaddr;	obj->value.netprefix.prefixlen = prefixlen;	*ret = obj;	return (ISC_R_SUCCESS); cleanup:	cfg_parser_error(pctx, CFG_LOG_NEAR, "expected network prefix");	return (result);}static voidprint_netprefix(cfg_printer_t *pctx, cfg_obj_t *obj) {	cfg_netprefix_t *p = &obj->value.netprefix;	cfg_print_rawaddr(pctx, &p->address);	cfg_print_chars(pctx, "/", 1);	cfg_print_rawuint(pctx, p->prefixlen);}isc_boolean_tcfg_obj_isnetprefix(cfg_obj_t *obj) {	REQUIRE(obj != NULL);	return (ISC_TF(obj->type->rep == &cfg_rep_netprefix));}voidcfg_obj_asnetprefix(cfg_obj_t *obj, isc_netaddr_t *netaddr,		    unsigned int *prefixlen) {	REQUIRE(obj != NULL && obj->type->rep == &cfg_rep_netprefix);	*netaddr = obj->value.netprefix.address;	*prefixlen = obj->value.netprefix.prefixlen;}cfg_type_t cfg_type_netprefix = {	"netprefix", cfg_parse_netprefix, print_netprefix, cfg_doc_terminal,	&cfg_rep_netprefix, NULL};static isc_result_tparse_sockaddrsub(cfg_parser_t *pctx, const cfg_type_t *type,		  int flags, cfg_obj_t **ret){	isc_result_t result;	isc_netaddr_t netaddr;	in_port_t port = 0;	cfg_obj_t *obj = NULL;	CHECK(cfg_create_obj(pctx, type, &obj));	CHECK(cfg_parse_rawaddr(pctx, flags, &netaddr));	CHECK(cfg_peektoken(pctx, 0));	if (pctx->token.type == isc_tokentype_string &&	    strcasecmp(TOKEN_STRING(pctx), "port") == 0) {		CHECK(cfg_gettoken(pctx, 0)); /* read "port" */		CHECK(cfg_parse_rawport(pctx, flags, &port));	}	isc_sockaddr_fromnetaddr(&obj->value.sockaddr, &netaddr, port);	*ret = obj;	return (ISC_R_SUCCESS); cleanup:	CLEANUP_OBJ(obj);	return (result);}static unsigned int sockaddr_flags = CFG_ADDR_V4OK | CFG_ADDR_V6OK;cfg_type_t cfg_type_sockaddr = {	"sockaddr", cfg_parse_sockaddr, cfg_print_sockaddr, cfg_doc_sockaddr,	&cfg_rep_sockaddr, &sockaddr_flags};isc_result_tcfg_parse_sockaddr(cfg_parser_t *pctx, const cfg_type_t *type, cfg_obj_t **ret) {	const unsigned int *flagp = type->of;	return (parse_sockaddrsub(pctx, &cfg_type_sockaddr, *flagp, ret));}voidcfg_print_sockaddr(cfg_printer_t *pctx, cfg_obj_t *obj) {	isc_netaddr_t netaddr;	in_port_t port;	char buf[ISC_NETADDR_FORMATSIZE];	isc_netaddr_fromsockaddr(&netaddr, &obj->value.sockaddr);	isc_netaddr_format(&netaddr, buf, sizeof(buf));	cfg_print_cstr(pctx, buf);	port = isc_sockaddr_getport(&obj->value.sockaddr);	if (port != 0) {		cfg_print_chars(pctx, " port ", 6);		cfg_print_rawuint(pctx, port);	}}voidcfg_doc_sockaddr(cfg_printer_t *pctx, const cfg_type_t *type) {	const unsigned int *flagp = type->of;	int n = 0;	cfg_print_chars(pctx, "( ", 2);	if (*flagp & CFG_ADDR_V4OK) {		if (n != 0)			cfg_print_chars(pctx, " | ", 3);		cfg_print_cstr(pctx, "<ipv4_address>");		n++;	}	if (*flagp & CFG_ADDR_V6OK) {		if (n != 0)			cfg_print_chars(pctx, " | ", 3);		cfg_print_cstr(pctx, "<ipv6_address>");		n++;				}	if (*flagp & CFG_ADDR_WILDOK) {		if (n != 0)			cfg_print_chars(pctx, " | ", 3);		cfg_print_chars(pctx, "*", 1);		n++;	}	cfg_print_chars(pctx, " ) ", 3);	if (*flagp & CFG_ADDR_WILDOK) {		cfg_print_cstr(pctx, "[ port ( <integer> | * ) ]");	} else {		cfg_print_cstr(pctx, "[ port <integer> ]");	}}isc_boolean_tcfg_obj_issockaddr(cfg_obj_t *obj) {	REQUIRE(obj != NULL);	return (ISC_TF(obj->type->rep == &cfg_rep_sockaddr));}isc_sockaddr_t *cfg_obj_assockaddr(cfg_obj_t *obj) {	REQUIRE(obj != NULL && obj->type->rep == &cfg_rep_sockaddr);	return (&obj->value.sockaddr);}isc_result_tcfg_gettoken(cfg_parser_t *pctx, int options) {	isc_result_t result;	if (pctx->seen_eof)		return (ISC_R_SUCCESS);	options |= (ISC_LEXOPT_EOF | ISC_LEXOPT_NOMORE); redo:	pctx->token.type = isc_tokentype_unknown;	result = isc_lex_gettoken(pctx->lexer, options, &pctx->token);	pctx->ungotten = ISC_FALSE;	pctx->line = isc_lex_getsourceline(pctx->lexer);	switch (result) {	case ISC_R_SUCCESS:		if (pctx->token.type == isc_tokentype_eof) {			result = isc_lex_close(pctx->lexer);			INSIST(result == ISC_R_NOMORE ||			       result == ISC_R_SUCCESS);			if (isc_lex_getsourcename(pctx->lexer) != NULL) {				/*				 * Closed an included file, not the main file.				 */				cfg_listelt_t *elt;				elt = ISC_LIST_TAIL(pctx->open_files->						    value.list);				INSIST(elt != NULL);				ISC_LIST_UNLINK(pctx->open_files->						value.list, elt, link);				ISC_LIST_APPEND(pctx->closed_files->						value.list, elt, link);				goto redo;			}			pctx->seen_eof = ISC_TRUE;		}		break;	case ISC_R_NOSPACE:		/* More understandable than "ran out of space". */		cfg_parser_error(pctx, CFG_LOG_NEAR, "token too big");		break;	case ISC_R_IOERROR:		cfg_parser_error(pctx, 0, "%s",				 isc_result_totext(result));		break;	default:		cfg_parser_error(pctx, CFG_LOG_NEAR, "%s",				 isc_result_totext(result));		break;	}	return (result);}voidcfg_ungettoken(cfg_parser_t *pctx) {	if (pctx->seen_eof)		return;	isc_lex_ungettoken(pctx->lexer, &pctx->token);	pctx->ungotten = ISC_TRUE;}isc_result_tcfg_peektoken(cfg_parser_t *pctx, int options) {	isc_result_t result;	CHECK(cfg_gettoken(pctx, options));	cfg_ungettoken(pctx); cleanup:	return (result);}/* * Get a string token, accepting both the quoted and the unquoted form. * Log an error if the next token is not a string. */static isc_result_tcfg_getstringtoken(cfg_parser_t *pctx) {	isc_result_t result;	result = cfg_gettoken(pctx, CFG_LEXOPT_QSTRING);	if (result != ISC_R_SUCCESS)		return (result);	if (pctx->token.type != isc_tokentype_string &&	    pctx->token.type != isc_tokentype_qstring) {		cfg_parser_error(pctx, CFG_LOG_NEAR, "expected string");		return (ISC_R_UNEXPECTEDTOKEN);	}	return (ISC_R_SUCCESS);}voidcfg_parser_error(cfg_parser_t *pctx, unsigned int flags, const char *fmt, ...) {	va_list args;	va_start(args, fmt);	parser_complain(pctx, ISC_FALSE, flags, fmt, args);	va_end(args);	pctx->errors++;}voidcfg_parser_warning(cfg_parser_t *pctx, unsigned int flags, const char *fmt, ...) {	va_list args;	va_start(args, fmt);	parser_complain(pctx, ISC_TRUE, flags, fmt, args);	va_end(args);	pctx->warnings++;}#define MAX_LOG_TOKEN 30 /* How much of a token to quote in log messages. */static char *current_file(cfg_parser_t *pctx) {	static char none[] = "none";	cfg_listelt_t *elt;	cfg_obj_t *fileobj;	if (pctx->open_files == NULL)		return (none);	elt = ISC_LIST_TAIL(pctx->open_files->value.list);	if (elt == NULL)	      return (none);	fileobj = elt->obj;	INSIST(fileobj->type == &cfg_type_qstring);	return (fileobj->value.string.base);}static voidparser_complain(cfg_parser_t *pctx, isc_boolean_t is_warning,		unsigned int flags, const char *format,		va_list args){	char tokenbuf[MAX_LOG_TOKEN + 10];	static char where[ISC_DIR_PATHMAX + 100];	static char message[2048];	int level = ISC_LOG_ERROR;	const char *prep = "";	size_t len;	if (is_warning)		level = ISC_LOG_WARNING;	snprintf(where, sizeof(where), "%s:%u: ",		 current_file(pctx), pctx->line);	len = vsnprintf(message, sizeof(message), format, args);	if (len >= sizeof(message))		FATAL_ERROR(__FILE__, __LINE__,			    "error message would overflow");	if ((flags & (CFG_LOG_NEAR|CFG_LOG_BEFORE|CFG_LOG_NOPREP)) != 0) {		isc_region_t r;		if (pctx->ungotten)			(void)cfg_gettoken(pctx, 0);		if (pctx->token.type == isc_tokentype_eof) {			snprintf(tokenbuf, sizeof(tokenbuf), "end of file");		} else if (pctx->token.type == isc_tokentype_unknown) {			flags = 0;			tokenbuf[0] = '\0';		} else {			isc_lex_getlasttokentext(pctx->lexer,						 &pctx->token, &r);			if (r.length > MAX_LOG_TOKEN)				snprintf(tokenbuf, sizeof(tokenbuf),					 "'%.*s...'", MAX_LOG_TOKEN, r.base);			else				snprintf(tokenbuf, sizeof(tokenbuf),					 "'%.*s'", (int)r.length, r.base);		}		/* Choose a preposition. */		if (flags & CFG_LOG_NEAR)			prep = " near ";		else if (flags & CFG_LOG_BEFORE)			prep = " before ";		else			prep = " ";	} else {		tokenbuf[0] = '\0';	}	isc_log_write(pctx->lctx, CAT, MOD, level,		      "%s%s%s%s", where, message, prep, tokenbuf);}voidcfg_obj_log(cfg_obj_t *obj, isc_log_t *lctx, int level, const char *fmt, ...) {	va_list ap;	char msgbuf[2048];	if (! isc_log_wouldlog(lctx, level))		return;	va_start(ap, fmt);	vsnprintf(msgbuf, sizeof(msgbuf), fmt, ap);	isc_log_write(lctx, CAT, MOD, level,		      "%s:%u: %s",		      obj->file == NULL ? "<unknown file>" : obj->file,		      obj->line, msgbuf);	va_end(ap);}const char *cfg_obj_file(cfg_obj_t *obj) {	return (obj->file);}unsigned intcfg_obj_line(cfg_obj_t *obj) {	return (obj->line);}isc_result_tcfg_create_obj(cfg_parser_t *pctx, const cfg_type_t *type, cfg_obj_t **ret) {	cfg_obj_t *obj;	obj = isc_mem_get(pctx->mctx, sizeof(cfg_obj_t));	if (obj == NULL)		return (ISC_R_NOMEMORY);	obj->type = type;	obj->file = current_file(pctx);	obj->line = pctx->line;	*ret = obj;	return (ISC_R_SUCCESS);}static voidmap_symtabitem_destroy(char *key, unsigned int type,		       isc_symvalue_t symval, void *userarg){	cfg_obj_t *obj = symval.as_pointer;	cfg_parser_t *pctx = (cfg_parser_t *)userarg;	UNUSED(key);	UNUSED(type);	cfg_obj_destroy(pctx, &obj);}static isc_result_tcreate_map(cfg_parser_t *pctx, const cfg_type_t *type, cfg_obj_t **ret) {	isc_result_t result;	isc_symtab_t *symtab = NULL;	cfg_obj_t *obj = NULL;	CHECK(cfg_create_obj(pctx, type, &obj));	CHECK(isc_symtab_create(pctx->mctx, 5, /* XXX */				map_symtabitem_destroy,				pctx, ISC_FALSE, &symtab));	obj->value.map.symtab = symtab;	obj->value.map.id = NULL;	*ret = obj;	return (ISC_R_SUCCESS); cleanup:	if (obj != NULL)		isc_mem_put(pctx->mctx, obj, sizeof(*obj));	return (result);}static voidfree_map(cfg_parser_t *pctx, cfg_obj_t *obj) {	CLEANUP_OBJ(obj->value.map.id);	isc_symtab_destroy(&obj->value.map.symtab);}isc_boolean_tcfg_obj_istype(cfg_obj_t *obj, const cfg_type_t *type) {	return (ISC_TF(obj->type == type));}/* * Destroy 'obj', a configuration object created in 'pctx'. */voidcfg_obj_destroy(cfg_parser_t *pctx, cfg_obj_t **objp) {	cfg_obj_t *obj = *objp;	obj->type->rep->free(pctx, obj);	isc_mem_put(pctx->mctx, obj, sizeof(cfg_obj_t));	*objp = NULL;}static voidfree_noop(cfg_parser_t *pctx, cfg_obj_t *obj) {	UNUSED(pctx);	UNUSED(obj);}voidcfg_doc_obj(cfg_printer_t *pctx, const cfg_type_t *type) {	type->doc(pctx, type);}voidcfg_doc_terminal(cfg_printer_t *pctx, const cfg_type_t *type) {	cfg_print_chars(pctx, "<", 1);	cfg_print_cstr(pctx, type->name);	cfg_print_chars(pctx, ">", 1);}voidcfg_print_grammar(const cfg_type_t *type,	void (*f)(void *closure, const char *text, int textlen),	void *closure){	cfg_printer_t pctx;	pctx.f = f;	pctx.closure = closure;	pctx.indent = 0;	cfg_doc_obj(&pctx, type);}

⌨️ 快捷键说明

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