String Converting ('strcmp')

I have been reading a tutorial about how to edit solitaire's memory addresses, since i am really interested in memory editing. I ran into a problem i can't fix as yet.
I am using microsoft visual c++ 2010 express.
Here it is

error C2664: 'strcmp' : cannot convert parameter 1 from 'WCHAR [260]' to 'const char *'
Types pointed to are unrelated; conversion requires reinterpret_cast, C-style cast or function-style cast


And the code of course:

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
#include <iostream>
#include <windows.h>
#include <tlhelp32.h>

using namespace std;

#define SCORE 0x066938B0

DWORD GetProcId(char* ProcName)
{
	PROCESSENTRY32 pe32;
	HANDLE		   hSnapshot = NULL;

	pe32.dwSize = sizeof( PROCESSENTRY32 );
	hSnapshot = CreateToolhelp32Snapshot( TH32CS_SNAPPROCESS, 0 );

	if( Process32First( hSnapshot, &pe32 ) )
	{
		do{
			if( strcmp( pe32.szExeFile, ProcName ) == 0 )
				break;
		}while( Process32Next( hSnapshot, &pe32 ) );
	}

	 if( hSnapshot != INVALID_HANDLE_VALUE )
		 CloseHandle( hSnapshot );

	 return pe32.th32ProcessID;
}

int main()
{
		DWORD pid;
		HANDLE phandle = NULL;
	pid = GetProcId("solitaire.exe");
		
		if(GetLastError())
			cout << "Error_PID_: " << GetLastError() << endl;

	phandle = OpenProcess(PROCESS_ALL_ACCESS,0,pid);
	if(GetLastError())
		cout << "Error_HANDLE_: " << GetLastError() << endl;

	int value;

	cout << "pid   : " << pid << endl;
	cout << "HANDLE: " << phandle << endl << endl;

	cout << "Enter a new and better (or worse) score!\n-> ";
	cin >> value;

	WriteProcessMemory(phandle, (LPVOID) SCORE, (LPVOID) &value, sizeof(&value), NULL);

	if(GetLastError())
		cout << "Error: " << GetLastError() << endl;

	system("PAUSE");

	return 0;
}



Thanks in advance.
Last edited on
Bump
strcmp is a function that takes two parameters. Each parameter must be a pointer to a const char.

You are trying to feed it an object of type WCHAR [260]. It does not take those objects. It takes const char* objects. You must pass it a const char* or something that the compiler knows how to transform into a const char*.

If you pass it the address of pe32.szExeFile[0], you will then be passing it a WCHAR*, which is a bit closer. I never work with WCHAR type, so I can't advise on the relationship between WCHAR and char.

Last edited on
So i need to make a pointer to his: pe32.szExeFile like: &pe32.szExeFile?

Actually, that bunch of code was given, with the tutorial, so the function GetProcId(char* ProcName), was said to be unexplained. I don't really understand that part.
Don't be mad though, i understand the other part, since it's not that complicated.
Last edited on
Well, there's a few things you can do. Two of them are:
1. You can #undef UNICODE at the beginning of the file.
2. You can use this instead of strcmp():
1
2
3
4
5
6
7
8
template <typename T1,typename T2>
int generic_strcmp(const T1 *str1,const T2 *str2){
	for (;;str1++,str2++){
		int d=*str1-*str2;
		if (d!=0)
			return d;
	}
}


Moschops: WCHAR is just a macro for wchar_t. It's not a complex type.
Last edited on
Or you could use wcscmp() instread of strcmp().

For each str- function, there's a wcs- version: strlen, strcpy, strchr, ... for Ansi; wcslen, wcscpy, wcschr, ... for Unicode.

Andy

PS And when tchar.h is included, the _tcs- macros map to either str- or wcs- depending on how _UNICODE is declared: _UNICODE controls the CRT, whereas UNICODE controls the Windows API mappings.
Last edited on
Thank you, i am not at home at the moment, when i get home, i will try your suggestions, and see how i can get them to work.
I think your best fix is to change the projects General / Character Set property to "Use Multi-Byte Character Set" (I would do this rather than use #undef UNICODE / #undef _UNICODE)

wcscmp() will fix the error you quoted, but then you'd have to move some other bits of your code to use Unicode (wchar_t/WCHAR) rather than char.

Andy
Last edited on
Since you are targeting Windows anyway, just use lstrcmp().
http://www.google.com/search?btnI=1&q=msdn+lstrcmp
It will do the Right Thing.
Just switching strcmp -> lstrcmp (or wcscmp) won't make everything right, as one of the params being passed to strcmp (or whatever) is currently a wchar_t (the left one) and the other a char.

The easiest way is to alter the char set the vcproj is using, so everything builds Ansi. Then the code should work as-is (or with lstrmcmp, for that matter).

If the project is left to build Unicode, the lstrcmp change will also require GetProcId() to be alterered to take a wchar_t* (or to use TCHAR*, tchar.h macro style). Which means the passed in string needs to become a "long" string:

pid = GetProcId(L"solitaire.exe");

or (with tchar.h macro)

pid = GetProcId(_T("solitaire.exe"));

Or you leave GetProcId() param as it is, but convert the passed in value from Ansi to Unicode (using MultiByteToWideChar) before calling lstrcmp.

Last edited on
Just switching strcmp -> lstrcmp (or wcscmp) won't make everything right, as one of the params being passed to strcmp (or whatever) is currently a wchar_t (the left one) and the other a char.

Oops! I missed that!
Thanks, works like a charm. Didn't even need to get debug privileges.
Didn't even need to get debug privileges.


It is truly horrifying to learn that there are some dev environments where the person writing the code does not inherently have the ability to debug that code :(
Topic archived. No new replies allowed.