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

📄 modcall.c

📁 使用最广泛的radius的linux的源码
💻 C
📖 第 1 页 / 共 4 页
字号:
			return csingle;		} else 	if (strcmp(modrefname, "elsif") == 0) {			if (parent &&			    ((parent->type == MOD_LOAD_BALANCE) ||			     (parent->type == MOD_REDUNDANT_LOAD_BALANCE))) {				cf_log_err(ci, "'elsif' cannot be used in this section section.");				return NULL;			}			if (!cf_section_name2(cs)) {				cf_log_err(ci, "'elsif' without condition.");				return NULL;			}			*modname = name2;			csingle= do_compile_modgroup(parent, component, cs,						     GROUPTYPE_SIMPLE,						     grouptype);			if (!csingle) return NULL;			csingle->type = MOD_ELSIF;			if (!radius_evaluate_condition(NULL, 0, 0, modname,						       FALSE, &result)) {				modcallable_free(&csingle);				return NULL;			}			*modname = name2;			return csingle;		} else 	if (strcmp(modrefname, "else") == 0) {			if (parent &&			    ((parent->type == MOD_LOAD_BALANCE) ||			     (parent->type == MOD_REDUNDANT_LOAD_BALANCE))) {				cf_log_err(ci, "'else' cannot be used in this section section.");				return NULL;			}			if (cf_section_name2(cs)) {				cf_log_err(ci, "Cannot have conditions on 'else'.");				return NULL;			}			*modname = name2;			csingle= do_compile_modgroup(parent, component, cs,						     GROUPTYPE_SIMPLE,						     grouptype);			if (!csingle) return NULL;			csingle->type = MOD_ELSE;			return csingle;		} else 	if (strcmp(modrefname, "update") == 0) {			*modname = name2;			csingle = do_compile_modupdate(parent, component, cs,						       name2);			if (!csingle) return NULL;			return csingle;		} else 	if (strcmp(modrefname, "switch") == 0) {			*modname = name2;			csingle = do_compile_modswitch(parent, component, cs);			if (!csingle) return NULL;			return csingle;		} else 	if (strcmp(modrefname, "case") == 0) {			int i;			*modname = name2;			/*			 *	FIXME: How to tell that the parent can only			 *	be a "switch" statement?			 */			if (!parent) {				cf_log_err(ci, "\"case\" statements may only appear within a \"switch\" section");				return NULL;			}			csingle= do_compile_modgroup(parent, component, cs,						     GROUPTYPE_SIMPLE,						     grouptype);			if (!csingle) return NULL;			csingle->type = MOD_CASE;			csingle->name = cf_section_name2(cs); /* may be NULL */			/*			 *	Set all of it's codes to return, so that			 *	when we pick a 'case' statement, we don't			 *	fall through to processing the next one.			 */			for (i = 0; i < RLM_MODULE_NUMCODES; i++) {				csingle->actions[i] = MOD_ACTION_RETURN;			}			return csingle;		} /* else it's something like sql { fail = 1 ...} */	} else if (!cf_item_is_pair(ci)) { /* CONF_DATA or some such */		return NULL;		/*		 *	Else it's a module reference, with updated return		 *	codes.		 */	} else {		CONF_PAIR *cp = cf_itemtopair(ci);		modrefname = cf_pair_attr(cp);		/*		 *	Actions (ok = 1), etc. are orthoganal to just		 *	about everything else.		 */		if (cf_pair_value(cp) != NULL) {			cf_log_err(ci, "Entry is not a reference to a module");			return NULL;		}		/*		 *	See if the module is a virtual one.  If so,		 *	return that, rather than doing anything here.		 */		subcs = NULL;		cs = cf_section_find("instantiate");		if (!subcs) {			cs = cf_section_find("policy");			if (cs) subcs = cf_section_sub_find_name2(cs, NULL,								  modrefname);		}		if (subcs) {			DEBUG2(" Module: Loading virtual module %s",			       modrefname);			/*			 *	redundant foo {} is a single.			 */			if (cf_section_name2(subcs)) {				return do_compile_modsingle(parent,							    component,							    cf_sectiontoitem(subcs),							    grouptype,							    modname);			} else {				/*				 *	foo {} is a group.				 */				return do_compile_modgroup(parent,							   component,							   subcs,							   GROUPTYPE_SIMPLE,							   grouptype);			}		}	}	/*	 *	Not a virtual module.  It must be a real module.	 */	modules = cf_section_find("modules");	this = NULL;	if (modules && cf_section_sub_find_name2(modules, NULL, modrefname)) {		this = find_module_instance(modules, modrefname);	}	if (!this) do {		int i;		char *p;	  		/*		 *	Maybe it's module.method		 */		p = strrchr(modrefname, '.');		if (p) for (i = RLM_COMPONENT_AUTH;			    i < RLM_COMPONENT_COUNT;			    i++) {			if (strcmp(p + 1, comp2str[i]) == 0) {				char buffer[256];				strlcpy(buffer, modrefname, sizeof(buffer));				buffer[p - modrefname] = '\0';				component = i;								this = find_module_instance(cf_section_find("modules"), buffer);				if (this &&				    !this->entry->module->methods[i]) {					*modname = NULL;					cf_log_err(ci, "Module %s has no such method %s", buffer, comp2str[i]);					return NULL;				}				break;			}		}		if (this) break;		if (strncmp(modrefname, "server[", 7) == 0) {			char buffer[256];			strlcpy(buffer, modrefname + 7, sizeof(buffer));			p = strrchr(buffer, ']');			if (!p || p[1] != '\0' || (p == buffer)) {				cf_log_err(ci, "Invalid server reference in \"%s\".", modrefname);				return NULL;			}			*p = '\0';			cs = cf_section_sub_find_name2(NULL, "server", buffer);			if (!cs) {				cf_log_err(ci, "No such server \"%s\".", buffer);				return NULL;			}						return do_compile_modserver(parent, component, ci,						    modrefname, cs, buffer);		}				*modname = NULL;		cf_log_err(ci, "Failed to find module \"%s\".", modrefname);		return NULL;	} while (0);	/*	 *	We know it's all OK, allocate the structures, and fill	 *	them in.	 */	single = rad_malloc(sizeof(*single));	memset(single, 0, sizeof(*single));	csingle = mod_singletocallable(single);	csingle->parent = parent;	csingle->next = NULL;	if (!parent || (component != RLM_COMPONENT_AUTH)) {		memcpy(csingle->actions, defaultactions[component][grouptype],		       sizeof csingle->actions);	} else { /* inside Auth-Type has different rules */		memcpy(csingle->actions, defaultactions[RLM_COMPONENT_AUTZ][grouptype],		       sizeof csingle->actions);	}	rad_assert(modrefname != NULL);	csingle->name = modrefname;	csingle->type = MOD_SINGLE;	csingle->method = component;	/*	 *	Singles can override the actions, virtual modules cannot.	 *	 *	FIXME: We may want to re-visit how to do this...	 *	maybe a csingle as a ref?	 */	if (cf_item_is_section(ci)) {		cs = cf_itemtosection(ci);		for (ci=cf_item_find_next(cs, NULL);		     ci != NULL;		     ci=cf_item_find_next(cs, ci)) {			if (cf_item_is_section(ci)) {				cf_log_err(ci, "Subsection of module instance call not allowed");				modcallable_free(&csingle);				return NULL;			}			if (!cf_item_is_pair(ci)) continue;			if (!compile_action(csingle, cf_itemtopair(ci))) {				modcallable_free(&csingle);				return NULL;			}		}	}	/*	 *	Bail out if the module in question does not supply the	 *	wanted component	 */	if (!this->entry->module->methods[component]) {		cf_log_err(ci, "\"%s\" modules aren't allowed in '%s' sections -- they have no such method.", this->entry->module->name,		       comp2str[component]);		modcallable_free(&csingle);		return NULL;	}	single->modinst = this;	*modname = this->entry->module->name;	return csingle;}modcallable *compile_modsingle(modcallable *parent,			       int component, CONF_ITEM *ci,			       const char **modname){	modcallable *ret = do_compile_modsingle(parent, component, ci,						GROUPTYPE_SIMPLE,						modname);	dump_tree(component, ret);	return ret;}/* *	Internal compile group code. */static modcallable *do_compile_modgroup(modcallable *parent,					int component, CONF_SECTION *cs,					int grouptype, int parentgrouptype){	int i;	modgroup *g;	modcallable *c;	CONF_ITEM *ci;	g = rad_malloc(sizeof(*g));	memset(g, 0, sizeof(*g));	g->grouptype = grouptype;	c = mod_grouptocallable(g);	c->parent = parent;	c->type = MOD_GROUP;	c->next = NULL;	memset(c->actions, 0, sizeof(c->actions));	/*	 *	Remember the name for printing, etc.	 *	 *	FIXME: We may also want to put the names into a	 *	rbtree, so that groups can reference each other...	 */	c->name = cf_section_name2(cs);	if (!c->name) {		c->name = cf_section_name1(cs);		if (strcmp(c->name, "group") == 0) {			c->name = "";		} else {			c->type = MOD_POLICY;		}	}	g->children = NULL;	/*	 *	Loop over the children of this group.	 */	for (ci=cf_item_find_next(cs, NULL);	     ci != NULL;	     ci=cf_item_find_next(cs, ci)) {		/*		 *	Sections are references to other groups, or		 *	to modules with updated return codes.		 */		if (cf_item_is_section(ci)) {			const char *junk = NULL;			modcallable *single;			CONF_SECTION *subcs = cf_itemtosection(ci);			single = do_compile_modsingle(c, component, ci,						      grouptype, &junk);			if (!single) {				cf_log_err(ci, "Failed to parse \"%s\" subsection.",				       cf_section_name1(subcs));				modcallable_free(&c);				return NULL;			}			add_child(g, single);		} else if (!cf_item_is_pair(ci)) { /* CONF_DATA */			continue;		} else {			const char *attr, *value;			CONF_PAIR *cp = cf_itemtopair(ci);			attr = cf_pair_attr(cp);			value = cf_pair_value(cp);			/*			 *	A CONF_PAIR is either a module			 *	instance with no actions			 *	specified ...			 */			if (!value) {				modcallable *single;				const char *junk = NULL;				single = do_compile_modsingle(c,							      component,							      ci,							      grouptype,							      &junk);				if (!single) {					cf_log_err(ci,						   "Failed to parse \"%s\" entry.",						   attr);					modcallable_free(&c);					return NULL;				}				add_child(g, single);				/*				 *	Or a module instance with action.				 */			} else if (!compile_action(c, cp)) {				modcallable_free(&c);				return NULL;			} /* else it worked */		}	}	/*	 *	Set the default actions, if they haven't already been	 *	set.	 */	for (i = 0; i < RLM_MODULE_NUMCODES; i++) {		if (!c->actions[i]) {			if (!parent || (component != RLM_COMPONENT_AUTH)) {				c->actions[i] = defaultactions[component][parentgrouptype][i];			} else { /* inside Auth-Type has different rules */				c->actions[i] = defaultactions[RLM_COMPONENT_AUTZ][parentgrouptype][i];			}		}	}	/*	 *	FIXME: If there are no children, return NULL?	 */	return mod_grouptocallable(g);}modcallable *compile_modgroup(modcallable *parent,			      int component, CONF_SECTION *cs){	modcallable *ret = do_compile_modgroup(parent, component, cs,					       GROUPTYPE_SIMPLE,					       GROUPTYPE_SIMPLE);	dump_tree(component, ret);	return ret;}void add_to_modcallable(modcallable **parent, modcallable *this,			int component, const char *name){	modgroup *g;	rad_assert(this != NULL);	if (*parent == NULL) {		modcallable *c;		g = rad_malloc(sizeof *g);		memset(g, 0, sizeof(*g));		g->grouptype = GROUPTYPE_SIMPLE;		c = mod_grouptocallable(g);		c->next = NULL;		memcpy(c->actions,		       defaultactions[component][GROUPTYPE_SIMPLE],		       sizeof(c->actions));		rad_assert(name != NULL);		c->name = name;		c->type = MOD_GROUP;		c->method = component;		g->children = NULL;		*parent = mod_grouptocallable(g);	} else {		g = mod_callabletogroup(*parent);	}	add_child(g, this);}void modcallable_free(modcallable **pc){	modcallable *c, *loop, *next;	c = *pc;	if (c->type != MOD_SINGLE) {		modgroup *g = mod_callabletogroup(c);		for(loop = g->children;		    loop ;		    loop = next) {			next = loop->next;			modcallable_free(&loop);		}		pairfree(&g->vps);	}	free(c);	*pc = NULL;}

⌨️ 快捷键说明

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