internal OleDbConnectionInternal(OleDbConnectionString constr, OleDbConnection connection)
 {
     this.ConnectionString = constr;
     if (constr.PossiblePrompt && !Environment.UserInteractive)
     {
         throw ODB.PossiblePromptNotUserInteractive();
     }
     try
     {
         OleDbServicesWrapper objectPool = GetObjectPool();
         this._datasrcwrp = new DataSourceWrapper();
         objectPool.GetDataSource(constr, ref this._datasrcwrp);
         if (connection != null)
         {
             this._sessionwrp = new SessionWrapper();
             OleDbHResult hresult = this._datasrcwrp.InitializeAndCreateSession(constr, ref this._sessionwrp);
             if ((OleDbHResult.S_OK > hresult) || this._sessionwrp.IsInvalid)
             {
                 throw OleDbConnection.ProcessResults(hresult, null, null);
             }
             OleDbConnection.ProcessResults(hresult, connection, connection);
         }
     }
     catch
     {
         if (this._sessionwrp != null)
         {
             this._sessionwrp.Dispose();
             this._sessionwrp = null;
         }
         if (this._datasrcwrp != null)
         {
             this._datasrcwrp.Dispose();
             this._datasrcwrp = null;
         }
         throw;
     }
 }
        internal OleDbConnectionInternal(OleDbConnectionString constr, OleDbConnection connection) : base()
        {
            Debug.Assert((null != constr) && !constr.IsEmpty, "empty connectionstring");
            ConnectionString = constr;

            if (constr.PossiblePrompt && !System.Environment.UserInteractive)
            {
                throw ODB.PossiblePromptNotUserInteractive();
            }

            try
            {
                // this is the native DataLinks object which pools the native datasource/session
                OleDbServicesWrapper wrapper = OleDbConnectionInternal.GetObjectPool();
                _datasrcwrp = new DataSourceWrapper();

                // DataLinks wrapper will call IDataInitialize::GetDataSource to create the DataSource
                // uses constr.ActualConnectionString, no InfoMessageEvent checking
                wrapper.GetDataSource(constr, ref _datasrcwrp);
                Debug.Assert(!_datasrcwrp.IsInvalid, "bad DataSource");

                // initialization is delayed because of OleDbConnectionStringBuilder only wants
                // pre-Initialize IDBPropertyInfo & IDBProperties on the data source
                if (null != connection)
                {
                    _sessionwrp = new SessionWrapper();

                    // From the DataSource object, will call IDBInitialize.Initialize & IDBCreateSession.CreateSession
                    // We always need both called so we use a single call for a single DangerousAddRef/DangerousRelease pair.
                    OleDbHResult hr = _datasrcwrp.InitializeAndCreateSession(constr, ref _sessionwrp);

                    // process the HResult here instead of from the SafeHandle because the possibility
                    // of an InfoMessageEvent.
                    if ((0 <= hr) && !_sessionwrp.IsInvalid)
                    { // process infonessage events
                        OleDbConnection.ProcessResults(hr, connection, connection);
                    }
                    else
                    {
                        Exception e = OleDbConnection.ProcessResults(hr, null, null);
                        Debug.Assert(null != e, "CreateSessionError");
                        throw e;
                    }
                    Debug.Assert(!_sessionwrp.IsInvalid, "bad Session");
                }
            }
            catch
            {
                if (null != _sessionwrp)
                {
                    _sessionwrp.Dispose();
                    _sessionwrp = null;
                }
                if (null != _datasrcwrp)
                {
                    _datasrcwrp.Dispose();
                    _datasrcwrp = null;
                }
                throw;
            }
        }
Пример #3
0
        internal unsafe OleDbHResult InitializeAndCreateSession(OleDbConnectionString constr, ref SessionWrapper sessionWrapper)
        {
            OleDbHResult hr;
            bool         mustRelease      = false;
            IntPtr       idbCreateSession = IntPtr.Zero;

            RuntimeHelpers.PrepareConstrainedRegions();
            try
            {
                DangerousAddRef(ref mustRelease);

                // native COM rules are the QI result is the 'this' pointer
                // the pointer stored at that location is the vtable
                // since IUnknown is a public,shipped COM interface, its layout will not change (ever)
                IntPtr vtable = Marshal.ReadIntPtr(base.handle, 0);
                IntPtr method = Marshal.ReadIntPtr(vtable, 0);

                // we cache the QueryInterface delegate to prevent recreating it on every call
                UnsafeNativeMethods.IUnknownQueryInterface?QueryInterface = constr.DangerousDataSourceIUnknownQueryInterface;

                // since the delegate lifetime is longer than the original instance used to create it
                // we double check before each usage to verify the delegates function pointer
                if ((null == QueryInterface) || (method != Marshal.GetFunctionPointerForDelegate(QueryInterface)))
                {
                    QueryInterface = (UnsafeNativeMethods.IUnknownQueryInterface)Marshal.GetDelegateForFunctionPointer(method, typeof(UnsafeNativeMethods.IUnknownQueryInterface));
                    constr.DangerousDataSourceIUnknownQueryInterface = QueryInterface;
                }

                // native COM rules are the QI result is the 'this' pointer
                // the pointer stored at that location is the vtable
                // since IDBInitialize is a public,shipped COM interface, its layout will not change (ever)
                vtable = Marshal.ReadIntPtr(base.handle, 0);
                method = Marshal.ReadIntPtr(vtable, 3 * IntPtr.Size);  // Initialize is the 4'th vtable entry

                // we cache the Initialize delegate to prevent recreating it on every call
                UnsafeNativeMethods.IDBInitializeInitialize?Initialize = constr.DangerousIDBInitializeInitialize;

                // since the delegate lifetime is longer than the original instance used to create it
                // we double check before each usage to verify the delegates function pointer
                if ((null == Initialize) || (method != Marshal.GetFunctionPointerForDelegate(Initialize)))
                {
                    Initialize = (UnsafeNativeMethods.IDBInitializeInitialize)Marshal.GetDelegateForFunctionPointer(method, typeof(UnsafeNativeMethods.IDBInitializeInitialize));
                    constr.DangerousIDBInitializeInitialize = Initialize;
                }

                // call IDBInitialize::Initialize via the delegate
                hr = Initialize(base.handle);

                // we don't ever expect DB_E_ALREADYINITIALIZED, but since we checked in V1.0 - its propagated along
                if ((0 <= hr) || (OleDbHResult.DB_E_ALREADYINITIALIZED == hr))
                {
                    // call IUnknown::QueryInterface via the delegate
                    fixed(Guid *riid = &ODB.IID_IDBCreateSession)
                    {
                        hr = (OleDbHResult)QueryInterface(base.handle, riid, &idbCreateSession);
                    }
                    if ((0 <= hr) && (IntPtr.Zero != idbCreateSession))
                    {
                        // native COM rules are the QI result is the 'this' pointer
                        // the pointer stored at that location is the vtable
                        // since IDBCreateSession is a public,shipped COM interface, its layout will not change (ever)
                        vtable = Marshal.ReadIntPtr(idbCreateSession, 0);
                        method = Marshal.ReadIntPtr(vtable, 3 * IntPtr.Size);  // CreateSession is the 4'th vtable entry

                        UnsafeNativeMethods.IDBCreateSessionCreateSession?CreateSession = constr.DangerousIDBCreateSessionCreateSession;

                        // since the delegate lifetime is longer than the original instance used to create it
                        // we double check before each usage to verify the delegates function pointer
                        if ((null == CreateSession) || (method != Marshal.GetFunctionPointerForDelegate(CreateSession)))
                        {
                            CreateSession = (UnsafeNativeMethods.IDBCreateSessionCreateSession)Marshal.GetDelegateForFunctionPointer(method, typeof(UnsafeNativeMethods.IDBCreateSessionCreateSession));
                            constr.DangerousIDBCreateSessionCreateSession = CreateSession;
                        }

                        // if I have a delegate for CreateCommand directly ask for IDBCreateCommand
                        if (null != constr.DangerousIDBCreateCommandCreateCommand)
                        {
                            // call IDBCreateSession::CreateSession via the delegate directly for IDBCreateCommand
                            fixed(Guid *riid = &ODB.IID_IDBCreateCommand)
                            {
                                bool           addRefd    = false;
                                SessionWrapper newWrapper = new SessionWrapper();

                                sessionWrapper.DangerousAddRef(ref addRefd);
                                IntPtr originalHandle = sessionWrapper.DangerousGetHandle();
                                IntPtr handle         = originalHandle;

                                try
                                {
                                    hr = CreateSession(idbCreateSession, IntPtr.Zero, riid, &handle);
                                }
                                finally
                                {
                                    if (addRefd)
                                    {
                                        sessionWrapper.DangerousRelease();
                                    }
                                    if (handle != originalHandle)
                                    {
                                        Marshal.InitHandle(newWrapper, handle);
                                        sessionWrapper = newWrapper;
                                    }
                                }
                            }
                            if ((0 <= hr) && !sessionWrapper.IsInvalid)
                            {
                                // double check the cached delegate is correct
                                sessionWrapper.VerifyIDBCreateCommand(constr);
                            }
                        }
                        else
                        {
                            // otherwise ask for IUnknown (it may be first time usage or IDBCreateCommand not supported)
                            fixed(Guid *riid = &ODB.IID_IUnknown)
                            {
                                bool           addRefd    = false;
                                SessionWrapper newWrapper = new SessionWrapper();

                                sessionWrapper.DangerousAddRef(ref addRefd);
                                IntPtr originalHandle = sessionWrapper.DangerousGetHandle();
                                IntPtr handle         = originalHandle;

                                try
                                {
                                    hr = CreateSession(idbCreateSession, IntPtr.Zero, riid, &handle);
                                }
                                finally
                                {
                                    if (addRefd)
                                    {
                                        sessionWrapper.DangerousRelease();
                                    }
                                    if (handle != originalHandle)
                                    {
                                        Marshal.InitHandle(newWrapper, handle);
                                        sessionWrapper = newWrapper;
                                    }
                                }
                            }
                            if ((0 <= hr) && !sessionWrapper.IsInvalid)
                            {
                                // and check support for IDBCreateCommand and create delegate for CreateCommand
                                sessionWrapper.QueryInterfaceIDBCreateCommand(constr);
                            }
                        }
                    }
                }
            }
            finally
            {
                if (IntPtr.Zero != idbCreateSession)
                {
                    // release the QI for IDBCreateSession
                    Marshal.Release(idbCreateSession);
                }
                if (mustRelease)
                {
                    // release the AddRef on DataLinks
                    DangerousRelease();
                }
            }
            return(hr);
        }
Пример #4
0
        internal OleDbHResult InitializeAndCreateSession(OleDbConnectionString constr, ref SessionWrapper sessionWrapper) {
            OleDbHResult hr;
            bool mustRelease = false;
            IntPtr idbCreateSession = IntPtr.Zero;
            RuntimeHelpers.PrepareConstrainedRegions();
            try {
                DangerousAddRef(ref mustRelease);
                
                // native COM rules are the QI result is the 'this' pointer
                // the pointer stored at that location is the vtable
                // since IUnknown is a public,shipped COM interface, its layout will not change (ever)
                IntPtr vtable = Marshal.ReadIntPtr(base.handle, 0);
                IntPtr method = Marshal.ReadIntPtr(vtable, 0);
                
                // we cache the QueryInterface delegate to prevent recreating it on every call
                UnsafeNativeMethods.IUnknownQueryInterface QueryInterface = constr.DangerousDataSourceIUnknownQueryInterface;

                // since the delegate lifetime is longer than the original instance used to create it
                // we double check before each usage to verify the delegates function pointer
                if ((null == QueryInterface) || (method != Marshal.GetFunctionPointerForDelegate(QueryInterface))) {
                    QueryInterface = (UnsafeNativeMethods.IUnknownQueryInterface)Marshal.GetDelegateForFunctionPointer(method, typeof(UnsafeNativeMethods.IUnknownQueryInterface));
                    constr.DangerousDataSourceIUnknownQueryInterface = QueryInterface;
                }
                
                // native COM rules are the QI result is the 'this' pointer
                // the pointer stored at that location is the vtable
                // since IDBInitialize is a public,shipped COM interface, its layout will not change (ever)
                vtable = Marshal.ReadIntPtr(base.handle, 0);
                method = Marshal.ReadIntPtr(vtable, 3 * IntPtr.Size);  // Initialize is the 4'th vtable entry

                // we cache the Initialize delegate to prevent recreating it on every call
                UnsafeNativeMethods.IDBInitializeInitialize Initialize = constr.DangerousIDBInitializeInitialize;
                
                // since the delegate lifetime is longer than the original instance used to create it
                // we double check before each usage to verify the delegates function pointer
                if ((null == Initialize) || (method != Marshal.GetFunctionPointerForDelegate(Initialize))) {
                    Initialize = (UnsafeNativeMethods.IDBInitializeInitialize)Marshal.GetDelegateForFunctionPointer(method, typeof(UnsafeNativeMethods.IDBInitializeInitialize));
                    constr.DangerousIDBInitializeInitialize = Initialize;
                }

                // call IDBInitialize::Initialize via the delegate
                hr = Initialize(base.handle);

                // we don't ever expect DB_E_ALREADYINITIALIZED, but since we checked in V1.0 - its propagated along
                if ((0 <= hr) || (OleDbHResult.DB_E_ALREADYINITIALIZED == hr)) {
                    
                    // call IUnknown::QueryInterface via the delegate
                    hr = (OleDbHResult)QueryInterface(base.handle, ref ODB.IID_IDBCreateSession, ref idbCreateSession);
                    if ((0 <= hr) && (IntPtr.Zero != idbCreateSession)) {
                        
                        // native COM rules are the QI result is the 'this' pointer
                        // the pointer stored at that location is the vtable
                        // since IDBCreateSession is a public,shipped COM interface, its layout will not change (ever)
                        vtable = Marshal.ReadIntPtr(idbCreateSession, 0);
                        method = Marshal.ReadIntPtr(vtable, 3 * IntPtr.Size);  // CreateSession is the 4'th vtable entry
                        
                        UnsafeNativeMethods.IDBCreateSessionCreateSession CreateSession = constr.DangerousIDBCreateSessionCreateSession;                                

                        // since the delegate lifetime is longer than the original instance used to create it
                        // we double check before each usage to verify the delegates function pointer
                        if ((null == CreateSession) || (method != Marshal.GetFunctionPointerForDelegate(CreateSession))) {
                            CreateSession = (UnsafeNativeMethods.IDBCreateSessionCreateSession)Marshal.GetDelegateForFunctionPointer(method, typeof(UnsafeNativeMethods.IDBCreateSessionCreateSession));
                            constr.DangerousIDBCreateSessionCreateSession = CreateSession;
                        }

                        // if I have a delegate for CreateCommand directly ask for IDBCreateCommand
                        if (null != constr.DangerousIDBCreateCommandCreateCommand) {
                            // call IDBCreateSession::CreateSession via the delegate directly for IDBCreateCommand
                            hr = CreateSession(idbCreateSession, IntPtr.Zero, ref ODB.IID_IDBCreateCommand, ref sessionWrapper);
                            if ((0 <= hr) && !sessionWrapper.IsInvalid) {                                        
                                // double check the cached delegate is correct
                                sessionWrapper.VerifyIDBCreateCommand(constr);
                            }
                        }
                        else {
                            // otherwise ask for IUnknown (it may be first time usage or IDBCreateCommand not supported)
                            hr = CreateSession(idbCreateSession, IntPtr.Zero, ref ODB.IID_IUnknown, ref sessionWrapper);
                            if ((0 <= hr) && !sessionWrapper.IsInvalid) {
                                // and check support for IDBCreateCommand and create delegate for CreateCommand
                                sessionWrapper.QueryInterfaceIDBCreateCommand(constr);
                            }
                        }
                    }
                }
            }
            finally {
                if (IntPtr.Zero != idbCreateSession) {
                    // release the QI for IDBCreateSession
                    Marshal.Release(idbCreateSession);
                }
                if (mustRelease) {
                    // release the AddRef on DataLinks
                    DangerousRelease();
                }
            }
            return hr;
        }
        internal OleDbHResult InitializeAndCreateSession(OleDbConnectionString constr, ref SessionWrapper sessionWrapper)
        {
            OleDbHResult result;
            bool         success = false;
            IntPtr       zero    = IntPtr.Zero;

            RuntimeHelpers.PrepareConstrainedRegions();
            try
            {
                base.DangerousAddRef(ref success);
                IntPtr ptr = Marshal.ReadIntPtr(Marshal.ReadIntPtr(base.handle, 0), 0);
                UnsafeNativeMethods.IUnknownQueryInterface dangerousDataSourceIUnknownQueryInterface = constr.DangerousDataSourceIUnknownQueryInterface;
                if ((dangerousDataSourceIUnknownQueryInterface == null) || (ptr != Marshal.GetFunctionPointerForDelegate(dangerousDataSourceIUnknownQueryInterface)))
                {
                    dangerousDataSourceIUnknownQueryInterface        = (UnsafeNativeMethods.IUnknownQueryInterface)Marshal.GetDelegateForFunctionPointer(ptr, typeof(UnsafeNativeMethods.IUnknownQueryInterface));
                    constr.DangerousDataSourceIUnknownQueryInterface = dangerousDataSourceIUnknownQueryInterface;
                }
                ptr = Marshal.ReadIntPtr(Marshal.ReadIntPtr(base.handle, 0), 3 * IntPtr.Size);
                UnsafeNativeMethods.IDBInitializeInitialize dangerousIDBInitializeInitialize = constr.DangerousIDBInitializeInitialize;
                if ((dangerousIDBInitializeInitialize == null) || (ptr != Marshal.GetFunctionPointerForDelegate(dangerousIDBInitializeInitialize)))
                {
                    dangerousIDBInitializeInitialize        = (UnsafeNativeMethods.IDBInitializeInitialize)Marshal.GetDelegateForFunctionPointer(ptr, typeof(UnsafeNativeMethods.IDBInitializeInitialize));
                    constr.DangerousIDBInitializeInitialize = dangerousIDBInitializeInitialize;
                }
                result = dangerousIDBInitializeInitialize(base.handle);
                if ((OleDbHResult.S_OK > result) && (OleDbHResult.DB_E_ALREADYINITIALIZED != result))
                {
                    return(result);
                }
                result = (OleDbHResult)dangerousDataSourceIUnknownQueryInterface(base.handle, ref ODB.IID_IDBCreateSession, ref zero);
                if ((OleDbHResult.S_OK > result) || !(IntPtr.Zero != zero))
                {
                    return(result);
                }
                ptr = Marshal.ReadIntPtr(Marshal.ReadIntPtr(zero, 0), 3 * IntPtr.Size);
                UnsafeNativeMethods.IDBCreateSessionCreateSession dangerousIDBCreateSessionCreateSession = constr.DangerousIDBCreateSessionCreateSession;
                if ((dangerousIDBCreateSessionCreateSession == null) || (ptr != Marshal.GetFunctionPointerForDelegate(dangerousIDBCreateSessionCreateSession)))
                {
                    dangerousIDBCreateSessionCreateSession        = (UnsafeNativeMethods.IDBCreateSessionCreateSession)Marshal.GetDelegateForFunctionPointer(ptr, typeof(UnsafeNativeMethods.IDBCreateSessionCreateSession));
                    constr.DangerousIDBCreateSessionCreateSession = dangerousIDBCreateSessionCreateSession;
                }
                if (constr.DangerousIDBCreateCommandCreateCommand != null)
                {
                    result = dangerousIDBCreateSessionCreateSession(zero, IntPtr.Zero, ref ODB.IID_IDBCreateCommand, ref sessionWrapper);
                    if ((OleDbHResult.S_OK <= result) && !sessionWrapper.IsInvalid)
                    {
                        sessionWrapper.VerifyIDBCreateCommand(constr);
                    }
                    return(result);
                }
                result = dangerousIDBCreateSessionCreateSession(zero, IntPtr.Zero, ref ODB.IID_IUnknown, ref sessionWrapper);
                if ((OleDbHResult.S_OK <= result) && !sessionWrapper.IsInvalid)
                {
                    sessionWrapper.QueryInterfaceIDBCreateCommand(constr);
                }
            }
            finally
            {
                if (IntPtr.Zero != zero)
                {
                    Marshal.Release(zero);
                }
                if (success)
                {
                    base.DangerousRelease();
                }
            }
            return(result);
        }
        internal OleDbConnectionInternal(OleDbConnectionString constr, OleDbConnection connection) : base () {
#if DEBUG
            try { // use this to help validate this object is only created after the following permission has been previously demanded in the current codepath
                if (null != connection) {
                    connection.UserConnectionOptions.DemandPermission();
                }
                else {
                    constr.DemandPermission();
                }
            }
            catch(System.Security.SecurityException) {
                System.Diagnostics.Debug.Assert(false, "unexpected SecurityException for current codepath");
                throw;
            }
#endif
            Debug.Assert((null != constr) && !constr.IsEmpty, "empty connectionstring");
            ConnectionString = constr;

            if (constr.PossiblePrompt && !System.Environment.UserInteractive) {
                throw ODB.PossiblePromptNotUserInteractive();
            }

            try {
                // this is the native DataLinks object which pools the native datasource/session
                OleDbServicesWrapper wrapper = OleDbConnectionInternal.GetObjectPool();
                _datasrcwrp = new DataSourceWrapper();

                // DataLinks wrapper will call IDataInitialize::GetDataSource to create the DataSource
                // uses constr.ActualConnectionString, no InfoMessageEvent checking
                wrapper.GetDataSource(constr, ref _datasrcwrp);
                Debug.Assert(!_datasrcwrp.IsInvalid, "bad DataSource");

                // initialization is delayed because of OleDbConnectionStringBuilder only wants
                // pre-Initialize IDBPropertyInfo & IDBProperties on the data source
                if (null != connection) {
                    _sessionwrp = new SessionWrapper();

                    // From the DataSource object, will call IDBInitialize.Initialize & IDBCreateSession.CreateSession
                    // We always need both called so we use a single call for a single DangerousAddRef/DangerousRelease pair.
                    OleDbHResult hr = _datasrcwrp.InitializeAndCreateSession(constr, ref _sessionwrp);

                    // process the HResult here instead of from the SafeHandle because the possibility
                    // of an InfoMessageEvent.
                    if ((0 <= hr) && !_sessionwrp.IsInvalid) { // process infonessage events
                        OleDbConnection.ProcessResults(hr, connection, connection);
                    }
                    else {
                        Exception e = OleDbConnection.ProcessResults(hr, null, null);
                        Debug.Assert(null != e, "CreateSessionError");
                        throw e;
                    }
                    Debug.Assert(!_sessionwrp.IsInvalid, "bad Session");
                }
            }
            catch {
                if (null != _sessionwrp) {
                    _sessionwrp.Dispose();
                    _sessionwrp = null;
                }
                if (null != _datasrcwrp) {
                    _datasrcwrp.Dispose();
                    _datasrcwrp = null;
                }
                throw;
            }
        }
 internal OleDbHResult InitializeAndCreateSession(OleDbConnectionString constr, ref SessionWrapper sessionWrapper)
 {
     OleDbHResult result;
     bool success = false;
     IntPtr zero = IntPtr.Zero;
     RuntimeHelpers.PrepareConstrainedRegions();
     try
     {
         base.DangerousAddRef(ref success);
         IntPtr ptr = Marshal.ReadIntPtr(Marshal.ReadIntPtr(base.handle, 0), 0);
         UnsafeNativeMethods.IUnknownQueryInterface dangerousDataSourceIUnknownQueryInterface = constr.DangerousDataSourceIUnknownQueryInterface;
         if ((dangerousDataSourceIUnknownQueryInterface == null) || (ptr != Marshal.GetFunctionPointerForDelegate(dangerousDataSourceIUnknownQueryInterface)))
         {
             dangerousDataSourceIUnknownQueryInterface = (UnsafeNativeMethods.IUnknownQueryInterface) Marshal.GetDelegateForFunctionPointer(ptr, typeof(UnsafeNativeMethods.IUnknownQueryInterface));
             constr.DangerousDataSourceIUnknownQueryInterface = dangerousDataSourceIUnknownQueryInterface;
         }
         ptr = Marshal.ReadIntPtr(Marshal.ReadIntPtr(base.handle, 0), 3 * IntPtr.Size);
         UnsafeNativeMethods.IDBInitializeInitialize dangerousIDBInitializeInitialize = constr.DangerousIDBInitializeInitialize;
         if ((dangerousIDBInitializeInitialize == null) || (ptr != Marshal.GetFunctionPointerForDelegate(dangerousIDBInitializeInitialize)))
         {
             dangerousIDBInitializeInitialize = (UnsafeNativeMethods.IDBInitializeInitialize) Marshal.GetDelegateForFunctionPointer(ptr, typeof(UnsafeNativeMethods.IDBInitializeInitialize));
             constr.DangerousIDBInitializeInitialize = dangerousIDBInitializeInitialize;
         }
         result = dangerousIDBInitializeInitialize(base.handle);
         if ((OleDbHResult.S_OK > result) && (OleDbHResult.DB_E_ALREADYINITIALIZED != result))
         {
             return result;
         }
         result = (OleDbHResult) dangerousDataSourceIUnknownQueryInterface(base.handle, ref ODB.IID_IDBCreateSession, ref zero);
         if ((OleDbHResult.S_OK > result) || !(IntPtr.Zero != zero))
         {
             return result;
         }
         ptr = Marshal.ReadIntPtr(Marshal.ReadIntPtr(zero, 0), 3 * IntPtr.Size);
         UnsafeNativeMethods.IDBCreateSessionCreateSession dangerousIDBCreateSessionCreateSession = constr.DangerousIDBCreateSessionCreateSession;
         if ((dangerousIDBCreateSessionCreateSession == null) || (ptr != Marshal.GetFunctionPointerForDelegate(dangerousIDBCreateSessionCreateSession)))
         {
             dangerousIDBCreateSessionCreateSession = (UnsafeNativeMethods.IDBCreateSessionCreateSession) Marshal.GetDelegateForFunctionPointer(ptr, typeof(UnsafeNativeMethods.IDBCreateSessionCreateSession));
             constr.DangerousIDBCreateSessionCreateSession = dangerousIDBCreateSessionCreateSession;
         }
         if (constr.DangerousIDBCreateCommandCreateCommand != null)
         {
             result = dangerousIDBCreateSessionCreateSession(zero, IntPtr.Zero, ref ODB.IID_IDBCreateCommand, ref sessionWrapper);
             if ((OleDbHResult.S_OK <= result) && !sessionWrapper.IsInvalid)
             {
                 sessionWrapper.VerifyIDBCreateCommand(constr);
             }
             return result;
         }
         result = dangerousIDBCreateSessionCreateSession(zero, IntPtr.Zero, ref ODB.IID_IUnknown, ref sessionWrapper);
         if ((OleDbHResult.S_OK <= result) && !sessionWrapper.IsInvalid)
         {
             sessionWrapper.QueryInterfaceIDBCreateCommand(constr);
         }
     }
     finally
     {
         if (IntPtr.Zero != zero)
         {
             Marshal.Release(zero);
         }
         if (success)
         {
             base.DangerousRelease();
         }
     }
     return result;
 }