Форум программистов, компьютерный форум, киберфорум
С++ для начинающих
Войти
Регистрация
Восстановить пароль
Карта форума Темы раздела Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.55/11: Рейтинг темы: голосов - 11, средняя оценка - 4.55
1 / 1 / 0
Регистрация: 21.02.2015
Сообщений: 126
1

Неразрешенный внешний символ при вызове методов класса в сторонней программе (dll)

07.11.2016, 14:46. Показов 2114. Ответов 10
Метки нет (Все метки)

Author24 — интернет-сервис помощи студентам
Здравствуйте. Пишу dll для клавиатурного хука. Есть класс, который я написал для работы с файлами. Он прекрасно компилируется в родной программе, но при попытках вызвать методы класса в программе не родственной классу возникают ошибки с неразрешенным внешним символом. Не уверен, что нужен код класса(он рабочий), но скину:
FileWork.h
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
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
#include <Windows.h>
#include <WinBase.h>
#include <string>
#include <conio.h>
#include <Lmcons.h>
#include <Aclapi.h>
#include "Shlwapi.h"
 
#pragma once
#pragma comment(lib, "Shlwapi.lib")
#pragma comment(lib, "Advapi32.lib")
 
 
#define EOF_POINTER_METHOD 1
#define EOF_READ_METHOD 2
 
bool SetPrivelege(char *privelege, bool EnableDisable = true);
bool IsFileExist(char *FName);
bool Copy(char *OldFName, char *NewFName, bool IsReplase = false);
bool Move(char *OldFName, char *NewFName, bool IsReplace = false);
bool Delete(char *FName);
bool CreateDir(char *DirPath);
bool RemoveDir(char *DirPath, bool delsubfiles = true);
bool SetArttributes(char *FName, DWORD64 attributes = FILE_ATTRIBUTE_NORMAL);
bool SetACL(char *FilePath, char *Username, DWORD access = GENERIC_ALL, ACCESS_MODE accessmode = GRANT_ACCESS);
bool GetACL(char *FilePath, ACL *acl);
DWORD GetArttributes(char *FName);
std::string GetFileNameInDirbyNumber(char *DirPath, DWORD number);
std::string GetThisUserName();
 
class FileWork
{
public:
    FileWork();
    ~FileWork();
    UINT64 GetSize();
    HANDLE GetFileHandle();
    DWORD GetSeek();
    DWORD GetArttributes();
    bool SetACL(char *Username, DWORD access = GENERIC_ALL, ACCESS_MODE accessmode = GRANT_ACCESS);
    bool SetAttributes(DWORD attributes = FILE_ATTRIBUTE_NORMAL);
    bool Lock(DWORD offsLow, DWORD offHigh, DWORD toLockLow, DWORD toLockHigh);
    bool Unlock(DWORD offsLow, DWORD offHigh, DWORD toLockLow, DWORD toLockHigh);
    bool SetEOF(DWORD pos = 0);
    bool AdvancedCreate(char *FileName, DWORD Access = GENERIC_READ | GENERIC_WRITE, DWORD ShareMode = FILE_SHARE_READ | FILE_SHARE_WRITE, SECURITY_ATTRIBUTES *SecrAttr = NULL, DWORD CreateDisp = OPEN_ALWAYS, DWORD Attributes = FILE_ATTRIBUTE_NORMAL);
    bool NormalCreate(char *FileName, DWORD Access = GENERIC_READ | GENERIC_WRITE, DWORD ShareMode = FILE_SHARE_READ | FILE_SHARE_WRITE, DWORD CreateDisp = OPEN_ALWAYS);
    bool BaseCreate(char *FileName, DWORD CreateDisp = OPEN_ALWAYS);
    bool AdvancedWrite(void *buffer, DWORD NumberOfBytesToWrite, DWORD *NumberOfBytesWritten = NULL, OVERLAPPED *ovl = NULL);
    bool NormalWrite(void *buffer, DWORD NumberOfBytesToWrite, OVERLAPPED *ovl = NULL);
    bool AdvancedRead(void *buffer, DWORD NumberOfBytesToRead, DWORD *NumberOfBytesReaden = NULL, OVERLAPPED *ovl = NULL);
    bool NormalRead(void *buffer, DWORD NumberOfBytesRead, OVERLAPPED *ovl = NULL);
    bool IsEOF(DWORD method = EOF_POINTER_METHOD, OVERLAPPED *ov = NULL);
    bool Seek(INT64 pos, DWORD basepos = FILE_BEGIN);
    bool Close();
    bool Flush();
private:
    char *m_FName;
    HANDLE m_Fhandle;
    DWORD m_Access;
    DWORD m_ShareMode;
    SECURITY_ATTRIBUTES *m_SecrAttr;
    DWORD m_CreateDisp;
    DWORD m_Attributes;
};
FileWork.cpp
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
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
#include "FileWork.h"
 
FileWork::FileWork()
{
}
 
 
FileWork::~FileWork()
{
}
 
HANDLE FileWork::GetFileHandle()
{
    return m_Fhandle;
}
 
DWORD FileWork::GetSeek()
{
    return SetFilePointer(m_Fhandle, 0, 0, FILE_CURRENT);
}
 
bool FileWork::Lock(DWORD offsLow, DWORD offHigh, DWORD toLockLow, DWORD toLockHigh)
{
    return LockFile(m_Fhandle, offsLow, offHigh, toLockLow, toLockHigh);
}
 
bool FileWork::Unlock(DWORD offsLow, DWORD offHigh, DWORD toLockLow, DWORD toLockHigh)
{
    return UnlockFile(m_Fhandle, offsLow, offHigh, toLockLow, toLockHigh);
}
 
DWORD FileWork::GetArttributes()
{
    return GetFileAttributes(m_FName);
}
 
bool FileWork::SetAttributes(DWORD attributes)
{
    return SetFileAttributes(m_FName, attributes);
}
 
bool FileWork::SetACL(char *Username, DWORD access, ACCESS_MODE accessmode)
{
    char *path = m_FName;
    char *usr = Username;
    bool result = false;
    DWORD dwRes = 0;
    PACL pOldDACL = NULL, pNewDACL = NULL;
    PSECURITY_DESCRIPTOR pSD = NULL;
    EXPLICIT_ACCESS ea;
    dwRes = GetNamedSecurityInfo(path, SE_FILE_OBJECT, DACL_SECURITY_INFORMATION, NULL, NULL, &pOldDACL, NULL, &pSD);
    if (ERROR_SUCCESS != dwRes) {
        goto Cleanup;
    }
    ZeroMemory(&ea, sizeof(EXPLICIT_ACCESS));
    ea.grfAccessPermissions = access;
    ea.grfAccessMode = accessmode;
    ea.grfInheritance = CONTAINER_INHERIT_ACE;
    ea.Trustee.TrusteeForm = TRUSTEE_IS_NAME;
    ea.Trustee.ptstrName = usr;
    dwRes = SetEntriesInAcl(1, &ea, pOldDACL, &pNewDACL);
    if (ERROR_SUCCESS != dwRes)  {
        goto Cleanup;
    }
    dwRes = SetNamedSecurityInfo(path, SE_FILE_OBJECT,
        DACL_SECURITY_INFORMATION,
        NULL, NULL, pNewDACL, NULL);
    if (ERROR_SUCCESS != dwRes)  {
        goto Cleanup;
    }
    result = true;
Cleanup:
    if (pSD != NULL)
        LocalFree((HLOCAL)pSD);
    if (pNewDACL != NULL)
        LocalFree((HLOCAL)pNewDACL);
    return result;
}
 
bool FileWork::IsEOF(DWORD method, OVERLAPPED *ov)
{
    switch (method)
    {
    case 1:
        {
              DWORD end, curr;
              curr = SetFilePointer(m_Fhandle, 0, 0, FILE_CURRENT);
              end = SetFilePointer(m_Fhandle, 0, 0, FILE_END);
              SetFilePointer(m_Fhandle, curr, 0, FILE_BEGIN);
              if (curr >= end)
                  return true;
              else
                  return false;
        }
    case 2:
        {
              char c;
              DWORD res;
              ReadFile(m_Fhandle, &c, 1, &res, ov);
              if (res)
                  SetFilePointer(m_Fhandle, -1, 0, FILE_CURRENT);
              return !res;
        }
    default:
        return false;
    }
}
 
bool FileWork::SetEOF(DWORD pos)
{
    Seek(pos);
    return SetEndOfFile(m_Fhandle);
}
 
bool FileWork::AdvancedCreate(char *FileName, DWORD Access, DWORD ShareMode, SECURITY_ATTRIBUTES *SecrAttr, DWORD CreateDisp, DWORD Attributes)
{
    m_FName = FileName;
    m_Access = Access;
    m_ShareMode = ShareMode;
    m_SecrAttr = SecrAttr;
    m_CreateDisp = CreateDisp;
    m_Attributes = Attributes;
    m_Fhandle = CreateFile(FileName, Access, ShareMode, SecrAttr, CreateDisp,
        Attributes, 0);
    if (m_Fhandle != INVALID_HANDLE_VALUE)
        return true;
    else
        return false;
}
 
bool FileWork::NormalCreate(char *FileName, DWORD Access, DWORD ShareMode, DWORD CreateDisp)
{
    m_FName = FileName;
    m_Access = Access;
    m_ShareMode = ShareMode;
    m_SecrAttr = NULL;
    m_CreateDisp = CreateDisp;
    m_Attributes = FILE_ATTRIBUTE_NORMAL;
    m_Fhandle = CreateFile(FileName, Access, ShareMode, NULL, CreateDisp,
        FILE_ATTRIBUTE_NORMAL, 0);
    if (m_Fhandle != INVALID_HANDLE_VALUE)
        return true;
    else
        return false;
}
 
bool FileWork::BaseCreate(char *FileName, DWORD CreateDisp)
{
    m_FName = FileName;
    m_Access = GENERIC_READ | GENERIC_WRITE;
    m_ShareMode = FILE_SHARE_READ | FILE_SHARE_WRITE;
    m_SecrAttr = NULL;
    m_CreateDisp = CreateDisp;
    m_Attributes = FILE_ATTRIBUTE_NORMAL;
    m_Fhandle = CreateFile(FileName, GENERIC_READ | GENERIC_WRITE, FILE_SHARE_READ | FILE_SHARE_WRITE, NULL, CreateDisp,
        FILE_ATTRIBUTE_NORMAL, 0);
    if (m_Fhandle != INVALID_HANDLE_VALUE)
        return true;
    else
        return false;
}
 
bool FileWork::AdvancedWrite(void *buffer, DWORD NumberOfBytesToWrite, DWORD *NumberOfBytesWritten, OVERLAPPED *ovl)
{
    bool result;
    if (NumberOfBytesWritten)
    result = WriteFile(m_Fhandle, buffer, NumberOfBytesToWrite, NumberOfBytesWritten, ovl);
    else
    {
        DWORD tmp;
        result = WriteFile(m_Fhandle, buffer, NumberOfBytesToWrite, &tmp, ovl);
    }
    return result;
}
 
bool FileWork::NormalWrite(void *buffer, DWORD NumberOfBytesToWrite, OVERLAPPED *ovl)
{
    bool result;
    DWORD tmp;
    result = WriteFile(m_Fhandle, buffer, NumberOfBytesToWrite, &tmp, ovl);
    return result;
}
 
bool FileWork::AdvancedRead(void *buffer, DWORD NumberOfBytesToRead, DWORD *NumberOfBytesReaden, OVERLAPPED *ovl)
{
    bool result;
    if (NumberOfBytesReaden)
        result = ReadFile(m_Fhandle, buffer, NumberOfBytesToRead, NumberOfBytesReaden, ovl);
    else
    {
        DWORD tmp;
        result = ReadFile(m_Fhandle, buffer, NumberOfBytesToRead, &tmp, ovl);
    }
    return result;
}
 
bool FileWork::NormalRead(void *buffer, DWORD NumberOfBytesRead, OVERLAPPED *ovl)
{
    bool result;
    DWORD tmp;
    result = ReadFile(m_Fhandle, buffer, NumberOfBytesRead, &tmp, ovl);
    return result;
}
 
bool FileWork::Seek(INT64 pos, DWORD basepos)
{
    if (SetFilePointer(m_Fhandle, pos, NULL, basepos) == INVALID_SET_FILE_POINTER)
        return false;
    else
        return true;
}
 
bool FileWork::Flush()
{
    return FlushFileBuffers(m_Fhandle);
}
 
bool FileWork::Close()
{
    return CloseHandle(m_Fhandle);
}
 
UINT64 FileWork::GetSize()
{
    LARGE_INTEGER li;
    GetFileSizeEx(m_Fhandle, &li);
    return li.QuadPart;
}
 
bool Delete(char *FName)
{
    return DeleteFile(FName);
}
 
bool Copy(char *OldFName, char *NewFName, bool IsReplase)
{
    return CopyFile(OldFName, NewFName, !IsReplase);
}
 
bool Move(char *OldFName, char *NewFName, bool IsReplace)
{
    if (!PathFileExists(NewFName))
        return MoveFile(OldFName, NewFName);
    else
    if (IsReplace)
    {
        Delete(NewFName);
        return MoveFile(OldFName, NewFName);
    }
    else
        return false;
}
 
bool IsFileExist(char *FName)
{
    return PathFileExists(FName);
}
 
bool CreateDir(char *DirPath)
{
    return CreateDirectory(DirPath, NULL);
}
 
bool RemoveDir(char *DirPath, bool delsubfiles)
{
    if (!delsubfiles)
    {
        return RemoveDirectory(DirPath);
    }
    WIN32_FIND_DATA FindFileData;
    HANDLE hFind = INVALID_HANDLE_VALUE;
    DWORD dwError, dwAttrs;
    BOOL bRes;
    int nLength;
    char cPath[MAX_PATH], cCurrentFile[MAX_PATH];
    if (DirPath == NULL)
        return false;
    if (lstrcmpi(DirPath + 1, TEXT(":\")) == 0 || DirPath[0] == '\\' || DirPath[0] == '\0')
        return false;
    dwAttrs = GetFileAttributes(DirPath);
    if (dwAttrs == INVALID_FILE_ATTRIBUTES)
        return true; 
    if (~dwAttrs & FILE_ATTRIBUTE_DIRECTORY)
        return false;
    SetLastError(0);
    bRes = RemoveDirectory(DirPath);
    if (bRes == true)
        return true;
    if (bRes == false  && GetLastError() != ERROR_DIR_NOT_EMPTY)
        return false;
    nLength = lstrlen(DirPath);
    if (nLength + lstrlen("\\*.*") + 1> MAX_PATH)
        return false;
    if (DirPath[nLength - 1] == '\\')
        wsprintf(cPath, "%s*.*", DirPath);
    else
        wsprintf(cPath, "%s\\*.*", DirPath);
    hFind = FindFirstFile(cPath, &FindFileData);
    if (hFind == INVALID_HANDLE_VALUE)
        return false;
    lstrcpy(cPath, DirPath);
    if (cPath[nLength - 1] == '\\')
        cPath[nLength - 1] = TEXT('\0');
 
    do
    {
        if (lstrcmpi(FindFileData.cFileName, ".") == 0 || lstrcmpi(FindFileData.cFileName, "..") == 0)
            continue;
        if (lstrlen(cPath) + lstrlen("\") + lstrlen(FindFileData.cFileName) + 1 > MAX_PATH)
            continue;
        wsprintf(cCurrentFile, "%s\\%s", cPath, FindFileData.cFileName);
        if (FindFileData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)
        {
            if (FindFileData.dwFileAttributes & FILE_ATTRIBUTE_READONLY)
            {
                FindFileData.dwFileAttributes &= ~FILE_ATTRIBUTE_READONLY;
                SetFileAttributes(cCurrentFile, FindFileData.dwFileAttributes);
            }
 
            bRes = RemoveDir(cCurrentFile);
        }
        else
        {
            if ((FindFileData.dwFileAttributes & FILE_ATTRIBUTE_READONLY) ||
                (FindFileData.dwFileAttributes & FILE_ATTRIBUTE_SYSTEM))
                SetFileAttributes(cCurrentFile, FILE_ATTRIBUTE_NORMAL);
            DeleteFile(cCurrentFile);
        }
    } while (FindNextFile(hFind, &FindFileData));
    dwError = GetLastError();
    if (hFind != INVALID_HANDLE_VALUE)
        FindClose(hFind);
    if (dwError != ERROR_NO_MORE_FILES)
        return false;
    bRes = RemoveDirectory(DirPath);
    return bRes;
}
 
std::string GetFileNameInDirbyNumber(char *DirPath, DWORD number)
{
    WIN32_FIND_DATA fd;
    HANDLE h;
    DWORD counter = number;
    char path[MAX_PATH] = "";
    strcat(path, DirPath);
    strcat(path, "\\*");
    if (h = FindFirstFile(path, &fd))
    {
        if (!counter)
        {
            return fd.cFileName;
        }
        counter--;
        while (FindNextFile(h, &fd))
        {
            if (!counter)
            {
                return fd.cFileName;
            }
            counter--;
        }
    }
    return "";
}
 
DWORD GetArttributes(char *FName)
{
    return GetFileAttributes(FName);
}
 
bool SetArttributes(char *FName, DWORD64 attributes)
{
    return SetFileAttributes(FName, attributes);
}
 
bool SetACL(char *FilePath, char *Username, DWORD access, ACCESS_MODE accessmode)
{
    char *path = FilePath;
    char *usr = Username;
    bool result = false;
    DWORD dwRes = 0;
    PACL pOldDACL = NULL, pNewDACL = NULL;
    PSECURITY_DESCRIPTOR pSD = NULL;
    EXPLICIT_ACCESS ea;
    dwRes = GetNamedSecurityInfo(path, SE_FILE_OBJECT, DACL_SECURITY_INFORMATION, NULL, NULL, &pOldDACL, NULL, &pSD);
    if (ERROR_SUCCESS != dwRes) {
        goto Cleanup;
    }
    ZeroMemory(&ea, sizeof(EXPLICIT_ACCESS));
    ea.grfAccessPermissions = access;
    ea.grfAccessMode = accessmode;
    ea.grfInheritance = CONTAINER_INHERIT_ACE;
    ea.Trustee.TrusteeForm = TRUSTEE_IS_NAME;
    ea.Trustee.ptstrName = usr;
    dwRes = SetEntriesInAcl(1, &ea, pOldDACL, &pNewDACL);
    if (ERROR_SUCCESS != dwRes)  {
        goto Cleanup;
    }
    dwRes = SetNamedSecurityInfo(path, SE_FILE_OBJECT,
        DACL_SECURITY_INFORMATION,
        NULL, NULL, pNewDACL, NULL);
    if (ERROR_SUCCESS != dwRes)  {
        goto Cleanup;
    }
    result = true;
Cleanup:
    if (pSD != NULL)
        LocalFree((HLOCAL)pSD);
    if (pNewDACL != NULL)
        LocalFree((HLOCAL)pNewDACL);
    return result;
}
 
bool GetACL(char *FilePath, ACL *acl)
{
    char *path = FilePath;
    DWORD dwRes = 0;
    PSECURITY_DESCRIPTOR ds;
    PACL pOldDACL = NULL;
    dwRes = GetNamedSecurityInfo(path, SE_FILE_OBJECT, DACL_SECURITY_INFORMATION, NULL, NULL, &acl, NULL, &ds);
    if (dwRes != ERROR_SUCCESS)
    {
        return false;
    }
    return true;
}
 
std::string GetThisUserName()
{
    std::string result = "\0";
    char buffer[UNLEN + 1];
    DWORD len = UNLEN + 1;
    GetUserName(buffer, &len);
    result = buffer;
    return result;
}
 
bool SetPrivelege(char *privelege, bool EnableDisable)
{
    bool result = false;
    HANDLE hToken;
    if (OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES, &hToken))
    {
        TOKEN_PRIVILEGES tp;
        tp.PrivilegeCount = 1;
        LookupPrivilegeValue(0, privelege, &tp.Privileges[0].Luid);
        tp.Privileges[0].Attributes = EnableDisable ? SE_PRIVILEGE_ENABLED : 0;
        result = AdjustTokenPrivileges(hToken, false, &tp, sizeof(tp), NULL, NULL);
    }
    CloseHandle(hToken);
    return result;
}
Буду благодарен, если скажите как решить проблему. Заранее спасибо.
0
Лучшие ответы (1)
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
07.11.2016, 14:46
Ответы с готовыми решениями:

Ссылка на неразрешенный внешний символ при использовании DLL
Всем привет. Подскажите пожалуйста, как работать с DLL... Я создаю новый проект с разрешением...

Ошибка при написании класса: error LNK2019: ссылка на неразрешенный внешний символ
Код: int _tmain(int argc, _TCHAR* argv) { Fraction x, x2, y, y2, fl, res, c; cout &lt;&lt;...

Ссылка на неразрешенный внешний символ в шаблоне класса
Добрый день, у меня возникла проблема. Выполняя лабораторную в универ задача которой звучит...

В элементарной программе из учебника - error LNK2019: ссылка на неразрешенный внешний символ
Элементарнейшая программа из учебника #include &lt;windows.h&gt; int WINAPI WinMain (HINSTANCE...

10
1 / 1 / 0
Регистрация: 21.02.2015
Сообщений: 126
07.11.2016, 19:10  [ТС] 2
Код dll:
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
32
33
#include <Windows.h>
#include "FileWork.h"
 
#pragma comment(lib, "Shlwapi.lib")
#pragma comment(lib, "Advapi32.lib")
 
HHOOK hook;
FileWork *f = new FileWork;
 
LRESULT CALLBACK KeyboardProc(int nCode, WPARAM wParam, LPARAM lParam)
{   
    int smb = nCode;
    if (smb < 0)
    {
        return CallNextHookEx(hook, nCode, wParam, lParam);
    }
    f->NormalWrite(&smb, sizeof(smb));
    return CallNextHookEx(hook, nCode, wParam, lParam);
}
 
void SetHOOK()
{
    hook = SetWindowsHookEx(WH_KEYBOARD, KeyboardProc, NULL, GetCurrentThreadId());
    f->NormalCreate("C:\\Users\\Алексей\\Desktop\\Hooklog.txt", GENERIC_READ | GENERIC_WRITE, NULL, OPEN_ALWAYS);
}
 
void UnsetHook()
{
    UnhookWindowsHookEx(hook);
    f->Flush();
    f->Close();
    f->~FileWork();
}
Добавлено через 3 часа 34 минуты
Только сейчас понял, какую хрень я написал в dll, но это не про класс, про хук.
P.S. Буду благодарен, если расскажите еще и про хуки(как их правильно устанавливать).

Добавлено через 46 минут
Мда... Дело точно не в dll. Написал программу:
C++
1
2
3
4
5
6
7
8
9
10
#include "FileWork.h"
 
int main()
{
    FileWork *fw = new FileWork;
    fw->BaseCreate("C:\\Users\\Алексей\\Desktop\\Dir\\.txt");
    fw->Close();
    fw->~FileWork();
    return 0;
}
Не компилируется. Пишет:
Ошибка 4 error LNK2019: ссылка на неразрешенный внешний символ "public: bool __thiscall FileWork::Close(void)" (?Close@FileWork@@QAE_NXZ) в функции _main D:\Projects\VS\MiniPrpoj\ZASHKVAR\FileWorkTest\FileWorkTest\main.obj FileWorkTest
Ошибка 3 error LNK2019: ссылка на неразрешенный внешний символ "public: bool __thiscall FileWork::BaseCreate(char *,unsigned long)" (?BaseCreate@FileWork@@QAE_NPADK@Z) в функции _main D:\Projects\VS\MiniPrpoj\ZASHKVAR\FileWorkTest\FileWorkTest\main.obj FileWorkTest
Ошибка 1 error LNK2019: ссылка на неразрешенный внешний символ "public: __thiscall FileWork::FileWork(void)" (??0FileWork@@QAE@XZ) в функции _main D:\Projects\VS\MiniPrpoj\ZASHKVAR\FileWorkTest\FileWorkTest\main.obj FileWorkTest
Ошибка 2 error LNK2019: ссылка на неразрешенный внешний символ "public: __thiscall FileWork::~FileWork(void)" (??1FileWork@@QAE@XZ) в функции "public: void * __thiscall FileWork::`scalar deleting destructor'(unsigned int)" (??_GFileWork@@QAEPAXI@Z) D:\Projects\VS\MiniPrpoj\ZASHKVAR\FileWorkTest\FileWorkTest\main.obj FileWorkTest
Ошибка 5 error LNK1120: неразрешенных внешних элементов: 4 D:\Projects\VS\MiniPrpoj\ZASHKVAR\FileWorkTest\Debug\FileWorkTest.exe FileWorkTest

Добавлено через 46 секунд
Цитата Сообщение от Алексей_Либанов Посмотреть сообщение
fw->BaseCreate("C:\\Users\\Алексей\\Desktop\\Dir\\.txt");
*1.txt
0
18842 / 9841 / 2408
Регистрация: 30.01.2014
Сообщений: 17,284
07.11.2016, 19:16 3
Цитата Сообщение от Алексей_Либанов Посмотреть сообщение
Не компилируется.
Это компилируется. А вот не линкуется - да.
cpp файл в проект-то добавил?

PS. Явный вызов деструктора тут не нужен. Используй delete.

Добавлено через 2 минуты
Алексей_Либанов, по поводу первоначального вопроса - см. тут: https://msdn.microsoft.com/ru-... 27t8c.aspx
0
1 / 1 / 0
Регистрация: 21.02.2015
Сообщений: 126
07.11.2016, 19:49  [ТС] 4
Цитата Сообщение от DrOffset Посмотреть сообщение
cpp файл в проект-то добавил?
Не понял вопрос. Вот скриншот папки проекта.
Миниатюры
Неразрешенный внешний символ при вызове методов класса в сторонней программе (dll)  
0
18842 / 9841 / 2408
Регистрация: 30.01.2014
Сообщений: 17,284
07.11.2016, 20:42 5
Алексей_Либанов, Ну, насколько я понимаю, последний тест свелся к тому, что этот класс использовался в одном проекте, без dll. И там тоже появились ошибки компоновщика. Если это так, то, вероятно, cpp файл забыли добавить в проект (то, что он лежит в папке рядом - ничего не значит, нужно, чтобы система сборки в IDE про него знала). Ну, или, если я не прав, нужно подробнее рассказать в каком сейчас состоянии проект.
Это я так мягко намекаю, что проблемы нынешние и прошлые - это разные проблемы, у них разные причины и делать общие выводы о них обеих - не надо.
0
1 / 1 / 0
Регистрация: 21.02.2015
Сообщений: 126
07.11.2016, 21:23  [ТС] 6
DrOffset, Еще раз описываю ситуацию, возможно Вы меня не так поняли. Есть родной проект, в котором я писал класс. В нем все линкуется. Я создал другой проект(никак не связанный с проектом в котором я писал класс). В папку этого проекта я закинул FileWork.cpp и FileWork.h, в main.cpp проекта написал #include "FileWork.h". Вопрос: что еще нужно написать/подключить, чтобы в проекте можно было вызывать методы класса?
0
18842 / 9841 / 2408
Регистрация: 30.01.2014
Сообщений: 17,284
07.11.2016, 21:41 7
Цитата Сообщение от Алексей_Либанов Посмотреть сообщение
Еще раз описываю ситуацию, возможно Вы меня не так поняли.
Ко мне можно (нужно) на "ты".
К сожалению понять можно было по-разному, т.к. информации было дано не совсем достаточно.

Цитата Сообщение от Алексей_Либанов Посмотреть сообщение
Я создал другой проект(никак не связанный с проектом в котором я писал класс).
К этому проекту этот класс планируется подцеплять из dll?
* Если да, то закидывание cpp - это лишнее, ненужное действие. Вместо этого нужно было предоставить библиотеку импорта (*.lib) и прописать ее в настройках компоновщика. Во-вторых, нужно было пометить соответствующие функции, как и сам класс, как экспортируемые иначе функции не будут видны извне, получим как раз похожие на представленные ошибки компоновщика. Об этом была дана ссылка выше. Вот, если угодно, более подробно:
https://habrahabr.ru/post/150327/
https://msdn.microsoft.com/ru-... k134d.aspx
https://msdn.microsoft.com/ru-... w9f6x.aspx
https://msdn.microsoft.com/ru-... k134d.aspx
* Если же класс просто хочется использовать как есть из этого нового проекта, то закидывание cpp файла в папку недостаточно, нужно еще подключить его в дереве проекта. Об этом я пытался сказать выше.

Кроме всего прочего, следует помнить, что имена функций и классов в С++ подвержены name mangling`у, что сводит на "нет" возможность взаимодействия (с использованием этих имен) между модулями, созданными в разных компиляторах. Поэтому обычно организуют взаимодействие через переносимый С-интерфейс. Из этого правила есть исключения, но необходимо оставаться в строгих рамках. Пример можно глянуть здесь.

Еще хочу заметить, что я пока даже не пытался касаться изначальной проблемы с хуком, т.к. по ней не хватает информации. Я думаю любой, кто соберется ответить, будет благодарен пошаговому описанию действий, в варианте "получилось" и в варианте "не получилось", начиная от компиляции тестового приложения и заканчивая установкой хука в целевую программу.
0
1 / 1 / 0
Регистрация: 21.02.2015
Сообщений: 126
07.11.2016, 21:58  [ТС] 8
Цитата Сообщение от DrOffset Посмотреть сообщение
Если же класс просто хочется использовать как есть из этого нового проекта, то закидывание cpp файла в папку недостаточно, нужно еще подключить его в дереве проекта.
Как "подключить его в дереве проекта"? Это именно то, что мне нужно.

Добавлено через 2 минуты
Цитата Сообщение от Алексей_Либанов Посмотреть сообщение
Это именно то, что мне нужно.
Пока я до конца не освоил dll Потом, кстати, планирую переписать класс в dll
(но это уже совсем другая история)
0
18842 / 9841 / 2408
Регистрация: 30.01.2014
Сообщений: 17,284
07.11.2016, 22:00 9
Лучший ответ Сообщение было отмечено Алексей_Либанов как решение

Решение

Цитата Сообщение от Алексей_Либанов Посмотреть сообщение
Как "подключить его в дереве проекта"? Это именно то, что мне нужно.
Неразрешенный внешний символ при вызове методов класса в сторонней программе (dll)
1
1 / 1 / 0
Регистрация: 21.02.2015
Сообщений: 126
07.11.2016, 22:11  [ТС] 10
Спасибо, от ошибок линковщика я избавился. Но вопрос с ловушками остался. Буду экспериментировать, потому что пока, все сводится к "не работает". Когда выявлю фактическую проблему - напишу. Ну а пока, не мог бы ты скинуть исходник программы для хукинга(если есть), хочу посмотреть, как там все устроено.
P.S. Инфы и интернете вроде много, но по фату, толковых статей по типу "хуки с нуля" практически нет.
0
DrOffset
07.11.2016, 22:17     Неразрешенный внешний символ при вызове методов класса в сторонней программе (dll)
  #11

Не по теме:

Цитата Сообщение от Алексей_Либанов Посмотреть сообщение
Ну а пока, не мог бы ты скинуть исходник программы для хукинга(если есть), хочу посмотреть, как там все устроено.
Под рукой, к сожалению, нет.
По вопросам организации хуков в windows лучше обратиться в этот форум: https://www.cyberforum.ru/win-api/
Начать, наверное, стоит с поиска. Наверняка есть уже примеры.

0
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
07.11.2016, 22:17

Создание шаблона класса ( Ошибка: ссылка на неразрешенный внешний символ )
Файл: Massive.h #ifndef MASSIVE_H #define MASSIVE_H #include &lt;iostream&gt; using std::istream;...

Ошибка неразрешенный внешний символ при подключении curl
Здравствуйте, скомпилил курл, подключил к проекту, но при компиляции проекта выдаёт 4 ошибки, и все...

Ошибка при работе с SFML: LNK2001 неразрешенный внешний символ
Доброго времени суток. Помогите с ошибками в коде, пожалуйста: LNK2001 неразрешенный внешний...

Ссылка на неразрешенный внешний символ __divti3 (при делении __int128)
int main() { volatile __int128 x = 1, y = 1; x /= y; return 0; } Вот такой простой код...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
11
Ответ Создать тему
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2024, CyberForum.ru