Передача параметров в DLL [masm32]

Тема в разделе "WASM.BEGINNERS", создана пользователем ActioN, 20 май 2007.

  1. Quantum

    Quantum Паладин дзена

    Публикаций:
    0
    Регистрация:
    6 янв 2003
    Сообщения:
    3.143
    Адрес:
    Ukraine
    ActioN
    Совершенно верно. Тот lib - библиотека импорта для dll, а вовсе не статическая либа. Статическую либу нужно собирать отдельно. Для этого первым делом можно убрать DllMain, т.к. эта функция уже не будет вызываться. Потом компилируем исходник также как и для DLL, т.е. так:

    ml /c /coff source.asm

    Потом кладём обьектник(и) в lib:

    lib *.obj /out:mystaticlib.lib

    Получаем mystaticlib.lib - это уже нормальная статическая библиотека.

    Дальше, для использования этой библиотеки в другом проекте нужно обратить внимание на 2 момента:

    1. Компилятору (ml.exe) дела нет до библиотек (статических и динамических). Директива includelib всего лишь указывает, что в обьектник нужно поместить нечто вроде комментария для линкера, что, мол, такая-то либа, возможно, понадобится в процессе линковки, но не более. Можете вообще не использовать includelib, а явно указывать имя (и путь) ко всем библиотекам в командной строке линкера. Компилятор следит за тем, чтобы все имена символов соответствовали либо внутренним символам (например, функции, которые обьявлены внутри данного модуля), либо внешним, но разбираться со внешними символами будет уже линкер. Поэтому, ошибку в данном случае выдаёт не компилятор, а линкер!

    2. Имена символов должны соответствовать полностью. _TestProc@0 и _TestProc@4 - это 2 совершенно разных символа для линкера. Исправьте исходник библиотеки, чтобы функция называлась так, как того требует линкер, т.е. _TestProc@4, а не _TestProc@0.
     
  2. ActioN

    ActioN New Member

    Публикаций:
    0
    Регистрация:
    1 апр 2005
    Сообщения:
    160
    Адрес:
    Ukraine
    Quantum, спасибо. Доступно объяснил. Собрал нормальную библиотеку. Теперь все работает. А эти dll и lib-файлы можно использовать на VC++?
     
  3. RamMerLabs

    RamMerLabs Well-Known Member

    Публикаций:
    0
    Регистрация:
    11 сен 2006
    Сообщения:
    1.412
    канешна можно.
     
  4. ActioN

    ActioN New Member

    Публикаций:
    0
    Регистрация:
    1 апр 2005
    Сообщения:
    160
    Адрес:
    Ukraine
    А если я на асме передавал через стек параметр, то как это в вижуале сделать (передать адресс строки)?
    Вариант со статистической lib-библиотекой:
    Код (Text):
    1. #include <windows.h>
    2. extern "C"__stdcall TestProc();
    3. int main()
    4. {
    5.     char Message[]="This is the string";
    6.     __asm
    7.     {
    8.         lea  esi,Message
    9.         push esi
    10.     }
    11.     TestProc();
    12.     return 0;
    13. }
     
  5. ActioN

    ActioN New Member

    Публикаций:
    0
    Регистрация:
    1 апр 2005
    Сообщения:
    160
    Адрес:
    Ukraine
    Почему-то в случае и со статистической и с динамической либами после выполнения функции из библиотеки вижуал выдает ошибку, что мол значение esp небыло сохранено (во время или перед) вызовом функции. Вот код с использованием dll:
    Код (Text):
    1. #include <windows.h>
    2. int main()
    3. {
    4.     char Message[]="This is the string";
    5.     HINSTANCE hDll;
    6.  
    7.     typedef void (*TestProcProto)();
    8.     hDll = LoadLibrary("tstdll.dll");
    9.     TestProcProto TestProc = (TestProcProto)GetProcAddress(hDll,"TestProc");
    10.     __asm
    11.     {
    12.         lea  esi,Message
    13.         push esi
    14.     }
    15.  
    16.     TestProc();
    17.     return 0;
    18. }
    А это исходный код либы:
    Код (Text):
    1.     .386
    2.     .model flat, stdcall
    3.     option casemap:none
    4.     include \masm32\include\windows.inc
    5.     include \masm32\include\user32.inc
    6.     include \masm32\include\kernel32.inc
    7.     includelib \masm32\lib\user32.lib
    8.     includelib \masm32\lib\kernel32.lib
    9. .data
    10. strBuf db 512 dup(0)
    11. .code
    12. startLib:
    13. TestProc proc
    14.     mov esi,[esp+4]
    15.     invoke lstrlen,esi
    16.     dec eax
    17.     mov ecx,eax
    18.     xor ebx,ebx
    19.  
    20.     lblStart:
    21.         mov al,byte ptr[esi+ecx]
    22.         dec ecx
    23.         cmp al,0
    24.         je  lblEnd
    25.         cmp al,' '
    26.         je  lblStart
    27.         mov byte ptr [strBuf+ebx],al
    28.         inc ebx
    29.         jmp lblStart
    30.  
    31.     lblEnd:
    32.  
    33.     invoke MessageBox,NULL,addr strBuf,0,MB_OK
    34.     ret
    35.  
    36. TestProc endp
    37. end startLib
     
  6. RamMerLabs

    RamMerLabs Well-Known Member

    Публикаций:
    0
    Регистрация:
    11 сен 2006
    Сообщения:
    1.412
    Код (Text):
    1. __asm
    2.     {
    3.         lea  esi,Message
    4.         push esi
    5.     }
    6.  
    7.     TestProc();
    ассемблер можно не мучать.
     
  7. MSoft

    MSoft New Member

    Публикаций:
    0
    Регистрация:
    16 дек 2006
    Сообщения:
    2.854
    не знаю, то или нет, но в синтаксисе Си за очистку стека отвечает тот, кто вызывал функцию, а не сама вызванная функция. Думаю, проблема в этом.
     
  8. ActioN

    ActioN New Member

    Публикаций:
    0
    Регистрация:
    1 апр 2005
    Сообщения:
    160
    Адрес:
    Ukraine
    Чтобы не использовать ассемблерных вставок на вижуале, пришлось изменить функции в dll и lib-файлах на функции с одним параметром.
    Quantum и все, кто помагал - огромное спасибо.