SepAccessCheck

__int64 __fastcall SepAccessCheck(
        __int64 a1,
        void *a2,
        __int64 a3,
        __int64 a4,
        unsigned int a5,
        __int128 *a6,
        unsigned int a7,
        _DWORD *a8,
        unsigned int a9,
        char a10,
        unsigned int *a11,
        LUID **a12,
        int *a13,
        char a14,
        char a15,
        int *a16,
        __int64 *a17,
        char *a18,
        char *a19,
        char a20){
  unsigned int v20; 
  LUID **Privileges; 
  int *v23; 
  unsigned int v25; 
  unsigned int v26; 
  unsigned int v27; 
  __int16 v28; 
  __int64 v29; 
  INT64 v30; 
  INT64 v31; 
  int v32; 
  unsigned int v33; 
  void *v34; 
  unsigned int v35; 
  _DWORD *v36; 
  int *v37; 
  int v38; 
  int v39; 
  unsigned int v40; 
  int v41; 
  UINT8 v42; 
  int v43; 
  unsigned __int8 v44; 
  int v46; 
  __int64 v47; 
  int v48; 
  _DWORD *v49; 
  int v50; 
  int v51; 
  int v52; 
  int v53; 
  int v54; 
  int v55; 
  CHAR v56; 
  int v57; 
  int v58; 
  unsigned __int8 v59; 
  int *v60; 
  int v61; 
  char v62; 
  char v63; 
  unsigned int v64; 
  unsigned int v65; 
  int *v66; 
  __int64 v67; 
  bool v68; 
  int v69; 
  unsigned int *v70; 
  unsigned int v71; 
  unsigned int v72; 
  __int64 v73; 
  __int64 v74; 
  int *v75; 
  unsigned __int64 k; 
  unsigned int *v77; 
  __int64 v78; 
  __int64 v79; 
  __int64 v80; 
  int *v81; 
  unsigned __int64 i; 
  unsigned int *v83; 
  unsigned __int64 j; 
  unsigned int *v85; 
  __int64 v86; 
  VOID *PrincipalSelfSid; 
  VOID *PrincipalSelfSida; 
  UINT64 v89; 
  UINT64 v90; 
  INT64 v91; 
  INT64 v92; 
  INT64 v93; 
  INT64 v94; 
  INT64 v95; 
  char v96; 
  UINT8 v97; 
  char v98; 
  UINT8 v99; 
  UINT8 v100; 
  unsigned int PrivilegeCount; 
  unsigned int PrivilegeCount_4; 
  unsigned int v103; 
  _DWORD *v104; 
  INT64 v107; 
  int v108; 
  INT64 v109[2]; 
  __int128 v110; 
  __int128 v111; 
  v20 = 0;
  Privileges = a12;
  v23 = a16;
  if( !a4 )
    a4 = a3;
  v104 = a6;
  v25 = a5;
  v26 = a5;
  PrivilegeCount = 0;
  v100 = 0;
  v97 = 0;
  v99 = 0;
  PrivilegeCount_4 = a5;
  v103 = 1;
  *(_OWORD *)v109 = 0i64;
  v110 = 0i64;
  v111 = 0i64;
  if( (a5 & 0x1000000) != 0 )
  {
    v107 = *(_QWORD *)SeSecurityPrivilege;
    v108 = 0;
    if( !SepPrivilegeCheck(a4, (INT64)&v107, 1ui64, 1, a10) )
    {
      v27 = 0;
      v43 = -1073741727;
      v44 = v59;
LABEL_33:
      if( a14 )
      {
        if( a7 )
        {
          if( a7 >= 4 )
          {
            v79 = a7 - 1;
            if( a11 > (unsigned int *)&a13[v79] || &a11[v79] < (unsigned int *)a13 )
            {
              v80 = a7 & 0xFFFFFFFC;
              do
                v20 += 4;
              while( v20 < (unsigned int)v80 );
              v81 = a13;
              for( i = (unsigned __int64)(4 * v80) >> 2; i; --i )
                *v81++ = v43;
              v83 = a11;
              for( j = (unsigned __int64)(4 * v80) >> 2; j; --j )
                *v83++ = v27;
            }
          }
          if( v20 < a7 )
          {
            v85 = &a11[v20];
            v86 = a7 - v20;
            do
            {
              *(unsigned int *)((char *)v85 + (char *)a13 - (char *)a11) = v43;
              *v85++ = v27;
              --v86;
            }
            while( v86 );
          }
        }
        goto LABEL_35;
      }
LABEL_34:
      *a13 = v43;
      *a11 = v27;
LABEL_35:
      if( v43 < 0 )
      {
        if( a18 )
          *a18 = 0;
        if( a19 )
          *a19 = 1;
      }
      else
      {
        if( a18 )
          *a18 = 1;
        if( a19 )
          *a19 = 0;
      }
      return v44;
    }
    v25 = a5;
    v32 = 1;
    PrivilegeCount = 1;
    v26 = a5 & 0xFEFFFFFF;
    v100 = 1;
    v27 = a9 | 0x1000000;
    PrivilegeCount_4 = a5 & 0xFEFFFFFF;
    if( (a5 & 0xFEFFFFFF) == 0 )
      goto LABEL_46;
    v23 = a16;
  }
  else
  {
    v27 = a9;
  }
  v28 = *(_WORD *)(a1 + 2);
  if( (v28 & 4) != 0 )
  {
    if( v28 >= 0 )
    {
      v30 = *(_QWORD *)(a1 + 32);
    }
    else
    {
      v29 = *(unsigned int *)(a1 + 16);
      if( (_DWORD)v29 )
        v30 = a1 + v29;
      else
        v30 = 0i64;
    }
  }
  else
  {
    v30 = 0i64;
  }
  if( (v28 & 0x10) != 0 )
  {
    if( v28 < 0 )
    {
      v47 = *(unsigned int *)(a1 + 12);
      if( (_DWORD)v47 )
        v31 = a1 + v47;
      else
        v31 = 0i64;
    }
    else
    {
      v31 = *(_QWORD *)(a1 + 24);
    }
  }
  else
  {
    v31 = 0i64;
  }
  if( (*(_WORD *)(a1 + 2) & 4) == 0 || !v30 )
  {
    v46 = v27 | v25;
    v27 |= v25;
    if( (v25 & 0x2000000) != 0 )
      v27 = v46 & 0xFDFFFFFF | a8[3];
    if( (*(_DWORD *)(a4 + 200) & 0x4000) != 0 )
    {
      v27 = 0;
      v23[1] = 0;
      *((_BYTE *)v23 + 21) = 0;
      goto LABEL_62;
    }
    v32 = PrivilegeCount;
LABEL_45:
    Privileges = a12;
LABEL_46:
    v42 = 0;
    goto LABEL_29;
  }
  if( (v26 & 0x80000) == 0 )
  {
    v32 = PrivilegeCount;
LABEL_16:
    v33 = 1;
    goto LABEL_17;
  }
  v107 = SeTakeOwnershipPrivilege;
  v108 = 0;
  if( SepPrivilegeCheck(a4, (INT64)&v107, 1ui64, 1, a10) )
  {
    v27 |= 0x80000u;
    v26 = PrivilegeCount_4 & 0xFFF7FFFF;
    v32 = PrivilegeCount + 1;
    PrivilegeCount_4 = v26;
    ++PrivilegeCount;
    v42 = 1;
    v97 = 1;
    if( !v26 )
    {
      Privileges = a12;
      goto LABEL_29;
    }
    goto LABEL_16;
  }
  v107 = SeRelabelPrivilege;
  v108 = 0;
  v56 = SepPrivilegeCheck(a4, (INT64)&v107, 1ui64, 1, a10);
  v26 = PrivilegeCount_4;
  v32 = PrivilegeCount;
  if( v56 )
  {
    v26 = PrivilegeCount_4 & 0xFFF7FFFF;
    v99 = v33;
    v32 = PrivilegeCount + 1;
    PrivilegeCount_4 = v26;
    v27 |= 0x80000u;
    ++PrivilegeCount;
    if( !v26 )
      goto LABEL_45;
  }
LABEL_17:
  if( !*(_WORD *)(v30 + 4) )
  {
    v60 = a16;
    a16[3] = v26;
    v61 = *(_DWORD *)(a4 + 200);
    if( (v61 & 0x4000) != 0 )
    {
      v27 &= ~*a16;
      v60 = a16;
    }
    if( v26 == 0x2000000 )
    {
      if( v27 )
      {
LABEL_105:
        Privileges = a12;
        v42 = v97;
        goto LABEL_29;
      }
    }
    else if( !v26 && *v60 && v27 && (v61 & 0x6000) == 0 )
    {
      goto LABEL_105;
    }
    v27 = 0;
    goto LABEL_62;
  }
  if( a7 )
  {
    v34 = a6;
    v33 = a7;
    v103 = a7;
  }
  else
  {
    v34 = v109;
    DWORD1(v110) = -1;
    v104 = v109;
  }
  v35 = a5 & 0x2000000;
  if( (a5 & 0x2000000) == 0 && !a14 )
  {
    LODWORD(v93) = a7;
    LODWORD(v89) = v33;
    SepNormalAccessCheck(v26, a4, (VOID *)a3, v30, v31, a17, a2, v89, (INT64)v34, v93, 0, a15, (INT64)a16, a20);
    v36 = v104;
    v37 = a16;
    a16[3] = v104[6];
    if( v104[6] )
      goto LABEL_67;
    v38 = *(_DWORD *)(a4 + 200);
    if( (v38 & 0x10) != 0 )
    {
      if( (v38 & 8) != 0 )
        v55 = a8[1] & ~(*a8 | a8[2]) | 0x10D0000;
      else
        v55 = a8[3] | 0x1FFFFF;
      v40 = a5;
      v39 = 0;
      if( (v55 & a5) == 0 )
      {
LABEL_26:
        v37[3] = v39;
        if( v36[6] )
          goto LABEL_67;
        v41 = *(_DWORD *)(a4 + 200);
        if( (v41 & 0x2000) != 0 )
        {
LABEL_28:
          v32 = PrivilegeCount;
          v27 |= v40;
          v42 = v97;
          Privileges = a12;
          goto LABEL_29;
        }
        v51 = v40 | PrivilegeCount_4;
        if( (v41 & 0x4000) != 0 )
        {
          v52 = ~(v37[1] | v37[2]);
          v53 = v51 | *v37;
        }
        else
        {
          if( !*((_BYTE *)v37 + 20) )
          {
            v54 = 0;
LABEL_66:
            v36[6] = v54;
            if( !v54 )
              goto LABEL_28;
LABEL_67:
            v43 = -1073741790;
            v27 = 0;
            v44 = 1;
            goto LABEL_34;
          }
          v52 = v51 | *v37;
          v53 = ~v37[1];
        }
        v54 = v53 & v52;
        goto LABEL_66;
      }
      LODWORD(v94) = a7;
      LODWORD(v90) = v103;
      SepNormalAccessCheck(
        v55 & PrivilegeCount_4,
        a4,
        (VOID *)a3,
        v30,
        v31,
        a17,
        a2,
        v90,
        (INT64)v104,
        v94,
        1,
        a15,
        (INT64)a16,
        a20);
      v36 = v104;
      v37 = a16;
      v39 = v104[6];
    }
    else
    {
      v39 = 0;
    }
    v40 = a5;
    goto LABEL_26;
  }
  LODWORD(v93) = 0;
  LODWORD(v91) = a7;
  LODWORD(PrincipalSelfSid) = v33;
  SepMaximumAccessCheck(
    (INT64 *)a4,
    (VOID *)a3,
    v30,
    v31,
    a17,
    a2,
    (UINT64)PrincipalSelfSid,
    (INT64)v34,
    v91,
    v93,
    0,
    a15,
    (INT64)a16,
    a20);
  v48 = *(_DWORD *)(a4 + 200);
  if( (v48 & 0x10) != 0 )
  {
    if( (v48 & 8) != 0 )
      v58 = a8[1] & ~(*a8 | a8[2]) | 0x10D0000;
    else
      v58 = a8[3] | 0x1FFFFF;
    LODWORD(v95) = v58;
    LODWORD(v92) = a7;
    LODWORD(PrincipalSelfSida) = v103;
    SepMaximumAccessCheck(
      (INT64 *)a4,
      (VOID *)a3,
      v30,
      v31,
      a17,
      a2,
      (UINT64)PrincipalSelfSida,
      (INT64)v104,
      v92,
      v95,
      1,
      a15,
      (INT64)a16,
      a20);
    v48 = *(_DWORD *)(a4 + 200);
  }
  v49 = v104 + 7;
  v50 = v104[7];
  if( (v48 & 0x2000) == 0 )
  {
    if( (v48 & 0x4000) != 0 )
    {
      v57 = *a16;
      v50 &= a16[1] | a16[2];
    }
    else
    {
      if( !*((_BYTE *)a16 + 20) )
        goto LABEL_54;
      v50 &= a16[1];
      v57 = *a16;
    }
    v27 &= ~v57;
  }
LABEL_54:
  if( !a14 )
  {
    if( (~(v50 | 0x2000000) & PrivilegeCount_4) != 0 )
      goto LABEL_67;
    Privileges = a12;
    v27 |= v50;
    v32 = PrivilegeCount;
    v42 = v97;
LABEL_29:
    if( v27 )
    {
      v43 = 0;
      if( KeGetCurrentIrql() < 2u )
      {
        if( v32 )
        {
          SepAssemblePrivileges(PrivilegeCount, v100, v42, v99, (PRIVILEGE_SET **)Privileges);
          if( Privileges )
          {
            if( !*Privileges )
            {
              v44 = 0;
              v43 = -1073741801;
              v27 = 0;
              goto LABEL_33;
            }
          }
        }
      }
LABEL_32:
      v44 = 1;
      goto LABEL_33;
    }
LABEL_62:
    v43 = -1073741790;
    goto LABEL_32;
  }
  v62 = 0;
  v63 = 0;
  v64 = v27 | a5;
  if( v35 )
    v64 = -33554433;
  v65 = (v27 | a5) & 0xFDFFFFFF;
  if( !v35 )
    v65 = v27 | a5;
  v66 = a13;
  v67 = v103;
  do
  {
    v68 = (v64 & (*v49 | v27)) == 0;
    v69 = v64 & (*v49 | v27);
    *(int *)((char *)v66 + (char *)a11 - (char *)a13) = v69;
    if( v68 )
    {
      *v66 = -1073741790;
      v63 = 1;
    }
    else if( (~v69 & v65) != 0 )
    {
      *v66 = -1073741790;
      v63 = 1;
    }
    else
    {
      *v66 = 0;
      v62 = 1;
    }
    v49 += 12;
    ++v66;
    --v67;
  }
  while( v67 );
  v96 = v63;
  v98 = v62;
  v70 = a11;
  if( KeGetCurrentIrql() < 2u && v62 && PrivilegeCount )
  {
    SepAssemblePrivileges(PrivilegeCount, v100, v97, v99, (PRIVILEGE_SET **)a12);
    if( a12 && !*a12 )
    {
      v71 = v103;
      v44 = 0;
      v62 = 0;
      v63 = 1;
      v72 = 0;
      if( v103 >= 4 )
      {
        v73 = v103 - 1;
        if( a11 > (unsigned int *)&a13[v73] || &a11[v73] < (unsigned int *)a13 )
        {
          v74 = v103 & 0xFFFFFFFC;
          do
            v72 += 4;
          while( v72 < (unsigned int)v74 );
          v75 = a13;
          for( k = (unsigned __int64)(4 * v74) >> 2; k; --k )
            *v75++ = -1073741801;
          v70 = a11;
          memset((INT64)a11, 0i64);
          v63 = 1;
          v62 = 0;
          v71 = v103;
        }
      }
      if( v72 < v71 )
      {
        v77 = &v70[v72];
        v78 = v71 - v72;
        do
        {
          *(unsigned int *)((char *)v77 + (char *)a13 - (char *)v70) = -1073741801;
          *v77++ = 0;
          --v78;
        }
        while( v78 );
      }
      goto LABEL_143;
    }
    v63 = v96;
    v62 = v98;
  }
  v44 = 1;
LABEL_143:
  if( a18 )
    *a18 = v62;
  if( a19 )
    *a19 = v63;
  return v44;
}

Referenced by:

SeAccessCheckByTypeWithAdminlessChecks
SeAccessCheckWithHintWithAdminlessChecks
SepAccessCheckAndAuditAlarmWithAdminlessChecks