2008-10-17 4 views
2

Я столкнулся с странной ошибкой чтения/записи памяти при вызове скомпилированной DLL из C#. Я использую DllImport, чтобы получить дескриптор функции, которая нам нужна, которая записывает возвращаемое значение параметрическому указателю на int (т. Е. Int * out). Эта функция вызывается несколько раз в потоке и успешно выполняется в течение срока службы первого потока. Однако, если один запускает другой поток после завершения первого, вызов внешней dll вызывает исключение AccessViolationException. Поскольку множественные вызовы из первого потока выполняются успешно, я думаю, что это как-то связано с первым потоком, не отбрасывающим указатели на соответствующие целочисленные параметры (?). Если да, то как я могу явным образом освободить эту память? Или, может быть, у кого-то есть другое представление о том, что может происходить здесь? Большое спасибо.Память AccessViolationException Ошибка вызова DLL из C#

EDIT: Дэнни запросил более подробную информацию, и я рад обязать вас. Вот где внешняя подпрограмма вызывается:

int success = -1; 
    unsafe 
    { 
     int res = 0; 
     int* res_ptr = &res; 
     int len = cmd.ToCharArray().Length; 
     int* len_ptr = &len; 
     CmdInterpreter(ref cmd, len_ptr, res_ptr); 
     success = *res_ptr; 
    } 

Где CmdInterpreter определяется как:

[DllImport("brugs.dll", EntryPoint="CmdInterpreter", 
     ExactSpelling=false, CallingConvention = CallingConvention.StdCall)] 
    public static unsafe extern void CmdInterpreter(ref string cmd, int *len, int *res); 

Пожалуйста, дайте мне знать, если есть какая-либо дополнительная информация, которая будет полезна. Спасибо!

+0

Нужны некоторые образцы кода. Это недостаточно специфично. Нам нужно увидеть вашу реализацию (т. Е. Ваш код C#, который вызывается), чтобы помочь. – TheSmurf 2008-10-17 13:44:04

+0

Можете ли вы показать нам собственный код? Глядя на функцию DLLImport, я считаю, что у вас есть ошибка, но я не могу быть уверен, пока не увижу родную подпись – JaredPar 2008-10-17 16:58:28

ответ

1

Учитывая, что проблема возникает только при задействовании нескольких потоков, возможно, что DLL командной интерпретатор использует какое-то локальное хранилище потоков и делает это неправильно. Это также может иметь отношение к состоянию инициализации COM второго потока (тот, который генерирует ошибку).

Было бы интересно узнать, что произойдет, если вы запустите свой новый поток и вызовите его в DLL до того, как совершит любые вызовы в DLL в вашем первом/основном потоке. Если он работает, это может поддержать теорию локального хранилища потоков. Если это не удастся, это будет поддерживать теорию состояния COM.

Смежные вопросы