Bug 59299 - mod_macro syntax clash
Summary: mod_macro syntax clash
Status: NEEDINFO
Alias: None
Product: Apache httpd-2
Classification: Unclassified
Component: mod_macro (show other bugs)
Version: 2.4.20
Hardware: PC All
: P2 normal (vote)
Target Milestone: ---
Assignee: Apache HTTPD Bugs Mailing List
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2016-04-11 13:56 UTC by Marc Stern
Modified: 2018-03-24 14:26 UTC (History)
0 users



Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Marc Stern 2016-04-11 13:56:10 UTC
${...} clashes with mod_define
%{...} clashes with mod_rewrite
We should have a different character that is not used by any module (like ~) for unescaped characters (and recommendations about $ and % should be removed)

Remark: enclosing the parameter name in braces is needed to concatenate a string with another one but it may be replaced, for instance, by $(param) or $[param]
Comment 1 Eric Covener 2016-04-12 14:23:10 UTC
Does the % syntax actually clash in any meaningful way?

AIUI the only reason $ clashes is because the core of the server looks to expand $ variables from the native environment / mod_define before directives even get to process the arguments.

But the % usage in a macro is expanded before mod_rewrite ever takes a look at the variables.

(99% of directives are like RewriteCond/RewriteRule. 1% are of a special type called "EXEC_ON_READ" which basically means some evaluation is done immediately -- those are the problematic ones because they run earlier then everything else).

For example this works:

<Macro rewriteme %rule %subst %condvar %condval>
RewriteEngine ON
RewriteCond %{%condvar} %condval
RewriteRule %rule %subst
</Macro>


<virtualhost *:80>
Use rewriteme .* /XXX HTTP_HOST .*
</virtualhost>

Should we just prefer % and then @ if you don't like looking at %{%... in expressions/mod_Rewrite and relegate to $ as a last resort?
Comment 2 Marc Stern 2016-04-14 11:46:41 UTC
Example of clash:
  <Macro rewriteme ... %{condvar} ...>
  RewriteCond %{condvar} %condval

You expect %{condvar} to be a macro parameter but it will maybe be replaced because we defined somewhere else "Define codvar ...".
Quite tricky to troubleshoot.

3 solutions:
 - modify mod_rewrite & mod_core (Define)
 - use other characters than %$ in mod_macro
 - use another character than {} as delimiter in macro parameters

The third solution works without any change (for people aware about it).
The second solution will avoid problems. If this is not done, documentation should at least speak about the problem and recommend solution 3.
Comment 3 Eric Covener 2016-04-24 16:56:42 UTC
lost track of this one...

(In reply to Marc Stern from comment #2)
> Example of clash:
>   <Macro rewriteme ... %{condvar} ...>
>   RewriteCond %{condvar} %condval
> 
> You expect %{condvar} to be a macro parameter but it will maybe be replaced
> because we defined somewhere else "Define codvar ...".
> Quite tricky to troubleshoot.

I'm confused, did you have a typo above?  The core only expands mod_define variable with ${...} which is not used.  How does %{condvar} get expanded incorrectly there?  It is not expanded like e.g. #define in the C preprocessor.

Do you have a more comprehensive example that fails?
Comment 4 Marc Stern 2016-04-25 06:37:16 UTC
(In reply to Eric Covener from comment #3)

Sorry, I wasn't clear at all.
If a user uses a RewriteCond keyword (like HTTPS), it will clash:
  <Macro rewriteme ... %{https} ...>
  RewriteCond %{https} %condval

In THIS case, we have a clash because %{https} is used by both mod_macro & mod_rewrite. Some keywords may come later and we can't expect all users to know all of them.