ткните что неправильно в ланчере...
От: Аноним  
Дата: 12.09.08 11:23
Оценка:
взял с мсдн-а, сама длл лежит рядом с ланчером с названием DLLnew.dll но постоянно получаю "Message printed from executable"
typedef int (__cdecl *MYPROC)(LPWSTR); 
VOID main(VOID){ 
    #undef _UNICODE
     int argc;
     char *argv[2];
    HINSTANCE hinstLib; 
    MYPROC ProcAdd; 
    BOOL fFreeResult, fRunTimeLinkSuccess = FALSE;  
    hinstLib = LoadLibrary(/*argv[1]*/_T("DLLnew.dll"));function address.
     if (hinstLib != NULL) { 
        ProcAdd = (MYPROC) GetProcAddress(hinstLib, /*argv[2]*/"new");
        if (NULL != ProcAdd) {
           fRunTimeLinkSuccess = TRUE;
            (ProcAdd) (L"Message sent to the DLL function\n"); 
        } 
        fFreeResult = FreeLibrary(hinstLib); 
    }  
  if (! fRunTimeLinkSuccess) 
        printf("Message printed from executable\n"); 
}
Re: ткните что неправильно в ланчере...
От: _Ursus_  
Дата: 12.09.08 11:54
Оценка:
Здравствуйте, Аноним, Вы писали:

А>взял с мсдн-а, сама длл лежит рядом с ланчером с названием DLLnew.dll но постоянно получаю "Message printed from executable"

А>
А>typedef int (__cdecl *MYPROC)(LPWSTR); 
А>VOID main(VOID){ 
А>    #undef _UNICODE
А>     int argc;
А>     char *argv[2];
А>    HINSTANCE hinstLib; 
А>    MYPROC ProcAdd; 
А>    BOOL fFreeResult, fRunTimeLinkSuccess = FALSE;  
А>    hinstLib = LoadLibrary(/*argv[1]*/_T("DLLnew.dll"));function address.
А>     if (hinstLib != NULL) { 
А>        ProcAdd = (MYPROC) GetProcAddress(hinstLib, /*argv[2]*/"new");
А>        if (NULL != ProcAdd) {
А>           fRunTimeLinkSuccess = TRUE;
А>            (ProcAdd) (L"Message sent to the DLL function\n"); 
А>        } 
А>        fFreeResult = FreeLibrary(hinstLib); 
А>    }  
А>  if (! fRunTimeLinkSuccess) 
А>        printf("Message printed from executable\n"); 
А>}
А>


Этот кошмар взят из MSDN-а??

есть 2 варианта:
— dllnew.dll не загружается (мабуть, ее DllMain вертает FALSE, или она зависит от других DLL, которых не может найти)
— она не экспортирует символ с именем "new"
Re: ткните что неправильно в ланчере...
От: quodum  
Дата: 12.09.08 12:02
Оценка:
Здравствуйте, Аноним, Вы писали:

[]

Сделай "dumpbin /exports DLLnew.dll" и убедись, что там есть функция с именем "new". Скорее всего, там окажется декорированное имя, потому что ты забыл принять соответствующие меры.

Соответственно, вариантов три:
1) написать .def-файл для dll'и, чтобы функция экспортировалась под тем именем, под каким нужно
2) импортировать функцию под тем именем, под которым она существует (согласно выводу dumpbin'а)
3) если окажется, что нужная функция вообще не экспортируется, разбираться с DLL'ю
Re: ткните что неправильно в ланчере...
От: quodum  
Дата: 12.09.08 12:05
Оценка:
Здравствуйте, Аноним, Вы писали:

кстати, вот это

typedef int (__cdecl *MYPROC)(LPWSTR); 
VOID main(VOID){ 
    #undef _UNICODE   // фигня
.......


здесь совершенно бессмысленно. Это надо делать до включения всех заголовков, а лучше вообще с командной строки.
Re: ткните что неправильно в ланчере...
От: Кодт Россия  
Дата: 12.09.08 12:34
Оценка:
Здравствуйте, <Аноним>, Вы писали:

А>взял с мсдн-а, сама длл лежит рядом с ланчером с названием DLLnew.dll но постоянно получаю "Message printed from executable"


Это значит, что
или библиотека DLLnew.dll не найдена
— в текущем каталоге
— в PATH
или она не смогла загрузиться (битая либо не найдены зависимости)
или в ней нет экспортированного имени "new".

Так что
1. запускай программу так, чтобы текущий каталог у неё был равен каталогу, где лежит она и библиотека
2. смотри таблицы экспорта и зависимостей у библиотеки

Кстати, покажи, как ты экспортируешь имя "new".
... << RSDN@Home 1.2.0 alpha 4 rev. 1111>>
Перекуём баги на фичи!
Re[2]: ткните что неправильно в ланчере...
От: Аноним  
Дата: 12.09.08 13:15
Оценка:
К>Кстати, покажи, как ты экспортируешь имя "new".
вот так
int __declspec(dllexport) __stdcall DllEntryPoint(HINSTANCE _hInst,DWORD Reason,void *)

вот таким файликом

; new.def : Declares the module parameters for the DLL.

LIBRARY      "new"

EXPORTS
    ; Explicit exports can go here
Re[3]: ткните что неправильно в ланчере...
От: Кодт Россия  
Дата: 12.09.08 14:07
Оценка:
Здравствуйте, <Аноним>, Вы писали:

К>>Кстати, покажи, как ты экспортируешь имя "new".

А>вот так
А>int __declspec(dllexport) __stdcall DllEntryPoint(HINSTANCE _hInst,DWORD Reason,void *)

А>вот таким файликом
А>
А>; new.def : Declares the module parameters for the DLL.

А>LIBRARY      "new"

А>EXPORTS
А>    ; Explicit exports can go here
А>


Здесь я вижу, что ты экспортируешь имя "?DllEntryPoint@@YGHPAUHINSTANCE__@@KPAX@Z" (декорированное имя DllEntryPoint).

Нужно было написать .def-файл так
LIBRARY "new" ; это имя библиотеки (вообще говоря, пофиг на него - разве что линкер напишет варнинг)
EXPORTS
    new = DllEntryPoint ; задаёт экспортируемый алиас new для имени DllEntryPoint


Тогда будут экспортированы два имени
          1    0 00001000 ?DllEntryPoint@@YGHPAUHINSTANCE__@@KPAX@Z
          2    1 00001000 new

Первое — потому что был __declspec(dllexport), второе — потому что .def-файл.
... << RSDN@Home 1.2.0 alpha 4 rev. 1111>>
Перекуём баги на фичи!
Re[4]: ткните что неправильно в ланчере...
От: quodum  
Дата: 12.09.08 14:28
Оценка: +1
Здравствуйте, Кодт, Вы писали:

К>>>Кстати, покажи, как ты экспортируешь имя "new".

А>>вот так
К>
А>>int __declspec(dllexport) __stdcall DllEntryPoint(HINSTANCE _hInst,DWORD Reason,void *)
К>


[]

К>Здесь я вижу, что ты экспортируешь имя "?DllEntryPoint@@YGHPAUHINSTANCE__@@KPAX@Z" (декорированное имя DllEntryPoint).


К>Нужно было написать .def-файл так

К>
К>LIBRARY "new" ; это имя библиотеки (вообще говоря, пофиг на него - разве что линкер напишет варнинг)
К>EXPORTS
К>    new = DllEntryPoint ; задаёт экспортируемый алиас new для имени DllEntryPoint
К>


[]

Только вот сигнатура DllEntryPoint немного не соответствует сигнатуре использования из оригинального поста:
typedef int (__cdecl *MYPROC)(LPWSTR);


А похожа она на сигнатуру DllMain или настоящей DLL entry point.

Ориг. постеру краткосрочный совет -- проэкспортировать функцию new так же как и DllEntryPoint, а долгосрочный -- почитать поподробнее про DLLи
Re[5]: ткните что неправильно в ланчере...
От: Аноним  
Дата: 13.09.08 05:03
Оценка:
->Сделай "dumpbin /exports DLLnew.dll" и убедись, что там есть функция с именем "new". Скорее всего, там окажется декорированное имя, потому что ты забыл принять соответствующие меры.
так у меня линкер на mspdb80.dll ругается и не загружается

когда я пишу не так в файлике new.def
LIBRARY      "new"

EXPORTS

new=DllEntryPoint

а вот так, то при запуске ланчера этой длл-ки получаю вылет
LIBRARY      "new"

EXPORTS

DllEntryPoint
Re[6]: ткните что неправильно в ланчере...
От: Аноним  
Дата: 13.09.08 16:57
Оценка:
все собралось, запускается без ошибок, но не работает почему-то
вот такое к примеру вставил в длл-ку
fstream outputFile("C:\output.txt");
 if(!outputFile.is_open())
     throw (ios::failure("Could't open file"));
     char OldWndProc;
     outputFile << "test";
 outputFile.close();

файлика нет
пробовал найти в системе ExtendedTaskManager'om, не нашел
чем проверить почему что-то не выполняется в длл или не работает и почему?
Re[7]: ткните что неправильно в ланчере...
От: Кодт Россия  
Дата: 15.09.08 11:39
Оценка: +1
Здравствуйте, <Аноним>, Вы писали:

А>все собралось, запускается без ошибок, но не работает почему-то


Телепатически предполагаю, что
1. fstream по умолчанию открывает существующий файл, а у тебя нет файла c:\output.txt
2. Исключение, кинутое в никуда (если нет блока try-catch) приводит к мгновенному terminate(). Также, если не включена опция компилятора "поддержка исключений" (у MSVC это /EHsc), то тоже будет непредсказуемый феерверк.
3. Возможно, что из-за путаницы в сигнатурах у тебя вообще управление досюда не дошло — то ли не смог найти GetProcAddress, то ли криво вызвал функцию, и она стремительно вернула управление.


Очень интересная строчка
char OldWndProc;

Вкупе с хаотичной табуляцией показывает на то, что ты изучаешь С++ методом Монте-Карло (научным тыком). Может, по учебнику продуктивнее будет?

А>чем проверить почему что-то не выполняется в длл или не работает и почему?


Дебаггером.
Создаёшь solution с двумя проектами — exe и dll.
Настраиваешь проекты так, чтобы экзешник и библиотека размещались в одном каталоге.
Собираешь оба проекта в дебажной версии.
Дальше по шагам отлаживаешь.
... << RSDN@Home 1.2.0 alpha 4 rev. 1111>>
Перекуём баги на фичи!
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.