示例#1
0
static TRI_aql_node_t* OptimiseConstantFilter (TRI_aql_node_t* const node) {
  if (TRI_GetBooleanNodeValueAql(node)) {
    // filter expression is always true => remove it
    LOG_TRACE("optimised away constant (true) filter");

    return TRI_GetDummyNopNodeAql();
  }

  // filter expression is always false => invalidate surrounding scope(s)
  LOG_TRACE("optimised away scope"); 

  return TRI_GetDummyReturnEmptyNodeAql();
}
示例#2
0
static TRI_aql_node_t* OptimiseFor (TRI_aql_statement_walker_t* const walker,
                                    TRI_aql_node_t* node) {
  TRI_aql_node_t* expression = TRI_AQL_NODE_MEMBER(node, 1);

  if (expression->_type == TRI_AQL_NODE_LIST) {
    // for statement with a list expression
    if (expression->_members._length == 0) {
      // list is empty => we can eliminate the for statement
      LOG_TRACE("optimised away empty for loop");

      return TRI_GetDummyReturnEmptyNodeAql();
    }
  }

  return node;
}
示例#3
0
size_t TRI_InvalidateStatementListAql (TRI_aql_statement_list_t* const list,
                                       const size_t position) {
  size_t i, n;
  size_t start;
  size_t scopes;
  size_t ignoreScopes;

  assert(list);
  assert(position >= 0);
  n = list->_statements._length;

  // walk the scope from the specified position backwards until we find the start of the scope
  scopes = 1;
  ignoreScopes = 0;
  i = position;
  while (true) {
    TRI_aql_node_t* node = StatementAt(list, i);
    TRI_aql_node_type_e type = node->_type;

    list->_statements._buffer[i] = TRI_GetDummyNopNodeAql();
    start = i;

    if (type == TRI_AQL_NODE_SCOPE_START) {
      // node is a scope start
      TRI_aql_scope_t* scope = (TRI_aql_scope_t*) TRI_AQL_NODE_DATA(node);

      if (ignoreScopes > 0) {
        // this is an inner, parallel scope that we can ignore
        --ignoreScopes;
      }
      else {
        if (scope->_type != TRI_AQL_SCOPE_FOR_NESTED) {
          // we have reached the scope and need to stop
          break;
        }
        scopes++;
      }
    }
    else if (type == TRI_AQL_NODE_SCOPE_END) {
      // we found the end of another scope
      // we must remember how many other scopes we passed
      ignoreScopes++;
    }

    if (i-- == 0) {
      break;
    }
  }

  assert(ignoreScopes == 0);

  // remove from position forwards to scope end
  i = position;
  while (true) {
    TRI_aql_node_t* node = StatementAt(list, i);
    TRI_aql_node_type_e type = node->_type;
    
    list->_statements._buffer[i] = TRI_GetDummyNopNodeAql();

    if (type == TRI_AQL_NODE_SCOPE_START) {
      ++scopes;
    }
    else if (type == TRI_AQL_NODE_SCOPE_END) {
      assert(scopes > 0);
      if (--scopes == 0) {
        break;
      }
    }

    if (++i == n) {
      break;
    }
  }
  
  list->_statements._buffer[start] = TRI_GetDummyReturnEmptyNodeAql();

  return start + 1;
}
示例#4
0
size_t TRI_InvalidateStatementListAql (TRI_aql_statement_list_t* const list,
                                       const size_t position) {
  size_t i, n;
  size_t start;
  size_t scopes;

  assert(list);
  assert(position >= 0);
  n = list->_statements._length;

  // remove from position backwards to scope start
  scopes = 1;
  i = position;
  while (true) {
    TRI_aql_node_t* node = StatementAt(list, i);
    TRI_aql_node_type_e type = node->_type;

    list->_statements._buffer[i] = TRI_GetDummyNopNodeAql();
    start = i;

    if (type == TRI_AQL_NODE_SCOPE_START) {
      TRI_aql_scope_t* scope = (TRI_aql_scope_t*) TRI_AQL_NODE_DATA(node);

      if (scope->_type != TRI_AQL_SCOPE_FOR_NESTED) {
        break;
      }
      scopes++;
    }

    if (i-- == 0) {
      break;
    }
  }

  // remove from position forwards to scope end
  i = position;
  while (true) {
    TRI_aql_node_t* node = StatementAt(list, i);
    TRI_aql_node_type_e type = node->_type;
    
    list->_statements._buffer[i] = TRI_GetDummyNopNodeAql();

    if (type == TRI_AQL_NODE_SCOPE_START) {
      ++scopes;
    }
    else if (type == TRI_AQL_NODE_SCOPE_END) {
      assert(scopes > 0);
      if (--scopes == 0) {
        break;
      }
    }

    if (++i == n) {
      break;
    }
  }
  
  list->_statements._buffer[start] = TRI_GetDummyReturnEmptyNodeAql();

  return start + 1;
}