• 创建GDI位图对象CreateBitmap函数逆向分析


    分析的时windows 10 21h2

    CreateBitmap 在3环会先调用gdi32.dll 同名函数接着调用 gdi32full.dll 的同名函数->再接着w32u.dll 的NtGdiCreateBitmap 让后进入内核

    __int64 __fastcall NtGdiCreateBitmap(unsigned int a1, unsigned int a2, unsigned int a3, unsigned int a4, char *Address)
    {
      __int64 Bitmap; // rbx
      HANDLE v10; // rdi
      unsigned __int64 v12; // r8
      unsigned __int64 v13; // r8
      char *v14; // rcx
    
      Bitmap = 1i64;
      v10 = 0i64;
      if ( Address )
      {
        v12 = ((a1 * (unsigned __int16)a3 * (unsigned __int64)(unsigned __int16)a4 + 15) >> 3) & 0x1FFFFFFFFFFFFFFEi64;
        if ( v12 <= 0xFFFFFFFF && (v13 = a2 * v12, v13 <= 0xFFFFFFFF) && (_DWORD)v13 )
        {
          v14 = &Address[(int)v13];
          if ( (unsigned __int64)v14 > MmUserProbeAddress || v14 < Address )
            *(_BYTE *)MmUserProbeAddress = 0;
          v10 = MmSecureVirtualMemory(Address, (int)v13, 2u);
          Bitmap = -(__int64)(v10 != 0i64) & 1;
        }
        else
        {
          Bitmap = 0i64;
        }
      }
      if ( Bitmap )
        Bitmap = GreCreateBitmap(a1, a2, a3, a4, Address);
      if ( v10 )
        MmUnsecureVirtualMemory(v10);
      return Bitmap;
    }
    会调用 win32kbase.sys 的
    GreCreateBitmap(a1, a2, a3, a4, Address); 进行bitmap 结构申请·和变量赋值
    __int64 __fastcall GreCreateBitmap(int a1, int a2, unsigned int a3, unsigned int a4, __int64 a5)
    {
      __int64 v5; // rdi
      unsigned int v6; // r10d
      unsigned __int64 v7; // r14
      int v8; // ebx
      __int64 v9; // rdx
      __int64 v10; // rsi
      __int64 v11; // r14
      __int64 v12; // rbx
      __int64 v13; // r8
      __int64 v15; // [rsp+50h] [rbp-30h] BYREF
      char v16; // [rsp+58h] [rbp-28h]
      int v17[4]; // [rsp+60h] [rbp-20h] BYREF
      _QWORD v18[2]; // [rsp+70h] [rbp-10h]
      int v19; // [rsp+A0h] [rbp+20h] BYREF
    
      v5 = 0i64;
      v6 = a4 * a3;
      if ( a1 <= 0
        || (unsigned int)a1 > 0x7FFFFFF
        || a2 <= 0
        || a3 > 0x20
        || a4 > 0x20
        || v6 > 0x20
        || (v7 = a2 * (unsigned __int64)(((a1 * v6 + 15) >> 3) & 0x1FFFFFFE), v7 > 0xFFFFFFFF) )
      {
        EngSetLastError(0x57u);
        return 0i64;
      }
      else
      {
        v17[3] = 0;
        v18[1] = 1i64;
        v17[1] = a1;
        v17[2] = a2;
        v18[0] = 0i64;
        if ( v6 > 1 )
        {
          v8 = 4;
          if ( v6 <= 4 )
          {
            v8 = 2;
          }
          else if ( v6 <= 8 )
          {
            v8 = 3;
          }
          else if ( v6 > 0x10 )
          {
            v8 = (v6 > 0x18) + 5;
          }
        }
        else
        {
          v8 = 1;
          v18[0] = WPP_MAIN_CB.Dpc.DeferredRoutine;
        }
        v17[0] = v8;
        v15 = 0i64;
        v16 = 0;
        SURFMEM::bCreateDIB((SURFMEM *)&v15, (struct _DEVBITMAPINFO *)v17, 0i64, 0i64, 0, 0i64, 0i64, 0, 1, 0);
        v10 = v15;
        if ( v15 )
        {
          *(_DWORD *)(v15 + 112) |= 0x4000000u;
          if ( a5 )
          {
            v19 = 0;
            if ( (int)IsGreSetBitmapBitsSupported_0() >= 0 )
              GreSetBitmapBits_0(*(_QWORD *)(v10 + 32), (unsigned int)v7, a5, &v19);
          }
          if ( v8 != 1 )
            *(_DWORD *)(v10 + 112) |= 0x800200u;
          v11 = *(_QWORD *)(v10 + 32);
          LOBYTE(v9) = 5;
          v16 |= 1u;
          v12 = HmgShareLockCheck(v11, v9);
          if ( v12 )
          {
            if ( (v11 & 0x800000) == 0 )
            {
              LOBYTE(v13) = 5;
              HmgSetOwner(v11, 2147483650i64, v13);
            }
            HmgDecrementShareReferenceCount(v12);
          }
          v5 = *(_QWORD *)(v10 + 32);
        }
        SURFMEM::~SURFMEM((SURFMEM *)&v15);
        return v5;
      }
    }

    接着调用

    SURFMEM::bCreateDIB   申请gib 对象 就结束了
    这里还涉及 对象大小计算 当nPlanes*nBitCount 不同结果导致不同的计算规则。
    
    
    当nPlanes*nBitCount=8时 有

    (nWidth+3)*nHeight+(对齐字节满足8字节对齐)+handle(0x10)+0x2b8 就是CreateBitmap 在内存的真正大小

    假定创建代码
      HGDIOBJ bitmap = CreateBitmap(1024, 2, 1, 8, NULL);

    这里我们用windbg 看是否是按这样计算的

    1: kd> !process 0 0 cs.exe
    PROCESS ffffbd0f9aacb300
        SessionId: 1  Cid: 1938    Peb: 0039d000  ParentCid: 0db0
        DirBase: 03f45000  ObjectTable: ffffe5030f923300  HandleCount:  51.
        Image: cs.exe
    1: kd> r $peb
    $peb=000000000039d000

    找GdiSharedHandleTable

    1: kd> dt nt!_peb 000000000039d000 GdiSharedHandleTable
       +0x0f8 GdiSharedHandleTable : 0x00000000`009d0000 Void
    1: kd> dq 0x00000000`009d0000+c02*18 L3
    00000000`009e2030 ffffffff`ff250c02 00052505`00001938
    00000000`009e2040 00000000`00000000
    GdiSharedHandleTable+ (返回句柄&0xffff)*18
    !pool ffffffff`ff250c02
    0xac8



    bCreateDIB  
     
    __int64 __fastcall SURFMEM::bCreateDIB(
            SURFMEM *this,
            struct _DEVBITMAPINFO *a2,
            void *a3,
            __int64 a4,
            unsigned int a5,
            void *a6,
            unsigned __int64 a7,
            int a8,
            int a9,
            int a10)
    {
      struct _DEVBITMAPINFO *v10; // r13
      int v11; // eax
      int v13; // r10d
      unsigned int v14; // edi
      unsigned int v15; // edi
      unsigned int v17; // edi
      unsigned int v18; // edi
      unsigned int v19; // edi
      unsigned int v20; // eax
      unsigned int v21; // edi
      bool v22; // cf
      unsigned int v23; // esi
      int v24; // r15d
      unsigned __int64 v25; // rcx
      __int64 v26; // rbx
      int v27; // eax
      int v28; // eax
      int v29; // eax
      PVOID v30; // rcx
      PVOID v31; // rax
      int v32; // r8d
      unsigned __int64 v33; // rcx
      int v34; // r15d
      int v35; // r12d
      __int64 v36; // rbx
      _QWORD *v37; // rax
      __int64 v38; // rbx
      void *v39; // rax
      __int64 v40; // r15
      __int64 v41; // r13
      __int64 v42; // r12
      __int64 v43; // rbx
      __int64 *CurrentThreadWin32ThreadAndEnterCriticalRegion; // rax
      __int64 v45; // rax
      signed __int32 v46; // eax
      unsigned int v47; // edx
      void *v48; // r12
      int v49; // r13d
      __int64 *ThreadWin32Thread; // rax
      __int64 v51; // rax
      _QWORD *v52; // rax
      __int64 CurrentProcess; // rax
      int v54; // edx
      __int64 v55; // r8
      __int64 v56; // r15
      __int64 v57; // rsi
      __int64 ProcessWin32Process; // rax
      __int64 v59; // rbx
      struct _ERESOURCE *v60; // rbx
      _QWORD *v61; // rax
      __int64 v62; // rax
      __int64 v63; // rax
      __int64 v64; // rax
      __int64 v65; // rax
      char v66; // si
      unsigned __int64 v67; // r12
      unsigned __int64 v68; // rbx
      __int64 *v69; // rax
      int v70; // edx
      __int64 v71; // rcx
      __int64 v72; // r8
      __int64 v73; // rax
      __int64 v74; // rax
      struct _ERESOURCE *v75; // rdi
      int v76; // r15d
      int v77; // esi
      struct _ERESOURCE *v78; // rdi
      __int64 CurrentProcessWin32Process; // rax
      __int64 v80; // rcx
      __int64 v81; // rdx
      unsigned int v82; // eax
      __int64 v83; // rax
      __int64 v84; // rdx
      int v85; // ecx
      unsigned int v86; // ecx
      unsigned int v87; // eax
      __int64 v88; // rdx
      int v89; // eax
      __int64 v90; // rdi
      __int64 *v91; // rax
      char v92; // r15
      __int64 v93; // rax
      __int64 v94; // r13
      unsigned int v95; // ebx
      bool v96; // zf
      signed __int32 v97; // eax
      struct _BASEOBJECT *v98; // rax
      __int64 v99; // r15
      struct _BASEOBJECT *v100; // rdx
      unsigned int v101; // r8d
      int v102; // ebx
      unsigned int v103; // ebx
      unsigned int CurrentProcessId; // eax
      struct _KTHREAD *CurrentThread; // rax
      __int128 v106; // xmm0
      __int64 v107; // rax
      __int128 v108; // xmm1
      __int128 v109; // xmm0
      PVOID v110; // rcx
      int v111; // eax
      __int64 v112; // rdi
      PVOID v113; // rbx
      __int64 v114; // rax
      PVOID v115; // rcx
      PVOID Object; // [rsp+50h] [rbp-B0h] BYREF
      int v117; // [rsp+58h] [rbp-A8h]
      int v118; // [rsp+5Ch] [rbp-A4h]
      int v119; // [rsp+60h] [rbp-A0h]
      unsigned int v120; // [rsp+64h] [rbp-9Ch]
      struct _BASEOBJECT *v121; // [rsp+68h] [rbp-98h]
      void *v122; // [rsp+70h] [rbp-90h] BYREF
      int v123[2]; // [rsp+78h] [rbp-88h] BYREF
      PEPROCESS v124; // [rsp+80h] [rbp-80h] BYREF
      PEPROCESS Process; // [rsp+88h] [rbp-78h] BYREF
      __int32 v126; // [rsp+9Ch] [rbp-64h]
      int v127; // [rsp+A0h] [rbp-60h]
      unsigned int v128; // [rsp+A4h] [rbp-5Ch]
      _OWORD v129[3]; // [rsp+A8h] [rbp-58h] BYREF
      __int64 v130; // [rsp+D8h] [rbp-28h] BYREF
      int v131[5]; // [rsp+E0h] [rbp-20h] BYREF
      __int32 v132; // [rsp+F4h] [rbp-Ch]
      int v133; // [rsp+F8h] [rbp-8h]
      char v134[24]; // [rsp+100h] [rbp+0h] BYREF
      __int32 v135; // [rsp+160h] [rbp+60h]
      unsigned int v136; // [rsp+160h] [rbp+60h]
      PVOID pv; // [rsp+170h] [rbp+70h] BYREF
      __int64 v139; // [rsp+178h] [rbp+78h]
    
      v139 = a4;
      pv = a3;
      *((_BYTE *)this + 8) = 8;
      *(_QWORD *)this = 0i64;
      v10 = a2;
      v11 = *(_DWORD *)a2 - 1;
      v120 = 1;
      v118 = 0;
      v13 = 0;
      v14 = 0;
      switch ( v11 )
      {
        case 0:
          v15 = *((_DWORD *)a2 + 1);
          if ( v15 >= 0xFFFFFFE0 )
            return 0i64;
          v14 = ((v15 + 31) >> 3) & 0x1FFFFFFC;
          goto LABEL_17;
        case 1:
          v17 = *((_DWORD *)a2 + 1);
          if ( v17 >= 0xFFFFFFF8 )
            return 0i64;
          v14 = ((v17 + 7) >> 1) & 0x7FFFFFFC;
          goto LABEL_17;
        case 2:
          v18 = *((_DWORD *)a2 + 1);
          if ( v18 >= 0xFFFFFFFC )
            return 0i64;
          v14 = (v18 + 3) & 0xFFFFFFFC;
          goto LABEL_17;
        case 3:
          v19 = *((_DWORD *)a2 + 1);
          if ( v19 >= 0xFFFFFFFE || v19 + 1 >= 0x7FFFFFFF )
            return 0i64;
          v14 = (2 * v19 + 2) & 0xFFFFFFFC;
          goto LABEL_17;
        case 4:
          v20 = *((_DWORD *)a2 + 1);
          if ( v20 >= 0x55555554 )
            return 0i64;
          v14 = (3 * (v20 + 1)) & 0xFFFFFFFC;
          goto LABEL_17;
        case 5:
          v21 = *((_DWORD *)a2 + 1);
          if ( v21 >= 0x3FFFFFFF )
            return 0i64;
          v14 = 4 * v21;
    LABEL_17:
          v22 = a8 != 0;
          a8 = -a8;
          v23 = SURFACE::tSize;
          Object = 0i64;
          memset(v129, 0, sizeof(v129));
          v24 = (v22 ? 8 : 0) | 6;
          v117 = v24;
          v119 = 0;
          v122 = 0i64;
          if ( a3 )
          {
            if ( !a9
              || (!v13 ? (v33 = v14 * (unsigned __int64)*((unsigned int *)a2 + 2)) : (v33 = *((unsigned int *)a2 + 3)),
                  v33 <= 0x7FFFFFFF) )
            {
              if ( (*((_DWORD *)a2 + 6) & 0x800) == 0 )
                goto LABEL_54;
              W32PIDLOCK::vInit((W32PIDLOCK *)v129);
              if ( *((_QWORD *)&v129[2] + 1) )
              {
                v118 = 2048;
                v119 = 1;
                goto LABEL_54;
              }
            }
            return 0i64;
          }
          if ( v13 )
            v25 = *((unsigned int *)a2 + 3);
          else
            v25 = v14 * (unsigned __int64)*((unsigned int *)a2 + 2);
          v26 = v25 + (unsigned int)SURFACE::tSize;
          if ( v26 < v25 || (unsigned __int64)v26 > 0x7FFFFFFF )
            return 0i64;
          v27 = *((_DWORD *)a2 + 6);
          if ( (v27 & 0x40000) != 0 && v26 > 4096 )
            *((_DWORD *)a2 + 6) = v27 | 8;
          v28 = *((_DWORD *)a2 + 6);
          if ( (v28 & 8) != 0 )
          {
            if ( (v28 & 0x80u) == 0 )
              v29 = EngAllocUserMemEx((int)v26, 0x1C0000000ui64, &pv);
            else
              v29 = AllocateSharedSection(v26, 0xC0000000, &Object, &v122, &pv);
            if ( v29 >= 0 )
            {
              v30 = pv;
              v31 = Object;
    LABEL_42:
              if ( v30 || v31 )
                goto LABEL_54;
              goto LABEL_44;
            }
            return 0i64;
          }
          if ( (v28 & 0x810) != 0 )
          {
            if ( (v28 & 0x800) != 0 )
            {
              W32PIDLOCK::vInit((W32PIDLOCK *)v129);
              if ( !*((_QWORD *)&v129[2] + 1) )
                return 0i64;
              Object = 0i64;
              v123[1] = 0;
              v123[0] = v26 - v23;
              Win32CreateSection((unsigned int)&Object, 6, v32, (unsigned int)v123);
              v31 = Object;
              if ( !Object )
              {
                W32PIDLOCK::vCleanUp((W32PIDLOCK *)v129);
                return 0i64;
              }
            }
            else
            {
              AllocateKernelSection(v26, 0xC0000000, &pv);
              v31 = Object;
            }
            v30 = pv;
            if ( pv || v31 )
            {
              v118 = *((_DWORD *)v10 + 6) & 0x800 | 0x10;
              goto LABEL_42;
            }
          }
    LABEL_44:
          v23 = v26;
          if ( (*((_DWORD *)v10 + 6) & 2) == 0 )
          {
            LOWORD(v24) = v24 & 0xFFFB;
            v117 = v24;
          }
    LABEL_54:
          v34 = ((unsigned __int8)~(_BYTE)v24 >> 2) & 1;
          if ( gulGdiHmgrTraceObjectType == 5 )
          {
            v35 = 1;
            v23 += 160;
          }
          else
          {
            v35 = 0;
          }
          if ( dword_1C0104624 >= v23 )
          {
            v36 = qword_1C01046E8;
            if ( (int)IsWin32AllocateFromPagedLookasideListImplSupported_0() >= 0 )
            {
              v37 = (_QWORD *)Win32AllocateFromPagedLookasideListImpl_0(v36);
              v38 = (__int64)v37;
              if ( v37 )
              {
                if ( v34 )
                {
                  memset(v37, 0, v23);
                }
                else
                {
                  *v37 = 0i64;
                  v37[1] = 0i64;
                  v37[2] = 0i64;
                }
                if ( v35 )
                  RtlCaptureStackBackTrace(0, 0x14u, (PVOID *)(v23 + v38 - 160), 0i64);
                LOWORD(v135) = *(_WORD *)(v38 + 12);
                HIWORD(v135) = *(_WORD *)(v38 + 14) | 0x8000;
                _InterlockedExchange((volatile __int32 *)(v38 + 12), v135);
                goto LABEL_76;
              }
            }
          }
          if ( v34 )
          {
            v38 = 0i64;
            if ( v23 )
            {
              if ( (int)IsWin32AllocPoolImplSupported_0() >= 0 )
              {
                v39 = (void *)Win32AllocPoolImpl_0(33i64, v23, 892364871i64);
                v38 = (__int64)v39;
                if ( v39 )
                  memset(v39, 0, v23);
              }
            }
          }
          else
          {
            v38 = PALLOCMEM2(v23);
            if ( !v38 )
            {
    LABEL_236:
              EngSetLastError(8u);
              goto LABEL_237;
            }
            *(_QWORD *)v38 = 0i64;
            *(_QWORD *)(v38 + 8) = 0i64;
            *(_QWORD *)(v38 + 16) = 0i64;
          }
          if ( !v38 )
            goto LABEL_236;
          if ( v35 )
            RtlCaptureStackBackTrace(0, 0x14u, (PVOID *)(v23 + v38 - 160), 0i64);
    LABEL_76:
          *(_QWORD *)this = v38;
          v40 = 0i64;
          *(_QWORD *)(v38 + 56) = *(_QWORD *)((char *)v10 + 4);
          *(_WORD *)(*(_QWORD *)this + 100i64) = 0;
          *(_QWORD *)(*(_QWORD *)this + 136i64) = 0i64;
          *(_QWORD *)(*(_QWORD *)this + 216i64) = 0i64;
          v41 = *((_QWORD *)v10 + 2);
          if ( !v41 )
            goto LABEL_101;
          v42 = 0i64;
          if ( (unsigned __int16)v41 >= (unsigned int)gcMaxHmgr )
            goto LABEL_101;
          v43 = gpentHmgr + 24i64 * (unsigned __int16)v41;
          CurrentThreadWin32ThreadAndEnterCriticalRegion = (__int64 *)PsGetCurrentThreadWin32ThreadAndEnterCriticalRegion(v131);
          if ( CurrentThreadWin32ThreadAndEnterCriticalRegion )
          {
            v45 = *CurrentThreadWin32ThreadAndEnterCriticalRegion;
            if ( v45 )
              v40 = *(_QWORD *)(v45 + 72);
          }
    LABEL_81:
          _m_prefetchw((const void *)(v43 + 8));
          v46 = *(_DWORD *)(v43 + 8);
          v47 = v46 & 0xFFFFFFFE;
          v132 = v46;
          if ( (v46 & 0xFFFFFFFE) != (v131[0] & 0xFFFFFFFC) && v47 && (!v40 || v47 != *(_DWORD *)(v40 + 8))
            || (*(_BYTE *)(v43 + 15) & 0x20) != 0 )
          {
            KeLeaveCriticalRegion();
    LABEL_101:
            *(_QWORD *)(*(_QWORD *)this + 120i64) = 0i64;
            goto LABEL_102;
          }
          while ( (*(_BYTE *)(v43 + 15) & 0x40) == 0 )
          {
            if ( (v46 & 1) != 0 )
            {
              KeDelayExecutionThread(0, 0, gpLockShortDelay);
              goto LABEL_81;
            }
            v133 = v46 | 1;
            if ( v46 != _InterlockedCompareExchange((volatile signed __int32 *)(v43 + 8), v46 | 1, v46)
              || (*(_BYTE *)(v43 + 15) & 0x40) != 0 )
            {
              goto LABEL_81;
            }
            *((_QWORD *)gpentPushLock + (unsigned __int16)v41) = 0i64;
            *(_BYTE *)(v43 + 15) |= 0x40u;
            _m_prefetchw((const void *)(v43 + 8));
            v132 = *(_DWORD *)(v43 + 8) & 0xFFFFFFFE;
            _InterlockedExchange((volatile __int32 *)(v43 + 8), v132);
            v46 = v132;
          }
          ExAcquirePushLockExclusiveEx((char *)gpentPushLock + 8 * (unsigned __int16)v41, 0i64);
          if ( *(_BYTE *)(v43 + 14) == 8 && *(_WORD *)(v43 + 12) == WORD1(v41) )
          {
            v42 = *(_QWORD *)v43;
            ++*(_DWORD *)(*(_QWORD *)v43 + 8i64);
          }
          if ( (*(_BYTE *)(v43 + 15) & 0x40) != 0 )
          {
            ExReleasePushLockExclusiveEx((char *)gpentPushLock + 8 * (unsigned __int16)v41, 0i64);
          }
          else
          {
            _m_prefetchw((const void *)(v43 + 8));
            v132 = *(_DWORD *)(v43 + 8) & 0xFFFFFFFE;
            _InterlockedExchange((volatile __int32 *)(v43 + 8), v132);
          }
          KeLeaveCriticalRegion();
          if ( !v42 )
            goto LABEL_101;
          *(_QWORD *)(*(_QWORD *)this + 120i64) = v42;
    LABEL_102:
          v48 = a6;
          v49 = a10;
          *(_DWORD *)(*(_QWORD *)this + 96i64) = *(_DWORD *)a2;
          *(_WORD *)(*(_QWORD *)this + 102i64) = v118 | *((_WORD *)a2 + 12) & 0x89;
          *(_QWORD *)(*(_QWORD *)this + 176i64) = v139;
          *(_DWORD *)(*(_QWORD *)this + 192i64) = a5;
          *(_QWORD *)(*(_QWORD *)this + 184i64) = v48;
          *(_QWORD *)(*(_QWORD *)this + 200i64) = a7;
          *(_DWORD *)(*(_QWORD *)this + 208i64) = v49;
          *(_QWORD *)(*(_QWORD *)this + 24i64) = 0i64;
          *(_QWORD *)(*(_QWORD *)this + 40i64) = 0i64;
          *(_DWORD *)(*(_QWORD *)this + 112i64) = *((_DWORD *)a2 + 6) & 0x40000;
          *(_QWORD *)(*(_QWORD *)this + 128i64) = 0i64;
          *(_QWORD *)(*(_QWORD *)this + 144i64) = 0i64;
          *(_QWORD *)(*(_QWORD *)this + 152i64) = 0i64;
          *(_DWORD *)(*(_QWORD *)this + 160i64) = 0;
          *(_QWORD *)(*(_QWORD *)this + 168i64) = 0i64;
          *(_QWORD *)(*(_QWORD *)this + 48i64) = 0i64;
          *(_QWORD *)(*(_QWORD *)this + 104i64) = 0i64;
          ThreadWin32Thread = (__int64 *)PsGetThreadWin32Thread(KeGetCurrentThread());
          if ( ThreadWin32Thread )
          {
            v51 = *ThreadWin32Thread;
            if ( v51 )
              *(_QWORD *)(v51 + 304) = 0i64;
          }
          *(_QWORD *)(*(_QWORD *)this + 240i64) = 0i64;
          *(_QWORD *)(*(_QWORD *)this + 248i64) = 0i64;
          *(_QWORD *)(*(_QWORD *)this + 256i64) = 0i64;
          *(_QWORD *)(*(_QWORD *)this + 584i64) = 0i64;
          *(_DWORD *)(*(_QWORD *)this + 592i64) = 0;
          *(_DWORD *)(*(_QWORD *)this + 116i64) = 0;
          *(_QWORD *)(*(_QWORD *)this + 496i64) = 0i64;
          *(_QWORD *)(*(_QWORD *)this + 488i64) = 0i64;
          v52 = (_QWORD *)(*(_QWORD *)this + 224i64);
          v52[1] = v52;
          *v52 = v52;
          *(_DWORD *)(*(_QWORD *)this + 312i64) = 0;
          *(_DWORD *)(*(_QWORD *)this + 316i64) = 0;
          *(_QWORD *)(*(_QWORD *)this + 568i64) = 0i64;
          CurrentProcess = PsGetCurrentProcess();
          v56 = *(_QWORD *)this;
          v57 = CurrentProcess;
          if ( CurrentProcess )
          {
            ProcessWin32Process = PsGetProcessWin32Process(CurrentProcess);
            v59 = ProcessWin32Process;
            if ( !ProcessWin32Process
              || !*(_DWORD *)(ProcessWin32Process + 836)
              || !(unsigned int)IsImmersiveAppRestricted(ProcessWin32Process)
              || (*(_DWORD *)(v59 + 776) & 0x200) != 0 )
            {
              v57 = 0i64;
            }
          }
          v60 = ghsemHmgr;
          if ( ghsemHmgr )
          {
            PsEnterPriorityRegion();
            ExEnterCriticalRegionAndAcquireResourceExclusive(v60);
            LODWORD(v60) = (_DWORD)ghsemHmgr;
          }
          if ( gbLockEtw && (Microsoft_Windows_Win32kEnableBits & 0x10) != 0 )
            Template_pqz((unsigned int)L"ghsemHmgr", v54, v55, (_DWORD)v60, 16, (__int64)L"ghsemHmgr");
          *(_QWORD *)(v56 + 576) = v57;
          if ( gbLockEtw && (Microsoft_Windows_Win32kEnableBits & 0x10) != 0 )
            Template_pz(L"ghsemHmgr", &LockRelease, v55, ghsemHmgr, L"ghsemHmgr");
          if ( ghsemHmgr )
          {
            ExReleaseResourceAndLeaveCriticalRegion(ghsemHmgr);
            PsLeavePriorityRegion();
          }
          v61 = (_QWORD *)(*(_QWORD *)this + 440i64);
          v61[1] = v61;
          *v61 = v61;
          *(_QWORD *)(*(_QWORD *)this + 560i64) = 0i64;
          if ( v119 )
            *(_DWORD *)(*(_QWORD *)this + 116i64) |= 1u;
          if ( v48 && !v49 )
            *(_WORD *)(*(_QWORD *)this + 102i64) |= 4u;
          if ( pv || Object )
            *(_QWORD *)(*(_QWORD *)this + 72i64) = pv;
          else
            *(_QWORD *)(*(_QWORD *)this + 72i64) = *(_QWORD *)this + SURFACE::tSize;
          v10 = a2;
          v62 = *(_QWORD *)this;
          if ( (unsigned int)(*(_DWORD *)a2 - 7) <= 3 )
          {
            *(_WORD *)(v62 + 102) &= ~0x800u;
            *(_DWORD *)(*(_QWORD *)this + 88i64) = 0;
            *(_DWORD *)(*(_QWORD *)this + 64i64) = *((_DWORD *)a2 + 3);
            if ( (unsigned int)(*(_DWORD *)a2 - 9) <= 1 )
              *(_QWORD *)(*(_QWORD *)this + 80i64) = 0i64;
            else
              *(_QWORD *)(*(_QWORD *)this + 80i64) = *(_QWORD *)(*(_QWORD *)this + 72i64);
          }
          else
          {
            *(_DWORD *)(v62 + 64) = v14 * *((_DWORD *)a2 + 2);
            v63 = *(_QWORD *)this;
            if ( (*((_DWORD *)a2 + 6) & 1) != 0 )
            {
              *(_DWORD *)(v63 + 88) = v14;
              *(_QWORD *)(*(_QWORD *)this + 80i64) = *(_QWORD *)(*(_QWORD *)this + 72i64);
            }
            else
            {
              *(_DWORD *)(v63 + 88) = -v14;
              *(_QWORD *)(*(_QWORD *)this + 80i64) = *(_QWORD *)(*(_QWORD *)this + 72i64)
                                                   + *(_DWORD *)(*(_QWORD *)this + 64i64)
                                                   - v14;
            }
          }
          if ( *(char *)(*(_QWORD *)this + 102i64) < 0 )
          {
            *(_QWORD *)(*(_QWORD *)this + 520i64) = Object;
            *(_QWORD *)(*(_QWORD *)this + 528i64) = v122;
            *(_QWORD *)(*(_QWORD *)this + 536i64) = (char *)v122
                                                  + *(_QWORD *)(*(_QWORD *)this + 80i64)
                                                  - *(_QWORD *)(*(_QWORD *)this + 72i64);
            *(_DWORD *)(*(_QWORD *)this + 544i64) = 1;
            v64 = W32GetThreadWin32Thread(KeGetCurrentThread());
            if ( v64 && (v65 = *(_QWORD *)(v64 + 72)) != 0 )
            {
              *(_DWORD *)(*(_QWORD *)this + 548i64) = *(_DWORD *)(v65 + 8);
              *(_DWORD *)(*(_QWORD *)this + 552i64) = 1;
            }
            else
            {
              *(_DWORD *)(*(_QWORD *)this + 548i64) = 0;
              *(_DWORD *)(*(_QWORD *)this + 552i64) = 0;
            }
          }
          v66 = v117;
          v67 = 0i64;
          v136 = (unsigned __int16)v117;
          *(_DWORD *)(*(_QWORD *)this + 92i64) = _InterlockedIncrement((volatile signed __int32 *)&_ulGlobalSurfaceUnique);
          v121 = *(struct _BASEOBJECT **)this;
          v68 = (unsigned __int64)PsGetCurrentProcessId() & 0xFFFFFFFC;
          v69 = (__int64 *)PsGetThreadWin32Thread(KeGetCurrentThread());
          if ( v69 )
          {
            v73 = *v69;
            if ( v73 )
            {
              v74 = *(_QWORD *)(v73 + 72);
              if ( v74 )
                LODWORD(v68) = *(_DWORD *)(v74 + 8);
            }
          }
          v75 = ghsemHmgr;
          if ( ghsemHmgr )
          {
            PsEnterPriorityRegion();
            ExEnterCriticalRegionAndAcquireResourceExclusive(v75);
          }
          if ( gbLockEtw && (Microsoft_Windows_Win32kEnableBits & 0x10) != 0 )
            Template_pqz(v71, v70, v72, (_DWORD)ghsemHmgr, 16, (__int64)L"ghsemHmgr");
          v76 = v66 & 8;
          if ( (v66 & 8) == 0 )
          {
            v77 = v76 + 1;
            if ( (_DWORD)v68 )
            {
              if ( (_DWORD)v68 != -2147483630 )
              {
                v78 = ghsemHmgr;
                if ( ghsemHmgr )
                {
                  PsEnterPriorityRegion();
                  ExEnterCriticalRegionAndAcquireResourceExclusive(v78);
                }
                if ( gbLockEtw && (Microsoft_Windows_Win32kEnableBits & 0x10) != 0 )
                  Template_pqz(v71, v70, v72, (_DWORD)ghsemHmgr, 16, (__int64)L"ghsemHmgr");
                if ( (_DWORD)v68 == ((unsigned int)PsGetCurrentProcessId() & 0xFFFFFFFC) )
                {
                  CurrentProcessWin32Process = PsGetCurrentProcessWin32Process();
                  v81 = CurrentProcessWin32Process;
                  if ( CurrentProcessWin32Process )
                  {
                    v80 = *(unsigned int *)(CurrentProcessWin32Process + 60);
                    if ( (int)v80 < gProcessHandleQuota )
                    {
                      v80 = (unsigned int)(v80 + 1);
                      *(_DWORD *)(CurrentProcessWin32Process + 60) = v80;
                      v82 = *(_DWORD *)(CurrentProcessWin32Process + 64);
                      if ( (unsigned int)v80 > v82 )
                        v82 = v80;
                      *(_DWORD *)(v81 + 64) = v82;
                    }
                    else
                    {
                      v77 = 0;
                    }
                  }
                }
                else if ( PsLookupProcessByProcessId((HANDLE)(int)v68, &Process) >= 0 )
                {
                  v83 = PsGetProcessWin32Process(Process);
                  v84 = v83;
                  if ( v83 )
                  {
                    v85 = *(_DWORD *)(v83 + 60);
                    if ( v85 < gProcessHandleQuota )
                    {
                      v86 = v85 + 1;
                      *(_DWORD *)(v83 + 60) = v86;
                      v87 = *(_DWORD *)(v83 + 64);
                      if ( v86 > v87 )
                        v87 = v86;
                      *(_DWORD *)(v84 + 64) = v87;
                    }
                    else
                    {
                      v77 = 0;
                    }
                  }
                  ObfDereferenceObject(Process);
                }
                if ( gbLockEtw && (Microsoft_Windows_Win32kEnableBits & 0x10) != 0 )
                  Template_pz(v80, &LockRelease, v72, ghsemHmgr, L"ghsemHmgr");
                v71 = (__int64)ghsemHmgr;
                if ( ghsemHmgr )
                {
                  ExReleaseResourceAndLeaveCriticalRegion(ghsemHmgr);
                  PsLeavePriorityRegion();
                }
                if ( !v77 )
                  goto LABEL_185;
              }
            }
          }
          if ( ghFreeHmgr )
          {
            v72 = (unsigned __int16)ghFreeHmgr;
            v88 = gpentHmgr + 24i64 * (unsigned __int16)ghFreeHmgr;
            v71 = 65285i64;
            ghFreeHmgr = *(_QWORD *)v88;
            v89 = *(_WORD *)(v88 + 12) & 0xFF00 | 5;
            *(_WORD *)(v88 + 12) = v89;
            v67 = (int)v72 | (unsigned __int64)(v89 << 16);
          }
          else
          {
            if ( gcMaxHmgr >= (unsigned int)gMaxGdiHandleCount )
              goto LABEL_183;
            v71 = 3i64 * (unsigned int)gcMaxHmgr;
            *(_WORD *)(gpentHmgr + 24i64 * (unsigned int)gcMaxHmgr + 12) = 261;
            v67 = gcMaxHmgr++ | 0x1050000i64;
          }
          if ( !v67 )
          {
    LABEL_183:
            if ( !v76 )
              HmgDecProcessHandleCount((unsigned int)v68);
            goto LABEL_185;
          }
          v90 = gpentHmgr;
          v91 = (__int64 *)PsGetThreadWin32Thread(KeGetCurrentThread());
          v92 = v136;
          if ( v91 && (v93 = *v91) != 0 && (v136 & 0x10) == 0 )
            v94 = *(_QWORD *)(v93 + 72);
          else
            v94 = 0i64;
          PsGetCurrentThreadWin32ThreadAndEnterCriticalRegion(v134);
          v95 = (unsigned __int16)v67;
          v117 = (unsigned __int16)v67;
          v128 = (unsigned __int16)v67;
          _m_prefetchw((const void *)(v90 + 24i64 * (unsigned __int16)v67 + 8));
          v96 = (*(_BYTE *)(v90 + 24i64 * (unsigned __int16)v67 + 15) & 0x20) == 0;
          v97 = *(_DWORD *)(v90 + 24i64 * (unsigned __int16)v67 + 8);
          v126 = v97;
          if ( !v96 )
          {
    LABEL_209:
            KeLeaveCriticalRegion();
            goto LABEL_210;
          }
          while ( (*(_BYTE *)(v90 + 24i64 * (unsigned __int16)v67 + 15) & 0x40) == 0 )
          {
            if ( (v97 & 1) != 0 )
            {
              KeDelayExecutionThread(0, 0, gpLockShortDelay);
    LABEL_208:
              _m_prefetchw((const void *)(v90 + 24i64 * (unsigned __int16)v67 + 8));
              v96 = (*(_BYTE *)(v90 + 24i64 * (unsigned __int16)v67 + 15) & 0x20) == 0;
              v97 = *(_DWORD *)(v90 + 24i64 * (unsigned __int16)v67 + 8);
              v126 = v97;
              if ( !v96 )
                goto LABEL_209;
            }
            else
            {
              v127 = v97 | 1;
              if ( v97 != _InterlockedCompareExchange(
                            (volatile signed __int32 *)(v90 + 24i64 * (unsigned __int16)v67 + 8),
                            v97 | 1,
                            v97)
                || (*(_BYTE *)(v90 + 24i64 * (unsigned __int16)v67 + 15) & 0x40) != 0 )
              {
                goto LABEL_208;
              }
              *((_QWORD *)gpentPushLock + v128) = 0i64;
              *(_BYTE *)(v90 + 24i64 * (unsigned __int16)v67 + 15) |= 0x40u;
              _m_prefetchw((const void *)(v90 + 24i64 * (unsigned __int16)v67 + 8));
              v126 = *(_DWORD *)(v90 + 24i64 * (unsigned __int16)v67 + 8) & 0xFFFFFFFE;
              _InterlockedExchange((volatile __int32 *)(v90 + 24i64 * (unsigned __int16)v67 + 8), v126);
              v97 = v126;
            }
          }
          v99 = 8i64 * v128;
          ExAcquirePushLockExclusiveEx((char *)gpentPushLock + v99, 0i64);
          *(_BYTE *)(v90 + 24i64 * (unsigned __int16)v67 + 15) &= 0x40u;
          v100 = v121;
          v101 = v136;
          v102 = *(_DWORD *)(v90 + 24i64 * (unsigned __int16)v67 + 8);
          *(_QWORD *)(v90 + 24i64 * (unsigned __int16)v67) = v121;
          *(_BYTE *)(v90 + 24i64 * (unsigned __int16)v67 + 14) = 5;
          *(_QWORD *)(v90 + 24i64 * (unsigned __int16)v67 + 16) = 0i64;
          if ( (v136 & 8) != 0 )
          {
            v103 = v102 & 1;
          }
          else if ( v94 )
          {
            v103 = *(_DWORD *)(v94 + 8) ^ (*(_DWORD *)(v94 + 8) ^ v102) & 1;
          }
          else
          {
            CurrentProcessId = (unsigned int)PsGetCurrentProcessId();
            v100 = v121;
            v101 = v136;
            v103 = v102 & 1 | CurrentProcessId & 0xFFFFFFFC;
          }
          if ( (v101 & 1) != 0 )
          {
            if ( v94 )
              CurrentThread = *(struct _KTHREAD **)v94;
            else
              CurrentThread = KeGetCurrentThread();
            *((_QWORD *)v100 + 2) = CurrentThread;
          }
          ++gcCurHmgr;
          *((_WORD *)v100 + 6) = v101 & 1;
          *((_DWORD *)v100 + 2) = (v101 >> 1) & 1;
          *(_QWORD *)(v90 + 24i64 * (unsigned __int16)v67 + 16) = 0i64;
          *(_DWORD *)(v90 + 24i64 * (unsigned __int16)v67 + 8) = v103;
          if ( (*(_BYTE *)(v90 + 24i64 * (unsigned __int16)v67 + 15) & 0x40) != 0 )
          {
            ExReleasePushLockExclusiveEx((char *)gpentPushLock + v99, 0i64);
          }
          else
          {
            _m_prefetchw((const void *)(v90 + 24i64 * (unsigned __int16)v67 + 8));
            v126 = v103 & 0xFFFFFFFE;
            _InterlockedExchange((volatile __int32 *)(v90 + 24i64 * (unsigned __int16)v67 + 8), v103 & 0xFFFFFFFE);
          }
          KeLeaveCriticalRegion();
          v95 = v117;
          v92 = v136;
    LABEL_210:
          v96 = gbGdiHmgrStacks == 0;
          v98 = v121;
          *(_QWORD *)v121 = v67;
          if ( !v96 && gpentHmgrStacks )
          {
            RECSTACKBACKTRACE(v95);
            v98 = v121;
          }
          if ( (v92 & 2) != 0 && gbGdiHmgrAltStacks && gpentHmgrAltStacks )
            RECALTLOCKSTACKBACKTRACE(v95, v98);
          v10 = a2;
    LABEL_185:
          if ( gbLockEtw && (Microsoft_Windows_Win32kEnableBits & 0x10) != 0 )
            Template_pz(v71, &LockRelease, v72, ghsemHmgr, L"ghsemHmgr");
          if ( ghsemHmgr )
          {
            ExReleaseResourceAndLeaveCriticalRegion(ghsemHmgr);
            PsLeavePriorityRegion();
          }
          if ( v67 )
          {
            *(_QWORD *)(*(_QWORD *)this + 32i64) = **(_QWORD **)this;
            if ( (*(_WORD *)(*(_QWORD *)this + 102i64) & 0x800) != 0 && *((_QWORD *)&v129[2] + 1) )
            {
              v106 = v129[0];
              *(_QWORD *)(*(_QWORD *)this + 240i64) = Object;
              v107 = *(_QWORD *)this;
              v108 = v129[1];
              *(_OWORD *)(v107 + 264) = v106;
              v109 = v129[2];
              *(_OWORD *)(v107 + 280) = v108;
              *(_OWORD *)(v107 + 296) = v109;
              *(_QWORD *)(*(_QWORD *)this + 72i64) = 0i64;
              *(_QWORD *)(*(_QWORD *)this + 80i64) = 0i64;
              *(_DWORD *)(*(_QWORD *)this + 112i64) |= 0x200u;
            }
          }
          else
          {
            if ( *(_QWORD *)(*(_QWORD *)this + 120i64) )
            {
              v130 = *(_QWORD *)(*(_QWORD *)this + 120i64);
              XEPALOBJ::vUnrefPalette((XEPALOBJ *)&v130, 1);
              *(_QWORD *)(*(_QWORD *)this + 120i64) = 0i64;
            }
            FreeObject(*(_QWORD *)this, 5i64);
    LABEL_237:
            v110 = pv;
            v120 = 0;
            *(_QWORD *)this = 0i64;
            if ( v110 || Object )
            {
              v111 = *((_DWORD *)v10 + 6);
              if ( (v111 & 8) != 0 )
              {
                if ( (v111 & 0x80u) == 0 )
                {
                  EngFreeUserMem(v110);
                }
                else
                {
                  v112 = W32GetThreadWin32Thread(KeGetCurrentThread());
                  if ( *(_QWORD *)(v112 + 72) )
                  {
                    v113 = pv;
                    v114 = PsGetCurrentProcess();
                    MmUnmapViewOfSection(v114, v113);
                    if ( PsLookupProcessByProcessId((HANDLE)*(int *)(*(_QWORD *)(v112 + 72) + 8i64), &v124) >= 0 )
                    {
                      MmUnmapViewOfSection(v124, v122);
                      ObfDereferenceObject(v124);
                    }
                    v115 = Object;
                    if ( !Object )
                      KeBugCheckEx(0x50u, 0i64, 0i64, 0x6D626B47ui64, 0i64);
                    goto LABEL_251;
                  }
                }
              }
              else if ( (v118 & 0x800) != 0 )
              {
                W32PIDLOCK::vCleanUp((W32PIDLOCK *)v129);
                if ( !v119 )
                {
                  v115 = Object;
                  if ( !Object )
                    KeBugCheckEx(0x50u, 0i64, 0i64, 0x6D626B47ui64, 0i64);
    LABEL_251:
                  ObfDereferenceObject(v115);
                }
              }
              else if ( (v118 & 0x10) != 0 )
              {
                vFreeKernelSection(v110);
              }
            }
          }
          return v120;
        case 6:
        case 7:
        case 8:
        case 9:
          v13 = 1;
          goto LABEL_17;
        default:
          return 0i64;
      }
    }
    
    


  • 相关阅读:
    波卡(Polkadot)创始人Gavin Wood眼中加密世界
    DOT的目的是什么
    如何在波卡测试网上起验证人节点
    Polkadot波卡链众筹成本价与总量、创始人团队简介
    Polkadot验证节点的安全性和可用性
    RSA算法详解
    haproxy+keepalived原理特点
    haproxy+keepalived原理特点
    haproxy+keepalived原理特点
    python基础1习题练习
  • 原文地址:https://www.cnblogs.com/feizianquan/p/16114531.html
Copyright © 2020-2023  润新知