このページを編集する際は,編集に関する方針に従ってください.
概要
- Jabberd14-1.6.0/jabberd/config.cにて定義
- 他のファイルをインクルードするプリプロセッサ
* check the parsed configuration file for include instructions, process these instructions, and check again
引数
* @param nesting_lefel nesting level of includes, used to stop recursion if nesting_level is bigger than ::MAX_INCLUDE_NESTING * @param x the parsed configuration (modified by this function)
実装
static void do_include(int nesting_level,xmlnode x) { xmlnode cur;
- 関数は名前からなんとなく理解できるけど、定数はexpatを調べないとだめ。NTYPE_TAGってなによ?
よくみたらJabberd14-1.6.0/jabberd/lib/jabberdlib.hに定義されていた。xmlnode関連はxmlnode.cに定義されてる。expatを使っているのはxstream.c?みたいだ。構造体にXML_Parserが定義されているし。
cur=xmlnode_get_firstchild(x); for(;cur!=NULL;) {
- NTYPE_TAG(element tag)以外のタグは処理しない
if(cur->type!=NTYPE_TAG) { cur=xmlnode_get_nextsibling(cur); continue; }
- include ファイルを読み込んで置き換える処理を行う
if(j_strcmp(xmlnode_get_localname(cur),"include") == 0 && j_strcmp(xmlnode_get_namespace(cur), NS_JABBERD_CONFIGFILE_REPLACE) == 0) { xmlnode include; char *include_file=xmlnode_get_data(cur); xmlnode include_x=xmlnode_file(include_file); /* check for bad nesting */ if(nesting_level>MAX_INCLUDE_NESTING) { fprintf(stderr, "ERROR: Included files nested %d levels deep. Possible Recursion\n",nesting_level); exit(1); } include=cur; xmlnode_hide(include); /* check to see what to insert... * if root tag matches parent tag of the <include/> -- firstchild * otherwise, insert the whole file */ if ( j_strcmp(xmlnode_get_localname(xmlnode_get_parent(cur)), xmlnode_get_localname(include_x)) == 0 && j_strcmp(xmlnode_get_namespace(xmlnode_get_parent(cur)), xmlnode_get_namespace(include_x)) == 0 ) { xmlnode_insert_node(x,xmlnode_get_firstchild(include_x)); } else { if (j_strcmp(xmlnode_get_localname(xmlnode_get_parent(cur)), xmlnode_get_localname(include_x)) == 0) { xmlnode example_root_element = xmlnode_dup(xmlnode_get_parent(cur));
while (xmlnode_get_firstchild(example_root_element) != NULL) xmlnode_hide(xmlnode_get_firstchild(example_root_element));
fprintf(stderr, "WARNING (while including file '%s'):\n", include_file); fprintf(stderr, "Local name (%s) of the included file's root element matches the\n", xmlnode_get_localname(include_x)); fprintf(stderr, "parent element, but namespaces are different. This means the two elements\n"); fprintf(stderr, "are different and are handled as different elements. You might want this,\n"); fprintf(stderr, "and in that case you can just ignore this warning. But in most cases this\n"); fprintf(stderr, "is a configuration bug, and not what the writer of the configuration file\n"); fprintf(stderr, "intends. In that case you might want to update the root element of the\n"); fprintf(stderr, "included file to declare the right namespace.\n\n"); fprintf(stderr, "Currently the namespace of the parent element is '%s',\n", xmlnode_get_namespace(xmlnode_get_parent(cur))); fprintf(stderr, "and the namespace of the included root element is '%s'.\n\n", xmlnode_get_namespace(include_x)); fprintf(stderr, "What you probably want is the following root element in the included file:\n"); fprintf(stderr, "%s\n\n", xmlnode_serialize_string(example_root_element, NULL, NULL, 0));
xmlnode_free(example_root_element); } xmlnode_insert_node(x,include_x); } do_include(nesting_level+1,include_x); cur=xmlnode_get_nextsibling(cur); continue; }
- 子要素にincludeタグがないか再帰的にチェックする
else { do_include(nesting_level,cur); }
- 現在のタグの処理は完了したので次へ
cur=xmlnode_get_nextsibling(cur); } }
呼出元
#related: relatedプラグインは廃止されました。