MemProcFS icon indicating copy to clipboard operation
MemProcFS copied to clipboard

[question] use sig to get offsets

Open S1ckZer opened this issue 3 years ago • 5 comments

Hello, is there a function to work with signatures from ida pro to get the offsets? I looked in the example.c but unfortunately couldn't find it, maybe I'm just blind.

S1ckZer avatar Aug 13 '22 22:08 S1ckZer

you can just read block-to-block of memories from module starting point and compare your signature.

0xGabriella avatar Aug 14 '22 01:08 0xGabriella

Huge thanks for the sponsorship @S1ckZer.

MemProcFS does not currently support ida pro flirt signatures.

At the moment MemProcFS only have some basic search functionality. You'll be able to search for binary data in the search module/and/or api. It's rather limited though since it's only allow you to specify the binary data to search together with an optional bitmask.

I'll try to better this support. Plan has been to add Yara rules for some time, but I need to look into it. Adding IDA signatures sounds like a really good idea also! I'm unfortunately just an IDA noob so I'll have to do some reading into this - but it's an awesome suggestion. I'll read up on it and see if I can add it in the not too distant future :)

ufrisk avatar Aug 14 '22 04:08 ufrisk

Thank you both for the quick replies. I'll just continue dumping my offsets manually and I'll be happy if one day the function for IDA signatures is available.

S1ckZer avatar Aug 14 '22 08:08 S1ckZer

you can just read block-to-block of memories from module starting point and compare your signature.

i will try thx

S1ckZer avatar Aug 14 '22 08:08 S1ckZer

+, need this too. If someone has working snippet that would be awesome

ruslanjan avatar Aug 23 '22 13:08 ruslanjan

DWORD findPattern(DWORD mBase, DWORD mSize, BYTE* mBytes, const char *szSignature, int start = 0)
{
    const char *pat = szSignature;
    DWORD firstMatch = 0;

    QWORD rangeStart = 0;
    DWORD rangeEnd = mSize;

    DWORD pCur;
    for (pCur = start; pCur < rangeEnd; pCur++)
    {

        if (!*pat)
            return mBase + firstMatch;

        if (*(PBYTE)pat == '\?' || mBytes[pCur] == GET_BYTE(pat))
        {
            if (!firstMatch)
                firstMatch = pCur;

            if (!pat[2])
            {
                return mBase + firstMatch;
            }

            if (*(PWORD)pat == '\?\?' || *(PBYTE)pat != '\?')
                pat += 3;

            else
                pat += 2;
        }
        else
        {
            pat = szSignature;
            firstMatch = 0;
        }
    }
    return 0u;
}

Use a Pattern of "00 ? 00". This will only return the first match.

r1ft4469 avatar Aug 20 '23 01:08 r1ft4469

Something like this:


#define INRANGE(x,a,b)   (x >= a && x <= b)
#define GET_BYTE( x )    (GET_BITS(x[0]) << 4 | GET_BITS(x[1]))
#define GET_BITS( x )    (INRANGE((x&(~0x20)),'A','F') ? ((x&(~0x20)) - 'A' + 0xa) : (INRANGE(x,'0','9') ? x - '0' : 0))

typedef struct _ModuleDump {
	BYTE* dump;
	DWORD base;
	DWORD size;
} ModuleDump;

static DWORD FindPattern(DWORD pid, ModuleDump module, const char* szSignature, int start = 0)
{

	const char* pat = szSignature;
	DWORD firstMatch = 0;

	QWORD rangeStart = 0;
	DWORD rangeEnd = module.size;

	DWORD pCur;
	for (pCur = start; pCur < rangeEnd; pCur++)
	{

		if (!*pat)
			return module.base + firstMatch;

		if (*(PBYTE)pat == '\?' || module.dump[pCur] == GET_BYTE(pat))
		{
			if (!firstMatch)
				firstMatch = pCur;

			if (!pat[2])
			{
				return module.base + firstMatch;
			}


			if (*(PWORD)pat == '\?\?' || *(PBYTE)pat != '\?')
				pat += 3;

			else
				pat += 2;
		}
		else
		{
			pat = szSignature;
			firstMatch = 0;
		}
	}
	return 0u;
}


static DWORD FindSignature(DWORD pid, ModuleDump module, const char* szSignature, int offset, int extra = 0)
{
	DWORD result = FindPattern(pid, module, szSignature) + offset;

	DWORD dwBytesRead = 0;
	VMMDLL_MemReadEx(hVMM, pid, (ULONG64)(result), (PBYTE)&result, sizeof(DWORD), &dwBytesRead,
		VMMDLL_FLAG_NOCACHE | VMMDLL_FLAG_NOCACHEPUT | VMMDLL_FLAG_ZEROPAD_ON_FAIL | VMMDLL_FLAG_NOPAGING_IO | VMMDLL_FLAG_NOPAGING);

	return result + extra;
}

static ModuleDump DumpModule(DWORD pid, PVMMDLL_MAP_MODULEENTRY module)
{
    ModuleDump moduleDump;
    moduleDump.base = (DWORD)module->vaBase;
    moduleDump.size = module->cbImageSize;
    moduleDump.dump = (BYTE*)malloc(sizeof(BYTE) * module->cbImageSize);

    VMMDLL_MemReadEx(hVMM, pid, module->vaBase, (PBYTE)moduleDump.dump, sizeof(BYTE) * moduleDump.size, NULL, VMMDLL_FLAG_NOCACHE);

    return moduleDump;
}

void getSig() {
    PVMMDLL_MAP_MODULEENTRY testModule;
    BOOL result = VMMDLL_Map_GetModuleFromNameU(hVMM, pid, procName, &testModule);
    ModuleDump testModuleDump = DumpModule(pid, testModule);


    DWORD addrOutput = FindSignature(pid, testModuleDump, "4C 8D 05 ? ? ? ? 48 8D 0D ? ? ? ? E8", 1, 0);
 
}


etapic avatar Aug 21 '23 00:08 etapic

Thank you very much for your contributions. I'm sure they'll help a few more people.

S1ckZer avatar Aug 21 '23 07:08 S1ckZer