Browse code

core: added new preprocessor directive: substdef

- prototype
!!substdef '/regexp/replacement/flags'
- separator char '/' can be replaced with any other character to avoid
conflicts
- it adds a preprocessor substitution like '!!subst' and in addition
defines the regexp to replacement, like
!!define regexp replacement
- useful when you need to replace tokens present as ID and inside string
values

Daniel-Constantin Mierla authored on 30/05/2011 21:57:18
Showing 4 changed files
... ...
@@ -561,6 +561,7 @@ EAT_ABLE	[\ \t\b\r]
561 561
 
562 562
 /* pre-processing blocks */
563 563
 SUBST       subst
564
+SUBSTDEF    substdef
564 565
 
565 566
 %%
566 567
 
... ...
@@ -1230,6 +1231,7 @@ SUBST       subst
1230 1230
 							addstr(&s_buf, yytext, yyleng); }
1231 1231
 
1232 1232
 <INITIAL>{PREP_START}{SUBST}	{ count();  return SUBST;}
1233
+<INITIAL>{PREP_START}{SUBSTDEF}	{ count();  return SUBSTDEF;}
1233 1234
 
1234 1235
 <INITIAL,IFDEF_SKIP>{PREP_START}{IFDEF}{EAT_ABLE}+    { count();
1235 1236
 								if (pp_ifdef_type(1)) return 1;
... ...
@@ -1663,7 +1665,7 @@ int pp_define(int len, const char * text)
1663 1663
 	return 0;
1664 1664
 }
1665 1665
 
1666
-int  pp_define_set(int len, char *text)
1666
+int pp_define_set(int len, char *text)
1667 1667
 {
1668 1668
 	if(len<=0) {
1669 1669
 		LOG(L_DBG, "no define value - ignoring\n");
... ...
@@ -1700,7 +1702,7 @@ int  pp_define_set(int len, char *text)
1700 1700
 	return 0;
1701 1701
 }
1702 1702
 
1703
-static str  *pp_define_get(int len, const char * text)
1703
+static str *pp_define_get(int len, const char * text)
1704 1704
 {
1705 1705
 	str var = {(char *)text, len};
1706 1706
 	int i;
... ...
@@ -562,6 +562,7 @@ extern char *finame;
562 562
 
563 563
 /*pre-processor*/
564 564
 %token SUBST
565
+%token SUBSTDEF
565 566
 
566 567
 /* operators, C like precedence */
567 568
 %right EQUAL
... ...
@@ -1968,6 +1969,8 @@ event_route_stm: ROUTE_EVENT LBRACK EVENT_RT_NAME RBRACK LBRACE actions RBRACE {
1968 1968
 preprocess_stm:
1969 1969
 	SUBST STRING { if(pp_subst_add($2)<0) YYERROR; }
1970 1970
 	| SUBST error { yyerror("invalid subst preprocess statement"); }
1971
+	| SUBSTDEF STRING { if(pp_substdef_add($2)<0) YYERROR; }
1972
+	| SUBSTDEF error { yyerror("invalid substdef preprocess statement"); }
1971 1973
 	;
1972 1974
 
1973 1975
 /*exp:	rval_expr
... ...
@@ -62,7 +62,7 @@ int pp_subst_add(char *data)
62 62
 	se=subst_parser(&subst);
63 63
 	if (se==0)
64 64
 	{
65
-		LM_ERR("bad subst expression:: %s\n", data);
65
+		LM_ERR("bad subst expression: %s\n", data);
66 66
 		pkg_free(pr);
67 67
 		return -2;
68 68
 	}
... ...
@@ -76,9 +76,79 @@ int pp_subst_add(char *data)
76 76
 	}
77 77
 	pp_subst_rules_tail = pr;
78 78
 
79
+	LM_ERR("### added subst expression: %s\n", data);
80
+
79 81
 	return 0;
80 82
 }
81 83
 
84
+int pp_substdef_add(char *data)
85
+{
86
+	char c;
87
+	char *p;
88
+	str defname;
89
+	str defvalue;
90
+
91
+	if(pp_subst_add(data)<0) {
92
+		LM_ERR("subst rule cannot be added\n");
93
+		goto error;
94
+	}
95
+
96
+	p=data;
97
+	c=*p;
98
+	if (c=='\\') {
99
+		LM_ERR("invalid separator char [%c] in [%s]\n", c, data);
100
+		goto error;
101
+	}
102
+	p++;
103
+	/* find regexp */
104
+	defname.s=p;
105
+	for ( ; *p; p++) {
106
+		/* if unescaped sep. char */
107
+		if ((*p==c) && (*(p-1)!='\\'))
108
+			goto found_regexp;
109
+	}
110
+	LM_ERR("separator [%c] not found after regexp: [%s]\n", c, data);
111
+	goto error;
112
+
113
+found_regexp:
114
+	defname.len = p - defname.s;
115
+	if(defname.len==0) {
116
+		LM_ERR("define name too short\n");
117
+		goto error;
118
+	}
119
+
120
+	p++;
121
+	defvalue.s = p;
122
+	/* find replacement */
123
+	for ( ; *p; p++) {
124
+		/* if unescaped sep. char */
125
+		if ((*p==c) && (*(p-1)!='\\'))
126
+			goto found_repl;
127
+	}
128
+	LM_ERR("separator [%c] not found after replacement: [%s]\n", c, data);
129
+	goto error;
130
+
131
+found_repl:
132
+	defvalue.len = p - defvalue.s;
133
+
134
+	if(pp_define(defname.len, defname.s)<0) {
135
+		LM_ERR("cannot set define name\n");
136
+		goto error;
137
+	}
138
+	if(pp_define_set(defvalue.len, defvalue.s)<0) {
139
+		LM_ERR("cannot set define value\n");
140
+		goto error;
141
+	}
142
+
143
+	LM_DBG("### added substdef: [%.*s]=[%.*s]\n", defname.len, defname.s,
144
+			defvalue.len, defvalue.s);
145
+
146
+	return 0;
147
+
148
+error:
149
+	return 1;
150
+}
151
+
82 152
 int pp_subst_run(char **data)
83 153
 {
84 154
 	str* result;
... ...
@@ -23,10 +23,11 @@
23 23
 #define _PPCFG_H_
24 24
 
25 25
 int pp_subst_add(char *data);
26
+int pp_substdef_add(char *data);
26 27
 int pp_subst_run(char **data);
27 28
 
28
-int  pp_define(int len, const char * text);
29
-int  pp_define_set(int len, char * text);
29
+int  pp_define(int len, const char *text);
30
+int  pp_define_set(int len, char *text);
30 31
 
31 32
 #endif /*_PPCFG_H_*/
32 33