Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Низкоуровневое программирование > Assembler - Ассемблер (FASM, MASM, WASM, NASM, GoASM, Gas, RosAsm, HLA) и не рекомендуем TASM
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 06.12.2014, 16:30   #1
Женька Good
Форумчанин
 
Регистрация: 15.03.2011
Сообщений: 126
По умолчанию Явное связывание при вызове библиотеки

пытаюсь разобраться с примером работы с dll-библиотекой при явнос связывании. Проверяю работу с помощью OllyDBG. После вызова GetProcAdress EIP = 0 и eax=0. После выделенной проверки выход в _freelibrry. Помогите доработать)

Код:
.486
 
OPTION CASEMAP:NONE
.MODEL FLAT, STDCALL

INCLUDE C:\MASM32\INCLUDE\WINDOWS.INC
INCLUDE C:\MASM32\INCLUDE\KERNEL32.INC
INCLUDE C:\MASM32\INCLUDE\USER32.INC
INCLUDE C:\MASM32\INCLUDE\masm32.INC
INCLUDE C:\MASM32\macros\macros.asm
 
INCLUDELIB C:\MASM32\LIB\KERNEL32.LIB
INCLUDELIB C:\MASM32\LIB\USER32.LIB
INCLUDELIB C:\MASM32\LIB\masm32.lib
 
.data
   
stroka     db   'afjkffFfjkghfjkj',0
podstroka    db   'fjk',0
rezultat    db    256 DUP ( 0 )                                      
dll_imya    db  'myDll.dll', 0 
proc_name   db  '_stroki_podstroki@12',0
dll_id      dd  ?
proc_addr   dd  ?
 
.code 
 
start:
 
      PUSH OFFSET dll_imya
      CALL LoadLibrary
      MOV dll_id, EAX
 
      CMP EAX, 0
      JZ  _end
 
      PUSH OFFSET proc_name
      PUSH dll_id
 
      CALL GetProcAddress
 
      MOV proc_addr, EAX
 
      CMP EAX, 0 
      JZ _freeLibrary
 
      PUSH OFFSET rezultat
      PUSH OFFSET podstroka
      PUSH OFFSET stroka
      
      CALL proc_addr
 
      PUSH dll_id
     
     PUSH MB_OK
      PUSH OFFSET stroka
      PUSH OFFSET rezultat
      PUSH 0
      CALL MessageBoxA
      
      
_freeLibrary:
      CALL FreeLibrary
 
_end:     
      PUSH 0
     CALL ExitProcess
 
end start
Женька Good вне форума Ответить с цитированием
Старый 06.12.2014, 18:20   #2
waleri
Старожил
 
Регистрация: 13.07.2012
Сообщений: 6,330
По умолчанию

А вы уверены, что в myDll есть функция с таким именем?
Кроме того, при возникновении ошибок можно вызвать GetLastError и посмотреть на код ошибки.
waleri вне форума Ответить с цитированием
Старый 06.12.2014, 18:32   #3
Женька Good
Форумчанин
 
Регистрация: 15.03.2011
Сообщений: 126
По умолчанию

Цитата:
Сообщение от waleri Посмотреть сообщение
А вы уверены, что в myDll есть функция с таким именем?
Кроме того, при возникновении ошибок можно вызвать GetLastError и посмотреть на код ошибки.
и так пробовал, но все то же самое(
Код:
proc_name   db  '_pod_prog@12',0
GetLastError куда записать для проверки?
Женька Good вне форума Ответить с цитированием
Старый 06.12.2014, 19:30   #4
AbakBarama
Пользователь
 
Регистрация: 12.05.2011
Сообщений: 57
По умолчанию

Цитата:
Сообщение от Женька Good Посмотреть сообщение
Проверяю работу с помощью OllyDBG.
Так посмотрите в OllyDbg, как на самом деле называется ваша экспортируемая функция. Там можно легко увидеть список имен любой загруженной DLL. Скорее всего, на конце не должно быть "@12".

И на вызов FreeLibrary внимание обратите, функции должен параметр передаваться, а он либо передается, либо нет, в зависимости от того, как к ней перешли.
AbakBarama на форуме Ответить с цитированием
Старый 06.12.2014, 19:42   #5
Женька Good
Форумчанин
 
Регистрация: 15.03.2011
Сообщений: 126
По умолчанию

Цитата:
Сообщение от AbakBarama Посмотреть сообщение
Так посмотрите в OllyDbg, как на самом деле называется ваша экспортируемая функция. Там можно легко увидеть список имен любой загруженной DLL. Скорее всего, на конце не должно быть "@12".

И на вызов FreeLibrary внимание обратите, функции должен параметр передаваться, а он либо передается, либо нет, в зависимости от того, как к ней перешли.
вот из олли
Женька Good вне форума Ответить с цитированием
Старый 07.12.2014, 07:16   #6
Mikl___
Участник клуба
 
Регистрация: 11.01.2010
Сообщений: 1,139
По умолчанию

Женька Good,
три темы об одном и том же, для чего их плодить?
  1. создаешь ЕХЕ-файл со встроенной внутрь функцией и УБЕЖДАЕШЬСЯ в том, что программа работает ТАК как нужно (у меня честно говоря зародились сомнения)
    Код:
    ; masm windows gui #
    .386
    .model flat, stdcall
    option casemap:none
    include \masm32\include\windows.inc
    include \masm32\include\kernel32.inc
    include \masm32\include\user32.inc
    includelib \masm32\lib\user32.lib
    includelib \masm32\lib\kernel32.lib
    .data
    MsgCaption      db "поиск подстроки в строке",0
    buffer      db 100 dup (0)
    str1     db    "six little rat cubs, big rat and three old rats",0
    str2     db    "rat",0
    template db "найдено %d вхождения подстроки str1 в строку str2",0
    count dd 0
    
    .code
    start:  call strfind
    	invoke wsprintf,addr buffer,addr template,eax
    	invoke MessageBox, NULL,addr buffer, addr MsgCaption, MB_OK
    	invoke ExitProcess,NULL
    strfind proc
    	push ebx
    	push esi
    	push edi
    	invoke lstrlen, addr str2
    	dec eax
    	mov ebx,eax
    	invoke lstrlen, addr str1
    	mov ecx,eax
    	mov edi,offset str1
    a2:	mov al,str2[0]
    	repne scasb
    	jecxz exit
    	push ecx
    	mov esi,offset str2+1
    	mov ecx,ebx
    	repe cmpsb
    	jne a1
    	inc count
    	sub [esp],ebx
    a1:	pop ecx
    	or ecx,ecx
    	jne a2
    exit:	mov eax,count
    	pop edi
    	pop esi
    	pop ebx
    	ret
    strfind endp
    end start
  2. на основе ОТЛАЖЕННОЙ функции создаю файл 3.asm
    Код:
    ; masm windows gui #
    .386
    .model flat, stdcall
    option casemap:none
    include \masm32\include\windows.inc
    include \masm32\include\kernel32.inc
    include \masm32\include\user32.inc
    includelib \masm32\lib\user32.lib
    includelib \masm32\lib\kernel32.lib
    .data
    str1	db "six little rat cubs, big rat and three old rats",0
    str2	db "rat",0
    count dd 0
    
    .code
    DllEntry proc hInstance:HINSTANCE, reason:DWORD, reserved1:DWORD
    	mov eax,TRUE
    	ret
    DllEntry endp
    strfind proc
    	push ebx
    	push esi
    	push edi
    	invoke lstrlen, addr str2
    	dec eax
    	mov ebx,eax
    	invoke lstrlen, addr str1
    	mov ecx,eax
    	mov edi,offset str1
    a2:	mov al,str2[0]
    	repne scasb
    	jecxz exit
    	push ecx
    	mov esi,offset str2+1
    	mov ecx,ebx
    	repe cmpsb
    	jne a1
    	inc count
    	sub [esp],ebx
    a1:	pop ecx
    	or ecx,ecx
    	jne a2
    exit:	mov eax,count
    	pop edi
    	pop esi
    	pop ebx
    	ret
    strfind endp
    end DllEntry
    файл 3.def
    Код:
    LIBRARY 3
    EXPORTS strfind
    и bat-файл
    Код:
    @echo off
    \masm32\bin\ml /c /coff /Cp 3.asm
    \masm32\bin\link /DLL /DEF:3.def /SUBSYSTEM:WINDOWS /LIBPATH:\masm32\lib 3.obj
    после запуска bat-файла появятся 3.obj, 3.dll, 3.exp, 3.lib, 3.obj
  3. создаем 4.asm
    Код:
    ; masm windows gui #
    .386
    .model flat, stdcall
    option casemap:none
    include \masm32\include\windows.inc
    include \masm32\include\kernel32.inc
    include \masm32\include\user32.inc
    includelib \masm32\lib\user32.lib
    includelib \masm32\lib\kernel32.lib
    .data
    MsgCaption      db "поиск подстроки в строке",0
    buffer      db 100 dup (0)
    template db "найдено %d вхождения подстроки str1 в строку str2",0
    LibName db "3.dll",0
    FunctionName db "strfind",0
    DllNotFound db "Cannot load library",0
    AppName db "Load Library",0
    FunctionNotFound db "strfind function not found",0
    .data?
    hLib dd ?
    strfind dd ?
    .code
    start:
    	invoke LoadLibrary,addr LibName
            .if eax==NULL
                    invoke MessageBox,NULL,addr DllNotFound,addr AppName,MB_OK
            .else
                    mov hLib,eax
                    invoke GetProcAddress,hLib,addr FunctionName
                    .if eax==NULL
                            invoke MessageBox,NULL,addr FunctionNotFound,addr AppName,MB_OK
                    .else
                            mov strfind,eax
                            call [strfind]
    	invoke wsprintf,addr buffer,addr template,eax
    	invoke MessageBox, NULL,addr buffer, addr MsgCaption, MB_OK
                    .endif
                    invoke FreeLibrary,hLib
            .endif
    	invoke ExitProcess,NULL
    end start
    файл 3.dll должен быть в той же папке, что и файл 4.exe
  4. ENJOY!
Mikl___ вне форума Ответить с цитированием
Старый 07.12.2014, 11:48   #7
Женька Good
Форумчанин
 
Регистрация: 15.03.2011
Сообщений: 126
По умолчанию

Цитата:
Сообщение от Mikl___ Посмотреть сообщение
Женька Good,
три темы об одном и том же, для чего их плодить?
  1. создаешь ЕХЕ-файл со встроенной внутрь функцией и УБЕЖДАЕШЬСЯ в том, что программа работает ТАК как нужно (у меня честно говоря зародились сомнения)
    Код:
    ; masm windows gui #
    .386
    .model flat, stdcall
    option casemap:none
    include \masm32\include\windows.inc
    include \masm32\include\kernel32.inc
    include \masm32\include\user32.inc
    includelib \masm32\lib\user32.lib
    includelib \masm32\lib\kernel32.lib
    .data
    MsgCaption      db "поиск подстроки в строке",0
    buffer      db 100 dup (0)
    str1     db    "six little rat cubs, big rat and three old rats",0
    str2     db    "rat",0
    template db "найдено %d вхождения подстроки str1 в строку str2",0
    count dd 0
    
    .code
    start:  call strfind
    	invoke wsprintf,addr buffer,addr template,eax
    	invoke MessageBox, NULL,addr buffer, addr MsgCaption, MB_OK
    	invoke ExitProcess,NULL
    strfind proc
    	push ebx
    	push esi
    	push edi
    	invoke lstrlen, addr str2
    	dec eax
    	mov ebx,eax
    	invoke lstrlen, addr str1
    	mov ecx,eax
    	mov edi,offset str1
    a2:	mov al,str2[0]
    	repne scasb
    	jecxz exit
    	push ecx
    	mov esi,offset str2+1
    	mov ecx,ebx
    	repe cmpsb
    	jne a1
    	inc count
    	sub [esp],ebx
    a1:	pop ecx
    	or ecx,ecx
    	jne a2
    exit:	mov eax,count
    	pop edi
    	pop esi
    	pop ebx
    	ret
    strfind endp
    end start
  2. на основе ОТЛАЖЕННОЙ функции создаю файл 3.asm
    Код:
    ; masm windows gui #
    .386
    .model flat, stdcall
    option casemap:none
    include \masm32\include\windows.inc
    include \masm32\include\kernel32.inc
    include \masm32\include\user32.inc
    includelib \masm32\lib\user32.lib
    includelib \masm32\lib\kernel32.lib
    .data
    str1	db "six little rat cubs, big rat and three old rats",0
    str2	db "rat",0
    count dd 0
    
    .code
    DllEntry proc hInstance:HINSTANCE, reason:DWORD, reserved1:DWORD
    	mov eax,TRUE
    	ret
    DllEntry endp
    strfind proc
    	push ebx
    	push esi
    	push edi
    	invoke lstrlen, addr str2
    	dec eax
    	mov ebx,eax
    	invoke lstrlen, addr str1
    	mov ecx,eax
    	mov edi,offset str1
    a2:	mov al,str2[0]
    	repne scasb
    	jecxz exit
    	push ecx
    	mov esi,offset str2+1
    	mov ecx,ebx
    	repe cmpsb
    	jne a1
    	inc count
    	sub [esp],ebx
    a1:	pop ecx
    	or ecx,ecx
    	jne a2
    exit:	mov eax,count
    	pop edi
    	pop esi
    	pop ebx
    	ret
    strfind endp
    end DllEntry
    файл 3.def
    Код:
    LIBRARY 3
    EXPORTS strfind
    и bat-файл
    Код:
    @echo off
    \masm32\bin\ml /c /coff /Cp 3.asm
    \masm32\bin\link /DLL /DEF:3.def /SUBSYSTEM:WINDOWS /LIBPATH:\masm32\lib 3.obj
    после запуска bat-файла появятся 3.obj, 3.dll, 3.exp, 3.lib, 3.obj
  3. создаем 4.asm
    Код:
    ; masm windows gui #
    .386
    .model flat, stdcall
    option casemap:none
    include \masm32\include\windows.inc
    include \masm32\include\kernel32.inc
    include \masm32\include\user32.inc
    includelib \masm32\lib\user32.lib
    includelib \masm32\lib\kernel32.lib
    .data
    MsgCaption      db "поиск подстроки в строке",0
    buffer      db 100 dup (0)
    template db "найдено %d вхождения подстроки str1 в строку str2",0
    LibName db "3.dll",0
    FunctionName db "strfind",0
    DllNotFound db "Cannot load library",0
    AppName db "Load Library",0
    FunctionNotFound db "strfind function not found",0
    .data?
    hLib dd ?
    strfind dd ?
    .code
    start:
    	invoke LoadLibrary,addr LibName
            .if eax==NULL
                    invoke MessageBox,NULL,addr DllNotFound,addr AppName,MB_OK
            .else
                    mov hLib,eax
                    invoke GetProcAddress,hLib,addr FunctionName
                    .if eax==NULL
                            invoke MessageBox,NULL,addr FunctionNotFound,addr AppName,MB_OK
                    .else
                            mov strfind,eax
                            call [strfind]
    	invoke wsprintf,addr buffer,addr template,eax
    	invoke MessageBox, NULL,addr buffer, addr MsgCaption, MB_OK
                    .endif
                    invoke FreeLibrary,hLib
            .endif
    	invoke ExitProcess,NULL
    end start
    файл 3.dll должен быть в той же папке, что и файл 4.exe
  4. ENJOY!
Вооу, спасибо!!!
подскажите как еще вывести номера позиций вхождений подстроки в строку?
Женька Good вне форума Ответить с цитированием
Старый 07.12.2014, 12:48   #8
Mikl___
Участник клуба
 
Регистрация: 11.01.2010
Сообщений: 1,139
По умолчанию

Женька Good,
  1. ни к чему цитировать всё сообщение целиком
  2. перечитай моё сообщение еще раз, переделай встроенную функцию так, что бы она "выводила номера позиций вхождений подстроки в строку"
  3. далее по аналогии САМОСТОЯТЕЛЬНО
Mikl___ вне форума Ответить с цитированием
Старый 08.12.2014, 18:43   #9
Женька Good
Форумчанин
 
Регистрация: 15.03.2011
Сообщений: 126
По умолчанию

Цитата:
Сообщение от Женька Good Посмотреть сообщение
Вооу, спасибо!!!
подскажите как еще вывести номера позиций вхождений подстроки в строку?
могли бы вы помочь переделать так, чтобы параметры передавались в функцию согласно конвенции STDCALL?
Женька Good вне форума Ответить с цитированием
Старый 09.12.2014, 03:16   #10
Mikl___
Участник клуба
 
Регистрация: 11.01.2010
Сообщений: 1,139
По умолчанию

Женька Good,
строка
Код:
.model flat, stdcall
формирует функцию автоматически согласно конвенции STDCALL, передавай параметры в процедуру через стек, остальное сделает компилятор
Mikl___ вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц

Опции темы Поиск в этой теме
Поиск в этой теме:

Расширенный поиск


Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
ошибка при вызове процедуры Emperator12 Общие вопросы Delphi 8 22.09.2012 00:52
Ошибка линковки при вызове функции другой библиотеки revaldo666 Общие вопросы C/C++ 2 23.07.2012 16:45
Ошибка при вызове openFileDialog ---FISHER--- C# (си шарп) 7 02.03.2011 13:25
beginthread, ошибка при вызове Dreanks Помощь студентам 2 28.10.2010 14:09