SmileCMutate (Simple Polymorph)

Posts 1–4 of 4 · Page 1 of 1
CMutate (Simple Polymorph)
Code:
#include <windows.h> 
#include <winnt.h> 

#ifndef _CMUTATE_ 
#define _CMUTATE_ 

class CMutate 
{ 
public: 
    void    SetRandomSeed( int iRandomSeed ); 
    void    InitiateMutation(); 

private: 

    int        m_iRandomSeed; 
}; 

#endif
Code:
#include "stdafx.h" 
#include <windows.h> 
#include "CMutate.h" 

__declspec(naked) void MutateCore( void ) 
{ 
    _asm _emit 0x90; //0 
    _asm _emit 0x90; //1 
    _asm _emit 0x90; //2 
    _asm _emit 0x90; //3 
    _asm _emit 0x90; //4 
    _asm _emit 0x90; //5 
    _asm _emit 0x90; //6 
    _asm _emit 0x90; //7 
    _asm _emit 0x90; //8 
    _asm _emit 0x90; //9 
    _asm _emit 0x90; //10 
    _asm _emit 0x90; //11 
    _asm _emit 0x90; //12 
    _asm _emit 0x90; //13 
    _asm _emit 0x90; //14 
    _asm _emit 0x90; //15 
    _asm _emit 0x90; //16 
    _asm _emit 0x90; //17 
    _asm _emit 0x90; //18 
    _asm _emit 0x90; //19 
    _asm _emit 0x90; //20 
    _asm _emit 0x90; //21 
    _asm _emit 0x90; //22 
    _asm _emit 0x90; //23 
    _asm _emit 0x90; //24 
    _asm _emit 0x90; //25 
    _asm _emit 0x90; //26 
    _asm _emit 0x90; //27 
    _asm _emit 0x90; //28 
    _asm _emit 0x90; //29 
    _asm _emit 0x90; //30 
    _asm _emit 0x90; //31 
    _asm _emit 0x90; //32 
    _asm retn; 
} 

DWORD WINAPI lpMutate( LPVOID lpParams ) 
{ 
    int *iRandomSeed = (int *)lpParams; 

    if( iRandomSeed == NULL ) 
    { 
        iRandomSeed        = new int; 
        *iRandomSeed    = rand()%9999; 
    } 
    else 
    { 
        if( *iRandomSeed == 0 ) 
        { 
            iRandomSeed        = new int; 
            *iRandomSeed    = rand()%9999; 
        } 
    } 

    while( true ) 
    { 
        MEMORY_BASIC_INFORMATION mbi; 
        VirtualQuery( MutateCore, &mbi, sizeof( mbi ) ); 
        VirtualProtect( mbi.BaseAddress, mbi.RegionSize, PAGE_EXECUTE_READWRITE, &mbi.Protect ); 

        BYTE *byteArrayMutateCore = (BYTE *)MutateCore; 

        for( int i = 0; i < 32; i++ ) 
        { 
            srand( GetTickCount() * (i + i * i) * (*iRandomSeed)); 

            byteArrayMutateCore[i] = rand() % 255; 
        } 

        VirtualProtect( mbi.BaseAddress, mbi.RegionSize, mbi.Protect, NULL ); 
        FlushInstructionCache( GetCurrentProcess(), MutateCore, 32 ); 

        Sleep(10); 
    } 

    return 0; 
} 

void CMutate::SetRandomSeed( int iRandomSeed ) 
{ 
    m_iRandomSeed = iRandomSeed; 
} 

void CMutate::InitiateMutation() 
{ 
    //this will ensure its referenced as a function 
    MutateCore(); 

    CreateThread( 0, 0, lpMutate, &m_iRandomSeed, 0, 0 ); 
}
Dont forget to thank me

Credits : S0beit.
This isn't even yours. Credits go to s0beit.
Quote Originally Posted by master131 View Post
This isn't even yours. Credits go to s0beit.
you'are right. i putted the credits now
That is not polymorphic code. You (/ the guy who made this) run through a nop sled wich you then repeatedly fill with random garbage.

Polymorphic code is, by definition, code that mutates but keeps the original algorithm in tact.
I made a quick demonstration, but I would not consider this real polymorphic code, since I don't morph any part of the code wich is relevant to execution. It does how ever execute mutated code and continuously morph itself.

Code:
#include <cstdio>
#include <cstdlib>
#include <ctime>
#include <windows.h>

/*      04.05.2014

        Harava's simple junk polymorphism demo.

        I would not consider this real polymorphism,
        since I am not morphing any part of the code
        that is actually relevant to execution.
*/

#define MAX_JUNKS 1024

#define Jdw __asm _emit 0x01 __asm _emit 0x01 __asm _emit 0x01 __asm _emit 0x01
#define Jins __asm _emit 0x50 __asm _emit 0x50 __asm _emit 0xB8 Jdw __asm _emit 0x69 __asm _emit 0xC0 Jdw __asm _emit 0x8B __asm _emit 0xC0 __asm _emit 0x3D Jdw __asm _emit 0x74 __asm _emit 0xFF __asm _emit 0x58 __asm _emit 0x58
#define Junk Jins Jins Jins

/*
This is what the Junk looks like:

0112117A   > 50             PUSH EAX
0112117B   . 50             PUSH EAX
0112117C   . B8 01010101    MOV EAX,1010101
01121181   . 69C0 01010101  IMUL EAX,EAX,1010101
01121187   . 8BC0           MOV EAX,EAX
01121189   . 3D 01010101    CMP EAX,1010101
0112118E   . 74 FF          JE SHORT ScratchP.0112118F
01121190   . 58             POP EAX
01121191   . 58             POP EAX
*/

DWORD dwEndOfScan, dwStartOfScan, dwOldProt;
DWORD dwAdressesOfJunks[MAX_JUNKS];
int nNumberOfJunksFound = 0, nTimesMutated = 1;

HANDLE hMainThread; // HANDLE of main thread for suspending

DWORD RandVal;
BYTE RandOffset;
BYTE RandReg;

void ScanStartAddress(){}

DWORD WINAPI MutatorThread( LPVOID lpParam )
{
    if(!VirtualProtect((LPVOID)dwStartOfScan, (dwEndOfScan-dwStartOfScan), PAGE_EXECUTE_READWRITE, &dwOldProt))
    {
        ExitProcess(-1);Junk;
    }
    while(1)
    {
        if(nTimesMutated % 250 == 0)
            printf("Mutation cycle %d\n", nTimesMutated);Junk;

        nTimesMutated++;Junk;

        SuspendThread(hMainThread); // Suspend the main thread, just in case it was in the middle of executing a junk block
        for(int n = 0; n < nNumberOfJunksFound; n++)
        {
            RandReg = rand() % 4;
            RandOffset = (rand() % 0xFF) + 1;
            RandVal = (rand() % 0xFFFFFFFF) + 1;

            *(BYTE*)(dwAdressesOfJunks[n]+1) = 0x50 + RandReg;Junk;           // Randomize register of second push
            *(BYTE*)(dwAdressesOfJunks[n]+2) = 0xB8 + RandReg;Junk;           // Randomize register of mov
            *(DWORD*)(dwAdressesOfJunks[n]+3) = RandVal;Junk;          // Randomize value of mov
            *(BYTE*)(dwAdressesOfJunks[n]+8) = 0xC0 + (RandReg*8);Junk;       // Randomize register of imul
            *(DWORD*)(dwAdressesOfJunks[n]+9) = RandVal;Junk;          // Randomize value of imul
            *(BYTE*)(dwAdressesOfJunks[n]+14) = 0xC0 + RandReg;Junk;          // Randomize register of mov
            *(DWORD*)(dwAdressesOfJunks[n]+16) = ((RandVal%100)-999);Junk;         // Randomize value of cmp
            *(BYTE*)(dwAdressesOfJunks[n]+21) = RandOffset;Junk;       // Randomize offset of jmp
            *(BYTE*)(dwAdressesOfJunks[n]+22) = 0x58 + RandReg;Junk;          // Randomize register of second last pop
        }
        ResumeThread(hMainThread);
        Sleep(1);
    }
}

bool MutateMain(DWORD AddressOfScanStart, DWORD SizeOfScan)
{
    Junk;   // Since execution is not altered by the junk code or morphing, the Morph function can alter itself too.

    if(!VirtualProtect((LPVOID)AddressOfScanStart, SizeOfScan, PAGE_EXECUTE_READWRITE, &dwOldProt))
    {
        ExitProcess(-1);Junk;
    }
    for(int n = AddressOfScanStart; n < (AddressOfScanStart+SizeOfScan); n++)   // Scan memory for all junk blocks
    {
        Junk;
        if(*(BYTE*)n == 0x50 && *(BYTE*)(n+23)==0x58)  // Check for the push pop eax
        {
            dwAdressesOfJunks[nNumberOfJunksFound] = n; // Store the address of the junk for continuous mutation
            nNumberOfJunksFound++;

            RandReg = rand() % 4;Junk;
            RandOffset = rand() % 0xFF;Junk;
            RandVal = rand() % 0xFFFFFFFF + 1;
            printf("Found junk at %x\n", n);Junk;       // Some initial randomization:
            *(BYTE*)(n+1) += RandReg;Junk;           // Randomize register of second push
            *(BYTE*)(n+2) += RandReg;Junk;           // Randomize register of mov
            *(DWORD*)(n+3) = RandVal;Junk;          // Randomize value of mov
            *(BYTE*)(n+8) += (RandReg*8);Junk;       // Randomize register of imul
            *(DWORD*)(n+9) = RandVal;Junk;          // Randomize value of imul
            *(BYTE*)(n+14) += RandReg;Junk;          // Randomize register of mov
            *(DWORD*)(n+16) = ((RandVal%100)-999);Junk;         // Randomize value of cmp
            *(BYTE*)(n+21) = RandOffset;Junk;       // Randomize offset of jmp
            *(BYTE*)(n+22) += RandReg;Junk;          // Randomize register of second last pop
        }
    }

    CreateThread(NULL, NULL, MutatorThread, NULL, NULL, NULL);  // Spawn a thread to continuously mutate the code
    return true;
}

int main()
{
    hMainThread = OpenThread(THREAD_ALL_ACCESS, FALSE, GetCurrentThreadId());

    srand(time(NULL));
    dwStartOfScan = (DWORD)&ScanStartAddress;   // Grab the address of the scan

    goto labelMainEnd;  // Go grab the address of the end of the scan
    labelStartOfMain:

    Junk;
    Junk;
    Junk;
    MutateMain(dwStartOfScan, (dwEndOfScan-dwStartOfScan));
    Junk;
    Junk;
    while(1)
    {
        Junk;
        for(int n = 0; n < 100; n++)
        {
            Sleep(10);Junk;         // We execute mutated code, but it does not screw up execution. That is the whole point in polymorphism
        }

        printf("MainThread says hello!\n");Junk;
    }
    Junk;
    Junk;

    return 1;

    labelMainEnd:       // Grab the address of "end" of main
    __asm
    {
        PUSH EAX
        CALL labelFetchAddress
        labelFetchAddress:
        POP EAX
        MOV dwEndOfScan, EAX
        POP EAX
        jmp labelStartOfMain    // Back to beginning of main
    }
}
This is how execution looks in a debugger:









Also, you don't need to call FlushInstructionCache() on x86 or x64.
Posts 1–4 of 4 · Page 1 of 1

Post a Reply

Similar Threads

Tags for this Thread

None

Talk with us