예제 #1
0
        public void Patch(LeagueProcess league)
        {
            uint createFileARefPointer = this.CreateFileARefOffset + league.Base;
            uint createFileAPointer    = this.CreateFileAOffset + league.Base;
            uint returnAddress         = this.ReturnAddressOffset + league.Base;
            uint freePointer           = this.FreePointerOffset + league.Base;
            uint freeFunction          = this.FreeFunctionOffset + league.Base;

            // wait untill CreateFileA has been used and unpacmaned
            league.WaitPointerEquals(createFileARefPointer, createFileAPointer);
            // wait until free pointer has been set
            league.WaitPointerNonZero(freePointer);

            // read trampoline shellcode that league creates for CreateFileA
            uint             createFileATrampolinePointer  = league.Read <uint>(createFileAPointer);
            ImportTrampoline originalCreateFileATrampoline = league.Read <ImportTrampoline>(createFileATrampolinePointer);

            uint    payloadPointer = league.AllocateMemory(0x1000);
            Payload payload        = new Payload(
                payloadPointer: payloadPointer,
                originalCreateFileATrampoline: originalCreateFileATrampoline,
                prefix: PrefixNormalized,
                originalFreePointer: freeFunction,
                findReturnAddress: returnAddress
                );
            uint             hookCreateFileAPointer    = payload.HookCreateFileAPointer(payloadPointer);
            uint             hookFreePointer           = payload.HookFreePointer(payloadPointer);
            ImportTrampoline hookCreateFileATrampoline = new ImportTrampoline(hookCreateFileAPointer);

            league.Write(payloadPointer, payload);
            league.MarkMemoryExecutable(payloadPointer, 0x1000);

            // write hooks
            league.Write(freePointer, hookFreePointer);
            league.Write(createFileATrampolinePointer, hookCreateFileATrampoline);
        }
        public void Patch(LeagueProcess league)
        {
            uint codePointer               = league.AllocateMemory(0x900);
            uint codeVerifyPointer         = codePointer + 0x000;
            uint codePrefixFnPointer       = codePointer + 0x100;
            uint codeOpenPointer           = codePointer + 0x200;
            uint codeCheckAccessPointer    = codePointer + 0x300;
            uint codeCreateIteratorPointer = codePointer + 0x400;
            uint codeVectorDeleterPointer  = codePointer + 0x500;
            uint codeIsRadsPointer         = codePointer + 0x600;

            league.WriteMemory(codeVerifyPointer, new byte[]
            {
                0xB8, 0x01, 0x00, 0x00, 0x00, 0xC3, 0x90, 0x90,
                0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90,
            });
            league.WriteMemory(codePrefixFnPointer, new byte[]
            {
                0x57, 0x56, 0x8b, 0x54, 0x24, 0x0c, 0x8b, 0x74,
                0x24, 0x14, 0x89, 0xd7, 0xac, 0xaa, 0x84, 0xc0,
                0x75, 0xfa, 0x8b, 0x74, 0x24, 0x10, 0x83, 0xef,
                0x01, 0xac, 0xaa, 0x84, 0xc0, 0x75, 0xfa, 0x5e,
                0x89, 0xd0, 0x5f, 0xc3, 0x90, 0x90, 0x90, 0x90,
                0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90,
            });
            league.WriteMemory(codeOpenPointer, new byte[]
            {
                0x56, 0x53, 0x81, 0xec, 0x14, 0x02, 0x00, 0x00,
                0x8b, 0x41, 0x04, 0x8b, 0x58, 0x08, 0x8b, 0x03,
                0x8b, 0x30, 0x8d, 0x41, 0x0c, 0x89, 0x44, 0x24,
                0x08, 0x8b, 0x84, 0x24, 0x20, 0x02, 0x00, 0x00,
                0x89, 0x44, 0x24, 0x04, 0x8d, 0x44, 0x24, 0x10,
                0x89, 0x04, 0x24, 0xff, 0x51, 0x08, 0x8b, 0x94,
                0x24, 0x24, 0x02, 0x00, 0x00, 0x89, 0xd9, 0x89,
                0x04, 0x24, 0x89, 0x54, 0x24, 0x04, 0xff, 0xd6,
                0x83, 0xec, 0x08, 0x81, 0xc4, 0x14, 0x02, 0x00,
                0x00, 0x5b, 0x5e, 0xc2, 0x08, 0x00, 0x90, 0x90,
            });
            league.WriteMemory(codeCheckAccessPointer, new byte[]
            {
                0x56, 0x53, 0x81, 0xec, 0x14, 0x02, 0x00, 0x00,
                0x8b, 0x41, 0x04, 0x8b, 0x58, 0x08, 0x8b, 0x03,
                0x8b, 0x70, 0x04, 0x8d, 0x41, 0x0c, 0x89, 0x44,
                0x24, 0x08, 0x8b, 0x84, 0x24, 0x20, 0x02, 0x00,
                0x00, 0x89, 0x44, 0x24, 0x04, 0x8d, 0x44, 0x24,
                0x10, 0x89, 0x04, 0x24, 0xff, 0x51, 0x08, 0x8b,
                0x94, 0x24, 0x24, 0x02, 0x00, 0x00, 0x89, 0xd9,
                0x89, 0x04, 0x24, 0x89, 0x54, 0x24, 0x04, 0xff,
                0xd6, 0x83, 0xec, 0x08, 0x81, 0xc4, 0x14, 0x02,
                0x00, 0x00, 0x5b, 0x5e, 0xc2, 0x08, 0x00, 0x90,
            });
            league.WriteMemory(codeCreateIteratorPointer, new byte[]
            {
                0x31, 0xc0, 0xc2, 0x08, 0x00, 0x90, 0x90, 0x90,
                0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90,
            });
            league.WriteMemory(codeVectorDeleterPointer, new byte[]
            {
                0x89, 0xc8, 0xc2, 0x04, 0x00, 0x90, 0x90, 0x90,
                0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90,
            });
            league.WriteMemory(codeIsRadsPointer, new byte[]
            {
                0x31, 0xc0, 0xc3, 0x90, 0x90, 0x90, 0x90, 0x90,
                0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90,
            });

            // Mark shellcode executable
            // League AC will trip over if we allocate ReadWriteExecutable in one go
            // So page can only be either ReadWrite or Executable
            league.MarkMemoryExecutable(codePointer, 0x900);

            uint modifiedPMethPointer      = league.Allocate <EVP_PKEY_METHOD>();
            uint orgignalPMethArrayPointer = this.PMethArrayOffset + league.Base;

            // Read first pointer when it gets initialized(tnx pacman)
            uint originalPMethFirstPointer = league.WaitPointerNonZero(orgignalPMethArrayPointer);

            // Read first PKEY_METHOD
            EVP_PKEY_METHOD originalPMeth = league.Read <EVP_PKEY_METHOD>(originalPMethFirstPointer);

            // Change verify function pointer
            originalPMeth.verify = codeVerifyPointer;

            // Write our new PKEY_METHOD
            league.Write(modifiedPMethPointer, originalPMeth);

            // Write the pointer to out PKEY_METHOD into pointer array
            league.Write(orgignalPMethArrayPointer, modifiedPMethPointer);

            uint orginalFileProviderListPointer = this.FileProviderListOffset + league.Base;

            // Those get deallocated upon exit so we need separate pages
            uint modifiedFileProviderPointer       = league.Allocate <FileProvider>();
            uint modifiedFileProviderVtablePointer = league.Allocate <FileProviderVtable>();

            league.Write(modifiedFileProviderPointer, new FileProvider
            {
                vtable   = modifiedFileProviderVtablePointer,
                list     = orginalFileProviderListPointer,
                prefixFn = codePrefixFnPointer,
                prefix   = _prefixBytes,
            });
            league.Write(modifiedFileProviderVtablePointer, new FileProviderVtable
            {
                Open           = codeOpenPointer,
                CheckAccess    = codeCheckAccessPointer,
                CreateIterator = codeCreateIteratorPointer,
                VectorDeleter  = codeVectorDeleterPointer,
                IsRads         = codeIsRadsPointer,
            });

            // Wait until providers have been registerd(first pointer turns non-0)
            league.WaitPointerNonZero(orginalFileProviderListPointer);
            FileProviderList originalFileProviderList = league.Read <FileProviderList>(orginalFileProviderListPointer);

            league.Write(orginalFileProviderListPointer, new FileProviderList
            {
                fileProviderPointer0 = modifiedFileProviderPointer,
                fileProviderPointer1 = originalFileProviderList.fileProviderPointer0,
                fileProviderPointer2 = originalFileProviderList.fileProviderPointer1,
                fileProviderPointer3 = originalFileProviderList.fileProviderPointer2,
                size = originalFileProviderList.size + 1,
            });
        }