Ejemplo n.º 1
0
        internal unsafe void GetDataSource(OleDbConnectionString constr, ref DataSourceWrapper datasrcWrapper)
        {
            OleDbHResult hr;

            UnsafeNativeMethods.IDataInitializeGetDataSource GetDataSource = DangerousIDataInitializeGetDataSource !;
            bool mustRelease = false;

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

                // this is the string that DataLinks / OLE DB Services will use to create the provider
                string connectionString = constr.ActualConnectionString !;

                // base.handle is the 'this' pointer for making the COM call to GetDataSource
                // the datasrcWrapper will store the IID_IDBInitialize pointer
                // call IDataInitiailze::GetDataSource via the delegate
                fixed(char *connectionStringPtr = connectionString)
                fixed(Guid * riid = &ODB.IID_IDBInitialize)
                {
                    bool addRefd = false;
                    DataSourceWrapper newWrapper = new DataSourceWrapper();

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

                    try
                    {
                        hr = GetDataSource(base.handle, IntPtr.Zero, ODB.CLSCTX_ALL, connectionStringPtr, riid, &handle);
                    }
                    finally
                    {
                        if (addRefd)
                        {
                            datasrcWrapper.DangerousRelease();
                        }
                        if (handle != originalHandle)
                        {
                            Marshal.InitHandle(newWrapper, handle);
                            datasrcWrapper = newWrapper;
                        }
                    }
                }
            }
            finally
            {
                if (mustRelease)
                {
                    DangerousRelease();
                }
            }
            if (hr < 0)
            { // ignore infomsg
                if (OleDbHResult.REGDB_E_CLASSNOTREG == hr)
                {
                    throw ODB.ProviderUnavailable(constr.Provider, null);
                }
                Exception?e = OleDbConnection.ProcessResults(hr, null, null);
                Debug.Assert(null != e, "CreateProviderError");
                throw e;
            }
            else if (datasrcWrapper.IsInvalid)
            {
                SafeNativeMethods.Wrapper.ClearErrorInfo();
                throw ODB.ProviderUnavailable(constr.Provider, null);
            }
            Debug.Assert(!datasrcWrapper.IsInvalid, "bad DataSource");
        }