diff --git a/coverage/Cobertura.xml b/coverage/Cobertura.xml index 6edeec2e..8036661b 100644 --- a/coverage/Cobertura.xml +++ b/coverage/Cobertura.xml @@ -1,9 +1,9 @@ - + - + @@ -295,18 +295,18 @@ - - - - + + + + - - - - + + + + @@ -391,360 +391,372 @@ - + - + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - + - - + + - - + + - - - - - - - - - + + + + + + + + + - - + + - - + + - - - - - - - - - - - - + + + + + + + + + + + + - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + - + - + + - - + + + + + + + + + + - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + - - - - - - - - - + + + + + + + + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - + - - + + - - + + - - - - - - - - - + + + + + + + + + - - + + - - + + - - - - - - - - - - - - + + + + + + + + + + + + - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + - + - + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + @@ -881,7 +893,7 @@ - + @@ -915,7 +927,7 @@ - + @@ -1169,200 +1181,200 @@ - - - - - + + + + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - + + + + - - - - - - - - + + + + + + + + - - - + + + - - - - - - - - - - - + + + + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - + + + + + + - - - + + + - - - + + + - - - + + + - - - - - - - + + + + + + + - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + @@ -2197,7 +2209,7 @@ - + @@ -2352,7 +2364,7 @@ - + @@ -2427,7 +2439,7 @@ - + @@ -2491,19 +2503,21 @@ - - + + - - + + - - + + - + - + + + @@ -2922,19 +2936,21 @@ - - + + - - + + - - + + - + - + + + @@ -4490,8 +4506,8 @@ - - + + @@ -4512,11 +4528,11 @@ - - - - - + + + + + @@ -4528,8 +4544,8 @@ - - + + @@ -5277,8 +5293,8 @@ - - + + @@ -5287,11 +5303,11 @@ - - - - - + + + + + @@ -5303,8 +5319,8 @@ - - + + @@ -6012,428 +6028,422 @@ - - - - - + + + + + - - - - - + + + + + - - - - - - - - - - - - + + + + + + + + + + + + - - - - - - - - - + + + + + + + + + - - - + + + - - - - - - - - + + - - - + + - - - - + + + + + + + + + + + - - - - - + + + + + - - - - - + + + + + - - - + + + - - - - - + + + + + - - - + + + - - - + + + - - - + + + - - - + + + - - - - - - - - - - - - + + + + - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + - - - - - - - - + + + + + + + + - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - + + + + + + + + + - - - - - - + + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - + + + + + + + + + + + + + + + + + + + - - - - - - - - - + + + + + + + + + - - - - - - - - - - - - + + + + + + + + + + + + - - - - - - - - - - + + + + @@ -6442,433 +6452,433 @@ - - - + + + - + - + + + + + + + - - - + + + - - - + + + - - - - - + + + + + - - - + + + - - - + + + - - - + + + - - - - + + + + - - - - + + + + - - - + + + - - - + + + - - - - - - - - - - + + + + - - - - - - - - + + + + + - - - + + + - - - - - - - - - + + + + + + + + + + + - - - - - - - - - - - + + + + + + + + + + + + - - - + + - - - - + + + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - - - + + + + + + + + - - - - - - - - - - - - + + + + + + + + + + + + + + + - - - - + + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - + + + + + + + + + - - - - - - + + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + - - - - + + + + + @@ -6877,47 +6887,53 @@ - - - + + + - + - - - - - - - - - - + + + + + + + + + + - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/coverage/SQLite.Tests_AsyncTableQuery_1.html b/coverage/SQLite.Tests_AsyncTableQuery_1.html index 88ea9ca1..8dc3f0ff 100644 --- a/coverage/SQLite.Tests_AsyncTableQuery_1.html +++ b/coverage/SQLite.Tests_AsyncTableQuery_1.html @@ -815,7 +815,7 @@

< Summary

Tag: -164_8458774659 +165_8458827553 @@ -2534,7 +2534,7 @@

/home/runner/work/sqli - +

Methods/Properties

diff --git a/coverage/SQLite.Tests_AutoGeneratedProgram.html b/coverage/SQLite.Tests_AutoGeneratedProgram.html index c63e5fc6..20b4fbb7 100644 --- a/coverage/SQLite.Tests_AutoGeneratedProgram.html +++ b/coverage/SQLite.Tests_AutoGeneratedProgram.html @@ -815,7 +815,7 @@

< Summary

Tag: -164_8458774659 +165_8458827553
@@ -915,7 +915,7 @@

Generated by: ReportGenerator 5.2.4.0
03/27/2024 - 21:18:16
GitHub | reportgenerator.io

+

Methods/Properties

diff --git a/coverage/SQLite.Tests_CollationAttribute.html b/coverage/SQLite.Tests_CollationAttribute.html index 0be4fb8e..d8ce705e 100644 --- a/coverage/SQLite.Tests_CollationAttribute.html +++ b/coverage/SQLite.Tests_CollationAttribute.html @@ -815,7 +815,7 @@

< Summary

Tag: -164_8458774659 +165_8458827553
@@ -843,7 +843,7 @@

< Summary

Total lines: -4956 +4965 Line coverage: @@ -4193,7 +4193,7 @@

/home/runner/work/sqlite-ne  3283        else if (value is Boolean) {  3284          SQLite3.BindInt (stmt, index, (bool)value ? 1 : 0);  3285        }3286        else if (value is UInt32 || value is Int64) {3286        else if (value is UInt32 || value is Int64 || value is UInt64) {  3287          SQLite3.BindInt64 (stmt, index, Convert.ToInt64 (value));  3288        }  3289        else if (value is Single || value is Double || value is Decimal) { @@ -4327,1547 +4327,1556 @@

/home/runner/work/sqlite-ne  3417        else if (clrType == typeof (Int64)) {  3418          return SQLite3.ColumnInt64 (stmt, index);  3419        }3420        else if (clrType == typeof (UInt32)) {3421          return (uint)SQLite3.ColumnInt64 (stmt, index);3420        else if (clrType == typeof (UInt64)) {3421          return (ulong)SQLite3.ColumnInt64 (stmt, index);  3422        }3423        else if (clrType == typeof (decimal)) {3424          return (decimal)SQLite3.ColumnDouble (stmt, index);3423        else if (clrType == typeof (UInt32)) {3424          return (uint)SQLite3.ColumnInt64 (stmt, index);  3425        }3426        else if (clrType == typeof (Byte)) {3427          return (byte)SQLite3.ColumnInt (stmt, index);3426        else if (clrType == typeof (decimal)) {3427          return (decimal)SQLite3.ColumnDouble (stmt, index);  3428        }3429        else if (clrType == typeof (UInt16)) {3430          return (ushort)SQLite3.ColumnInt (stmt, index);3429        else if (clrType == typeof (Byte)) {3430          return (byte)SQLite3.ColumnInt (stmt, index);  3431        }3432        else if (clrType == typeof (Int16)) {3433          return (short)SQLite3.ColumnInt (stmt, index);3432        else if (clrType == typeof (UInt16)) {3433          return (ushort)SQLite3.ColumnInt (stmt, index);  3434        }3435        else if (clrType == typeof (sbyte)) {3436          return (sbyte)SQLite3.ColumnInt (stmt, index);3435        else if (clrType == typeof (Int16)) {3436          return (short)SQLite3.ColumnInt (stmt, index);  3437        }3438        else if (clrType == typeof (byte[])) {3439          return SQLite3.ColumnByteArray (stmt, index);3438        else if (clrType == typeof (sbyte)) {3439          return (sbyte)SQLite3.ColumnInt (stmt, index);  3440        }3441        else if (clrType == typeof (Guid)) {3442          var text = SQLite3.ColumnString (stmt, index);3443          return new Guid (text);3444        }3445        else if (clrType == typeof (Uri)) {3446          var text = SQLite3.ColumnString (stmt, index);3447          return new Uri (text);3448        }3449        else if (clrType == typeof (StringBuilder)) {3450          var text = SQLite3.ColumnString (stmt, index);3451          return new StringBuilder (text);3452        }3453        else if (clrType == typeof (UriBuilder)) {3454          var text = SQLite3.ColumnString (stmt, index);3455          return new UriBuilder (text);3456        }3457        else {3458          throw new NotSupportedException ("Don't know how to read " + clrType);3441        else if (clrType == typeof (byte[])) {3442          return SQLite3.ColumnByteArray (stmt, index);3443        }3444        else if (clrType == typeof (Guid)) {3445          var text = SQLite3.ColumnString (stmt, index);3446          return new Guid (text);3447        }3448        else if (clrType == typeof (Uri)) {3449          var text = SQLite3.ColumnString (stmt, index);3450          return new Uri (text);3451        }3452        else if (clrType == typeof (StringBuilder)) {3453          var text = SQLite3.ColumnString (stmt, index);3454          return new StringBuilder (text);3455        }3456        else if (clrType == typeof (UriBuilder)) {3457          var text = SQLite3.ColumnString (stmt, index);3458          return new UriBuilder (text);  3459        }3460      }3461    }3462  }34633464  internal class FastColumnSetter3465  {3466    /// <summary>3467    /// Creates a delegate that can be used to quickly set object members from query columns.3468    ///3469    /// Note that this frontloads the slow reflection-based type checking for columns to only happen once at the beginni3470    /// and then afterwards each row of the query can invoke the delegate returned by this function to get much better p3471    /// </summary>3472    /// <typeparam name="T">The type of the destination object that the query will read into</typeparam>3473    /// <param name="conn">The active connection.  Note that this is primarily needed in order to read preferences regar3474    /// <param name="column">The table mapping used to map the statement column to a member of the destination object ty3475    /// <returns>3476    /// A delegate for fast-setting of object members from statement columns.3477    ///3478    /// If no fast setter is available for the requested column (enums in particular cause headache), then this function3479    /// </returns>3480    internal static Action<object, Sqlite3Statement, int> GetFastSetter<T> (SQLiteConnection conn, TableMapping.Column c3481    {3482      Action<object, Sqlite3Statement, int> fastSetter = null;34833484      Type clrType = column.PropertyInfo.PropertyType;34853486      var clrTypeInfo = clrType.GetTypeInfo ();3487      if (clrTypeInfo.IsGenericType && clrTypeInfo.GetGenericTypeDefinition () == typeof (Nullable<>)) {3488        clrType = clrTypeInfo.GenericTypeArguments[0];3489        clrTypeInfo = clrType.GetTypeInfo ();3490      }34913492      if (clrType == typeof (String)) {3493        fastSetter = CreateTypedSetterDelegate<T, string> (column, (stmt, index) => {3494          return SQLite3.ColumnString (stmt, index);3495        });3496      }3497      else if (clrType == typeof (Int32)) {3498        fastSetter = CreateNullableTypedSetterDelegate<T, int> (column, (stmt, index)=>{3499          return SQLite3.ColumnInt (stmt, index);3500        });3501      }3502      else if (clrType == typeof (Boolean)) {3503        fastSetter = CreateNullableTypedSetterDelegate<T, bool> (column, (stmt, index) => {3504          return SQLite3.ColumnInt (stmt, index) == 1;3505        });3506      }3507      else if (clrType == typeof (double)) {3508        fastSetter = CreateNullableTypedSetterDelegate<T, double> (column, (stmt, index) => {3509          return SQLite3.ColumnDouble (stmt, index);3510        });3511      }3512      else if (clrType == typeof (float)) {3513        fastSetter = CreateNullableTypedSetterDelegate<T, float> (column, (stmt, index) => {3514          return (float) SQLite3.ColumnDouble (stmt, index);3515        });3516      }3517      else if (clrType == typeof (TimeSpan)) {3518        if (conn.StoreTimeSpanAsTicks) {3519          fastSetter = CreateNullableTypedSetterDelegate<T, TimeSpan> (column, (stmt, index) => {3520            return new TimeSpan (SQLite3.ColumnInt64 (stmt, index));3521          });3522        }3523        else {3524          fastSetter = CreateNullableTypedSetterDelegate<T, TimeSpan> (column, (stmt, index) => {3525            var text = SQLite3.ColumnString (stmt, index);3526            TimeSpan resultTime;3527            if (!TimeSpan.TryParseExact (text, "c", System.Globalization.CultureInfo.InvariantCulture, System.Globalizat3528              resultTime = TimeSpan.Parse (text);3529            }3530            return resultTime;3531          });3532        }3533      }3534      else if (clrType == typeof (DateTime)) {3535        if (conn.StoreDateTimeAsTicks) {3536          fastSetter = CreateNullableTypedSetterDelegate<T, DateTime> (column, (stmt, index) => {3537            return new DateTime (SQLite3.ColumnInt64 (stmt, index));3538          });3539        }3540        else {3541          fastSetter = CreateNullableTypedSetterDelegate<T, DateTime> (column, (stmt, index) => {3542            var text = SQLite3.ColumnString (stmt, index);3543            DateTime resultDate;3544            if (!DateTime.TryParseExact (text, conn.DateTimeStringFormat, System.Globalization.CultureInfo.InvariantCult3545              resultDate = DateTime.Parse (text);3546            }3547            return resultDate;3548          });3549        }3550      }3551      else if (clrType == typeof (DateTimeOffset)) {3552        fastSetter = CreateNullableTypedSetterDelegate<T, DateTimeOffset> (column, (stmt, index) => {3553          return new DateTimeOffset (SQLite3.ColumnInt64 (stmt, index), TimeSpan.Zero);3554        });3555      }3556      else if (clrTypeInfo.IsEnum) {3557        // NOTE: Not sure of a good way (if any?) to do a strongly-typed fast setter like this for enumerated types -- f3460        else {3461          throw new NotSupportedException ("Don't know how to read " + clrType);3462        }3463      }3464    }3465  }34663467  internal class FastColumnSetter3468  {3469    /// <summary>3470    /// Creates a delegate that can be used to quickly set object members from query columns.3471    ///3472    /// Note that this frontloads the slow reflection-based type checking for columns to only happen once at the beginni3473    /// and then afterwards each row of the query can invoke the delegate returned by this function to get much better p3474    /// </summary>3475    /// <typeparam name="T">The type of the destination object that the query will read into</typeparam>3476    /// <param name="conn">The active connection.  Note that this is primarily needed in order to read preferences regar3477    /// <param name="column">The table mapping used to map the statement column to a member of the destination object ty3478    /// <returns>3479    /// A delegate for fast-setting of object members from statement columns.3480    ///3481    /// If no fast setter is available for the requested column (enums in particular cause headache), then this function3482    /// </returns>3483    internal static Action<object, Sqlite3Statement, int> GetFastSetter<T> (SQLiteConnection conn, TableMapping.Column c3484    {3485      Action<object, Sqlite3Statement, int> fastSetter = null;34863487      Type clrType = column.PropertyInfo.PropertyType;34883489      var clrTypeInfo = clrType.GetTypeInfo ();3490      if (clrTypeInfo.IsGenericType && clrTypeInfo.GetGenericTypeDefinition () == typeof (Nullable<>)) {3491        clrType = clrTypeInfo.GenericTypeArguments[0];3492        clrTypeInfo = clrType.GetTypeInfo ();3493      }34943495      if (clrType == typeof (String)) {3496        fastSetter = CreateTypedSetterDelegate<T, string> (column, (stmt, index) => {3497          return SQLite3.ColumnString (stmt, index);3498        });3499      }3500      else if (clrType == typeof (Int32)) {3501        fastSetter = CreateNullableTypedSetterDelegate<T, int> (column, (stmt, index)=>{3502          return SQLite3.ColumnInt (stmt, index);3503        });3504      }3505      else if (clrType == typeof (Boolean)) {3506        fastSetter = CreateNullableTypedSetterDelegate<T, bool> (column, (stmt, index) => {3507          return SQLite3.ColumnInt (stmt, index) == 1;3508        });3509      }3510      else if (clrType == typeof (double)) {3511        fastSetter = CreateNullableTypedSetterDelegate<T, double> (column, (stmt, index) => {3512          return SQLite3.ColumnDouble (stmt, index);3513        });3514      }3515      else if (clrType == typeof (float)) {3516        fastSetter = CreateNullableTypedSetterDelegate<T, float> (column, (stmt, index) => {3517          return (float) SQLite3.ColumnDouble (stmt, index);3518        });3519      }3520      else if (clrType == typeof (TimeSpan)) {3521        if (conn.StoreTimeSpanAsTicks) {3522          fastSetter = CreateNullableTypedSetterDelegate<T, TimeSpan> (column, (stmt, index) => {3523            return new TimeSpan (SQLite3.ColumnInt64 (stmt, index));3524          });3525        }3526        else {3527          fastSetter = CreateNullableTypedSetterDelegate<T, TimeSpan> (column, (stmt, index) => {3528            var text = SQLite3.ColumnString (stmt, index);3529            TimeSpan resultTime;3530            if (!TimeSpan.TryParseExact (text, "c", System.Globalization.CultureInfo.InvariantCulture, System.Globalizat3531              resultTime = TimeSpan.Parse (text);3532            }3533            return resultTime;3534          });3535        }3536      }3537      else if (clrType == typeof (DateTime)) {3538        if (conn.StoreDateTimeAsTicks) {3539          fastSetter = CreateNullableTypedSetterDelegate<T, DateTime> (column, (stmt, index) => {3540            return new DateTime (SQLite3.ColumnInt64 (stmt, index));3541          });3542        }3543        else {3544          fastSetter = CreateNullableTypedSetterDelegate<T, DateTime> (column, (stmt, index) => {3545            var text = SQLite3.ColumnString (stmt, index);3546            DateTime resultDate;3547            if (!DateTime.TryParseExact (text, conn.DateTimeStringFormat, System.Globalization.CultureInfo.InvariantCult3548              resultDate = DateTime.Parse (text);3549            }3550            return resultDate;3551          });3552        }3553      }3554      else if (clrType == typeof (DateTimeOffset)) {3555        fastSetter = CreateNullableTypedSetterDelegate<T, DateTimeOffset> (column, (stmt, index) => {3556          return new DateTimeOffset (SQLite3.ColumnInt64 (stmt, index), TimeSpan.Zero);3557        });  3558      }3559      else if (clrType == typeof (Int64)) {3560        fastSetter = CreateNullableTypedSetterDelegate<T, Int64> (column, (stmt, index) => {3561          return SQLite3.ColumnInt64 (stmt, index);3562        });3563      }3564      else if (clrType == typeof (UInt32)) {3565        fastSetter = CreateNullableTypedSetterDelegate<T, UInt32> (column, (stmt, index) => {3566          return (uint)SQLite3.ColumnInt64 (stmt, index);3567        });3568      }3569      else if (clrType == typeof (decimal)) {3570        fastSetter = CreateNullableTypedSetterDelegate<T, decimal> (column, (stmt, index) => {3571          return (decimal)SQLite3.ColumnDouble (stmt, index);3572        });3573      }3574      else if (clrType == typeof (Byte)) {3575        fastSetter = CreateNullableTypedSetterDelegate<T, Byte> (column, (stmt, index) => {3576          return (byte)SQLite3.ColumnInt (stmt, index);3577        });3578      }3579      else if (clrType == typeof (UInt16)) {3580        fastSetter = CreateNullableTypedSetterDelegate<T, UInt16> (column, (stmt, index) => {3581          return (ushort)SQLite3.ColumnInt (stmt, index);3582        });3583      }3584      else if (clrType == typeof (Int16)) {3585        fastSetter = CreateNullableTypedSetterDelegate<T, Int16> (column, (stmt, index) => {3586          return (short)SQLite3.ColumnInt (stmt, index);3587        });3588      }3589      else if (clrType == typeof (sbyte)) {3590        fastSetter = CreateNullableTypedSetterDelegate<T, sbyte> (column, (stmt, index) => {3591          return (sbyte)SQLite3.ColumnInt (stmt, index);3592        });3593      }3594      else if (clrType == typeof (byte[])) {3595        fastSetter = CreateTypedSetterDelegate<T, byte[]> (column, (stmt, index) => {3596          return SQLite3.ColumnByteArray (stmt, index);3597        });3598      }3599      else if (clrType == typeof (Guid)) {3600        fastSetter = CreateNullableTypedSetterDelegate<T, Guid> (column, (stmt, index) => {3601          var text = SQLite3.ColumnString (stmt, index);3602          return new Guid (text);3603        });3604      }3605      else if (clrType == typeof (Uri)) {3606        fastSetter = CreateTypedSetterDelegate<T, Uri> (column, (stmt, index) => {3607          var text = SQLite3.ColumnString (stmt, index);3608          return new Uri (text);3609        });3610      }3611      else if (clrType == typeof (StringBuilder)) {3612        fastSetter = CreateTypedSetterDelegate<T, StringBuilder> (column, (stmt, index) => {3613          var text = SQLite3.ColumnString (stmt, index);3614          return new StringBuilder (text);3615        });3616      }3617      else if (clrType == typeof (UriBuilder)) {3618        fastSetter = CreateTypedSetterDelegate<T, UriBuilder> (column, (stmt, index) => {3619          var text = SQLite3.ColumnString (stmt, index);3620          return new UriBuilder (text);3621        });3622      }3623      else {3624        // NOTE: Will fall back to the slow setter method in the event that we are unable to create a fast setter delega3559      else if (clrTypeInfo.IsEnum) {3560        // NOTE: Not sure of a good way (if any?) to do a strongly-typed fast setter like this for enumerated types -- f3561      }3562      else if (clrType == typeof (Int64)) {3563        fastSetter = CreateNullableTypedSetterDelegate<T, Int64> (column, (stmt, index) => {3564          return SQLite3.ColumnInt64 (stmt, index);3565        });3566      }3567      else if (clrType == typeof(UInt64))3568      {3569        fastSetter = CreateNullableTypedSetterDelegate<T, UInt64>(column, (stmt, index) => {3570          return (ulong)SQLite3.ColumnInt64(stmt, index);3571        });3572      }3573      else if (clrType == typeof (UInt32)) {3574        fastSetter = CreateNullableTypedSetterDelegate<T, UInt32> (column, (stmt, index) => {3575          return (uint)SQLite3.ColumnInt64 (stmt, index);3576        });3577      }3578      else if (clrType == typeof (decimal)) {3579        fastSetter = CreateNullableTypedSetterDelegate<T, decimal> (column, (stmt, index) => {3580          return (decimal)SQLite3.ColumnDouble (stmt, index);3581        });3582      }3583      else if (clrType == typeof (Byte)) {3584        fastSetter = CreateNullableTypedSetterDelegate<T, Byte> (column, (stmt, index) => {3585          return (byte)SQLite3.ColumnInt (stmt, index);3586        });3587      }3588      else if (clrType == typeof (UInt16)) {3589        fastSetter = CreateNullableTypedSetterDelegate<T, UInt16> (column, (stmt, index) => {3590          return (ushort)SQLite3.ColumnInt (stmt, index);3591        });3592      }3593      else if (clrType == typeof (Int16)) {3594        fastSetter = CreateNullableTypedSetterDelegate<T, Int16> (column, (stmt, index) => {3595          return (short)SQLite3.ColumnInt (stmt, index);3596        });3597      }3598      else if (clrType == typeof (sbyte)) {3599        fastSetter = CreateNullableTypedSetterDelegate<T, sbyte> (column, (stmt, index) => {3600          return (sbyte)SQLite3.ColumnInt (stmt, index);3601        });3602      }3603      else if (clrType == typeof (byte[])) {3604        fastSetter = CreateTypedSetterDelegate<T, byte[]> (column, (stmt, index) => {3605          return SQLite3.ColumnByteArray (stmt, index);3606        });3607      }3608      else if (clrType == typeof (Guid)) {3609        fastSetter = CreateNullableTypedSetterDelegate<T, Guid> (column, (stmt, index) => {3610          var text = SQLite3.ColumnString (stmt, index);3611          return new Guid (text);3612        });3613      }3614      else if (clrType == typeof (Uri)) {3615        fastSetter = CreateTypedSetterDelegate<T, Uri> (column, (stmt, index) => {3616          var text = SQLite3.ColumnString (stmt, index);3617          return new Uri (text);3618        });3619      }3620      else if (clrType == typeof (StringBuilder)) {3621        fastSetter = CreateTypedSetterDelegate<T, StringBuilder> (column, (stmt, index) => {3622          var text = SQLite3.ColumnString (stmt, index);3623          return new StringBuilder (text);3624        });  3625      }3626      return fastSetter;3627    }36283629    /// <summary>3630    /// This creates a strongly typed delegate that will permit fast setting of column values given a Sqlite3Statement a3631    ///3632    /// Note that this is identical to CreateTypedSetterDelegate(), but has an extra check to see if it should create a 3633    /// </summary>3634    /// <typeparam name="ObjectType">The type of the object whose member column is being set</typeparam>3635    /// <typeparam name="ColumnMemberType">The CLR type of the member in the object which corresponds to the given SQLit3636    /// <param name="column">The column mapping that identifies the target member of the destination object</param>3637    /// <param name="getColumnValue">A lambda that can be used to retrieve the column value at query-time</param>3638    /// <returns>A strongly-typed delegate</returns>3639    private static Action<object, Sqlite3Statement, int> CreateNullableTypedSetterDelegate<ObjectType, ColumnMemberType>3640    {3641      var clrTypeInfo = column.PropertyInfo.PropertyType.GetTypeInfo();3642      bool isNullable = false;36433644      if (clrTypeInfo.IsGenericType && clrTypeInfo.GetGenericTypeDefinition () == typeof (Nullable<>)) {3645        isNullable = true;3646      }36473648      if (isNullable) {3649        var setProperty = (Action<ObjectType, ColumnMemberType?>)Delegate.CreateDelegate (3650            typeof (Action<ObjectType, ColumnMemberType?>), null,3651            column.PropertyInfo.GetSetMethod ());3626      else if (clrType == typeof (UriBuilder)) {3627        fastSetter = CreateTypedSetterDelegate<T, UriBuilder> (column, (stmt, index) => {3628          var text = SQLite3.ColumnString (stmt, index);3629          return new UriBuilder (text);3630        });3631      }3632      else {3633        // NOTE: Will fall back to the slow setter method in the event that we are unable to create a fast setter delega3634      }3635      return fastSetter;3636    }36373638    /// <summary>3639    /// This creates a strongly typed delegate that will permit fast setting of column values given a Sqlite3Statement a3640    ///3641    /// Note that this is identical to CreateTypedSetterDelegate(), but has an extra check to see if it should create a 3642    /// </summary>3643    /// <typeparam name="ObjectType">The type of the object whose member column is being set</typeparam>3644    /// <typeparam name="ColumnMemberType">The CLR type of the member in the object which corresponds to the given SQLit3645    /// <param name="column">The column mapping that identifies the target member of the destination object</param>3646    /// <param name="getColumnValue">A lambda that can be used to retrieve the column value at query-time</param>3647    /// <returns>A strongly-typed delegate</returns>3648    private static Action<object, Sqlite3Statement, int> CreateNullableTypedSetterDelegate<ObjectType, ColumnMemberType>3649    {3650      var clrTypeInfo = column.PropertyInfo.PropertyType.GetTypeInfo();3651      bool isNullable = false;  36523653        return (o, stmt, i) => {3654          var colType = SQLite3.ColumnType (stmt, i);3655          if (colType != SQLite3.ColType.Null)3656            setProperty.Invoke ((ObjectType)o, getColumnValue.Invoke (stmt, i));3657        };3658      }36593660      return CreateTypedSetterDelegate<ObjectType, ColumnMemberType> (column, getColumnValue);3661    }36623663    /// <summary>3664    /// This creates a strongly typed delegate that will permit fast setting of column values given a Sqlite3Statement a3665    /// </summary>3666    /// <typeparam name="ObjectType">The type of the object whose member column is being set</typeparam>3667    /// <typeparam name="ColumnMemberType">The CLR type of the member in the object which corresponds to the given SQLit3668    /// <param name="column">The column mapping that identifies the target member of the destination object</param>3669    /// <param name="getColumnValue">A lambda that can be used to retrieve the column value at query-time</param>3670    /// <returns>A strongly-typed delegate</returns>3671    private static Action<object, Sqlite3Statement, int> CreateTypedSetterDelegate<ObjectType, ColumnMemberType> (TableM3672    {3673      var setProperty = (Action<ObjectType, ColumnMemberType>)Delegate.CreateDelegate (3674          typeof (Action<ObjectType, ColumnMemberType>), null,3675          column.PropertyInfo.GetSetMethod ());36763677      return (o, stmt, i) => {3678        var colType = SQLite3.ColumnType (stmt, i);3679        if (colType != SQLite3.ColType.Null)3680          setProperty.Invoke ((ObjectType)o, getColumnValue.Invoke (stmt, i));3681      };3682    }3683  }36843685  /// <summary>3686  /// Since the insert never changed, we only need to prepare once.3687  /// </summary>3688  class PreparedSqlLiteInsertCommand : IDisposable3689  {3690    bool Initialized;36913692    SQLiteConnection Connection;3653      if (clrTypeInfo.IsGenericType && clrTypeInfo.GetGenericTypeDefinition () == typeof (Nullable<>)) {3654        isNullable = true;3655      }36563657      if (isNullable) {3658        var setProperty = (Action<ObjectType, ColumnMemberType?>)Delegate.CreateDelegate (3659            typeof (Action<ObjectType, ColumnMemberType?>), null,3660            column.PropertyInfo.GetSetMethod ());36613662        return (o, stmt, i) => {3663          var colType = SQLite3.ColumnType (stmt, i);3664          if (colType != SQLite3.ColType.Null)3665            setProperty.Invoke ((ObjectType)o, getColumnValue.Invoke (stmt, i));3666        };3667      }36683669      return CreateTypedSetterDelegate<ObjectType, ColumnMemberType> (column, getColumnValue);3670    }36713672    /// <summary>3673    /// This creates a strongly typed delegate that will permit fast setting of column values given a Sqlite3Statement a3674    /// </summary>3675    /// <typeparam name="ObjectType">The type of the object whose member column is being set</typeparam>3676    /// <typeparam name="ColumnMemberType">The CLR type of the member in the object which corresponds to the given SQLit3677    /// <param name="column">The column mapping that identifies the target member of the destination object</param>3678    /// <param name="getColumnValue">A lambda that can be used to retrieve the column value at query-time</param>3679    /// <returns>A strongly-typed delegate</returns>3680    private static Action<object, Sqlite3Statement, int> CreateTypedSetterDelegate<ObjectType, ColumnMemberType> (TableM3681    {3682      var setProperty = (Action<ObjectType, ColumnMemberType>)Delegate.CreateDelegate (3683          typeof (Action<ObjectType, ColumnMemberType>), null,3684          column.PropertyInfo.GetSetMethod ());36853686      return (o, stmt, i) => {3687        var colType = SQLite3.ColumnType (stmt, i);3688        if (colType != SQLite3.ColType.Null)3689          setProperty.Invoke ((ObjectType)o, getColumnValue.Invoke (stmt, i));3690      };3691    }3692  }  36933694    string CommandText;36953696    Sqlite3Statement Statement;3697    static readonly Sqlite3Statement NullStatement = default (Sqlite3Statement);36983699    public PreparedSqlLiteInsertCommand (SQLiteConnection conn, string commandText)3700    {3701      Connection = conn;3702      CommandText = commandText;3703    }3694  /// <summary>3695  /// Since the insert never changed, we only need to prepare once.3696  /// </summary>3697  class PreparedSqlLiteInsertCommand : IDisposable3698  {3699    bool Initialized;37003701    SQLiteConnection Connection;37023703    string CommandText;  37043705    public int ExecuteNonQuery (object[] source)3706    {3707      if (Initialized && Statement == NullStatement) {3708        throw new ObjectDisposedException (nameof (PreparedSqlLiteInsertCommand));3709      }37103711      if (Connection.Trace) {3712        Connection.Tracer?.Invoke ("Executing: " + CommandText);3713      }37143715      var r = SQLite3.Result.OK;37163717      if (!Initialized) {3718        Statement = SQLite3.Prepare2 (Connection.Handle, CommandText);3719        Initialized = true;3720      }37213722      //bind the values.3723      if (source != null) {3724        for (int i = 0; i < source.Length; i++) {3725          SQLiteCommand.BindParameter (Statement, i + 1, source[i], Connection.StoreDateTimeAsTicks, Connection.DateTime3726        }3727      }3728      r = SQLite3.Step (Statement);37293730      if (r == SQLite3.Result.Done) {3731        int rowsAffected = SQLite3.Changes (Connection.Handle);3732        SQLite3.Reset (Statement);3733        return rowsAffected;3734      }3735      else if (r == SQLite3.Result.Error) {3736        string msg = SQLite3.GetErrmsg (Connection.Handle);3737        SQLite3.Reset (Statement);3738        throw SQLiteException.New (r, msg);3739      }3740      else if (r == SQLite3.Result.Constraint && SQLite3.ExtendedErrCode (Connection.Handle) == SQLite3.ExtendedResult.C3705    Sqlite3Statement Statement;3706    static readonly Sqlite3Statement NullStatement = default (Sqlite3Statement);37073708    public PreparedSqlLiteInsertCommand (SQLiteConnection conn, string commandText)3709    {3710      Connection = conn;3711      CommandText = commandText;3712    }37133714    public int ExecuteNonQuery (object[] source)3715    {3716      if (Initialized && Statement == NullStatement) {3717        throw new ObjectDisposedException (nameof (PreparedSqlLiteInsertCommand));3718      }37193720      if (Connection.Trace) {3721        Connection.Tracer?.Invoke ("Executing: " + CommandText);3722      }37233724      var r = SQLite3.Result.OK;37253726      if (!Initialized) {3727        Statement = SQLite3.Prepare2 (Connection.Handle, CommandText);3728        Initialized = true;3729      }37303731      //bind the values.3732      if (source != null) {3733        for (int i = 0; i < source.Length; i++) {3734          SQLiteCommand.BindParameter (Statement, i + 1, source[i], Connection.StoreDateTimeAsTicks, Connection.DateTime3735        }3736      }3737      r = SQLite3.Step (Statement);37383739      if (r == SQLite3.Result.Done) {3740        int rowsAffected = SQLite3.Changes (Connection.Handle);  3741        SQLite3.Reset (Statement);3742        throw NotNullConstraintViolationException.New (r, SQLite3.GetErrmsg (Connection.Handle));3742        return rowsAffected;  3743      }3744      else {3745        SQLite3.Reset (Statement);3746        throw SQLiteException.New (r, SQLite3.GetErrmsg (Connection.Handle));3747      }3748    }37493750    public void Dispose ()3751    {3752      Dispose (true);3753      GC.SuppressFinalize (this);3754    }37553756    void Dispose (bool disposing)3757    {3758      var s = Statement;3759      Statement = NullStatement;3760      Connection = null;3761      if (s != NullStatement) {3762        SQLite3.Finalize (s);3763      }3764    }37653766    ~PreparedSqlLiteInsertCommand ()3767    {3768      Dispose (false);3769    }3770  }37713772  public enum CreateTableResult3773  {3774    Created,3775    Migrated,3776  }37773778  public class CreateTablesResult3779  {3780    public Dictionary<Type, CreateTableResult> Results { get; private set; }37813782    public CreateTablesResult ()3783    {3784      Results = new Dictionary<Type, CreateTableResult> ();3785    }3786  }37873788  public abstract class BaseTableQuery3789  {3790    protected class Ordering3791    {3792      public string ColumnName { get; set; }3793      public bool Ascending { get; set; }3744      else if (r == SQLite3.Result.Error) {3745        string msg = SQLite3.GetErrmsg (Connection.Handle);3746        SQLite3.Reset (Statement);3747        throw SQLiteException.New (r, msg);3748      }3749      else if (r == SQLite3.Result.Constraint && SQLite3.ExtendedErrCode (Connection.Handle) == SQLite3.ExtendedResult.C3750        SQLite3.Reset (Statement);3751        throw NotNullConstraintViolationException.New (r, SQLite3.GetErrmsg (Connection.Handle));3752      }3753      else {3754        SQLite3.Reset (Statement);3755        throw SQLiteException.New (r, SQLite3.GetErrmsg (Connection.Handle));3756      }3757    }37583759    public void Dispose ()3760    {3761      Dispose (true);3762      GC.SuppressFinalize (this);3763    }37643765    void Dispose (bool disposing)3766    {3767      var s = Statement;3768      Statement = NullStatement;3769      Connection = null;3770      if (s != NullStatement) {3771        SQLite3.Finalize (s);3772      }3773    }37743775    ~PreparedSqlLiteInsertCommand ()3776    {3777      Dispose (false);3778    }3779  }37803781  public enum CreateTableResult3782  {3783    Created,3784    Migrated,3785  }37863787  public class CreateTablesResult3788  {3789    public Dictionary<Type, CreateTableResult> Results { get; private set; }37903791    public CreateTablesResult ()3792    {3793      Results = new Dictionary<Type, CreateTableResult> ();  3794    }  3795  }  37963797  public class TableQuery<T> : BaseTableQuery, IEnumerable<T>3797  public abstract class BaseTableQuery  3798  {3799    public SQLiteConnection Connection { get; private set; }38003801    public TableMapping Table { get; private set; }38023803    Expression _where;3804    List<Ordering> _orderBys;3805    int? _limit;3806    int? _offset;38073808    BaseTableQuery _joinInner;3809    Expression _joinInnerKeySelector;3810    BaseTableQuery _joinOuter;3811    Expression _joinOuterKeySelector;3812    Expression _joinSelector;38133814    Expression _selector;38153816    TableQuery (SQLiteConnection conn, TableMapping table)3817    {3818      Connection = conn;3819      Table = table;3820    }38213822    public TableQuery (SQLiteConnection conn)3823    {3824      Connection = conn;3825      Table = Connection.GetMapping (typeof (T));3826    }38273828    public TableQuery<U> Clone<U> ()3829    {3830      var q = new TableQuery<U> (Connection, Table);3831      q._where = _where;3832      q._deferred = _deferred;3833      if (_orderBys != null) {3834        q._orderBys = new List<Ordering> (_orderBys);3835      }3836      q._limit = _limit;3837      q._offset = _offset;3838      q._joinInner = _joinInner;3839      q._joinInnerKeySelector = _joinInnerKeySelector;3840      q._joinOuter = _joinOuter;3841      q._joinOuterKeySelector = _joinOuterKeySelector;3842      q._joinSelector = _joinSelector;3843      q._selector = _selector;3844      return q;3845    }38463847    /// <summary>3848    /// Filters the query based on a predicate.3849    /// </summary>3850    public TableQuery<T> Where (Expression<Func<T, bool>> predExpr)3851    {3852      if (predExpr.NodeType == ExpressionType.Lambda) {3853        var lambda = (LambdaExpression)predExpr;3854        var pred = lambda.Body;3855        var q = Clone<T> ();3856        q.AddWhere (pred);3857        return q;3858      }3859      else {3860        throw new NotSupportedException ("Must be a predicate");3861      }3862    }38633864    /// <summary>3865    /// Delete all the rows that match this query.3866    /// </summary>3867    public int Delete ()3868    {3869      return Delete (null);3870    }38713872    /// <summary>3873    /// Delete all the rows that match this query and the given predicate.3874    /// </summary>3875    public int Delete (Expression<Func<T, bool>> predExpr)3876    {3877      if (_limit.HasValue || _offset.HasValue)3878        throw new InvalidOperationException ("Cannot delete with limits or offsets");38793880      if (_where == null && predExpr == null)3881        throw new InvalidOperationException ("No condition specified");38823883      var pred = _where;38843885      if (predExpr != null && predExpr.NodeType == ExpressionType.Lambda) {3886        var lambda = (LambdaExpression)predExpr;3887        pred = pred != null ? Expression.AndAlso (pred, lambda.Body) : lambda.Body;3888      }38893890      var args = new List<object> ();3891      var cmdText = "delete from \"" + Table.TableName + "\"";3892      var w = CompileExpr (pred, args);3893      cmdText += " where " + w.CommandText;38943895      var command = Connection.CreateCommand (cmdText, args.ToArray ());38963897      int result = command.ExecuteNonQuery ();3898      return result;3899    }39003901    /// <summary>3902    /// Yields a given number of elements from the query and then skips the remainder.3903    /// </summary>3904    public TableQuery<T> Take (int n)3905    {3906      var q = Clone<T> ();3907      q._limit = n;3908      return q;3909    }39103911    /// <summary>3912    /// Skips a given number of elements from the query and then yields the remainder.3913    /// </summary>3914    public TableQuery<T> Skip (int n)3915    {3916      var q = Clone<T> ();3917      q._offset = n;3918      return q;3919    }39203921    /// <summary>3922    /// Returns the element at a given index3923    /// </summary>3924    public T ElementAt (int index)3925    {3926      return Skip (index).Take (1).First ();3927    }39283929    bool _deferred;3930    public TableQuery<T> Deferred ()3931    {3932      var q = Clone<T> ();3933      q._deferred = true;3934      return q;3935    }39363937    /// <summary>3938    /// Order the query results according to a key.3939    /// </summary>3940    public TableQuery<T> OrderBy<U> (Expression<Func<T, U>> orderExpr)3941    {3942      return AddOrderBy<U> (orderExpr, true);3943    }39443945    /// <summary>3946    /// Order the query results according to a key.3947    /// </summary>3948    public TableQuery<T> OrderByDescending<U> (Expression<Func<T, U>> orderExpr)3949    {3950      return AddOrderBy<U> (orderExpr, false);3951    }39523953    /// <summary>3954    /// Order the query results according to a key.3955    /// </summary>3956    public TableQuery<T> ThenBy<U> (Expression<Func<T, U>> orderExpr)3957    {3958      return AddOrderBy<U> (orderExpr, true);3959    }39603961    /// <summary>3962    /// Order the query results according to a key.3963    /// </summary>3964    public TableQuery<T> ThenByDescending<U> (Expression<Func<T, U>> orderExpr)3965    {3966      return AddOrderBy<U> (orderExpr, false);3967    }39683969    TableQuery<T> AddOrderBy<U> (Expression<Func<T, U>> orderExpr, bool asc)3970    {3971      if (orderExpr.NodeType == ExpressionType.Lambda) {3972        var lambda = (LambdaExpression)orderExpr;39733974        MemberExpression mem = null;39753976        var unary = lambda.Body as UnaryExpression;3977        if (unary != null && unary.NodeType == ExpressionType.Convert) {3978          mem = unary.Operand as MemberExpression;3979        }3980        else {3981          mem = lambda.Body as MemberExpression;3982        }39833984        if (mem != null && (mem.Expression.NodeType == ExpressionType.Parameter)) {3985          var q = Clone<T> ();3986          if (q._orderBys == null) {3987            q._orderBys = new List<Ordering> ();3988          }3989          q._orderBys.Add (new Ordering {3990            ColumnName = Table.FindColumnWithPropertyName (mem.Member.Name).Name,3991            Ascending = asc3992          });3993          return q;3994        }3995        else {3996          throw new NotSupportedException ("Order By does not support: " + orderExpr);3997        }3998      }3999      else {4000        throw new NotSupportedException ("Must be a predicate");4001      }4002    }40034004    private void AddWhere (Expression pred)4005    {4006      if (_where == null) {4007        _where = pred;4008      }4009      else {4010        _where = Expression.AndAlso (_where, pred);4011      }4012    }40134014    ///// <summary>4015    ///// Performs an inner join of two queries based on matching keys extracted from the elements.4016    ///// </summary>4017    //public TableQuery<TResult> Join<TInner, TKey, TResult> (4018    //  TableQuery<TInner> inner,4019    //  Expression<Func<T, TKey>> outerKeySelector,4020    //  Expression<Func<TInner, TKey>> innerKeySelector,4021    //  Expression<Func<T, TInner, TResult>> resultSelector)4022    //{4023    //  var q = new TableQuery<TResult> (Connection, Connection.GetMapping (typeof (TResult))) {4024    //    _joinOuter = this,4025    //    _joinOuterKeySelector = outerKeySelector,4026    //    _joinInner = inner,4027    //    _joinInnerKeySelector = innerKeySelector,4028    //    _joinSelector = resultSelector,4029    //  };4030    //  return q;4031    //}40324033    // Not needed until Joins are supported4034    // Keeping this commented out forces the default Linq to objects processor to run4035    //public TableQuery<TResult> Select<TResult> (Expression<Func<T, TResult>> selector)4036    //{4037    //  var q = Clone<TResult> ();4038    //  q._selector = selector;3799    protected class Ordering3800    {3801      public string ColumnName { get; set; }3802      public bool Ascending { get; set; }3803    }3804  }38053806  public class TableQuery<T> : BaseTableQuery, IEnumerable<T>3807  {3808    public SQLiteConnection Connection { get; private set; }38093810    public TableMapping Table { get; private set; }38113812    Expression _where;3813    List<Ordering> _orderBys;3814    int? _limit;3815    int? _offset;38163817    BaseTableQuery _joinInner;3818    Expression _joinInnerKeySelector;3819    BaseTableQuery _joinOuter;3820    Expression _joinOuterKeySelector;3821    Expression _joinSelector;38223823    Expression _selector;38243825    TableQuery (SQLiteConnection conn, TableMapping table)3826    {3827      Connection = conn;3828      Table = table;3829    }38303831    public TableQuery (SQLiteConnection conn)3832    {3833      Connection = conn;3834      Table = Connection.GetMapping (typeof (T));3835    }38363837    public TableQuery<U> Clone<U> ()3838    {3839      var q = new TableQuery<U> (Connection, Table);3840      q._where = _where;3841      q._deferred = _deferred;3842      if (_orderBys != null) {3843        q._orderBys = new List<Ordering> (_orderBys);3844      }3845      q._limit = _limit;3846      q._offset = _offset;3847      q._joinInner = _joinInner;3848      q._joinInnerKeySelector = _joinInnerKeySelector;3849      q._joinOuter = _joinOuter;3850      q._joinOuterKeySelector = _joinOuterKeySelector;3851      q._joinSelector = _joinSelector;3852      q._selector = _selector;3853      return q;3854    }38553856    /// <summary>3857    /// Filters the query based on a predicate.3858    /// </summary>3859    public TableQuery<T> Where (Expression<Func<T, bool>> predExpr)3860    {3861      if (predExpr.NodeType == ExpressionType.Lambda) {3862        var lambda = (LambdaExpression)predExpr;3863        var pred = lambda.Body;3864        var q = Clone<T> ();3865        q.AddWhere (pred);3866        return q;3867      }3868      else {3869        throw new NotSupportedException ("Must be a predicate");3870      }3871    }38723873    /// <summary>3874    /// Delete all the rows that match this query.3875    /// </summary>3876    public int Delete ()3877    {3878      return Delete (null);3879    }38803881    /// <summary>3882    /// Delete all the rows that match this query and the given predicate.3883    /// </summary>3884    public int Delete (Expression<Func<T, bool>> predExpr)3885    {3886      if (_limit.HasValue || _offset.HasValue)3887        throw new InvalidOperationException ("Cannot delete with limits or offsets");38883889      if (_where == null && predExpr == null)3890        throw new InvalidOperationException ("No condition specified");38913892      var pred = _where;38933894      if (predExpr != null && predExpr.NodeType == ExpressionType.Lambda) {3895        var lambda = (LambdaExpression)predExpr;3896        pred = pred != null ? Expression.AndAlso (pred, lambda.Body) : lambda.Body;3897      }38983899      var args = new List<object> ();3900      var cmdText = "delete from \"" + Table.TableName + "\"";3901      var w = CompileExpr (pred, args);3902      cmdText += " where " + w.CommandText;39033904      var command = Connection.CreateCommand (cmdText, args.ToArray ());39053906      int result = command.ExecuteNonQuery ();3907      return result;3908    }39093910    /// <summary>3911    /// Yields a given number of elements from the query and then skips the remainder.3912    /// </summary>3913    public TableQuery<T> Take (int n)3914    {3915      var q = Clone<T> ();3916      q._limit = n;3917      return q;3918    }39193920    /// <summary>3921    /// Skips a given number of elements from the query and then yields the remainder.3922    /// </summary>3923    public TableQuery<T> Skip (int n)3924    {3925      var q = Clone<T> ();3926      q._offset = n;3927      return q;3928    }39293930    /// <summary>3931    /// Returns the element at a given index3932    /// </summary>3933    public T ElementAt (int index)3934    {3935      return Skip (index).Take (1).First ();3936    }39373938    bool _deferred;3939    public TableQuery<T> Deferred ()3940    {3941      var q = Clone<T> ();3942      q._deferred = true;3943      return q;3944    }39453946    /// <summary>3947    /// Order the query results according to a key.3948    /// </summary>3949    public TableQuery<T> OrderBy<U> (Expression<Func<T, U>> orderExpr)3950    {3951      return AddOrderBy<U> (orderExpr, true);3952    }39533954    /// <summary>3955    /// Order the query results according to a key.3956    /// </summary>3957    public TableQuery<T> OrderByDescending<U> (Expression<Func<T, U>> orderExpr)3958    {3959      return AddOrderBy<U> (orderExpr, false);3960    }39613962    /// <summary>3963    /// Order the query results according to a key.3964    /// </summary>3965    public TableQuery<T> ThenBy<U> (Expression<Func<T, U>> orderExpr)3966    {3967      return AddOrderBy<U> (orderExpr, true);3968    }39693970    /// <summary>3971    /// Order the query results according to a key.3972    /// </summary>3973    public TableQuery<T> ThenByDescending<U> (Expression<Func<T, U>> orderExpr)3974    {3975      return AddOrderBy<U> (orderExpr, false);3976    }39773978    TableQuery<T> AddOrderBy<U> (Expression<Func<T, U>> orderExpr, bool asc)3979    {3980      if (orderExpr.NodeType == ExpressionType.Lambda) {3981        var lambda = (LambdaExpression)orderExpr;39823983        MemberExpression mem = null;39843985        var unary = lambda.Body as UnaryExpression;3986        if (unary != null && unary.NodeType == ExpressionType.Convert) {3987          mem = unary.Operand as MemberExpression;3988        }3989        else {3990          mem = lambda.Body as MemberExpression;3991        }39923993        if (mem != null && (mem.Expression.NodeType == ExpressionType.Parameter)) {3994          var q = Clone<T> ();3995          if (q._orderBys == null) {3996            q._orderBys = new List<Ordering> ();3997          }3998          q._orderBys.Add (new Ordering {3999            ColumnName = Table.FindColumnWithPropertyName (mem.Member.Name).Name,4000            Ascending = asc4001          });4002          return q;4003        }4004        else {4005          throw new NotSupportedException ("Order By does not support: " + orderExpr);4006        }4007      }4008      else {4009        throw new NotSupportedException ("Must be a predicate");4010      }4011    }40124013    private void AddWhere (Expression pred)4014    {4015      if (_where == null) {4016        _where = pred;4017      }4018      else {4019        _where = Expression.AndAlso (_where, pred);4020      }4021    }40224023    ///// <summary>4024    ///// Performs an inner join of two queries based on matching keys extracted from the elements.4025    ///// </summary>4026    //public TableQuery<TResult> Join<TInner, TKey, TResult> (4027    //  TableQuery<TInner> inner,4028    //  Expression<Func<T, TKey>> outerKeySelector,4029    //  Expression<Func<TInner, TKey>> innerKeySelector,4030    //  Expression<Func<T, TInner, TResult>> resultSelector)4031    //{4032    //  var q = new TableQuery<TResult> (Connection, Connection.GetMapping (typeof (TResult))) {4033    //    _joinOuter = this,4034    //    _joinOuterKeySelector = outerKeySelector,4035    //    _joinInner = inner,4036    //    _joinInnerKeySelector = innerKeySelector,4037    //    _joinSelector = resultSelector,4038    //  };  4039    //  return q;  4040    //}  40414042    private SQLiteCommand GenerateCommand (string selectionList)4043    {4044      if (_joinInner != null && _joinOuter != null) {4045        throw new NotSupportedException ("Joins are not supported.");4046      }4047      else {4048        var cmdText = "select " + selectionList + " from \"" + Table.TableName + "\"";4049        var args = new List<object> ();4050        if (_where != null) {4051          var w = CompileExpr (_where, args);4052          cmdText += " where " + w.CommandText;4053        }4054        if ((_orderBys != null) && (_orderBys.Count > 0)) {4055          var t = string.Join (", ", _orderBys.Select (o => "\"" + o.ColumnName + "\"" + (o.Ascending ? "" : " desc")).T4056          cmdText += " order by " + t;4057        }4058        if (_limit.HasValue) {4059          cmdText += " limit " + _limit.Value;4060        }4061        if (_offset.HasValue) {4062          if (!_limit.HasValue) {4063            cmdText += " limit -1 ";4064          }4065          cmdText += " offset " + _offset.Value;4042    // Not needed until Joins are supported4043    // Keeping this commented out forces the default Linq to objects processor to run4044    //public TableQuery<TResult> Select<TResult> (Expression<Func<T, TResult>> selector)4045    //{4046    //  var q = Clone<TResult> ();4047    //  q._selector = selector;4048    //  return q;4049    //}40504051    private SQLiteCommand GenerateCommand (string selectionList)4052    {4053      if (_joinInner != null && _joinOuter != null) {4054        throw new NotSupportedException ("Joins are not supported.");4055      }4056      else {4057        var cmdText = "select " + selectionList + " from \"" + Table.TableName + "\"";4058        var args = new List<object> ();4059        if (_where != null) {4060          var w = CompileExpr (_where, args);4061          cmdText += " where " + w.CommandText;4062        }4063        if ((_orderBys != null) && (_orderBys.Count > 0)) {4064          var t = string.Join (", ", _orderBys.Select (o => "\"" + o.ColumnName + "\"" + (o.Ascending ? "" : " desc")).T4065          cmdText += " order by " + t;  4066        }4067        return Connection.CreateCommand (cmdText, args.ToArray ());4068      }4069    }40704071    class CompileResult4072    {4073      public string CommandText { get; set; }40744075      public object Value { get; set; }4076    }40774078    private CompileResult CompileExpr (Expression expr, List<object> queryArgs)4079    {4080      if (expr == null) {4081        throw new NotSupportedException ("Expression is NULL");4082      }4083      else if (expr is BinaryExpression) {4084        var bin = (BinaryExpression)expr;40854086        // VB turns 'x=="foo"' into 'CompareString(x,"foo",true/false)==0', so we need to unwrap it4087        // http://blogs.msdn.com/b/vbteam/archive/2007/09/18/vb-expression-trees-string-comparisons.aspx4088        if (bin.Left.NodeType == ExpressionType.Call) {4089          var call = (MethodCallExpression)bin.Left;4090          if (call.Method.DeclaringType.FullName == "Microsoft.VisualBasic.CompilerServices.Operators"4091            && call.Method.Name == "CompareString")4092            bin = Expression.MakeBinary (bin.NodeType, call.Arguments[0], call.Arguments[1]);4093        }4067        if (_limit.HasValue) {4068          cmdText += " limit " + _limit.Value;4069        }4070        if (_offset.HasValue) {4071          if (!_limit.HasValue) {4072            cmdText += " limit -1 ";4073          }4074          cmdText += " offset " + _offset.Value;4075        }4076        return Connection.CreateCommand (cmdText, args.ToArray ());4077      }4078    }40794080    class CompileResult4081    {4082      public string CommandText { get; set; }40834084      public object Value { get; set; }4085    }40864087    private CompileResult CompileExpr (Expression expr, List<object> queryArgs)4088    {4089      if (expr == null) {4090        throw new NotSupportedException ("Expression is NULL");4091      }4092      else if (expr is BinaryExpression) {4093        var bin = (BinaryExpression)expr;  409440954096        var leftr = CompileExpr (bin.Left, queryArgs);4097        var rightr = CompileExpr (bin.Right, queryArgs);40984099        //If either side is a parameter and is null, then handle the other side specially (for "is null"/"is not null")4100        string text;4101        if (leftr.CommandText == "?" && leftr.Value == null)4102          text = CompileNullBinaryExpression (bin, rightr);4103        else if (rightr.CommandText == "?" && rightr.Value == null)4104          text = CompileNullBinaryExpression (bin, leftr);4105        else4106          text = "(" + leftr.CommandText + " " + GetSqlName (bin) + " " + rightr.CommandText + ")";4107        return new CompileResult { CommandText = text };4108      }4109      else if (expr.NodeType == ExpressionType.Not) {4110        var operandExpr = ((UnaryExpression)expr).Operand;4111        var opr = CompileExpr (operandExpr, queryArgs);4112        object val = opr.Value;4113        if (val is bool)4114          val = !((bool)val);4115        return new CompileResult {4116          CommandText = "NOT(" + opr.CommandText + ")",4117          Value = val4118        };4119      }4120      else if (expr.NodeType == ExpressionType.Call) {41214122        var call = (MethodCallExpression)expr;4123        var args = new CompileResult[call.Arguments.Count];4124        var obj = call.Object != null ? CompileExpr (call.Object, queryArgs) : null;41254126        for (var i = 0; i < args.Length; i++) {4127          args[i] = CompileExpr (call.Arguments[i], queryArgs);4128        }41294130        var sqlCall = "";41314132        if (call.Method.Name == "Like" && args.Length == 2) {4133          sqlCall = "(" + args[0].CommandText + " like " + args[1].CommandText + ")";4134        }4135        else if (call.Method.Name == "Contains" && args.Length == 2) {4136          sqlCall = "(" + args[1].CommandText + " in " + args[0].CommandText + ")";4095        // VB turns 'x=="foo"' into 'CompareString(x,"foo",true/false)==0', so we need to unwrap it4096        // http://blogs.msdn.com/b/vbteam/archive/2007/09/18/vb-expression-trees-string-comparisons.aspx4097        if (bin.Left.NodeType == ExpressionType.Call) {4098          var call = (MethodCallExpression)bin.Left;4099          if (call.Method.DeclaringType.FullName == "Microsoft.VisualBasic.CompilerServices.Operators"4100            && call.Method.Name == "CompareString")4101            bin = Expression.MakeBinary (bin.NodeType, call.Arguments[0], call.Arguments[1]);4102        }410341044105        var leftr = CompileExpr (bin.Left, queryArgs);4106        var rightr = CompileExpr (bin.Right, queryArgs);41074108        //If either side is a parameter and is null, then handle the other side specially (for "is null"/"is not null")4109        string text;4110        if (leftr.CommandText == "?" && leftr.Value == null)4111          text = CompileNullBinaryExpression (bin, rightr);4112        else if (rightr.CommandText == "?" && rightr.Value == null)4113          text = CompileNullBinaryExpression (bin, leftr);4114        else4115          text = "(" + leftr.CommandText + " " + GetSqlName (bin) + " " + rightr.CommandText + ")";4116        return new CompileResult { CommandText = text };4117      }4118      else if (expr.NodeType == ExpressionType.Not) {4119        var operandExpr = ((UnaryExpression)expr).Operand;4120        var opr = CompileExpr (operandExpr, queryArgs);4121        object val = opr.Value;4122        if (val is bool)4123          val = !((bool)val);4124        return new CompileResult {4125          CommandText = "NOT(" + opr.CommandText + ")",4126          Value = val4127        };4128      }4129      else if (expr.NodeType == ExpressionType.Call) {41304131        var call = (MethodCallExpression)expr;4132        var args = new CompileResult[call.Arguments.Count];4133        var obj = call.Object != null ? CompileExpr (call.Object, queryArgs) : null;41344135        for (var i = 0; i < args.Length; i++) {4136          args[i] = CompileExpr (call.Arguments[i], queryArgs);  4137        }4138        else if (call.Method.Name == "Contains" && args.Length == 1) {4139          if (call.Object != null && call.Object.Type == typeof (string)) {4140            sqlCall = "( instr(" + obj.CommandText + "," + args[0].CommandText + ") >0 )";4141          }4142          else {4143            sqlCall = "(" + args[0].CommandText + " in " + obj.CommandText + ")";4144          }4145        }4146        else if (call.Method.Name == "StartsWith" && args.Length >= 1) {4147          var startsWithCmpOp = StringComparison.CurrentCulture;4148          if (args.Length == 2) {4149            startsWithCmpOp = (StringComparison)args[1].Value;41384139        var sqlCall = "";41404141        if (call.Method.Name == "Like" && args.Length == 2) {4142          sqlCall = "(" + args[0].CommandText + " like " + args[1].CommandText + ")";4143        }4144        else if (call.Method.Name == "Contains" && args.Length == 2) {4145          sqlCall = "(" + args[1].CommandText + " in " + args[0].CommandText + ")";4146        }4147        else if (call.Method.Name == "Contains" && args.Length == 1) {4148          if (call.Object != null && call.Object.Type == typeof (string)) {4149            sqlCall = "( instr(" + obj.CommandText + "," + args[0].CommandText + ") >0 )";  4150          }4151          switch (startsWithCmpOp) {4152            case StringComparison.Ordinal:4153            case StringComparison.CurrentCulture:4154              sqlCall = "( substr(" + obj.CommandText + ", 1, " + args[0].Value.ToString ().Length + ") =  " + args[0].C4155              break;4156            case StringComparison.OrdinalIgnoreCase:4157            case StringComparison.CurrentCultureIgnoreCase:4158              sqlCall = "(" + obj.CommandText + " like (" + args[0].CommandText + " || '%'))";4159              break;4160          }41614162        }4163        else if (call.Method.Name == "EndsWith" && args.Length >= 1) {4164          var endsWithCmpOp = StringComparison.CurrentCulture;4165          if (args.Length == 2) {4166            endsWithCmpOp = (StringComparison)args[1].Value;4167          }4168          switch (endsWithCmpOp) {4169            case StringComparison.Ordinal:4170            case StringComparison.CurrentCulture:4171              sqlCall = "( substr(" + obj.CommandText + ", length(" + obj.CommandText + ") - " + args[0].Value.ToString 4172              break;4173            case StringComparison.OrdinalIgnoreCase:4174            case StringComparison.CurrentCultureIgnoreCase:4175              sqlCall = "(" + obj.CommandText + " like ('%' || " + args[0].CommandText + "))";4176              break;4177          }4178        }4179        else if (call.Method.Name == "Equals" && args.Length == 1) {4180          sqlCall = "(" + obj.CommandText + " = (" + args[0].CommandText + "))";4181        }4182        else if (call.Method.Name == "ToLower") {4183          sqlCall = "(lower(" + obj.CommandText + "))";4184        }4185        else if (call.Method.Name == "ToUpper") {4186          sqlCall = "(upper(" + obj.CommandText + "))";4151          else {4152            sqlCall = "(" + args[0].CommandText + " in " + obj.CommandText + ")";4153          }4154        }4155        else if (call.Method.Name == "StartsWith" && args.Length >= 1) {4156          var startsWithCmpOp = StringComparison.CurrentCulture;4157          if (args.Length == 2) {4158            startsWithCmpOp = (StringComparison)args[1].Value;4159          }4160          switch (startsWithCmpOp) {4161            case StringComparison.Ordinal:4162            case StringComparison.CurrentCulture:4163              sqlCall = "( substr(" + obj.CommandText + ", 1, " + args[0].Value.ToString ().Length + ") =  " + args[0].C4164              break;4165            case StringComparison.OrdinalIgnoreCase:4166            case StringComparison.CurrentCultureIgnoreCase:4167              sqlCall = "(" + obj.CommandText + " like (" + args[0].CommandText + " || '%'))";4168              break;4169          }41704171        }4172        else if (call.Method.Name == "EndsWith" && args.Length >= 1) {4173          var endsWithCmpOp = StringComparison.CurrentCulture;4174          if (args.Length == 2) {4175            endsWithCmpOp = (StringComparison)args[1].Value;4176          }4177          switch (endsWithCmpOp) {4178            case StringComparison.Ordinal:4179            case StringComparison.CurrentCulture:4180              sqlCall = "( substr(" + obj.CommandText + ", length(" + obj.CommandText + ") - " + args[0].Value.ToString 4181              break;4182            case StringComparison.OrdinalIgnoreCase:4183            case StringComparison.CurrentCultureIgnoreCase:4184              sqlCall = "(" + obj.CommandText + " like ('%' || " + args[0].CommandText + "))";4185              break;4186          }  4187        }4188        else if (call.Method.Name == "Replace" && args.Length == 2) {4189          sqlCall = "(replace(" + obj.CommandText + "," + args[0].CommandText + "," + args[1].CommandText + "))";4188        else if (call.Method.Name == "Equals" && args.Length == 1) {4189          sqlCall = "(" + obj.CommandText + " = (" + args[0].CommandText + "))";  4190        }4191        else if (call.Method.Name == "IsNullOrEmpty" && args.Length == 1) {4192          sqlCall = "(" + args[0].CommandText + " is null or" + args[0].CommandText + " ='' )";4191        else if (call.Method.Name == "ToLower") {4192          sqlCall = "(lower(" + obj.CommandText + "))";  4193        }4194        else {4195          sqlCall = call.Method.Name.ToLower () + "(" + string.Join (",", args.Select (a => a.CommandText).ToArray ()) +4194        else if (call.Method.Name == "ToUpper") {4195          sqlCall = "(upper(" + obj.CommandText + "))";  4196        }4197        return new CompileResult { CommandText = sqlCall };41984199      }4200      else if (expr.NodeType == ExpressionType.Constant) {4201        var c = (ConstantExpression)expr;4202        queryArgs.Add (c.Value);4203        return new CompileResult {4204          CommandText = "?",4205          Value = c.Value4206        };4207      }4208      else if (expr.NodeType == ExpressionType.Convert) {4209        var u = (UnaryExpression)expr;4210        var ty = u.Type;4211        var valr = CompileExpr (u.Operand, queryArgs);4197        else if (call.Method.Name == "Replace" && args.Length == 2) {4198          sqlCall = "(replace(" + obj.CommandText + "," + args[0].CommandText + "," + args[1].CommandText + "))";4199        }4200        else if (call.Method.Name == "IsNullOrEmpty" && args.Length == 1) {4201          sqlCall = "(" + args[0].CommandText + " is null or" + args[0].CommandText + " ='' )";4202        }4203        else {4204          sqlCall = call.Method.Name.ToLower () + "(" + string.Join (",", args.Select (a => a.CommandText).ToArray ()) +4205        }4206        return new CompileResult { CommandText = sqlCall };42074208      }4209      else if (expr.NodeType == ExpressionType.Constant) {4210        var c = (ConstantExpression)expr;4211        queryArgs.Add (c.Value);  4212        return new CompileResult {4213          CommandText = valr.CommandText,4214          Value = valr.Value != null ? ConvertTo (valr.Value, ty) : null4213          CommandText = "?",4214          Value = c.Value  4215        };  4216      }4217      else if (expr.NodeType == ExpressionType.MemberAccess) {4218        var mem = (MemberExpression)expr;42194220        var paramExpr = mem.Expression as ParameterExpression;4221        if (paramExpr == null) {4222          var convert = mem.Expression as UnaryExpression;4223          if (convert != null && convert.NodeType == ExpressionType.Convert) {4224            paramExpr = convert.Operand as ParameterExpression;4225          }4226        }42274228        if (paramExpr != null) {4229          //4230          // This is a column of our table, output just the column name4231          // Need to translate it if that column name is mapped4232          //4233          var columnName = Table.FindColumnWithPropertyName (mem.Member.Name).Name;4234          return new CompileResult { CommandText = "\"" + columnName + "\"" };4217      else if (expr.NodeType == ExpressionType.Convert) {4218        var u = (UnaryExpression)expr;4219        var ty = u.Type;4220        var valr = CompileExpr (u.Operand, queryArgs);4221        return new CompileResult {4222          CommandText = valr.CommandText,4223          Value = valr.Value != null ? ConvertTo (valr.Value, ty) : null4224        };4225      }4226      else if (expr.NodeType == ExpressionType.MemberAccess) {4227        var mem = (MemberExpression)expr;42284229        var paramExpr = mem.Expression as ParameterExpression;4230        if (paramExpr == null) {4231          var convert = mem.Expression as UnaryExpression;4232          if (convert != null && convert.NodeType == ExpressionType.Convert) {4233            paramExpr = convert.Operand as ParameterExpression;4234          }  4235        }4236        else {4237          object obj = null;4238          if (mem.Expression != null) {4239            var r = CompileExpr (mem.Expression, queryArgs);4240            if (r.Value == null) {4241              throw new NotSupportedException ("Member access failed to compile expression");4242            }4243            if (r.CommandText == "?") {4244              queryArgs.RemoveAt (queryArgs.Count - 1);4245            }4246            obj = r.Value;4247          }42484249          //4250          // Get the member value4251          //4252          object val = null;42534254          if (mem.Member is PropertyInfo) {4255            var m = (PropertyInfo)mem.Member;4256            val = m.GetValue (obj, null);4257          }4258          else if (mem.Member is FieldInfo) {4259            var m = (FieldInfo)mem.Member;4260            val = m.GetValue (obj);4261          }4262          else {4263            throw new NotSupportedException ("MemberExpr: " + mem.Member.GetType ());4264          }42654266          //4267          // Work special magic for enumerables4268          //4269          if (val != null && val is System.Collections.IEnumerable && !(val is string) && !(val is System.Collections.Ge4270            var sb = new System.Text.StringBuilder ();4271            sb.Append ("(");4272            var head = "";4273            foreach (var a in (System.Collections.IEnumerable)val) {4274              queryArgs.Add (a);4275              sb.Append (head);4276              sb.Append ("?");4277              head = ",";4278            }4279            sb.Append (")");4280            return new CompileResult {4281              CommandText = sb.ToString (),4282              Value = val4283            };4284          }4285          else {4286            queryArgs.Add (val);4287            return new CompileResult {4288              CommandText = "?",4289              Value = val4290            };4291          }4292        }4293      }4294      throw new NotSupportedException ("Cannot compile: " + expr.NodeType.ToString ());4295    }42964297    static object ConvertTo (object obj, Type t)4298    {4299      Type nut = Nullable.GetUnderlyingType (t);43004301      if (nut != null) {4302        if (obj == null)4303          return null;4304        return Convert.ChangeType (obj, nut);4305      }4306      else {4307        return Convert.ChangeType (obj, t);4308      }4309    }43104311    /// <summary>4312    /// Compiles a BinaryExpression where one of the parameters is null.4313    /// </summary>4314    /// <param name="expression">The expression to compile</param>4315    /// <param name="parameter">The non-null parameter</param>4316    private string CompileNullBinaryExpression (BinaryExpression expression, CompileResult parameter)4317    {4318      if (expression.NodeType == ExpressionType.Equal)4319        return "(" + parameter.CommandText + " is ?)";4320      else if (expression.NodeType == ExpressionType.NotEqual)4321        return "(" + parameter.CommandText + " is not ?)";4322      else if (expression.NodeType == ExpressionType.GreaterThan4323        || expression.NodeType == ExpressionType.GreaterThanOrEqual4324        || expression.NodeType == ExpressionType.LessThan4325        || expression.NodeType == ExpressionType.LessThanOrEqual)4326        return "(" + parameter.CommandText + " < ?)"; // always false4327      else4328        throw new NotSupportedException ("Cannot compile Null-BinaryExpression with type " + expression.NodeType.ToStrin4329    }43304331    string GetSqlName (Expression expr)4332    {4333      var n = expr.NodeType;4334      if (n == ExpressionType.GreaterThan)4335        return ">";4336      else if (n == ExpressionType.GreaterThanOrEqual) {4337        return ">=";4338      }4339      else if (n == ExpressionType.LessThan) {4340        return "<";4341      }4342      else if (n == ExpressionType.LessThanOrEqual) {4343        return "<=";4344      }4345      else if (n == ExpressionType.And) {4346        return "&";42364237        if (paramExpr != null) {4238          //4239          // This is a column of our table, output just the column name4240          // Need to translate it if that column name is mapped4241          //4242          var columnName = Table.FindColumnWithPropertyName (mem.Member.Name).Name;4243          return new CompileResult { CommandText = "\"" + columnName + "\"" };4244        }4245        else {4246          object obj = null;4247          if (mem.Expression != null) {4248            var r = CompileExpr (mem.Expression, queryArgs);4249            if (r.Value == null) {4250              throw new NotSupportedException ("Member access failed to compile expression");4251            }4252            if (r.CommandText == "?") {4253              queryArgs.RemoveAt (queryArgs.Count - 1);4254            }4255            obj = r.Value;4256          }42574258          //4259          // Get the member value4260          //4261          object val = null;42624263          if (mem.Member is PropertyInfo) {4264            var m = (PropertyInfo)mem.Member;4265            val = m.GetValue (obj, null);4266          }4267          else if (mem.Member is FieldInfo) {4268            var m = (FieldInfo)mem.Member;4269            val = m.GetValue (obj);4270          }4271          else {4272            throw new NotSupportedException ("MemberExpr: " + mem.Member.GetType ());4273          }42744275          //4276          // Work special magic for enumerables4277          //4278          if (val != null && val is System.Collections.IEnumerable && !(val is string) && !(val is System.Collections.Ge4279            var sb = new System.Text.StringBuilder ();4280            sb.Append ("(");4281            var head = "";4282            foreach (var a in (System.Collections.IEnumerable)val) {4283              queryArgs.Add (a);4284              sb.Append (head);4285              sb.Append ("?");4286              head = ",";4287            }4288            sb.Append (")");4289            return new CompileResult {4290              CommandText = sb.ToString (),4291              Value = val4292            };4293          }4294          else {4295            queryArgs.Add (val);4296            return new CompileResult {4297              CommandText = "?",4298              Value = val4299            };4300          }4301        }4302      }4303      throw new NotSupportedException ("Cannot compile: " + expr.NodeType.ToString ());4304    }43054306    static object ConvertTo (object obj, Type t)4307    {4308      Type nut = Nullable.GetUnderlyingType (t);43094310      if (nut != null) {4311        if (obj == null)4312          return null;4313        return Convert.ChangeType (obj, nut);4314      }4315      else {4316        return Convert.ChangeType (obj, t);4317      }4318    }43194320    /// <summary>4321    /// Compiles a BinaryExpression where one of the parameters is null.4322    /// </summary>4323    /// <param name="expression">The expression to compile</param>4324    /// <param name="parameter">The non-null parameter</param>4325    private string CompileNullBinaryExpression (BinaryExpression expression, CompileResult parameter)4326    {4327      if (expression.NodeType == ExpressionType.Equal)4328        return "(" + parameter.CommandText + " is ?)";4329      else if (expression.NodeType == ExpressionType.NotEqual)4330        return "(" + parameter.CommandText + " is not ?)";4331      else if (expression.NodeType == ExpressionType.GreaterThan4332        || expression.NodeType == ExpressionType.GreaterThanOrEqual4333        || expression.NodeType == ExpressionType.LessThan4334        || expression.NodeType == ExpressionType.LessThanOrEqual)4335        return "(" + parameter.CommandText + " < ?)"; // always false4336      else4337        throw new NotSupportedException ("Cannot compile Null-BinaryExpression with type " + expression.NodeType.ToStrin4338    }43394340    string GetSqlName (Expression expr)4341    {4342      var n = expr.NodeType;4343      if (n == ExpressionType.GreaterThan)4344        return ">";4345      else if (n == ExpressionType.GreaterThanOrEqual) {4346        return ">=";  4347      }4348      else if (n == ExpressionType.AndAlso) {4349        return "and";4348      else if (n == ExpressionType.LessThan) {4349        return "<";  4350      }4351      else if (n == ExpressionType.Or) {4352        return "|";4351      else if (n == ExpressionType.LessThanOrEqual) {4352        return "<=";  4353      }4354      else if (n == ExpressionType.OrElse) {4355        return "or";4354      else if (n == ExpressionType.And) {4355        return "&";  4356      }4357      else if (n == ExpressionType.Equal) {4358        return "=";4357      else if (n == ExpressionType.AndAlso) {4358        return "and";  4359      }4360      else if (n == ExpressionType.NotEqual) {4361        return "!=";4360      else if (n == ExpressionType.Or) {4361        return "|";  4362      }4363      else {4364        throw new NotSupportedException ("Cannot get SQL for: " + n);4363      else if (n == ExpressionType.OrElse) {4364        return "or";  4365      }4366    }43674368    /// <summary>4369    /// Execute SELECT COUNT(*) on the query4370    /// </summary>4371    public int Count ()4372    {4373      return GenerateCommand ("count(*)").ExecuteScalar<int> ();4374    }43754376    /// <summary>4377    /// Execute SELECT COUNT(*) on the query with an additional WHERE clause.4378    /// </summary>4379    public int Count (Expression<Func<T, bool>> predExpr)4380    {4381      return Where (predExpr).Count ();4382    }43834384    public IEnumerator<T> GetEnumerator ()4385    {4386      if (!_deferred)4387        return GenerateCommand ("*").ExecuteQuery<T> ().GetEnumerator ();43884389      return GenerateCommand ("*").ExecuteDeferredQuery<T> ().GetEnumerator ();4390    }43914392    System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator ()4393    {4394      return GetEnumerator ();4395    }43964397    /// <summary>4398    /// Queries the database and returns the results as a List.4399    /// </summary>4400    public List<T> ToList ()4401    {4402      return GenerateCommand ("*").ExecuteQuery<T> ();4403    }44044405    /// <summary>4406    /// Queries the database and returns the results as an array.4407    /// </summary>4408    public T[] ToArray ()4409    {4410      return GenerateCommand ("*").ExecuteQuery<T> ().ToArray ();4411    }44124413    /// <summary>4414    /// Returns the first element of this query.4415    /// </summary>4416    public T First ()4417    {4418      var query = Take (1);4419      return query.ToList ().First ();4366      else if (n == ExpressionType.Equal) {4367        return "=";4368      }4369      else if (n == ExpressionType.NotEqual) {4370        return "!=";4371      }4372      else {4373        throw new NotSupportedException ("Cannot get SQL for: " + n);4374      }4375    }43764377    /// <summary>4378    /// Execute SELECT COUNT(*) on the query4379    /// </summary>4380    public int Count ()4381    {4382      return GenerateCommand ("count(*)").ExecuteScalar<int> ();4383    }43844385    /// <summary>4386    /// Execute SELECT COUNT(*) on the query with an additional WHERE clause.4387    /// </summary>4388    public int Count (Expression<Func<T, bool>> predExpr)4389    {4390      return Where (predExpr).Count ();4391    }43924393    public IEnumerator<T> GetEnumerator ()4394    {4395      if (!_deferred)4396        return GenerateCommand ("*").ExecuteQuery<T> ().GetEnumerator ();43974398      return GenerateCommand ("*").ExecuteDeferredQuery<T> ().GetEnumerator ();4399    }44004401    System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator ()4402    {4403      return GetEnumerator ();4404    }44054406    /// <summary>4407    /// Queries the database and returns the results as a List.4408    /// </summary>4409    public List<T> ToList ()4410    {4411      return GenerateCommand ("*").ExecuteQuery<T> ();4412    }44134414    /// <summary>4415    /// Queries the database and returns the results as an array.4416    /// </summary>4417    public T[] ToArray ()4418    {4419      return GenerateCommand ("*").ExecuteQuery<T> ().ToArray ();  4420    }  4421  4422    /// <summary>4423    /// Returns the first element of this query, or null if no element is found.4423    /// Returns the first element of this query.  4424    /// </summary>4425    public T FirstOrDefault ()4425    public T First ()  4426    {  4427      var query = Take (1);4428      return query.ToList ().FirstOrDefault ();4428      return query.ToList ().First ();  4429    }  4430  4431    /// <summary>4432    /// Returns the first element of this query that matches the predicate.4432    /// Returns the first element of this query, or null if no element is found.  4433    /// </summary>4434    public T First (Expression<Func<T, bool>> predExpr)4434    public T FirstOrDefault ()  4435    {4436      return Where (predExpr).First ();4437    }44384439    /// <summary>4440    /// Returns the first element of this query that matches the predicate, or null4441    /// if no element is found.4436      var query = Take (1);4437      return query.ToList ().FirstOrDefault ();4438    }44394440    /// <summary>4441    /// Returns the first element of this query that matches the predicate.  4442    /// </summary>4443    public T FirstOrDefault (Expression<Func<T, bool>> predExpr)4443    public T First (Expression<Func<T, bool>> predExpr)  4444    {4445      return Where (predExpr).FirstOrDefault ();4445      return Where (predExpr).First ();  4446    }4447  }44484449  public static class SQLite34450  {4451    public enum Result : int4452    {4453      OK = 0,4454      Error = 1,4455      Internal = 2,4456      Perm = 3,4457      Abort = 4,4458      Busy = 5,4459      Locked = 6,4460      NoMem = 7,4461      ReadOnly = 8,4462      Interrupt = 9,4463      IOError = 10,4464      Corrupt = 11,4465      NotFound = 12,4466      Full = 13,4467      CannotOpen = 14,4468      LockErr = 15,4469      Empty = 16,4470      SchemaChngd = 17,4471      TooBig = 18,4472      Constraint = 19,4473      Mismatch = 20,4474      Misuse = 21,4475      NotImplementedLFS = 22,4476      AccessDenied = 23,4477      Format = 24,4478      Range = 25,4479      NonDBFile = 26,4480      Notice = 27,4481      Warning = 28,4482      Row = 100,4483      Done = 1014484    }44854486    public enum ExtendedResult : int4487    {4488      IOErrorRead = (Result.IOError | (1 << 8)),4489      IOErrorShortRead = (Result.IOError | (2 << 8)),4490      IOErrorWrite = (Result.IOError | (3 << 8)),4491      IOErrorFsync = (Result.IOError | (4 << 8)),4492      IOErrorDirFSync = (Result.IOError | (5 << 8)),4493      IOErrorTruncate = (Result.IOError | (6 << 8)),4494      IOErrorFStat = (Result.IOError | (7 << 8)),4495      IOErrorUnlock = (Result.IOError | (8 << 8)),4496      IOErrorRdlock = (Result.IOError | (9 << 8)),4497      IOErrorDelete = (Result.IOError | (10 << 8)),4498      IOErrorBlocked = (Result.IOError | (11 << 8)),4499      IOErrorNoMem = (Result.IOError | (12 << 8)),4500      IOErrorAccess = (Result.IOError | (13 << 8)),4501      IOErrorCheckReservedLock = (Result.IOError | (14 << 8)),4502      IOErrorLock = (Result.IOError | (15 << 8)),4503      IOErrorClose = (Result.IOError | (16 << 8)),4504      IOErrorDirClose = (Result.IOError | (17 << 8)),4505      IOErrorSHMOpen = (Result.IOError | (18 << 8)),4506      IOErrorSHMSize = (Result.IOError | (19 << 8)),4507      IOErrorSHMLock = (Result.IOError | (20 << 8)),4508      IOErrorSHMMap = (Result.IOError | (21 << 8)),4509      IOErrorSeek = (Result.IOError | (22 << 8)),4510      IOErrorDeleteNoEnt = (Result.IOError | (23 << 8)),4511      IOErrorMMap = (Result.IOError | (24 << 8)),4512      LockedSharedcache = (Result.Locked | (1 << 8)),4513      BusyRecovery = (Result.Busy | (1 << 8)),4514      CannottOpenNoTempDir = (Result.CannotOpen | (1 << 8)),4515      CannotOpenIsDir = (Result.CannotOpen | (2 << 8)),4516      CannotOpenFullPath = (Result.CannotOpen | (3 << 8)),4517      CorruptVTab = (Result.Corrupt | (1 << 8)),4518      ReadonlyRecovery = (Result.ReadOnly | (1 << 8)),4519      ReadonlyCannotLock = (Result.ReadOnly | (2 << 8)),4520      ReadonlyRollback = (Result.ReadOnly | (3 << 8)),4521      AbortRollback = (Result.Abort | (2 << 8)),4522      ConstraintCheck = (Result.Constraint | (1 << 8)),4523      ConstraintCommitHook = (Result.Constraint | (2 << 8)),4524      ConstraintForeignKey = (Result.Constraint | (3 << 8)),4525      ConstraintFunction = (Result.Constraint | (4 << 8)),4526      ConstraintNotNull = (Result.Constraint | (5 << 8)),4527      ConstraintPrimaryKey = (Result.Constraint | (6 << 8)),4528      ConstraintTrigger = (Result.Constraint | (7 << 8)),4529      ConstraintUnique = (Result.Constraint | (8 << 8)),4530      ConstraintVTab = (Result.Constraint | (9 << 8)),4531      NoticeRecoverWAL = (Result.Notice | (1 << 8)),4532      NoticeRecoverRollback = (Result.Notice | (2 << 8))4533    }453445354536    public enum ConfigOption : int4537    {4538      SingleThread = 1,4539      MultiThread = 2,4540      Serialized = 34541    }45424543    const string LibraryPath = "sqlite3";44474448    /// <summary>4449    /// Returns the first element of this query that matches the predicate, or null4450    /// if no element is found.4451    /// </summary>4452    public T FirstOrDefault (Expression<Func<T, bool>> predExpr)4453    {4454      return Where (predExpr).FirstOrDefault ();4455    }4456  }44574458  public static class SQLite34459  {4460    public enum Result : int4461    {4462      OK = 0,4463      Error = 1,4464      Internal = 2,4465      Perm = 3,4466      Abort = 4,4467      Busy = 5,4468      Locked = 6,4469      NoMem = 7,4470      ReadOnly = 8,4471      Interrupt = 9,4472      IOError = 10,4473      Corrupt = 11,4474      NotFound = 12,4475      Full = 13,4476      CannotOpen = 14,4477      LockErr = 15,4478      Empty = 16,4479      SchemaChngd = 17,4480      TooBig = 18,4481      Constraint = 19,4482      Mismatch = 20,4483      Misuse = 21,4484      NotImplementedLFS = 22,4485      AccessDenied = 23,4486      Format = 24,4487      Range = 25,4488      NonDBFile = 26,4489      Notice = 27,4490      Warning = 28,4491      Row = 100,4492      Done = 1014493    }44944495    public enum ExtendedResult : int4496    {4497      IOErrorRead = (Result.IOError | (1 << 8)),4498      IOErrorShortRead = (Result.IOError | (2 << 8)),4499      IOErrorWrite = (Result.IOError | (3 << 8)),4500      IOErrorFsync = (Result.IOError | (4 << 8)),4501      IOErrorDirFSync = (Result.IOError | (5 << 8)),4502      IOErrorTruncate = (Result.IOError | (6 << 8)),4503      IOErrorFStat = (Result.IOError | (7 << 8)),4504      IOErrorUnlock = (Result.IOError | (8 << 8)),4505      IOErrorRdlock = (Result.IOError | (9 << 8)),4506      IOErrorDelete = (Result.IOError | (10 << 8)),4507      IOErrorBlocked = (Result.IOError | (11 << 8)),4508      IOErrorNoMem = (Result.IOError | (12 << 8)),4509      IOErrorAccess = (Result.IOError | (13 << 8)),4510      IOErrorCheckReservedLock = (Result.IOError | (14 << 8)),4511      IOErrorLock = (Result.IOError | (15 << 8)),4512      IOErrorClose = (Result.IOError | (16 << 8)),4513      IOErrorDirClose = (Result.IOError | (17 << 8)),4514      IOErrorSHMOpen = (Result.IOError | (18 << 8)),4515      IOErrorSHMSize = (Result.IOError | (19 << 8)),4516      IOErrorSHMLock = (Result.IOError | (20 << 8)),4517      IOErrorSHMMap = (Result.IOError | (21 << 8)),4518      IOErrorSeek = (Result.IOError | (22 << 8)),4519      IOErrorDeleteNoEnt = (Result.IOError | (23 << 8)),4520      IOErrorMMap = (Result.IOError | (24 << 8)),4521      LockedSharedcache = (Result.Locked | (1 << 8)),4522      BusyRecovery = (Result.Busy | (1 << 8)),4523      CannottOpenNoTempDir = (Result.CannotOpen | (1 << 8)),4524      CannotOpenIsDir = (Result.CannotOpen | (2 << 8)),4525      CannotOpenFullPath = (Result.CannotOpen | (3 << 8)),4526      CorruptVTab = (Result.Corrupt | (1 << 8)),4527      ReadonlyRecovery = (Result.ReadOnly | (1 << 8)),4528      ReadonlyCannotLock = (Result.ReadOnly | (2 << 8)),4529      ReadonlyRollback = (Result.ReadOnly | (3 << 8)),4530      AbortRollback = (Result.Abort | (2 << 8)),4531      ConstraintCheck = (Result.Constraint | (1 << 8)),4532      ConstraintCommitHook = (Result.Constraint | (2 << 8)),4533      ConstraintForeignKey = (Result.Constraint | (3 << 8)),4534      ConstraintFunction = (Result.Constraint | (4 << 8)),4535      ConstraintNotNull = (Result.Constraint | (5 << 8)),4536      ConstraintPrimaryKey = (Result.Constraint | (6 << 8)),4537      ConstraintTrigger = (Result.Constraint | (7 << 8)),4538      ConstraintUnique = (Result.Constraint | (8 << 8)),4539      ConstraintVTab = (Result.Constraint | (9 << 8)),4540      NoticeRecoverWAL = (Result.Notice | (1 << 8)),4541      NoticeRecoverRollback = (Result.Notice | (2 << 8))4542    }4543  45444545#if !USE_CSHARP_SQLITE && !USE_WP8_NATIVE_SQLITE && !USE_SQLITEPCL_RAW4546    [DllImport(LibraryPath, EntryPoint = "sqlite3_threadsafe", CallingConvention=CallingConvention.Cdecl)]4547    public static extern int Threadsafe ();45484549    [DllImport(LibraryPath, EntryPoint = "sqlite3_open", CallingConvention=CallingConvention.Cdecl)]4550    public static extern Result Open ([MarshalAs(UnmanagedType.LPStr)] string filename, out IntPtr db);4545    public enum ConfigOption : int4546    {4547      SingleThread = 1,4548      MultiThread = 2,4549      Serialized = 34550    }  45514552    [DllImport(LibraryPath, EntryPoint = "sqlite3_open_v2", CallingConvention=CallingConvention.Cdecl)]4553    public static extern Result Open ([MarshalAs(UnmanagedType.LPStr)] string filename, out IntPtr db, int flags, [Marsh45544555    [DllImport(LibraryPath, EntryPoint = "sqlite3_open_v2", CallingConvention = CallingConvention.Cdecl)]4556    public static extern Result Open(byte[] filename, out IntPtr db, int flags, [MarshalAs (UnmanagedType.LPStr)] string4552    const string LibraryPath = "sqlite3";45534554#if !USE_CSHARP_SQLITE && !USE_WP8_NATIVE_SQLITE && !USE_SQLITEPCL_RAW4555    [DllImport(LibraryPath, EntryPoint = "sqlite3_threadsafe", CallingConvention=CallingConvention.Cdecl)]4556    public static extern int Threadsafe ();  45574558    [DllImport(LibraryPath, EntryPoint = "sqlite3_open16", CallingConvention = CallingConvention.Cdecl)]4559    public static extern Result Open16([MarshalAs(UnmanagedType.LPWStr)] string filename, out IntPtr db);4558    [DllImport(LibraryPath, EntryPoint = "sqlite3_open", CallingConvention=CallingConvention.Cdecl)]4559    public static extern Result Open ([MarshalAs(UnmanagedType.LPStr)] string filename, out IntPtr db);  45604561    [DllImport(LibraryPath, EntryPoint = "sqlite3_enable_load_extension", CallingConvention=CallingConvention.Cdecl)]4562    public static extern Result EnableLoadExtension (IntPtr db, int onoff);4561    [DllImport(LibraryPath, EntryPoint = "sqlite3_open_v2", CallingConvention=CallingConvention.Cdecl)]4562    public static extern Result Open ([MarshalAs(UnmanagedType.LPStr)] string filename, out IntPtr db, int flags, [Marsh  45634564    [DllImport(LibraryPath, EntryPoint = "sqlite3_close", CallingConvention=CallingConvention.Cdecl)]4565    public static extern Result Close (IntPtr db);4564    [DllImport(LibraryPath, EntryPoint = "sqlite3_open_v2", CallingConvention = CallingConvention.Cdecl)]4565    public static extern Result Open(byte[] filename, out IntPtr db, int flags, [MarshalAs (UnmanagedType.LPStr)] string  45664567    [DllImport(LibraryPath, EntryPoint = "sqlite3_close_v2", CallingConvention = CallingConvention.Cdecl)]4568    public static extern Result Close2(IntPtr db);4567    [DllImport(LibraryPath, EntryPoint = "sqlite3_open16", CallingConvention = CallingConvention.Cdecl)]4568    public static extern Result Open16([MarshalAs(UnmanagedType.LPWStr)] string filename, out IntPtr db);  45694570    [DllImport(LibraryPath, EntryPoint = "sqlite3_initialize", CallingConvention=CallingConvention.Cdecl)]4571    public static extern Result Initialize();4570    [DllImport(LibraryPath, EntryPoint = "sqlite3_enable_load_extension", CallingConvention=CallingConvention.Cdecl)]4571    public static extern Result EnableLoadExtension (IntPtr db, int onoff);  45724573    [DllImport(LibraryPath, EntryPoint = "sqlite3_shutdown", CallingConvention=CallingConvention.Cdecl)]4574    public static extern Result Shutdown();4573    [DllImport(LibraryPath, EntryPoint = "sqlite3_close", CallingConvention=CallingConvention.Cdecl)]4574    public static extern Result Close (IntPtr db);  45754576    [DllImport(LibraryPath, EntryPoint = "sqlite3_config", CallingConvention=CallingConvention.Cdecl)]4577    public static extern Result Config (ConfigOption option);4576    [DllImport(LibraryPath, EntryPoint = "sqlite3_close_v2", CallingConvention = CallingConvention.Cdecl)]4577    public static extern Result Close2(IntPtr db);  45784579    [DllImport(LibraryPath, EntryPoint = "sqlite3_win32_set_directory", CallingConvention=CallingConvention.Cdecl, CharS4580    public static extern int SetDirectory (uint directoryType, string directoryPath);4579    [DllImport(LibraryPath, EntryPoint = "sqlite3_initialize", CallingConvention=CallingConvention.Cdecl)]4580    public static extern Result Initialize();  45814582    [DllImport(LibraryPath, EntryPoint = "sqlite3_busy_timeout", CallingConvention=CallingConvention.Cdecl)]4583    public static extern Result BusyTimeout (IntPtr db, int milliseconds);4582    [DllImport(LibraryPath, EntryPoint = "sqlite3_shutdown", CallingConvention=CallingConvention.Cdecl)]4583    public static extern Result Shutdown();  45844585    [DllImport(LibraryPath, EntryPoint = "sqlite3_changes", CallingConvention=CallingConvention.Cdecl)]4586    public static extern int Changes (IntPtr db);4585    [DllImport(LibraryPath, EntryPoint = "sqlite3_config", CallingConvention=CallingConvention.Cdecl)]4586    public static extern Result Config (ConfigOption option);  45874588    [DllImport(LibraryPath, EntryPoint = "sqlite3_prepare_v2", CallingConvention=CallingConvention.Cdecl)]4589    public static extern Result Prepare2 (IntPtr db, [MarshalAs(UnmanagedType.LPStr)] string sql, int numBytes, out IntP4588    [DllImport(LibraryPath, EntryPoint = "sqlite3_win32_set_directory", CallingConvention=CallingConvention.Cdecl, CharS4589    public static extern int SetDirectory (uint directoryType, string directoryPath);  45904591#if NETFX_CORE4592    [DllImport (LibraryPath, EntryPoint = "sqlite3_prepare_v2", CallingConvention = CallingConvention.Cdecl)]4593    public static extern Result Prepare2 (IntPtr db, byte[] queryBytes, int numBytes, out IntPtr stmt, IntPtr pzTail);4594#endif45954596    public static IntPtr Prepare2 (IntPtr db, string query)4597    {4598      IntPtr stmt;4599#if NETFX_CORE4600            byte[] queryBytes = System.Text.UTF8Encoding.UTF8.GetBytes (query);4601            var r = Prepare2 (db, queryBytes, queryBytes.Length, out stmt, IntPtr.Zero);4602#else4603            var r = Prepare2 (db, query, System.Text.UTF8Encoding.UTF8.GetByteCount (query), out stmt, IntPtr.Zero);4604#endif4605      if (r != Result.OK) {4606        throw SQLiteException.New (r, GetErrmsg (db));4607      }4608      return stmt;4609    }46104611    [DllImport(LibraryPath, EntryPoint = "sqlite3_step", CallingConvention=CallingConvention.Cdecl)]4612    public static extern Result Step (IntPtr stmt);46134614    [DllImport(LibraryPath, EntryPoint = "sqlite3_reset", CallingConvention=CallingConvention.Cdecl)]4615    public static extern Result Reset (IntPtr stmt);46164617    [DllImport(LibraryPath, EntryPoint = "sqlite3_finalize", CallingConvention=CallingConvention.Cdecl)]4618    public static extern Result Finalize (IntPtr stmt);4591    [DllImport(LibraryPath, EntryPoint = "sqlite3_busy_timeout", CallingConvention=CallingConvention.Cdecl)]4592    public static extern Result BusyTimeout (IntPtr db, int milliseconds);45934594    [DllImport(LibraryPath, EntryPoint = "sqlite3_changes", CallingConvention=CallingConvention.Cdecl)]4595    public static extern int Changes (IntPtr db);45964597    [DllImport(LibraryPath, EntryPoint = "sqlite3_prepare_v2", CallingConvention=CallingConvention.Cdecl)]4598    public static extern Result Prepare2 (IntPtr db, [MarshalAs(UnmanagedType.LPStr)] string sql, int numBytes, out IntP45994600#if NETFX_CORE4601    [DllImport (LibraryPath, EntryPoint = "sqlite3_prepare_v2", CallingConvention = CallingConvention.Cdecl)]4602    public static extern Result Prepare2 (IntPtr db, byte[] queryBytes, int numBytes, out IntPtr stmt, IntPtr pzTail);4603#endif46044605    public static IntPtr Prepare2 (IntPtr db, string query)4606    {4607      IntPtr stmt;4608#if NETFX_CORE4609            byte[] queryBytes = System.Text.UTF8Encoding.UTF8.GetBytes (query);4610            var r = Prepare2 (db, queryBytes, queryBytes.Length, out stmt, IntPtr.Zero);4611#else4612            var r = Prepare2 (db, query, System.Text.UTF8Encoding.UTF8.GetByteCount (query), out stmt, IntPtr.Zero);4613#endif4614      if (r != Result.OK) {4615        throw SQLiteException.New (r, GetErrmsg (db));4616      }4617      return stmt;4618    }  46194620    [DllImport(LibraryPath, EntryPoint = "sqlite3_last_insert_rowid", CallingConvention=CallingConvention.Cdecl)]4621    public static extern long LastInsertRowid (IntPtr db);4620    [DllImport(LibraryPath, EntryPoint = "sqlite3_step", CallingConvention=CallingConvention.Cdecl)]4621    public static extern Result Step (IntPtr stmt);  46224623    [DllImport(LibraryPath, EntryPoint = "sqlite3_errmsg16", CallingConvention=CallingConvention.Cdecl)]4624    public static extern IntPtr Errmsg (IntPtr db);4623    [DllImport(LibraryPath, EntryPoint = "sqlite3_reset", CallingConvention=CallingConvention.Cdecl)]4624    public static extern Result Reset (IntPtr stmt);  46254626    public static string GetErrmsg (IntPtr db)4627    {4628      return Marshal.PtrToStringUni (Errmsg (db));4629    }46304631    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_parameter_index", CallingConvention=CallingConvention.Cdecl)]4632    public static extern int BindParameterIndex (IntPtr stmt, [MarshalAs(UnmanagedType.LPStr)] string name);46334634    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_null", CallingConvention=CallingConvention.Cdecl)]4635    public static extern int BindNull (IntPtr stmt, int index);46364637    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_int", CallingConvention=CallingConvention.Cdecl)]4638    public static extern int BindInt (IntPtr stmt, int index, int val);4626    [DllImport(LibraryPath, EntryPoint = "sqlite3_finalize", CallingConvention=CallingConvention.Cdecl)]4627    public static extern Result Finalize (IntPtr stmt);46284629    [DllImport(LibraryPath, EntryPoint = "sqlite3_last_insert_rowid", CallingConvention=CallingConvention.Cdecl)]4630    public static extern long LastInsertRowid (IntPtr db);46314632    [DllImport(LibraryPath, EntryPoint = "sqlite3_errmsg16", CallingConvention=CallingConvention.Cdecl)]4633    public static extern IntPtr Errmsg (IntPtr db);46344635    public static string GetErrmsg (IntPtr db)4636    {4637      return Marshal.PtrToStringUni (Errmsg (db));4638    }  46394640    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_int64", CallingConvention=CallingConvention.Cdecl)]4641    public static extern int BindInt64 (IntPtr stmt, int index, long val);4640    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_parameter_index", CallingConvention=CallingConvention.Cdecl)]4641    public static extern int BindParameterIndex (IntPtr stmt, [MarshalAs(UnmanagedType.LPStr)] string name);  46424643    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_double", CallingConvention=CallingConvention.Cdecl)]4644    public static extern int BindDouble (IntPtr stmt, int index, double val);4643    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_null", CallingConvention=CallingConvention.Cdecl)]4644    public static extern int BindNull (IntPtr stmt, int index);  46454646    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_text16", CallingConvention=CallingConvention.Cdecl, CharSet = Cha4647    public static extern int BindText (IntPtr stmt, int index, [MarshalAs(UnmanagedType.LPWStr)] string val, int n, IntP4646    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_int", CallingConvention=CallingConvention.Cdecl)]4647    public static extern int BindInt (IntPtr stmt, int index, int val);  46484649    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_blob", CallingConvention=CallingConvention.Cdecl)]4650    public static extern int BindBlob (IntPtr stmt, int index, byte[] val, int n, IntPtr free);4649    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_int64", CallingConvention=CallingConvention.Cdecl)]4650    public static extern int BindInt64 (IntPtr stmt, int index, long val);  46514652    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_count", CallingConvention=CallingConvention.Cdecl)]4653    public static extern int ColumnCount (IntPtr stmt);4652    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_double", CallingConvention=CallingConvention.Cdecl)]4653    public static extern int BindDouble (IntPtr stmt, int index, double val);  46544655    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_name", CallingConvention=CallingConvention.Cdecl)]4656    public static extern IntPtr ColumnName (IntPtr stmt, int index);4655    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_text16", CallingConvention=CallingConvention.Cdecl, CharSet = Cha4656    public static extern int BindText (IntPtr stmt, int index, [MarshalAs(UnmanagedType.LPWStr)] string val, int n, IntP  46574658    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_name16", CallingConvention=CallingConvention.Cdecl)]4659    static extern IntPtr ColumnName16Internal (IntPtr stmt, int index);4660    public static string ColumnName16(IntPtr stmt, int index)4661    {4662      return Marshal.PtrToStringUni(ColumnName16Internal(stmt, index));4663    }46644665    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_type", CallingConvention=CallingConvention.Cdecl)]4666    public static extern ColType ColumnType (IntPtr stmt, int index);46674668    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_int", CallingConvention=CallingConvention.Cdecl)]4669    public static extern int ColumnInt (IntPtr stmt, int index);46704671    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_int64", CallingConvention=CallingConvention.Cdecl)]4672    public static extern long ColumnInt64 (IntPtr stmt, int index);4658    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_blob", CallingConvention=CallingConvention.Cdecl)]4659    public static extern int BindBlob (IntPtr stmt, int index, byte[] val, int n, IntPtr free);46604661    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_count", CallingConvention=CallingConvention.Cdecl)]4662    public static extern int ColumnCount (IntPtr stmt);46634664    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_name", CallingConvention=CallingConvention.Cdecl)]4665    public static extern IntPtr ColumnName (IntPtr stmt, int index);46664667    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_name16", CallingConvention=CallingConvention.Cdecl)]4668    static extern IntPtr ColumnName16Internal (IntPtr stmt, int index);4669    public static string ColumnName16(IntPtr stmt, int index)4670    {4671      return Marshal.PtrToStringUni(ColumnName16Internal(stmt, index));4672    }  46734674    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_double", CallingConvention=CallingConvention.Cdecl)]4675    public static extern double ColumnDouble (IntPtr stmt, int index);4674    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_type", CallingConvention=CallingConvention.Cdecl)]4675    public static extern ColType ColumnType (IntPtr stmt, int index);  46764677    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_text", CallingConvention=CallingConvention.Cdecl)]4678    public static extern IntPtr ColumnText (IntPtr stmt, int index);4677    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_int", CallingConvention=CallingConvention.Cdecl)]4678    public static extern int ColumnInt (IntPtr stmt, int index);  46794680    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_text16", CallingConvention=CallingConvention.Cdecl)]4681    public static extern IntPtr ColumnText16 (IntPtr stmt, int index);4680    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_int64", CallingConvention=CallingConvention.Cdecl)]4681    public static extern long ColumnInt64 (IntPtr stmt, int index);  46824683    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_blob", CallingConvention=CallingConvention.Cdecl)]4684    public static extern IntPtr ColumnBlob (IntPtr stmt, int index);4683    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_double", CallingConvention=CallingConvention.Cdecl)]4684    public static extern double ColumnDouble (IntPtr stmt, int index);  46854686    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_bytes", CallingConvention=CallingConvention.Cdecl)]4687    public static extern int ColumnBytes (IntPtr stmt, int index);4686    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_text", CallingConvention=CallingConvention.Cdecl)]4687    public static extern IntPtr ColumnText (IntPtr stmt, int index);  46884689    public static string ColumnString (IntPtr stmt, int index)4690    {4691      return Marshal.PtrToStringUni (SQLite3.ColumnText16 (stmt, index));4692    }46934694    public static byte[] ColumnByteArray (IntPtr stmt, int index)4695    {4696      int length = ColumnBytes (stmt, index);4697      var result = new byte[length];4698      if (length > 0)4699        Marshal.Copy (ColumnBlob (stmt, index), result, 0, length);4700      return result;4689    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_text16", CallingConvention=CallingConvention.Cdecl)]4690    public static extern IntPtr ColumnText16 (IntPtr stmt, int index);46914692    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_blob", CallingConvention=CallingConvention.Cdecl)]4693    public static extern IntPtr ColumnBlob (IntPtr stmt, int index);46944695    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_bytes", CallingConvention=CallingConvention.Cdecl)]4696    public static extern int ColumnBytes (IntPtr stmt, int index);46974698    public static string ColumnString (IntPtr stmt, int index)4699    {4700      return Marshal.PtrToStringUni (SQLite3.ColumnText16 (stmt, index));  4701    }  47024703    [DllImport (LibraryPath, EntryPoint = "sqlite3_errcode", CallingConvention = CallingConvention.Cdecl)]4704    public static extern Result GetResult (Sqlite3DatabaseHandle db);47054706    [DllImport (LibraryPath, EntryPoint = "sqlite3_extended_errcode", CallingConvention = CallingConvention.Cdecl)]4707    public static extern ExtendedResult ExtendedErrCode (IntPtr db);47084709    [DllImport (LibraryPath, EntryPoint = "sqlite3_libversion_number", CallingConvention = CallingConvention.Cdecl)]4710    public static extern int LibVersionNumber ();4703    public static byte[] ColumnByteArray (IntPtr stmt, int index)4704    {4705      int length = ColumnBytes (stmt, index);4706      var result = new byte[length];4707      if (length > 0)4708        Marshal.Copy (ColumnBlob (stmt, index), result, 0, length);4709      return result;4710    }  47114712    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_init", CallingConvention = CallingConvention.Cdecl)]4713    public static extern Sqlite3BackupHandle BackupInit (Sqlite3DatabaseHandle destDb, [MarshalAs (UnmanagedType.LPStr)]4712    [DllImport (LibraryPath, EntryPoint = "sqlite3_errcode", CallingConvention = CallingConvention.Cdecl)]4713    public static extern Result GetResult (Sqlite3DatabaseHandle db);  47144715    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_step", CallingConvention = CallingConvention.Cdecl)]4716    public static extern Result BackupStep (Sqlite3BackupHandle backup, int numPages);4715    [DllImport (LibraryPath, EntryPoint = "sqlite3_extended_errcode", CallingConvention = CallingConvention.Cdecl)]4716    public static extern ExtendedResult ExtendedErrCode (IntPtr db);  47174718    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_finish", CallingConvention = CallingConvention.Cdecl)]4719    public static extern Result BackupFinish (Sqlite3BackupHandle backup);4720#else4721    public static Result Open (string filename, out Sqlite3DatabaseHandle db)4722    {4723      return (Result)Sqlite3.sqlite3_open (filename, out db);4724    }47254726    public static Result Open (string filename, out Sqlite3DatabaseHandle db, int flags, string vfsName)4727    {4728#if USE_WP8_NATIVE_SQLITE4729      return (Result)Sqlite3.sqlite3_open_v2(filename, out db, flags, vfsName ?? "");4730#else4731      return (Result)Sqlite3.sqlite3_open_v2 (filename, out db, flags, vfsName);4732#endif4718    [DllImport (LibraryPath, EntryPoint = "sqlite3_libversion_number", CallingConvention = CallingConvention.Cdecl)]4719    public static extern int LibVersionNumber ();47204721    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_init", CallingConvention = CallingConvention.Cdecl)]4722    public static extern Sqlite3BackupHandle BackupInit (Sqlite3DatabaseHandle destDb, [MarshalAs (UnmanagedType.LPStr)]47234724    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_step", CallingConvention = CallingConvention.Cdecl)]4725    public static extern Result BackupStep (Sqlite3BackupHandle backup, int numPages);47264727    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_finish", CallingConvention = CallingConvention.Cdecl)]4728    public static extern Result BackupFinish (Sqlite3BackupHandle backup);4729#else4730    public static Result Open (string filename, out Sqlite3DatabaseHandle db)4731    {4732      return (Result)Sqlite3.sqlite3_open (filename, out db);  4733    }  47344735    public static Result Close (Sqlite3DatabaseHandle db)4735    public static Result Open (string filename, out Sqlite3DatabaseHandle db, int flags, string vfsName)  4736    {4737      return (Result)Sqlite3.sqlite3_close (db);4738    }47394740    public static Result Close2 (Sqlite3DatabaseHandle db)4741    {4742      return (Result)Sqlite3.sqlite3_close_v2 (db);4743    }47444745    public static Result BusyTimeout (Sqlite3DatabaseHandle db, int milliseconds)4746    {4747      return (Result)Sqlite3.sqlite3_busy_timeout (db, milliseconds);4748    }47494750    public static int Changes (Sqlite3DatabaseHandle db)4751    {4752      return Sqlite3.sqlite3_changes (db);4753    }47544755    public static Sqlite3Statement Prepare2 (Sqlite3DatabaseHandle db, string query)4756    {4757      Sqlite3Statement stmt = default (Sqlite3Statement);4758#if USE_WP8_NATIVE_SQLITE || USE_SQLITEPCL_RAW4759      var r = Sqlite3.sqlite3_prepare_v2 (db, query, out stmt);4760#else4761      stmt = new Sqlite3Statement();4762      var r = Sqlite3.sqlite3_prepare_v2(db, query, -1, ref stmt, 0);4763#endif4764      if (r != 0) {4765        throw SQLiteException.New ((Result)r, GetErrmsg (db));4766      }4767      return stmt;4768    }47694770    public static Result Step (Sqlite3Statement stmt)4771    {4772      return (Result)Sqlite3.sqlite3_step (stmt);4773    }47744775    public static Result Reset (Sqlite3Statement stmt)4776    {4777      return (Result)Sqlite3.sqlite3_reset (stmt);4778    }47794780    public static Result Finalize (Sqlite3Statement stmt)4781    {4782      return (Result)Sqlite3.sqlite3_finalize (stmt);4783    }47844785    public static long LastInsertRowid (Sqlite3DatabaseHandle db)4786    {4787      return Sqlite3.sqlite3_last_insert_rowid (db);4788    }47894790    public static string GetErrmsg (Sqlite3DatabaseHandle db)4791    {4792      return Sqlite3.sqlite3_errmsg (db).utf8_to_string ();4793    }47944795    public static int BindParameterIndex (Sqlite3Statement stmt, string name)4796    {4797      return Sqlite3.sqlite3_bind_parameter_index (stmt, name);4798    }47994800    public static int BindNull (Sqlite3Statement stmt, int index)4801    {4802      return Sqlite3.sqlite3_bind_null (stmt, index);4803    }48044805    public static int BindInt (Sqlite3Statement stmt, int index, int val)4806    {4807      return Sqlite3.sqlite3_bind_int (stmt, index, val);4808    }48094810    public static int BindInt64 (Sqlite3Statement stmt, int index, long val)4811    {4812      return Sqlite3.sqlite3_bind_int64 (stmt, index, val);4813    }48144815    public static int BindDouble (Sqlite3Statement stmt, int index, double val)4816    {4817      return Sqlite3.sqlite3_bind_double (stmt, index, val);4818    }48194820    public static int BindText (Sqlite3Statement stmt, int index, string val, int n, IntPtr free)4821    {4822#if USE_WP8_NATIVE_SQLITE4823      return Sqlite3.sqlite3_bind_text(stmt, index, val, n);4824#elif USE_SQLITEPCL_RAW4825      return Sqlite3.sqlite3_bind_text (stmt, index, val);4826#else4827      return Sqlite3.sqlite3_bind_text(stmt, index, val, n, null);4828#endif4829    }48304831    public static int BindBlob (Sqlite3Statement stmt, int index, byte[] val, int n, IntPtr free)4832    {4833#if USE_WP8_NATIVE_SQLITE4834      return Sqlite3.sqlite3_bind_blob(stmt, index, val, n);4835#elif USE_SQLITEPCL_RAW4836      return Sqlite3.sqlite3_bind_blob (stmt, index, val);4837#else4838      return Sqlite3.sqlite3_bind_blob(stmt, index, val, n, null);4839#endif4840    }48414842    public static int ColumnCount (Sqlite3Statement stmt)4843    {4844      return Sqlite3.sqlite3_column_count (stmt);4845    }48464847    public static string ColumnName (Sqlite3Statement stmt, int index)4848    {4849      return Sqlite3.sqlite3_column_name (stmt, index).utf8_to_string ();4850    }48514852    public static string ColumnName16 (Sqlite3Statement stmt, int index)4853    {4854      return Sqlite3.sqlite3_column_name (stmt, index).utf8_to_string ();4855    }48564857    public static ColType ColumnType (Sqlite3Statement stmt, int index)4858    {4859      return (ColType)Sqlite3.sqlite3_column_type (stmt, index);4860    }48614862    public static int ColumnInt (Sqlite3Statement stmt, int index)4863    {4864      return Sqlite3.sqlite3_column_int (stmt, index);4865    }48664867    public static long ColumnInt64 (Sqlite3Statement stmt, int index)4868    {4869      return Sqlite3.sqlite3_column_int64 (stmt, index);4870    }48714872    public static double ColumnDouble (Sqlite3Statement stmt, int index)4873    {4874      return Sqlite3.sqlite3_column_double (stmt, index);4875    }48764877    public static string ColumnText (Sqlite3Statement stmt, int index)4878    {4879      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();4880    }48814882    public static string ColumnText16 (Sqlite3Statement stmt, int index)4883    {4884      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();4885    }48864887    public static byte[] ColumnBlob (Sqlite3Statement stmt, int index)4888    {4889      return Sqlite3.sqlite3_column_blob (stmt, index).ToArray ();4890    }48914892    public static int ColumnBytes (Sqlite3Statement stmt, int index)4893    {4894      return Sqlite3.sqlite3_column_bytes (stmt, index);4895    }48964897    public static string ColumnString (Sqlite3Statement stmt, int index)4898    {4899      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();4900    }49014902    public static byte[] ColumnByteArray (Sqlite3Statement stmt, int index)4903    {4904      int length = ColumnBytes (stmt, index);4905      if (length > 0) {4906        return ColumnBlob (stmt, index);4907      }4908      return new byte[0];4737#if USE_WP8_NATIVE_SQLITE4738      return (Result)Sqlite3.sqlite3_open_v2(filename, out db, flags, vfsName ?? "");4739#else4740      return (Result)Sqlite3.sqlite3_open_v2 (filename, out db, flags, vfsName);4741#endif4742    }47434744    public static Result Close (Sqlite3DatabaseHandle db)4745    {4746      return (Result)Sqlite3.sqlite3_close (db);4747    }47484749    public static Result Close2 (Sqlite3DatabaseHandle db)4750    {4751      return (Result)Sqlite3.sqlite3_close_v2 (db);4752    }47534754    public static Result BusyTimeout (Sqlite3DatabaseHandle db, int milliseconds)4755    {4756      return (Result)Sqlite3.sqlite3_busy_timeout (db, milliseconds);4757    }47584759    public static int Changes (Sqlite3DatabaseHandle db)4760    {4761      return Sqlite3.sqlite3_changes (db);4762    }47634764    public static Sqlite3Statement Prepare2 (Sqlite3DatabaseHandle db, string query)4765    {4766      Sqlite3Statement stmt = default (Sqlite3Statement);4767#if USE_WP8_NATIVE_SQLITE || USE_SQLITEPCL_RAW4768      var r = Sqlite3.sqlite3_prepare_v2 (db, query, out stmt);4769#else4770      stmt = new Sqlite3Statement();4771      var r = Sqlite3.sqlite3_prepare_v2(db, query, -1, ref stmt, 0);4772#endif4773      if (r != 0) {4774        throw SQLiteException.New ((Result)r, GetErrmsg (db));4775      }4776      return stmt;4777    }47784779    public static Result Step (Sqlite3Statement stmt)4780    {4781      return (Result)Sqlite3.sqlite3_step (stmt);4782    }47834784    public static Result Reset (Sqlite3Statement stmt)4785    {4786      return (Result)Sqlite3.sqlite3_reset (stmt);4787    }47884789    public static Result Finalize (Sqlite3Statement stmt)4790    {4791      return (Result)Sqlite3.sqlite3_finalize (stmt);4792    }47934794    public static long LastInsertRowid (Sqlite3DatabaseHandle db)4795    {4796      return Sqlite3.sqlite3_last_insert_rowid (db);4797    }47984799    public static string GetErrmsg (Sqlite3DatabaseHandle db)4800    {4801      return Sqlite3.sqlite3_errmsg (db).utf8_to_string ();4802    }48034804    public static int BindParameterIndex (Sqlite3Statement stmt, string name)4805    {4806      return Sqlite3.sqlite3_bind_parameter_index (stmt, name);4807    }48084809    public static int BindNull (Sqlite3Statement stmt, int index)4810    {4811      return Sqlite3.sqlite3_bind_null (stmt, index);4812    }48134814    public static int BindInt (Sqlite3Statement stmt, int index, int val)4815    {4816      return Sqlite3.sqlite3_bind_int (stmt, index, val);4817    }48184819    public static int BindInt64 (Sqlite3Statement stmt, int index, long val)4820    {4821      return Sqlite3.sqlite3_bind_int64 (stmt, index, val);4822    }48234824    public static int BindDouble (Sqlite3Statement stmt, int index, double val)4825    {4826      return Sqlite3.sqlite3_bind_double (stmt, index, val);4827    }48284829    public static int BindText (Sqlite3Statement stmt, int index, string val, int n, IntPtr free)4830    {4831#if USE_WP8_NATIVE_SQLITE4832      return Sqlite3.sqlite3_bind_text(stmt, index, val, n);4833#elif USE_SQLITEPCL_RAW4834      return Sqlite3.sqlite3_bind_text (stmt, index, val);4835#else4836      return Sqlite3.sqlite3_bind_text(stmt, index, val, n, null);4837#endif4838    }48394840    public static int BindBlob (Sqlite3Statement stmt, int index, byte[] val, int n, IntPtr free)4841    {4842#if USE_WP8_NATIVE_SQLITE4843      return Sqlite3.sqlite3_bind_blob(stmt, index, val, n);4844#elif USE_SQLITEPCL_RAW4845      return Sqlite3.sqlite3_bind_blob (stmt, index, val);4846#else4847      return Sqlite3.sqlite3_bind_blob(stmt, index, val, n, null);4848#endif4849    }48504851    public static int ColumnCount (Sqlite3Statement stmt)4852    {4853      return Sqlite3.sqlite3_column_count (stmt);4854    }48554856    public static string ColumnName (Sqlite3Statement stmt, int index)4857    {4858      return Sqlite3.sqlite3_column_name (stmt, index).utf8_to_string ();4859    }48604861    public static string ColumnName16 (Sqlite3Statement stmt, int index)4862    {4863      return Sqlite3.sqlite3_column_name (stmt, index).utf8_to_string ();4864    }48654866    public static ColType ColumnType (Sqlite3Statement stmt, int index)4867    {4868      return (ColType)Sqlite3.sqlite3_column_type (stmt, index);4869    }48704871    public static int ColumnInt (Sqlite3Statement stmt, int index)4872    {4873      return Sqlite3.sqlite3_column_int (stmt, index);4874    }48754876    public static long ColumnInt64 (Sqlite3Statement stmt, int index)4877    {4878      return Sqlite3.sqlite3_column_int64 (stmt, index);4879    }48804881    public static double ColumnDouble (Sqlite3Statement stmt, int index)4882    {4883      return Sqlite3.sqlite3_column_double (stmt, index);4884    }48854886    public static string ColumnText (Sqlite3Statement stmt, int index)4887    {4888      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();4889    }48904891    public static string ColumnText16 (Sqlite3Statement stmt, int index)4892    {4893      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();4894    }48954896    public static byte[] ColumnBlob (Sqlite3Statement stmt, int index)4897    {4898      return Sqlite3.sqlite3_column_blob (stmt, index).ToArray ();4899    }49004901    public static int ColumnBytes (Sqlite3Statement stmt, int index)4902    {4903      return Sqlite3.sqlite3_column_bytes (stmt, index);4904    }49054906    public static string ColumnString (Sqlite3Statement stmt, int index)4907    {4908      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();  4909    }  49104911    public static Result EnableLoadExtension (Sqlite3DatabaseHandle db, int onoff)4911    public static byte[] ColumnByteArray (Sqlite3Statement stmt, int index)  4912    {4913      return (Result)Sqlite3.sqlite3_enable_load_extension (db, onoff);4914    }49154916    public static int LibVersionNumber ()4917    {4918      return Sqlite3.sqlite3_libversion_number ();4919    }49204921    public static Result GetResult (Sqlite3DatabaseHandle db)4922    {4923      return (Result)Sqlite3.sqlite3_errcode (db);4924    }49254926    public static ExtendedResult ExtendedErrCode (Sqlite3DatabaseHandle db)4927    {4928      return (ExtendedResult)Sqlite3.sqlite3_extended_errcode (db);4929    }49304931    public static Sqlite3BackupHandle BackupInit (Sqlite3DatabaseHandle destDb, string destName, Sqlite3DatabaseHandle s4932    {4933      return Sqlite3.sqlite3_backup_init (destDb, destName, sourceDb, sourceName);4934    }49354936    public static Result BackupStep (Sqlite3BackupHandle backup, int numPages)4937    {4938      return (Result)Sqlite3.sqlite3_backup_step (backup, numPages);4939    }49404941    public static Result BackupFinish (Sqlite3BackupHandle backup)4942    {4943      return (Result)Sqlite3.sqlite3_backup_finish (backup);4944    }4945#endif49464947    public enum ColType : int4948    {4949      Integer = 1,4950      Float = 2,4951      Text = 3,4952      Blob = 4,4953      Null = 54954    }4955  }4956}4913      int length = ColumnBytes (stmt, index);4914      if (length > 0) {4915        return ColumnBlob (stmt, index);4916      }4917      return new byte[0];4918    }49194920    public static Result EnableLoadExtension (Sqlite3DatabaseHandle db, int onoff)4921    {4922      return (Result)Sqlite3.sqlite3_enable_load_extension (db, onoff);4923    }49244925    public static int LibVersionNumber ()4926    {4927      return Sqlite3.sqlite3_libversion_number ();4928    }49294930    public static Result GetResult (Sqlite3DatabaseHandle db)4931    {4932      return (Result)Sqlite3.sqlite3_errcode (db);4933    }49344935    public static ExtendedResult ExtendedErrCode (Sqlite3DatabaseHandle db)4936    {4937      return (ExtendedResult)Sqlite3.sqlite3_extended_errcode (db);4938    }49394940    public static Sqlite3BackupHandle BackupInit (Sqlite3DatabaseHandle destDb, string destName, Sqlite3DatabaseHandle s4941    {4942      return Sqlite3.sqlite3_backup_init (destDb, destName, sourceDb, sourceName);4943    }49444945    public static Result BackupStep (Sqlite3BackupHandle backup, int numPages)4946    {4947      return (Result)Sqlite3.sqlite3_backup_step (backup, numPages);4948    }49494950    public static Result BackupFinish (Sqlite3BackupHandle backup)4951    {4952      return (Result)Sqlite3.sqlite3_backup_finish (backup);4953    }4954#endif49554956    public enum ColType : int4957    {4958      Integer = 1,4959      Float = 2,4960      Text = 3,4961      Blob = 4,4962      Null = 54963    }4964  }4965}

- +

Methods/Properties

diff --git a/coverage/SQLite.Tests_ColumnAttribute.html b/coverage/SQLite.Tests_ColumnAttribute.html index 0d3c2e7f..61d7e075 100644 --- a/coverage/SQLite.Tests_ColumnAttribute.html +++ b/coverage/SQLite.Tests_ColumnAttribute.html @@ -815,7 +815,7 @@

< Summary

Tag: -164_8458774659 +165_8458827553
@@ -843,7 +843,7 @@

< Summary

Total lines: -4956 +4965 Line coverage: @@ -4193,7 +4193,7 @@

/home/runner/work/sqlite-ne  3283        else if (value is Boolean) {  3284          SQLite3.BindInt (stmt, index, (bool)value ? 1 : 0);  3285        }3286        else if (value is UInt32 || value is Int64) {3286        else if (value is UInt32 || value is Int64 || value is UInt64) {  3287          SQLite3.BindInt64 (stmt, index, Convert.ToInt64 (value));  3288        }  3289        else if (value is Single || value is Double || value is Decimal) { @@ -4327,1547 +4327,1556 @@

/home/runner/work/sqlite-ne  3417        else if (clrType == typeof (Int64)) {  3418          return SQLite3.ColumnInt64 (stmt, index);  3419        }3420        else if (clrType == typeof (UInt32)) {3421          return (uint)SQLite3.ColumnInt64 (stmt, index);3420        else if (clrType == typeof (UInt64)) {3421          return (ulong)SQLite3.ColumnInt64 (stmt, index);  3422        }3423        else if (clrType == typeof (decimal)) {3424          return (decimal)SQLite3.ColumnDouble (stmt, index);3423        else if (clrType == typeof (UInt32)) {3424          return (uint)SQLite3.ColumnInt64 (stmt, index);  3425        }3426        else if (clrType == typeof (Byte)) {3427          return (byte)SQLite3.ColumnInt (stmt, index);3426        else if (clrType == typeof (decimal)) {3427          return (decimal)SQLite3.ColumnDouble (stmt, index);  3428        }3429        else if (clrType == typeof (UInt16)) {3430          return (ushort)SQLite3.ColumnInt (stmt, index);3429        else if (clrType == typeof (Byte)) {3430          return (byte)SQLite3.ColumnInt (stmt, index);  3431        }3432        else if (clrType == typeof (Int16)) {3433          return (short)SQLite3.ColumnInt (stmt, index);3432        else if (clrType == typeof (UInt16)) {3433          return (ushort)SQLite3.ColumnInt (stmt, index);  3434        }3435        else if (clrType == typeof (sbyte)) {3436          return (sbyte)SQLite3.ColumnInt (stmt, index);3435        else if (clrType == typeof (Int16)) {3436          return (short)SQLite3.ColumnInt (stmt, index);  3437        }3438        else if (clrType == typeof (byte[])) {3439          return SQLite3.ColumnByteArray (stmt, index);3438        else if (clrType == typeof (sbyte)) {3439          return (sbyte)SQLite3.ColumnInt (stmt, index);  3440        }3441        else if (clrType == typeof (Guid)) {3442          var text = SQLite3.ColumnString (stmt, index);3443          return new Guid (text);3444        }3445        else if (clrType == typeof (Uri)) {3446          var text = SQLite3.ColumnString (stmt, index);3447          return new Uri (text);3448        }3449        else if (clrType == typeof (StringBuilder)) {3450          var text = SQLite3.ColumnString (stmt, index);3451          return new StringBuilder (text);3452        }3453        else if (clrType == typeof (UriBuilder)) {3454          var text = SQLite3.ColumnString (stmt, index);3455          return new UriBuilder (text);3456        }3457        else {3458          throw new NotSupportedException ("Don't know how to read " + clrType);3441        else if (clrType == typeof (byte[])) {3442          return SQLite3.ColumnByteArray (stmt, index);3443        }3444        else if (clrType == typeof (Guid)) {3445          var text = SQLite3.ColumnString (stmt, index);3446          return new Guid (text);3447        }3448        else if (clrType == typeof (Uri)) {3449          var text = SQLite3.ColumnString (stmt, index);3450          return new Uri (text);3451        }3452        else if (clrType == typeof (StringBuilder)) {3453          var text = SQLite3.ColumnString (stmt, index);3454          return new StringBuilder (text);3455        }3456        else if (clrType == typeof (UriBuilder)) {3457          var text = SQLite3.ColumnString (stmt, index);3458          return new UriBuilder (text);  3459        }3460      }3461    }3462  }34633464  internal class FastColumnSetter3465  {3466    /// <summary>3467    /// Creates a delegate that can be used to quickly set object members from query columns.3468    ///3469    /// Note that this frontloads the slow reflection-based type checking for columns to only happen once at the beginni3470    /// and then afterwards each row of the query can invoke the delegate returned by this function to get much better p3471    /// </summary>3472    /// <typeparam name="T">The type of the destination object that the query will read into</typeparam>3473    /// <param name="conn">The active connection.  Note that this is primarily needed in order to read preferences regar3474    /// <param name="column">The table mapping used to map the statement column to a member of the destination object ty3475    /// <returns>3476    /// A delegate for fast-setting of object members from statement columns.3477    ///3478    /// If no fast setter is available for the requested column (enums in particular cause headache), then this function3479    /// </returns>3480    internal static Action<object, Sqlite3Statement, int> GetFastSetter<T> (SQLiteConnection conn, TableMapping.Column c3481    {3482      Action<object, Sqlite3Statement, int> fastSetter = null;34833484      Type clrType = column.PropertyInfo.PropertyType;34853486      var clrTypeInfo = clrType.GetTypeInfo ();3487      if (clrTypeInfo.IsGenericType && clrTypeInfo.GetGenericTypeDefinition () == typeof (Nullable<>)) {3488        clrType = clrTypeInfo.GenericTypeArguments[0];3489        clrTypeInfo = clrType.GetTypeInfo ();3490      }34913492      if (clrType == typeof (String)) {3493        fastSetter = CreateTypedSetterDelegate<T, string> (column, (stmt, index) => {3494          return SQLite3.ColumnString (stmt, index);3495        });3496      }3497      else if (clrType == typeof (Int32)) {3498        fastSetter = CreateNullableTypedSetterDelegate<T, int> (column, (stmt, index)=>{3499          return SQLite3.ColumnInt (stmt, index);3500        });3501      }3502      else if (clrType == typeof (Boolean)) {3503        fastSetter = CreateNullableTypedSetterDelegate<T, bool> (column, (stmt, index) => {3504          return SQLite3.ColumnInt (stmt, index) == 1;3505        });3506      }3507      else if (clrType == typeof (double)) {3508        fastSetter = CreateNullableTypedSetterDelegate<T, double> (column, (stmt, index) => {3509          return SQLite3.ColumnDouble (stmt, index);3510        });3511      }3512      else if (clrType == typeof (float)) {3513        fastSetter = CreateNullableTypedSetterDelegate<T, float> (column, (stmt, index) => {3514          return (float) SQLite3.ColumnDouble (stmt, index);3515        });3516      }3517      else if (clrType == typeof (TimeSpan)) {3518        if (conn.StoreTimeSpanAsTicks) {3519          fastSetter = CreateNullableTypedSetterDelegate<T, TimeSpan> (column, (stmt, index) => {3520            return new TimeSpan (SQLite3.ColumnInt64 (stmt, index));3521          });3522        }3523        else {3524          fastSetter = CreateNullableTypedSetterDelegate<T, TimeSpan> (column, (stmt, index) => {3525            var text = SQLite3.ColumnString (stmt, index);3526            TimeSpan resultTime;3527            if (!TimeSpan.TryParseExact (text, "c", System.Globalization.CultureInfo.InvariantCulture, System.Globalizat3528              resultTime = TimeSpan.Parse (text);3529            }3530            return resultTime;3531          });3532        }3533      }3534      else if (clrType == typeof (DateTime)) {3535        if (conn.StoreDateTimeAsTicks) {3536          fastSetter = CreateNullableTypedSetterDelegate<T, DateTime> (column, (stmt, index) => {3537            return new DateTime (SQLite3.ColumnInt64 (stmt, index));3538          });3539        }3540        else {3541          fastSetter = CreateNullableTypedSetterDelegate<T, DateTime> (column, (stmt, index) => {3542            var text = SQLite3.ColumnString (stmt, index);3543            DateTime resultDate;3544            if (!DateTime.TryParseExact (text, conn.DateTimeStringFormat, System.Globalization.CultureInfo.InvariantCult3545              resultDate = DateTime.Parse (text);3546            }3547            return resultDate;3548          });3549        }3550      }3551      else if (clrType == typeof (DateTimeOffset)) {3552        fastSetter = CreateNullableTypedSetterDelegate<T, DateTimeOffset> (column, (stmt, index) => {3553          return new DateTimeOffset (SQLite3.ColumnInt64 (stmt, index), TimeSpan.Zero);3554        });3555      }3556      else if (clrTypeInfo.IsEnum) {3557        // NOTE: Not sure of a good way (if any?) to do a strongly-typed fast setter like this for enumerated types -- f3460        else {3461          throw new NotSupportedException ("Don't know how to read " + clrType);3462        }3463      }3464    }3465  }34663467  internal class FastColumnSetter3468  {3469    /// <summary>3470    /// Creates a delegate that can be used to quickly set object members from query columns.3471    ///3472    /// Note that this frontloads the slow reflection-based type checking for columns to only happen once at the beginni3473    /// and then afterwards each row of the query can invoke the delegate returned by this function to get much better p3474    /// </summary>3475    /// <typeparam name="T">The type of the destination object that the query will read into</typeparam>3476    /// <param name="conn">The active connection.  Note that this is primarily needed in order to read preferences regar3477    /// <param name="column">The table mapping used to map the statement column to a member of the destination object ty3478    /// <returns>3479    /// A delegate for fast-setting of object members from statement columns.3480    ///3481    /// If no fast setter is available for the requested column (enums in particular cause headache), then this function3482    /// </returns>3483    internal static Action<object, Sqlite3Statement, int> GetFastSetter<T> (SQLiteConnection conn, TableMapping.Column c3484    {3485      Action<object, Sqlite3Statement, int> fastSetter = null;34863487      Type clrType = column.PropertyInfo.PropertyType;34883489      var clrTypeInfo = clrType.GetTypeInfo ();3490      if (clrTypeInfo.IsGenericType && clrTypeInfo.GetGenericTypeDefinition () == typeof (Nullable<>)) {3491        clrType = clrTypeInfo.GenericTypeArguments[0];3492        clrTypeInfo = clrType.GetTypeInfo ();3493      }34943495      if (clrType == typeof (String)) {3496        fastSetter = CreateTypedSetterDelegate<T, string> (column, (stmt, index) => {3497          return SQLite3.ColumnString (stmt, index);3498        });3499      }3500      else if (clrType == typeof (Int32)) {3501        fastSetter = CreateNullableTypedSetterDelegate<T, int> (column, (stmt, index)=>{3502          return SQLite3.ColumnInt (stmt, index);3503        });3504      }3505      else if (clrType == typeof (Boolean)) {3506        fastSetter = CreateNullableTypedSetterDelegate<T, bool> (column, (stmt, index) => {3507          return SQLite3.ColumnInt (stmt, index) == 1;3508        });3509      }3510      else if (clrType == typeof (double)) {3511        fastSetter = CreateNullableTypedSetterDelegate<T, double> (column, (stmt, index) => {3512          return SQLite3.ColumnDouble (stmt, index);3513        });3514      }3515      else if (clrType == typeof (float)) {3516        fastSetter = CreateNullableTypedSetterDelegate<T, float> (column, (stmt, index) => {3517          return (float) SQLite3.ColumnDouble (stmt, index);3518        });3519      }3520      else if (clrType == typeof (TimeSpan)) {3521        if (conn.StoreTimeSpanAsTicks) {3522          fastSetter = CreateNullableTypedSetterDelegate<T, TimeSpan> (column, (stmt, index) => {3523            return new TimeSpan (SQLite3.ColumnInt64 (stmt, index));3524          });3525        }3526        else {3527          fastSetter = CreateNullableTypedSetterDelegate<T, TimeSpan> (column, (stmt, index) => {3528            var text = SQLite3.ColumnString (stmt, index);3529            TimeSpan resultTime;3530            if (!TimeSpan.TryParseExact (text, "c", System.Globalization.CultureInfo.InvariantCulture, System.Globalizat3531              resultTime = TimeSpan.Parse (text);3532            }3533            return resultTime;3534          });3535        }3536      }3537      else if (clrType == typeof (DateTime)) {3538        if (conn.StoreDateTimeAsTicks) {3539          fastSetter = CreateNullableTypedSetterDelegate<T, DateTime> (column, (stmt, index) => {3540            return new DateTime (SQLite3.ColumnInt64 (stmt, index));3541          });3542        }3543        else {3544          fastSetter = CreateNullableTypedSetterDelegate<T, DateTime> (column, (stmt, index) => {3545            var text = SQLite3.ColumnString (stmt, index);3546            DateTime resultDate;3547            if (!DateTime.TryParseExact (text, conn.DateTimeStringFormat, System.Globalization.CultureInfo.InvariantCult3548              resultDate = DateTime.Parse (text);3549            }3550            return resultDate;3551          });3552        }3553      }3554      else if (clrType == typeof (DateTimeOffset)) {3555        fastSetter = CreateNullableTypedSetterDelegate<T, DateTimeOffset> (column, (stmt, index) => {3556          return new DateTimeOffset (SQLite3.ColumnInt64 (stmt, index), TimeSpan.Zero);3557        });  3558      }3559      else if (clrType == typeof (Int64)) {3560        fastSetter = CreateNullableTypedSetterDelegate<T, Int64> (column, (stmt, index) => {3561          return SQLite3.ColumnInt64 (stmt, index);3562        });3563      }3564      else if (clrType == typeof (UInt32)) {3565        fastSetter = CreateNullableTypedSetterDelegate<T, UInt32> (column, (stmt, index) => {3566          return (uint)SQLite3.ColumnInt64 (stmt, index);3567        });3568      }3569      else if (clrType == typeof (decimal)) {3570        fastSetter = CreateNullableTypedSetterDelegate<T, decimal> (column, (stmt, index) => {3571          return (decimal)SQLite3.ColumnDouble (stmt, index);3572        });3573      }3574      else if (clrType == typeof (Byte)) {3575        fastSetter = CreateNullableTypedSetterDelegate<T, Byte> (column, (stmt, index) => {3576          return (byte)SQLite3.ColumnInt (stmt, index);3577        });3578      }3579      else if (clrType == typeof (UInt16)) {3580        fastSetter = CreateNullableTypedSetterDelegate<T, UInt16> (column, (stmt, index) => {3581          return (ushort)SQLite3.ColumnInt (stmt, index);3582        });3583      }3584      else if (clrType == typeof (Int16)) {3585        fastSetter = CreateNullableTypedSetterDelegate<T, Int16> (column, (stmt, index) => {3586          return (short)SQLite3.ColumnInt (stmt, index);3587        });3588      }3589      else if (clrType == typeof (sbyte)) {3590        fastSetter = CreateNullableTypedSetterDelegate<T, sbyte> (column, (stmt, index) => {3591          return (sbyte)SQLite3.ColumnInt (stmt, index);3592        });3593      }3594      else if (clrType == typeof (byte[])) {3595        fastSetter = CreateTypedSetterDelegate<T, byte[]> (column, (stmt, index) => {3596          return SQLite3.ColumnByteArray (stmt, index);3597        });3598      }3599      else if (clrType == typeof (Guid)) {3600        fastSetter = CreateNullableTypedSetterDelegate<T, Guid> (column, (stmt, index) => {3601          var text = SQLite3.ColumnString (stmt, index);3602          return new Guid (text);3603        });3604      }3605      else if (clrType == typeof (Uri)) {3606        fastSetter = CreateTypedSetterDelegate<T, Uri> (column, (stmt, index) => {3607          var text = SQLite3.ColumnString (stmt, index);3608          return new Uri (text);3609        });3610      }3611      else if (clrType == typeof (StringBuilder)) {3612        fastSetter = CreateTypedSetterDelegate<T, StringBuilder> (column, (stmt, index) => {3613          var text = SQLite3.ColumnString (stmt, index);3614          return new StringBuilder (text);3615        });3616      }3617      else if (clrType == typeof (UriBuilder)) {3618        fastSetter = CreateTypedSetterDelegate<T, UriBuilder> (column, (stmt, index) => {3619          var text = SQLite3.ColumnString (stmt, index);3620          return new UriBuilder (text);3621        });3622      }3623      else {3624        // NOTE: Will fall back to the slow setter method in the event that we are unable to create a fast setter delega3559      else if (clrTypeInfo.IsEnum) {3560        // NOTE: Not sure of a good way (if any?) to do a strongly-typed fast setter like this for enumerated types -- f3561      }3562      else if (clrType == typeof (Int64)) {3563        fastSetter = CreateNullableTypedSetterDelegate<T, Int64> (column, (stmt, index) => {3564          return SQLite3.ColumnInt64 (stmt, index);3565        });3566      }3567      else if (clrType == typeof(UInt64))3568      {3569        fastSetter = CreateNullableTypedSetterDelegate<T, UInt64>(column, (stmt, index) => {3570          return (ulong)SQLite3.ColumnInt64(stmt, index);3571        });3572      }3573      else if (clrType == typeof (UInt32)) {3574        fastSetter = CreateNullableTypedSetterDelegate<T, UInt32> (column, (stmt, index) => {3575          return (uint)SQLite3.ColumnInt64 (stmt, index);3576        });3577      }3578      else if (clrType == typeof (decimal)) {3579        fastSetter = CreateNullableTypedSetterDelegate<T, decimal> (column, (stmt, index) => {3580          return (decimal)SQLite3.ColumnDouble (stmt, index);3581        });3582      }3583      else if (clrType == typeof (Byte)) {3584        fastSetter = CreateNullableTypedSetterDelegate<T, Byte> (column, (stmt, index) => {3585          return (byte)SQLite3.ColumnInt (stmt, index);3586        });3587      }3588      else if (clrType == typeof (UInt16)) {3589        fastSetter = CreateNullableTypedSetterDelegate<T, UInt16> (column, (stmt, index) => {3590          return (ushort)SQLite3.ColumnInt (stmt, index);3591        });3592      }3593      else if (clrType == typeof (Int16)) {3594        fastSetter = CreateNullableTypedSetterDelegate<T, Int16> (column, (stmt, index) => {3595          return (short)SQLite3.ColumnInt (stmt, index);3596        });3597      }3598      else if (clrType == typeof (sbyte)) {3599        fastSetter = CreateNullableTypedSetterDelegate<T, sbyte> (column, (stmt, index) => {3600          return (sbyte)SQLite3.ColumnInt (stmt, index);3601        });3602      }3603      else if (clrType == typeof (byte[])) {3604        fastSetter = CreateTypedSetterDelegate<T, byte[]> (column, (stmt, index) => {3605          return SQLite3.ColumnByteArray (stmt, index);3606        });3607      }3608      else if (clrType == typeof (Guid)) {3609        fastSetter = CreateNullableTypedSetterDelegate<T, Guid> (column, (stmt, index) => {3610          var text = SQLite3.ColumnString (stmt, index);3611          return new Guid (text);3612        });3613      }3614      else if (clrType == typeof (Uri)) {3615        fastSetter = CreateTypedSetterDelegate<T, Uri> (column, (stmt, index) => {3616          var text = SQLite3.ColumnString (stmt, index);3617          return new Uri (text);3618        });3619      }3620      else if (clrType == typeof (StringBuilder)) {3621        fastSetter = CreateTypedSetterDelegate<T, StringBuilder> (column, (stmt, index) => {3622          var text = SQLite3.ColumnString (stmt, index);3623          return new StringBuilder (text);3624        });  3625      }3626      return fastSetter;3627    }36283629    /// <summary>3630    /// This creates a strongly typed delegate that will permit fast setting of column values given a Sqlite3Statement a3631    ///3632    /// Note that this is identical to CreateTypedSetterDelegate(), but has an extra check to see if it should create a 3633    /// </summary>3634    /// <typeparam name="ObjectType">The type of the object whose member column is being set</typeparam>3635    /// <typeparam name="ColumnMemberType">The CLR type of the member in the object which corresponds to the given SQLit3636    /// <param name="column">The column mapping that identifies the target member of the destination object</param>3637    /// <param name="getColumnValue">A lambda that can be used to retrieve the column value at query-time</param>3638    /// <returns>A strongly-typed delegate</returns>3639    private static Action<object, Sqlite3Statement, int> CreateNullableTypedSetterDelegate<ObjectType, ColumnMemberType>3640    {3641      var clrTypeInfo = column.PropertyInfo.PropertyType.GetTypeInfo();3642      bool isNullable = false;36433644      if (clrTypeInfo.IsGenericType && clrTypeInfo.GetGenericTypeDefinition () == typeof (Nullable<>)) {3645        isNullable = true;3646      }36473648      if (isNullable) {3649        var setProperty = (Action<ObjectType, ColumnMemberType?>)Delegate.CreateDelegate (3650            typeof (Action<ObjectType, ColumnMemberType?>), null,3651            column.PropertyInfo.GetSetMethod ());3626      else if (clrType == typeof (UriBuilder)) {3627        fastSetter = CreateTypedSetterDelegate<T, UriBuilder> (column, (stmt, index) => {3628          var text = SQLite3.ColumnString (stmt, index);3629          return new UriBuilder (text);3630        });3631      }3632      else {3633        // NOTE: Will fall back to the slow setter method in the event that we are unable to create a fast setter delega3634      }3635      return fastSetter;3636    }36373638    /// <summary>3639    /// This creates a strongly typed delegate that will permit fast setting of column values given a Sqlite3Statement a3640    ///3641    /// Note that this is identical to CreateTypedSetterDelegate(), but has an extra check to see if it should create a 3642    /// </summary>3643    /// <typeparam name="ObjectType">The type of the object whose member column is being set</typeparam>3644    /// <typeparam name="ColumnMemberType">The CLR type of the member in the object which corresponds to the given SQLit3645    /// <param name="column">The column mapping that identifies the target member of the destination object</param>3646    /// <param name="getColumnValue">A lambda that can be used to retrieve the column value at query-time</param>3647    /// <returns>A strongly-typed delegate</returns>3648    private static Action<object, Sqlite3Statement, int> CreateNullableTypedSetterDelegate<ObjectType, ColumnMemberType>3649    {3650      var clrTypeInfo = column.PropertyInfo.PropertyType.GetTypeInfo();3651      bool isNullable = false;  36523653        return (o, stmt, i) => {3654          var colType = SQLite3.ColumnType (stmt, i);3655          if (colType != SQLite3.ColType.Null)3656            setProperty.Invoke ((ObjectType)o, getColumnValue.Invoke (stmt, i));3657        };3658      }36593660      return CreateTypedSetterDelegate<ObjectType, ColumnMemberType> (column, getColumnValue);3661    }36623663    /// <summary>3664    /// This creates a strongly typed delegate that will permit fast setting of column values given a Sqlite3Statement a3665    /// </summary>3666    /// <typeparam name="ObjectType">The type of the object whose member column is being set</typeparam>3667    /// <typeparam name="ColumnMemberType">The CLR type of the member in the object which corresponds to the given SQLit3668    /// <param name="column">The column mapping that identifies the target member of the destination object</param>3669    /// <param name="getColumnValue">A lambda that can be used to retrieve the column value at query-time</param>3670    /// <returns>A strongly-typed delegate</returns>3671    private static Action<object, Sqlite3Statement, int> CreateTypedSetterDelegate<ObjectType, ColumnMemberType> (TableM3672    {3673      var setProperty = (Action<ObjectType, ColumnMemberType>)Delegate.CreateDelegate (3674          typeof (Action<ObjectType, ColumnMemberType>), null,3675          column.PropertyInfo.GetSetMethod ());36763677      return (o, stmt, i) => {3678        var colType = SQLite3.ColumnType (stmt, i);3679        if (colType != SQLite3.ColType.Null)3680          setProperty.Invoke ((ObjectType)o, getColumnValue.Invoke (stmt, i));3681      };3682    }3683  }36843685  /// <summary>3686  /// Since the insert never changed, we only need to prepare once.3687  /// </summary>3688  class PreparedSqlLiteInsertCommand : IDisposable3689  {3690    bool Initialized;36913692    SQLiteConnection Connection;3653      if (clrTypeInfo.IsGenericType && clrTypeInfo.GetGenericTypeDefinition () == typeof (Nullable<>)) {3654        isNullable = true;3655      }36563657      if (isNullable) {3658        var setProperty = (Action<ObjectType, ColumnMemberType?>)Delegate.CreateDelegate (3659            typeof (Action<ObjectType, ColumnMemberType?>), null,3660            column.PropertyInfo.GetSetMethod ());36613662        return (o, stmt, i) => {3663          var colType = SQLite3.ColumnType (stmt, i);3664          if (colType != SQLite3.ColType.Null)3665            setProperty.Invoke ((ObjectType)o, getColumnValue.Invoke (stmt, i));3666        };3667      }36683669      return CreateTypedSetterDelegate<ObjectType, ColumnMemberType> (column, getColumnValue);3670    }36713672    /// <summary>3673    /// This creates a strongly typed delegate that will permit fast setting of column values given a Sqlite3Statement a3674    /// </summary>3675    /// <typeparam name="ObjectType">The type of the object whose member column is being set</typeparam>3676    /// <typeparam name="ColumnMemberType">The CLR type of the member in the object which corresponds to the given SQLit3677    /// <param name="column">The column mapping that identifies the target member of the destination object</param>3678    /// <param name="getColumnValue">A lambda that can be used to retrieve the column value at query-time</param>3679    /// <returns>A strongly-typed delegate</returns>3680    private static Action<object, Sqlite3Statement, int> CreateTypedSetterDelegate<ObjectType, ColumnMemberType> (TableM3681    {3682      var setProperty = (Action<ObjectType, ColumnMemberType>)Delegate.CreateDelegate (3683          typeof (Action<ObjectType, ColumnMemberType>), null,3684          column.PropertyInfo.GetSetMethod ());36853686      return (o, stmt, i) => {3687        var colType = SQLite3.ColumnType (stmt, i);3688        if (colType != SQLite3.ColType.Null)3689          setProperty.Invoke ((ObjectType)o, getColumnValue.Invoke (stmt, i));3690      };3691    }3692  }  36933694    string CommandText;36953696    Sqlite3Statement Statement;3697    static readonly Sqlite3Statement NullStatement = default (Sqlite3Statement);36983699    public PreparedSqlLiteInsertCommand (SQLiteConnection conn, string commandText)3700    {3701      Connection = conn;3702      CommandText = commandText;3703    }3694  /// <summary>3695  /// Since the insert never changed, we only need to prepare once.3696  /// </summary>3697  class PreparedSqlLiteInsertCommand : IDisposable3698  {3699    bool Initialized;37003701    SQLiteConnection Connection;37023703    string CommandText;  37043705    public int ExecuteNonQuery (object[] source)3706    {3707      if (Initialized && Statement == NullStatement) {3708        throw new ObjectDisposedException (nameof (PreparedSqlLiteInsertCommand));3709      }37103711      if (Connection.Trace) {3712        Connection.Tracer?.Invoke ("Executing: " + CommandText);3713      }37143715      var r = SQLite3.Result.OK;37163717      if (!Initialized) {3718        Statement = SQLite3.Prepare2 (Connection.Handle, CommandText);3719        Initialized = true;3720      }37213722      //bind the values.3723      if (source != null) {3724        for (int i = 0; i < source.Length; i++) {3725          SQLiteCommand.BindParameter (Statement, i + 1, source[i], Connection.StoreDateTimeAsTicks, Connection.DateTime3726        }3727      }3728      r = SQLite3.Step (Statement);37293730      if (r == SQLite3.Result.Done) {3731        int rowsAffected = SQLite3.Changes (Connection.Handle);3732        SQLite3.Reset (Statement);3733        return rowsAffected;3734      }3735      else if (r == SQLite3.Result.Error) {3736        string msg = SQLite3.GetErrmsg (Connection.Handle);3737        SQLite3.Reset (Statement);3738        throw SQLiteException.New (r, msg);3739      }3740      else if (r == SQLite3.Result.Constraint && SQLite3.ExtendedErrCode (Connection.Handle) == SQLite3.ExtendedResult.C3705    Sqlite3Statement Statement;3706    static readonly Sqlite3Statement NullStatement = default (Sqlite3Statement);37073708    public PreparedSqlLiteInsertCommand (SQLiteConnection conn, string commandText)3709    {3710      Connection = conn;3711      CommandText = commandText;3712    }37133714    public int ExecuteNonQuery (object[] source)3715    {3716      if (Initialized && Statement == NullStatement) {3717        throw new ObjectDisposedException (nameof (PreparedSqlLiteInsertCommand));3718      }37193720      if (Connection.Trace) {3721        Connection.Tracer?.Invoke ("Executing: " + CommandText);3722      }37233724      var r = SQLite3.Result.OK;37253726      if (!Initialized) {3727        Statement = SQLite3.Prepare2 (Connection.Handle, CommandText);3728        Initialized = true;3729      }37303731      //bind the values.3732      if (source != null) {3733        for (int i = 0; i < source.Length; i++) {3734          SQLiteCommand.BindParameter (Statement, i + 1, source[i], Connection.StoreDateTimeAsTicks, Connection.DateTime3735        }3736      }3737      r = SQLite3.Step (Statement);37383739      if (r == SQLite3.Result.Done) {3740        int rowsAffected = SQLite3.Changes (Connection.Handle);  3741        SQLite3.Reset (Statement);3742        throw NotNullConstraintViolationException.New (r, SQLite3.GetErrmsg (Connection.Handle));3742        return rowsAffected;  3743      }3744      else {3745        SQLite3.Reset (Statement);3746        throw SQLiteException.New (r, SQLite3.GetErrmsg (Connection.Handle));3747      }3748    }37493750    public void Dispose ()3751    {3752      Dispose (true);3753      GC.SuppressFinalize (this);3754    }37553756    void Dispose (bool disposing)3757    {3758      var s = Statement;3759      Statement = NullStatement;3760      Connection = null;3761      if (s != NullStatement) {3762        SQLite3.Finalize (s);3763      }3764    }37653766    ~PreparedSqlLiteInsertCommand ()3767    {3768      Dispose (false);3769    }3770  }37713772  public enum CreateTableResult3773  {3774    Created,3775    Migrated,3776  }37773778  public class CreateTablesResult3779  {3780    public Dictionary<Type, CreateTableResult> Results { get; private set; }37813782    public CreateTablesResult ()3783    {3784      Results = new Dictionary<Type, CreateTableResult> ();3785    }3786  }37873788  public abstract class BaseTableQuery3789  {3790    protected class Ordering3791    {3792      public string ColumnName { get; set; }3793      public bool Ascending { get; set; }3744      else if (r == SQLite3.Result.Error) {3745        string msg = SQLite3.GetErrmsg (Connection.Handle);3746        SQLite3.Reset (Statement);3747        throw SQLiteException.New (r, msg);3748      }3749      else if (r == SQLite3.Result.Constraint && SQLite3.ExtendedErrCode (Connection.Handle) == SQLite3.ExtendedResult.C3750        SQLite3.Reset (Statement);3751        throw NotNullConstraintViolationException.New (r, SQLite3.GetErrmsg (Connection.Handle));3752      }3753      else {3754        SQLite3.Reset (Statement);3755        throw SQLiteException.New (r, SQLite3.GetErrmsg (Connection.Handle));3756      }3757    }37583759    public void Dispose ()3760    {3761      Dispose (true);3762      GC.SuppressFinalize (this);3763    }37643765    void Dispose (bool disposing)3766    {3767      var s = Statement;3768      Statement = NullStatement;3769      Connection = null;3770      if (s != NullStatement) {3771        SQLite3.Finalize (s);3772      }3773    }37743775    ~PreparedSqlLiteInsertCommand ()3776    {3777      Dispose (false);3778    }3779  }37803781  public enum CreateTableResult3782  {3783    Created,3784    Migrated,3785  }37863787  public class CreateTablesResult3788  {3789    public Dictionary<Type, CreateTableResult> Results { get; private set; }37903791    public CreateTablesResult ()3792    {3793      Results = new Dictionary<Type, CreateTableResult> ();  3794    }  3795  }  37963797  public class TableQuery<T> : BaseTableQuery, IEnumerable<T>3797  public abstract class BaseTableQuery  3798  {3799    public SQLiteConnection Connection { get; private set; }38003801    public TableMapping Table { get; private set; }38023803    Expression _where;3804    List<Ordering> _orderBys;3805    int? _limit;3806    int? _offset;38073808    BaseTableQuery _joinInner;3809    Expression _joinInnerKeySelector;3810    BaseTableQuery _joinOuter;3811    Expression _joinOuterKeySelector;3812    Expression _joinSelector;38133814    Expression _selector;38153816    TableQuery (SQLiteConnection conn, TableMapping table)3817    {3818      Connection = conn;3819      Table = table;3820    }38213822    public TableQuery (SQLiteConnection conn)3823    {3824      Connection = conn;3825      Table = Connection.GetMapping (typeof (T));3826    }38273828    public TableQuery<U> Clone<U> ()3829    {3830      var q = new TableQuery<U> (Connection, Table);3831      q._where = _where;3832      q._deferred = _deferred;3833      if (_orderBys != null) {3834        q._orderBys = new List<Ordering> (_orderBys);3835      }3836      q._limit = _limit;3837      q._offset = _offset;3838      q._joinInner = _joinInner;3839      q._joinInnerKeySelector = _joinInnerKeySelector;3840      q._joinOuter = _joinOuter;3841      q._joinOuterKeySelector = _joinOuterKeySelector;3842      q._joinSelector = _joinSelector;3843      q._selector = _selector;3844      return q;3845    }38463847    /// <summary>3848    /// Filters the query based on a predicate.3849    /// </summary>3850    public TableQuery<T> Where (Expression<Func<T, bool>> predExpr)3851    {3852      if (predExpr.NodeType == ExpressionType.Lambda) {3853        var lambda = (LambdaExpression)predExpr;3854        var pred = lambda.Body;3855        var q = Clone<T> ();3856        q.AddWhere (pred);3857        return q;3858      }3859      else {3860        throw new NotSupportedException ("Must be a predicate");3861      }3862    }38633864    /// <summary>3865    /// Delete all the rows that match this query.3866    /// </summary>3867    public int Delete ()3868    {3869      return Delete (null);3870    }38713872    /// <summary>3873    /// Delete all the rows that match this query and the given predicate.3874    /// </summary>3875    public int Delete (Expression<Func<T, bool>> predExpr)3876    {3877      if (_limit.HasValue || _offset.HasValue)3878        throw new InvalidOperationException ("Cannot delete with limits or offsets");38793880      if (_where == null && predExpr == null)3881        throw new InvalidOperationException ("No condition specified");38823883      var pred = _where;38843885      if (predExpr != null && predExpr.NodeType == ExpressionType.Lambda) {3886        var lambda = (LambdaExpression)predExpr;3887        pred = pred != null ? Expression.AndAlso (pred, lambda.Body) : lambda.Body;3888      }38893890      var args = new List<object> ();3891      var cmdText = "delete from \"" + Table.TableName + "\"";3892      var w = CompileExpr (pred, args);3893      cmdText += " where " + w.CommandText;38943895      var command = Connection.CreateCommand (cmdText, args.ToArray ());38963897      int result = command.ExecuteNonQuery ();3898      return result;3899    }39003901    /// <summary>3902    /// Yields a given number of elements from the query and then skips the remainder.3903    /// </summary>3904    public TableQuery<T> Take (int n)3905    {3906      var q = Clone<T> ();3907      q._limit = n;3908      return q;3909    }39103911    /// <summary>3912    /// Skips a given number of elements from the query and then yields the remainder.3913    /// </summary>3914    public TableQuery<T> Skip (int n)3915    {3916      var q = Clone<T> ();3917      q._offset = n;3918      return q;3919    }39203921    /// <summary>3922    /// Returns the element at a given index3923    /// </summary>3924    public T ElementAt (int index)3925    {3926      return Skip (index).Take (1).First ();3927    }39283929    bool _deferred;3930    public TableQuery<T> Deferred ()3931    {3932      var q = Clone<T> ();3933      q._deferred = true;3934      return q;3935    }39363937    /// <summary>3938    /// Order the query results according to a key.3939    /// </summary>3940    public TableQuery<T> OrderBy<U> (Expression<Func<T, U>> orderExpr)3941    {3942      return AddOrderBy<U> (orderExpr, true);3943    }39443945    /// <summary>3946    /// Order the query results according to a key.3947    /// </summary>3948    public TableQuery<T> OrderByDescending<U> (Expression<Func<T, U>> orderExpr)3949    {3950      return AddOrderBy<U> (orderExpr, false);3951    }39523953    /// <summary>3954    /// Order the query results according to a key.3955    /// </summary>3956    public TableQuery<T> ThenBy<U> (Expression<Func<T, U>> orderExpr)3957    {3958      return AddOrderBy<U> (orderExpr, true);3959    }39603961    /// <summary>3962    /// Order the query results according to a key.3963    /// </summary>3964    public TableQuery<T> ThenByDescending<U> (Expression<Func<T, U>> orderExpr)3965    {3966      return AddOrderBy<U> (orderExpr, false);3967    }39683969    TableQuery<T> AddOrderBy<U> (Expression<Func<T, U>> orderExpr, bool asc)3970    {3971      if (orderExpr.NodeType == ExpressionType.Lambda) {3972        var lambda = (LambdaExpression)orderExpr;39733974        MemberExpression mem = null;39753976        var unary = lambda.Body as UnaryExpression;3977        if (unary != null && unary.NodeType == ExpressionType.Convert) {3978          mem = unary.Operand as MemberExpression;3979        }3980        else {3981          mem = lambda.Body as MemberExpression;3982        }39833984        if (mem != null && (mem.Expression.NodeType == ExpressionType.Parameter)) {3985          var q = Clone<T> ();3986          if (q._orderBys == null) {3987            q._orderBys = new List<Ordering> ();3988          }3989          q._orderBys.Add (new Ordering {3990            ColumnName = Table.FindColumnWithPropertyName (mem.Member.Name).Name,3991            Ascending = asc3992          });3993          return q;3994        }3995        else {3996          throw new NotSupportedException ("Order By does not support: " + orderExpr);3997        }3998      }3999      else {4000        throw new NotSupportedException ("Must be a predicate");4001      }4002    }40034004    private void AddWhere (Expression pred)4005    {4006      if (_where == null) {4007        _where = pred;4008      }4009      else {4010        _where = Expression.AndAlso (_where, pred);4011      }4012    }40134014    ///// <summary>4015    ///// Performs an inner join of two queries based on matching keys extracted from the elements.4016    ///// </summary>4017    //public TableQuery<TResult> Join<TInner, TKey, TResult> (4018    //  TableQuery<TInner> inner,4019    //  Expression<Func<T, TKey>> outerKeySelector,4020    //  Expression<Func<TInner, TKey>> innerKeySelector,4021    //  Expression<Func<T, TInner, TResult>> resultSelector)4022    //{4023    //  var q = new TableQuery<TResult> (Connection, Connection.GetMapping (typeof (TResult))) {4024    //    _joinOuter = this,4025    //    _joinOuterKeySelector = outerKeySelector,4026    //    _joinInner = inner,4027    //    _joinInnerKeySelector = innerKeySelector,4028    //    _joinSelector = resultSelector,4029    //  };4030    //  return q;4031    //}40324033    // Not needed until Joins are supported4034    // Keeping this commented out forces the default Linq to objects processor to run4035    //public TableQuery<TResult> Select<TResult> (Expression<Func<T, TResult>> selector)4036    //{4037    //  var q = Clone<TResult> ();4038    //  q._selector = selector;3799    protected class Ordering3800    {3801      public string ColumnName { get; set; }3802      public bool Ascending { get; set; }3803    }3804  }38053806  public class TableQuery<T> : BaseTableQuery, IEnumerable<T>3807  {3808    public SQLiteConnection Connection { get; private set; }38093810    public TableMapping Table { get; private set; }38113812    Expression _where;3813    List<Ordering> _orderBys;3814    int? _limit;3815    int? _offset;38163817    BaseTableQuery _joinInner;3818    Expression _joinInnerKeySelector;3819    BaseTableQuery _joinOuter;3820    Expression _joinOuterKeySelector;3821    Expression _joinSelector;38223823    Expression _selector;38243825    TableQuery (SQLiteConnection conn, TableMapping table)3826    {3827      Connection = conn;3828      Table = table;3829    }38303831    public TableQuery (SQLiteConnection conn)3832    {3833      Connection = conn;3834      Table = Connection.GetMapping (typeof (T));3835    }38363837    public TableQuery<U> Clone<U> ()3838    {3839      var q = new TableQuery<U> (Connection, Table);3840      q._where = _where;3841      q._deferred = _deferred;3842      if (_orderBys != null) {3843        q._orderBys = new List<Ordering> (_orderBys);3844      }3845      q._limit = _limit;3846      q._offset = _offset;3847      q._joinInner = _joinInner;3848      q._joinInnerKeySelector = _joinInnerKeySelector;3849      q._joinOuter = _joinOuter;3850      q._joinOuterKeySelector = _joinOuterKeySelector;3851      q._joinSelector = _joinSelector;3852      q._selector = _selector;3853      return q;3854    }38553856    /// <summary>3857    /// Filters the query based on a predicate.3858    /// </summary>3859    public TableQuery<T> Where (Expression<Func<T, bool>> predExpr)3860    {3861      if (predExpr.NodeType == ExpressionType.Lambda) {3862        var lambda = (LambdaExpression)predExpr;3863        var pred = lambda.Body;3864        var q = Clone<T> ();3865        q.AddWhere (pred);3866        return q;3867      }3868      else {3869        throw new NotSupportedException ("Must be a predicate");3870      }3871    }38723873    /// <summary>3874    /// Delete all the rows that match this query.3875    /// </summary>3876    public int Delete ()3877    {3878      return Delete (null);3879    }38803881    /// <summary>3882    /// Delete all the rows that match this query and the given predicate.3883    /// </summary>3884    public int Delete (Expression<Func<T, bool>> predExpr)3885    {3886      if (_limit.HasValue || _offset.HasValue)3887        throw new InvalidOperationException ("Cannot delete with limits or offsets");38883889      if (_where == null && predExpr == null)3890        throw new InvalidOperationException ("No condition specified");38913892      var pred = _where;38933894      if (predExpr != null && predExpr.NodeType == ExpressionType.Lambda) {3895        var lambda = (LambdaExpression)predExpr;3896        pred = pred != null ? Expression.AndAlso (pred, lambda.Body) : lambda.Body;3897      }38983899      var args = new List<object> ();3900      var cmdText = "delete from \"" + Table.TableName + "\"";3901      var w = CompileExpr (pred, args);3902      cmdText += " where " + w.CommandText;39033904      var command = Connection.CreateCommand (cmdText, args.ToArray ());39053906      int result = command.ExecuteNonQuery ();3907      return result;3908    }39093910    /// <summary>3911    /// Yields a given number of elements from the query and then skips the remainder.3912    /// </summary>3913    public TableQuery<T> Take (int n)3914    {3915      var q = Clone<T> ();3916      q._limit = n;3917      return q;3918    }39193920    /// <summary>3921    /// Skips a given number of elements from the query and then yields the remainder.3922    /// </summary>3923    public TableQuery<T> Skip (int n)3924    {3925      var q = Clone<T> ();3926      q._offset = n;3927      return q;3928    }39293930    /// <summary>3931    /// Returns the element at a given index3932    /// </summary>3933    public T ElementAt (int index)3934    {3935      return Skip (index).Take (1).First ();3936    }39373938    bool _deferred;3939    public TableQuery<T> Deferred ()3940    {3941      var q = Clone<T> ();3942      q._deferred = true;3943      return q;3944    }39453946    /// <summary>3947    /// Order the query results according to a key.3948    /// </summary>3949    public TableQuery<T> OrderBy<U> (Expression<Func<T, U>> orderExpr)3950    {3951      return AddOrderBy<U> (orderExpr, true);3952    }39533954    /// <summary>3955    /// Order the query results according to a key.3956    /// </summary>3957    public TableQuery<T> OrderByDescending<U> (Expression<Func<T, U>> orderExpr)3958    {3959      return AddOrderBy<U> (orderExpr, false);3960    }39613962    /// <summary>3963    /// Order the query results according to a key.3964    /// </summary>3965    public TableQuery<T> ThenBy<U> (Expression<Func<T, U>> orderExpr)3966    {3967      return AddOrderBy<U> (orderExpr, true);3968    }39693970    /// <summary>3971    /// Order the query results according to a key.3972    /// </summary>3973    public TableQuery<T> ThenByDescending<U> (Expression<Func<T, U>> orderExpr)3974    {3975      return AddOrderBy<U> (orderExpr, false);3976    }39773978    TableQuery<T> AddOrderBy<U> (Expression<Func<T, U>> orderExpr, bool asc)3979    {3980      if (orderExpr.NodeType == ExpressionType.Lambda) {3981        var lambda = (LambdaExpression)orderExpr;39823983        MemberExpression mem = null;39843985        var unary = lambda.Body as UnaryExpression;3986        if (unary != null && unary.NodeType == ExpressionType.Convert) {3987          mem = unary.Operand as MemberExpression;3988        }3989        else {3990          mem = lambda.Body as MemberExpression;3991        }39923993        if (mem != null && (mem.Expression.NodeType == ExpressionType.Parameter)) {3994          var q = Clone<T> ();3995          if (q._orderBys == null) {3996            q._orderBys = new List<Ordering> ();3997          }3998          q._orderBys.Add (new Ordering {3999            ColumnName = Table.FindColumnWithPropertyName (mem.Member.Name).Name,4000            Ascending = asc4001          });4002          return q;4003        }4004        else {4005          throw new NotSupportedException ("Order By does not support: " + orderExpr);4006        }4007      }4008      else {4009        throw new NotSupportedException ("Must be a predicate");4010      }4011    }40124013    private void AddWhere (Expression pred)4014    {4015      if (_where == null) {4016        _where = pred;4017      }4018      else {4019        _where = Expression.AndAlso (_where, pred);4020      }4021    }40224023    ///// <summary>4024    ///// Performs an inner join of two queries based on matching keys extracted from the elements.4025    ///// </summary>4026    //public TableQuery<TResult> Join<TInner, TKey, TResult> (4027    //  TableQuery<TInner> inner,4028    //  Expression<Func<T, TKey>> outerKeySelector,4029    //  Expression<Func<TInner, TKey>> innerKeySelector,4030    //  Expression<Func<T, TInner, TResult>> resultSelector)4031    //{4032    //  var q = new TableQuery<TResult> (Connection, Connection.GetMapping (typeof (TResult))) {4033    //    _joinOuter = this,4034    //    _joinOuterKeySelector = outerKeySelector,4035    //    _joinInner = inner,4036    //    _joinInnerKeySelector = innerKeySelector,4037    //    _joinSelector = resultSelector,4038    //  };  4039    //  return q;  4040    //}  40414042    private SQLiteCommand GenerateCommand (string selectionList)4043    {4044      if (_joinInner != null && _joinOuter != null) {4045        throw new NotSupportedException ("Joins are not supported.");4046      }4047      else {4048        var cmdText = "select " + selectionList + " from \"" + Table.TableName + "\"";4049        var args = new List<object> ();4050        if (_where != null) {4051          var w = CompileExpr (_where, args);4052          cmdText += " where " + w.CommandText;4053        }4054        if ((_orderBys != null) && (_orderBys.Count > 0)) {4055          var t = string.Join (", ", _orderBys.Select (o => "\"" + o.ColumnName + "\"" + (o.Ascending ? "" : " desc")).T4056          cmdText += " order by " + t;4057        }4058        if (_limit.HasValue) {4059          cmdText += " limit " + _limit.Value;4060        }4061        if (_offset.HasValue) {4062          if (!_limit.HasValue) {4063            cmdText += " limit -1 ";4064          }4065          cmdText += " offset " + _offset.Value;4042    // Not needed until Joins are supported4043    // Keeping this commented out forces the default Linq to objects processor to run4044    //public TableQuery<TResult> Select<TResult> (Expression<Func<T, TResult>> selector)4045    //{4046    //  var q = Clone<TResult> ();4047    //  q._selector = selector;4048    //  return q;4049    //}40504051    private SQLiteCommand GenerateCommand (string selectionList)4052    {4053      if (_joinInner != null && _joinOuter != null) {4054        throw new NotSupportedException ("Joins are not supported.");4055      }4056      else {4057        var cmdText = "select " + selectionList + " from \"" + Table.TableName + "\"";4058        var args = new List<object> ();4059        if (_where != null) {4060          var w = CompileExpr (_where, args);4061          cmdText += " where " + w.CommandText;4062        }4063        if ((_orderBys != null) && (_orderBys.Count > 0)) {4064          var t = string.Join (", ", _orderBys.Select (o => "\"" + o.ColumnName + "\"" + (o.Ascending ? "" : " desc")).T4065          cmdText += " order by " + t;  4066        }4067        return Connection.CreateCommand (cmdText, args.ToArray ());4068      }4069    }40704071    class CompileResult4072    {4073      public string CommandText { get; set; }40744075      public object Value { get; set; }4076    }40774078    private CompileResult CompileExpr (Expression expr, List<object> queryArgs)4079    {4080      if (expr == null) {4081        throw new NotSupportedException ("Expression is NULL");4082      }4083      else if (expr is BinaryExpression) {4084        var bin = (BinaryExpression)expr;40854086        // VB turns 'x=="foo"' into 'CompareString(x,"foo",true/false)==0', so we need to unwrap it4087        // http://blogs.msdn.com/b/vbteam/archive/2007/09/18/vb-expression-trees-string-comparisons.aspx4088        if (bin.Left.NodeType == ExpressionType.Call) {4089          var call = (MethodCallExpression)bin.Left;4090          if (call.Method.DeclaringType.FullName == "Microsoft.VisualBasic.CompilerServices.Operators"4091            && call.Method.Name == "CompareString")4092            bin = Expression.MakeBinary (bin.NodeType, call.Arguments[0], call.Arguments[1]);4093        }4067        if (_limit.HasValue) {4068          cmdText += " limit " + _limit.Value;4069        }4070        if (_offset.HasValue) {4071          if (!_limit.HasValue) {4072            cmdText += " limit -1 ";4073          }4074          cmdText += " offset " + _offset.Value;4075        }4076        return Connection.CreateCommand (cmdText, args.ToArray ());4077      }4078    }40794080    class CompileResult4081    {4082      public string CommandText { get; set; }40834084      public object Value { get; set; }4085    }40864087    private CompileResult CompileExpr (Expression expr, List<object> queryArgs)4088    {4089      if (expr == null) {4090        throw new NotSupportedException ("Expression is NULL");4091      }4092      else if (expr is BinaryExpression) {4093        var bin = (BinaryExpression)expr;  409440954096        var leftr = CompileExpr (bin.Left, queryArgs);4097        var rightr = CompileExpr (bin.Right, queryArgs);40984099        //If either side is a parameter and is null, then handle the other side specially (for "is null"/"is not null")4100        string text;4101        if (leftr.CommandText == "?" && leftr.Value == null)4102          text = CompileNullBinaryExpression (bin, rightr);4103        else if (rightr.CommandText == "?" && rightr.Value == null)4104          text = CompileNullBinaryExpression (bin, leftr);4105        else4106          text = "(" + leftr.CommandText + " " + GetSqlName (bin) + " " + rightr.CommandText + ")";4107        return new CompileResult { CommandText = text };4108      }4109      else if (expr.NodeType == ExpressionType.Not) {4110        var operandExpr = ((UnaryExpression)expr).Operand;4111        var opr = CompileExpr (operandExpr, queryArgs);4112        object val = opr.Value;4113        if (val is bool)4114          val = !((bool)val);4115        return new CompileResult {4116          CommandText = "NOT(" + opr.CommandText + ")",4117          Value = val4118        };4119      }4120      else if (expr.NodeType == ExpressionType.Call) {41214122        var call = (MethodCallExpression)expr;4123        var args = new CompileResult[call.Arguments.Count];4124        var obj = call.Object != null ? CompileExpr (call.Object, queryArgs) : null;41254126        for (var i = 0; i < args.Length; i++) {4127          args[i] = CompileExpr (call.Arguments[i], queryArgs);4128        }41294130        var sqlCall = "";41314132        if (call.Method.Name == "Like" && args.Length == 2) {4133          sqlCall = "(" + args[0].CommandText + " like " + args[1].CommandText + ")";4134        }4135        else if (call.Method.Name == "Contains" && args.Length == 2) {4136          sqlCall = "(" + args[1].CommandText + " in " + args[0].CommandText + ")";4095        // VB turns 'x=="foo"' into 'CompareString(x,"foo",true/false)==0', so we need to unwrap it4096        // http://blogs.msdn.com/b/vbteam/archive/2007/09/18/vb-expression-trees-string-comparisons.aspx4097        if (bin.Left.NodeType == ExpressionType.Call) {4098          var call = (MethodCallExpression)bin.Left;4099          if (call.Method.DeclaringType.FullName == "Microsoft.VisualBasic.CompilerServices.Operators"4100            && call.Method.Name == "CompareString")4101            bin = Expression.MakeBinary (bin.NodeType, call.Arguments[0], call.Arguments[1]);4102        }410341044105        var leftr = CompileExpr (bin.Left, queryArgs);4106        var rightr = CompileExpr (bin.Right, queryArgs);41074108        //If either side is a parameter and is null, then handle the other side specially (for "is null"/"is not null")4109        string text;4110        if (leftr.CommandText == "?" && leftr.Value == null)4111          text = CompileNullBinaryExpression (bin, rightr);4112        else if (rightr.CommandText == "?" && rightr.Value == null)4113          text = CompileNullBinaryExpression (bin, leftr);4114        else4115          text = "(" + leftr.CommandText + " " + GetSqlName (bin) + " " + rightr.CommandText + ")";4116        return new CompileResult { CommandText = text };4117      }4118      else if (expr.NodeType == ExpressionType.Not) {4119        var operandExpr = ((UnaryExpression)expr).Operand;4120        var opr = CompileExpr (operandExpr, queryArgs);4121        object val = opr.Value;4122        if (val is bool)4123          val = !((bool)val);4124        return new CompileResult {4125          CommandText = "NOT(" + opr.CommandText + ")",4126          Value = val4127        };4128      }4129      else if (expr.NodeType == ExpressionType.Call) {41304131        var call = (MethodCallExpression)expr;4132        var args = new CompileResult[call.Arguments.Count];4133        var obj = call.Object != null ? CompileExpr (call.Object, queryArgs) : null;41344135        for (var i = 0; i < args.Length; i++) {4136          args[i] = CompileExpr (call.Arguments[i], queryArgs);  4137        }4138        else if (call.Method.Name == "Contains" && args.Length == 1) {4139          if (call.Object != null && call.Object.Type == typeof (string)) {4140            sqlCall = "( instr(" + obj.CommandText + "," + args[0].CommandText + ") >0 )";4141          }4142          else {4143            sqlCall = "(" + args[0].CommandText + " in " + obj.CommandText + ")";4144          }4145        }4146        else if (call.Method.Name == "StartsWith" && args.Length >= 1) {4147          var startsWithCmpOp = StringComparison.CurrentCulture;4148          if (args.Length == 2) {4149            startsWithCmpOp = (StringComparison)args[1].Value;41384139        var sqlCall = "";41404141        if (call.Method.Name == "Like" && args.Length == 2) {4142          sqlCall = "(" + args[0].CommandText + " like " + args[1].CommandText + ")";4143        }4144        else if (call.Method.Name == "Contains" && args.Length == 2) {4145          sqlCall = "(" + args[1].CommandText + " in " + args[0].CommandText + ")";4146        }4147        else if (call.Method.Name == "Contains" && args.Length == 1) {4148          if (call.Object != null && call.Object.Type == typeof (string)) {4149            sqlCall = "( instr(" + obj.CommandText + "," + args[0].CommandText + ") >0 )";  4150          }4151          switch (startsWithCmpOp) {4152            case StringComparison.Ordinal:4153            case StringComparison.CurrentCulture:4154              sqlCall = "( substr(" + obj.CommandText + ", 1, " + args[0].Value.ToString ().Length + ") =  " + args[0].C4155              break;4156            case StringComparison.OrdinalIgnoreCase:4157            case StringComparison.CurrentCultureIgnoreCase:4158              sqlCall = "(" + obj.CommandText + " like (" + args[0].CommandText + " || '%'))";4159              break;4160          }41614162        }4163        else if (call.Method.Name == "EndsWith" && args.Length >= 1) {4164          var endsWithCmpOp = StringComparison.CurrentCulture;4165          if (args.Length == 2) {4166            endsWithCmpOp = (StringComparison)args[1].Value;4167          }4168          switch (endsWithCmpOp) {4169            case StringComparison.Ordinal:4170            case StringComparison.CurrentCulture:4171              sqlCall = "( substr(" + obj.CommandText + ", length(" + obj.CommandText + ") - " + args[0].Value.ToString 4172              break;4173            case StringComparison.OrdinalIgnoreCase:4174            case StringComparison.CurrentCultureIgnoreCase:4175              sqlCall = "(" + obj.CommandText + " like ('%' || " + args[0].CommandText + "))";4176              break;4177          }4178        }4179        else if (call.Method.Name == "Equals" && args.Length == 1) {4180          sqlCall = "(" + obj.CommandText + " = (" + args[0].CommandText + "))";4181        }4182        else if (call.Method.Name == "ToLower") {4183          sqlCall = "(lower(" + obj.CommandText + "))";4184        }4185        else if (call.Method.Name == "ToUpper") {4186          sqlCall = "(upper(" + obj.CommandText + "))";4151          else {4152            sqlCall = "(" + args[0].CommandText + " in " + obj.CommandText + ")";4153          }4154        }4155        else if (call.Method.Name == "StartsWith" && args.Length >= 1) {4156          var startsWithCmpOp = StringComparison.CurrentCulture;4157          if (args.Length == 2) {4158            startsWithCmpOp = (StringComparison)args[1].Value;4159          }4160          switch (startsWithCmpOp) {4161            case StringComparison.Ordinal:4162            case StringComparison.CurrentCulture:4163              sqlCall = "( substr(" + obj.CommandText + ", 1, " + args[0].Value.ToString ().Length + ") =  " + args[0].C4164              break;4165            case StringComparison.OrdinalIgnoreCase:4166            case StringComparison.CurrentCultureIgnoreCase:4167              sqlCall = "(" + obj.CommandText + " like (" + args[0].CommandText + " || '%'))";4168              break;4169          }41704171        }4172        else if (call.Method.Name == "EndsWith" && args.Length >= 1) {4173          var endsWithCmpOp = StringComparison.CurrentCulture;4174          if (args.Length == 2) {4175            endsWithCmpOp = (StringComparison)args[1].Value;4176          }4177          switch (endsWithCmpOp) {4178            case StringComparison.Ordinal:4179            case StringComparison.CurrentCulture:4180              sqlCall = "( substr(" + obj.CommandText + ", length(" + obj.CommandText + ") - " + args[0].Value.ToString 4181              break;4182            case StringComparison.OrdinalIgnoreCase:4183            case StringComparison.CurrentCultureIgnoreCase:4184              sqlCall = "(" + obj.CommandText + " like ('%' || " + args[0].CommandText + "))";4185              break;4186          }  4187        }4188        else if (call.Method.Name == "Replace" && args.Length == 2) {4189          sqlCall = "(replace(" + obj.CommandText + "," + args[0].CommandText + "," + args[1].CommandText + "))";4188        else if (call.Method.Name == "Equals" && args.Length == 1) {4189          sqlCall = "(" + obj.CommandText + " = (" + args[0].CommandText + "))";  4190        }4191        else if (call.Method.Name == "IsNullOrEmpty" && args.Length == 1) {4192          sqlCall = "(" + args[0].CommandText + " is null or" + args[0].CommandText + " ='' )";4191        else if (call.Method.Name == "ToLower") {4192          sqlCall = "(lower(" + obj.CommandText + "))";  4193        }4194        else {4195          sqlCall = call.Method.Name.ToLower () + "(" + string.Join (",", args.Select (a => a.CommandText).ToArray ()) +4194        else if (call.Method.Name == "ToUpper") {4195          sqlCall = "(upper(" + obj.CommandText + "))";  4196        }4197        return new CompileResult { CommandText = sqlCall };41984199      }4200      else if (expr.NodeType == ExpressionType.Constant) {4201        var c = (ConstantExpression)expr;4202        queryArgs.Add (c.Value);4203        return new CompileResult {4204          CommandText = "?",4205          Value = c.Value4206        };4207      }4208      else if (expr.NodeType == ExpressionType.Convert) {4209        var u = (UnaryExpression)expr;4210        var ty = u.Type;4211        var valr = CompileExpr (u.Operand, queryArgs);4197        else if (call.Method.Name == "Replace" && args.Length == 2) {4198          sqlCall = "(replace(" + obj.CommandText + "," + args[0].CommandText + "," + args[1].CommandText + "))";4199        }4200        else if (call.Method.Name == "IsNullOrEmpty" && args.Length == 1) {4201          sqlCall = "(" + args[0].CommandText + " is null or" + args[0].CommandText + " ='' )";4202        }4203        else {4204          sqlCall = call.Method.Name.ToLower () + "(" + string.Join (",", args.Select (a => a.CommandText).ToArray ()) +4205        }4206        return new CompileResult { CommandText = sqlCall };42074208      }4209      else if (expr.NodeType == ExpressionType.Constant) {4210        var c = (ConstantExpression)expr;4211        queryArgs.Add (c.Value);  4212        return new CompileResult {4213          CommandText = valr.CommandText,4214          Value = valr.Value != null ? ConvertTo (valr.Value, ty) : null4213          CommandText = "?",4214          Value = c.Value  4215        };  4216      }4217      else if (expr.NodeType == ExpressionType.MemberAccess) {4218        var mem = (MemberExpression)expr;42194220        var paramExpr = mem.Expression as ParameterExpression;4221        if (paramExpr == null) {4222          var convert = mem.Expression as UnaryExpression;4223          if (convert != null && convert.NodeType == ExpressionType.Convert) {4224            paramExpr = convert.Operand as ParameterExpression;4225          }4226        }42274228        if (paramExpr != null) {4229          //4230          // This is a column of our table, output just the column name4231          // Need to translate it if that column name is mapped4232          //4233          var columnName = Table.FindColumnWithPropertyName (mem.Member.Name).Name;4234          return new CompileResult { CommandText = "\"" + columnName + "\"" };4217      else if (expr.NodeType == ExpressionType.Convert) {4218        var u = (UnaryExpression)expr;4219        var ty = u.Type;4220        var valr = CompileExpr (u.Operand, queryArgs);4221        return new CompileResult {4222          CommandText = valr.CommandText,4223          Value = valr.Value != null ? ConvertTo (valr.Value, ty) : null4224        };4225      }4226      else if (expr.NodeType == ExpressionType.MemberAccess) {4227        var mem = (MemberExpression)expr;42284229        var paramExpr = mem.Expression as ParameterExpression;4230        if (paramExpr == null) {4231          var convert = mem.Expression as UnaryExpression;4232          if (convert != null && convert.NodeType == ExpressionType.Convert) {4233            paramExpr = convert.Operand as ParameterExpression;4234          }  4235        }4236        else {4237          object obj = null;4238          if (mem.Expression != null) {4239            var r = CompileExpr (mem.Expression, queryArgs);4240            if (r.Value == null) {4241              throw new NotSupportedException ("Member access failed to compile expression");4242            }4243            if (r.CommandText == "?") {4244              queryArgs.RemoveAt (queryArgs.Count - 1);4245            }4246            obj = r.Value;4247          }42484249          //4250          // Get the member value4251          //4252          object val = null;42534254          if (mem.Member is PropertyInfo) {4255            var m = (PropertyInfo)mem.Member;4256            val = m.GetValue (obj, null);4257          }4258          else if (mem.Member is FieldInfo) {4259            var m = (FieldInfo)mem.Member;4260            val = m.GetValue (obj);4261          }4262          else {4263            throw new NotSupportedException ("MemberExpr: " + mem.Member.GetType ());4264          }42654266          //4267          // Work special magic for enumerables4268          //4269          if (val != null && val is System.Collections.IEnumerable && !(val is string) && !(val is System.Collections.Ge4270            var sb = new System.Text.StringBuilder ();4271            sb.Append ("(");4272            var head = "";4273            foreach (var a in (System.Collections.IEnumerable)val) {4274              queryArgs.Add (a);4275              sb.Append (head);4276              sb.Append ("?");4277              head = ",";4278            }4279            sb.Append (")");4280            return new CompileResult {4281              CommandText = sb.ToString (),4282              Value = val4283            };4284          }4285          else {4286            queryArgs.Add (val);4287            return new CompileResult {4288              CommandText = "?",4289              Value = val4290            };4291          }4292        }4293      }4294      throw new NotSupportedException ("Cannot compile: " + expr.NodeType.ToString ());4295    }42964297    static object ConvertTo (object obj, Type t)4298    {4299      Type nut = Nullable.GetUnderlyingType (t);43004301      if (nut != null) {4302        if (obj == null)4303          return null;4304        return Convert.ChangeType (obj, nut);4305      }4306      else {4307        return Convert.ChangeType (obj, t);4308      }4309    }43104311    /// <summary>4312    /// Compiles a BinaryExpression where one of the parameters is null.4313    /// </summary>4314    /// <param name="expression">The expression to compile</param>4315    /// <param name="parameter">The non-null parameter</param>4316    private string CompileNullBinaryExpression (BinaryExpression expression, CompileResult parameter)4317    {4318      if (expression.NodeType == ExpressionType.Equal)4319        return "(" + parameter.CommandText + " is ?)";4320      else if (expression.NodeType == ExpressionType.NotEqual)4321        return "(" + parameter.CommandText + " is not ?)";4322      else if (expression.NodeType == ExpressionType.GreaterThan4323        || expression.NodeType == ExpressionType.GreaterThanOrEqual4324        || expression.NodeType == ExpressionType.LessThan4325        || expression.NodeType == ExpressionType.LessThanOrEqual)4326        return "(" + parameter.CommandText + " < ?)"; // always false4327      else4328        throw new NotSupportedException ("Cannot compile Null-BinaryExpression with type " + expression.NodeType.ToStrin4329    }43304331    string GetSqlName (Expression expr)4332    {4333      var n = expr.NodeType;4334      if (n == ExpressionType.GreaterThan)4335        return ">";4336      else if (n == ExpressionType.GreaterThanOrEqual) {4337        return ">=";4338      }4339      else if (n == ExpressionType.LessThan) {4340        return "<";4341      }4342      else if (n == ExpressionType.LessThanOrEqual) {4343        return "<=";4344      }4345      else if (n == ExpressionType.And) {4346        return "&";42364237        if (paramExpr != null) {4238          //4239          // This is a column of our table, output just the column name4240          // Need to translate it if that column name is mapped4241          //4242          var columnName = Table.FindColumnWithPropertyName (mem.Member.Name).Name;4243          return new CompileResult { CommandText = "\"" + columnName + "\"" };4244        }4245        else {4246          object obj = null;4247          if (mem.Expression != null) {4248            var r = CompileExpr (mem.Expression, queryArgs);4249            if (r.Value == null) {4250              throw new NotSupportedException ("Member access failed to compile expression");4251            }4252            if (r.CommandText == "?") {4253              queryArgs.RemoveAt (queryArgs.Count - 1);4254            }4255            obj = r.Value;4256          }42574258          //4259          // Get the member value4260          //4261          object val = null;42624263          if (mem.Member is PropertyInfo) {4264            var m = (PropertyInfo)mem.Member;4265            val = m.GetValue (obj, null);4266          }4267          else if (mem.Member is FieldInfo) {4268            var m = (FieldInfo)mem.Member;4269            val = m.GetValue (obj);4270          }4271          else {4272            throw new NotSupportedException ("MemberExpr: " + mem.Member.GetType ());4273          }42744275          //4276          // Work special magic for enumerables4277          //4278          if (val != null && val is System.Collections.IEnumerable && !(val is string) && !(val is System.Collections.Ge4279            var sb = new System.Text.StringBuilder ();4280            sb.Append ("(");4281            var head = "";4282            foreach (var a in (System.Collections.IEnumerable)val) {4283              queryArgs.Add (a);4284              sb.Append (head);4285              sb.Append ("?");4286              head = ",";4287            }4288            sb.Append (")");4289            return new CompileResult {4290              CommandText = sb.ToString (),4291              Value = val4292            };4293          }4294          else {4295            queryArgs.Add (val);4296            return new CompileResult {4297              CommandText = "?",4298              Value = val4299            };4300          }4301        }4302      }4303      throw new NotSupportedException ("Cannot compile: " + expr.NodeType.ToString ());4304    }43054306    static object ConvertTo (object obj, Type t)4307    {4308      Type nut = Nullable.GetUnderlyingType (t);43094310      if (nut != null) {4311        if (obj == null)4312          return null;4313        return Convert.ChangeType (obj, nut);4314      }4315      else {4316        return Convert.ChangeType (obj, t);4317      }4318    }43194320    /// <summary>4321    /// Compiles a BinaryExpression where one of the parameters is null.4322    /// </summary>4323    /// <param name="expression">The expression to compile</param>4324    /// <param name="parameter">The non-null parameter</param>4325    private string CompileNullBinaryExpression (BinaryExpression expression, CompileResult parameter)4326    {4327      if (expression.NodeType == ExpressionType.Equal)4328        return "(" + parameter.CommandText + " is ?)";4329      else if (expression.NodeType == ExpressionType.NotEqual)4330        return "(" + parameter.CommandText + " is not ?)";4331      else if (expression.NodeType == ExpressionType.GreaterThan4332        || expression.NodeType == ExpressionType.GreaterThanOrEqual4333        || expression.NodeType == ExpressionType.LessThan4334        || expression.NodeType == ExpressionType.LessThanOrEqual)4335        return "(" + parameter.CommandText + " < ?)"; // always false4336      else4337        throw new NotSupportedException ("Cannot compile Null-BinaryExpression with type " + expression.NodeType.ToStrin4338    }43394340    string GetSqlName (Expression expr)4341    {4342      var n = expr.NodeType;4343      if (n == ExpressionType.GreaterThan)4344        return ">";4345      else if (n == ExpressionType.GreaterThanOrEqual) {4346        return ">=";  4347      }4348      else if (n == ExpressionType.AndAlso) {4349        return "and";4348      else if (n == ExpressionType.LessThan) {4349        return "<";  4350      }4351      else if (n == ExpressionType.Or) {4352        return "|";4351      else if (n == ExpressionType.LessThanOrEqual) {4352        return "<=";  4353      }4354      else if (n == ExpressionType.OrElse) {4355        return "or";4354      else if (n == ExpressionType.And) {4355        return "&";  4356      }4357      else if (n == ExpressionType.Equal) {4358        return "=";4357      else if (n == ExpressionType.AndAlso) {4358        return "and";  4359      }4360      else if (n == ExpressionType.NotEqual) {4361        return "!=";4360      else if (n == ExpressionType.Or) {4361        return "|";  4362      }4363      else {4364        throw new NotSupportedException ("Cannot get SQL for: " + n);4363      else if (n == ExpressionType.OrElse) {4364        return "or";  4365      }4366    }43674368    /// <summary>4369    /// Execute SELECT COUNT(*) on the query4370    /// </summary>4371    public int Count ()4372    {4373      return GenerateCommand ("count(*)").ExecuteScalar<int> ();4374    }43754376    /// <summary>4377    /// Execute SELECT COUNT(*) on the query with an additional WHERE clause.4378    /// </summary>4379    public int Count (Expression<Func<T, bool>> predExpr)4380    {4381      return Where (predExpr).Count ();4382    }43834384    public IEnumerator<T> GetEnumerator ()4385    {4386      if (!_deferred)4387        return GenerateCommand ("*").ExecuteQuery<T> ().GetEnumerator ();43884389      return GenerateCommand ("*").ExecuteDeferredQuery<T> ().GetEnumerator ();4390    }43914392    System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator ()4393    {4394      return GetEnumerator ();4395    }43964397    /// <summary>4398    /// Queries the database and returns the results as a List.4399    /// </summary>4400    public List<T> ToList ()4401    {4402      return GenerateCommand ("*").ExecuteQuery<T> ();4403    }44044405    /// <summary>4406    /// Queries the database and returns the results as an array.4407    /// </summary>4408    public T[] ToArray ()4409    {4410      return GenerateCommand ("*").ExecuteQuery<T> ().ToArray ();4411    }44124413    /// <summary>4414    /// Returns the first element of this query.4415    /// </summary>4416    public T First ()4417    {4418      var query = Take (1);4419      return query.ToList ().First ();4366      else if (n == ExpressionType.Equal) {4367        return "=";4368      }4369      else if (n == ExpressionType.NotEqual) {4370        return "!=";4371      }4372      else {4373        throw new NotSupportedException ("Cannot get SQL for: " + n);4374      }4375    }43764377    /// <summary>4378    /// Execute SELECT COUNT(*) on the query4379    /// </summary>4380    public int Count ()4381    {4382      return GenerateCommand ("count(*)").ExecuteScalar<int> ();4383    }43844385    /// <summary>4386    /// Execute SELECT COUNT(*) on the query with an additional WHERE clause.4387    /// </summary>4388    public int Count (Expression<Func<T, bool>> predExpr)4389    {4390      return Where (predExpr).Count ();4391    }43924393    public IEnumerator<T> GetEnumerator ()4394    {4395      if (!_deferred)4396        return GenerateCommand ("*").ExecuteQuery<T> ().GetEnumerator ();43974398      return GenerateCommand ("*").ExecuteDeferredQuery<T> ().GetEnumerator ();4399    }44004401    System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator ()4402    {4403      return GetEnumerator ();4404    }44054406    /// <summary>4407    /// Queries the database and returns the results as a List.4408    /// </summary>4409    public List<T> ToList ()4410    {4411      return GenerateCommand ("*").ExecuteQuery<T> ();4412    }44134414    /// <summary>4415    /// Queries the database and returns the results as an array.4416    /// </summary>4417    public T[] ToArray ()4418    {4419      return GenerateCommand ("*").ExecuteQuery<T> ().ToArray ();  4420    }  4421  4422    /// <summary>4423    /// Returns the first element of this query, or null if no element is found.4423    /// Returns the first element of this query.  4424    /// </summary>4425    public T FirstOrDefault ()4425    public T First ()  4426    {  4427      var query = Take (1);4428      return query.ToList ().FirstOrDefault ();4428      return query.ToList ().First ();  4429    }  4430  4431    /// <summary>4432    /// Returns the first element of this query that matches the predicate.4432    /// Returns the first element of this query, or null if no element is found.  4433    /// </summary>4434    public T First (Expression<Func<T, bool>> predExpr)4434    public T FirstOrDefault ()  4435    {4436      return Where (predExpr).First ();4437    }44384439    /// <summary>4440    /// Returns the first element of this query that matches the predicate, or null4441    /// if no element is found.4436      var query = Take (1);4437      return query.ToList ().FirstOrDefault ();4438    }44394440    /// <summary>4441    /// Returns the first element of this query that matches the predicate.  4442    /// </summary>4443    public T FirstOrDefault (Expression<Func<T, bool>> predExpr)4443    public T First (Expression<Func<T, bool>> predExpr)  4444    {4445      return Where (predExpr).FirstOrDefault ();4445      return Where (predExpr).First ();  4446    }4447  }44484449  public static class SQLite34450  {4451    public enum Result : int4452    {4453      OK = 0,4454      Error = 1,4455      Internal = 2,4456      Perm = 3,4457      Abort = 4,4458      Busy = 5,4459      Locked = 6,4460      NoMem = 7,4461      ReadOnly = 8,4462      Interrupt = 9,4463      IOError = 10,4464      Corrupt = 11,4465      NotFound = 12,4466      Full = 13,4467      CannotOpen = 14,4468      LockErr = 15,4469      Empty = 16,4470      SchemaChngd = 17,4471      TooBig = 18,4472      Constraint = 19,4473      Mismatch = 20,4474      Misuse = 21,4475      NotImplementedLFS = 22,4476      AccessDenied = 23,4477      Format = 24,4478      Range = 25,4479      NonDBFile = 26,4480      Notice = 27,4481      Warning = 28,4482      Row = 100,4483      Done = 1014484    }44854486    public enum ExtendedResult : int4487    {4488      IOErrorRead = (Result.IOError | (1 << 8)),4489      IOErrorShortRead = (Result.IOError | (2 << 8)),4490      IOErrorWrite = (Result.IOError | (3 << 8)),4491      IOErrorFsync = (Result.IOError | (4 << 8)),4492      IOErrorDirFSync = (Result.IOError | (5 << 8)),4493      IOErrorTruncate = (Result.IOError | (6 << 8)),4494      IOErrorFStat = (Result.IOError | (7 << 8)),4495      IOErrorUnlock = (Result.IOError | (8 << 8)),4496      IOErrorRdlock = (Result.IOError | (9 << 8)),4497      IOErrorDelete = (Result.IOError | (10 << 8)),4498      IOErrorBlocked = (Result.IOError | (11 << 8)),4499      IOErrorNoMem = (Result.IOError | (12 << 8)),4500      IOErrorAccess = (Result.IOError | (13 << 8)),4501      IOErrorCheckReservedLock = (Result.IOError | (14 << 8)),4502      IOErrorLock = (Result.IOError | (15 << 8)),4503      IOErrorClose = (Result.IOError | (16 << 8)),4504      IOErrorDirClose = (Result.IOError | (17 << 8)),4505      IOErrorSHMOpen = (Result.IOError | (18 << 8)),4506      IOErrorSHMSize = (Result.IOError | (19 << 8)),4507      IOErrorSHMLock = (Result.IOError | (20 << 8)),4508      IOErrorSHMMap = (Result.IOError | (21 << 8)),4509      IOErrorSeek = (Result.IOError | (22 << 8)),4510      IOErrorDeleteNoEnt = (Result.IOError | (23 << 8)),4511      IOErrorMMap = (Result.IOError | (24 << 8)),4512      LockedSharedcache = (Result.Locked | (1 << 8)),4513      BusyRecovery = (Result.Busy | (1 << 8)),4514      CannottOpenNoTempDir = (Result.CannotOpen | (1 << 8)),4515      CannotOpenIsDir = (Result.CannotOpen | (2 << 8)),4516      CannotOpenFullPath = (Result.CannotOpen | (3 << 8)),4517      CorruptVTab = (Result.Corrupt | (1 << 8)),4518      ReadonlyRecovery = (Result.ReadOnly | (1 << 8)),4519      ReadonlyCannotLock = (Result.ReadOnly | (2 << 8)),4520      ReadonlyRollback = (Result.ReadOnly | (3 << 8)),4521      AbortRollback = (Result.Abort | (2 << 8)),4522      ConstraintCheck = (Result.Constraint | (1 << 8)),4523      ConstraintCommitHook = (Result.Constraint | (2 << 8)),4524      ConstraintForeignKey = (Result.Constraint | (3 << 8)),4525      ConstraintFunction = (Result.Constraint | (4 << 8)),4526      ConstraintNotNull = (Result.Constraint | (5 << 8)),4527      ConstraintPrimaryKey = (Result.Constraint | (6 << 8)),4528      ConstraintTrigger = (Result.Constraint | (7 << 8)),4529      ConstraintUnique = (Result.Constraint | (8 << 8)),4530      ConstraintVTab = (Result.Constraint | (9 << 8)),4531      NoticeRecoverWAL = (Result.Notice | (1 << 8)),4532      NoticeRecoverRollback = (Result.Notice | (2 << 8))4533    }453445354536    public enum ConfigOption : int4537    {4538      SingleThread = 1,4539      MultiThread = 2,4540      Serialized = 34541    }45424543    const string LibraryPath = "sqlite3";44474448    /// <summary>4449    /// Returns the first element of this query that matches the predicate, or null4450    /// if no element is found.4451    /// </summary>4452    public T FirstOrDefault (Expression<Func<T, bool>> predExpr)4453    {4454      return Where (predExpr).FirstOrDefault ();4455    }4456  }44574458  public static class SQLite34459  {4460    public enum Result : int4461    {4462      OK = 0,4463      Error = 1,4464      Internal = 2,4465      Perm = 3,4466      Abort = 4,4467      Busy = 5,4468      Locked = 6,4469      NoMem = 7,4470      ReadOnly = 8,4471      Interrupt = 9,4472      IOError = 10,4473      Corrupt = 11,4474      NotFound = 12,4475      Full = 13,4476      CannotOpen = 14,4477      LockErr = 15,4478      Empty = 16,4479      SchemaChngd = 17,4480      TooBig = 18,4481      Constraint = 19,4482      Mismatch = 20,4483      Misuse = 21,4484      NotImplementedLFS = 22,4485      AccessDenied = 23,4486      Format = 24,4487      Range = 25,4488      NonDBFile = 26,4489      Notice = 27,4490      Warning = 28,4491      Row = 100,4492      Done = 1014493    }44944495    public enum ExtendedResult : int4496    {4497      IOErrorRead = (Result.IOError | (1 << 8)),4498      IOErrorShortRead = (Result.IOError | (2 << 8)),4499      IOErrorWrite = (Result.IOError | (3 << 8)),4500      IOErrorFsync = (Result.IOError | (4 << 8)),4501      IOErrorDirFSync = (Result.IOError | (5 << 8)),4502      IOErrorTruncate = (Result.IOError | (6 << 8)),4503      IOErrorFStat = (Result.IOError | (7 << 8)),4504      IOErrorUnlock = (Result.IOError | (8 << 8)),4505      IOErrorRdlock = (Result.IOError | (9 << 8)),4506      IOErrorDelete = (Result.IOError | (10 << 8)),4507      IOErrorBlocked = (Result.IOError | (11 << 8)),4508      IOErrorNoMem = (Result.IOError | (12 << 8)),4509      IOErrorAccess = (Result.IOError | (13 << 8)),4510      IOErrorCheckReservedLock = (Result.IOError | (14 << 8)),4511      IOErrorLock = (Result.IOError | (15 << 8)),4512      IOErrorClose = (Result.IOError | (16 << 8)),4513      IOErrorDirClose = (Result.IOError | (17 << 8)),4514      IOErrorSHMOpen = (Result.IOError | (18 << 8)),4515      IOErrorSHMSize = (Result.IOError | (19 << 8)),4516      IOErrorSHMLock = (Result.IOError | (20 << 8)),4517      IOErrorSHMMap = (Result.IOError | (21 << 8)),4518      IOErrorSeek = (Result.IOError | (22 << 8)),4519      IOErrorDeleteNoEnt = (Result.IOError | (23 << 8)),4520      IOErrorMMap = (Result.IOError | (24 << 8)),4521      LockedSharedcache = (Result.Locked | (1 << 8)),4522      BusyRecovery = (Result.Busy | (1 << 8)),4523      CannottOpenNoTempDir = (Result.CannotOpen | (1 << 8)),4524      CannotOpenIsDir = (Result.CannotOpen | (2 << 8)),4525      CannotOpenFullPath = (Result.CannotOpen | (3 << 8)),4526      CorruptVTab = (Result.Corrupt | (1 << 8)),4527      ReadonlyRecovery = (Result.ReadOnly | (1 << 8)),4528      ReadonlyCannotLock = (Result.ReadOnly | (2 << 8)),4529      ReadonlyRollback = (Result.ReadOnly | (3 << 8)),4530      AbortRollback = (Result.Abort | (2 << 8)),4531      ConstraintCheck = (Result.Constraint | (1 << 8)),4532      ConstraintCommitHook = (Result.Constraint | (2 << 8)),4533      ConstraintForeignKey = (Result.Constraint | (3 << 8)),4534      ConstraintFunction = (Result.Constraint | (4 << 8)),4535      ConstraintNotNull = (Result.Constraint | (5 << 8)),4536      ConstraintPrimaryKey = (Result.Constraint | (6 << 8)),4537      ConstraintTrigger = (Result.Constraint | (7 << 8)),4538      ConstraintUnique = (Result.Constraint | (8 << 8)),4539      ConstraintVTab = (Result.Constraint | (9 << 8)),4540      NoticeRecoverWAL = (Result.Notice | (1 << 8)),4541      NoticeRecoverRollback = (Result.Notice | (2 << 8))4542    }4543  45444545#if !USE_CSHARP_SQLITE && !USE_WP8_NATIVE_SQLITE && !USE_SQLITEPCL_RAW4546    [DllImport(LibraryPath, EntryPoint = "sqlite3_threadsafe", CallingConvention=CallingConvention.Cdecl)]4547    public static extern int Threadsafe ();45484549    [DllImport(LibraryPath, EntryPoint = "sqlite3_open", CallingConvention=CallingConvention.Cdecl)]4550    public static extern Result Open ([MarshalAs(UnmanagedType.LPStr)] string filename, out IntPtr db);4545    public enum ConfigOption : int4546    {4547      SingleThread = 1,4548      MultiThread = 2,4549      Serialized = 34550    }  45514552    [DllImport(LibraryPath, EntryPoint = "sqlite3_open_v2", CallingConvention=CallingConvention.Cdecl)]4553    public static extern Result Open ([MarshalAs(UnmanagedType.LPStr)] string filename, out IntPtr db, int flags, [Marsh45544555    [DllImport(LibraryPath, EntryPoint = "sqlite3_open_v2", CallingConvention = CallingConvention.Cdecl)]4556    public static extern Result Open(byte[] filename, out IntPtr db, int flags, [MarshalAs (UnmanagedType.LPStr)] string4552    const string LibraryPath = "sqlite3";45534554#if !USE_CSHARP_SQLITE && !USE_WP8_NATIVE_SQLITE && !USE_SQLITEPCL_RAW4555    [DllImport(LibraryPath, EntryPoint = "sqlite3_threadsafe", CallingConvention=CallingConvention.Cdecl)]4556    public static extern int Threadsafe ();  45574558    [DllImport(LibraryPath, EntryPoint = "sqlite3_open16", CallingConvention = CallingConvention.Cdecl)]4559    public static extern Result Open16([MarshalAs(UnmanagedType.LPWStr)] string filename, out IntPtr db);4558    [DllImport(LibraryPath, EntryPoint = "sqlite3_open", CallingConvention=CallingConvention.Cdecl)]4559    public static extern Result Open ([MarshalAs(UnmanagedType.LPStr)] string filename, out IntPtr db);  45604561    [DllImport(LibraryPath, EntryPoint = "sqlite3_enable_load_extension", CallingConvention=CallingConvention.Cdecl)]4562    public static extern Result EnableLoadExtension (IntPtr db, int onoff);4561    [DllImport(LibraryPath, EntryPoint = "sqlite3_open_v2", CallingConvention=CallingConvention.Cdecl)]4562    public static extern Result Open ([MarshalAs(UnmanagedType.LPStr)] string filename, out IntPtr db, int flags, [Marsh  45634564    [DllImport(LibraryPath, EntryPoint = "sqlite3_close", CallingConvention=CallingConvention.Cdecl)]4565    public static extern Result Close (IntPtr db);4564    [DllImport(LibraryPath, EntryPoint = "sqlite3_open_v2", CallingConvention = CallingConvention.Cdecl)]4565    public static extern Result Open(byte[] filename, out IntPtr db, int flags, [MarshalAs (UnmanagedType.LPStr)] string  45664567    [DllImport(LibraryPath, EntryPoint = "sqlite3_close_v2", CallingConvention = CallingConvention.Cdecl)]4568    public static extern Result Close2(IntPtr db);4567    [DllImport(LibraryPath, EntryPoint = "sqlite3_open16", CallingConvention = CallingConvention.Cdecl)]4568    public static extern Result Open16([MarshalAs(UnmanagedType.LPWStr)] string filename, out IntPtr db);  45694570    [DllImport(LibraryPath, EntryPoint = "sqlite3_initialize", CallingConvention=CallingConvention.Cdecl)]4571    public static extern Result Initialize();4570    [DllImport(LibraryPath, EntryPoint = "sqlite3_enable_load_extension", CallingConvention=CallingConvention.Cdecl)]4571    public static extern Result EnableLoadExtension (IntPtr db, int onoff);  45724573    [DllImport(LibraryPath, EntryPoint = "sqlite3_shutdown", CallingConvention=CallingConvention.Cdecl)]4574    public static extern Result Shutdown();4573    [DllImport(LibraryPath, EntryPoint = "sqlite3_close", CallingConvention=CallingConvention.Cdecl)]4574    public static extern Result Close (IntPtr db);  45754576    [DllImport(LibraryPath, EntryPoint = "sqlite3_config", CallingConvention=CallingConvention.Cdecl)]4577    public static extern Result Config (ConfigOption option);4576    [DllImport(LibraryPath, EntryPoint = "sqlite3_close_v2", CallingConvention = CallingConvention.Cdecl)]4577    public static extern Result Close2(IntPtr db);  45784579    [DllImport(LibraryPath, EntryPoint = "sqlite3_win32_set_directory", CallingConvention=CallingConvention.Cdecl, CharS4580    public static extern int SetDirectory (uint directoryType, string directoryPath);4579    [DllImport(LibraryPath, EntryPoint = "sqlite3_initialize", CallingConvention=CallingConvention.Cdecl)]4580    public static extern Result Initialize();  45814582    [DllImport(LibraryPath, EntryPoint = "sqlite3_busy_timeout", CallingConvention=CallingConvention.Cdecl)]4583    public static extern Result BusyTimeout (IntPtr db, int milliseconds);4582    [DllImport(LibraryPath, EntryPoint = "sqlite3_shutdown", CallingConvention=CallingConvention.Cdecl)]4583    public static extern Result Shutdown();  45844585    [DllImport(LibraryPath, EntryPoint = "sqlite3_changes", CallingConvention=CallingConvention.Cdecl)]4586    public static extern int Changes (IntPtr db);4585    [DllImport(LibraryPath, EntryPoint = "sqlite3_config", CallingConvention=CallingConvention.Cdecl)]4586    public static extern Result Config (ConfigOption option);  45874588    [DllImport(LibraryPath, EntryPoint = "sqlite3_prepare_v2", CallingConvention=CallingConvention.Cdecl)]4589    public static extern Result Prepare2 (IntPtr db, [MarshalAs(UnmanagedType.LPStr)] string sql, int numBytes, out IntP4588    [DllImport(LibraryPath, EntryPoint = "sqlite3_win32_set_directory", CallingConvention=CallingConvention.Cdecl, CharS4589    public static extern int SetDirectory (uint directoryType, string directoryPath);  45904591#if NETFX_CORE4592    [DllImport (LibraryPath, EntryPoint = "sqlite3_prepare_v2", CallingConvention = CallingConvention.Cdecl)]4593    public static extern Result Prepare2 (IntPtr db, byte[] queryBytes, int numBytes, out IntPtr stmt, IntPtr pzTail);4594#endif45954596    public static IntPtr Prepare2 (IntPtr db, string query)4597    {4598      IntPtr stmt;4599#if NETFX_CORE4600            byte[] queryBytes = System.Text.UTF8Encoding.UTF8.GetBytes (query);4601            var r = Prepare2 (db, queryBytes, queryBytes.Length, out stmt, IntPtr.Zero);4602#else4603            var r = Prepare2 (db, query, System.Text.UTF8Encoding.UTF8.GetByteCount (query), out stmt, IntPtr.Zero);4604#endif4605      if (r != Result.OK) {4606        throw SQLiteException.New (r, GetErrmsg (db));4607      }4608      return stmt;4609    }46104611    [DllImport(LibraryPath, EntryPoint = "sqlite3_step", CallingConvention=CallingConvention.Cdecl)]4612    public static extern Result Step (IntPtr stmt);46134614    [DllImport(LibraryPath, EntryPoint = "sqlite3_reset", CallingConvention=CallingConvention.Cdecl)]4615    public static extern Result Reset (IntPtr stmt);46164617    [DllImport(LibraryPath, EntryPoint = "sqlite3_finalize", CallingConvention=CallingConvention.Cdecl)]4618    public static extern Result Finalize (IntPtr stmt);4591    [DllImport(LibraryPath, EntryPoint = "sqlite3_busy_timeout", CallingConvention=CallingConvention.Cdecl)]4592    public static extern Result BusyTimeout (IntPtr db, int milliseconds);45934594    [DllImport(LibraryPath, EntryPoint = "sqlite3_changes", CallingConvention=CallingConvention.Cdecl)]4595    public static extern int Changes (IntPtr db);45964597    [DllImport(LibraryPath, EntryPoint = "sqlite3_prepare_v2", CallingConvention=CallingConvention.Cdecl)]4598    public static extern Result Prepare2 (IntPtr db, [MarshalAs(UnmanagedType.LPStr)] string sql, int numBytes, out IntP45994600#if NETFX_CORE4601    [DllImport (LibraryPath, EntryPoint = "sqlite3_prepare_v2", CallingConvention = CallingConvention.Cdecl)]4602    public static extern Result Prepare2 (IntPtr db, byte[] queryBytes, int numBytes, out IntPtr stmt, IntPtr pzTail);4603#endif46044605    public static IntPtr Prepare2 (IntPtr db, string query)4606    {4607      IntPtr stmt;4608#if NETFX_CORE4609            byte[] queryBytes = System.Text.UTF8Encoding.UTF8.GetBytes (query);4610            var r = Prepare2 (db, queryBytes, queryBytes.Length, out stmt, IntPtr.Zero);4611#else4612            var r = Prepare2 (db, query, System.Text.UTF8Encoding.UTF8.GetByteCount (query), out stmt, IntPtr.Zero);4613#endif4614      if (r != Result.OK) {4615        throw SQLiteException.New (r, GetErrmsg (db));4616      }4617      return stmt;4618    }  46194620    [DllImport(LibraryPath, EntryPoint = "sqlite3_last_insert_rowid", CallingConvention=CallingConvention.Cdecl)]4621    public static extern long LastInsertRowid (IntPtr db);4620    [DllImport(LibraryPath, EntryPoint = "sqlite3_step", CallingConvention=CallingConvention.Cdecl)]4621    public static extern Result Step (IntPtr stmt);  46224623    [DllImport(LibraryPath, EntryPoint = "sqlite3_errmsg16", CallingConvention=CallingConvention.Cdecl)]4624    public static extern IntPtr Errmsg (IntPtr db);4623    [DllImport(LibraryPath, EntryPoint = "sqlite3_reset", CallingConvention=CallingConvention.Cdecl)]4624    public static extern Result Reset (IntPtr stmt);  46254626    public static string GetErrmsg (IntPtr db)4627    {4628      return Marshal.PtrToStringUni (Errmsg (db));4629    }46304631    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_parameter_index", CallingConvention=CallingConvention.Cdecl)]4632    public static extern int BindParameterIndex (IntPtr stmt, [MarshalAs(UnmanagedType.LPStr)] string name);46334634    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_null", CallingConvention=CallingConvention.Cdecl)]4635    public static extern int BindNull (IntPtr stmt, int index);46364637    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_int", CallingConvention=CallingConvention.Cdecl)]4638    public static extern int BindInt (IntPtr stmt, int index, int val);4626    [DllImport(LibraryPath, EntryPoint = "sqlite3_finalize", CallingConvention=CallingConvention.Cdecl)]4627    public static extern Result Finalize (IntPtr stmt);46284629    [DllImport(LibraryPath, EntryPoint = "sqlite3_last_insert_rowid", CallingConvention=CallingConvention.Cdecl)]4630    public static extern long LastInsertRowid (IntPtr db);46314632    [DllImport(LibraryPath, EntryPoint = "sqlite3_errmsg16", CallingConvention=CallingConvention.Cdecl)]4633    public static extern IntPtr Errmsg (IntPtr db);46344635    public static string GetErrmsg (IntPtr db)4636    {4637      return Marshal.PtrToStringUni (Errmsg (db));4638    }  46394640    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_int64", CallingConvention=CallingConvention.Cdecl)]4641    public static extern int BindInt64 (IntPtr stmt, int index, long val);4640    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_parameter_index", CallingConvention=CallingConvention.Cdecl)]4641    public static extern int BindParameterIndex (IntPtr stmt, [MarshalAs(UnmanagedType.LPStr)] string name);  46424643    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_double", CallingConvention=CallingConvention.Cdecl)]4644    public static extern int BindDouble (IntPtr stmt, int index, double val);4643    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_null", CallingConvention=CallingConvention.Cdecl)]4644    public static extern int BindNull (IntPtr stmt, int index);  46454646    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_text16", CallingConvention=CallingConvention.Cdecl, CharSet = Cha4647    public static extern int BindText (IntPtr stmt, int index, [MarshalAs(UnmanagedType.LPWStr)] string val, int n, IntP4646    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_int", CallingConvention=CallingConvention.Cdecl)]4647    public static extern int BindInt (IntPtr stmt, int index, int val);  46484649    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_blob", CallingConvention=CallingConvention.Cdecl)]4650    public static extern int BindBlob (IntPtr stmt, int index, byte[] val, int n, IntPtr free);4649    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_int64", CallingConvention=CallingConvention.Cdecl)]4650    public static extern int BindInt64 (IntPtr stmt, int index, long val);  46514652    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_count", CallingConvention=CallingConvention.Cdecl)]4653    public static extern int ColumnCount (IntPtr stmt);4652    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_double", CallingConvention=CallingConvention.Cdecl)]4653    public static extern int BindDouble (IntPtr stmt, int index, double val);  46544655    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_name", CallingConvention=CallingConvention.Cdecl)]4656    public static extern IntPtr ColumnName (IntPtr stmt, int index);4655    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_text16", CallingConvention=CallingConvention.Cdecl, CharSet = Cha4656    public static extern int BindText (IntPtr stmt, int index, [MarshalAs(UnmanagedType.LPWStr)] string val, int n, IntP  46574658    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_name16", CallingConvention=CallingConvention.Cdecl)]4659    static extern IntPtr ColumnName16Internal (IntPtr stmt, int index);4660    public static string ColumnName16(IntPtr stmt, int index)4661    {4662      return Marshal.PtrToStringUni(ColumnName16Internal(stmt, index));4663    }46644665    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_type", CallingConvention=CallingConvention.Cdecl)]4666    public static extern ColType ColumnType (IntPtr stmt, int index);46674668    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_int", CallingConvention=CallingConvention.Cdecl)]4669    public static extern int ColumnInt (IntPtr stmt, int index);46704671    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_int64", CallingConvention=CallingConvention.Cdecl)]4672    public static extern long ColumnInt64 (IntPtr stmt, int index);4658    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_blob", CallingConvention=CallingConvention.Cdecl)]4659    public static extern int BindBlob (IntPtr stmt, int index, byte[] val, int n, IntPtr free);46604661    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_count", CallingConvention=CallingConvention.Cdecl)]4662    public static extern int ColumnCount (IntPtr stmt);46634664    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_name", CallingConvention=CallingConvention.Cdecl)]4665    public static extern IntPtr ColumnName (IntPtr stmt, int index);46664667    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_name16", CallingConvention=CallingConvention.Cdecl)]4668    static extern IntPtr ColumnName16Internal (IntPtr stmt, int index);4669    public static string ColumnName16(IntPtr stmt, int index)4670    {4671      return Marshal.PtrToStringUni(ColumnName16Internal(stmt, index));4672    }  46734674    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_double", CallingConvention=CallingConvention.Cdecl)]4675    public static extern double ColumnDouble (IntPtr stmt, int index);4674    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_type", CallingConvention=CallingConvention.Cdecl)]4675    public static extern ColType ColumnType (IntPtr stmt, int index);  46764677    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_text", CallingConvention=CallingConvention.Cdecl)]4678    public static extern IntPtr ColumnText (IntPtr stmt, int index);4677    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_int", CallingConvention=CallingConvention.Cdecl)]4678    public static extern int ColumnInt (IntPtr stmt, int index);  46794680    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_text16", CallingConvention=CallingConvention.Cdecl)]4681    public static extern IntPtr ColumnText16 (IntPtr stmt, int index);4680    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_int64", CallingConvention=CallingConvention.Cdecl)]4681    public static extern long ColumnInt64 (IntPtr stmt, int index);  46824683    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_blob", CallingConvention=CallingConvention.Cdecl)]4684    public static extern IntPtr ColumnBlob (IntPtr stmt, int index);4683    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_double", CallingConvention=CallingConvention.Cdecl)]4684    public static extern double ColumnDouble (IntPtr stmt, int index);  46854686    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_bytes", CallingConvention=CallingConvention.Cdecl)]4687    public static extern int ColumnBytes (IntPtr stmt, int index);4686    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_text", CallingConvention=CallingConvention.Cdecl)]4687    public static extern IntPtr ColumnText (IntPtr stmt, int index);  46884689    public static string ColumnString (IntPtr stmt, int index)4690    {4691      return Marshal.PtrToStringUni (SQLite3.ColumnText16 (stmt, index));4692    }46934694    public static byte[] ColumnByteArray (IntPtr stmt, int index)4695    {4696      int length = ColumnBytes (stmt, index);4697      var result = new byte[length];4698      if (length > 0)4699        Marshal.Copy (ColumnBlob (stmt, index), result, 0, length);4700      return result;4689    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_text16", CallingConvention=CallingConvention.Cdecl)]4690    public static extern IntPtr ColumnText16 (IntPtr stmt, int index);46914692    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_blob", CallingConvention=CallingConvention.Cdecl)]4693    public static extern IntPtr ColumnBlob (IntPtr stmt, int index);46944695    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_bytes", CallingConvention=CallingConvention.Cdecl)]4696    public static extern int ColumnBytes (IntPtr stmt, int index);46974698    public static string ColumnString (IntPtr stmt, int index)4699    {4700      return Marshal.PtrToStringUni (SQLite3.ColumnText16 (stmt, index));  4701    }  47024703    [DllImport (LibraryPath, EntryPoint = "sqlite3_errcode", CallingConvention = CallingConvention.Cdecl)]4704    public static extern Result GetResult (Sqlite3DatabaseHandle db);47054706    [DllImport (LibraryPath, EntryPoint = "sqlite3_extended_errcode", CallingConvention = CallingConvention.Cdecl)]4707    public static extern ExtendedResult ExtendedErrCode (IntPtr db);47084709    [DllImport (LibraryPath, EntryPoint = "sqlite3_libversion_number", CallingConvention = CallingConvention.Cdecl)]4710    public static extern int LibVersionNumber ();4703    public static byte[] ColumnByteArray (IntPtr stmt, int index)4704    {4705      int length = ColumnBytes (stmt, index);4706      var result = new byte[length];4707      if (length > 0)4708        Marshal.Copy (ColumnBlob (stmt, index), result, 0, length);4709      return result;4710    }  47114712    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_init", CallingConvention = CallingConvention.Cdecl)]4713    public static extern Sqlite3BackupHandle BackupInit (Sqlite3DatabaseHandle destDb, [MarshalAs (UnmanagedType.LPStr)]4712    [DllImport (LibraryPath, EntryPoint = "sqlite3_errcode", CallingConvention = CallingConvention.Cdecl)]4713    public static extern Result GetResult (Sqlite3DatabaseHandle db);  47144715    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_step", CallingConvention = CallingConvention.Cdecl)]4716    public static extern Result BackupStep (Sqlite3BackupHandle backup, int numPages);4715    [DllImport (LibraryPath, EntryPoint = "sqlite3_extended_errcode", CallingConvention = CallingConvention.Cdecl)]4716    public static extern ExtendedResult ExtendedErrCode (IntPtr db);  47174718    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_finish", CallingConvention = CallingConvention.Cdecl)]4719    public static extern Result BackupFinish (Sqlite3BackupHandle backup);4720#else4721    public static Result Open (string filename, out Sqlite3DatabaseHandle db)4722    {4723      return (Result)Sqlite3.sqlite3_open (filename, out db);4724    }47254726    public static Result Open (string filename, out Sqlite3DatabaseHandle db, int flags, string vfsName)4727    {4728#if USE_WP8_NATIVE_SQLITE4729      return (Result)Sqlite3.sqlite3_open_v2(filename, out db, flags, vfsName ?? "");4730#else4731      return (Result)Sqlite3.sqlite3_open_v2 (filename, out db, flags, vfsName);4732#endif4718    [DllImport (LibraryPath, EntryPoint = "sqlite3_libversion_number", CallingConvention = CallingConvention.Cdecl)]4719    public static extern int LibVersionNumber ();47204721    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_init", CallingConvention = CallingConvention.Cdecl)]4722    public static extern Sqlite3BackupHandle BackupInit (Sqlite3DatabaseHandle destDb, [MarshalAs (UnmanagedType.LPStr)]47234724    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_step", CallingConvention = CallingConvention.Cdecl)]4725    public static extern Result BackupStep (Sqlite3BackupHandle backup, int numPages);47264727    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_finish", CallingConvention = CallingConvention.Cdecl)]4728    public static extern Result BackupFinish (Sqlite3BackupHandle backup);4729#else4730    public static Result Open (string filename, out Sqlite3DatabaseHandle db)4731    {4732      return (Result)Sqlite3.sqlite3_open (filename, out db);  4733    }  47344735    public static Result Close (Sqlite3DatabaseHandle db)4735    public static Result Open (string filename, out Sqlite3DatabaseHandle db, int flags, string vfsName)  4736    {4737      return (Result)Sqlite3.sqlite3_close (db);4738    }47394740    public static Result Close2 (Sqlite3DatabaseHandle db)4741    {4742      return (Result)Sqlite3.sqlite3_close_v2 (db);4743    }47444745    public static Result BusyTimeout (Sqlite3DatabaseHandle db, int milliseconds)4746    {4747      return (Result)Sqlite3.sqlite3_busy_timeout (db, milliseconds);4748    }47494750    public static int Changes (Sqlite3DatabaseHandle db)4751    {4752      return Sqlite3.sqlite3_changes (db);4753    }47544755    public static Sqlite3Statement Prepare2 (Sqlite3DatabaseHandle db, string query)4756    {4757      Sqlite3Statement stmt = default (Sqlite3Statement);4758#if USE_WP8_NATIVE_SQLITE || USE_SQLITEPCL_RAW4759      var r = Sqlite3.sqlite3_prepare_v2 (db, query, out stmt);4760#else4761      stmt = new Sqlite3Statement();4762      var r = Sqlite3.sqlite3_prepare_v2(db, query, -1, ref stmt, 0);4763#endif4764      if (r != 0) {4765        throw SQLiteException.New ((Result)r, GetErrmsg (db));4766      }4767      return stmt;4768    }47694770    public static Result Step (Sqlite3Statement stmt)4771    {4772      return (Result)Sqlite3.sqlite3_step (stmt);4773    }47744775    public static Result Reset (Sqlite3Statement stmt)4776    {4777      return (Result)Sqlite3.sqlite3_reset (stmt);4778    }47794780    public static Result Finalize (Sqlite3Statement stmt)4781    {4782      return (Result)Sqlite3.sqlite3_finalize (stmt);4783    }47844785    public static long LastInsertRowid (Sqlite3DatabaseHandle db)4786    {4787      return Sqlite3.sqlite3_last_insert_rowid (db);4788    }47894790    public static string GetErrmsg (Sqlite3DatabaseHandle db)4791    {4792      return Sqlite3.sqlite3_errmsg (db).utf8_to_string ();4793    }47944795    public static int BindParameterIndex (Sqlite3Statement stmt, string name)4796    {4797      return Sqlite3.sqlite3_bind_parameter_index (stmt, name);4798    }47994800    public static int BindNull (Sqlite3Statement stmt, int index)4801    {4802      return Sqlite3.sqlite3_bind_null (stmt, index);4803    }48044805    public static int BindInt (Sqlite3Statement stmt, int index, int val)4806    {4807      return Sqlite3.sqlite3_bind_int (stmt, index, val);4808    }48094810    public static int BindInt64 (Sqlite3Statement stmt, int index, long val)4811    {4812      return Sqlite3.sqlite3_bind_int64 (stmt, index, val);4813    }48144815    public static int BindDouble (Sqlite3Statement stmt, int index, double val)4816    {4817      return Sqlite3.sqlite3_bind_double (stmt, index, val);4818    }48194820    public static int BindText (Sqlite3Statement stmt, int index, string val, int n, IntPtr free)4821    {4822#if USE_WP8_NATIVE_SQLITE4823      return Sqlite3.sqlite3_bind_text(stmt, index, val, n);4824#elif USE_SQLITEPCL_RAW4825      return Sqlite3.sqlite3_bind_text (stmt, index, val);4826#else4827      return Sqlite3.sqlite3_bind_text(stmt, index, val, n, null);4828#endif4829    }48304831    public static int BindBlob (Sqlite3Statement stmt, int index, byte[] val, int n, IntPtr free)4832    {4833#if USE_WP8_NATIVE_SQLITE4834      return Sqlite3.sqlite3_bind_blob(stmt, index, val, n);4835#elif USE_SQLITEPCL_RAW4836      return Sqlite3.sqlite3_bind_blob (stmt, index, val);4837#else4838      return Sqlite3.sqlite3_bind_blob(stmt, index, val, n, null);4839#endif4840    }48414842    public static int ColumnCount (Sqlite3Statement stmt)4843    {4844      return Sqlite3.sqlite3_column_count (stmt);4845    }48464847    public static string ColumnName (Sqlite3Statement stmt, int index)4848    {4849      return Sqlite3.sqlite3_column_name (stmt, index).utf8_to_string ();4850    }48514852    public static string ColumnName16 (Sqlite3Statement stmt, int index)4853    {4854      return Sqlite3.sqlite3_column_name (stmt, index).utf8_to_string ();4855    }48564857    public static ColType ColumnType (Sqlite3Statement stmt, int index)4858    {4859      return (ColType)Sqlite3.sqlite3_column_type (stmt, index);4860    }48614862    public static int ColumnInt (Sqlite3Statement stmt, int index)4863    {4864      return Sqlite3.sqlite3_column_int (stmt, index);4865    }48664867    public static long ColumnInt64 (Sqlite3Statement stmt, int index)4868    {4869      return Sqlite3.sqlite3_column_int64 (stmt, index);4870    }48714872    public static double ColumnDouble (Sqlite3Statement stmt, int index)4873    {4874      return Sqlite3.sqlite3_column_double (stmt, index);4875    }48764877    public static string ColumnText (Sqlite3Statement stmt, int index)4878    {4879      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();4880    }48814882    public static string ColumnText16 (Sqlite3Statement stmt, int index)4883    {4884      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();4885    }48864887    public static byte[] ColumnBlob (Sqlite3Statement stmt, int index)4888    {4889      return Sqlite3.sqlite3_column_blob (stmt, index).ToArray ();4890    }48914892    public static int ColumnBytes (Sqlite3Statement stmt, int index)4893    {4894      return Sqlite3.sqlite3_column_bytes (stmt, index);4895    }48964897    public static string ColumnString (Sqlite3Statement stmt, int index)4898    {4899      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();4900    }49014902    public static byte[] ColumnByteArray (Sqlite3Statement stmt, int index)4903    {4904      int length = ColumnBytes (stmt, index);4905      if (length > 0) {4906        return ColumnBlob (stmt, index);4907      }4908      return new byte[0];4737#if USE_WP8_NATIVE_SQLITE4738      return (Result)Sqlite3.sqlite3_open_v2(filename, out db, flags, vfsName ?? "");4739#else4740      return (Result)Sqlite3.sqlite3_open_v2 (filename, out db, flags, vfsName);4741#endif4742    }47434744    public static Result Close (Sqlite3DatabaseHandle db)4745    {4746      return (Result)Sqlite3.sqlite3_close (db);4747    }47484749    public static Result Close2 (Sqlite3DatabaseHandle db)4750    {4751      return (Result)Sqlite3.sqlite3_close_v2 (db);4752    }47534754    public static Result BusyTimeout (Sqlite3DatabaseHandle db, int milliseconds)4755    {4756      return (Result)Sqlite3.sqlite3_busy_timeout (db, milliseconds);4757    }47584759    public static int Changes (Sqlite3DatabaseHandle db)4760    {4761      return Sqlite3.sqlite3_changes (db);4762    }47634764    public static Sqlite3Statement Prepare2 (Sqlite3DatabaseHandle db, string query)4765    {4766      Sqlite3Statement stmt = default (Sqlite3Statement);4767#if USE_WP8_NATIVE_SQLITE || USE_SQLITEPCL_RAW4768      var r = Sqlite3.sqlite3_prepare_v2 (db, query, out stmt);4769#else4770      stmt = new Sqlite3Statement();4771      var r = Sqlite3.sqlite3_prepare_v2(db, query, -1, ref stmt, 0);4772#endif4773      if (r != 0) {4774        throw SQLiteException.New ((Result)r, GetErrmsg (db));4775      }4776      return stmt;4777    }47784779    public static Result Step (Sqlite3Statement stmt)4780    {4781      return (Result)Sqlite3.sqlite3_step (stmt);4782    }47834784    public static Result Reset (Sqlite3Statement stmt)4785    {4786      return (Result)Sqlite3.sqlite3_reset (stmt);4787    }47884789    public static Result Finalize (Sqlite3Statement stmt)4790    {4791      return (Result)Sqlite3.sqlite3_finalize (stmt);4792    }47934794    public static long LastInsertRowid (Sqlite3DatabaseHandle db)4795    {4796      return Sqlite3.sqlite3_last_insert_rowid (db);4797    }47984799    public static string GetErrmsg (Sqlite3DatabaseHandle db)4800    {4801      return Sqlite3.sqlite3_errmsg (db).utf8_to_string ();4802    }48034804    public static int BindParameterIndex (Sqlite3Statement stmt, string name)4805    {4806      return Sqlite3.sqlite3_bind_parameter_index (stmt, name);4807    }48084809    public static int BindNull (Sqlite3Statement stmt, int index)4810    {4811      return Sqlite3.sqlite3_bind_null (stmt, index);4812    }48134814    public static int BindInt (Sqlite3Statement stmt, int index, int val)4815    {4816      return Sqlite3.sqlite3_bind_int (stmt, index, val);4817    }48184819    public static int BindInt64 (Sqlite3Statement stmt, int index, long val)4820    {4821      return Sqlite3.sqlite3_bind_int64 (stmt, index, val);4822    }48234824    public static int BindDouble (Sqlite3Statement stmt, int index, double val)4825    {4826      return Sqlite3.sqlite3_bind_double (stmt, index, val);4827    }48284829    public static int BindText (Sqlite3Statement stmt, int index, string val, int n, IntPtr free)4830    {4831#if USE_WP8_NATIVE_SQLITE4832      return Sqlite3.sqlite3_bind_text(stmt, index, val, n);4833#elif USE_SQLITEPCL_RAW4834      return Sqlite3.sqlite3_bind_text (stmt, index, val);4835#else4836      return Sqlite3.sqlite3_bind_text(stmt, index, val, n, null);4837#endif4838    }48394840    public static int BindBlob (Sqlite3Statement stmt, int index, byte[] val, int n, IntPtr free)4841    {4842#if USE_WP8_NATIVE_SQLITE4843      return Sqlite3.sqlite3_bind_blob(stmt, index, val, n);4844#elif USE_SQLITEPCL_RAW4845      return Sqlite3.sqlite3_bind_blob (stmt, index, val);4846#else4847      return Sqlite3.sqlite3_bind_blob(stmt, index, val, n, null);4848#endif4849    }48504851    public static int ColumnCount (Sqlite3Statement stmt)4852    {4853      return Sqlite3.sqlite3_column_count (stmt);4854    }48554856    public static string ColumnName (Sqlite3Statement stmt, int index)4857    {4858      return Sqlite3.sqlite3_column_name (stmt, index).utf8_to_string ();4859    }48604861    public static string ColumnName16 (Sqlite3Statement stmt, int index)4862    {4863      return Sqlite3.sqlite3_column_name (stmt, index).utf8_to_string ();4864    }48654866    public static ColType ColumnType (Sqlite3Statement stmt, int index)4867    {4868      return (ColType)Sqlite3.sqlite3_column_type (stmt, index);4869    }48704871    public static int ColumnInt (Sqlite3Statement stmt, int index)4872    {4873      return Sqlite3.sqlite3_column_int (stmt, index);4874    }48754876    public static long ColumnInt64 (Sqlite3Statement stmt, int index)4877    {4878      return Sqlite3.sqlite3_column_int64 (stmt, index);4879    }48804881    public static double ColumnDouble (Sqlite3Statement stmt, int index)4882    {4883      return Sqlite3.sqlite3_column_double (stmt, index);4884    }48854886    public static string ColumnText (Sqlite3Statement stmt, int index)4887    {4888      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();4889    }48904891    public static string ColumnText16 (Sqlite3Statement stmt, int index)4892    {4893      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();4894    }48954896    public static byte[] ColumnBlob (Sqlite3Statement stmt, int index)4897    {4898      return Sqlite3.sqlite3_column_blob (stmt, index).ToArray ();4899    }49004901    public static int ColumnBytes (Sqlite3Statement stmt, int index)4902    {4903      return Sqlite3.sqlite3_column_bytes (stmt, index);4904    }49054906    public static string ColumnString (Sqlite3Statement stmt, int index)4907    {4908      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();  4909    }  49104911    public static Result EnableLoadExtension (Sqlite3DatabaseHandle db, int onoff)4911    public static byte[] ColumnByteArray (Sqlite3Statement stmt, int index)  4912    {4913      return (Result)Sqlite3.sqlite3_enable_load_extension (db, onoff);4914    }49154916    public static int LibVersionNumber ()4917    {4918      return Sqlite3.sqlite3_libversion_number ();4919    }49204921    public static Result GetResult (Sqlite3DatabaseHandle db)4922    {4923      return (Result)Sqlite3.sqlite3_errcode (db);4924    }49254926    public static ExtendedResult ExtendedErrCode (Sqlite3DatabaseHandle db)4927    {4928      return (ExtendedResult)Sqlite3.sqlite3_extended_errcode (db);4929    }49304931    public static Sqlite3BackupHandle BackupInit (Sqlite3DatabaseHandle destDb, string destName, Sqlite3DatabaseHandle s4932    {4933      return Sqlite3.sqlite3_backup_init (destDb, destName, sourceDb, sourceName);4934    }49354936    public static Result BackupStep (Sqlite3BackupHandle backup, int numPages)4937    {4938      return (Result)Sqlite3.sqlite3_backup_step (backup, numPages);4939    }49404941    public static Result BackupFinish (Sqlite3BackupHandle backup)4942    {4943      return (Result)Sqlite3.sqlite3_backup_finish (backup);4944    }4945#endif49464947    public enum ColType : int4948    {4949      Integer = 1,4950      Float = 2,4951      Text = 3,4952      Blob = 4,4953      Null = 54954    }4955  }4956}4913      int length = ColumnBytes (stmt, index);4914      if (length > 0) {4915        return ColumnBlob (stmt, index);4916      }4917      return new byte[0];4918    }49194920    public static Result EnableLoadExtension (Sqlite3DatabaseHandle db, int onoff)4921    {4922      return (Result)Sqlite3.sqlite3_enable_load_extension (db, onoff);4923    }49244925    public static int LibVersionNumber ()4926    {4927      return Sqlite3.sqlite3_libversion_number ();4928    }49294930    public static Result GetResult (Sqlite3DatabaseHandle db)4931    {4932      return (Result)Sqlite3.sqlite3_errcode (db);4933    }49344935    public static ExtendedResult ExtendedErrCode (Sqlite3DatabaseHandle db)4936    {4937      return (ExtendedResult)Sqlite3.sqlite3_extended_errcode (db);4938    }49394940    public static Sqlite3BackupHandle BackupInit (Sqlite3DatabaseHandle destDb, string destName, Sqlite3DatabaseHandle s4941    {4942      return Sqlite3.sqlite3_backup_init (destDb, destName, sourceDb, sourceName);4943    }49444945    public static Result BackupStep (Sqlite3BackupHandle backup, int numPages)4946    {4947      return (Result)Sqlite3.sqlite3_backup_step (backup, numPages);4948    }49494950    public static Result BackupFinish (Sqlite3BackupHandle backup)4951    {4952      return (Result)Sqlite3.sqlite3_backup_finish (backup);4953    }4954#endif49554956    public enum ColType : int4957    {4958      Integer = 1,4959      Float = 2,4960      Text = 3,4961      Blob = 4,4962      Null = 54963    }4964  }4965}

- +

Methods/Properties

diff --git a/coverage/SQLite.Tests_CreateTablesResult.html b/coverage/SQLite.Tests_CreateTablesResult.html index ec70383a..8a87cbea 100644 --- a/coverage/SQLite.Tests_CreateTablesResult.html +++ b/coverage/SQLite.Tests_CreateTablesResult.html @@ -815,7 +815,7 @@

< Summary

Tag: -164_8458774659 +165_8458827553
@@ -843,7 +843,7 @@

< Summary

Total lines: -4956 +4965 Line coverage: @@ -898,7 +898,7 @@

Metrics

MethodBranch coverage Crap Score Cyclomatic complexity NPath complexity Sequence coverage -.ctor()0%110100% +.ctor()0%110100%
@@ -4193,7 +4193,7 @@

/home/runner/work/sqlite-ne  3283        else if (value is Boolean) {  3284          SQLite3.BindInt (stmt, index, (bool)value ? 1 : 0);  3285        }3286        else if (value is UInt32 || value is Int64) {3286        else if (value is UInt32 || value is Int64 || value is UInt64) {  3287          SQLite3.BindInt64 (stmt, index, Convert.ToInt64 (value));  3288        }  3289        else if (value is Single || value is Double || value is Decimal) { @@ -4327,1551 +4327,1560 @@

/home/runner/work/sqlite-ne  3417        else if (clrType == typeof (Int64)) {  3418          return SQLite3.ColumnInt64 (stmt, index);  3419        }3420        else if (clrType == typeof (UInt32)) {3421          return (uint)SQLite3.ColumnInt64 (stmt, index);3420        else if (clrType == typeof (UInt64)) {3421          return (ulong)SQLite3.ColumnInt64 (stmt, index);  3422        }3423        else if (clrType == typeof (decimal)) {3424          return (decimal)SQLite3.ColumnDouble (stmt, index);3423        else if (clrType == typeof (UInt32)) {3424          return (uint)SQLite3.ColumnInt64 (stmt, index);  3425        }3426        else if (clrType == typeof (Byte)) {3427          return (byte)SQLite3.ColumnInt (stmt, index);3426        else if (clrType == typeof (decimal)) {3427          return (decimal)SQLite3.ColumnDouble (stmt, index);  3428        }3429        else if (clrType == typeof (UInt16)) {3430          return (ushort)SQLite3.ColumnInt (stmt, index);3429        else if (clrType == typeof (Byte)) {3430          return (byte)SQLite3.ColumnInt (stmt, index);  3431        }3432        else if (clrType == typeof (Int16)) {3433          return (short)SQLite3.ColumnInt (stmt, index);3432        else if (clrType == typeof (UInt16)) {3433          return (ushort)SQLite3.ColumnInt (stmt, index);  3434        }3435        else if (clrType == typeof (sbyte)) {3436          return (sbyte)SQLite3.ColumnInt (stmt, index);3435        else if (clrType == typeof (Int16)) {3436          return (short)SQLite3.ColumnInt (stmt, index);  3437        }3438        else if (clrType == typeof (byte[])) {3439          return SQLite3.ColumnByteArray (stmt, index);3438        else if (clrType == typeof (sbyte)) {3439          return (sbyte)SQLite3.ColumnInt (stmt, index);  3440        }3441        else if (clrType == typeof (Guid)) {3442          var text = SQLite3.ColumnString (stmt, index);3443          return new Guid (text);3444        }3445        else if (clrType == typeof (Uri)) {3446          var text = SQLite3.ColumnString (stmt, index);3447          return new Uri (text);3448        }3449        else if (clrType == typeof (StringBuilder)) {3450          var text = SQLite3.ColumnString (stmt, index);3451          return new StringBuilder (text);3452        }3453        else if (clrType == typeof (UriBuilder)) {3454          var text = SQLite3.ColumnString (stmt, index);3455          return new UriBuilder (text);3456        }3457        else {3458          throw new NotSupportedException ("Don't know how to read " + clrType);3441        else if (clrType == typeof (byte[])) {3442          return SQLite3.ColumnByteArray (stmt, index);3443        }3444        else if (clrType == typeof (Guid)) {3445          var text = SQLite3.ColumnString (stmt, index);3446          return new Guid (text);3447        }3448        else if (clrType == typeof (Uri)) {3449          var text = SQLite3.ColumnString (stmt, index);3450          return new Uri (text);3451        }3452        else if (clrType == typeof (StringBuilder)) {3453          var text = SQLite3.ColumnString (stmt, index);3454          return new StringBuilder (text);3455        }3456        else if (clrType == typeof (UriBuilder)) {3457          var text = SQLite3.ColumnString (stmt, index);3458          return new UriBuilder (text);  3459        }3460      }3461    }3462  }34633464  internal class FastColumnSetter3465  {3466    /// <summary>3467    /// Creates a delegate that can be used to quickly set object members from query columns.3468    ///3469    /// Note that this frontloads the slow reflection-based type checking for columns to only happen once at the beginni3470    /// and then afterwards each row of the query can invoke the delegate returned by this function to get much better p3471    /// </summary>3472    /// <typeparam name="T">The type of the destination object that the query will read into</typeparam>3473    /// <param name="conn">The active connection.  Note that this is primarily needed in order to read preferences regar3474    /// <param name="column">The table mapping used to map the statement column to a member of the destination object ty3475    /// <returns>3476    /// A delegate for fast-setting of object members from statement columns.3477    ///3478    /// If no fast setter is available for the requested column (enums in particular cause headache), then this function3479    /// </returns>3480    internal static Action<object, Sqlite3Statement, int> GetFastSetter<T> (SQLiteConnection conn, TableMapping.Column c3481    {3482      Action<object, Sqlite3Statement, int> fastSetter = null;34833484      Type clrType = column.PropertyInfo.PropertyType;34853486      var clrTypeInfo = clrType.GetTypeInfo ();3487      if (clrTypeInfo.IsGenericType && clrTypeInfo.GetGenericTypeDefinition () == typeof (Nullable<>)) {3488        clrType = clrTypeInfo.GenericTypeArguments[0];3489        clrTypeInfo = clrType.GetTypeInfo ();3490      }34913492      if (clrType == typeof (String)) {3493        fastSetter = CreateTypedSetterDelegate<T, string> (column, (stmt, index) => {3494          return SQLite3.ColumnString (stmt, index);3495        });3496      }3497      else if (clrType == typeof (Int32)) {3498        fastSetter = CreateNullableTypedSetterDelegate<T, int> (column, (stmt, index)=>{3499          return SQLite3.ColumnInt (stmt, index);3500        });3501      }3502      else if (clrType == typeof (Boolean)) {3503        fastSetter = CreateNullableTypedSetterDelegate<T, bool> (column, (stmt, index) => {3504          return SQLite3.ColumnInt (stmt, index) == 1;3505        });3506      }3507      else if (clrType == typeof (double)) {3508        fastSetter = CreateNullableTypedSetterDelegate<T, double> (column, (stmt, index) => {3509          return SQLite3.ColumnDouble (stmt, index);3510        });3511      }3512      else if (clrType == typeof (float)) {3513        fastSetter = CreateNullableTypedSetterDelegate<T, float> (column, (stmt, index) => {3514          return (float) SQLite3.ColumnDouble (stmt, index);3515        });3516      }3517      else if (clrType == typeof (TimeSpan)) {3518        if (conn.StoreTimeSpanAsTicks) {3519          fastSetter = CreateNullableTypedSetterDelegate<T, TimeSpan> (column, (stmt, index) => {3520            return new TimeSpan (SQLite3.ColumnInt64 (stmt, index));3521          });3522        }3523        else {3524          fastSetter = CreateNullableTypedSetterDelegate<T, TimeSpan> (column, (stmt, index) => {3525            var text = SQLite3.ColumnString (stmt, index);3526            TimeSpan resultTime;3527            if (!TimeSpan.TryParseExact (text, "c", System.Globalization.CultureInfo.InvariantCulture, System.Globalizat3528              resultTime = TimeSpan.Parse (text);3529            }3530            return resultTime;3531          });3532        }3533      }3534      else if (clrType == typeof (DateTime)) {3535        if (conn.StoreDateTimeAsTicks) {3536          fastSetter = CreateNullableTypedSetterDelegate<T, DateTime> (column, (stmt, index) => {3537            return new DateTime (SQLite3.ColumnInt64 (stmt, index));3538          });3539        }3540        else {3541          fastSetter = CreateNullableTypedSetterDelegate<T, DateTime> (column, (stmt, index) => {3542            var text = SQLite3.ColumnString (stmt, index);3543            DateTime resultDate;3544            if (!DateTime.TryParseExact (text, conn.DateTimeStringFormat, System.Globalization.CultureInfo.InvariantCult3545              resultDate = DateTime.Parse (text);3546            }3547            return resultDate;3548          });3549        }3550      }3551      else if (clrType == typeof (DateTimeOffset)) {3552        fastSetter = CreateNullableTypedSetterDelegate<T, DateTimeOffset> (column, (stmt, index) => {3553          return new DateTimeOffset (SQLite3.ColumnInt64 (stmt, index), TimeSpan.Zero);3554        });3555      }3556      else if (clrTypeInfo.IsEnum) {3557        // NOTE: Not sure of a good way (if any?) to do a strongly-typed fast setter like this for enumerated types -- f3460        else {3461          throw new NotSupportedException ("Don't know how to read " + clrType);3462        }3463      }3464    }3465  }34663467  internal class FastColumnSetter3468  {3469    /// <summary>3470    /// Creates a delegate that can be used to quickly set object members from query columns.3471    ///3472    /// Note that this frontloads the slow reflection-based type checking for columns to only happen once at the beginni3473    /// and then afterwards each row of the query can invoke the delegate returned by this function to get much better p3474    /// </summary>3475    /// <typeparam name="T">The type of the destination object that the query will read into</typeparam>3476    /// <param name="conn">The active connection.  Note that this is primarily needed in order to read preferences regar3477    /// <param name="column">The table mapping used to map the statement column to a member of the destination object ty3478    /// <returns>3479    /// A delegate for fast-setting of object members from statement columns.3480    ///3481    /// If no fast setter is available for the requested column (enums in particular cause headache), then this function3482    /// </returns>3483    internal static Action<object, Sqlite3Statement, int> GetFastSetter<T> (SQLiteConnection conn, TableMapping.Column c3484    {3485      Action<object, Sqlite3Statement, int> fastSetter = null;34863487      Type clrType = column.PropertyInfo.PropertyType;34883489      var clrTypeInfo = clrType.GetTypeInfo ();3490      if (clrTypeInfo.IsGenericType && clrTypeInfo.GetGenericTypeDefinition () == typeof (Nullable<>)) {3491        clrType = clrTypeInfo.GenericTypeArguments[0];3492        clrTypeInfo = clrType.GetTypeInfo ();3493      }34943495      if (clrType == typeof (String)) {3496        fastSetter = CreateTypedSetterDelegate<T, string> (column, (stmt, index) => {3497          return SQLite3.ColumnString (stmt, index);3498        });3499      }3500      else if (clrType == typeof (Int32)) {3501        fastSetter = CreateNullableTypedSetterDelegate<T, int> (column, (stmt, index)=>{3502          return SQLite3.ColumnInt (stmt, index);3503        });3504      }3505      else if (clrType == typeof (Boolean)) {3506        fastSetter = CreateNullableTypedSetterDelegate<T, bool> (column, (stmt, index) => {3507          return SQLite3.ColumnInt (stmt, index) == 1;3508        });3509      }3510      else if (clrType == typeof (double)) {3511        fastSetter = CreateNullableTypedSetterDelegate<T, double> (column, (stmt, index) => {3512          return SQLite3.ColumnDouble (stmt, index);3513        });3514      }3515      else if (clrType == typeof (float)) {3516        fastSetter = CreateNullableTypedSetterDelegate<T, float> (column, (stmt, index) => {3517          return (float) SQLite3.ColumnDouble (stmt, index);3518        });3519      }3520      else if (clrType == typeof (TimeSpan)) {3521        if (conn.StoreTimeSpanAsTicks) {3522          fastSetter = CreateNullableTypedSetterDelegate<T, TimeSpan> (column, (stmt, index) => {3523            return new TimeSpan (SQLite3.ColumnInt64 (stmt, index));3524          });3525        }3526        else {3527          fastSetter = CreateNullableTypedSetterDelegate<T, TimeSpan> (column, (stmt, index) => {3528            var text = SQLite3.ColumnString (stmt, index);3529            TimeSpan resultTime;3530            if (!TimeSpan.TryParseExact (text, "c", System.Globalization.CultureInfo.InvariantCulture, System.Globalizat3531              resultTime = TimeSpan.Parse (text);3532            }3533            return resultTime;3534          });3535        }3536      }3537      else if (clrType == typeof (DateTime)) {3538        if (conn.StoreDateTimeAsTicks) {3539          fastSetter = CreateNullableTypedSetterDelegate<T, DateTime> (column, (stmt, index) => {3540            return new DateTime (SQLite3.ColumnInt64 (stmt, index));3541          });3542        }3543        else {3544          fastSetter = CreateNullableTypedSetterDelegate<T, DateTime> (column, (stmt, index) => {3545            var text = SQLite3.ColumnString (stmt, index);3546            DateTime resultDate;3547            if (!DateTime.TryParseExact (text, conn.DateTimeStringFormat, System.Globalization.CultureInfo.InvariantCult3548              resultDate = DateTime.Parse (text);3549            }3550            return resultDate;3551          });3552        }3553      }3554      else if (clrType == typeof (DateTimeOffset)) {3555        fastSetter = CreateNullableTypedSetterDelegate<T, DateTimeOffset> (column, (stmt, index) => {3556          return new DateTimeOffset (SQLite3.ColumnInt64 (stmt, index), TimeSpan.Zero);3557        });  3558      }3559      else if (clrType == typeof (Int64)) {3560        fastSetter = CreateNullableTypedSetterDelegate<T, Int64> (column, (stmt, index) => {3561          return SQLite3.ColumnInt64 (stmt, index);3562        });3563      }3564      else if (clrType == typeof (UInt32)) {3565        fastSetter = CreateNullableTypedSetterDelegate<T, UInt32> (column, (stmt, index) => {3566          return (uint)SQLite3.ColumnInt64 (stmt, index);3567        });3568      }3569      else if (clrType == typeof (decimal)) {3570        fastSetter = CreateNullableTypedSetterDelegate<T, decimal> (column, (stmt, index) => {3571          return (decimal)SQLite3.ColumnDouble (stmt, index);3572        });3573      }3574      else if (clrType == typeof (Byte)) {3575        fastSetter = CreateNullableTypedSetterDelegate<T, Byte> (column, (stmt, index) => {3576          return (byte)SQLite3.ColumnInt (stmt, index);3577        });3578      }3579      else if (clrType == typeof (UInt16)) {3580        fastSetter = CreateNullableTypedSetterDelegate<T, UInt16> (column, (stmt, index) => {3581          return (ushort)SQLite3.ColumnInt (stmt, index);3582        });3583      }3584      else if (clrType == typeof (Int16)) {3585        fastSetter = CreateNullableTypedSetterDelegate<T, Int16> (column, (stmt, index) => {3586          return (short)SQLite3.ColumnInt (stmt, index);3587        });3588      }3589      else if (clrType == typeof (sbyte)) {3590        fastSetter = CreateNullableTypedSetterDelegate<T, sbyte> (column, (stmt, index) => {3591          return (sbyte)SQLite3.ColumnInt (stmt, index);3592        });3593      }3594      else if (clrType == typeof (byte[])) {3595        fastSetter = CreateTypedSetterDelegate<T, byte[]> (column, (stmt, index) => {3596          return SQLite3.ColumnByteArray (stmt, index);3597        });3598      }3599      else if (clrType == typeof (Guid)) {3600        fastSetter = CreateNullableTypedSetterDelegate<T, Guid> (column, (stmt, index) => {3601          var text = SQLite3.ColumnString (stmt, index);3602          return new Guid (text);3603        });3604      }3605      else if (clrType == typeof (Uri)) {3606        fastSetter = CreateTypedSetterDelegate<T, Uri> (column, (stmt, index) => {3607          var text = SQLite3.ColumnString (stmt, index);3608          return new Uri (text);3609        });3610      }3611      else if (clrType == typeof (StringBuilder)) {3612        fastSetter = CreateTypedSetterDelegate<T, StringBuilder> (column, (stmt, index) => {3613          var text = SQLite3.ColumnString (stmt, index);3614          return new StringBuilder (text);3615        });3616      }3617      else if (clrType == typeof (UriBuilder)) {3618        fastSetter = CreateTypedSetterDelegate<T, UriBuilder> (column, (stmt, index) => {3619          var text = SQLite3.ColumnString (stmt, index);3620          return new UriBuilder (text);3621        });3622      }3623      else {3624        // NOTE: Will fall back to the slow setter method in the event that we are unable to create a fast setter delega3559      else if (clrTypeInfo.IsEnum) {3560        // NOTE: Not sure of a good way (if any?) to do a strongly-typed fast setter like this for enumerated types -- f3561      }3562      else if (clrType == typeof (Int64)) {3563        fastSetter = CreateNullableTypedSetterDelegate<T, Int64> (column, (stmt, index) => {3564          return SQLite3.ColumnInt64 (stmt, index);3565        });3566      }3567      else if (clrType == typeof(UInt64))3568      {3569        fastSetter = CreateNullableTypedSetterDelegate<T, UInt64>(column, (stmt, index) => {3570          return (ulong)SQLite3.ColumnInt64(stmt, index);3571        });3572      }3573      else if (clrType == typeof (UInt32)) {3574        fastSetter = CreateNullableTypedSetterDelegate<T, UInt32> (column, (stmt, index) => {3575          return (uint)SQLite3.ColumnInt64 (stmt, index);3576        });3577      }3578      else if (clrType == typeof (decimal)) {3579        fastSetter = CreateNullableTypedSetterDelegate<T, decimal> (column, (stmt, index) => {3580          return (decimal)SQLite3.ColumnDouble (stmt, index);3581        });3582      }3583      else if (clrType == typeof (Byte)) {3584        fastSetter = CreateNullableTypedSetterDelegate<T, Byte> (column, (stmt, index) => {3585          return (byte)SQLite3.ColumnInt (stmt, index);3586        });3587      }3588      else if (clrType == typeof (UInt16)) {3589        fastSetter = CreateNullableTypedSetterDelegate<T, UInt16> (column, (stmt, index) => {3590          return (ushort)SQLite3.ColumnInt (stmt, index);3591        });3592      }3593      else if (clrType == typeof (Int16)) {3594        fastSetter = CreateNullableTypedSetterDelegate<T, Int16> (column, (stmt, index) => {3595          return (short)SQLite3.ColumnInt (stmt, index);3596        });3597      }3598      else if (clrType == typeof (sbyte)) {3599        fastSetter = CreateNullableTypedSetterDelegate<T, sbyte> (column, (stmt, index) => {3600          return (sbyte)SQLite3.ColumnInt (stmt, index);3601        });3602      }3603      else if (clrType == typeof (byte[])) {3604        fastSetter = CreateTypedSetterDelegate<T, byte[]> (column, (stmt, index) => {3605          return SQLite3.ColumnByteArray (stmt, index);3606        });3607      }3608      else if (clrType == typeof (Guid)) {3609        fastSetter = CreateNullableTypedSetterDelegate<T, Guid> (column, (stmt, index) => {3610          var text = SQLite3.ColumnString (stmt, index);3611          return new Guid (text);3612        });3613      }3614      else if (clrType == typeof (Uri)) {3615        fastSetter = CreateTypedSetterDelegate<T, Uri> (column, (stmt, index) => {3616          var text = SQLite3.ColumnString (stmt, index);3617          return new Uri (text);3618        });3619      }3620      else if (clrType == typeof (StringBuilder)) {3621        fastSetter = CreateTypedSetterDelegate<T, StringBuilder> (column, (stmt, index) => {3622          var text = SQLite3.ColumnString (stmt, index);3623          return new StringBuilder (text);3624        });  3625      }3626      return fastSetter;3627    }36283629    /// <summary>3630    /// This creates a strongly typed delegate that will permit fast setting of column values given a Sqlite3Statement a3631    ///3632    /// Note that this is identical to CreateTypedSetterDelegate(), but has an extra check to see if it should create a 3633    /// </summary>3634    /// <typeparam name="ObjectType">The type of the object whose member column is being set</typeparam>3635    /// <typeparam name="ColumnMemberType">The CLR type of the member in the object which corresponds to the given SQLit3636    /// <param name="column">The column mapping that identifies the target member of the destination object</param>3637    /// <param name="getColumnValue">A lambda that can be used to retrieve the column value at query-time</param>3638    /// <returns>A strongly-typed delegate</returns>3639    private static Action<object, Sqlite3Statement, int> CreateNullableTypedSetterDelegate<ObjectType, ColumnMemberType>3640    {3641      var clrTypeInfo = column.PropertyInfo.PropertyType.GetTypeInfo();3642      bool isNullable = false;36433644      if (clrTypeInfo.IsGenericType && clrTypeInfo.GetGenericTypeDefinition () == typeof (Nullable<>)) {3645        isNullable = true;3646      }36473648      if (isNullable) {3649        var setProperty = (Action<ObjectType, ColumnMemberType?>)Delegate.CreateDelegate (3650            typeof (Action<ObjectType, ColumnMemberType?>), null,3651            column.PropertyInfo.GetSetMethod ());3626      else if (clrType == typeof (UriBuilder)) {3627        fastSetter = CreateTypedSetterDelegate<T, UriBuilder> (column, (stmt, index) => {3628          var text = SQLite3.ColumnString (stmt, index);3629          return new UriBuilder (text);3630        });3631      }3632      else {3633        // NOTE: Will fall back to the slow setter method in the event that we are unable to create a fast setter delega3634      }3635      return fastSetter;3636    }36373638    /// <summary>3639    /// This creates a strongly typed delegate that will permit fast setting of column values given a Sqlite3Statement a3640    ///3641    /// Note that this is identical to CreateTypedSetterDelegate(), but has an extra check to see if it should create a 3642    /// </summary>3643    /// <typeparam name="ObjectType">The type of the object whose member column is being set</typeparam>3644    /// <typeparam name="ColumnMemberType">The CLR type of the member in the object which corresponds to the given SQLit3645    /// <param name="column">The column mapping that identifies the target member of the destination object</param>3646    /// <param name="getColumnValue">A lambda that can be used to retrieve the column value at query-time</param>3647    /// <returns>A strongly-typed delegate</returns>3648    private static Action<object, Sqlite3Statement, int> CreateNullableTypedSetterDelegate<ObjectType, ColumnMemberType>3649    {3650      var clrTypeInfo = column.PropertyInfo.PropertyType.GetTypeInfo();3651      bool isNullable = false;  36523653        return (o, stmt, i) => {3654          var colType = SQLite3.ColumnType (stmt, i);3655          if (colType != SQLite3.ColType.Null)3656            setProperty.Invoke ((ObjectType)o, getColumnValue.Invoke (stmt, i));3657        };3658      }36593660      return CreateTypedSetterDelegate<ObjectType, ColumnMemberType> (column, getColumnValue);3661    }36623663    /// <summary>3664    /// This creates a strongly typed delegate that will permit fast setting of column values given a Sqlite3Statement a3665    /// </summary>3666    /// <typeparam name="ObjectType">The type of the object whose member column is being set</typeparam>3667    /// <typeparam name="ColumnMemberType">The CLR type of the member in the object which corresponds to the given SQLit3668    /// <param name="column">The column mapping that identifies the target member of the destination object</param>3669    /// <param name="getColumnValue">A lambda that can be used to retrieve the column value at query-time</param>3670    /// <returns>A strongly-typed delegate</returns>3671    private static Action<object, Sqlite3Statement, int> CreateTypedSetterDelegate<ObjectType, ColumnMemberType> (TableM3672    {3673      var setProperty = (Action<ObjectType, ColumnMemberType>)Delegate.CreateDelegate (3674          typeof (Action<ObjectType, ColumnMemberType>), null,3675          column.PropertyInfo.GetSetMethod ());36763677      return (o, stmt, i) => {3678        var colType = SQLite3.ColumnType (stmt, i);3679        if (colType != SQLite3.ColType.Null)3680          setProperty.Invoke ((ObjectType)o, getColumnValue.Invoke (stmt, i));3681      };3682    }3683  }36843685  /// <summary>3686  /// Since the insert never changed, we only need to prepare once.3687  /// </summary>3688  class PreparedSqlLiteInsertCommand : IDisposable3689  {3690    bool Initialized;36913692    SQLiteConnection Connection;3653      if (clrTypeInfo.IsGenericType && clrTypeInfo.GetGenericTypeDefinition () == typeof (Nullable<>)) {3654        isNullable = true;3655      }36563657      if (isNullable) {3658        var setProperty = (Action<ObjectType, ColumnMemberType?>)Delegate.CreateDelegate (3659            typeof (Action<ObjectType, ColumnMemberType?>), null,3660            column.PropertyInfo.GetSetMethod ());36613662        return (o, stmt, i) => {3663          var colType = SQLite3.ColumnType (stmt, i);3664          if (colType != SQLite3.ColType.Null)3665            setProperty.Invoke ((ObjectType)o, getColumnValue.Invoke (stmt, i));3666        };3667      }36683669      return CreateTypedSetterDelegate<ObjectType, ColumnMemberType> (column, getColumnValue);3670    }36713672    /// <summary>3673    /// This creates a strongly typed delegate that will permit fast setting of column values given a Sqlite3Statement a3674    /// </summary>3675    /// <typeparam name="ObjectType">The type of the object whose member column is being set</typeparam>3676    /// <typeparam name="ColumnMemberType">The CLR type of the member in the object which corresponds to the given SQLit3677    /// <param name="column">The column mapping that identifies the target member of the destination object</param>3678    /// <param name="getColumnValue">A lambda that can be used to retrieve the column value at query-time</param>3679    /// <returns>A strongly-typed delegate</returns>3680    private static Action<object, Sqlite3Statement, int> CreateTypedSetterDelegate<ObjectType, ColumnMemberType> (TableM3681    {3682      var setProperty = (Action<ObjectType, ColumnMemberType>)Delegate.CreateDelegate (3683          typeof (Action<ObjectType, ColumnMemberType>), null,3684          column.PropertyInfo.GetSetMethod ());36853686      return (o, stmt, i) => {3687        var colType = SQLite3.ColumnType (stmt, i);3688        if (colType != SQLite3.ColType.Null)3689          setProperty.Invoke ((ObjectType)o, getColumnValue.Invoke (stmt, i));3690      };3691    }3692  }  36933694    string CommandText;36953696    Sqlite3Statement Statement;3697    static readonly Sqlite3Statement NullStatement = default (Sqlite3Statement);36983699    public PreparedSqlLiteInsertCommand (SQLiteConnection conn, string commandText)3700    {3701      Connection = conn;3702      CommandText = commandText;3703    }3694  /// <summary>3695  /// Since the insert never changed, we only need to prepare once.3696  /// </summary>3697  class PreparedSqlLiteInsertCommand : IDisposable3698  {3699    bool Initialized;37003701    SQLiteConnection Connection;37023703    string CommandText;  37043705    public int ExecuteNonQuery (object[] source)3706    {3707      if (Initialized && Statement == NullStatement) {3708        throw new ObjectDisposedException (nameof (PreparedSqlLiteInsertCommand));3709      }37103711      if (Connection.Trace) {3712        Connection.Tracer?.Invoke ("Executing: " + CommandText);3713      }37143715      var r = SQLite3.Result.OK;37163717      if (!Initialized) {3718        Statement = SQLite3.Prepare2 (Connection.Handle, CommandText);3719        Initialized = true;3720      }37213722      //bind the values.3723      if (source != null) {3724        for (int i = 0; i < source.Length; i++) {3725          SQLiteCommand.BindParameter (Statement, i + 1, source[i], Connection.StoreDateTimeAsTicks, Connection.DateTime3726        }3727      }3728      r = SQLite3.Step (Statement);37293730      if (r == SQLite3.Result.Done) {3731        int rowsAffected = SQLite3.Changes (Connection.Handle);3732        SQLite3.Reset (Statement);3733        return rowsAffected;3734      }3735      else if (r == SQLite3.Result.Error) {3736        string msg = SQLite3.GetErrmsg (Connection.Handle);3737        SQLite3.Reset (Statement);3738        throw SQLiteException.New (r, msg);3739      }3740      else if (r == SQLite3.Result.Constraint && SQLite3.ExtendedErrCode (Connection.Handle) == SQLite3.ExtendedResult.C3705    Sqlite3Statement Statement;3706    static readonly Sqlite3Statement NullStatement = default (Sqlite3Statement);37073708    public PreparedSqlLiteInsertCommand (SQLiteConnection conn, string commandText)3709    {3710      Connection = conn;3711      CommandText = commandText;3712    }37133714    public int ExecuteNonQuery (object[] source)3715    {3716      if (Initialized && Statement == NullStatement) {3717        throw new ObjectDisposedException (nameof (PreparedSqlLiteInsertCommand));3718      }37193720      if (Connection.Trace) {3721        Connection.Tracer?.Invoke ("Executing: " + CommandText);3722      }37233724      var r = SQLite3.Result.OK;37253726      if (!Initialized) {3727        Statement = SQLite3.Prepare2 (Connection.Handle, CommandText);3728        Initialized = true;3729      }37303731      //bind the values.3732      if (source != null) {3733        for (int i = 0; i < source.Length; i++) {3734          SQLiteCommand.BindParameter (Statement, i + 1, source[i], Connection.StoreDateTimeAsTicks, Connection.DateTime3735        }3736      }3737      r = SQLite3.Step (Statement);37383739      if (r == SQLite3.Result.Done) {3740        int rowsAffected = SQLite3.Changes (Connection.Handle);  3741        SQLite3.Reset (Statement);3742        throw NotNullConstraintViolationException.New (r, SQLite3.GetErrmsg (Connection.Handle));3742        return rowsAffected;  3743      }3744      else {3745        SQLite3.Reset (Statement);3746        throw SQLiteException.New (r, SQLite3.GetErrmsg (Connection.Handle));3747      }3748    }37493750    public void Dispose ()3751    {3752      Dispose (true);3753      GC.SuppressFinalize (this);3754    }37553756    void Dispose (bool disposing)3757    {3758      var s = Statement;3759      Statement = NullStatement;3760      Connection = null;3761      if (s != NullStatement) {3762        SQLite3.Finalize (s);3763      }3764    }37653766    ~PreparedSqlLiteInsertCommand ()3767    {3768      Dispose (false);3769    }3770  }37713772  public enum CreateTableResult3773  {3774    Created,3775    Migrated,3776  }37773778  public class CreateTablesResult3779  {3780    public Dictionary<Type, CreateTableResult> Results { get; private set; }3781 - 53782    public CreateTablesResult () - 53783    { - 53784      Results = new Dictionary<Type, CreateTableResult> (); - 53785    }3786  }37873788  public abstract class BaseTableQuery3789  {3790    protected class Ordering3791    {3792      public string ColumnName { get; set; }3793      public bool Ascending { get; set; }3794    }3744      else if (r == SQLite3.Result.Error) {3745        string msg = SQLite3.GetErrmsg (Connection.Handle);3746        SQLite3.Reset (Statement);3747        throw SQLiteException.New (r, msg);3748      }3749      else if (r == SQLite3.Result.Constraint && SQLite3.ExtendedErrCode (Connection.Handle) == SQLite3.ExtendedResult.C3750        SQLite3.Reset (Statement);3751        throw NotNullConstraintViolationException.New (r, SQLite3.GetErrmsg (Connection.Handle));3752      }3753      else {3754        SQLite3.Reset (Statement);3755        throw SQLiteException.New (r, SQLite3.GetErrmsg (Connection.Handle));3756      }3757    }37583759    public void Dispose ()3760    {3761      Dispose (true);3762      GC.SuppressFinalize (this);3763    }37643765    void Dispose (bool disposing)3766    {3767      var s = Statement;3768      Statement = NullStatement;3769      Connection = null;3770      if (s != NullStatement) {3771        SQLite3.Finalize (s);3772      }3773    }37743775    ~PreparedSqlLiteInsertCommand ()3776    {3777      Dispose (false);3778    }3779  }37803781  public enum CreateTableResult3782  {3783    Created,3784    Migrated,3785  }37863787  public class CreateTablesResult3788  {3789    public Dictionary<Type, CreateTableResult> Results { get; private set; }3790 + 53791    public CreateTablesResult () + 53792    { + 53793      Results = new Dictionary<Type, CreateTableResult> (); + 53794    }  3795  }  37963797  public class TableQuery<T> : BaseTableQuery, IEnumerable<T>3797  public abstract class BaseTableQuery  3798  {3799    public SQLiteConnection Connection { get; private set; }38003801    public TableMapping Table { get; private set; }38023803    Expression _where;3804    List<Ordering> _orderBys;3805    int? _limit;3806    int? _offset;38073808    BaseTableQuery _joinInner;3809    Expression _joinInnerKeySelector;3810    BaseTableQuery _joinOuter;3811    Expression _joinOuterKeySelector;3812    Expression _joinSelector;38133814    Expression _selector;38153816    TableQuery (SQLiteConnection conn, TableMapping table)3817    {3818      Connection = conn;3819      Table = table;3820    }38213822    public TableQuery (SQLiteConnection conn)3823    {3824      Connection = conn;3825      Table = Connection.GetMapping (typeof (T));3826    }38273828    public TableQuery<U> Clone<U> ()3829    {3830      var q = new TableQuery<U> (Connection, Table);3831      q._where = _where;3832      q._deferred = _deferred;3833      if (_orderBys != null) {3834        q._orderBys = new List<Ordering> (_orderBys);3835      }3836      q._limit = _limit;3837      q._offset = _offset;3838      q._joinInner = _joinInner;3839      q._joinInnerKeySelector = _joinInnerKeySelector;3840      q._joinOuter = _joinOuter;3841      q._joinOuterKeySelector = _joinOuterKeySelector;3842      q._joinSelector = _joinSelector;3843      q._selector = _selector;3844      return q;3845    }38463847    /// <summary>3848    /// Filters the query based on a predicate.3849    /// </summary>3850    public TableQuery<T> Where (Expression<Func<T, bool>> predExpr)3851    {3852      if (predExpr.NodeType == ExpressionType.Lambda) {3853        var lambda = (LambdaExpression)predExpr;3854        var pred = lambda.Body;3855        var q = Clone<T> ();3856        q.AddWhere (pred);3857        return q;3858      }3859      else {3860        throw new NotSupportedException ("Must be a predicate");3861      }3862    }38633864    /// <summary>3865    /// Delete all the rows that match this query.3866    /// </summary>3867    public int Delete ()3868    {3869      return Delete (null);3870    }38713872    /// <summary>3873    /// Delete all the rows that match this query and the given predicate.3874    /// </summary>3875    public int Delete (Expression<Func<T, bool>> predExpr)3876    {3877      if (_limit.HasValue || _offset.HasValue)3878        throw new InvalidOperationException ("Cannot delete with limits or offsets");38793880      if (_where == null && predExpr == null)3881        throw new InvalidOperationException ("No condition specified");38823883      var pred = _where;38843885      if (predExpr != null && predExpr.NodeType == ExpressionType.Lambda) {3886        var lambda = (LambdaExpression)predExpr;3887        pred = pred != null ? Expression.AndAlso (pred, lambda.Body) : lambda.Body;3888      }38893890      var args = new List<object> ();3891      var cmdText = "delete from \"" + Table.TableName + "\"";3892      var w = CompileExpr (pred, args);3893      cmdText += " where " + w.CommandText;38943895      var command = Connection.CreateCommand (cmdText, args.ToArray ());38963897      int result = command.ExecuteNonQuery ();3898      return result;3899    }39003901    /// <summary>3902    /// Yields a given number of elements from the query and then skips the remainder.3903    /// </summary>3904    public TableQuery<T> Take (int n)3905    {3906      var q = Clone<T> ();3907      q._limit = n;3908      return q;3909    }39103911    /// <summary>3912    /// Skips a given number of elements from the query and then yields the remainder.3913    /// </summary>3914    public TableQuery<T> Skip (int n)3915    {3916      var q = Clone<T> ();3917      q._offset = n;3918      return q;3919    }39203921    /// <summary>3922    /// Returns the element at a given index3923    /// </summary>3924    public T ElementAt (int index)3925    {3926      return Skip (index).Take (1).First ();3927    }39283929    bool _deferred;3930    public TableQuery<T> Deferred ()3931    {3932      var q = Clone<T> ();3933      q._deferred = true;3934      return q;3935    }39363937    /// <summary>3938    /// Order the query results according to a key.3939    /// </summary>3940    public TableQuery<T> OrderBy<U> (Expression<Func<T, U>> orderExpr)3941    {3942      return AddOrderBy<U> (orderExpr, true);3943    }39443945    /// <summary>3946    /// Order the query results according to a key.3947    /// </summary>3948    public TableQuery<T> OrderByDescending<U> (Expression<Func<T, U>> orderExpr)3949    {3950      return AddOrderBy<U> (orderExpr, false);3951    }39523953    /// <summary>3954    /// Order the query results according to a key.3955    /// </summary>3956    public TableQuery<T> ThenBy<U> (Expression<Func<T, U>> orderExpr)3957    {3958      return AddOrderBy<U> (orderExpr, true);3959    }39603961    /// <summary>3962    /// Order the query results according to a key.3963    /// </summary>3964    public TableQuery<T> ThenByDescending<U> (Expression<Func<T, U>> orderExpr)3965    {3966      return AddOrderBy<U> (orderExpr, false);3967    }39683969    TableQuery<T> AddOrderBy<U> (Expression<Func<T, U>> orderExpr, bool asc)3970    {3971      if (orderExpr.NodeType == ExpressionType.Lambda) {3972        var lambda = (LambdaExpression)orderExpr;39733974        MemberExpression mem = null;39753976        var unary = lambda.Body as UnaryExpression;3977        if (unary != null && unary.NodeType == ExpressionType.Convert) {3978          mem = unary.Operand as MemberExpression;3979        }3980        else {3981          mem = lambda.Body as MemberExpression;3982        }39833984        if (mem != null && (mem.Expression.NodeType == ExpressionType.Parameter)) {3985          var q = Clone<T> ();3986          if (q._orderBys == null) {3987            q._orderBys = new List<Ordering> ();3988          }3989          q._orderBys.Add (new Ordering {3990            ColumnName = Table.FindColumnWithPropertyName (mem.Member.Name).Name,3991            Ascending = asc3992          });3993          return q;3994        }3995        else {3996          throw new NotSupportedException ("Order By does not support: " + orderExpr);3997        }3998      }3999      else {4000        throw new NotSupportedException ("Must be a predicate");4001      }4002    }40034004    private void AddWhere (Expression pred)4005    {4006      if (_where == null) {4007        _where = pred;4008      }4009      else {4010        _where = Expression.AndAlso (_where, pred);4011      }4012    }40134014    ///// <summary>4015    ///// Performs an inner join of two queries based on matching keys extracted from the elements.4016    ///// </summary>4017    //public TableQuery<TResult> Join<TInner, TKey, TResult> (4018    //  TableQuery<TInner> inner,4019    //  Expression<Func<T, TKey>> outerKeySelector,4020    //  Expression<Func<TInner, TKey>> innerKeySelector,4021    //  Expression<Func<T, TInner, TResult>> resultSelector)4022    //{4023    //  var q = new TableQuery<TResult> (Connection, Connection.GetMapping (typeof (TResult))) {4024    //    _joinOuter = this,4025    //    _joinOuterKeySelector = outerKeySelector,4026    //    _joinInner = inner,4027    //    _joinInnerKeySelector = innerKeySelector,4028    //    _joinSelector = resultSelector,4029    //  };4030    //  return q;4031    //}40324033    // Not needed until Joins are supported4034    // Keeping this commented out forces the default Linq to objects processor to run4035    //public TableQuery<TResult> Select<TResult> (Expression<Func<T, TResult>> selector)4036    //{4037    //  var q = Clone<TResult> ();4038    //  q._selector = selector;3799    protected class Ordering3800    {3801      public string ColumnName { get; set; }3802      public bool Ascending { get; set; }3803    }3804  }38053806  public class TableQuery<T> : BaseTableQuery, IEnumerable<T>3807  {3808    public SQLiteConnection Connection { get; private set; }38093810    public TableMapping Table { get; private set; }38113812    Expression _where;3813    List<Ordering> _orderBys;3814    int? _limit;3815    int? _offset;38163817    BaseTableQuery _joinInner;3818    Expression _joinInnerKeySelector;3819    BaseTableQuery _joinOuter;3820    Expression _joinOuterKeySelector;3821    Expression _joinSelector;38223823    Expression _selector;38243825    TableQuery (SQLiteConnection conn, TableMapping table)3826    {3827      Connection = conn;3828      Table = table;3829    }38303831    public TableQuery (SQLiteConnection conn)3832    {3833      Connection = conn;3834      Table = Connection.GetMapping (typeof (T));3835    }38363837    public TableQuery<U> Clone<U> ()3838    {3839      var q = new TableQuery<U> (Connection, Table);3840      q._where = _where;3841      q._deferred = _deferred;3842      if (_orderBys != null) {3843        q._orderBys = new List<Ordering> (_orderBys);3844      }3845      q._limit = _limit;3846      q._offset = _offset;3847      q._joinInner = _joinInner;3848      q._joinInnerKeySelector = _joinInnerKeySelector;3849      q._joinOuter = _joinOuter;3850      q._joinOuterKeySelector = _joinOuterKeySelector;3851      q._joinSelector = _joinSelector;3852      q._selector = _selector;3853      return q;3854    }38553856    /// <summary>3857    /// Filters the query based on a predicate.3858    /// </summary>3859    public TableQuery<T> Where (Expression<Func<T, bool>> predExpr)3860    {3861      if (predExpr.NodeType == ExpressionType.Lambda) {3862        var lambda = (LambdaExpression)predExpr;3863        var pred = lambda.Body;3864        var q = Clone<T> ();3865        q.AddWhere (pred);3866        return q;3867      }3868      else {3869        throw new NotSupportedException ("Must be a predicate");3870      }3871    }38723873    /// <summary>3874    /// Delete all the rows that match this query.3875    /// </summary>3876    public int Delete ()3877    {3878      return Delete (null);3879    }38803881    /// <summary>3882    /// Delete all the rows that match this query and the given predicate.3883    /// </summary>3884    public int Delete (Expression<Func<T, bool>> predExpr)3885    {3886      if (_limit.HasValue || _offset.HasValue)3887        throw new InvalidOperationException ("Cannot delete with limits or offsets");38883889      if (_where == null && predExpr == null)3890        throw new InvalidOperationException ("No condition specified");38913892      var pred = _where;38933894      if (predExpr != null && predExpr.NodeType == ExpressionType.Lambda) {3895        var lambda = (LambdaExpression)predExpr;3896        pred = pred != null ? Expression.AndAlso (pred, lambda.Body) : lambda.Body;3897      }38983899      var args = new List<object> ();3900      var cmdText = "delete from \"" + Table.TableName + "\"";3901      var w = CompileExpr (pred, args);3902      cmdText += " where " + w.CommandText;39033904      var command = Connection.CreateCommand (cmdText, args.ToArray ());39053906      int result = command.ExecuteNonQuery ();3907      return result;3908    }39093910    /// <summary>3911    /// Yields a given number of elements from the query and then skips the remainder.3912    /// </summary>3913    public TableQuery<T> Take (int n)3914    {3915      var q = Clone<T> ();3916      q._limit = n;3917      return q;3918    }39193920    /// <summary>3921    /// Skips a given number of elements from the query and then yields the remainder.3922    /// </summary>3923    public TableQuery<T> Skip (int n)3924    {3925      var q = Clone<T> ();3926      q._offset = n;3927      return q;3928    }39293930    /// <summary>3931    /// Returns the element at a given index3932    /// </summary>3933    public T ElementAt (int index)3934    {3935      return Skip (index).Take (1).First ();3936    }39373938    bool _deferred;3939    public TableQuery<T> Deferred ()3940    {3941      var q = Clone<T> ();3942      q._deferred = true;3943      return q;3944    }39453946    /// <summary>3947    /// Order the query results according to a key.3948    /// </summary>3949    public TableQuery<T> OrderBy<U> (Expression<Func<T, U>> orderExpr)3950    {3951      return AddOrderBy<U> (orderExpr, true);3952    }39533954    /// <summary>3955    /// Order the query results according to a key.3956    /// </summary>3957    public TableQuery<T> OrderByDescending<U> (Expression<Func<T, U>> orderExpr)3958    {3959      return AddOrderBy<U> (orderExpr, false);3960    }39613962    /// <summary>3963    /// Order the query results according to a key.3964    /// </summary>3965    public TableQuery<T> ThenBy<U> (Expression<Func<T, U>> orderExpr)3966    {3967      return AddOrderBy<U> (orderExpr, true);3968    }39693970    /// <summary>3971    /// Order the query results according to a key.3972    /// </summary>3973    public TableQuery<T> ThenByDescending<U> (Expression<Func<T, U>> orderExpr)3974    {3975      return AddOrderBy<U> (orderExpr, false);3976    }39773978    TableQuery<T> AddOrderBy<U> (Expression<Func<T, U>> orderExpr, bool asc)3979    {3980      if (orderExpr.NodeType == ExpressionType.Lambda) {3981        var lambda = (LambdaExpression)orderExpr;39823983        MemberExpression mem = null;39843985        var unary = lambda.Body as UnaryExpression;3986        if (unary != null && unary.NodeType == ExpressionType.Convert) {3987          mem = unary.Operand as MemberExpression;3988        }3989        else {3990          mem = lambda.Body as MemberExpression;3991        }39923993        if (mem != null && (mem.Expression.NodeType == ExpressionType.Parameter)) {3994          var q = Clone<T> ();3995          if (q._orderBys == null) {3996            q._orderBys = new List<Ordering> ();3997          }3998          q._orderBys.Add (new Ordering {3999            ColumnName = Table.FindColumnWithPropertyName (mem.Member.Name).Name,4000            Ascending = asc4001          });4002          return q;4003        }4004        else {4005          throw new NotSupportedException ("Order By does not support: " + orderExpr);4006        }4007      }4008      else {4009        throw new NotSupportedException ("Must be a predicate");4010      }4011    }40124013    private void AddWhere (Expression pred)4014    {4015      if (_where == null) {4016        _where = pred;4017      }4018      else {4019        _where = Expression.AndAlso (_where, pred);4020      }4021    }40224023    ///// <summary>4024    ///// Performs an inner join of two queries based on matching keys extracted from the elements.4025    ///// </summary>4026    //public TableQuery<TResult> Join<TInner, TKey, TResult> (4027    //  TableQuery<TInner> inner,4028    //  Expression<Func<T, TKey>> outerKeySelector,4029    //  Expression<Func<TInner, TKey>> innerKeySelector,4030    //  Expression<Func<T, TInner, TResult>> resultSelector)4031    //{4032    //  var q = new TableQuery<TResult> (Connection, Connection.GetMapping (typeof (TResult))) {4033    //    _joinOuter = this,4034    //    _joinOuterKeySelector = outerKeySelector,4035    //    _joinInner = inner,4036    //    _joinInnerKeySelector = innerKeySelector,4037    //    _joinSelector = resultSelector,4038    //  };  4039    //  return q;  4040    //}  40414042    private SQLiteCommand GenerateCommand (string selectionList)4043    {4044      if (_joinInner != null && _joinOuter != null) {4045        throw new NotSupportedException ("Joins are not supported.");4046      }4047      else {4048        var cmdText = "select " + selectionList + " from \"" + Table.TableName + "\"";4049        var args = new List<object> ();4050        if (_where != null) {4051          var w = CompileExpr (_where, args);4052          cmdText += " where " + w.CommandText;4053        }4054        if ((_orderBys != null) && (_orderBys.Count > 0)) {4055          var t = string.Join (", ", _orderBys.Select (o => "\"" + o.ColumnName + "\"" + (o.Ascending ? "" : " desc")).T4056          cmdText += " order by " + t;4057        }4058        if (_limit.HasValue) {4059          cmdText += " limit " + _limit.Value;4060        }4061        if (_offset.HasValue) {4062          if (!_limit.HasValue) {4063            cmdText += " limit -1 ";4064          }4065          cmdText += " offset " + _offset.Value;4042    // Not needed until Joins are supported4043    // Keeping this commented out forces the default Linq to objects processor to run4044    //public TableQuery<TResult> Select<TResult> (Expression<Func<T, TResult>> selector)4045    //{4046    //  var q = Clone<TResult> ();4047    //  q._selector = selector;4048    //  return q;4049    //}40504051    private SQLiteCommand GenerateCommand (string selectionList)4052    {4053      if (_joinInner != null && _joinOuter != null) {4054        throw new NotSupportedException ("Joins are not supported.");4055      }4056      else {4057        var cmdText = "select " + selectionList + " from \"" + Table.TableName + "\"";4058        var args = new List<object> ();4059        if (_where != null) {4060          var w = CompileExpr (_where, args);4061          cmdText += " where " + w.CommandText;4062        }4063        if ((_orderBys != null) && (_orderBys.Count > 0)) {4064          var t = string.Join (", ", _orderBys.Select (o => "\"" + o.ColumnName + "\"" + (o.Ascending ? "" : " desc")).T4065          cmdText += " order by " + t;  4066        }4067        return Connection.CreateCommand (cmdText, args.ToArray ());4068      }4069    }40704071    class CompileResult4072    {4073      public string CommandText { get; set; }40744075      public object Value { get; set; }4076    }40774078    private CompileResult CompileExpr (Expression expr, List<object> queryArgs)4079    {4080      if (expr == null) {4081        throw new NotSupportedException ("Expression is NULL");4082      }4083      else if (expr is BinaryExpression) {4084        var bin = (BinaryExpression)expr;40854086        // VB turns 'x=="foo"' into 'CompareString(x,"foo",true/false)==0', so we need to unwrap it4087        // http://blogs.msdn.com/b/vbteam/archive/2007/09/18/vb-expression-trees-string-comparisons.aspx4088        if (bin.Left.NodeType == ExpressionType.Call) {4089          var call = (MethodCallExpression)bin.Left;4090          if (call.Method.DeclaringType.FullName == "Microsoft.VisualBasic.CompilerServices.Operators"4091            && call.Method.Name == "CompareString")4092            bin = Expression.MakeBinary (bin.NodeType, call.Arguments[0], call.Arguments[1]);4093        }4067        if (_limit.HasValue) {4068          cmdText += " limit " + _limit.Value;4069        }4070        if (_offset.HasValue) {4071          if (!_limit.HasValue) {4072            cmdText += " limit -1 ";4073          }4074          cmdText += " offset " + _offset.Value;4075        }4076        return Connection.CreateCommand (cmdText, args.ToArray ());4077      }4078    }40794080    class CompileResult4081    {4082      public string CommandText { get; set; }40834084      public object Value { get; set; }4085    }40864087    private CompileResult CompileExpr (Expression expr, List<object> queryArgs)4088    {4089      if (expr == null) {4090        throw new NotSupportedException ("Expression is NULL");4091      }4092      else if (expr is BinaryExpression) {4093        var bin = (BinaryExpression)expr;  409440954096        var leftr = CompileExpr (bin.Left, queryArgs);4097        var rightr = CompileExpr (bin.Right, queryArgs);40984099        //If either side is a parameter and is null, then handle the other side specially (for "is null"/"is not null")4100        string text;4101        if (leftr.CommandText == "?" && leftr.Value == null)4102          text = CompileNullBinaryExpression (bin, rightr);4103        else if (rightr.CommandText == "?" && rightr.Value == null)4104          text = CompileNullBinaryExpression (bin, leftr);4105        else4106          text = "(" + leftr.CommandText + " " + GetSqlName (bin) + " " + rightr.CommandText + ")";4107        return new CompileResult { CommandText = text };4108      }4109      else if (expr.NodeType == ExpressionType.Not) {4110        var operandExpr = ((UnaryExpression)expr).Operand;4111        var opr = CompileExpr (operandExpr, queryArgs);4112        object val = opr.Value;4113        if (val is bool)4114          val = !((bool)val);4115        return new CompileResult {4116          CommandText = "NOT(" + opr.CommandText + ")",4117          Value = val4118        };4119      }4120      else if (expr.NodeType == ExpressionType.Call) {41214122        var call = (MethodCallExpression)expr;4123        var args = new CompileResult[call.Arguments.Count];4124        var obj = call.Object != null ? CompileExpr (call.Object, queryArgs) : null;41254126        for (var i = 0; i < args.Length; i++) {4127          args[i] = CompileExpr (call.Arguments[i], queryArgs);4128        }41294130        var sqlCall = "";41314132        if (call.Method.Name == "Like" && args.Length == 2) {4133          sqlCall = "(" + args[0].CommandText + " like " + args[1].CommandText + ")";4134        }4135        else if (call.Method.Name == "Contains" && args.Length == 2) {4136          sqlCall = "(" + args[1].CommandText + " in " + args[0].CommandText + ")";4095        // VB turns 'x=="foo"' into 'CompareString(x,"foo",true/false)==0', so we need to unwrap it4096        // http://blogs.msdn.com/b/vbteam/archive/2007/09/18/vb-expression-trees-string-comparisons.aspx4097        if (bin.Left.NodeType == ExpressionType.Call) {4098          var call = (MethodCallExpression)bin.Left;4099          if (call.Method.DeclaringType.FullName == "Microsoft.VisualBasic.CompilerServices.Operators"4100            && call.Method.Name == "CompareString")4101            bin = Expression.MakeBinary (bin.NodeType, call.Arguments[0], call.Arguments[1]);4102        }410341044105        var leftr = CompileExpr (bin.Left, queryArgs);4106        var rightr = CompileExpr (bin.Right, queryArgs);41074108        //If either side is a parameter and is null, then handle the other side specially (for "is null"/"is not null")4109        string text;4110        if (leftr.CommandText == "?" && leftr.Value == null)4111          text = CompileNullBinaryExpression (bin, rightr);4112        else if (rightr.CommandText == "?" && rightr.Value == null)4113          text = CompileNullBinaryExpression (bin, leftr);4114        else4115          text = "(" + leftr.CommandText + " " + GetSqlName (bin) + " " + rightr.CommandText + ")";4116        return new CompileResult { CommandText = text };4117      }4118      else if (expr.NodeType == ExpressionType.Not) {4119        var operandExpr = ((UnaryExpression)expr).Operand;4120        var opr = CompileExpr (operandExpr, queryArgs);4121        object val = opr.Value;4122        if (val is bool)4123          val = !((bool)val);4124        return new CompileResult {4125          CommandText = "NOT(" + opr.CommandText + ")",4126          Value = val4127        };4128      }4129      else if (expr.NodeType == ExpressionType.Call) {41304131        var call = (MethodCallExpression)expr;4132        var args = new CompileResult[call.Arguments.Count];4133        var obj = call.Object != null ? CompileExpr (call.Object, queryArgs) : null;41344135        for (var i = 0; i < args.Length; i++) {4136          args[i] = CompileExpr (call.Arguments[i], queryArgs);  4137        }4138        else if (call.Method.Name == "Contains" && args.Length == 1) {4139          if (call.Object != null && call.Object.Type == typeof (string)) {4140            sqlCall = "( instr(" + obj.CommandText + "," + args[0].CommandText + ") >0 )";4141          }4142          else {4143            sqlCall = "(" + args[0].CommandText + " in " + obj.CommandText + ")";4144          }4145        }4146        else if (call.Method.Name == "StartsWith" && args.Length >= 1) {4147          var startsWithCmpOp = StringComparison.CurrentCulture;4148          if (args.Length == 2) {4149            startsWithCmpOp = (StringComparison)args[1].Value;41384139        var sqlCall = "";41404141        if (call.Method.Name == "Like" && args.Length == 2) {4142          sqlCall = "(" + args[0].CommandText + " like " + args[1].CommandText + ")";4143        }4144        else if (call.Method.Name == "Contains" && args.Length == 2) {4145          sqlCall = "(" + args[1].CommandText + " in " + args[0].CommandText + ")";4146        }4147        else if (call.Method.Name == "Contains" && args.Length == 1) {4148          if (call.Object != null && call.Object.Type == typeof (string)) {4149            sqlCall = "( instr(" + obj.CommandText + "," + args[0].CommandText + ") >0 )";  4150          }4151          switch (startsWithCmpOp) {4152            case StringComparison.Ordinal:4153            case StringComparison.CurrentCulture:4154              sqlCall = "( substr(" + obj.CommandText + ", 1, " + args[0].Value.ToString ().Length + ") =  " + args[0].C4155              break;4156            case StringComparison.OrdinalIgnoreCase:4157            case StringComparison.CurrentCultureIgnoreCase:4158              sqlCall = "(" + obj.CommandText + " like (" + args[0].CommandText + " || '%'))";4159              break;4160          }41614162        }4163        else if (call.Method.Name == "EndsWith" && args.Length >= 1) {4164          var endsWithCmpOp = StringComparison.CurrentCulture;4165          if (args.Length == 2) {4166            endsWithCmpOp = (StringComparison)args[1].Value;4167          }4168          switch (endsWithCmpOp) {4169            case StringComparison.Ordinal:4170            case StringComparison.CurrentCulture:4171              sqlCall = "( substr(" + obj.CommandText + ", length(" + obj.CommandText + ") - " + args[0].Value.ToString 4172              break;4173            case StringComparison.OrdinalIgnoreCase:4174            case StringComparison.CurrentCultureIgnoreCase:4175              sqlCall = "(" + obj.CommandText + " like ('%' || " + args[0].CommandText + "))";4176              break;4177          }4178        }4179        else if (call.Method.Name == "Equals" && args.Length == 1) {4180          sqlCall = "(" + obj.CommandText + " = (" + args[0].CommandText + "))";4181        }4182        else if (call.Method.Name == "ToLower") {4183          sqlCall = "(lower(" + obj.CommandText + "))";4184        }4185        else if (call.Method.Name == "ToUpper") {4186          sqlCall = "(upper(" + obj.CommandText + "))";4151          else {4152            sqlCall = "(" + args[0].CommandText + " in " + obj.CommandText + ")";4153          }4154        }4155        else if (call.Method.Name == "StartsWith" && args.Length >= 1) {4156          var startsWithCmpOp = StringComparison.CurrentCulture;4157          if (args.Length == 2) {4158            startsWithCmpOp = (StringComparison)args[1].Value;4159          }4160          switch (startsWithCmpOp) {4161            case StringComparison.Ordinal:4162            case StringComparison.CurrentCulture:4163              sqlCall = "( substr(" + obj.CommandText + ", 1, " + args[0].Value.ToString ().Length + ") =  " + args[0].C4164              break;4165            case StringComparison.OrdinalIgnoreCase:4166            case StringComparison.CurrentCultureIgnoreCase:4167              sqlCall = "(" + obj.CommandText + " like (" + args[0].CommandText + " || '%'))";4168              break;4169          }41704171        }4172        else if (call.Method.Name == "EndsWith" && args.Length >= 1) {4173          var endsWithCmpOp = StringComparison.CurrentCulture;4174          if (args.Length == 2) {4175            endsWithCmpOp = (StringComparison)args[1].Value;4176          }4177          switch (endsWithCmpOp) {4178            case StringComparison.Ordinal:4179            case StringComparison.CurrentCulture:4180              sqlCall = "( substr(" + obj.CommandText + ", length(" + obj.CommandText + ") - " + args[0].Value.ToString 4181              break;4182            case StringComparison.OrdinalIgnoreCase:4183            case StringComparison.CurrentCultureIgnoreCase:4184              sqlCall = "(" + obj.CommandText + " like ('%' || " + args[0].CommandText + "))";4185              break;4186          }  4187        }4188        else if (call.Method.Name == "Replace" && args.Length == 2) {4189          sqlCall = "(replace(" + obj.CommandText + "," + args[0].CommandText + "," + args[1].CommandText + "))";4188        else if (call.Method.Name == "Equals" && args.Length == 1) {4189          sqlCall = "(" + obj.CommandText + " = (" + args[0].CommandText + "))";  4190        }4191        else if (call.Method.Name == "IsNullOrEmpty" && args.Length == 1) {4192          sqlCall = "(" + args[0].CommandText + " is null or" + args[0].CommandText + " ='' )";4191        else if (call.Method.Name == "ToLower") {4192          sqlCall = "(lower(" + obj.CommandText + "))";  4193        }4194        else {4195          sqlCall = call.Method.Name.ToLower () + "(" + string.Join (",", args.Select (a => a.CommandText).ToArray ()) +4194        else if (call.Method.Name == "ToUpper") {4195          sqlCall = "(upper(" + obj.CommandText + "))";  4196        }4197        return new CompileResult { CommandText = sqlCall };41984199      }4200      else if (expr.NodeType == ExpressionType.Constant) {4201        var c = (ConstantExpression)expr;4202        queryArgs.Add (c.Value);4203        return new CompileResult {4204          CommandText = "?",4205          Value = c.Value4206        };4207      }4208      else if (expr.NodeType == ExpressionType.Convert) {4209        var u = (UnaryExpression)expr;4210        var ty = u.Type;4211        var valr = CompileExpr (u.Operand, queryArgs);4197        else if (call.Method.Name == "Replace" && args.Length == 2) {4198          sqlCall = "(replace(" + obj.CommandText + "," + args[0].CommandText + "," + args[1].CommandText + "))";4199        }4200        else if (call.Method.Name == "IsNullOrEmpty" && args.Length == 1) {4201          sqlCall = "(" + args[0].CommandText + " is null or" + args[0].CommandText + " ='' )";4202        }4203        else {4204          sqlCall = call.Method.Name.ToLower () + "(" + string.Join (",", args.Select (a => a.CommandText).ToArray ()) +4205        }4206        return new CompileResult { CommandText = sqlCall };42074208      }4209      else if (expr.NodeType == ExpressionType.Constant) {4210        var c = (ConstantExpression)expr;4211        queryArgs.Add (c.Value);  4212        return new CompileResult {4213          CommandText = valr.CommandText,4214          Value = valr.Value != null ? ConvertTo (valr.Value, ty) : null4213          CommandText = "?",4214          Value = c.Value  4215        };  4216      }4217      else if (expr.NodeType == ExpressionType.MemberAccess) {4218        var mem = (MemberExpression)expr;42194220        var paramExpr = mem.Expression as ParameterExpression;4221        if (paramExpr == null) {4222          var convert = mem.Expression as UnaryExpression;4223          if (convert != null && convert.NodeType == ExpressionType.Convert) {4224            paramExpr = convert.Operand as ParameterExpression;4225          }4226        }42274228        if (paramExpr != null) {4229          //4230          // This is a column of our table, output just the column name4231          // Need to translate it if that column name is mapped4232          //4233          var columnName = Table.FindColumnWithPropertyName (mem.Member.Name).Name;4234          return new CompileResult { CommandText = "\"" + columnName + "\"" };4217      else if (expr.NodeType == ExpressionType.Convert) {4218        var u = (UnaryExpression)expr;4219        var ty = u.Type;4220        var valr = CompileExpr (u.Operand, queryArgs);4221        return new CompileResult {4222          CommandText = valr.CommandText,4223          Value = valr.Value != null ? ConvertTo (valr.Value, ty) : null4224        };4225      }4226      else if (expr.NodeType == ExpressionType.MemberAccess) {4227        var mem = (MemberExpression)expr;42284229        var paramExpr = mem.Expression as ParameterExpression;4230        if (paramExpr == null) {4231          var convert = mem.Expression as UnaryExpression;4232          if (convert != null && convert.NodeType == ExpressionType.Convert) {4233            paramExpr = convert.Operand as ParameterExpression;4234          }  4235        }4236        else {4237          object obj = null;4238          if (mem.Expression != null) {4239            var r = CompileExpr (mem.Expression, queryArgs);4240            if (r.Value == null) {4241              throw new NotSupportedException ("Member access failed to compile expression");4242            }4243            if (r.CommandText == "?") {4244              queryArgs.RemoveAt (queryArgs.Count - 1);4245            }4246            obj = r.Value;4247          }42484249          //4250          // Get the member value4251          //4252          object val = null;42534254          if (mem.Member is PropertyInfo) {4255            var m = (PropertyInfo)mem.Member;4256            val = m.GetValue (obj, null);4257          }4258          else if (mem.Member is FieldInfo) {4259            var m = (FieldInfo)mem.Member;4260            val = m.GetValue (obj);4261          }4262          else {4263            throw new NotSupportedException ("MemberExpr: " + mem.Member.GetType ());4264          }42654266          //4267          // Work special magic for enumerables4268          //4269          if (val != null && val is System.Collections.IEnumerable && !(val is string) && !(val is System.Collections.Ge4270            var sb = new System.Text.StringBuilder ();4271            sb.Append ("(");4272            var head = "";4273            foreach (var a in (System.Collections.IEnumerable)val) {4274              queryArgs.Add (a);4275              sb.Append (head);4276              sb.Append ("?");4277              head = ",";4278            }4279            sb.Append (")");4280            return new CompileResult {4281              CommandText = sb.ToString (),4282              Value = val4283            };4284          }4285          else {4286            queryArgs.Add (val);4287            return new CompileResult {4288              CommandText = "?",4289              Value = val4290            };4291          }4292        }4293      }4294      throw new NotSupportedException ("Cannot compile: " + expr.NodeType.ToString ());4295    }42964297    static object ConvertTo (object obj, Type t)4298    {4299      Type nut = Nullable.GetUnderlyingType (t);43004301      if (nut != null) {4302        if (obj == null)4303          return null;4304        return Convert.ChangeType (obj, nut);4305      }4306      else {4307        return Convert.ChangeType (obj, t);4308      }4309    }43104311    /// <summary>4312    /// Compiles a BinaryExpression where one of the parameters is null.4313    /// </summary>4314    /// <param name="expression">The expression to compile</param>4315    /// <param name="parameter">The non-null parameter</param>4316    private string CompileNullBinaryExpression (BinaryExpression expression, CompileResult parameter)4317    {4318      if (expression.NodeType == ExpressionType.Equal)4319        return "(" + parameter.CommandText + " is ?)";4320      else if (expression.NodeType == ExpressionType.NotEqual)4321        return "(" + parameter.CommandText + " is not ?)";4322      else if (expression.NodeType == ExpressionType.GreaterThan4323        || expression.NodeType == ExpressionType.GreaterThanOrEqual4324        || expression.NodeType == ExpressionType.LessThan4325        || expression.NodeType == ExpressionType.LessThanOrEqual)4326        return "(" + parameter.CommandText + " < ?)"; // always false4327      else4328        throw new NotSupportedException ("Cannot compile Null-BinaryExpression with type " + expression.NodeType.ToStrin4329    }43304331    string GetSqlName (Expression expr)4332    {4333      var n = expr.NodeType;4334      if (n == ExpressionType.GreaterThan)4335        return ">";4336      else if (n == ExpressionType.GreaterThanOrEqual) {4337        return ">=";4338      }4339      else if (n == ExpressionType.LessThan) {4340        return "<";4341      }4342      else if (n == ExpressionType.LessThanOrEqual) {4343        return "<=";4344      }4345      else if (n == ExpressionType.And) {4346        return "&";42364237        if (paramExpr != null) {4238          //4239          // This is a column of our table, output just the column name4240          // Need to translate it if that column name is mapped4241          //4242          var columnName = Table.FindColumnWithPropertyName (mem.Member.Name).Name;4243          return new CompileResult { CommandText = "\"" + columnName + "\"" };4244        }4245        else {4246          object obj = null;4247          if (mem.Expression != null) {4248            var r = CompileExpr (mem.Expression, queryArgs);4249            if (r.Value == null) {4250              throw new NotSupportedException ("Member access failed to compile expression");4251            }4252            if (r.CommandText == "?") {4253              queryArgs.RemoveAt (queryArgs.Count - 1);4254            }4255            obj = r.Value;4256          }42574258          //4259          // Get the member value4260          //4261          object val = null;42624263          if (mem.Member is PropertyInfo) {4264            var m = (PropertyInfo)mem.Member;4265            val = m.GetValue (obj, null);4266          }4267          else if (mem.Member is FieldInfo) {4268            var m = (FieldInfo)mem.Member;4269            val = m.GetValue (obj);4270          }4271          else {4272            throw new NotSupportedException ("MemberExpr: " + mem.Member.GetType ());4273          }42744275          //4276          // Work special magic for enumerables4277          //4278          if (val != null && val is System.Collections.IEnumerable && !(val is string) && !(val is System.Collections.Ge4279            var sb = new System.Text.StringBuilder ();4280            sb.Append ("(");4281            var head = "";4282            foreach (var a in (System.Collections.IEnumerable)val) {4283              queryArgs.Add (a);4284              sb.Append (head);4285              sb.Append ("?");4286              head = ",";4287            }4288            sb.Append (")");4289            return new CompileResult {4290              CommandText = sb.ToString (),4291              Value = val4292            };4293          }4294          else {4295            queryArgs.Add (val);4296            return new CompileResult {4297              CommandText = "?",4298              Value = val4299            };4300          }4301        }4302      }4303      throw new NotSupportedException ("Cannot compile: " + expr.NodeType.ToString ());4304    }43054306    static object ConvertTo (object obj, Type t)4307    {4308      Type nut = Nullable.GetUnderlyingType (t);43094310      if (nut != null) {4311        if (obj == null)4312          return null;4313        return Convert.ChangeType (obj, nut);4314      }4315      else {4316        return Convert.ChangeType (obj, t);4317      }4318    }43194320    /// <summary>4321    /// Compiles a BinaryExpression where one of the parameters is null.4322    /// </summary>4323    /// <param name="expression">The expression to compile</param>4324    /// <param name="parameter">The non-null parameter</param>4325    private string CompileNullBinaryExpression (BinaryExpression expression, CompileResult parameter)4326    {4327      if (expression.NodeType == ExpressionType.Equal)4328        return "(" + parameter.CommandText + " is ?)";4329      else if (expression.NodeType == ExpressionType.NotEqual)4330        return "(" + parameter.CommandText + " is not ?)";4331      else if (expression.NodeType == ExpressionType.GreaterThan4332        || expression.NodeType == ExpressionType.GreaterThanOrEqual4333        || expression.NodeType == ExpressionType.LessThan4334        || expression.NodeType == ExpressionType.LessThanOrEqual)4335        return "(" + parameter.CommandText + " < ?)"; // always false4336      else4337        throw new NotSupportedException ("Cannot compile Null-BinaryExpression with type " + expression.NodeType.ToStrin4338    }43394340    string GetSqlName (Expression expr)4341    {4342      var n = expr.NodeType;4343      if (n == ExpressionType.GreaterThan)4344        return ">";4345      else if (n == ExpressionType.GreaterThanOrEqual) {4346        return ">=";  4347      }4348      else if (n == ExpressionType.AndAlso) {4349        return "and";4348      else if (n == ExpressionType.LessThan) {4349        return "<";  4350      }4351      else if (n == ExpressionType.Or) {4352        return "|";4351      else if (n == ExpressionType.LessThanOrEqual) {4352        return "<=";  4353      }4354      else if (n == ExpressionType.OrElse) {4355        return "or";4354      else if (n == ExpressionType.And) {4355        return "&";  4356      }4357      else if (n == ExpressionType.Equal) {4358        return "=";4357      else if (n == ExpressionType.AndAlso) {4358        return "and";  4359      }4360      else if (n == ExpressionType.NotEqual) {4361        return "!=";4360      else if (n == ExpressionType.Or) {4361        return "|";  4362      }4363      else {4364        throw new NotSupportedException ("Cannot get SQL for: " + n);4363      else if (n == ExpressionType.OrElse) {4364        return "or";  4365      }4366    }43674368    /// <summary>4369    /// Execute SELECT COUNT(*) on the query4370    /// </summary>4371    public int Count ()4372    {4373      return GenerateCommand ("count(*)").ExecuteScalar<int> ();4374    }43754376    /// <summary>4377    /// Execute SELECT COUNT(*) on the query with an additional WHERE clause.4378    /// </summary>4379    public int Count (Expression<Func<T, bool>> predExpr)4380    {4381      return Where (predExpr).Count ();4382    }43834384    public IEnumerator<T> GetEnumerator ()4385    {4386      if (!_deferred)4387        return GenerateCommand ("*").ExecuteQuery<T> ().GetEnumerator ();43884389      return GenerateCommand ("*").ExecuteDeferredQuery<T> ().GetEnumerator ();4390    }43914392    System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator ()4393    {4394      return GetEnumerator ();4395    }43964397    /// <summary>4398    /// Queries the database and returns the results as a List.4399    /// </summary>4400    public List<T> ToList ()4401    {4402      return GenerateCommand ("*").ExecuteQuery<T> ();4403    }44044405    /// <summary>4406    /// Queries the database and returns the results as an array.4407    /// </summary>4408    public T[] ToArray ()4409    {4410      return GenerateCommand ("*").ExecuteQuery<T> ().ToArray ();4411    }44124413    /// <summary>4414    /// Returns the first element of this query.4415    /// </summary>4416    public T First ()4417    {4418      var query = Take (1);4419      return query.ToList ().First ();4366      else if (n == ExpressionType.Equal) {4367        return "=";4368      }4369      else if (n == ExpressionType.NotEqual) {4370        return "!=";4371      }4372      else {4373        throw new NotSupportedException ("Cannot get SQL for: " + n);4374      }4375    }43764377    /// <summary>4378    /// Execute SELECT COUNT(*) on the query4379    /// </summary>4380    public int Count ()4381    {4382      return GenerateCommand ("count(*)").ExecuteScalar<int> ();4383    }43844385    /// <summary>4386    /// Execute SELECT COUNT(*) on the query with an additional WHERE clause.4387    /// </summary>4388    public int Count (Expression<Func<T, bool>> predExpr)4389    {4390      return Where (predExpr).Count ();4391    }43924393    public IEnumerator<T> GetEnumerator ()4394    {4395      if (!_deferred)4396        return GenerateCommand ("*").ExecuteQuery<T> ().GetEnumerator ();43974398      return GenerateCommand ("*").ExecuteDeferredQuery<T> ().GetEnumerator ();4399    }44004401    System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator ()4402    {4403      return GetEnumerator ();4404    }44054406    /// <summary>4407    /// Queries the database and returns the results as a List.4408    /// </summary>4409    public List<T> ToList ()4410    {4411      return GenerateCommand ("*").ExecuteQuery<T> ();4412    }44134414    /// <summary>4415    /// Queries the database and returns the results as an array.4416    /// </summary>4417    public T[] ToArray ()4418    {4419      return GenerateCommand ("*").ExecuteQuery<T> ().ToArray ();  4420    }  4421  4422    /// <summary>4423    /// Returns the first element of this query, or null if no element is found.4423    /// Returns the first element of this query.  4424    /// </summary>4425    public T FirstOrDefault ()4425    public T First ()  4426    {  4427      var query = Take (1);4428      return query.ToList ().FirstOrDefault ();4428      return query.ToList ().First ();  4429    }  4430  4431    /// <summary>4432    /// Returns the first element of this query that matches the predicate.4432    /// Returns the first element of this query, or null if no element is found.  4433    /// </summary>4434    public T First (Expression<Func<T, bool>> predExpr)4434    public T FirstOrDefault ()  4435    {4436      return Where (predExpr).First ();4437    }44384439    /// <summary>4440    /// Returns the first element of this query that matches the predicate, or null4441    /// if no element is found.4436      var query = Take (1);4437      return query.ToList ().FirstOrDefault ();4438    }44394440    /// <summary>4441    /// Returns the first element of this query that matches the predicate.  4442    /// </summary>4443    public T FirstOrDefault (Expression<Func<T, bool>> predExpr)4443    public T First (Expression<Func<T, bool>> predExpr)  4444    {4445      return Where (predExpr).FirstOrDefault ();4445      return Where (predExpr).First ();  4446    }4447  }44484449  public static class SQLite34450  {4451    public enum Result : int4452    {4453      OK = 0,4454      Error = 1,4455      Internal = 2,4456      Perm = 3,4457      Abort = 4,4458      Busy = 5,4459      Locked = 6,4460      NoMem = 7,4461      ReadOnly = 8,4462      Interrupt = 9,4463      IOError = 10,4464      Corrupt = 11,4465      NotFound = 12,4466      Full = 13,4467      CannotOpen = 14,4468      LockErr = 15,4469      Empty = 16,4470      SchemaChngd = 17,4471      TooBig = 18,4472      Constraint = 19,4473      Mismatch = 20,4474      Misuse = 21,4475      NotImplementedLFS = 22,4476      AccessDenied = 23,4477      Format = 24,4478      Range = 25,4479      NonDBFile = 26,4480      Notice = 27,4481      Warning = 28,4482      Row = 100,4483      Done = 1014484    }44854486    public enum ExtendedResult : int4487    {4488      IOErrorRead = (Result.IOError | (1 << 8)),4489      IOErrorShortRead = (Result.IOError | (2 << 8)),4490      IOErrorWrite = (Result.IOError | (3 << 8)),4491      IOErrorFsync = (Result.IOError | (4 << 8)),4492      IOErrorDirFSync = (Result.IOError | (5 << 8)),4493      IOErrorTruncate = (Result.IOError | (6 << 8)),4494      IOErrorFStat = (Result.IOError | (7 << 8)),4495      IOErrorUnlock = (Result.IOError | (8 << 8)),4496      IOErrorRdlock = (Result.IOError | (9 << 8)),4497      IOErrorDelete = (Result.IOError | (10 << 8)),4498      IOErrorBlocked = (Result.IOError | (11 << 8)),4499      IOErrorNoMem = (Result.IOError | (12 << 8)),4500      IOErrorAccess = (Result.IOError | (13 << 8)),4501      IOErrorCheckReservedLock = (Result.IOError | (14 << 8)),4502      IOErrorLock = (Result.IOError | (15 << 8)),4503      IOErrorClose = (Result.IOError | (16 << 8)),4504      IOErrorDirClose = (Result.IOError | (17 << 8)),4505      IOErrorSHMOpen = (Result.IOError | (18 << 8)),4506      IOErrorSHMSize = (Result.IOError | (19 << 8)),4507      IOErrorSHMLock = (Result.IOError | (20 << 8)),4508      IOErrorSHMMap = (Result.IOError | (21 << 8)),4509      IOErrorSeek = (Result.IOError | (22 << 8)),4510      IOErrorDeleteNoEnt = (Result.IOError | (23 << 8)),4511      IOErrorMMap = (Result.IOError | (24 << 8)),4512      LockedSharedcache = (Result.Locked | (1 << 8)),4513      BusyRecovery = (Result.Busy | (1 << 8)),4514      CannottOpenNoTempDir = (Result.CannotOpen | (1 << 8)),4515      CannotOpenIsDir = (Result.CannotOpen | (2 << 8)),4516      CannotOpenFullPath = (Result.CannotOpen | (3 << 8)),4517      CorruptVTab = (Result.Corrupt | (1 << 8)),4518      ReadonlyRecovery = (Result.ReadOnly | (1 << 8)),4519      ReadonlyCannotLock = (Result.ReadOnly | (2 << 8)),4520      ReadonlyRollback = (Result.ReadOnly | (3 << 8)),4521      AbortRollback = (Result.Abort | (2 << 8)),4522      ConstraintCheck = (Result.Constraint | (1 << 8)),4523      ConstraintCommitHook = (Result.Constraint | (2 << 8)),4524      ConstraintForeignKey = (Result.Constraint | (3 << 8)),4525      ConstraintFunction = (Result.Constraint | (4 << 8)),4526      ConstraintNotNull = (Result.Constraint | (5 << 8)),4527      ConstraintPrimaryKey = (Result.Constraint | (6 << 8)),4528      ConstraintTrigger = (Result.Constraint | (7 << 8)),4529      ConstraintUnique = (Result.Constraint | (8 << 8)),4530      ConstraintVTab = (Result.Constraint | (9 << 8)),4531      NoticeRecoverWAL = (Result.Notice | (1 << 8)),4532      NoticeRecoverRollback = (Result.Notice | (2 << 8))4533    }453445354536    public enum ConfigOption : int4537    {4538      SingleThread = 1,4539      MultiThread = 2,4540      Serialized = 34541    }45424543    const string LibraryPath = "sqlite3";44474448    /// <summary>4449    /// Returns the first element of this query that matches the predicate, or null4450    /// if no element is found.4451    /// </summary>4452    public T FirstOrDefault (Expression<Func<T, bool>> predExpr)4453    {4454      return Where (predExpr).FirstOrDefault ();4455    }4456  }44574458  public static class SQLite34459  {4460    public enum Result : int4461    {4462      OK = 0,4463      Error = 1,4464      Internal = 2,4465      Perm = 3,4466      Abort = 4,4467      Busy = 5,4468      Locked = 6,4469      NoMem = 7,4470      ReadOnly = 8,4471      Interrupt = 9,4472      IOError = 10,4473      Corrupt = 11,4474      NotFound = 12,4475      Full = 13,4476      CannotOpen = 14,4477      LockErr = 15,4478      Empty = 16,4479      SchemaChngd = 17,4480      TooBig = 18,4481      Constraint = 19,4482      Mismatch = 20,4483      Misuse = 21,4484      NotImplementedLFS = 22,4485      AccessDenied = 23,4486      Format = 24,4487      Range = 25,4488      NonDBFile = 26,4489      Notice = 27,4490      Warning = 28,4491      Row = 100,4492      Done = 1014493    }44944495    public enum ExtendedResult : int4496    {4497      IOErrorRead = (Result.IOError | (1 << 8)),4498      IOErrorShortRead = (Result.IOError | (2 << 8)),4499      IOErrorWrite = (Result.IOError | (3 << 8)),4500      IOErrorFsync = (Result.IOError | (4 << 8)),4501      IOErrorDirFSync = (Result.IOError | (5 << 8)),4502      IOErrorTruncate = (Result.IOError | (6 << 8)),4503      IOErrorFStat = (Result.IOError | (7 << 8)),4504      IOErrorUnlock = (Result.IOError | (8 << 8)),4505      IOErrorRdlock = (Result.IOError | (9 << 8)),4506      IOErrorDelete = (Result.IOError | (10 << 8)),4507      IOErrorBlocked = (Result.IOError | (11 << 8)),4508      IOErrorNoMem = (Result.IOError | (12 << 8)),4509      IOErrorAccess = (Result.IOError | (13 << 8)),4510      IOErrorCheckReservedLock = (Result.IOError | (14 << 8)),4511      IOErrorLock = (Result.IOError | (15 << 8)),4512      IOErrorClose = (Result.IOError | (16 << 8)),4513      IOErrorDirClose = (Result.IOError | (17 << 8)),4514      IOErrorSHMOpen = (Result.IOError | (18 << 8)),4515      IOErrorSHMSize = (Result.IOError | (19 << 8)),4516      IOErrorSHMLock = (Result.IOError | (20 << 8)),4517      IOErrorSHMMap = (Result.IOError | (21 << 8)),4518      IOErrorSeek = (Result.IOError | (22 << 8)),4519      IOErrorDeleteNoEnt = (Result.IOError | (23 << 8)),4520      IOErrorMMap = (Result.IOError | (24 << 8)),4521      LockedSharedcache = (Result.Locked | (1 << 8)),4522      BusyRecovery = (Result.Busy | (1 << 8)),4523      CannottOpenNoTempDir = (Result.CannotOpen | (1 << 8)),4524      CannotOpenIsDir = (Result.CannotOpen | (2 << 8)),4525      CannotOpenFullPath = (Result.CannotOpen | (3 << 8)),4526      CorruptVTab = (Result.Corrupt | (1 << 8)),4527      ReadonlyRecovery = (Result.ReadOnly | (1 << 8)),4528      ReadonlyCannotLock = (Result.ReadOnly | (2 << 8)),4529      ReadonlyRollback = (Result.ReadOnly | (3 << 8)),4530      AbortRollback = (Result.Abort | (2 << 8)),4531      ConstraintCheck = (Result.Constraint | (1 << 8)),4532      ConstraintCommitHook = (Result.Constraint | (2 << 8)),4533      ConstraintForeignKey = (Result.Constraint | (3 << 8)),4534      ConstraintFunction = (Result.Constraint | (4 << 8)),4535      ConstraintNotNull = (Result.Constraint | (5 << 8)),4536      ConstraintPrimaryKey = (Result.Constraint | (6 << 8)),4537      ConstraintTrigger = (Result.Constraint | (7 << 8)),4538      ConstraintUnique = (Result.Constraint | (8 << 8)),4539      ConstraintVTab = (Result.Constraint | (9 << 8)),4540      NoticeRecoverWAL = (Result.Notice | (1 << 8)),4541      NoticeRecoverRollback = (Result.Notice | (2 << 8))4542    }4543  45444545#if !USE_CSHARP_SQLITE && !USE_WP8_NATIVE_SQLITE && !USE_SQLITEPCL_RAW4546    [DllImport(LibraryPath, EntryPoint = "sqlite3_threadsafe", CallingConvention=CallingConvention.Cdecl)]4547    public static extern int Threadsafe ();45484549    [DllImport(LibraryPath, EntryPoint = "sqlite3_open", CallingConvention=CallingConvention.Cdecl)]4550    public static extern Result Open ([MarshalAs(UnmanagedType.LPStr)] string filename, out IntPtr db);4545    public enum ConfigOption : int4546    {4547      SingleThread = 1,4548      MultiThread = 2,4549      Serialized = 34550    }  45514552    [DllImport(LibraryPath, EntryPoint = "sqlite3_open_v2", CallingConvention=CallingConvention.Cdecl)]4553    public static extern Result Open ([MarshalAs(UnmanagedType.LPStr)] string filename, out IntPtr db, int flags, [Marsh45544555    [DllImport(LibraryPath, EntryPoint = "sqlite3_open_v2", CallingConvention = CallingConvention.Cdecl)]4556    public static extern Result Open(byte[] filename, out IntPtr db, int flags, [MarshalAs (UnmanagedType.LPStr)] string4552    const string LibraryPath = "sqlite3";45534554#if !USE_CSHARP_SQLITE && !USE_WP8_NATIVE_SQLITE && !USE_SQLITEPCL_RAW4555    [DllImport(LibraryPath, EntryPoint = "sqlite3_threadsafe", CallingConvention=CallingConvention.Cdecl)]4556    public static extern int Threadsafe ();  45574558    [DllImport(LibraryPath, EntryPoint = "sqlite3_open16", CallingConvention = CallingConvention.Cdecl)]4559    public static extern Result Open16([MarshalAs(UnmanagedType.LPWStr)] string filename, out IntPtr db);4558    [DllImport(LibraryPath, EntryPoint = "sqlite3_open", CallingConvention=CallingConvention.Cdecl)]4559    public static extern Result Open ([MarshalAs(UnmanagedType.LPStr)] string filename, out IntPtr db);  45604561    [DllImport(LibraryPath, EntryPoint = "sqlite3_enable_load_extension", CallingConvention=CallingConvention.Cdecl)]4562    public static extern Result EnableLoadExtension (IntPtr db, int onoff);4561    [DllImport(LibraryPath, EntryPoint = "sqlite3_open_v2", CallingConvention=CallingConvention.Cdecl)]4562    public static extern Result Open ([MarshalAs(UnmanagedType.LPStr)] string filename, out IntPtr db, int flags, [Marsh  45634564    [DllImport(LibraryPath, EntryPoint = "sqlite3_close", CallingConvention=CallingConvention.Cdecl)]4565    public static extern Result Close (IntPtr db);4564    [DllImport(LibraryPath, EntryPoint = "sqlite3_open_v2", CallingConvention = CallingConvention.Cdecl)]4565    public static extern Result Open(byte[] filename, out IntPtr db, int flags, [MarshalAs (UnmanagedType.LPStr)] string  45664567    [DllImport(LibraryPath, EntryPoint = "sqlite3_close_v2", CallingConvention = CallingConvention.Cdecl)]4568    public static extern Result Close2(IntPtr db);4567    [DllImport(LibraryPath, EntryPoint = "sqlite3_open16", CallingConvention = CallingConvention.Cdecl)]4568    public static extern Result Open16([MarshalAs(UnmanagedType.LPWStr)] string filename, out IntPtr db);  45694570    [DllImport(LibraryPath, EntryPoint = "sqlite3_initialize", CallingConvention=CallingConvention.Cdecl)]4571    public static extern Result Initialize();4570    [DllImport(LibraryPath, EntryPoint = "sqlite3_enable_load_extension", CallingConvention=CallingConvention.Cdecl)]4571    public static extern Result EnableLoadExtension (IntPtr db, int onoff);  45724573    [DllImport(LibraryPath, EntryPoint = "sqlite3_shutdown", CallingConvention=CallingConvention.Cdecl)]4574    public static extern Result Shutdown();4573    [DllImport(LibraryPath, EntryPoint = "sqlite3_close", CallingConvention=CallingConvention.Cdecl)]4574    public static extern Result Close (IntPtr db);  45754576    [DllImport(LibraryPath, EntryPoint = "sqlite3_config", CallingConvention=CallingConvention.Cdecl)]4577    public static extern Result Config (ConfigOption option);4576    [DllImport(LibraryPath, EntryPoint = "sqlite3_close_v2", CallingConvention = CallingConvention.Cdecl)]4577    public static extern Result Close2(IntPtr db);  45784579    [DllImport(LibraryPath, EntryPoint = "sqlite3_win32_set_directory", CallingConvention=CallingConvention.Cdecl, CharS4580    public static extern int SetDirectory (uint directoryType, string directoryPath);4579    [DllImport(LibraryPath, EntryPoint = "sqlite3_initialize", CallingConvention=CallingConvention.Cdecl)]4580    public static extern Result Initialize();  45814582    [DllImport(LibraryPath, EntryPoint = "sqlite3_busy_timeout", CallingConvention=CallingConvention.Cdecl)]4583    public static extern Result BusyTimeout (IntPtr db, int milliseconds);4582    [DllImport(LibraryPath, EntryPoint = "sqlite3_shutdown", CallingConvention=CallingConvention.Cdecl)]4583    public static extern Result Shutdown();  45844585    [DllImport(LibraryPath, EntryPoint = "sqlite3_changes", CallingConvention=CallingConvention.Cdecl)]4586    public static extern int Changes (IntPtr db);4585    [DllImport(LibraryPath, EntryPoint = "sqlite3_config", CallingConvention=CallingConvention.Cdecl)]4586    public static extern Result Config (ConfigOption option);  45874588    [DllImport(LibraryPath, EntryPoint = "sqlite3_prepare_v2", CallingConvention=CallingConvention.Cdecl)]4589    public static extern Result Prepare2 (IntPtr db, [MarshalAs(UnmanagedType.LPStr)] string sql, int numBytes, out IntP4588    [DllImport(LibraryPath, EntryPoint = "sqlite3_win32_set_directory", CallingConvention=CallingConvention.Cdecl, CharS4589    public static extern int SetDirectory (uint directoryType, string directoryPath);  45904591#if NETFX_CORE4592    [DllImport (LibraryPath, EntryPoint = "sqlite3_prepare_v2", CallingConvention = CallingConvention.Cdecl)]4593    public static extern Result Prepare2 (IntPtr db, byte[] queryBytes, int numBytes, out IntPtr stmt, IntPtr pzTail);4594#endif45954596    public static IntPtr Prepare2 (IntPtr db, string query)4597    {4598      IntPtr stmt;4599#if NETFX_CORE4600            byte[] queryBytes = System.Text.UTF8Encoding.UTF8.GetBytes (query);4601            var r = Prepare2 (db, queryBytes, queryBytes.Length, out stmt, IntPtr.Zero);4602#else4603            var r = Prepare2 (db, query, System.Text.UTF8Encoding.UTF8.GetByteCount (query), out stmt, IntPtr.Zero);4604#endif4605      if (r != Result.OK) {4606        throw SQLiteException.New (r, GetErrmsg (db));4607      }4608      return stmt;4609    }46104611    [DllImport(LibraryPath, EntryPoint = "sqlite3_step", CallingConvention=CallingConvention.Cdecl)]4612    public static extern Result Step (IntPtr stmt);46134614    [DllImport(LibraryPath, EntryPoint = "sqlite3_reset", CallingConvention=CallingConvention.Cdecl)]4615    public static extern Result Reset (IntPtr stmt);46164617    [DllImport(LibraryPath, EntryPoint = "sqlite3_finalize", CallingConvention=CallingConvention.Cdecl)]4618    public static extern Result Finalize (IntPtr stmt);4591    [DllImport(LibraryPath, EntryPoint = "sqlite3_busy_timeout", CallingConvention=CallingConvention.Cdecl)]4592    public static extern Result BusyTimeout (IntPtr db, int milliseconds);45934594    [DllImport(LibraryPath, EntryPoint = "sqlite3_changes", CallingConvention=CallingConvention.Cdecl)]4595    public static extern int Changes (IntPtr db);45964597    [DllImport(LibraryPath, EntryPoint = "sqlite3_prepare_v2", CallingConvention=CallingConvention.Cdecl)]4598    public static extern Result Prepare2 (IntPtr db, [MarshalAs(UnmanagedType.LPStr)] string sql, int numBytes, out IntP45994600#if NETFX_CORE4601    [DllImport (LibraryPath, EntryPoint = "sqlite3_prepare_v2", CallingConvention = CallingConvention.Cdecl)]4602    public static extern Result Prepare2 (IntPtr db, byte[] queryBytes, int numBytes, out IntPtr stmt, IntPtr pzTail);4603#endif46044605    public static IntPtr Prepare2 (IntPtr db, string query)4606    {4607      IntPtr stmt;4608#if NETFX_CORE4609            byte[] queryBytes = System.Text.UTF8Encoding.UTF8.GetBytes (query);4610            var r = Prepare2 (db, queryBytes, queryBytes.Length, out stmt, IntPtr.Zero);4611#else4612            var r = Prepare2 (db, query, System.Text.UTF8Encoding.UTF8.GetByteCount (query), out stmt, IntPtr.Zero);4613#endif4614      if (r != Result.OK) {4615        throw SQLiteException.New (r, GetErrmsg (db));4616      }4617      return stmt;4618    }  46194620    [DllImport(LibraryPath, EntryPoint = "sqlite3_last_insert_rowid", CallingConvention=CallingConvention.Cdecl)]4621    public static extern long LastInsertRowid (IntPtr db);4620    [DllImport(LibraryPath, EntryPoint = "sqlite3_step", CallingConvention=CallingConvention.Cdecl)]4621    public static extern Result Step (IntPtr stmt);  46224623    [DllImport(LibraryPath, EntryPoint = "sqlite3_errmsg16", CallingConvention=CallingConvention.Cdecl)]4624    public static extern IntPtr Errmsg (IntPtr db);4623    [DllImport(LibraryPath, EntryPoint = "sqlite3_reset", CallingConvention=CallingConvention.Cdecl)]4624    public static extern Result Reset (IntPtr stmt);  46254626    public static string GetErrmsg (IntPtr db)4627    {4628      return Marshal.PtrToStringUni (Errmsg (db));4629    }46304631    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_parameter_index", CallingConvention=CallingConvention.Cdecl)]4632    public static extern int BindParameterIndex (IntPtr stmt, [MarshalAs(UnmanagedType.LPStr)] string name);46334634    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_null", CallingConvention=CallingConvention.Cdecl)]4635    public static extern int BindNull (IntPtr stmt, int index);46364637    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_int", CallingConvention=CallingConvention.Cdecl)]4638    public static extern int BindInt (IntPtr stmt, int index, int val);4626    [DllImport(LibraryPath, EntryPoint = "sqlite3_finalize", CallingConvention=CallingConvention.Cdecl)]4627    public static extern Result Finalize (IntPtr stmt);46284629    [DllImport(LibraryPath, EntryPoint = "sqlite3_last_insert_rowid", CallingConvention=CallingConvention.Cdecl)]4630    public static extern long LastInsertRowid (IntPtr db);46314632    [DllImport(LibraryPath, EntryPoint = "sqlite3_errmsg16", CallingConvention=CallingConvention.Cdecl)]4633    public static extern IntPtr Errmsg (IntPtr db);46344635    public static string GetErrmsg (IntPtr db)4636    {4637      return Marshal.PtrToStringUni (Errmsg (db));4638    }  46394640    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_int64", CallingConvention=CallingConvention.Cdecl)]4641    public static extern int BindInt64 (IntPtr stmt, int index, long val);4640    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_parameter_index", CallingConvention=CallingConvention.Cdecl)]4641    public static extern int BindParameterIndex (IntPtr stmt, [MarshalAs(UnmanagedType.LPStr)] string name);  46424643    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_double", CallingConvention=CallingConvention.Cdecl)]4644    public static extern int BindDouble (IntPtr stmt, int index, double val);4643    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_null", CallingConvention=CallingConvention.Cdecl)]4644    public static extern int BindNull (IntPtr stmt, int index);  46454646    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_text16", CallingConvention=CallingConvention.Cdecl, CharSet = Cha4647    public static extern int BindText (IntPtr stmt, int index, [MarshalAs(UnmanagedType.LPWStr)] string val, int n, IntP4646    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_int", CallingConvention=CallingConvention.Cdecl)]4647    public static extern int BindInt (IntPtr stmt, int index, int val);  46484649    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_blob", CallingConvention=CallingConvention.Cdecl)]4650    public static extern int BindBlob (IntPtr stmt, int index, byte[] val, int n, IntPtr free);4649    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_int64", CallingConvention=CallingConvention.Cdecl)]4650    public static extern int BindInt64 (IntPtr stmt, int index, long val);  46514652    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_count", CallingConvention=CallingConvention.Cdecl)]4653    public static extern int ColumnCount (IntPtr stmt);4652    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_double", CallingConvention=CallingConvention.Cdecl)]4653    public static extern int BindDouble (IntPtr stmt, int index, double val);  46544655    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_name", CallingConvention=CallingConvention.Cdecl)]4656    public static extern IntPtr ColumnName (IntPtr stmt, int index);4655    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_text16", CallingConvention=CallingConvention.Cdecl, CharSet = Cha4656    public static extern int BindText (IntPtr stmt, int index, [MarshalAs(UnmanagedType.LPWStr)] string val, int n, IntP  46574658    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_name16", CallingConvention=CallingConvention.Cdecl)]4659    static extern IntPtr ColumnName16Internal (IntPtr stmt, int index);4660    public static string ColumnName16(IntPtr stmt, int index)4661    {4662      return Marshal.PtrToStringUni(ColumnName16Internal(stmt, index));4663    }46644665    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_type", CallingConvention=CallingConvention.Cdecl)]4666    public static extern ColType ColumnType (IntPtr stmt, int index);46674668    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_int", CallingConvention=CallingConvention.Cdecl)]4669    public static extern int ColumnInt (IntPtr stmt, int index);46704671    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_int64", CallingConvention=CallingConvention.Cdecl)]4672    public static extern long ColumnInt64 (IntPtr stmt, int index);4658    [DllImport(LibraryPath, EntryPoint = "sqlite3_bind_blob", CallingConvention=CallingConvention.Cdecl)]4659    public static extern int BindBlob (IntPtr stmt, int index, byte[] val, int n, IntPtr free);46604661    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_count", CallingConvention=CallingConvention.Cdecl)]4662    public static extern int ColumnCount (IntPtr stmt);46634664    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_name", CallingConvention=CallingConvention.Cdecl)]4665    public static extern IntPtr ColumnName (IntPtr stmt, int index);46664667    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_name16", CallingConvention=CallingConvention.Cdecl)]4668    static extern IntPtr ColumnName16Internal (IntPtr stmt, int index);4669    public static string ColumnName16(IntPtr stmt, int index)4670    {4671      return Marshal.PtrToStringUni(ColumnName16Internal(stmt, index));4672    }  46734674    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_double", CallingConvention=CallingConvention.Cdecl)]4675    public static extern double ColumnDouble (IntPtr stmt, int index);4674    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_type", CallingConvention=CallingConvention.Cdecl)]4675    public static extern ColType ColumnType (IntPtr stmt, int index);  46764677    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_text", CallingConvention=CallingConvention.Cdecl)]4678    public static extern IntPtr ColumnText (IntPtr stmt, int index);4677    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_int", CallingConvention=CallingConvention.Cdecl)]4678    public static extern int ColumnInt (IntPtr stmt, int index);  46794680    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_text16", CallingConvention=CallingConvention.Cdecl)]4681    public static extern IntPtr ColumnText16 (IntPtr stmt, int index);4680    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_int64", CallingConvention=CallingConvention.Cdecl)]4681    public static extern long ColumnInt64 (IntPtr stmt, int index);  46824683    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_blob", CallingConvention=CallingConvention.Cdecl)]4684    public static extern IntPtr ColumnBlob (IntPtr stmt, int index);4683    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_double", CallingConvention=CallingConvention.Cdecl)]4684    public static extern double ColumnDouble (IntPtr stmt, int index);  46854686    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_bytes", CallingConvention=CallingConvention.Cdecl)]4687    public static extern int ColumnBytes (IntPtr stmt, int index);4686    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_text", CallingConvention=CallingConvention.Cdecl)]4687    public static extern IntPtr ColumnText (IntPtr stmt, int index);  46884689    public static string ColumnString (IntPtr stmt, int index)4690    {4691      return Marshal.PtrToStringUni (SQLite3.ColumnText16 (stmt, index));4692    }46934694    public static byte[] ColumnByteArray (IntPtr stmt, int index)4695    {4696      int length = ColumnBytes (stmt, index);4697      var result = new byte[length];4698      if (length > 0)4699        Marshal.Copy (ColumnBlob (stmt, index), result, 0, length);4700      return result;4689    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_text16", CallingConvention=CallingConvention.Cdecl)]4690    public static extern IntPtr ColumnText16 (IntPtr stmt, int index);46914692    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_blob", CallingConvention=CallingConvention.Cdecl)]4693    public static extern IntPtr ColumnBlob (IntPtr stmt, int index);46944695    [DllImport(LibraryPath, EntryPoint = "sqlite3_column_bytes", CallingConvention=CallingConvention.Cdecl)]4696    public static extern int ColumnBytes (IntPtr stmt, int index);46974698    public static string ColumnString (IntPtr stmt, int index)4699    {4700      return Marshal.PtrToStringUni (SQLite3.ColumnText16 (stmt, index));  4701    }  47024703    [DllImport (LibraryPath, EntryPoint = "sqlite3_errcode", CallingConvention = CallingConvention.Cdecl)]4704    public static extern Result GetResult (Sqlite3DatabaseHandle db);47054706    [DllImport (LibraryPath, EntryPoint = "sqlite3_extended_errcode", CallingConvention = CallingConvention.Cdecl)]4707    public static extern ExtendedResult ExtendedErrCode (IntPtr db);47084709    [DllImport (LibraryPath, EntryPoint = "sqlite3_libversion_number", CallingConvention = CallingConvention.Cdecl)]4710    public static extern int LibVersionNumber ();4703    public static byte[] ColumnByteArray (IntPtr stmt, int index)4704    {4705      int length = ColumnBytes (stmt, index);4706      var result = new byte[length];4707      if (length > 0)4708        Marshal.Copy (ColumnBlob (stmt, index), result, 0, length);4709      return result;4710    }  47114712    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_init", CallingConvention = CallingConvention.Cdecl)]4713    public static extern Sqlite3BackupHandle BackupInit (Sqlite3DatabaseHandle destDb, [MarshalAs (UnmanagedType.LPStr)]4712    [DllImport (LibraryPath, EntryPoint = "sqlite3_errcode", CallingConvention = CallingConvention.Cdecl)]4713    public static extern Result GetResult (Sqlite3DatabaseHandle db);  47144715    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_step", CallingConvention = CallingConvention.Cdecl)]4716    public static extern Result BackupStep (Sqlite3BackupHandle backup, int numPages);4715    [DllImport (LibraryPath, EntryPoint = "sqlite3_extended_errcode", CallingConvention = CallingConvention.Cdecl)]4716    public static extern ExtendedResult ExtendedErrCode (IntPtr db);  47174718    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_finish", CallingConvention = CallingConvention.Cdecl)]4719    public static extern Result BackupFinish (Sqlite3BackupHandle backup);4720#else4721    public static Result Open (string filename, out Sqlite3DatabaseHandle db)4722    {4723      return (Result)Sqlite3.sqlite3_open (filename, out db);4724    }47254726    public static Result Open (string filename, out Sqlite3DatabaseHandle db, int flags, string vfsName)4727    {4728#if USE_WP8_NATIVE_SQLITE4729      return (Result)Sqlite3.sqlite3_open_v2(filename, out db, flags, vfsName ?? "");4730#else4731      return (Result)Sqlite3.sqlite3_open_v2 (filename, out db, flags, vfsName);4732#endif4718    [DllImport (LibraryPath, EntryPoint = "sqlite3_libversion_number", CallingConvention = CallingConvention.Cdecl)]4719    public static extern int LibVersionNumber ();47204721    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_init", CallingConvention = CallingConvention.Cdecl)]4722    public static extern Sqlite3BackupHandle BackupInit (Sqlite3DatabaseHandle destDb, [MarshalAs (UnmanagedType.LPStr)]47234724    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_step", CallingConvention = CallingConvention.Cdecl)]4725    public static extern Result BackupStep (Sqlite3BackupHandle backup, int numPages);47264727    [DllImport (LibraryPath, EntryPoint = "sqlite3_backup_finish", CallingConvention = CallingConvention.Cdecl)]4728    public static extern Result BackupFinish (Sqlite3BackupHandle backup);4729#else4730    public static Result Open (string filename, out Sqlite3DatabaseHandle db)4731    {4732      return (Result)Sqlite3.sqlite3_open (filename, out db);  4733    }  47344735    public static Result Close (Sqlite3DatabaseHandle db)4735    public static Result Open (string filename, out Sqlite3DatabaseHandle db, int flags, string vfsName)  4736    {4737      return (Result)Sqlite3.sqlite3_close (db);4738    }47394740    public static Result Close2 (Sqlite3DatabaseHandle db)4741    {4742      return (Result)Sqlite3.sqlite3_close_v2 (db);4743    }47444745    public static Result BusyTimeout (Sqlite3DatabaseHandle db, int milliseconds)4746    {4747      return (Result)Sqlite3.sqlite3_busy_timeout (db, milliseconds);4748    }47494750    public static int Changes (Sqlite3DatabaseHandle db)4751    {4752      return Sqlite3.sqlite3_changes (db);4753    }47544755    public static Sqlite3Statement Prepare2 (Sqlite3DatabaseHandle db, string query)4756    {4757      Sqlite3Statement stmt = default (Sqlite3Statement);4758#if USE_WP8_NATIVE_SQLITE || USE_SQLITEPCL_RAW4759      var r = Sqlite3.sqlite3_prepare_v2 (db, query, out stmt);4760#else4761      stmt = new Sqlite3Statement();4762      var r = Sqlite3.sqlite3_prepare_v2(db, query, -1, ref stmt, 0);4763#endif4764      if (r != 0) {4765        throw SQLiteException.New ((Result)r, GetErrmsg (db));4766      }4767      return stmt;4768    }47694770    public static Result Step (Sqlite3Statement stmt)4771    {4772      return (Result)Sqlite3.sqlite3_step (stmt);4773    }47744775    public static Result Reset (Sqlite3Statement stmt)4776    {4777      return (Result)Sqlite3.sqlite3_reset (stmt);4778    }47794780    public static Result Finalize (Sqlite3Statement stmt)4781    {4782      return (Result)Sqlite3.sqlite3_finalize (stmt);4783    }47844785    public static long LastInsertRowid (Sqlite3DatabaseHandle db)4786    {4787      return Sqlite3.sqlite3_last_insert_rowid (db);4788    }47894790    public static string GetErrmsg (Sqlite3DatabaseHandle db)4791    {4792      return Sqlite3.sqlite3_errmsg (db).utf8_to_string ();4793    }47944795    public static int BindParameterIndex (Sqlite3Statement stmt, string name)4796    {4797      return Sqlite3.sqlite3_bind_parameter_index (stmt, name);4798    }47994800    public static int BindNull (Sqlite3Statement stmt, int index)4801    {4802      return Sqlite3.sqlite3_bind_null (stmt, index);4803    }48044805    public static int BindInt (Sqlite3Statement stmt, int index, int val)4806    {4807      return Sqlite3.sqlite3_bind_int (stmt, index, val);4808    }48094810    public static int BindInt64 (Sqlite3Statement stmt, int index, long val)4811    {4812      return Sqlite3.sqlite3_bind_int64 (stmt, index, val);4813    }48144815    public static int BindDouble (Sqlite3Statement stmt, int index, double val)4816    {4817      return Sqlite3.sqlite3_bind_double (stmt, index, val);4818    }48194820    public static int BindText (Sqlite3Statement stmt, int index, string val, int n, IntPtr free)4821    {4822#if USE_WP8_NATIVE_SQLITE4823      return Sqlite3.sqlite3_bind_text(stmt, index, val, n);4824#elif USE_SQLITEPCL_RAW4825      return Sqlite3.sqlite3_bind_text (stmt, index, val);4826#else4827      return Sqlite3.sqlite3_bind_text(stmt, index, val, n, null);4828#endif4829    }48304831    public static int BindBlob (Sqlite3Statement stmt, int index, byte[] val, int n, IntPtr free)4832    {4833#if USE_WP8_NATIVE_SQLITE4834      return Sqlite3.sqlite3_bind_blob(stmt, index, val, n);4835#elif USE_SQLITEPCL_RAW4836      return Sqlite3.sqlite3_bind_blob (stmt, index, val);4837#else4838      return Sqlite3.sqlite3_bind_blob(stmt, index, val, n, null);4839#endif4840    }48414842    public static int ColumnCount (Sqlite3Statement stmt)4843    {4844      return Sqlite3.sqlite3_column_count (stmt);4845    }48464847    public static string ColumnName (Sqlite3Statement stmt, int index)4848    {4849      return Sqlite3.sqlite3_column_name (stmt, index).utf8_to_string ();4850    }48514852    public static string ColumnName16 (Sqlite3Statement stmt, int index)4853    {4854      return Sqlite3.sqlite3_column_name (stmt, index).utf8_to_string ();4855    }48564857    public static ColType ColumnType (Sqlite3Statement stmt, int index)4858    {4859      return (ColType)Sqlite3.sqlite3_column_type (stmt, index);4860    }48614862    public static int ColumnInt (Sqlite3Statement stmt, int index)4863    {4864      return Sqlite3.sqlite3_column_int (stmt, index);4865    }48664867    public static long ColumnInt64 (Sqlite3Statement stmt, int index)4868    {4869      return Sqlite3.sqlite3_column_int64 (stmt, index);4870    }48714872    public static double ColumnDouble (Sqlite3Statement stmt, int index)4873    {4874      return Sqlite3.sqlite3_column_double (stmt, index);4875    }48764877    public static string ColumnText (Sqlite3Statement stmt, int index)4878    {4879      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();4880    }48814882    public static string ColumnText16 (Sqlite3Statement stmt, int index)4883    {4884      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();4885    }48864887    public static byte[] ColumnBlob (Sqlite3Statement stmt, int index)4888    {4889      return Sqlite3.sqlite3_column_blob (stmt, index).ToArray ();4890    }48914892    public static int ColumnBytes (Sqlite3Statement stmt, int index)4893    {4894      return Sqlite3.sqlite3_column_bytes (stmt, index);4895    }48964897    public static string ColumnString (Sqlite3Statement stmt, int index)4898    {4899      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();4900    }49014902    public static byte[] ColumnByteArray (Sqlite3Statement stmt, int index)4903    {4904      int length = ColumnBytes (stmt, index);4905      if (length > 0) {4906        return ColumnBlob (stmt, index);4907      }4908      return new byte[0];4737#if USE_WP8_NATIVE_SQLITE4738      return (Result)Sqlite3.sqlite3_open_v2(filename, out db, flags, vfsName ?? "");4739#else4740      return (Result)Sqlite3.sqlite3_open_v2 (filename, out db, flags, vfsName);4741#endif4742    }47434744    public static Result Close (Sqlite3DatabaseHandle db)4745    {4746      return (Result)Sqlite3.sqlite3_close (db);4747    }47484749    public static Result Close2 (Sqlite3DatabaseHandle db)4750    {4751      return (Result)Sqlite3.sqlite3_close_v2 (db);4752    }47534754    public static Result BusyTimeout (Sqlite3DatabaseHandle db, int milliseconds)4755    {4756      return (Result)Sqlite3.sqlite3_busy_timeout (db, milliseconds);4757    }47584759    public static int Changes (Sqlite3DatabaseHandle db)4760    {4761      return Sqlite3.sqlite3_changes (db);4762    }47634764    public static Sqlite3Statement Prepare2 (Sqlite3DatabaseHandle db, string query)4765    {4766      Sqlite3Statement stmt = default (Sqlite3Statement);4767#if USE_WP8_NATIVE_SQLITE || USE_SQLITEPCL_RAW4768      var r = Sqlite3.sqlite3_prepare_v2 (db, query, out stmt);4769#else4770      stmt = new Sqlite3Statement();4771      var r = Sqlite3.sqlite3_prepare_v2(db, query, -1, ref stmt, 0);4772#endif4773      if (r != 0) {4774        throw SQLiteException.New ((Result)r, GetErrmsg (db));4775      }4776      return stmt;4777    }47784779    public static Result Step (Sqlite3Statement stmt)4780    {4781      return (Result)Sqlite3.sqlite3_step (stmt);4782    }47834784    public static Result Reset (Sqlite3Statement stmt)4785    {4786      return (Result)Sqlite3.sqlite3_reset (stmt);4787    }47884789    public static Result Finalize (Sqlite3Statement stmt)4790    {4791      return (Result)Sqlite3.sqlite3_finalize (stmt);4792    }47934794    public static long LastInsertRowid (Sqlite3DatabaseHandle db)4795    {4796      return Sqlite3.sqlite3_last_insert_rowid (db);4797    }47984799    public static string GetErrmsg (Sqlite3DatabaseHandle db)4800    {4801      return Sqlite3.sqlite3_errmsg (db).utf8_to_string ();4802    }48034804    public static int BindParameterIndex (Sqlite3Statement stmt, string name)4805    {4806      return Sqlite3.sqlite3_bind_parameter_index (stmt, name);4807    }48084809    public static int BindNull (Sqlite3Statement stmt, int index)4810    {4811      return Sqlite3.sqlite3_bind_null (stmt, index);4812    }48134814    public static int BindInt (Sqlite3Statement stmt, int index, int val)4815    {4816      return Sqlite3.sqlite3_bind_int (stmt, index, val);4817    }48184819    public static int BindInt64 (Sqlite3Statement stmt, int index, long val)4820    {4821      return Sqlite3.sqlite3_bind_int64 (stmt, index, val);4822    }48234824    public static int BindDouble (Sqlite3Statement stmt, int index, double val)4825    {4826      return Sqlite3.sqlite3_bind_double (stmt, index, val);4827    }48284829    public static int BindText (Sqlite3Statement stmt, int index, string val, int n, IntPtr free)4830    {4831#if USE_WP8_NATIVE_SQLITE4832      return Sqlite3.sqlite3_bind_text(stmt, index, val, n);4833#elif USE_SQLITEPCL_RAW4834      return Sqlite3.sqlite3_bind_text (stmt, index, val);4835#else4836      return Sqlite3.sqlite3_bind_text(stmt, index, val, n, null);4837#endif4838    }48394840    public static int BindBlob (Sqlite3Statement stmt, int index, byte[] val, int n, IntPtr free)4841    {4842#if USE_WP8_NATIVE_SQLITE4843      return Sqlite3.sqlite3_bind_blob(stmt, index, val, n);4844#elif USE_SQLITEPCL_RAW4845      return Sqlite3.sqlite3_bind_blob (stmt, index, val);4846#else4847      return Sqlite3.sqlite3_bind_blob(stmt, index, val, n, null);4848#endif4849    }48504851    public static int ColumnCount (Sqlite3Statement stmt)4852    {4853      return Sqlite3.sqlite3_column_count (stmt);4854    }48554856    public static string ColumnName (Sqlite3Statement stmt, int index)4857    {4858      return Sqlite3.sqlite3_column_name (stmt, index).utf8_to_string ();4859    }48604861    public static string ColumnName16 (Sqlite3Statement stmt, int index)4862    {4863      return Sqlite3.sqlite3_column_name (stmt, index).utf8_to_string ();4864    }48654866    public static ColType ColumnType (Sqlite3Statement stmt, int index)4867    {4868      return (ColType)Sqlite3.sqlite3_column_type (stmt, index);4869    }48704871    public static int ColumnInt (Sqlite3Statement stmt, int index)4872    {4873      return Sqlite3.sqlite3_column_int (stmt, index);4874    }48754876    public static long ColumnInt64 (Sqlite3Statement stmt, int index)4877    {4878      return Sqlite3.sqlite3_column_int64 (stmt, index);4879    }48804881    public static double ColumnDouble (Sqlite3Statement stmt, int index)4882    {4883      return Sqlite3.sqlite3_column_double (stmt, index);4884    }48854886    public static string ColumnText (Sqlite3Statement stmt, int index)4887    {4888      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();4889    }48904891    public static string ColumnText16 (Sqlite3Statement stmt, int index)4892    {4893      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();4894    }48954896    public static byte[] ColumnBlob (Sqlite3Statement stmt, int index)4897    {4898      return Sqlite3.sqlite3_column_blob (stmt, index).ToArray ();4899    }49004901    public static int ColumnBytes (Sqlite3Statement stmt, int index)4902    {4903      return Sqlite3.sqlite3_column_bytes (stmt, index);4904    }49054906    public static string ColumnString (Sqlite3Statement stmt, int index)4907    {4908      return Sqlite3.sqlite3_column_text (stmt, index).utf8_to_string ();  4909    }  49104911    public static Result EnableLoadExtension (Sqlite3DatabaseHandle db, int onoff)4911    public static byte[] ColumnByteArray (Sqlite3Statement stmt, int index)  4912    {4913      return (Result)Sqlite3.sqlite3_enable_load_extension (db, onoff);4914    }49154916    public static int LibVersionNumber ()4917    {4918      return Sqlite3.sqlite3_libversion_number ();4919    }49204921    public static Result GetResult (Sqlite3DatabaseHandle db)4922    {4923      return (Result)Sqlite3.sqlite3_errcode (db);4924    }49254926    public static ExtendedResult ExtendedErrCode (Sqlite3DatabaseHandle db)4927    {4928      return (ExtendedResult)Sqlite3.sqlite3_extended_errcode (db);4929    }49304931    public static Sqlite3BackupHandle BackupInit (Sqlite3DatabaseHandle destDb, string destName, Sqlite3DatabaseHandle s4932    {4933      return Sqlite3.sqlite3_backup_init (destDb, destName, sourceDb, sourceName);4934    }49354936    public static Result BackupStep (Sqlite3BackupHandle backup, int numPages)4937    {4938      return (Result)Sqlite3.sqlite3_backup_step (backup, numPages);4939    }49404941    public static Result BackupFinish (Sqlite3BackupHandle backup)4942    {4943      return (Result)Sqlite3.sqlite3_backup_finish (backup);4944    }4945#endif49464947    public enum ColType : int4948    {4949      Integer = 1,4950      Float = 2,4951      Text = 3,4952      Blob = 4,4953      Null = 54954    }4955  }4956}4913      int length = ColumnBytes (stmt, index);4914      if (length > 0) {4915        return ColumnBlob (stmt, index);4916      }4917      return new byte[0];4918    }49194920    public static Result EnableLoadExtension (Sqlite3DatabaseHandle db, int onoff)4921    {4922      return (Result)Sqlite3.sqlite3_enable_load_extension (db, onoff);4923    }49244925    public static int LibVersionNumber ()4926    {4927      return Sqlite3.sqlite3_libversion_number ();4928    }49294930    public static Result GetResult (Sqlite3DatabaseHandle db)4931    {4932      return (Result)Sqlite3.sqlite3_errcode (db);4933    }49344935    public static ExtendedResult ExtendedErrCode (Sqlite3DatabaseHandle db)4936    {4937      return (ExtendedResult)Sqlite3.sqlite3_extended_errcode (db);4938    }49394940    public static Sqlite3BackupHandle BackupInit (Sqlite3DatabaseHandle destDb, string destName, Sqlite3DatabaseHandle s4941    {4942      return Sqlite3.sqlite3_backup_init (destDb, destName, sourceDb, sourceName);4943    }49444945    public static Result BackupStep (Sqlite3BackupHandle backup, int numPages)4946    {4947      return (Result)Sqlite3.sqlite3_backup_step (backup, numPages);4948    }49494950    public static Result BackupFinish (Sqlite3BackupHandle backup)4951    {4952      return (Result)Sqlite3.sqlite3_backup_finish (backup);4953    }4954#endif49554956    public enum ColType : int4957    {4958      Integer = 1,4959      Float = 2,4960      Text = 3,4961      Blob = 4,4962      Null = 54963    }4964  }4965} - +

Methods/Properties

-.ctor()
+.ctor()