/// <summary>
        /// Constructs a search key that may then be used by <see cref="JetSeek"/>
        /// and <see cref="JetSetIndexRange"/>.
        /// </summary>
        /// <param name="sesid">The session to use.</param>
        /// <param name="tableid">The cursor to create the key on.</param>
        /// <param name="data">Column data for the current key column of the current index.</param>
        /// <param name="encoding">The encoding used to convert the string.</param>
        /// <param name="grbit">Key options.</param>
        public static void MakeKey(JET_SESID sesid, JET_TABLEID tableid, string data, Encoding encoding, MakeKeyGrbit grbit)
        {
            CheckEncodingIsValid(encoding);

            if (null == data)
            {
                Api.JetMakeKey(sesid, tableid, null, 0, grbit);
            }
            else if (0 == data.Length)
            {
                Api.JetMakeKey(sesid, tableid, null, 0, grbit | MakeKeyGrbit.KeyDataZeroLength);
            }
            else if (Encoding.Unicode == encoding)
            {
                // Optimization for Unicode strings
                unsafe
                {
                    fixed (char* buffer = data)
                    {
                        Api.JetMakeKey(sesid, tableid, (IntPtr) buffer, data.Length * sizeof(char), grbit);
                    }
                }
            }
            else
            {
                byte[] bytes = encoding.GetBytes(data);
                Api.JetMakeKey(sesid, tableid, bytes, bytes.Length, grbit);
            }
        }
Example #2
0
        private static void CreateDocumentsTable(Session session, JET_TABLEID tableid)
        {
            JET_COLUMNID columnid;

            var guidColumn = new JET_COLUMNDEF
                                 {
                                     cbMax = 255,
                                     coltyp = JET_coltyp.Text,
                                     cp = JET_CP.Unicode,
                                     grbit = ColumndefGrbit.ColumnTagged
                                 };
            Api.JetAddColumn(session, tableid, "id", guidColumn, null, 0, out columnid);

            var collectionColumn = new JET_COLUMNDEF
                                       {
                                           cbMax = 1000,
                                           coltyp = JET_coltyp.Text,
                                           cp = JET_CP.Unicode,
                                           grbit = ColumndefGrbit.ColumnTagged
                                       };
            Api.JetAddColumn(session, tableid, "collection_name", collectionColumn, null, 0, out columnid);

            const string colectionIndexDef = "+collection_name\0\0";
            Api.JetCreateIndex(session, tableid, "by_collection_name", CreateIndexGrbit.None, colectionIndexDef, colectionIndexDef.Length, 100);

            var textColumn = new JET_COLUMNDEF
                                 {
                                     coltyp = JET_coltyp.LongText,
                                     grbit = ColumndefGrbit.ColumnTagged
                                 };
            Api.JetAddColumn(session, tableid, "data", textColumn, null, 0, out columnid);

            const string idIndexDef = "+id\0\0";
            Api.JetCreateIndex(session, tableid, "by_id", CreateIndexGrbit.IndexPrimary, idIndexDef, idIndexDef.Length, 100);
        }
Example #3
0
        /// <summary>
        /// The JetSetColumn function modifies a single column value in a modified record to be inserted or to
        /// update the current record. It can overwrite an existing value, add a new value to a sequence of
        /// values in a multi-valued column, remove a value from a sequence of values in a multi-valued column,
        /// or update all or part of a long value (a column of type <see cref="JET_coltyp.LongText"/>
        /// or <see cref="JET_coltyp.LongBinary"/>). 
        /// </summary>
        /// <remarks>
        /// This is an internal-only version of the API that takes a data buffer and an offset into the buffer.
        /// </remarks>
        /// <param name="sesid">The session which is performing the update.</param>
        /// <param name="tableid">The cursor to update. An update should be prepared.</param>
        /// <param name="columnid">The columnid to set.</param>
        /// <param name="data">The data to set.</param>
        /// <param name="dataSize">The size of data to set.</param>
        /// <param name="dataOffset">The offset in the data buffer to set data from.</param>
        /// <param name="grbit">SetColumn options.</param>
        /// <param name="setinfo">Used to specify itag or long-value offset.</param>
        /// <returns>A warning value.</returns>
        public static JET_wrn JetSetColumn(JET_SESID sesid, JET_TABLEID tableid, JET_COLUMNID columnid, byte[] data, int dataSize, int dataOffset, SetColumnGrbit grbit, JET_SETINFO setinfo)
        {
            if (dataOffset < 0
                || (null != data && 0 != dataSize && dataOffset >= data.Length)
                || (null == data && dataOffset != 0))
            {
                throw new ArgumentOutOfRangeException(
                    "dataOffset",
                    dataOffset,
                    "must be inside the data buffer");                    
            }

            if (null != data && dataSize > checked(data.Length - dataOffset) && (SetColumnGrbit.SizeLV != (grbit & SetColumnGrbit.SizeLV)))
            {
                throw new ArgumentOutOfRangeException(
                    "dataSize",
                    dataSize,
                    "cannot be greater than the length of the data (unless the SizeLV option is used)");
            }

            unsafe
            {
                fixed (byte* pointer = data)
                {
                    return Api.JetSetColumn(sesid, tableid, columnid, new IntPtr(pointer + dataOffset), dataSize, grbit, setinfo);
                }
            }
        }
Example #4
0
 /// <summary>
 /// Initializes a new instance of the <see cref="ColumnAccessor" /> class.
 /// </summary>
 /// <param name="cursor">The cursor.</param>
 /// <param name="isamSession">The session.</param>
 /// <param name="tableid">The tableid.</param>
 /// <param name="grbit">The grbit.</param>
 internal ColumnAccessor(Cursor cursor, IsamSession isamSession, JET_TABLEID tableid, RetrieveColumnGrbit grbit)
 {
     this.cursor = cursor;
     this.isamSession = isamSession;
     this.tableid = tableid;
     this.grbit = grbit;
 }
Example #5
0
        /// <summary>
        /// Retrieves a single column value from the current record. The record is that
        /// record associated with the index entry at the current position of the cursor.
        /// Alternatively, this function can retrieve a column from a record being created
        /// in the cursor copy buffer. This function can also retrieve column data from an
        /// index entry that references the current record. In addition to retrieving the
        /// actual column value, JetRetrieveColumn can also be used to retrieve the size
        /// of a column, before retrieving the column data itself so that application
        /// buffers can be sized appropriately.  
        /// </summary>
        /// <remarks>
        /// This is an internal method that takes a buffer offset as well as size.
        /// </remarks>
        /// <param name="sesid">The session to use.</param>
        /// <param name="tableid">The cursor to retrieve the column from.</param>
        /// <param name="columnid">The columnid to retrieve.</param>
        /// <param name="data">The data buffer to be retrieved into.</param>
        /// <param name="dataSize">The size of the data buffer.</param>
        /// <param name="dataOffset">Offset into the data buffer to read data into.</param>
        /// <param name="actualDataSize">Returns the actual size of the data buffer.</param>
        /// <param name="grbit">Retrieve column options.</param>
        /// <param name="retinfo">
        /// If pretinfo is give as NULL then the function behaves as though an itagSequence
        /// of 1 and an ibLongValue of 0 (zero) were given. This causes column retrieval to
        /// retrieve the first value of a multi-valued column, and to retrieve long data at
        /// offset 0 (zero).
        /// </param>
        /// <returns>An ESENT warning code.</returns>
        public static JET_wrn JetRetrieveColumn(JET_SESID sesid, JET_TABLEID tableid, JET_COLUMNID columnid, byte[] data, int dataSize, int dataOffset, out int actualDataSize, RetrieveColumnGrbit grbit, JET_RETINFO retinfo)
        {
            if (dataOffset < 0
                || (null != data && 0 != dataSize && dataOffset >= data.Length)
                || (null == data && dataOffset != 0))
            {
                throw new ArgumentOutOfRangeException(
                    "dataOffset",
                    dataOffset,
                    "must be inside the data buffer");
            }

            if ((null == data && dataSize > 0) || (null != data && dataSize > data.Length))
            {
                throw new ArgumentOutOfRangeException(
                    "dataSize",
                    dataSize,
                    "cannot be greater than the length of the data");
            }

            unsafe
            {
                fixed (byte* pointer = data)
                {
                    return Api.JetRetrieveColumn(
                        sesid, tableid, columnid, new IntPtr(pointer + dataOffset), dataSize, out actualDataSize, grbit, retinfo);
                }
            }
        }
Example #6
0
        public void ConvertObjectlistFromNative()
        {
            var tableid = new JET_TABLEID { Value = (IntPtr)0x1000 };
            var col1 = new JET_COLUMNID { Value = 1 };
            var col2 = new JET_COLUMNID { Value = 2 };
            var col3 = new JET_COLUMNID { Value = 3 };
            var col4 = new JET_COLUMNID { Value = 4 };
            var col5 = new JET_COLUMNID { Value = 5 };
            var col6 = new JET_COLUMNID { Value = 6 };

            var native = new NATIVE_OBJECTLIST()
            {
                tableid = tableid.Value,
                cRecord = 100,
                columnidobjectname = col1.Value,
                columnidobjtyp = col2.Value,
                columnidgrbit = col3.Value,
                columnidflags = col4.Value,
                columnidcRecord = col5.Value,
                columnidcPage = col6.Value,
            };

            var objectlist = new JET_OBJECTLIST();
            objectlist.SetFromNativeObjectlist(native);

            Assert.AreEqual(tableid, objectlist.tableid);
            Assert.AreEqual(100, objectlist.cRecord);
            Assert.AreEqual(col1, objectlist.columnidobjectname);
            Assert.AreEqual(col2, objectlist.columnidobjtyp);
            Assert.AreEqual(col3, objectlist.columnidgrbit);
            Assert.AreEqual(col4, objectlist.columnidflags);
            Assert.AreEqual(col5, objectlist.columnidcRecord);
            Assert.AreEqual(col6, objectlist.columnidcPage);
        }
Example #7
0
        public bool Add(JET_SESID session, JET_TABLEID table, int level)
        {
            byte[] buffer;
            int actualBookmarkSize;

            var largeBuffer = IndexReaderBuffers.Buffers.TakeBuffer(bookmarkMost);
            try
            {
                Api.JetGetBookmark(session, table, largeBuffer,
                                   largeBuffer.Length, out actualBookmarkSize);

                buffer = new byte[actualBookmarkSize];
                Buffer.BlockCopy(largeBuffer, 0, buffer, 0, actualBookmarkSize);
            }
            finally
            {
                IndexReaderBuffers.Buffers.ReturnBuffer(largeBuffer);
            }
            var res = itemsToDelete.TryAdd(new Key(buffer, actualBookmarkSize));
            if (res)
            {
                itemsToDeletePerViewAndLevel.DecrementPerLevelCounters(level);
            }
            return res;
        }
        protected override void DoCreateTable(Session session, JET_TABLEID tableid)
        {
            JET_COLUMNID columnid;

            Api.JetAddColumn(session, tableid, "FileId", new JET_COLUMNDEF()
            {
                coltyp = JET_coltyp.Text,
                cp = JET_CP.Unicode,
                cbMax = 255,
                grbit = ColumndefGrbit.ColumnNotNULL
            }, null, 0, out columnid);

            Api.JetAddColumn(session, tableid, "Size", new JET_COLUMNDEF()
            {
                coltyp = Windows10Coltyp.UnsignedLongLong,
                grbit = ColumndefGrbit.ColumnNotNULL
            }, null, 0, out columnid);

            Api.JetAddColumn(session, tableid, "DTicks", new JET_COLUMNDEF()
            {
                coltyp = VistaColtyp.LongLong,
                grbit = ColumndefGrbit.ColumnNotNULL
            }, null, 0, out columnid);

            Api.JetAddColumn(session, tableid, "OTicks", new JET_COLUMNDEF()
            {
                coltyp = VistaColtyp.LongLong,
                grbit = ColumndefGrbit.ColumnNotNULL
            }, null, 0, out columnid);

            var indexDef = "+FileId\0\0";
            Api.JetCreateIndex(session, tableid, PrimaryIndexName, CreateIndexGrbit.IndexPrimary, indexDef, indexDef.Length, 100);
        }
Example #9
0
        public void Setup()
        {
            JET_TABLEID tableidTemp = new JET_TABLEID()
            {
                Value = (IntPtr)456,
            };
            this.managed = new JET_TABLECREATE()
            {
                szTableName = "table7",
                szTemplateTableName = "parentTable",
                ulPages = 7,
                ulDensity = 62,
                rgcolumncreate = null,
                cColumns = 0,
                rgindexcreate = null,
                cIndexes = 0,
                szCallback = "module!FunkyFunction",
                cbtyp = JET_cbtyp.AfterReplace,
                grbit = CreateTableColumnIndexGrbit.FixedDDL,
                pSeqSpacehints = null,
                pLVSpacehints = null,
                cbSeparateLV = 0x999,
                tableid = tableidTemp,
                cCreated = 2,
            };

            this.native = this.managed.GetNativeTableCreate2();
        }
        /// <summary>
        /// Constructs a search key that may then be used by <see cref="JetSeek"/>
        /// and <see cref="JetSetIndexRange"/>.
        /// </summary>
        /// <param name="sesid">The session to use.</param>
        /// <param name="tableid">The cursor to create the key on.</param>
        /// <param name="data">Column data for the current key column of the current index.</param>
        /// <param name="encoding">The encoding used to convert the string.</param>
        /// <param name="grbit">Key options.</param>
        public static void MakeKey(JET_SESID sesid, JET_TABLEID tableid, string data, Encoding encoding, MakeKeyGrbit grbit)
        {
            CheckEncodingIsValid(encoding);

            if (null == data)
            {
                Api.JetMakeKey(sesid, tableid, null, 0, grbit);
            }
            else if (0 == data.Length)
            {
                Api.JetMakeKey(sesid, tableid, null, 0, grbit | MakeKeyGrbit.KeyDataZeroLength);
            }
            else if (Encoding.Unicode == encoding)
            {
                // Optimization for Unicode strings
                unsafe
                {
                    fixed (char* buffer = data)
                    {
                        Api.JetMakeKey(sesid, tableid, new IntPtr(buffer), checked(data.Length * sizeof(char)), grbit);
                    }
                }
            }
            else
            {
            #if MANAGEDESENT_ON_WSA
                // Encoding.GetBytes(char*, int, byte*, int) overload is missing in new Windows UI.
                // So we can't use the ColumnCache. We'll just use a different GetBytes() overload.
                byte[] buffer = encoding.GetBytes(data);
                Api.JetMakeKey(sesid, tableid, buffer, buffer.Length, grbit);
            #else
                // Convert the string using a cached column buffer. The column buffer is far larger
                // than the maximum key size, so any data truncation here won't matter.
                byte[] buffer = null;
                try
                {
                    buffer = Caches.ColumnCache.Allocate();
                    int dataSize;
                    unsafe
                    {
                        fixed (char* chars = data)
                        fixed (byte* bytes = buffer)
                        {
                            dataSize = encoding.GetBytes(chars, data.Length, bytes, buffer.Length);
                        }
                    }

                    JetMakeKey(sesid, tableid, buffer, dataSize, grbit);
                }
                finally
                {
                    if (buffer != null)
                    {
                        Caches.ColumnCache.Free(ref buffer);
                    }
                }
            #endif
            }
        }
Example #11
0
 /// <summary>
 /// Creates indexes over data in an ESE database.
 /// </summary>
 /// <remarks>
 /// When creating multiple indexes (i.e. with numIndexCreates
 /// greater than 1) this method MUST be called
 /// outside of any transactions and with exclusive access to the
 /// table. The JET_TABLEID returned by "Api.JetCreateTable"
 /// will have exlusive access or the table can be opened for
 /// exclusive access by passing <see cref="OpenTableGrbit.DenyRead"/>
 /// to <see cref="Api.JetOpenTable"/>.
 /// </remarks>
 /// <param name="sesid">The session to use.</param>
 /// <param name="tableid">The table to create the index on.</param>
 /// <param name="indexcreates">Array of objects describing the indexes to be created.</param>
 /// <param name="numIndexCreates">Number of index description objects.</param>
 public static void JetCreateIndex4(
     JET_SESID sesid,
     JET_TABLEID tableid,
     JET_INDEXCREATE[] indexcreates,
     int numIndexCreates)
 {
     Api.Check(Api.Impl.JetCreateIndex4(sesid, tableid, indexcreates, numIndexCreates));
 }
Example #12
0
 /// <summary>
 /// Retrieves information about a table column.
 /// </summary>
 /// <param name="sesid">The session to use.</param>
 /// <param name="tableid">The table containing the column.</param>
 /// <param name="columnid">The columnid of the column.</param>
 /// <param name="columnbase">Filled in with information about the column.</param>
 public static void JetGetTableColumnInfo(
     JET_SESID sesid,
     JET_TABLEID tableid,
     JET_COLUMNID columnid,
     out JET_COLUMNBASE columnbase)
 {
     Api.Check(Api.Impl.JetGetTableColumnInfo(sesid, tableid, columnid, out columnbase));
 }
Example #13
0
 public static void JetGetTableIndexInfo(
     JET_SESID sesid,
     JET_TABLEID tableid,
     string indexname,
     out JET_INDEXLIST indexlist)
 {
     Api.JetGetTableIndexInfo(sesid, tableid, indexname, out indexlist, JET_IdxInfo.List);
 }
Example #14
0
 /// <summary>
 /// Initializes a new instance of the ColumnStream class.
 /// </summary>
 /// <param name="sesid">The session to use.</param>
 /// <param name="tableid">The cursor to use.</param>
 /// <param name="columnid">The columnid of the column to set/retrieve data from.</param>
 public ColumnStream(JET_SESID sesid, JET_TABLEID tableid, JET_COLUMNID columnid)
 {
     this.sesid = sesid;
     this.tableid = tableid;
     this.columnid = columnid;
     this.ibLongValue = 0;
     this.Itag = 1;
 }
Example #15
0
 public EsentDb(string dbname)
 {
     this.dbname = dbname;
       instance = OpenInstance(dbname);
       session = CreateSession(instance);
       dbid = CreateDatabase(dbname, instance, session);
       table = CreateTable(session, dbid, "store", new Tuple<string, JET_coltyp>[] { Tuple.Create("key", JET_coltyp.Long), Tuple.Create("data", JET_coltyp.LongText) });
 }
Example #16
0
		void ISchemaPart.ApplyToTable(Session session, JET_TABLEID table)
		{
			if (Api.GetTableColumns(session, table).All(ci => ci.Name != Name))
			{
				var factory = EsentHelper.GetColumnFactory(Member);
				JET_COLUMNID columnid;
				Api.JetAddColumn(session, table, Name, factory(), null, 0, out columnid);
			}
		}
Example #17
0
 /// <summary>
 /// Initializes a new instance of the <see cref="TempTableHandle"/> class.
 /// </summary>
 /// <param name="name">The name.</param>
 /// <param name="sesid">The sesid.</param>
 /// <param name="tableid">The tableid.</param>
 /// <param name="inInsertMode">if set to <c>true</c> [in insert mode].</param>
 internal TempTableHandle(string name, JET_SESID sesid, JET_TABLEID tableid, bool inInsertMode)
 {
     this.guid = Guid.NewGuid();
     this.name = name;
     this.sesid = sesid;
     this.tableid = tableid;
     this.inInsertMode = inInsertMode;
     this.cursorCount = 0;
 }
Example #18
0
 /// <summary>
 /// Create a NATIVE_INDEXRANGE from a cursor.
 /// </summary>
 /// <param name="tableid">The cursor containing the index range.</param>
 /// <returns>A new NATIVE_INDEXRANGE on the cursor.</returns>
 public static NATIVE_INDEXRANGE MakeIndexRangeFromTableid(JET_TABLEID tableid)
 {
     var s = new NATIVE_INDEXRANGE
     {
         tableid = tableid.Value,
         grbit = (uint) IndexRangeGrbit.RecordInIndex,
     };
     s.cbStruct = (uint)Marshal.SizeOf(s);
     return s;
 }
Example #19
0
		void ISchemaPart.ApplyToTable(Session session, JET_TABLEID table)
		{
			if (!Api.GetTableColumns(session, table).Any(ci => ci.Name == Name))
			{
				JET_COLUMNID columnid;
				Api.JetAddColumn(session, table, Name,
				                 new JET_COLUMNDEF {coltyp = JET_coltyp.Long, grbit = ColumndefGrbit.ColumnVersion}, null, 0,
				                 out columnid);
			}
		}
Example #20
0
        public void Setup()
        {
            this.directory = SetupHelper.CreateRandomDirectory();
            this.instance = SetupHelper.CreateNewInstance(this.directory);

            // turn off logging so initialization is faster
            Api.JetSetSystemParameter(this.instance, JET_SESID.Nil, JET_param.Recovery, 0, "off");
            Api.JetInit(ref this.instance);
            Api.JetBeginSession(this.instance, out this.sesid, String.Empty, String.Empty);
            this.tableid = JET_TABLEID.Nil;
        }
Example #21
0
        /// <summary>
        /// Initializes a new instance of the ColumnStream class.
        /// </summary>
        /// <param name="sesid">The session to use.</param>
        /// <param name="tableid">The cursor to use.</param>
        /// <param name="columnid">The columnid of the column to set/retrieve data from.</param>
        public ColumnStream(JET_SESID sesid, JET_TABLEID tableid, JET_COLUMNID columnid)
        {
            // In some cases we rely on Int32 arithmetic overflow checking to catch
            // errors, which assumes that a long-value can store Int32.MaxValue bytes.
            Debug.Assert(MaxLongValueSize == Int32.MaxValue, "Expected maximum long value size to be Int32.MaxValue");

            this.sesid = sesid;
            this.tableid = tableid;
            this.columnid = columnid;
            this.Itag = 1;
        }
Example #22
0
 /// <summary>
 /// If the records with the specified keys are not in the buffer cache
 /// then start asynchronous reads to bring the records into the database
 /// buffer cache.
 /// </summary>
 /// <param name="sesid">The session to use.</param>
 /// <param name="tableid">The table to issue the prereads against.</param>
 /// <param name="keys">
 /// The keys to preread. The keys must be sorted.
 /// </param>
 /// <param name="keyLengths">The lengths of the keys to preread.</param>
 /// <param name="keyCount">
 /// The maximum number of keys to preread.
 /// </param>
 /// <param name="keysPreread">
 /// Returns the number of keys to actually preread.
 /// </param>
 /// <param name="grbit">
 /// Preread options. Used to specify the direction of the preread.
 /// </param>
 public static void JetPrereadKeys(
     JET_SESID sesid,
     JET_TABLEID tableid,
     byte[][] keys,
     int[] keyLengths,
     int keyCount,
     out int keysPreread,
     PrereadKeysGrbit grbit)
 {
     JetPrereadKeys(sesid, tableid, keys, keyLengths, 0, keyCount, out keysPreread, grbit);
 }
Example #23
0
        /// <summary>
        /// Modifies a single column value in a modified record to be inserted or to
        /// update the current record.
        /// </summary>
        /// <param name="sesid">The session to use.</param>
        /// <param name="tableid">The cursor to update. An update should be prepared.</param>
        /// <param name="columnid">The columnid to set.</param>
        /// <param name="data">The data to set.</param>
        /// <param name="encoding">The encoding used to convert the string.</param>
        /// <param name="grbit">SetColumn options.</param>
        public static void SetColumn(
            JET_SESID sesid, JET_TABLEID tableid, JET_COLUMNID columnid, string data, Encoding encoding, SetColumnGrbit grbit)
        {
            CheckEncodingIsValid(encoding);

            if (null == data)
            {
                JetSetColumn(sesid, tableid, columnid, null, 0, grbit, null);
            }
            else if (0 == data.Length)
            {
                JetSetColumn(sesid, tableid, columnid, null, 0, grbit | SetColumnGrbit.ZeroLength, null);
            }
            else if (Encoding.Unicode == encoding)
            {
                // Optimization for setting Unicode strings.
                unsafe
                {
                    fixed (char* buffer = data)
                    {
                        JetSetColumn(
                            sesid,
                            tableid,
                            columnid,
                            new IntPtr(buffer),
                            checked(data.Length * sizeof(char)),
                            grbit,
                            null);
                    }
                }
            }
            else if (encoding.GetMaxByteCount(data.Length) <= Caches.ColumnCache.BufferSize)
            {
                // The encoding output will fix in a cached buffer. Get one to avoid 
                // more memory allocations.
                byte[] buffer = Caches.ColumnCache.Allocate();
                unsafe
                {
                    fixed (char* chars = data)
                    fixed (byte* bytes = buffer)
                    {
                        int dataSize = encoding.GetBytes(chars, data.Length, bytes, buffer.Length);
                        JetSetColumn(sesid, tableid, columnid, new IntPtr(bytes), dataSize, grbit, null);
                    }                    
                }

                Caches.ColumnCache.Free(ref buffer);
            }
            else
            {
                byte[] bytes = encoding.GetBytes(data);
                JetSetColumn(sesid, tableid, columnid, bytes, bytes.Length, grbit, null);
            }
        }
Example #24
0
        /// <summary>
        /// Removes an index range created with <see cref="JetSetIndexRange"/> or
        /// <see cref="TrySetIndexRange"/>. If no index range is present this
        /// method does nothing.
        /// </summary>
        /// <param name="sesid">The session to use.</param>
        /// <param name="tableid">The cursor to remove the index range on.</param>
        public static void ResetIndexRange(JET_SESID sesid, JET_TABLEID tableid)
        {
            var err = (JET_err)Impl.JetSetIndexRange(sesid, tableid, SetIndexRangeGrbit.RangeRemove);
            if (JET_err.InvalidOperation == err)
            {
                // this error is expected if there isn't currently an index range
                return;
            }

            Api.Check((int)err);
            return;
        }
Example #25
0
 /// <summary>
 /// Add a column to the table.
 /// </summary>
 /// <param name="sesid">The session to use.</param>
 /// <param name="tableid">The table to add the column to.</param>
 /// <param name="name">The name of the column.</param>
 /// <param name="coltyp">The type of the column.</param>
 /// <param name="cp">The codepage to use.</param>
 private void AddColumn(JET_SESID sesid, JET_TABLEID tableid, string name, JET_coltyp coltyp, JET_CP cp)
 {
     JET_COLUMNID ignored;
     Api.JetAddColumn(
         sesid,
         tableid,
         name,
         new JET_COLUMNDEF() { coltyp = coltyp, cp = cp },
         null,
         0,
         out ignored);
 }
Example #26
0
 /// <summary>
 /// If the records with the specified keys are not in the buffer cache
 /// then start asynchronous reads to bring the records into the database
 /// buffer cache.
 /// </summary>
 /// <param name="sesid">The session to use.</param>
 /// <param name="tableid">The table to issue the prereads against.</param>
 /// <param name="keys">
 /// The keys to preread. The keys must be sorted.
 /// </param>
 /// <param name="keyLengths">The lengths of the keys to preread.</param>
 /// <param name="keyIndex">
 /// The index of the first key in the keys array to read.
 /// </param>
 /// <param name="keyCount">
 /// The maximum number of keys to preread.
 /// </param>
 /// <param name="keysPreread">
 /// Returns the number of keys to actually preread.
 /// </param>
 /// <param name="grbit">
 /// Preread options. Used to specify the direction of the preread.
 /// </param>
 public static void JetPrereadKeys(
     JET_SESID sesid,
     JET_TABLEID tableid,
     byte[][] keys,
     int[] keyLengths,
     int keyIndex,
     int keyCount,
     out int keysPreread,
     PrereadKeysGrbit grbit)
 {
     Api.Check(Api.Impl.JetPrereadKeys(sesid, tableid, keys, keyLengths, keyIndex, keyCount, out keysPreread, grbit));
 }
Example #27
0
		void ISchemaPart.ApplyToTable(Session session, JET_TABLEID table)
		{
			var indexDef = IndexHelper.BuildIndexDefinition(Name);

			if (Api.GetTableColumns(session, table).All(ci => ci.Name != Name))
			{
				JET_COLUMNID columnid;
				var factory = EsentHelper.GetColumnFactory(Member);
				Api.JetAddColumn(session, table, Name, factory(), null, 0, out columnid);
				Api.JetCreateIndex(session, table, Name + "_index", CreateIndexGrbit.IndexPrimary, indexDef, indexDef.Length, _density);
			}
		}
Example #28
0
        /// <summary>
        /// Explicitly reserve the ability to update a row, write lock, or to explicitly prevent a row from
        /// being updated by any other session, read lock. Normally, row write locks are acquired implicitly as a
        /// result of updating rows. Read locks are usually not required because of record versioning. However,
        /// in some cases a transaction may desire to explicitly lock a row to enforce serialization, or to ensure
        /// that a subsequent operation will succeed. 
        /// </summary>
        /// <param name="sesid">The session to use.</param>
        /// <param name="tableid">The cursor to use. A lock will be acquired on the current record.</param>
        /// <param name="grbit">Lock options, use this to specify which type of lock to obtain.</param>
        /// <returns>
        /// True if the lock was obtained, false otherwise. An exception is thrown if an unexpected
        /// error is encountered.
        /// </returns>
        public static bool TryGetLock(JET_SESID sesid, JET_TABLEID tableid, GetLockGrbit grbit)
        {
            var err = (JET_err)Impl.JetGetLock(sesid, tableid, grbit);
            if (JET_err.WriteConflict == err)
            {
                return false;
            }

            Api.Check((int)err);
            Debug.Assert(err >= JET_err.Success, "Exception should have been thrown in case of error");
            return true;
        }
Example #29
0
        /// <summary>
        /// Initializes a new instance of the Update class. This automatically
        /// begins an update. The update will be cancelled if
        /// not explicitly saved.
        /// </summary>
        /// <param name="sesid">The session to start the transaction for.</param>
        /// <param name="tableid">The tableid to prepare the update for.</param>
        /// <param name="prep">The type of update.</param>
        public Update(JET_SESID sesid, JET_TABLEID tableid, JET_prep prep)
        {
            if (JET_prep.Cancel == prep)
            {
                throw new ArgumentException("Cannot create an Update for JET_prep.Cancel", "prep");
            }

            this.sesid = sesid;
            this.tableid = tableid;
            Api.JetPrepareUpdate(this.sesid, this.tableid, prep);
            this.ResourceWasAllocated();
        }
Example #30
0
        /// <summary>
        /// Try to move to the last record in the table. If the table is empty this
        /// returns false, if a different error is encountered an exception is thrown.
        /// </summary>
        /// <param name="sesid">The session to use.</param>
        /// <param name="tableid">The cursor to position.</param>
        /// <returns>True if the move was successful.</returns>
        public static bool TryMoveLast(JET_SESID sesid, JET_TABLEID tableid)
        {
            var err = (JET_err)Impl.JetMove(sesid, tableid, (int)JET_Move.Last, MoveGrbit.None);
            if (JET_err.NoCurrentRecord == err)
            {
                return false;
            }

            Api.Check((int)err);
            Debug.Assert(err >= JET_err.Success, "Exception should have been thrown in case of error");
            return true;
        }
Example #31
0
        public IEnumerable <RevaleeTask> ListAllTasks()
        {
            if (_EseInstance == null)
            {
                throw new InvalidOperationException("Storage provider has not been opened.");
            }

            EseConnection connection = this._ConnectionPool.OpenConnection();

            try
            {
                using (Table table = connection.GetTable(_TableNameCallbacks, OpenTableGrbit.DenyWrite | OpenTableGrbit.Preread | OpenTableGrbit.ReadOnly | OpenTableGrbit.Sequential))
                {
                    IDictionary <string, JET_COLUMNID> columnIds = connection.GetSchema(_TableNameCallbacks);

                    if (Api.TryMoveFirst(connection, table))
                    {
                        JET_SESID    jetSession                   = connection;
                        JET_TABLEID  jetTable                     = table;
                        JET_COLUMNID jetColumnCallbackId          = columnIds[_ColumnNameCallbackId];
                        JET_COLUMNID jetColumnCreatedTime         = columnIds[_ColumnNameCreatedTime];
                        JET_COLUMNID jetColumnCallbackTime        = columnIds[_ColumnNameCallbackTime];
                        JET_COLUMNID jetColumnCallbackUrl         = columnIds[_ColumnNameCallbackUrl];
                        JET_COLUMNID jetColumnAttemptsRemaining   = columnIds[_ColumnNameAttemptsRemaining];
                        JET_COLUMNID jetColumnAuthorizationCipher = columnIds[_ColumnNameAuthorizationCipher];

                        do
                        {
                            Guid?    callbackId              = Api.RetrieveColumnAsGuid(jetSession, jetTable, jetColumnCallbackId);
                            DateTime?createdTime             = Api.RetrieveColumnAsDateTime(jetSession, jetTable, jetColumnCreatedTime);
                            DateTime?callbackTime            = Api.RetrieveColumnAsDateTime(jetSession, jetTable, jetColumnCallbackTime);
                            string   callbackUrl             = Api.RetrieveColumnAsString(jetSession, jetTable, jetColumnCallbackUrl);
                            int?     attemptsRemainingColumn = Api.RetrieveColumnAsInt32(jetSession, jetTable, jetColumnAttemptsRemaining);
                            string   authorizationCipher     = Api.RetrieveColumnAsString(jetSession, jetTable, jetColumnAuthorizationCipher);

                            Uri callbackUri = null;

                            if (callbackTime.HasValue &&
                                Uri.TryCreate(callbackUrl, UriKind.Absolute, out callbackUri) &&
                                createdTime.HasValue &&
                                callbackId.HasValue &&
                                attemptsRemainingColumn.HasValue)
                            {
                                RevaleeTask revivedTask = RevaleeTask.Revive(
                                    DateTime.SpecifyKind(callbackTime.Value, DateTimeKind.Utc),
                                    callbackUri,
                                    DateTime.SpecifyKind(createdTime.Value, DateTimeKind.Utc),
                                    callbackId.Value,
                                    attemptsRemainingColumn.Value,
                                    string.IsNullOrEmpty(authorizationCipher) ? null : authorizationCipher);

                                yield return(revivedTask);
                            }
                        } while (Api.TryMoveNext(jetSession, jetTable));
                    }
                }
            }
            finally
            {
                _ConnectionPool.CloseConnection(connection);
            }

            yield break;
        }
Example #32
0
        private List <ColSpec> GetTableDef(JET_TABLEID table)
        {
            var columns  = new List <ColumnInfo>(Esent.GetTableColumns(m_sesid, table));
            var tableDef = new List <ColSpec>();

            foreach (var column in columns)
            {
                var colspec = new ColSpec();
                colspec.Name      = column.Name;
                colspec.ColumnId  = column.Columnid;
                colspec.Retriever = null;

                switch (column.Coltyp)
                {
                case JET_coltyp.Text:
                case JET_coltyp.LongText:
                    colspec.Type = typeof(string);
                    break;

                case JET_coltyp.Long:
                    colspec.Type = typeof(int?);
                    break;

                case JET_coltyp.Short:
                    colspec.Type = typeof(short?);
                    break;

                case JET_coltyp.UnsignedByte:
                    colspec.Type = typeof(byte?);
                    break;

                case JET_coltyp.Bit:
                    colspec.Type = typeof(bool?);
                    break;

                case JET_coltyp.DateTime:
                    colspec.Type = typeof(DateTime?);
                    break;

                case JET_coltyp.IEEEDouble:
                    colspec.Type = typeof(double?);
                    break;

                case JET_coltyp.IEEESingle:
                    colspec.Type = typeof(float?);
                    break;

                case JET_coltyp.Binary:
                case JET_coltyp.LongBinary:
                    colspec.Retriever = (s, t, c) =>
                    {
                        byte[] value = Esent.RetrieveColumn(s, t, c);
                        if (value != null)
                        {
                            return(Convert.ToBase64String(value));
                        }
                        else
                        {
                            return(value);
                        }
                    };
                    colspec.Type = typeof(string);
                    break;

                case VistaColtyp.UnsignedLong:
                    colspec.Type = typeof(UInt32?);
                    break;

                case VistaColtyp.LongLong:
                    colspec.Type = typeof(Int64?);
                    break;

                case VistaColtyp.GUID:
                    colspec.Type = typeof(Guid?);
                    break;

                case VistaColtyp.UnsignedShort:
                    colspec.Type = typeof(UInt16?);
                    break;

                default:
                    colspec.Retriever = (s, t, c) => "ERROR: unhandled type " + Enum.GetName(typeof(JET_coltyp), column.Coltyp) + "(" + (int)column.Coltyp + ")";
                    colspec.Type      = typeof(string);
                    break;
                }

                if (colspec.Retriever == null)
                {
                    colspec.Retriever = ColumnRetrievers.ForType(colspec.Type);
                }

                tableDef.Add(colspec);
            }

            return(tableDef);
        }
Example #33
0
 /// <summary>
 /// Set a string.
 /// </summary>
 /// <param name="sesid">The session to use.</param>
 /// <param name="tableid">The table to set the value in.</param>
 /// <param name="columnid">The column to set.</param>
 /// <param name="value">The value to set.</param>
 private static void SetColumn(JET_SESID sesid, JET_TABLEID tableid, JET_COLUMNID columnid, string value)
 {
     Api.SetColumn(sesid, tableid, columnid, value, Encoding.Unicode, SetColumnGrbit.IntrinsicLV);
 }
Example #34
0
 /// <summary>
 /// Set a date time.
 /// </summary>
 /// <param name="sesid">The session to use.</param>
 /// <param name="tableid">The table to set the value in.</param>
 /// <param name="columnid">The column to set.</param>
 /// <param name="value">The value to set.</param>
 private static void SetColumn(JET_SESID sesid, JET_TABLEID tableid, JET_COLUMNID columnid, DateTime value)
 {
     Api.SetColumn(sesid, tableid, columnid, value.Ticks);
 }
Example #35
0
        public IEnumerable <RevaleeTask> ListTasksDueBetween(DateTime startTime, DateTime endTime)
        {
            if (_EseInstance == null)
            {
                throw new InvalidOperationException("Storage provider has not been opened.");
            }

            DateTime rangeStartTime = NormalizeDateTime(startTime);
            DateTime rangeEndTime   = NormalizeDateTime(endTime);

            // Inclusive Upper Limit does not work properly for the CLR DateTime type.
            // Add the smallest amount of time that the Esent engine will detect to include the ending range inclusively.
            rangeEndTime = rangeEndTime.AddMilliseconds(1.0);

            EseConnection connection = this._ConnectionPool.OpenConnection();

            try
            {
                using (Table table = connection.GetTable(_TableNameCallbacks, OpenTableGrbit.DenyWrite | OpenTableGrbit.Preread | OpenTableGrbit.ReadOnly | OpenTableGrbit.Sequential))
                {
                    IDictionary <string, JET_COLUMNID> columnIds = connection.GetSchema(_TableNameCallbacks);
                    Api.JetSetCurrentIndex(connection, table, "due");
                    Api.MakeKey(connection, table, rangeStartTime, MakeKeyGrbit.NewKey);

                    if (Api.TrySeek(connection, table, SeekGrbit.SeekGE))
                    {
                        Api.MakeKey(connection, table, rangeEndTime, MakeKeyGrbit.NewKey);
                        if (Api.TrySetIndexRange(connection, table, SetIndexRangeGrbit.RangeInclusive | SetIndexRangeGrbit.RangeUpperLimit))
                        {
                            JET_SESID    jetSession                   = connection;
                            JET_TABLEID  jetTable                     = table;
                            JET_COLUMNID jetColumnCallbackId          = columnIds[_ColumnNameCallbackId];
                            JET_COLUMNID jetColumnCreatedTime         = columnIds[_ColumnNameCreatedTime];
                            JET_COLUMNID jetColumnCallbackTime        = columnIds[_ColumnNameCallbackTime];
                            JET_COLUMNID jetColumnCallbackUrl         = columnIds[_ColumnNameCallbackUrl];
                            JET_COLUMNID jetColumnAttemptsRemaining   = columnIds[_ColumnNameAttemptsRemaining];
                            JET_COLUMNID jetColumnAuthorizationCipher = columnIds[_ColumnNameAuthorizationCipher];

                            do
                            {
                                Guid?    callbackId              = Api.RetrieveColumnAsGuid(jetSession, jetTable, jetColumnCallbackId);
                                DateTime?createdTime             = Api.RetrieveColumnAsDateTime(jetSession, jetTable, jetColumnCreatedTime);
                                DateTime?callbackTime            = Api.RetrieveColumnAsDateTime(jetSession, jetTable, jetColumnCallbackTime);
                                string   callbackUrl             = Api.RetrieveColumnAsString(jetSession, jetTable, jetColumnCallbackUrl);
                                int?     attemptsRemainingColumn = Api.RetrieveColumnAsInt32(jetSession, jetTable, jetColumnAttemptsRemaining);
                                string   authorizationCipher     = Api.RetrieveColumnAsString(jetSession, jetTable, jetColumnAuthorizationCipher);

                                Uri callbackUri = null;

                                if (callbackTime.HasValue &&
                                    Uri.TryCreate(callbackUrl, UriKind.Absolute, out callbackUri) &&
                                    createdTime.HasValue &&
                                    callbackId.HasValue &&
                                    attemptsRemainingColumn.HasValue)
                                {
                                    RevaleeTask revivedTask = RevaleeTask.Revive(
                                        DateTime.SpecifyKind(callbackTime.Value, DateTimeKind.Utc),
                                        callbackUri,
                                        DateTime.SpecifyKind(createdTime.Value, DateTimeKind.Utc),
                                        callbackId.Value,
                                        attemptsRemainingColumn.Value,
                                        string.IsNullOrEmpty(authorizationCipher) ? null : authorizationCipher);

                                    yield return(revivedTask);
                                }
                            } while (Api.TryMoveNext(jetSession, jetTable));
                        }
                    }
                }
            }
            finally
            {
                _ConnectionPool.CloseConnection(connection);
            }

            yield break;
        }