2011-08-16 40 views
2

有一個使用.NET Framework 3.5以C#編寫的WinForms應用程序。此應用程序使用其使用下面的聲明導入的C++ DLL:從給定的ODBC的DSN使用SQL Server數據庫從託管代碼調用時,C++ DLL崩潰

[DllImport(DllName)] 
public static unsafe extern int LoadDBData(String dsn, String userid, String password); 

這種方法導入數據。當數據庫中的數據太多時,調用會崩潰。這個extern dll的提供者說這是因爲dll無法獲取更多的堆大小,我的應用程序應該提供更多的堆內存。

我該如何解決這個問題?據我所知,從自動垃圾收集中排除組件的唯一可能性是我已經使用的不安全關鍵字。 任何想法,將不勝感激。

在此先感謝

馬丁

回答

0

這似乎是供應商的庫問題,而不是您的代碼。

託管和非託管內存應該被認爲是完全獨立的。託管內存通常是分配在垃圾回收堆上的內存,而非託管內存則是其他任何內容:通過malloc(3)分配的ANSI C內存池 ,自定義內存池和 CLI以外的垃圾分配堆執行...

請注意,上述報價是從Mono documentation,但我相信(如果我沒有弄錯)一般情況下,.NET也是如此。如果數據正在加載到DLL的內部數據結構中,那麼它應該分配它自己的內存。如果您提供的緩衝區將被填滿數據,那麼它將只填充您爲緩衝區分配的數據(並在編組之前固定)。那麼在哪裏加載數據?

+0

我也認爲這是供應商的庫問題。但是,由於我主要以託管代碼開發,供應商使他的意見不安。 但我試圖從excel makro調用庫,它也崩潰了。所以我相信這不是我在C#中調用的問題。 –

0

您不能在.NET增加堆大小。 您可以使用Process.Start在.NET應用程序調用的c/C++中創建EXE。 您的c/C++ EXE會調用DLL函數並返回結果(或者如果您有多個函數,它可能需要一個命令行參數)。如果你不想單獨的EXE,你可以嘗試使用RunDll32。

0

我懷疑這是特定於.NET,託管內存,垃圾回收等。它是一個本地DLL,因此它使用常規的非託管內存。當然,.NET運行時也會使用它的內存份額,但使用該DLL的本地應用程序也會這樣做。

如果您運行的是32位進程,則.NET和非託管代碼的總堆大小可限制爲1.5 GB。沒有附加信息很難說,但你可能達到了這個限度。

所以一個選擇是詢問你的供應商,他們是否有一個64位版本的庫並切換到64進程。在64位的過程中,內存幾乎是無限的(根據當今的標準)。

相關問題