Skip to content

Commit

Permalink
added testing stuff
Browse files Browse the repository at this point in the history
  • Loading branch information
MrAle98 committed Feb 23, 2024
1 parent 93b7533 commit 1b102e5
Show file tree
Hide file tree
Showing 3 changed files with 42 additions and 15 deletions.
23 changes: 21 additions & 2 deletions impacket/krb5/crypto.py
Original file line number Diff line number Diff line change
Expand Up @@ -228,13 +228,32 @@ def decrypt(cls, key, keyusage, ciphertext):
basic_ctext, mac = bytearray(ciphertext[:-cls.macsize]), bytearray(ciphertext[-cls.macsize:])
if len(basic_ctext) % cls.padsize != 0:
raise ValueError('ciphertext does not meet padding requirement')
print(len(basic_ctext))
for i in basic_ctext:
print(f"{hex(i)},", end="")
print("")
print(len(mac))
for i in mac:
print(f"{hex(i)},", end="")
print("")
print(len(ciphertext))
for i in ciphertext:
print(f"{hex(i)},", end="")
basic_plaintext = cls.basic_decrypt(ke, bytes(basic_ctext))
tmp = basic_plaintext[cls.blocksize:]
padding = tmp[-16-16:-16]
basic_plaintext = basic_plaintext.replace(padding,b"\xff"*len(padding))
hmac = bytearray(HMAC.new(ki.contents, basic_plaintext, cls.hashmod).digest())
expmac = hmac[:cls.macsize]
print(hmac)
print(expmac)
print(mac)
if not _mac_equal(mac, expmac):
raise InvalidChecksum('ciphertext integrity failure')
print('ciphertext integrity failure')
else:
print('ciphertext integrity correct')
# Discard the confounder.
return bytes(basic_plaintext[cls.blocksize:])
return bytes(basic_plaintext[cls.blocksize:]),bytes(basic_plaintext[:cls.blocksize])

@classmethod
def prf(cls, key, string):
Expand Down
28 changes: 18 additions & 10 deletions impacket/krb5/gssapi.py
Original file line number Diff line number Diff line change
Expand Up @@ -226,7 +226,7 @@ def GSS_GetMIC(self, sessionKey, data, sequenceNumber, direction = 'init'):
# Let's pad the data
pad = (4 - (len(data) % 4)) & 0x3
padStr = chr(pad) * pad
data += padStr
data += padStr.encode()

checkSumProfile = self.checkSumProfile()

Expand All @@ -247,26 +247,28 @@ def unrotate(self, data, numBytes):
result = data[numBytes:] + data[:numBytes]
return result

def GSS_Wrap(self, sessionKey, data, sequenceNumber, direction = 'init', encrypt=True):
def GSS_Wrap(self, sessionKey, data, sequenceNumber, direction = 'init', encrypt=True,keyUsage=KG_USAGE_INITIATOR_SEAL,confounder=None):
token = self.WRAP()

cipher = self.cipherType()

# Let's pad the data
pad = (cipher.blocksize - (len(data) % cipher.blocksize)) & 15
pad = (cipher.blocksize - (len(data) % cipher.blocksize)) & 16
padStr = b'\xFF' * pad
data += padStr

# The RRC field ([RFC4121] section 4.2.5) is 12 if no encryption is requested or 28 if encryption
# is requested. The RRC field is chosen such that all the data can be encrypted in place.
rrc = 28

token['Flags'] = 6
if direction != 'init':
token['Flags'] = 7
else:
token['Flags'] = 6
token['EC'] = pad
token['RRC'] = 0
token['SND_SEQ'] = struct.pack('>Q',sequenceNumber)

cipherText = cipher.encrypt(sessionKey, KG_USAGE_INITIATOR_SEAL, data + token.getData(), None)
cipherText = cipher.encrypt(sessionKey, keyUsage, data + token.getData(), confounder)
token['RRC'] = rrc

cipherText = self.rotate(cipherText, token['RRC'] + token['EC'])
Expand All @@ -277,18 +279,24 @@ def GSS_Wrap(self, sessionKey, data, sequenceNumber, direction = 'init', encrypt

return ret1, ret2

def GSS_Unwrap(self, sessionKey, data, sequenceNumber, direction = 'init', encrypt=True, authData=None):
def GSS_Unwrap(self, sessionKey, data, sequenceNumber, direction = 'init', encrypt=True, authData=None,keyUsage=KG_USAGE_ACCEPTOR_SEAL):
from impacket.dcerpc.v5.rpcrt import SEC_TRAILER

cipher = self.cipherType()
token = self.WRAP(authData[len(SEC_TRAILER()):])

rotated = authData[len(self.WRAP())+len(SEC_TRAILER()):] + data

cipherText = self.unrotate(rotated, token['RRC'] + token['EC'])
plainText = cipher.decrypt(sessionKey, KG_USAGE_ACCEPTOR_SEAL, cipherText)

return plainText[:-(token['EC']+len(self.WRAP()))], None
# rotated = authData[len(self.WRAP())+len(SEC_TRAILER()):]
# cipherText = data + self.unrotate(rotated, token['RRC'] + token['EC'])
print(f"\ncipherText len={len(cipherText)}")
for i in cipherText:
print(f"{hex(i)},", end="")
plainText, confounder = cipher.decrypt(sessionKey, keyUsage, cipherText)

return plainText[:-(token['EC']+len(self.WRAP()))], confounder

class GSSAPI_AES256(GSSAPI_AES):
checkSumProfile = crypto._SHA1AES256
Expand Down
6 changes: 3 additions & 3 deletions impacket/krb5/kerberosv5.py
Original file line number Diff line number Diff line change
Expand Up @@ -189,7 +189,7 @@ def getKerberosTGT(clientName, password, domain, lmhash, nthash, aesKey='', kdcH
except KerberosError as e:
if e.getErrorCode() == constants.ErrorCodes.KDC_ERR_ETYPE_NOSUPP.value:
if supportedCiphers[0] in (constants.EncryptionTypes.aes128_cts_hmac_sha1_96.value, constants.EncryptionTypes.aes256_cts_hmac_sha1_96.value) and aesKey == b'':
supportedCiphers = (int(constants.EncryptionTypes.rc4_hmac.value),)
supportedCiphers = (int(constants.EncryptionTypes.aes256_cts_hmac_sha1_96.value),)
seq_set_iter(reqBody, 'etype', supportedCiphers)
message = encoder.encode(asReq)
r = sendReceive(message, domain, kdcHost)
Expand Down Expand Up @@ -439,10 +439,10 @@ def getKerberosTGS(serverName, domain, kdcHost, tgt, cipher, sessionKey):
reqBody['nonce'] = rand.getrandbits(31)
seq_set_iter(reqBody, 'etype',
(
int(cipher.enctype),
int(constants.EncryptionTypes.rc4_hmac.value),
int(constants.EncryptionTypes.des3_cbc_sha1_kd.value),
int(constants.EncryptionTypes.des_cbc_md5.value),
int(cipher.enctype)
int(constants.EncryptionTypes.des_cbc_md5.value)
)
)

Expand Down

0 comments on commit 1b102e5

Please sign in to comment.