Гость
Целевая тема:
Создать новую тему:
Автор:
Форумы / WinForms, .Net Framework [игнор отключен] [закрыт для гостей] / Как правильно передать указатель в функцию из dll / 11 сообщений из 11, страница 1 из 1
11.01.2013, 03:41
    #38105746
Random2
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно передать указатель в функцию из dll
Добрый день. Есть подключаемая к проекту на C# длл с нужной мне функцией. Функция принимает два параметра - адреса буфферов типа byte. Так как синтаксис и принципы написания программ в C# заметно отличаются от C++, возникли трудности - не получается получить адресс выделенного буффера. Подскажите, что я не так делаю?

Код: c#
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
//Функцию из длл описал так:
        [DllImport("genmd5.dll")]
        public static extern unsafe void procMD5hash(int pTempBuffer, int pHashBuffer);

//Пытаюсь вызвать:
        byte[] TempBuffer = new byte[255];
        byte[] HashBuffer = new byte[255];

        fixed (int *PTempBuffer = &TempBuffer)
        {
            fixed (int *PHashBuffer = &HashBuffer)
            {
                procMD5hash(PTempBuffer, PHashBuffer);
                lblHash.Text = Convert.ToString(HashBuffer);
            }
        }
...
Рейтинг: 0 / 0
11.01.2013, 10:36
    #38105938
bazile
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно передать указатель в функцию из dll
Random2,

p/invoke сам умеет работать с массивами, поэтому можно написать так:
Код: c#
1.
2.
3.
4.
5.
6.
7.
[DllImport("genmd5.dll")]
public static extern unsafe void procMD5hash(byte[] tempBuffer, byte[] hashBuffer);
...
byte[] TempBuffer = new byte[255];
byte[] HashBuffer = new byte[255];
procMD5hash(TempBuffer, HashBuffer);
lblHash.Text = Convert.ToString(HashBuffer);



fixed не нужен т.к. он будет сделан автоматически в этом случае. На будущее имей в виду что для ручной передачи указателя есть тип IntPtr.

P.S. Для расчета md5 в .NET есть класс MD5CryptoServiceProvider .
...
Рейтинг: 0 / 0
11.01.2013, 11:58
    #38106105
beg-in-er
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно передать указатель в функцию из dll
Можно как bazile прделожил, а можно и так.
надо взять новый, не зафиксированный указатель от fixed int *PHashBuffer и будет щастье
Код: c#
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
//Функцию из длл описал так:
        [DllImport("genmd5.dll")]
        public static extern unsafe void procMD5hash(int* pTempBuffer, int* pHashBuffer); //<===

//Пытаюсь вызвать:

        byte[] TempBuffer = new byte[255];
        byte[] HashBuffer = new byte[255];

        fixed (int *PTempBuffer = &TempBuffer)
        {
            fixed (int *PHashBuffer = &HashBuffer)
            {
                int* PT=PTempBuffer ;  //<===
                int* PH=PHashBuffer ;  //<===
                procMD5hash(PT, PH);
                lblHash.Text = Convert.ToString(HashBuffer);
            }
        }
...
Рейтинг: 0 / 0
11.01.2013, 17:34
    #38106824
Random2
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно передать указатель в функцию из dll
bazile ,
Исправил, но уже при выполнении программы получил другую ошибку:
"Attempted to read or write protected memory. This is often an indication that other memory is corrupt."
Что имеется ввиду под защищенной памятью?
Насчет класса MD5CryptoServiceProvider в курсе, но мне нужно именно из длл вызвать функцию.

beg-in-er ,
Не выходит, на этой и следующей строках
Код: c#
1.
2.
fixed (int* PTempBuffer = &TempBuffer)
fixed (int* PHashBuffer = &HashBuffer)


error CS0208: Cannot take the address of, get the size of, or declare a pointer to a managed type ('byte[]')
error CS0266: Cannot implicitly convert type 'byte[]*' to 'int*'. An explicit conversion exists (are you missing a cast?)
...
Рейтинг: 0 / 0
11.01.2013, 18:17
    #38106898
bazile
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно передать указатель в функцию из dll
Random2, процессор и ОС имеют механизмы защиты памяти позволящие указать уровень доступа - чтение/запись. Если такая ошибка возникает в программе, то причины могут быть разные. Возможно соглашение о вызове (calling convention) надо указать. Возможно твоя функция неправильно работает с памятью. Тогда надо её исправлять.

Random2Насчет класса MD5CryptoServiceProvider в курсе, но мне нужно именно из длл вызвать функцию.
Зачем, если не секрет?
...
Рейтинг: 0 / 0
11.01.2013, 19:38
    #38106988
beg-in-er
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно передать указатель в функцию из dll
Random2,

beg-in-er, Не выходит, на этой и следующей строках
я быстро делал , не сразу посмотрел. просто ваш код переделал. думал у вас всё в коде в порядке
естественно не будет.
вот отплиленная и копилирующая тема.
Код: c#
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
  [DllImport("genmd5.dll")]
        public static extern unsafe void procMD5hash(int* pTempBuffer, int* pHashBuffer); //<===

//Пытаюсь вызвать:
         public unsafe void dd()
         {
             byte[] TempBuffer = new byte[255];
             byte[] HashBuffer = new byte[255];

             fixed (byte* PTempBuffer = TempBuffer)
             {
                 fixed (byte* PHashBuffer = HashBuffer)
                 {
                     int* PT =(int*) PTempBuffer;  //<===
                     int* PH = (int*)PHashBuffer;  //<===
                     procMD5hash(PT, PH);
                 }
             }
         }



или вот точно работающий вариант.
Код: c#
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
//mydll.cpp
EXPORT int ZZZZ(int* nn, int* nn2,int a1, int a2,int size)
{
      int Bingo=0;
      int sz=size;
      for (int q = 0; q < sz; q++)
     {
     }
     return Bingo;
}

//usemydll.cs
[DllImport(@"Mydll.dll")]
public static extern int ZZZZ(int* n1,int* n2, int a1, int a2,int size);

int[] NN1 = new int[95000];
int[] NN2 = new int[95000];
unsafe zzzz()
{
 int result;
 fixed (int* N1 = NN1)
            {
                fixed (int* N2 = NN2)
                {
                    int* n1 = N1;
                    int* n2 = N2;
                    result= ZZZZ(n1, n2, 30000, 0, NN1.Length);
                    
                }
            }
}



кстати , а подо что компилите. под х86 или под х64. указатели там же разные.
...
Рейтинг: 0 / 0
13.01.2013, 01:17
    #38108058
Random2
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно передать указатель в функцию из dll
bazile,
Нужна максимальная скорость. А стандартная C# функция позволяет получить около 100 000 хешей в секунду.

beg-in-er,
Пробовал и x32 и x64 - все равно получал ошибку. Попробовал ваш код под х32 - теперь все ОК, но все равно иногда получаю или неправильные хеши или ошибки. Тут уже дело, я думаю в самой dll-ке.

Спасибо вам большое за помощь, ушел искать причину в коде dll.
...
Рейтинг: 0 / 0
13.01.2013, 02:35
    #38108079
beg-in-er
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно передать указатель в функцию из dll
Random2bazile,
Нужна максимальная скорость. А стандартная C# функция позволяет получить около 100 000 хешей в секунду.

try it. вроде больше ляма в секунду выдаёт
Код: c#
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
   public unsafe static int Get_Hash_Code(string s)
        {
            List<char> cc = new List<char>();
            for (int i = 0; i < s.Length; i++) cc.Add(s[i]);
            fixed (char* str = &(cc.ToArray())[0])
            {
                int num3;
                char* chPtr = str;
                int num = 0x1505;
                int num2 = num;
                for (char* chPtr2 = chPtr; (num3 = chPtr2[0]) != '\0'; chPtr2 += 2)
                {
                    num = ((num << 5) + num) ^ num3;
                    num3 = chPtr2[1];
                    if (num3 == 0) break;

                    num2 = ((num2 << 5) + num2) ^ num3;
                }
                int k = (num + (num2 * 0x5d588b65));
                return (num + (num2 * 0x5d588b65));
            }

            return 1;
        }
...
Рейтинг: 0 / 0
15.01.2013, 02:47
    #38110199
Random2
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно передать указатель в функцию из dll
beg-in-er,

Что-то не очень похоже на вычисление MD5 строки. Хотябы даже потому, что тип возвращаемого значения - int. Даже если перевести результат из dec в hex, все равно и близко не похоже на MD5 Хеш. Или есть какие-нибудь тонкости работы с этой функцией?
...
Рейтинг: 0 / 0
15.01.2013, 14:23
    #38110721
bazile
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно передать указатель в функцию из dll
Random2, пример приведенный beg-in-er-ом точно не md5 вычисляет
...
Рейтинг: 0 / 0
15.01.2013, 14:35
    #38110735
beg-in-er
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно передать указатель в функцию из dll
Random2beg-in-er,

Что-то не очень похоже на вычисление MD5 строки. Хотябы даже потому, что тип возвращаемого значения - int. Даже если перевести результат из dec в hex, все равно и близко не похоже на MD5 Хеш. Или есть какие-нибудь тонкости работы с этой функцией?
а , в запарке был , среагировал на "Хэшкод" )))
а по MD5 Есть же куча открытых реализаций , в частности куча открытых реализаций
берите и пользуйтесь .
...
Рейтинг: 0 / 0
Форумы / WinForms, .Net Framework [игнор отключен] [закрыт для гостей] / Как правильно передать указатель в функцию из dll / 11 сообщений из 11, страница 1 из 1
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]