protected override Expression VisitBinary(BinaryExpression b)
            {
                BinaryExpression   binaryExpression = b.Left as BinaryExpression;
                ConstantExpression constant         = b.Right as ConstantExpression;

                // Ignore VB coalesce operator.
                if (binaryExpression != null && b.NodeType == ExpressionType.Coalesce)
                {
                    // VB translates comparisons against nullable values to the following expression:
                    //     (comparison) ?? false // E.g. (nullableInt > 5) ?? false
                    // Because we don't support coalesce on the server, we will convert this expression to:
                    //     (comparison) // E.g. (nullableInt > 5)
                    if (constant != null && constant.Type == typeof(bool) && ((bool)constant.Value == false) &&
                        MethodCallConverter.IsComparison(b.Left))
                    {
                        return(Expression.MakeBinary(binaryExpression.NodeType, binaryExpression.Left, binaryExpression.Right));
                    }
                }

                MethodCallExpression mce = b.Left as MethodCallExpression;

                // Translate VB equality/inequality comparisons into normal string comparisons
                bool isVbCompareString =
                    mce != null && TypeIsVBOperatorsType(mce.Method.DeclaringType) &&
                    mce.Method.Name == "CompareString" && mce.Arguments.Count == 3;

                if (isVbCompareString && constant != null && constant.Type == typeof(int) && (int)constant.Value == 0)
                {
                    Expression         left             = mce.Arguments[0];
                    Expression         right            = mce.Arguments[1];
                    bool               caseSensitive    = true;
                    ConstantExpression textCompareParam = mce.Arguments[2] as ConstantExpression;
                    if (textCompareParam != null && textCompareParam.Type == typeof(bool) && (bool)textCompareParam.Value == true)
                    {
                        // the CompareString param is means ignore case, so we invert here
                        caseSensitive = false;
                    }

                    if ((b.NodeType == ExpressionType.Equal || b.NodeType == ExpressionType.NotEqual) && caseSensitive)
                    {
                        // Case sensitive equality/inequality comparisons translate to simple equality/inequality operators
                        // CompareString(expr1, expr2, false) == 0 translates to expr1 == expr2
                        // CompareString(expr1, expr2, false) != 0 translates to expr1 != expr2
                        return(Expression.MakeBinary(b.NodeType, left, right));
                    }
                    else
                    {
                        // for all other comparisons, we make an equivalent translation to string.Compare
                        return(Expression.MakeBinary(b.NodeType, MakeVBCompare(left, right, caseSensitive), Expression.Constant(0)));
                    }
                }

                return(base.VisitBinary(b));
            }
            protected override Expression VisitUnary(UnaryExpression u)
            {
                if (u.NodeType == ExpressionType.Convert)
                {
                    Expression operand = this.Visit(u.Operand);
                    if (u.Type == typeof(object))
                    {
                        // Remove the conversion.
                        return(operand);
                    }
                    else if (u.Type == typeof(bool) && (operand.NodeType == ExpressionType.Conditional || MethodCallConverter.IsComparison(operand)))
                    {
                        // We don't want to try and convert the conditional/comparison to a boolean because
                        // its type may no longer be an object/string (the supported types for Conversions.ToBoolean).
                        return(operand);
                    }
                }

                return(base.VisitUnary(u));
            }