httpd-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Rüdiger Plüm <ruediger.pl...@vodafone.com>
Subject Fwd: svn commit: r1204087 - in /httpd/httpd/trunk: include/ap_expr.h include/ap_mmn.h server/util_expr_eval.c server/util_expr_parse.c server/util_expr_parse.y
Date Mon, 21 Nov 2011 08:02:59 GMT


-------- Original-Nachricht --------
Betreff: 	svn commit: r1204087 - in /httpd/httpd/trunk: include/ap_expr.h include/ap_mmn.h
server/util_expr_eval.c 
server/util_expr_parse.c server/util_expr_parse.y
Datum: 	Sat, 19 Nov 2011 21:58:49 GMT
Von: 	sf@apache.org



Author: sf
Date: Sat Nov 19 21:58:48 2011
New Revision: 1204087

URL: http://svn.apache.org/viewvc?rev=1204087&view=rev
Log:
Limit recursion in ap_expr evaluation to avoid unbounded stack usage
* evaluate chains of ||,&&, and string concatenation non-recursively
* limit other types of recursion to 20 levels
* avoid some string copies if concatenating more than 2 strings

Modified:
     httpd/httpd/trunk/include/ap_expr.h
     httpd/httpd/trunk/include/ap_mmn.h
     httpd/httpd/trunk/server/util_expr_eval.c
     httpd/httpd/trunk/server/util_expr_parse.c
     httpd/httpd/trunk/server/util_expr_parse.y


Modified: httpd/httpd/trunk/server/util_expr_eval.c
URL: http://svn.apache.org/viewvc/httpd/httpd/trunk/server/util_expr_eval.c?rev=1204087&r1=1204086&r2=1204087&view=diff
==============================================================================
--- httpd/httpd/trunk/server/util_expr_eval.c (original)
+++ httpd/httpd/trunk/server/util_expr_eval.c Sat Nov 19 21:58:48 2011

@@ -657,30 +702,81 @@ static int ap_expr_eval(ap_expr_eval_ctx
  {
      const ap_expr_t *e1 = node->node_arg1;
      const ap_expr_t *e2 = node->node_arg2;
-    switch (node->node_op) {
-    case op_True:
-        return 1;
-    case op_False:
-        return 0;
-    case op_Not:
-        return (!ap_expr_eval(ctx, e1));
-    case op_Or:
-        return (ap_expr_eval(ctx, e1) || ap_expr_eval(ctx, e2));
-    case op_And:
-        return (ap_expr_eval(ctx, e1)&&  ap_expr_eval(ctx, e2));
-    case op_UnaryOpCall:
-        return ap_expr_eval_unary_op(ctx, e1, e2);
-    case op_BinaryOpCall:
-        return ap_expr_eval_binary_op(ctx, e1, e2);
-    case op_Comp:
-        if (ctx->info->flags&  AP_EXPR_FLAG_SSL_EXPR_COMPAT)
-            return ssl_expr_eval_comp(ctx, e1);
-        else
-            return ap_expr_eval_comp(ctx, e1);
-    default:
-        *ctx->err = "Internal evaluation error: Unknown expression node";
-        return FALSE;
+    int result = FALSE;
+    if (inc_rec(ctx))
+        return result;
+    while (1) {
+        switch (node->node_op) {
+        case op_True:
+            result ^= TRUE;

Why all these XOR operations and no simple assignments?

+            goto out;
+        case op_False:
+            ctx->reclvl--;

Why this? We already decrement below.

+            result ^= FALSE;
+            goto out;
+        case op_Not:
+            result = !result;
+            node = e1;
+            break;
+        case op_Or:
+            do {
+                if (e1->node_op == op_Not) {
+                    if (!ap_expr_eval(ctx, e1->node_arg1)) {
+                        result ^= TRUE;
+                        goto out;
+                    }
+                }
+                else {
+                    if (ap_expr_eval(ctx, e1)) {
+                        ctx->reclvl--;


Why this? We already decrement below.

+                        result ^= TRUE;
+                        goto out;
+                    }
+                }
+                node = node->node_arg2;
+                e1 = node->node_arg1;
+            } while (node->node_op == op_Or);
+            break;
+        case op_And:
+            do {
+                if (e1->node_op == op_Not) {
+                    if (ap_expr_eval(ctx, e1->node_arg1)) {
+                        result ^= FALSE;
+                        goto out;
+                    }
+                }
+                else {
+                    if (!ap_expr_eval(ctx, e1)) {
+                        result ^= FALSE;
+                        goto out;
+                    }
+                }
+                node = node->node_arg2;
+                e1 = node->node_arg1;
+            } while (node->node_op == op_And);
+            break;
+        case op_UnaryOpCall:
+            result ^= ap_expr_eval_unary_op(ctx, e1, e2);
+            goto out;
+        case op_BinaryOpCall:
+            result ^= ap_expr_eval_binary_op(ctx, e1, e2);
+            goto out;
+        case op_Comp:
+            if (ctx->info->flags&  AP_EXPR_FLAG_SSL_EXPR_COMPAT)
+                result ^= ssl_expr_eval_comp(ctx, e1);
+            else
+                result ^= ap_expr_eval_comp(ctx, e1);
+            goto out;
+        default:
+            *ctx->err = "Internal evaluation error: Unknown expression node";
+            goto out;
+        }
+        e1 = node->node_arg1;
+        e2 = node->node_arg2;
      }
+out:
+    ctx->reclvl--;
+    return result;
  }

  AP_DECLARE(int) ap_expr_exec(request_rec *r, const ap_expr_info_t *info,



Mime
View raw message