//----------------------------------------------------------------------- // // Copyright (c) Microsoft Corporation. // //----------------------------------------------------------------------- // The Microsoft.Isam.Esent.Interop namespace will be developed with these principles: // - Any program written with this Api should work with the ESENT.dll from either // Windows XP, Windows Server 2003, Windows Vista, Windows Server 2008 or // Windows 7. // - The Esent.Interop DLL should only require version 2.0 of the .NET Framework. // - Full and complete documentation. Intellisense should be able to // provide useful and extensive help. // - Minimal editorialization. Whenever possible the Microsoft.Isam.Esent.Interop Jet* api will // exactly match the ESENT Api. In particular the names of structs, types // and functions will not be changed. Except for: // - Cleaning up Api constants. Instead of providing the constants from // esent.h they will be grouped into useful enumerations. This will // eliminate a lot of common Api errors. // - Provide helper methods/objects for common operations. These will be layered // on top of the ESENT Api. // - Minimize the interop overhead. // Changes that will be made are: // - Convert JET_coltyp etc. into real enumerations // - Removing cbStruct from structures // - Removing unused/reserved entries from structures // - Working around ESENT bugs or variances in API behavior // - Automatically using upgraded/downgraded functionality where possible // - Removing common API confusion where possible (e.g. always setting the columnid // in the JET_COLUMNDEF) // - Throwing exceptions instead of returning errors // The Api has four layers: // - NativeMethods (internal): this is the P/Invoke interop layer. This layer deals // with IntPtr and other basic types as opposed to the managed types // such as JET_TABLEID. // - JetApi (internal): this layer turns managed objects into // objects which can be passed into the P/Invoke interop layer. // Methods at this level return an error instead of throwing an exception. // This layer is implemented as an object with an interface. This allows // the actual implementation to be replaced at runtime, either for testing // or to use a different DLL. // - Api (public): this layer provides error-handling, turning errors // returned by lower layers into exceptions and warnings. // - Helper methods (public): this layer provides data conversion and // iteration for common API activities. These methods do not start // with 'Jet' but are implemented using the Jet methods. // - Disposable objects (public): these disposable object automatically // release esent resources (instances, sessions, tables and transactions). namespace Microsoft.Isam.Esent.Interop { using System; using System.Collections.Generic; using System.Diagnostics; using System.Runtime.InteropServices; using System.Security.Permissions; using Microsoft.Isam.Esent.Interop.Implementation; /// /// Managed versions of the ESENT Api. This class contains static methods corresponding /// with the unmanaged ESENT Api. These methods throw exceptions when errors are returned. /// public static partial class Api { /// /// Initializes static members of the Api class. /// static Api() { Api.Impl = new JetApi(); } /// /// Delegate for error handling code. /// /// The error that has been encountered. internal delegate void ErrorHandler(JET_err error); /// /// Gets or sets the ErrorHandler for all errors. This can /// be used for logging or to throw an exception. /// internal static event ErrorHandler HandleError; /// /// Gets or sets the IJetApi this is called for all functions. /// internal static IJetApi Impl { get; set; } #region Init/Term /// /// Allocates a new instance of the database engine. /// /// Returns the new instance. /// The name of the instance. Names must be unique. public static void JetCreateInstance(out JET_INSTANCE instance, string name) { Api.Check(Impl.JetCreateInstance(out instance, name)); } /// /// Allocate a new instance of the database engine for use in a single /// process, with a display name specified. /// /// Returns the newly create instance. /// /// Specifies a unique string identifier for the instance to be created. /// This string must be unique within a given process hosting the /// database engine. /// /// /// A display name for the instance to be created. This will be used /// in eventlog entries. /// /// Creation options. public static void JetCreateInstance2(out JET_INSTANCE instance, string name, string displayName, CreateInstanceGrbit grbit) { Api.Check(Impl.JetCreateInstance2(out instance, name, displayName, grbit)); } /// /// Initialize the ESENT database engine. /// /// /// The instance to initialize. If an instance hasn't been /// allocated then a new one is created and the engine /// will operate in single-instance mode. /// public static void JetInit(ref JET_INSTANCE instance) { Api.Check(Impl.JetInit(ref instance)); } /// /// Initialize the ESENT database engine. /// /// /// The instance to initialize. If an instance hasn't been /// allocated then a new one is created and the engine /// will operate in single-instance mode. /// /// /// Initialization options. /// /// /// A warning code. /// public static JET_wrn JetInit2(ref JET_INSTANCE instance, InitGrbit grbit) { return Api.Check(Impl.JetInit2(ref instance, grbit)); } #if !MANAGEDESENT_ON_WSA // Not exposed in MSDK /// /// Retrieves information about the instances that are running. /// /// /// Returns the number of instances. /// /// /// Returns an array of instance info objects, one for each running /// instance. /// public static void JetGetInstanceInfo(out int numInstances, out JET_INSTANCE_INFO[] instances) { Api.Check(Impl.JetGetInstanceInfo(out numInstances, out instances)); } /// /// Prevents streaming backup-related activity from continuing on a /// specific running instance, thus ending the streaming backup in /// a predictable way. /// /// The instance to use. public static void JetStopBackupInstance(JET_INSTANCE instance) { Api.Check(Impl.JetStopBackupInstance(instance)); } /// /// Prepares an instance for termination. /// /// The (running) instance to use. public static void JetStopServiceInstance(JET_INSTANCE instance) { Api.Check(Impl.JetStopServiceInstance(instance)); } #endif // !MANAGEDESENT_ON_WSA /// /// Terminate an instance that was created with or /// . /// /// The instance to terminate. public static void JetTerm(JET_INSTANCE instance) { Api.Check(Impl.JetTerm(instance)); } /// /// Terminate an instance that was created with or /// . /// /// The instance to terminate. /// Termination options. public static void JetTerm2(JET_INSTANCE instance, TermGrbit grbit) { Api.Check(Impl.JetTerm2(instance, grbit)); } /// /// Sets database configuration options. /// /// /// The instance to set the option on or /// to set the option on all instances. /// /// The session to use. /// The parameter to set. /// The value of the parameter to set, if the parameter is an integer type. /// The value of the parameter to set, if the parameter is a string type. /// An ESENT warning code. public static JET_wrn JetSetSystemParameter(JET_INSTANCE instance, JET_SESID sesid, JET_param paramid, int paramValue, string paramString) { return Api.Check(Impl.JetSetSystemParameter(instance, sesid, paramid, new IntPtr(paramValue), paramString)); } /// /// Sets database configuration options. /// /// /// The instance to set the option on or /// to set the option on all instances. /// /// The session to use. /// The parameter to set. /// The value of the parameter to set, if the parameter is a JET_CALLBACK. /// The value of the parameter to set, if the parameter is a string type. /// An ESENT warning code. public static JET_wrn JetSetSystemParameter(JET_INSTANCE instance, JET_SESID sesid, JET_param paramid, JET_CALLBACK paramValue, string paramString) { return Api.Check(Impl.JetSetSystemParameter(instance, sesid, paramid, paramValue, paramString)); } /// /// Sets database configuration options. /// /// /// The instance to set the option on or /// to set the option on all instances. /// /// The session to use. /// The parameter to set. /// The value of the parameter to set, if the parameter is an integer type. /// The value of the parameter to set, if the parameter is a string type. /// An ESENT warning code. public static JET_wrn JetSetSystemParameter( JET_INSTANCE instance, JET_SESID sesid, JET_param paramid, IntPtr paramValue, string paramString) { return Api.Check(Impl.JetSetSystemParameter(instance, sesid, paramid, paramValue, paramString)); } /// /// Gets database configuration options. /// /// The instance to retrieve the options from. /// The session to use. /// The parameter to get. /// Returns the value of the parameter, if the value is an integer. /// Returns the value of the parameter, if the value is a string. /// The maximum size of the parameter string. /// An ESENT warning code. /// /// passes in the error number in the paramValue, which is why it is /// a ref parameter and not an out parameter. /// public static JET_wrn JetGetSystemParameter( JET_INSTANCE instance, JET_SESID sesid, JET_param paramid, ref IntPtr paramValue, out string paramString, int maxParam) { return Api.Check(Impl.JetGetSystemParameter(instance, sesid, paramid, ref paramValue, out paramString, maxParam)); } /// /// Gets database configuration options. /// /// The instance to retrieve the options from. /// The session to use. /// The parameter to get. /// Returns the value of the parameter, if the value is an integer. /// Returns the value of the parameter, if the value is a string. /// The maximum size of the parameter string. /// An ESENT warning code. /// /// passes in the error number in the paramValue, which is why it is /// a ref parameter and not an out parameter. /// public static JET_wrn JetGetSystemParameter(JET_INSTANCE instance, JET_SESID sesid, JET_param paramid, ref int paramValue, out string paramString, int maxParam) { var intValue = new IntPtr(paramValue); JET_wrn wrn = Api.Check(Impl.JetGetSystemParameter(instance, sesid, paramid, ref intValue, out paramString, maxParam)); paramValue = intValue.ToInt32(); return wrn; } #if !MANAGEDESENT_ON_WSA // Not exposed in MSDK /// /// Retrieves the version of the database engine. /// /// The session to use. /// Returns the version number of the database engine. [CLSCompliant(false)] public static void JetGetVersion(JET_SESID sesid, out uint version) { Api.Check(Impl.JetGetVersion(sesid, out version)); } #endif // !MANAGEDESENT_ON_WSA #endregion #region Databases /// /// Creates and attaches a database file. /// /// The session to use. /// The path to the database file to create. /// The parameter is not used. /// Returns the dbid of the new database. /// Database creation options. /// public static void JetCreateDatabase(JET_SESID sesid, string database, string connect, out JET_DBID dbid, CreateDatabaseGrbit grbit) { Api.Check(Impl.JetCreateDatabase(sesid, database, connect, out dbid, grbit)); } /// /// Creates and attaches a database file with a maximum database size specified. /// . /// /// The session to use. /// The path to the database file to create. /// /// The maximum size, in database pages, of the database. Passing 0 means there is /// no enforced maximum. /// /// Returns the dbid of the new database. /// Database creation options. public static void JetCreateDatabase2(JET_SESID sesid, string database, int maxPages, out JET_DBID dbid, CreateDatabaseGrbit grbit) { Api.Check(Impl.JetCreateDatabase2(sesid, database, maxPages, out dbid, grbit)); } /// /// Attaches a database file for use with a database instance. In order to use the /// database, it will need to be subsequently opened with . /// /// The session to use. /// The database to attach. /// Attach options. /// An ESENT warning code. public static JET_wrn JetAttachDatabase(JET_SESID sesid, string database, AttachDatabaseGrbit grbit) { return Api.Check(Impl.JetAttachDatabase(sesid, database, grbit)); } /// /// Attaches a database file for use with a database instance. In order to use the /// database, it will need to be subsequently opened with . /// /// The session to use. /// The database to attach. /// /// The maximum size, in database pages, of the database. Passing 0 means there is /// no enforced maximum. /// /// Attach options. /// An ESENT warning code. public static JET_wrn JetAttachDatabase2(JET_SESID sesid, string database, int maxPages, AttachDatabaseGrbit grbit) { return Api.Check(Impl.JetAttachDatabase2(sesid, database, maxPages, grbit)); } /// /// Opens a database previously attached with , /// for use with a database session. This function can be called multiple times /// for the same database. /// /// The session that is opening the database. /// The database to open. /// Reserved for future use. /// Returns the dbid of the attached database. /// Open database options. /// An ESENT warning code. /// public static JET_wrn JetOpenDatabase(JET_SESID sesid, string database, string connect, out JET_DBID dbid, OpenDatabaseGrbit grbit) { return Api.Check(Impl.JetOpenDatabase(sesid, database, connect, out dbid, grbit)); } /// /// Closes a database file that was previously opened with or /// created with . /// /// The session to use. /// The database to close. /// Close options. public static void JetCloseDatabase(JET_SESID sesid, JET_DBID dbid, CloseDatabaseGrbit grbit) { Api.Check(Impl.JetCloseDatabase(sesid, dbid, grbit)); } /// /// Releases a database file that was previously attached to a database session. /// /// The database session to use. /// The database to detach. public static void JetDetachDatabase(JET_SESID sesid, string database) { Api.Check(Impl.JetDetachDatabase(sesid, database)); } /// /// Releases a database file that was previously attached to a database session. /// /// The database session to use. /// The database to detach. /// Detach options. public static void JetDetachDatabase2(JET_SESID sesid, string database, DetachDatabaseGrbit grbit) { Api.Check(Impl.JetDetachDatabase2(sesid, database, grbit)); } #if !MANAGEDESENT_ON_WSA // Not exposed in MSDK #pragma warning disable 618,612 // Disable warning that JET_CONVERT is obsolete /// /// Makes a copy of an existing database. The copy is compacted to a /// state optimal for usage. Data in the copied data will be packed /// according to the measures chosen for the indexes at index create. /// In this way, compacted data may be stored as densely as possible. /// Alternatively, compacted data may reserve space for subsequent /// record growth or index insertions. /// /// The session to use for the call. /// The source database that will be compacted. /// The name to use for the compacted database. /// /// A callback function that can be called periodically through the /// database compact operation to report progress. /// /// /// This parameter is ignored and should be null. /// /// Compact options. public static void JetCompact( JET_SESID sesid, string sourceDatabase, string destinationDatabase, JET_PFNSTATUS statusCallback, JET_CONVERT ignored, CompactGrbit grbit) { Api.Check( Impl.JetCompact(sesid, sourceDatabase, destinationDatabase, statusCallback, ignored, grbit)); } #pragma warning restore 618,612 /// /// Extends the size of a database that is currently open. /// /// The session to use. /// The database to grow. /// The desired size of the database, in pages. /// /// The size of the database, in pages, after the call. /// public static void JetGrowDatabase(JET_SESID sesid, JET_DBID dbid, int desiredPages, out int actualPages) { Api.Check(Impl.JetGrowDatabase(sesid, dbid, desiredPages, out actualPages)); } /// /// Sets the size of an unopened database file. /// /// The session to use. /// The name of the database. /// The desired size of the database, in pages. /// /// The size of the database, in pages, after the call. /// public static void JetSetDatabaseSize(JET_SESID sesid, string database, int desiredPages, out int actualPages) { Api.Check(Impl.JetSetDatabaseSize(sesid, database, desiredPages, out actualPages)); } #endif // !MANAGEDESENT_ON_WSA /// /// Retrieves certain information about the given database. /// /// The session to use. /// The database identifier. /// The value to be retrieved. /// The specific data to retrieve. public static void JetGetDatabaseInfo( JET_SESID sesid, JET_DBID dbid, out int value, JET_DbInfo infoLevel) { Api.Check(Impl.JetGetDatabaseInfo(sesid, dbid, out value, infoLevel)); } /// /// Retrieves certain information about the given database. /// /// The session to use. /// The database identifier. /// The value to be retrieved. /// The specific data to retrieve. public static void JetGetDatabaseInfo( JET_SESID sesid, JET_DBID dbid, out JET_DBINFOMISC dbinfomisc, JET_DbInfo infoLevel) { Api.Check(Impl.JetGetDatabaseInfo(sesid, dbid, out dbinfomisc, infoLevel)); } /// /// Retrieves certain information about the given database. /// /// The session to use. /// The database identifier. /// The value to be retrieved. /// The specific data to retrieve. public static void JetGetDatabaseInfo( JET_SESID sesid, JET_DBID dbid, out string value, JET_DbInfo infoLevel) { Api.Check(Impl.JetGetDatabaseInfo(sesid, dbid, out value, infoLevel)); } /// /// Retrieves certain information about the given database. /// /// The file name of the database. /// The value to be retrieved. /// The specific data to retrieve. public static void JetGetDatabaseFileInfo( string databaseName, out int value, JET_DbInfo infoLevel) { Api.Check(Impl.JetGetDatabaseFileInfo(databaseName, out value, infoLevel)); } /// /// Retrieves certain information about the given database. /// /// The file name of the database. /// The value to be retrieved. /// The specific data to retrieve. public static void JetGetDatabaseFileInfo( string databaseName, out long value, JET_DbInfo infoLevel) { Api.Check(Impl.JetGetDatabaseFileInfo(databaseName, out value, infoLevel)); } /// /// Retrieves certain information about the given database. /// /// The file name of the database. /// The value to be retrieved. /// The specific data to retrieve. public static void JetGetDatabaseFileInfo( string databaseName, out JET_DBINFOMISC dbinfomisc, JET_DbInfo infoLevel) { Api.Check(Impl.JetGetDatabaseFileInfo(databaseName, out dbinfomisc, infoLevel)); } #endregion #region Backup/Restore #if !MANAGEDESENT_ON_WSA /// /// Performs a streaming backup of an instance, including all the attached /// databases, to a directory. With multiple backup methods supported by /// the engine, this is the simplest and most encapsulated function. /// /// The instance to backup. /// /// The directory where the backup is to be stored. If the backup path is /// null to use the function will truncate the logs, if possible. /// /// Backup options. /// /// Optional status notification callback. /// public static void JetBackupInstance(JET_INSTANCE instance, string destination, BackupGrbit grbit, JET_PFNSTATUS statusCallback) { Api.Check(Impl.JetBackupInstance(instance, destination, grbit, statusCallback)); } /// /// Restores and recovers a streaming backup of an instance including all /// the attached databases. It is designed to work with a backup created /// with the function. This is the /// simplest and most encapsulated restore function. /// /// /// The instance to use. The instance should not be initialized. /// Restoring the files will initialize the instance. /// /// /// Location of the backup. The backup should have been created with /// . /// /// /// Name of the folder where the database files from the backup set will /// be copied and recovered. If this is set to null, the database files /// will be copied and recovered to their original location. /// /// /// Optional status notification callback. /// public static void JetRestoreInstance(JET_INSTANCE instance, string source, string destination, JET_PFNSTATUS statusCallback) { Api.Check(Impl.JetRestoreInstance(instance, source, destination, statusCallback)); } #endif // !MANAGEDESENT_ON_WSA #endregion #region Snapshot Backup #if !MANAGEDESENT_ON_WSA /// /// Starts a snapshot. While the snapshot is in progress, no /// write-to-disk activity by the engine can take place. /// /// The snapshot session. /// /// Returns the number of instances that are part of the snapshot session. /// /// /// Returns information about the instances that are part of the snapshot session. /// /// /// Snapshot freeze options. /// public static void JetOSSnapshotFreeze(JET_OSSNAPID snapshot, out int numInstances, out JET_INSTANCE_INFO[] instances, SnapshotFreezeGrbit grbit) { Api.Check(Impl.JetOSSnapshotFreeze(snapshot, out numInstances, out instances, grbit)); } /// /// Begins the preparations for a snapshot session. A snapshot session /// is a short time interval in which the engine does not issue any /// write IOs to disk, so that the engine can participate in a volume /// snapshot session (when driven by a snapshot writer). /// /// Returns the ID of the snapshot session. /// Snapshot options. public static void JetOSSnapshotPrepare(out JET_OSSNAPID snapshot, SnapshotPrepareGrbit grbit) { Api.Check(Impl.JetOSSnapshotPrepare(out snapshot, grbit)); } /// /// Notifies the engine that it can resume normal IO operations after a /// freeze period and a successful snapshot. /// /// The ID of the snapshot. /// Thaw options. public static void JetOSSnapshotThaw(JET_OSSNAPID snapshot, SnapshotThawGrbit grbit) { Api.Check(Impl.JetOSSnapshotThaw(snapshot, grbit)); } #endif // !MANAGEDESENT_ON_WSA #endregion #region Streaming Backup/Restore #if !MANAGEDESENT_ON_WSA /// /// Initiates an external backup while the engine and database are online and active. /// /// The instance prepare for backup. /// Backup options. public static void JetBeginExternalBackupInstance(JET_INSTANCE instance, BeginExternalBackupGrbit grbit) { Api.Check(Impl.JetBeginExternalBackupInstance(instance, grbit)); } /// /// Closes a file that was opened with JetOpenFileInstance after the /// data from that file has been extracted using JetReadFileInstance. /// /// The instance to use. /// The handle to close. public static void JetCloseFileInstance(JET_INSTANCE instance, JET_HANDLE handle) { Api.Check(Impl.JetCloseFileInstance(instance, handle)); } /// /// Ends an external backup session. This API is the last API in a series /// of APIs that must be called to execute a successful online /// (non-VSS based) backup. /// /// The instance to end the backup for. public static void JetEndExternalBackupInstance(JET_INSTANCE instance) { Api.Check(Impl.JetEndExternalBackupInstance(instance)); } /// /// Ends an external backup session. This API is the last API in a series /// of APIs that must be called to execute a successful online /// (non-VSS based) backup. /// /// The instance to end the backup for. /// Options that specify how the backup ended. public static void JetEndExternalBackupInstance2(JET_INSTANCE instance, EndExternalBackupGrbit grbit) { Api.Check(Impl.JetEndExternalBackupInstance2(instance, grbit)); } /// /// Used during a backup initiated by /// to query an instance for the names of database files that should become part of /// the backup file set. Only databases that are currently attached to the instance /// using will be considered. These files may /// subsequently be opened using and read /// using . /// /// /// It is important to note that this API does not return an error or warning if /// the output buffer is too small to accept the full list of files that should be /// part of the backup file set. /// /// The instance to get the information for. /// /// Returns a list of null terminated strings describing the set of database files /// that should be a part of the backup file set. The list of strings returned in /// this buffer is in the same format as a multi-string used by the registry. Each /// null-terminated string is returned in sequence followed by a final null terminator. /// /// /// Maximum number of characters to retrieve. /// /// /// Actual size of the file list. If this is greater than maxChars /// then the list has been truncated. /// public static void JetGetAttachInfoInstance(JET_INSTANCE instance, out string files, int maxChars, out int actualChars) { Api.Check(Impl.JetGetAttachInfoInstance(instance, out files, maxChars, out actualChars)); } /// /// Used during a backup initiated by /// to query an instance for the names of database patch files and logfiles that /// should become part of the backup file set. These files may subsequently be /// opened using and read using . /// /// /// It is important to note that this API does not return an error or warning if /// the output buffer is too small to accept the full list of files that should be /// part of the backup file set. /// /// The instance to get the information for. /// /// Returns a list of null terminated strings describing the set of database patch files /// and log files that should be a part of the backup file set. The list of strings returned in /// this buffer is in the same format as a multi-string used by the registry. Each /// null-terminated string is returned in sequence followed by a final null terminator. /// /// /// Maximum number of characters to retrieve. /// /// /// Actual size of the file list. If this is greater than maxChars /// then the list has been truncated. /// public static void JetGetLogInfoInstance(JET_INSTANCE instance, out string files, int maxChars, out int actualChars) { Api.Check(Impl.JetGetLogInfoInstance(instance, out files, maxChars, out actualChars)); } /// /// Used during a backup initiated by /// to query an instance for the names of the transaction log files that can be safely /// deleted after the backup has successfully completed. /// /// /// It is important to note that this API does not return an error or warning if /// the output buffer is too small to accept the full list of files that should be /// part of the backup file set. /// /// The instance to get the information for. /// /// Returns a list of null terminated strings describing the set of database log files /// that can be safely deleted after the backup completes. The list of strings returned in /// this buffer is in the same format as a multi-string used by the registry. Each /// null-terminated string is returned in sequence followed by a final null terminator. /// /// /// Maximum number of characters to retrieve. /// /// /// Actual size of the file list. If this is greater than maxChars /// then the list has been truncated. /// public static void JetGetTruncateLogInfoInstance(JET_INSTANCE instance, out string files, int maxChars, out int actualChars) { Api.Check(Impl.JetGetTruncateLogInfoInstance(instance, out files, maxChars, out actualChars)); } /// /// Opens an attached database, database patch file, or transaction log /// file of an active instance for the purpose of performing a streaming /// fuzzy backup. The data from these files can subsequently be read /// through the returned handle using JetReadFileInstance. The returned /// handle must be closed using JetCloseFileInstance. An external backup /// of the instance must have been previously initiated using /// JetBeginExternalBackupInstance. /// /// The instance to use. /// The file to open. /// Returns a handle to the file. /// Returns the least significant 32 bits of the file size. /// Returns the most significant 32 bits of the file size. public static void JetOpenFileInstance(JET_INSTANCE instance, string file, out JET_HANDLE handle, out long fileSizeLow, out long fileSizeHigh) { Api.Check(Impl.JetOpenFileInstance(instance, file, out handle, out fileSizeLow, out fileSizeHigh)); } /// /// Retrieves the contents of a file opened with . /// /// The instance to use. /// The file to read from. /// The buffer to read into. /// The size of the buffer. /// Returns the amount of data read into the buffer. public static void JetReadFileInstance(JET_INSTANCE instance, JET_HANDLE file, byte[] buffer, int bufferSize, out int bytesRead) { Api.Check(Impl.JetReadFileInstance(instance, file, buffer, bufferSize, out bytesRead)); } /// /// Used during a backup initiated by JetBeginExternalBackup to delete /// any transaction log files that will no longer be needed once the /// current backup completes successfully. /// /// The instance to truncate. public static void JetTruncateLogInstance(JET_INSTANCE instance) { Api.Check(Impl.JetTruncateLogInstance(instance)); } #endif // !MANAGEDESENT_ON_WSA #endregion #region Sessions /// /// Initialize a new ESENT session. /// /// The initialized instance to create the session in. /// Returns the created session. /// The parameter is not used. /// The parameter is not used. /// public static void JetBeginSession(JET_INSTANCE instance, out JET_SESID sesid, string username, string password) { Api.Check(Impl.JetBeginSession(instance, out sesid, username, password)); } /// /// Associates a session with the current thread using the given context /// handle. This association overrides the default engine requirement /// that a transaction for a given session must occur entirely on the /// same thread. Use to remove the /// association. /// /// The session to set the context on. /// The context to set. public static void JetSetSessionContext(JET_SESID sesid, IntPtr context) { Api.Check(Impl.JetSetSessionContext(sesid, context)); } /// /// Disassociates a session from the current thread. This should be /// used in conjunction with . /// /// The session to use. public static void JetResetSessionContext(JET_SESID sesid) { Api.Check(Impl.JetResetSessionContext(sesid)); } /// /// Ends a session. /// /// The session to end. /// This parameter is not used. public static void JetEndSession(JET_SESID sesid, EndSessionGrbit grbit) { Api.Check(Impl.JetEndSession(sesid, grbit)); } #if !MANAGEDESENT_ON_WSA // Not exposed in MSDK /// /// Initialize a new ESE session in the same instance as the given sesid. /// /// The session to duplicate. /// Returns the new session. public static void JetDupSession(JET_SESID sesid, out JET_SESID newSesid) { Api.Check(Impl.JetDupSession(sesid, out newSesid)); } #endif // !MANAGEDESENT_ON_WSA #endregion #region Tables /// /// Opens a cursor on a previously created table. /// /// The database session to use. /// The database to open the table in. /// The name of the table to open. /// The parameter is not used. /// The parameter is not used. /// Table open options. /// Returns the opened table. /// An ESENT warning. public static JET_wrn JetOpenTable(JET_SESID sesid, JET_DBID dbid, string tablename, byte[] parameters, int parametersSize, OpenTableGrbit grbit, out JET_TABLEID tableid) { return Api.Check(Impl.JetOpenTable(sesid, dbid, tablename, parameters, parametersSize, grbit, out tableid)); } /// /// Close an open table. /// /// The session which opened the table. /// The table to close. public static void JetCloseTable(JET_SESID sesid, JET_TABLEID tableid) { Api.Check(Impl.JetCloseTable(sesid, tableid)); } #if !MANAGEDESENT_ON_WSA // Not exposed in MSDK /// /// Duplicates an open cursor and returns a handle to the duplicated cursor. /// If the cursor that was duplicated was a read-only cursor then the /// duplicated cursor is also a read-only cursor. /// Any state related to constructing a search key or updating a record is /// not copied into the duplicated cursor. In addition, the location of the /// original cursor is not duplicated into the duplicated cursor. The /// duplicated cursor is always opened on the clustered index and its /// location is always on the first row of the table. /// /// The session to use. /// The cursor to duplicate. /// The duplicated cursor. /// Reserved for future use. public static void JetDupCursor(JET_SESID sesid, JET_TABLEID tableid, out JET_TABLEID newTableid, DupCursorGrbit grbit) { Api.Check(Impl.JetDupCursor(sesid, tableid, out newTableid, grbit)); } /// /// Walks each index of a table to exactly compute the number of entries /// in an index, and the number of distinct keys in an index. This /// information, together with the number of database pages allocated /// for an index and the current time of the computation is stored in /// index metadata in the database. This data can be subsequently retrieved /// with information operations. /// /// The session to use. /// The table that the statistics will be computed on. public static void JetComputeStats(JET_SESID sesid, JET_TABLEID tableid) { Api.Check(Impl.JetComputeStats(sesid, tableid)); } /// /// Enables the application to associate a context handle known as /// Local Storage with a cursor or the table associated with that /// cursor. This context handle can be used by the application to /// store auxiliary data that is associated with a cursor or table. /// The application is later notified using a runtime callback when /// the context handle must be released. This makes it possible to /// associate dynamically allocated state with a cursor or table. /// /// The session to use. /// The cursor to use. /// The context handle to be associated with the session or cursor. /// Set options. public static void JetSetLS(JET_SESID sesid, JET_TABLEID tableid, JET_LS ls, LsGrbit grbit) { Api.Check(Impl.JetSetLS(sesid, tableid, ls, grbit)); } /// /// Enables the application to retrieve the context handle known /// as Local Storage that is associated with a cursor or the table /// associated with that cursor. This context handle must have been /// previously set using . JetGetLS can also /// be used to simultaneously fetch the current context handle for /// a cursor or table and reset that context handle. /// /// The session to use. /// The cursor to use. /// Returns the retrieved context handle. /// Retrieve options. public static void JetGetLS(JET_SESID sesid, JET_TABLEID tableid, out JET_LS ls, LsGrbit grbit) { Api.Check(Impl.JetGetLS(sesid, tableid, out ls, grbit)); } /// /// Determine whether an update of the current record of a cursor /// will result in a write conflict, based on the current update /// status of the record. It is possible that a write conflict will /// ultimately be returned even if JetGetCursorInfo returns successfully. /// because another session may update the record before the current /// session is able to update the same record. /// /// The session to use. /// The cursor to check. public static void JetGetCursorInfo(JET_SESID sesid, JET_TABLEID tableid) { Api.Check(Impl.JetGetCursorInfo(sesid, tableid)); } #endif // !MANAGEDESENT_ON_WSA #endregion #region Transactions /// /// Causes a session to enter a transaction or create a new save point in an existing /// transaction. /// /// The session to begin the transaction for. public static void JetBeginTransaction(JET_SESID sesid) { Api.Check(Impl.JetBeginTransaction(sesid)); } /// /// Causes a session to enter a transaction or create a new save point in an existing /// transaction. /// /// The session to begin the transaction for. /// Transaction options. public static void JetBeginTransaction2(JET_SESID sesid, BeginTransactionGrbit grbit) { Api.Check(Impl.JetBeginTransaction2(sesid, grbit)); } /// /// Commits the changes made to the state of the database during the current save point /// and migrates them to the previous save point. If the outermost save point is committed /// then the changes made during that save point will be committed to the state of the /// database and the session will exit the transaction. /// /// The session to commit the transaction for. /// Commit options. public static void JetCommitTransaction(JET_SESID sesid, CommitTransactionGrbit grbit) { Api.Check(Impl.JetCommitTransaction(sesid, grbit)); } /// /// Undoes the changes made to the state of the database /// and returns to the last save point. JetRollback will also close any cursors /// opened during the save point. If the outermost save point is undone, the /// session will exit the transaction. /// /// The session to rollback the transaction for. /// Rollback options. public static void JetRollback(JET_SESID sesid, RollbackTransactionGrbit grbit) { Api.Check(Impl.JetRollback(sesid, grbit)); } #endregion #region DDL /// /// Create an empty table. The newly created table is opened exclusively. /// /// The session to use. /// The database to create the table in. /// The name of the table to create. /// Initial number of pages in the table. /// /// The default density of the table. This is used when doing sequential inserts. /// /// Returns the tableid of the new table. public static void JetCreateTable(JET_SESID sesid, JET_DBID dbid, string table, int pages, int density, out JET_TABLEID tableid) { Api.Check(Impl.JetCreateTable(sesid, dbid, table, pages, density, out tableid)); } /// /// Add a new column to an existing table. /// /// The session to use. /// The table to add the column to. /// The name of the column. /// The definition of the column. /// The default value of the column. /// The size of the default value. /// Returns the columnid of the new column. public static void JetAddColumn(JET_SESID sesid, JET_TABLEID tableid, string column, JET_COLUMNDEF columndef, byte[] defaultValue, int defaultValueSize, out JET_COLUMNID columnid) { Api.Check(Impl.JetAddColumn(sesid, tableid, column, columndef, defaultValue, defaultValueSize, out columnid)); } /// /// Deletes a column from a database table. /// /// The session to use. /// A cursor on the table to delete the column from. /// The name of the column to be deleted. public static void JetDeleteColumn(JET_SESID sesid, JET_TABLEID tableid, string column) { Api.Check(Impl.JetDeleteColumn(sesid, tableid, column)); } /// /// Deletes a column from a database table. /// /// The session to use. /// A cursor on the table to delete the column from. /// The name of the column to be deleted. /// Column deletion options. public static void JetDeleteColumn2(JET_SESID sesid, JET_TABLEID tableid, string column, DeleteColumnGrbit grbit) { Api.Check(Impl.JetDeleteColumn2(sesid, tableid, column, grbit)); } /// /// Deletes an index from a database table. /// /// The session to use. /// A cursor on the table to delete the index from. /// The name of the index to be deleted. public static void JetDeleteIndex(JET_SESID sesid, JET_TABLEID tableid, string index) { Api.Check(Impl.JetDeleteIndex(sesid, tableid, index)); } /// /// Deletes a table from a database. /// /// The session to use. /// The database to delete the table from. /// The name of the table to delete. public static void JetDeleteTable(JET_SESID sesid, JET_DBID dbid, string table) { Api.Check(Impl.JetDeleteTable(sesid, dbid, table)); } /// /// Creates an index over data in an ESE database. An index can be used to locate /// specific data quickly. /// /// The session to use. /// The table to create the index on. /// /// Pointer to a null-terminated string that specifies the name of the index to create. /// /// Index creation options. /// /// Pointer to a double null-terminated string of null-delimited tokens. /// /// /// The length, in characters, of szKey including the two terminating nulls. /// /// Initial B+ tree density. /// /// public static void JetCreateIndex( JET_SESID sesid, JET_TABLEID tableid, string indexName, CreateIndexGrbit grbit, string keyDescription, int keyDescriptionLength, int density) { Api.Check(Impl.JetCreateIndex(sesid, tableid, indexName, grbit, keyDescription, keyDescriptionLength, density)); } /// /// Creates indexes over data in an ESE database. /// /// /// 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 "JetCreateTable" /// will have exlusive access or the table can be opened for /// exclusive access by passing /// to . /// /// and /// are very similar, and appear to take the same arguments. The difference is in the /// implementation. JetCreateIndex2 uses LCIDs for Unicode indices (e.g. 1033), while /// JetCreateIndex4 uses Locale Names (e.g. "en-US" or "de-DE". LCIDs are older, and not as well /// supported in newer version of windows. /// /// /// The session to use. /// The table to create the index on. /// Array of objects describing the indexes to be created. /// Number of index description objects. /// /// public static void JetCreateIndex2( JET_SESID sesid, JET_TABLEID tableid, JET_INDEXCREATE[] indexcreates, int numIndexCreates) { Api.Check(Impl.JetCreateIndex2(sesid, tableid, indexcreates, numIndexCreates)); } /// /// Creates a temporary table with a single index. A temporary table /// stores and retrieves records just like an ordinary table created /// using JetCreateTableColumnIndex. However, temporary tables are /// much faster than ordinary tables due to their volatile nature. /// They can also be used to very quickly sort and perform duplicate /// removal on record sets when accessed in a purely sequential manner. /// Also see /// . /// . /// /// The session to use. /// /// Column definitions for the columns created in the temporary table. /// /// Number of column definitions. /// Table creation options. /// /// Returns the tableid of the temporary table. Closing this tableid /// with frees the resources associated /// with the temporary table. /// /// /// The output buffer that receives the array of column IDs generated /// during the creation of the temporary table. The column IDs in this /// array will exactly correspond to the input array of column definitions. /// As a result, the size of this buffer must correspond to the size of /// the input array. /// public static void JetOpenTempTable( JET_SESID sesid, JET_COLUMNDEF[] columns, int numColumns, TempTableGrbit grbit, out JET_TABLEID tableid, JET_COLUMNID[] columnids) { Api.Check(Impl.JetOpenTempTable(sesid, columns, numColumns, grbit, out tableid, columnids)); } #if !MANAGEDESENT_ON_WSA // Not exposed in MSDK /// /// Creates a temporary table with a single index. A temporary table /// stores and retrieves records just like an ordinary table created /// using JetCreateTableColumnIndex. However, temporary tables are /// much faster than ordinary tables due to their volatile nature. /// They can also be used to very quickly sort and perform duplicate /// removal on record sets when accessed in a purely sequential manner. /// Also see /// , /// . /// . /// /// The session to use. /// /// Column definitions for the columns created in the temporary table. /// /// Number of column definitions. /// /// The locale ID to use to compare any Unicode key column data in the temporary table. /// Any locale may be used as long as the appropriate language pack has been installed /// on the machine. /// /// Table creation options. /// /// Returns the tableid of the temporary table. Closing this tableid /// with frees the resources associated /// with the temporary table. /// /// /// The output buffer that receives the array of column IDs generated /// during the creation of the temporary table. The column IDs in this /// array will exactly correspond to the input array of column definitions. /// As a result, the size of this buffer must correspond to the size of /// the input array. /// public static void JetOpenTempTable2( JET_SESID sesid, JET_COLUMNDEF[] columns, int numColumns, int lcid, TempTableGrbit grbit, out JET_TABLEID tableid, JET_COLUMNID[] columnids) { Api.Check(Impl.JetOpenTempTable2(sesid, columns, numColumns, lcid, grbit, out tableid, columnids)); } #endif // !MANAGEDESENT_ON_WSA /// /// Creates a temporary table with a single index. A temporary table /// stores and retrieves records just like an ordinary table created /// using JetCreateTableColumnIndex. However, temporary tables are /// much faster than ordinary tables due to their volatile nature. /// They can also be used to very quickly sort and perform duplicate /// removal on record sets when accessed in a purely sequential manner. /// Also see /// , /// . /// /// The session to use. /// /// Column definitions for the columns created in the temporary table. /// /// Number of column definitions. /// /// The Locale ID and normalization flags that will be used to compare /// any Unicode key column data in the temporary table. When this /// is not present then the default options are used. /// /// Table creation options. /// /// Returns the tableid of the temporary table. Closing this tableid /// with frees the resources associated /// with the temporary table. /// /// /// The output buffer that receives the array of column IDs generated /// during the creation of the temporary table. The column IDs in this /// array will exactly correspond to the input array of column definitions. /// As a result, the size of this buffer must correspond to the size of /// the input array. /// public static void JetOpenTempTable3( JET_SESID sesid, JET_COLUMNDEF[] columns, int numColumns, JET_UNICODEINDEX unicodeindex, TempTableGrbit grbit, out JET_TABLEID tableid, JET_COLUMNID[] columnids) { Api.Check(Impl.JetOpenTempTable3(sesid, columns, numColumns, unicodeindex, grbit, out tableid, columnids)); } /// /// Creates a table, adds columns, and indices on that table. /// /// The session to use. /// The database to which to add the new table. /// Object describing the table to create. /// public static void JetCreateTableColumnIndex3( JET_SESID sesid, JET_DBID dbid, JET_TABLECREATE tablecreate) { Api.Check(Impl.JetCreateTableColumnIndex3(sesid, dbid, tablecreate)); } #region JetGetTableColumnInfo overloads /// /// Retrieves information about a table column. /// /// The session to use. /// The table containing the column. /// The name of the column. /// Filled in with information about the column. public static void JetGetTableColumnInfo( JET_SESID sesid, JET_TABLEID tableid, string columnName, out JET_COLUMNDEF columndef) { Api.Check(Impl.JetGetTableColumnInfo(sesid, tableid, columnName, out columndef)); } /// /// Retrieves information about a table column. /// /// The session to use. /// The table containing the column. /// The columnid of the column. /// Filled in with information about the column. public static void JetGetTableColumnInfo( JET_SESID sesid, JET_TABLEID tableid, JET_COLUMNID columnid, out JET_COLUMNDEF columndef) { Api.Check(Impl.JetGetTableColumnInfo(sesid, tableid, columnid, out columndef)); } /// /// Retrieves information about a table column. /// /// The session to use. /// The table containing the column. /// The name of the column. /// Filled in with information about the column. public static void JetGetTableColumnInfo( JET_SESID sesid, JET_TABLEID tableid, string columnName, out JET_COLUMNBASE columnbase) { Api.Check(Impl.JetGetTableColumnInfo(sesid, tableid, columnName, out columnbase)); } /// /// Retrieves information about all columns in the table. /// /// The session to use. /// The table containing the column. /// The parameter is ignored. /// Filled in with information about the columns in the table. public static void JetGetTableColumnInfo( JET_SESID sesid, JET_TABLEID tableid, string columnName, out JET_COLUMNLIST columnlist) { Api.Check(Impl.JetGetTableColumnInfo(sesid, tableid, columnName, ColInfoGrbit.None, out columnlist)); } /// /// Retrieves information about all columns in the table. /// /// The session to use. /// The table containing the column. /// The parameter is ignored. /// Additional options for JetGetTableColumnInfo. /// Filled in with information about the columns in the table. public static void JetGetTableColumnInfo( JET_SESID sesid, JET_TABLEID tableid, string columnName, ColInfoGrbit grbit, out JET_COLUMNLIST columnlist) { Api.Check(Impl.JetGetTableColumnInfo(sesid, tableid, columnName, grbit, out columnlist)); } #endregion #region JetGetColumnInfo overloads /// /// Retrieves information about a table column. /// /// The session to use. /// The database that contains the table. /// The name of the table containing the column. /// The name of the column. /// Filled in with information about the column. public static void JetGetColumnInfo( JET_SESID sesid, JET_DBID dbid, string tablename, string columnName, out JET_COLUMNDEF columndef) { Api.Check(Impl.JetGetColumnInfo(sesid, dbid, tablename, columnName, out columndef)); } /// /// Retrieves information about all columns in a table. /// /// The session to use. /// The database that contains the table. /// The name of the table containing the column. /// This parameter is ignored. /// Filled in with information about the columns in the table. public static void JetGetColumnInfo( JET_SESID sesid, JET_DBID dbid, string tablename, string columnName, out JET_COLUMNLIST columnlist) { Api.Check(Impl.JetGetColumnInfo(sesid, dbid, tablename, columnName, out columnlist)); } /// /// Retrieves information about a column in a table. /// /// The session to use. /// The database that contains the table. /// The name of the table containing the column. /// The name of the column. /// Filled in with information about the columns in the table. public static void JetGetColumnInfo( JET_SESID sesid, JET_DBID dbid, string tablename, string columnName, out JET_COLUMNBASE columnbase) { Api.Check(Impl.JetGetColumnInfo(sesid, dbid, tablename, columnName, out columnbase)); } #endregion #region JetGetObjectInfo overloads /// /// Retrieves information about database objects. /// /// The session to use. /// The database to use. /// Filled in with information about the objects in the database. public static void JetGetObjectInfo(JET_SESID sesid, JET_DBID dbid, out JET_OBJECTLIST objectlist) { Api.Check(Impl.JetGetObjectInfo(sesid, dbid, out objectlist)); } /// /// Retrieves information about database objects. /// /// The session to use. /// The database to use. /// The type of the object. /// The object name about which to retrieve information. /// Filled in with information about the objects in the database. public static void JetGetObjectInfo( JET_SESID sesid, JET_DBID dbid, JET_objtyp objtyp, string objectName, out JET_OBJECTINFO objectinfo) { Api.Check(Impl.JetGetObjectInfo(sesid, dbid, objtyp, objectName, out objectinfo)); } #endregion /// /// Determines the name of the current index of a given cursor. /// /// /// This name is also used to later re-select that index as the current index using /// . It can also be used to discover the properties of that index using /// JetGetTableIndexInfo. /// /// The returned name of the index will be an empty string if the current index is the clustered index and no /// primary index was explicitly defined. /// /// The session to use. /// The cursor to get the index name for. /// Returns the name of the index. /// /// The maximum length of the index name. Index names are no more than /// characters. /// public static void JetGetCurrentIndex(JET_SESID sesid, JET_TABLEID tableid, out string indexName, int maxNameLength) { Api.Check(Impl.JetGetCurrentIndex(sesid, tableid, out indexName, maxNameLength)); } #region JetGetTableInfo overloads /// /// Retrieves various pieces of information about a table in a database. /// /// /// This overload is used with . /// /// The session to use. /// The table to retrieve information about. /// Retrieved information. /// The type of information to retrieve. public static void JetGetTableInfo(JET_SESID sesid, JET_TABLEID tableid, out JET_OBJECTINFO result, JET_TblInfo infoLevel) { Api.Check(Impl.JetGetTableInfo(sesid, tableid, out result, infoLevel)); } /// /// Retrieves various pieces of information about a table in a database. /// /// /// This overload is used with and /// . /// /// The session to use. /// The table to retrieve information about. /// Retrieved information. /// The type of information to retrieve. public static void JetGetTableInfo(JET_SESID sesid, JET_TABLEID tableid, out string result, JET_TblInfo infoLevel) { Api.Check(Impl.JetGetTableInfo(sesid, tableid, out result, infoLevel)); } /// /// Retrieves various pieces of information about a table in a database. /// /// /// This overload is used with . /// /// The session to use. /// The table to retrieve information about. /// Retrieved information. /// The type of information to retrieve. public static void JetGetTableInfo(JET_SESID sesid, JET_TABLEID tableid, out JET_DBID result, JET_TblInfo infoLevel) { Api.Check(Impl.JetGetTableInfo(sesid, tableid, out result, infoLevel)); } /// /// Retrieves various pieces of information about a table in a database. /// /// /// This overload is used with and /// . /// /// The session to use. /// The table to retrieve information about. /// Retrieved information. /// The type of information to retrieve. public static void JetGetTableInfo(JET_SESID sesid, JET_TABLEID tableid, int[] result, JET_TblInfo infoLevel) { Api.Check(Impl.JetGetTableInfo(sesid, tableid, result, infoLevel)); } /// /// Retrieves various pieces of information about a table in a database. /// /// /// This overload is used with and /// . /// /// The session to use. /// The table to retrieve information about. /// Retrieved information. /// The type of information to retrieve. public static void JetGetTableInfo(JET_SESID sesid, JET_TABLEID tableid, out int result, JET_TblInfo infoLevel) { Api.Check(Impl.JetGetTableInfo(sesid, tableid, out result, infoLevel)); } #endregion #region JetGetIndexInfo overloads /// /// Retrieves information about indexes on a table. /// /// The session to use. /// The database to use. /// The name of the table to retrieve index information about. /// The name of the index to retrieve information about. /// Filled in with information about indexes on the table. /// The type of information to retrieve. [CLSCompliant(false)] public static void JetGetIndexInfo( JET_SESID sesid, JET_DBID dbid, string tablename, string indexname, out ushort result, JET_IdxInfo infoLevel) { Api.Check(Impl.JetGetIndexInfo(sesid, dbid, tablename, indexname, out result, infoLevel)); } /// /// Retrieves information about indexes on a table. /// /// The session to use. /// The database to use. /// The name of the table to retrieve index information about. /// The name of the index to retrieve information about. /// Filled in with information about indexes on the table. /// The type of information to retrieve. public static void JetGetIndexInfo( JET_SESID sesid, JET_DBID dbid, string tablename, string indexname, out int result, JET_IdxInfo infoLevel) { Api.Check(Impl.JetGetIndexInfo(sesid, dbid, tablename, indexname, out result, infoLevel)); } /// /// Retrieves information about indexes on a table. /// /// The session to use. /// The database to use. /// The name of the table to retrieve index information about. /// The name of the index to retrieve information about. /// Filled in with information about indexes on the table. /// The type of information to retrieve. public static void JetGetIndexInfo( JET_SESID sesid, JET_DBID dbid, string tablename, string indexname, out JET_INDEXID result, JET_IdxInfo infoLevel) { Api.Check(Impl.JetGetIndexInfo(sesid, dbid, tablename, indexname, out result, infoLevel)); } /// /// Retrieves information about indexes on a table. /// /// The session to use. /// The database to use. /// The name of the table to retrieve index information about. /// The name of the index to retrieve information about. /// Filled in with information about indexes on the table. /// The type of information to retrieve. public static void JetGetIndexInfo( JET_SESID sesid, JET_DBID dbid, string tablename, string indexname, out JET_INDEXLIST result, JET_IdxInfo infoLevel) { Api.Check(Impl.JetGetIndexInfo(sesid, dbid, tablename, indexname, out result, infoLevel)); } /// /// Retrieves information about indexes on a table. /// /// The session to use. /// The database to use. /// The name of the table to retrieve index information about. /// The name of the index to retrieve information about. /// Filled in with information about indexes on the table. /// The type of information to retrieve. public static void JetGetIndexInfo( JET_SESID sesid, JET_DBID dbid, string tablename, string indexname, out string result, JET_IdxInfo infoLevel) { Api.Check(Impl.JetGetIndexInfo(sesid, dbid, tablename, indexname, out result, infoLevel)); } /// /// Retrieves information about indexes on a table. /// /// The session to use. /// The database to use. /// The name of the table to retrieve index information about. /// The name of the index to retrieve information about. /// Filled in with information about indexes on the table. /// The type of information to retrieve. public static void JetGetIndexInfo( JET_SESID sesid, JET_DBID dbid, string tablename, string indexname, out JET_INDEXCREATE result, JET_IdxInfo infoLevel) { Api.Check(Impl.JetGetIndexInfo(sesid, dbid, tablename, indexname, out result, infoLevel)); } #endregion #region JetGetTableIndexInfo overloads /// /// Retrieves information about indexes on a table. /// /// The session to use. /// The table to retrieve index information about. /// The name of the index. /// Filled in with information about indexes on the table. /// The type of information to retrieve. [CLSCompliant(false)] public static void JetGetTableIndexInfo( JET_SESID sesid, JET_TABLEID tableid, string indexname, out ushort result, JET_IdxInfo infoLevel) { Api.Check(Impl.JetGetTableIndexInfo(sesid, tableid, indexname, out result, infoLevel)); } /// /// Retrieves information about indexes on a table. /// /// The session to use. /// The table to retrieve index information about. /// The name of the index. /// Filled in with information about indexes on the table. /// The type of information to retrieve. public static void JetGetTableIndexInfo( JET_SESID sesid, JET_TABLEID tableid, string indexname, out int result, JET_IdxInfo infoLevel) { Api.Check(Impl.JetGetTableIndexInfo(sesid, tableid, indexname, out result, infoLevel)); } /// /// Retrieves information about indexes on a table. /// /// The session to use. /// The table to retrieve index information about. /// The name of the index. /// Filled in with information about indexes on the table. /// The type of information to retrieve. public static void JetGetTableIndexInfo( JET_SESID sesid, JET_TABLEID tableid, string indexname, out JET_INDEXID result, JET_IdxInfo infoLevel) { Api.Check(Impl.JetGetTableIndexInfo(sesid, tableid, indexname, out result, infoLevel)); } /// /// Retrieves information about indexes on a table. /// /// The session to use. /// The table to retrieve index information about. /// The name of the index. /// Filled in with information about indexes on the table. /// The type of information to retrieve. public static void JetGetTableIndexInfo( JET_SESID sesid, JET_TABLEID tableid, string indexname, out JET_INDEXLIST result, JET_IdxInfo infoLevel) { Api.Check(Impl.JetGetTableIndexInfo(sesid, tableid, indexname, out result, infoLevel)); } /// /// Retrieves information about indexes on a table. /// /// The session to use. /// The table to retrieve index information about. /// The name of the index. /// Filled in with information about indexes on the table. /// The type of information to retrieve. public static void JetGetTableIndexInfo( JET_SESID sesid, JET_TABLEID tableid, string indexname, out string result, JET_IdxInfo infoLevel) { Api.Check(Impl.JetGetTableIndexInfo(sesid, tableid, indexname, out result, infoLevel)); } /// /// Retrieves information about indexes on a table. /// /// The session to use. /// The table to retrieve index information about. /// The name of the index to retrieve information about. /// Filled in with information about indexes on the table. /// The type of information to retrieve. public static void JetGetTableIndexInfo( JET_SESID sesid, JET_TABLEID tableid, string indexname, out JET_INDEXCREATE result, JET_IdxInfo infoLevel) { Api.Check(Impl.JetGetTableIndexInfo(sesid, tableid, indexname, out result, infoLevel)); } #endregion /// /// Changes the name of an existing table. /// /// The session to use. /// The database containing the table. /// The name of the table. /// The new name of the table. public static void JetRenameTable(JET_SESID sesid, JET_DBID dbid, string tableName, string newTableName) { Api.Check(Impl.JetRenameTable(sesid, dbid, tableName, newTableName)); } /// /// Changes the name of an existing column. /// /// The session to use. /// The table containing the column. /// The name of the column. /// The new name of the column. /// Column rename options. public static void JetRenameColumn(JET_SESID sesid, JET_TABLEID tableid, string name, string newName, RenameColumnGrbit grbit) { Api.Check(Impl.JetRenameColumn(sesid, tableid, name, newName, grbit)); } #if !MANAGEDESENT_ON_WSA // Not exposed in MSDK /// /// Changes the default value of an existing column. /// /// The session to use. /// The database containing the column. /// The name of the table containing the column. /// The name of the column. /// The new default value. /// Size of the new default value. /// Column default value options. public static void JetSetColumnDefaultValue( JET_SESID sesid, JET_DBID dbid, string tableName, string columnName, byte[] data, int dataSize, SetColumnDefaultValueGrbit grbit) { Api.Check(Impl.JetSetColumnDefaultValue(sesid, dbid, tableName, columnName, data, dataSize, grbit)); } #endif // !MANAGEDESENT_ON_WSA #endregion #region Navigation /// /// Positions a cursor to an index entry for the record that is associated with /// the specified bookmark. The bookmark can be used with any index defined over /// a table. The bookmark for a record can be retrieved using . /// /// The session to use. /// The cursor to position. /// The bookmark used to position the cursor. /// The size of the bookmark. public static void JetGotoBookmark(JET_SESID sesid, JET_TABLEID tableid, byte[] bookmark, int bookmarkSize) { Api.Check(Impl.JetGotoBookmark(sesid, tableid, bookmark, bookmarkSize)); } /// /// Positions a cursor to an index entry that is associated with the /// specified secondary index bookmark. The secondary index bookmark /// must be used with the same index over the same table from which it /// was originally retrieved. The secondary index bookmark for an index /// entry can be retrieved using . /// /// The session to use. /// The table cursor to position. /// The buffer that contains the secondary key. /// The size of the secondary key. /// The buffer that contains the primary key. /// The size of the primary key. /// Options for positioning the bookmark. public static void JetGotoSecondaryIndexBookmark( JET_SESID sesid, JET_TABLEID tableid, byte[] secondaryKey, int secondaryKeySize, byte[] primaryKey, int primaryKeySize, GotoSecondaryIndexBookmarkGrbit grbit) { Api.Check( Impl.JetGotoSecondaryIndexBookmark( sesid, tableid, secondaryKey, secondaryKeySize, primaryKey, primaryKeySize, grbit)); } /// /// Navigate through an index. The cursor can be positioned at the start or /// end of the index and moved backwards and forwards by a specified number /// of index entries. Also see /// , , /// , . /// /// The session to use for the call. /// The cursor to position. /// An offset which indicates how far to move the cursor. /// Move options. public static void JetMove(JET_SESID sesid, JET_TABLEID tableid, int numRows, MoveGrbit grbit) { Api.Check(Impl.JetMove(sesid, tableid, numRows, grbit)); } /// /// Navigate through an index. The cursor can be positioned at the start or /// end of the index and moved backwards and forwards by a specified number /// of index entries. Also see /// , , /// , . /// /// The session to use for the call. /// The cursor to position. /// An offset which indicates how far to move the cursor. /// Move options. public static void JetMove(JET_SESID sesid, JET_TABLEID tableid, JET_Move numRows, MoveGrbit grbit) { Api.Check(Impl.JetMove(sesid, tableid, (int)numRows, grbit)); } /// /// Constructs search keys that may then be used by and . /// /// /// The MakeKey functions provide datatype-specific make key functionality. /// /// The session to use. /// The cursor to create the key on. /// Column data for the current key column of the current index. /// Size of the data. /// Key options. public static void JetMakeKey(JET_SESID sesid, JET_TABLEID tableid, byte[] data, int dataSize, MakeKeyGrbit grbit) { if ((null == data && 0 != dataSize) || (null != data && dataSize > data.Length)) { throw new ArgumentOutOfRangeException( "dataSize", dataSize, "cannot be greater than the length of the data"); } unsafe { fixed (byte* pointer = data) { Api.JetMakeKey(sesid, tableid, new IntPtr(pointer), dataSize, grbit); } } } /// /// Efficiently positions a cursor to an index entry that matches the search /// criteria specified by the search key in that cursor and the specified /// inequality. A search key must have been previously constructed using /// . /// Also see . /// /// The session to use. /// The cursor to position. /// Seek options. /// An ESENT warning. public static JET_wrn JetSeek(JET_SESID sesid, JET_TABLEID tableid, SeekGrbit grbit) { return Api.Check(Impl.JetSeek(sesid, tableid, grbit)); } /// /// Temporarily limits the set of index entries that the cursor can walk using /// to those starting /// from the current index entry and ending at the index entry that matches the /// search criteria specified by the search key in that cursor and the specified /// bound criteria. A search key must have been previously constructed using /// . /// Also see . /// /// The session to use. /// The cursor to set the index range on. /// Index range options. public static void JetSetIndexRange(JET_SESID sesid, JET_TABLEID tableid, SetIndexRangeGrbit grbit) { Api.Check(Impl.JetSetIndexRange(sesid, tableid, grbit)); } /// /// Computes the intersection between multiple sets of index entries from different secondary /// indices over the same table. This operation is useful for finding the set of records in a /// table that match two or more criteria that can be expressed using index ranges. Also see /// . /// /// The session to use. /// /// An the index ranges to intersect. The tableids in the ranges /// must have index ranges set on them. Use /// to create an index range. /// /// /// The number of index ranges. /// /// /// Returns information about the temporary table containing the intersection results. /// /// Intersection options. public static void JetIntersectIndexes( JET_SESID sesid, JET_INDEXRANGE[] ranges, int numRanges, out JET_RECORDLIST recordlist, IntersectIndexesGrbit grbit) { Api.Check(Impl.JetIntersectIndexes(sesid, ranges, numRanges, out recordlist, grbit)); } /// /// Set the current index of a cursor. /// /// The session to use. /// The cursor to set the index on. /// /// The name of the index to be selected. If this is null or empty the primary /// index will be selected. /// public static void JetSetCurrentIndex(JET_SESID sesid, JET_TABLEID tableid, string index) { Api.Check(Impl.JetSetCurrentIndex(sesid, tableid, index)); } /// /// Set the current index of a cursor. /// /// The session to use. /// The cursor to set the index on. /// /// The name of the index to be selected. If this is null or empty the primary /// index will be selected. /// /// /// Set index options. /// public static void JetSetCurrentIndex2(JET_SESID sesid, JET_TABLEID tableid, string index, SetCurrentIndexGrbit grbit) { Api.Check(Impl.JetSetCurrentIndex2(sesid, tableid, index, grbit)); } /// /// Set the current index of a cursor. /// /// The session to use. /// The cursor to set the index on. /// /// The name of the index to be selected. If this is null or empty the primary /// index will be selected. /// /// /// Set index options. /// /// /// Sequence number of the multi-valued column value which will be used /// to position the cursor on the new index. This parameter is only used /// in conjunction with . When /// this parameter is not present or is set to zero, its value is presumed /// to be 1. /// public static void JetSetCurrentIndex3(JET_SESID sesid, JET_TABLEID tableid, string index, SetCurrentIndexGrbit grbit, int itagSequence) { Api.Check(Impl.JetSetCurrentIndex3(sesid, tableid, index, grbit, itagSequence)); } /// /// Set the current index of a cursor. /// /// The session to use. /// The cursor to set the index on. /// /// The name of the index to be selected. If this is null or empty the primary /// index will be selected. /// /// /// The id of the index to select. This id can be obtained using JetGetIndexInfo /// or JetGetTableIndexInfo with the option. /// /// /// Set index options. /// /// /// Sequence number of the multi-valued column value which will be used /// to position the cursor on the new index. This parameter is only used /// in conjunction with . When /// this parameter is not present or is set to zero, its value is presumed /// to be 1. /// public static void JetSetCurrentIndex4( JET_SESID sesid, JET_TABLEID tableid, string index, JET_INDEXID indexid, SetCurrentIndexGrbit grbit, int itagSequence) { Api.Check(Impl.JetSetCurrentIndex4(sesid, tableid, index, indexid, grbit, itagSequence)); } /// /// Counts the number of entries in the current index from the current position forward. /// The current position is included in the count. The count can be greater than the /// total number of records in the table if the current index is over a multi-valued /// column and instances of the column have multiple-values. If the table is empty, /// then 0 will be returned for the count. /// /// The session to use. /// The cursor to count the records in. /// Returns the number of records. /// /// The maximum number of records to count. A value of 0 indicates that the count /// is unlimited. /// public static void JetIndexRecordCount(JET_SESID sesid, JET_TABLEID tableid, out int numRecords, int maxRecordsToCount) { if (0 == maxRecordsToCount) { // BUG: Older versions of esent (e.g. Windows XP) don't use 0 as an unlimited count, // instead they simply count zero records (which isn't very useful). To make // sure this API works as advertised we will increase the maximum record count. maxRecordsToCount = int.MaxValue; } Api.Check(Impl.JetIndexRecordCount(sesid, tableid, out numRecords, maxRecordsToCount)); } /// /// Counts the number of entries in the current index from the current position forward. /// The current position is included in the count. The count can be greater than the /// total number of records in the table if the current index is over a multi-valued /// column and instances of the column have multiple-values. If the table is empty, /// then 0 will be returned for the count. /// /// The session to use. /// The cursor to count the records in. /// Returns the number of records. /// /// The maximum number of records to count. A value of 0 indicates that the count /// is unlimited. /// public static void JetIndexRecordCount2(JET_SESID sesid, JET_TABLEID tableid, out long numRecords, long maxRecordsToCount) { if (0 == maxRecordsToCount) { // BUG: Older versions of esent (e.g. Windows XP) don't use 0 as an unlimited count, // instead they simply count zero records (which isn't very useful). To make // sure this API works as advertised we will increase the maximum record count. // This will also prevent an overflow as the underlying API works with unsigned // numbers maxRecordsToCount = long.MaxValue; } Api.Check(Impl.JetIndexRecordCount2(sesid, tableid, out numRecords, maxRecordsToCount)); } /// /// Notifies the database engine that the application is scanning the entire /// index that the cursor is positioned on. Consequently, the methods that /// are used to access the index data will be tuned to make this scenario as /// fast as possible. /// Also see . /// /// The session to use. /// The cursor that will be accessing the data. /// Reserved for future use. public static void JetSetTableSequential(JET_SESID sesid, JET_TABLEID tableid, SetTableSequentialGrbit grbit) { Api.Check(Impl.JetSetTableSequential(sesid, tableid, grbit)); } /// /// Notifies the database engine that the application is no longer scanning the /// entire index the cursor is positioned on. This call reverses a notification /// sent by . /// /// The session to use. /// The cursor that was accessing the data. /// Reserved for future use. public static void JetResetTableSequential(JET_SESID sesid, JET_TABLEID tableid, ResetTableSequentialGrbit grbit) { Api.Check(Impl.JetResetTableSequential(sesid, tableid, grbit)); } /// /// Returns the fractional position of the current record in the current index /// in the form of a structure. /// Also see . /// /// The session to use. /// The cursor positioned on the record. /// Returns the approximate fractional position of the record. public static void JetGetRecordPosition(JET_SESID sesid, JET_TABLEID tableid, out JET_RECPOS recpos) { Api.Check(Impl.JetGetRecordPosition(sesid, tableid, out recpos)); } /// /// Moves a cursor to a new location that is a fraction of the way through /// the current index. /// Also see . /// /// The session to use. /// The cursor to position. /// The approximate position to move to. public static void JetGotoPosition(JET_SESID sesid, JET_TABLEID tableid, JET_RECPOS recpos) { Api.Check(Impl.JetGotoPosition(sesid, tableid, recpos)); } #endregion #region Data Retrieval /// /// Retrieves the bookmark for the record that is associated with the index entry /// at the current position of a cursor. This bookmark can then be used to /// reposition that cursor back to the same record using . /// The bookmark will be no longer than /// bytes. /// Also see . /// /// The session to use. /// The cursor to retrieve the bookmark from. /// Buffer to contain the bookmark. /// Size of the bookmark buffer. /// Returns the actual size of the bookmark. public static void JetGetBookmark(JET_SESID sesid, JET_TABLEID tableid, byte[] bookmark, int bookmarkSize, out int actualBookmarkSize) { Api.Check(Impl.JetGetBookmark(sesid, tableid, bookmark, bookmarkSize, out actualBookmarkSize)); } /// /// Retrieves a special bookmark for the secondary index entry at the /// current position of a cursor. This bookmark can then be used to /// efficiently reposition that cursor back to the same index entry /// using JetGotoSecondaryIndexBookmark. This is most useful when /// repositioning on a secondary index that contains duplicate keys or /// that contains multiple index entries for the same record. /// /// The session to use. /// The cursor to retrieve the bookmark from. /// Output buffer for the secondary key. /// Size of the secondary key buffer. /// Returns the size of the secondary key. /// Output buffer for the primary key. /// Size of the primary key buffer. /// Returns the size of the primary key. /// Options for the call. public static void JetGetSecondaryIndexBookmark( JET_SESID sesid, JET_TABLEID tableid, byte[] secondaryKey, int secondaryKeySize, out int actualSecondaryKeySize, byte[] primaryKey, int primaryKeySize, out int actualPrimaryKeySize, GetSecondaryIndexBookmarkGrbit grbit) { Api.Check( Impl.JetGetSecondaryIndexBookmark( sesid, tableid, secondaryKey, secondaryKeySize, out actualSecondaryKeySize, primaryKey, primaryKeySize, out actualPrimaryKeySize, grbit)); } /// /// Retrieves the key for the index entry at the current position of a cursor. /// Also see . /// /// The session to use. /// The cursor to retrieve the key from. /// The buffer to retrieve the key into. /// The size of the buffer. /// Returns the actual size of the data. /// Retrieve key options. public static void JetRetrieveKey(JET_SESID sesid, JET_TABLEID tableid, byte[] data, int dataSize, out int actualDataSize, RetrieveKeyGrbit grbit) { Api.Check(Impl.JetRetrieveKey(sesid, tableid, data, dataSize, out actualDataSize, grbit)); } /// /// 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. /// /// /// The RetrieveColumnAs functions provide datatype-specific retrieval functions. /// /// The session to use. /// The cursor to retrieve the column from. /// The columnid to retrieve. /// The data buffer to be retrieved into. /// The size of the data buffer. /// Returns the actual size of the data buffer. /// Retrieve column options. /// /// 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). /// /// An ESENT warning code. public static JET_wrn JetRetrieveColumn(JET_SESID sesid, JET_TABLEID tableid, JET_COLUMNID columnid, byte[] data, int dataSize, out int actualDataSize, RetrieveColumnGrbit grbit, JET_RETINFO retinfo) { return Api.JetRetrieveColumn(sesid, tableid, columnid, data, dataSize, 0, out actualDataSize, grbit, retinfo); } /// /// Retrieves multiple column values from the current record in a /// single operation. An array of JET_RETRIEVECOLUMN structures is /// used to describe the set of column values to be retrieved, and /// to describe output buffers for each column value to be retrieved. /// /// The session to use. /// The cursor to retrieve the data from. /// /// An array of one or more objects /// describing the data to be retrieved. /// /// /// The number of entries in the columns array. /// /// /// If any column retrieved is truncated due to an insufficient /// length buffer, then the API will return /// . However other errors /// JET_wrnColumnNull are returned only in the error field of /// the object. /// public static JET_wrn JetRetrieveColumns(JET_SESID sesid, JET_TABLEID tableid, JET_RETRIEVECOLUMN[] retrievecolumns, int numColumns) { if (null == retrievecolumns) { throw new ArgumentNullException("retrievecolumns"); } if (numColumns < 0 || numColumns > retrievecolumns.Length) { throw new ArgumentOutOfRangeException("numColumns", numColumns, "cannot be negative or greater than retrievecolumns.Length"); } unsafe { NATIVE_RETRIEVECOLUMN* nativeretrievecolumns = stackalloc NATIVE_RETRIEVECOLUMN[numColumns]; int err = Api.PinColumnsAndRetrieve(sesid, tableid, nativeretrievecolumns, retrievecolumns, numColumns, 0); for (int i = 0; i < numColumns; ++i) { retrievecolumns[i].UpdateFromNativeRetrievecolumn(ref nativeretrievecolumns[i]); } return Api.Check(err); } } /// /// Efficiently retrieves a set of columns and their values from the /// current record of a cursor or the copy buffer of that cursor. The /// columns and values retrieved can be restricted by a list of /// column IDs, itagSequence numbers, and other characteristics. This /// column retrieval API is unique in that it returns information in /// dynamically allocated memory that is obtained using a /// user-provided realloc compatible callback. This new flexibility /// permits the efficient retrieval of column data with specific /// characteristics (such as size and multiplicity) that are unknown /// to the caller. This eliminates the need for the use of the discovery /// modes of JetRetrieveColumn to determine those /// characteristics in order to setup a final call to /// JetRetrieveColumn that will successfully retrieve /// the desired data. /// /// The session to use. /// The cursor to retrieve data from. /// The numbers of JET_ENUMCOLUMNIDS. /// /// An optional array of column IDs, each with an optional array of itagSequence /// numbers to enumerate. /// /// /// Returns the number of column values retrieved. /// /// /// Returns the enumerated column values. /// /// /// Callback used to allocate memory. /// /// /// Context for the allocation callback. /// /// /// Sets a cap on the amount of data to return from a long text or long /// binary column. This parameter can be used to prevent the enumeration /// of an extremely large column value. /// /// Retrieve options. /// A warning or success. [CLSCompliant(false)] public static JET_wrn JetEnumerateColumns( JET_SESID sesid, JET_TABLEID tableid, int numColumnids, JET_ENUMCOLUMNID[] columnids, out int numColumnValues, out JET_ENUMCOLUMN[] columnValues, JET_PFNREALLOC allocator, IntPtr allocatorContext, int maxDataSize, EnumerateColumnsGrbit grbit) { return Api.Check( Impl.JetEnumerateColumns( sesid, tableid, numColumnids, columnids, out numColumnValues, out columnValues, allocator, allocatorContext, maxDataSize, grbit)); } /// /// Efficiently retrieves a set of columns and their values from the /// current record of a cursor or the copy buffer of that cursor. /// /// The session to use. /// The cursor to retrieve data from. /// Enumerate options. /// The discovered columns and their values. /// A warning or success. public static JET_wrn JetEnumerateColumns( JET_SESID sesid, JET_TABLEID tableid, EnumerateColumnsGrbit grbit, out IEnumerable enumeratedColumns) { return Api.Check( Impl.JetEnumerateColumns(sesid, tableid, grbit, out enumeratedColumns)); } #endregion #region DML /// /// Deletes the current record in a database table. /// /// The session that opened the cursor. /// The cursor on a database table. The current row will be deleted. public static void JetDelete(JET_SESID sesid, JET_TABLEID tableid) { Api.Check(Impl.JetDelete(sesid, tableid)); } /// /// Prepare a cursor for update. /// /// The session which is starting the update. /// The cursor to start the update for. /// The type of update to prepare. public static void JetPrepareUpdate(JET_SESID sesid, JET_TABLEID tableid, JET_prep prep) { Api.Check(Impl.JetPrepareUpdate(sesid, tableid, prep)); } /// /// The JetUpdate function performs an update operation including inserting a new row into /// a table or updating an existing row. Deleting a table row is performed by calling /// . /// /// The session which started the update. /// The cursor to update. An update should be prepared. /// Returns the bookmark of the updated record. This can be null. /// The size of the bookmark buffer. /// Returns the actual size of the bookmark. /// /// JetUpdate is the final step in performing an insert or an update. The update is begun by /// calling and then by calling /// /// one or more times to set the record state. Finally, /// is called to complete the update operation. Indexes are updated only by JetUpdate or and not during JetSetColumn. /// public static void JetUpdate(JET_SESID sesid, JET_TABLEID tableid, byte[] bookmark, int bookmarkSize, out int actualBookmarkSize) { Api.Check(Impl.JetUpdate(sesid, tableid, bookmark, bookmarkSize, out actualBookmarkSize)); } /// /// The JetUpdate function performs an update operation including inserting a new row into /// a table or updating an existing row. Deleting a table row is performed by calling /// . /// /// The session which started the update. /// The cursor to update. An update should be prepared. /// /// JetUpdate is the final step in performing an insert or an update. The update is begun by /// calling and then by calling /// /// one or more times to set the record state. Finally, /// is called to complete the update operation. Indexes are updated only by JetUpdate or and not during JetSetColumn. /// public static void JetUpdate(JET_SESID sesid, JET_TABLEID tableid) { int ignored; Api.Check(Impl.JetUpdate(sesid, tableid, null, 0, out ignored)); } /// /// 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 /// or ). /// /// /// The SetColumn methods provide datatype-specific overrides which may be more efficient. /// /// The session which is performing the update. /// The cursor to update. An update should be prepared. /// The columnid to set. /// The data to set. /// The size of data to set. /// SetColumn options. /// Used to specify itag or long-value offset. /// A warning code. public static JET_wrn JetSetColumn(JET_SESID sesid, JET_TABLEID tableid, JET_COLUMNID columnid, byte[] data, int dataSize, SetColumnGrbit grbit, JET_SETINFO setinfo) { return Api.JetSetColumn(sesid, tableid, columnid, data, dataSize, 0, grbit, setinfo); } /// /// Allows an application to set multiple column values in a single /// operation. An array of structures is /// used to describe the set of column values to be set, and to describe /// input buffers for each column value to be set. /// /// The session to use. /// The cursor to set the columns on. /// /// An array of structures describing the /// data to set. /// /// /// Number of entries in the setcolumns parameter. /// /// /// A warning. If the last column set has a warning, then /// this warning will be returned from JetSetColumns itself. /// [SecurityPermissionAttribute(SecurityAction.LinkDemand)] public static JET_wrn JetSetColumns(JET_SESID sesid, JET_TABLEID tableid, JET_SETCOLUMN[] setcolumns, int numColumns) { if (null == setcolumns) { throw new ArgumentNullException("setcolumns"); } if (numColumns < 0 || numColumns > setcolumns.Length) { throw new ArgumentOutOfRangeException("numColumns", numColumns, "cannot be negative or greater than setcolumns.Length"); } using (var gchandles = new GCHandleCollection()) { unsafe { NATIVE_SETCOLUMN* nativeSetColumns = stackalloc NATIVE_SETCOLUMN[numColumns]; // For performance, copy small amounts of data into a local buffer instead // of pinning the data. const int BufferSize = 128; byte* buffer = stackalloc byte[BufferSize]; int bufferRemaining = BufferSize; for (int i = 0; i < numColumns; ++i) { setcolumns[i].CheckDataSize(); nativeSetColumns[i] = setcolumns[i].GetNativeSetcolumn(); if (null == setcolumns[i].pvData) { nativeSetColumns[i].pvData = IntPtr.Zero; } else if (bufferRemaining >= setcolumns[i].cbData) { nativeSetColumns[i].pvData = new IntPtr(buffer); Marshal.Copy(setcolumns[i].pvData, setcolumns[i].ibData, nativeSetColumns[i].pvData, setcolumns[i].cbData); buffer += setcolumns[i].cbData; bufferRemaining -= setcolumns[i].cbData; Debug.Assert(bufferRemaining >= 0, "Buffer remaining is negative"); } else { byte* pinnedBuffer = (byte*)gchandles.Add(setcolumns[i].pvData).ToPointer(); nativeSetColumns[i].pvData = new IntPtr(pinnedBuffer + setcolumns[i].ibData); } } int err = Impl.JetSetColumns(sesid, tableid, nativeSetColumns, numColumns); for (int i = 0; i < numColumns; ++i) { setcolumns[i].err = (JET_wrn)nativeSetColumns[i].err; } return Api.Check(err); } } } #if !MANAGEDESENT_ON_WSA // Not exposed in MSDK /// /// 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. /// /// The session to use. /// The cursor to use. A lock will be acquired on the current record. /// Lock options, use this to specify which type of lock to obtain. public static void JetGetLock(JET_SESID sesid, JET_TABLEID tableid, GetLockGrbit grbit) { Api.Check(Impl.JetGetLock(sesid, tableid, grbit)); } #endif // !MANAGEDESENT_ON_WSA /// /// Performs an atomic addition operation on one column. This function allows /// multiple sessions to update the same record concurrently without conflicts. /// Also see /// . /// . /// /// /// The session to use. The session must be in a transaction. /// /// The cursor to update. /// /// The column to update. This must be an escrow updatable column. /// /// The buffer containing the addend. /// The size of the addend. /// /// An output buffer that will recieve the current value of the column. This buffer /// can be null. /// /// The size of the previousValue buffer. /// Returns the actual size of the previousValue. /// Escrow update options. public static void JetEscrowUpdate( JET_SESID sesid, JET_TABLEID tableid, JET_COLUMNID columnid, byte[] delta, int deltaSize, byte[] previousValue, int previousValueLength, out int actualPreviousValueLength, EscrowUpdateGrbit grbit) { Api.Check(Impl.JetEscrowUpdate( sesid, tableid, columnid, delta, deltaSize, previousValue, previousValueLength, out actualPreviousValueLength, grbit)); } #endregion #region Callbacks /// /// Allows the application to configure the database engine to issue /// notifications to the application for specific events. These /// notifications are associated with a specific table and remain in /// effect only until the instance containing the table is shut down /// using . /// /// The session to use. /// /// A cursor opened on the table that the callback should be /// registered on. /// /// /// The callback reasons for which the application wishes to receive notifications. /// /// The callback function. /// A context that will be given to the callback. /// /// A handle that can later be used to cancel the registration of the given /// callback function using . /// public static void JetRegisterCallback( JET_SESID sesid, JET_TABLEID tableid, JET_cbtyp cbtyp, JET_CALLBACK callback, IntPtr context, out JET_HANDLE callbackId) { Api.Check(Impl.JetRegisterCallback(sesid, tableid, cbtyp, callback, context, out callbackId)); } /// /// Configures the database engine to stop issuing notifications to the /// application as previously requested through /// . /// /// The session to use. /// /// A cursor opened on the table that the callback should be /// registered on. /// /// /// The callback reasons for which the application no longer wishes to receive notifications. /// /// /// The handle of the registered callback that was returned by . /// public static void JetUnregisterCallback(JET_SESID sesid, JET_TABLEID tableid, JET_cbtyp cbtyp, JET_HANDLE callbackId) { Api.Check(Impl.JetUnregisterCallback(sesid, tableid, cbtyp, callbackId)); } #endregion #region Online Maintenance /// /// Starts and stops database defragmentation tasks that improves data /// organization within a database. /// /// The session to use for the call. /// The database to be defragmented. /// /// Under some options defragmentation is performed for the entire database described by the given /// database ID, and other options (such as ) require /// the name of the table to defragment. /// /// /// When starting an online defragmentation task, this parameter sets the maximum number of defragmentation /// passes. When stopping an online defragmentation task, this parameter is set to the number of passes /// performed. This is not honored in all modes (such as ). /// /// /// When starting an online defragmentation task, this parameter sets /// the maximum time for defragmentation. When stopping an online /// defragmentation task, this output buffer is set to the length of /// time used for defragmentation. This is not honored in all modes (such as ). /// /// Defragmentation options. /// A warning code. /// public static JET_wrn JetDefragment( JET_SESID sesid, JET_DBID dbid, string tableName, ref int passes, ref int seconds, DefragGrbit grbit) { return Api.Check(Impl.JetDefragment(sesid, dbid, tableName, ref passes, ref seconds, grbit)); } /// /// Starts and stops database defragmentation tasks that improves data /// organization within a database. /// /// /// The callback passed to JetDefragment2 can be executed asynchronously. /// The GC doesn't know that the unmanaged code has a reference to the callback /// so it is important to make sure the callback isn't collected. /// /// The session to use for the call. /// The database to be defragmented. /// /// Under some options defragmentation is performed for the entire database described by the given /// database ID, and other options (such as ) require /// the name of the table to defragment. /// /// /// When starting an online defragmentation task, this parameter sets the maximum number of defragmentation /// passes. When stopping an online defragmentation task, this parameter is set to the number of passes /// performed. This is not honored in all modes (such as ). /// /// /// When starting an online defragmentation task, this parameter sets /// the maximum time for defragmentation. When stopping an online /// defragmentation task, this output buffer is set to the length of /// time used for defragmentation. This is not honored in all modes (such as ). /// /// Callback function that defrag uses to report progress. /// Defragmentation options. /// A warning code. public static JET_wrn JetDefragment2( JET_SESID sesid, JET_DBID dbid, string tableName, ref int passes, ref int seconds, JET_CALLBACK callback, DefragGrbit grbit) { return Api.Check(Impl.JetDefragment2(sesid, dbid, tableName, ref passes, ref seconds, callback, grbit)); } #if !MANAGEDESENT_ON_WSA // Not exposed in MSDK /// /// Performs idle cleanup tasks or checks the version store status in ESE. /// /// The session to use. /// A combination of JetIdleGrbit flags. /// An error code if the operation fails. public static JET_wrn JetIdle(JET_SESID sesid, IdleGrbit grbit) { return Api.Check(Impl.JetIdle(sesid, grbit)); } #endif #endregion #region Misc #if !MANAGEDESENT_ON_WSA // Not exposed in MSDK /// /// Frees memory that was allocated by a database engine call. /// /// /// This method is internal because we never expose the memory /// allocated by ESENT to our callers. /// /// /// The buffer allocated by a call to the database engine. /// is acceptable, and will be ignored. /// public static void JetFreeBuffer(IntPtr buffer) { Api.Check(Impl.JetFreeBuffer(buffer)); } #endif // !MANAGEDESENT_ON_WSA #endregion #region Error Handling /// /// Throw an exception if the parameter is an ESE error, /// returns a otherwise. /// /// The error code to check. /// An ESENT warning code (possibly success). internal static JET_wrn Check(int err) { if (err < 0) { throw CreateErrorException(err); } return unchecked((JET_wrn)err); } /// /// Create an error exception that should be thrown for a failure. /// /// The error code. /// A failure exception. private static Exception CreateErrorException(int err) { Debug.Assert(err < 0, "expected a negative error code"); JET_err error = unchecked((JET_err)err); var handler = Api.HandleError; if (handler != null) { handler(error); } // We didn't throw an exception from the handler, so // generate the default exception. return EsentExceptionHelper.JetErrToException(error); } #endregion Error Handling } }