Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Function kull_m_cred_create does not copy actual credentials blob size #436

Open
BubbleMaker2089 opened this issue Oct 25, 2023 · 2 comments

Comments

@BubbleMaker2089
Copy link

BubbleMaker2089 commented Oct 25, 2023

I'm trying to decrypt credential related to my email account

mimikatz # dpapi::cred /in:C:\Users\<user>\AppData\Local\Microsoft\Credentials\<cred_name>
**BLOB**
  dwVersion          : 00000001 - 1
  guidProvider       : {guidProvider       }
  dwMasterKeyVersion : 00000001 - 1
  guidMasterKey      : {guidMasterKey      }
  dwFlags            : 20000000 - 536870912 (system ; )
  dwDescriptionLen   : 00000030 - 48
  szDescription      : Local Credential Data

  algCrypt           : 00006610 - 26128 (CALG_AES_256)
  dwAlgCryptLen      : 00000100 - 256
  dwSaltLen          : 00000020 - 32
  pbSalt             : <hex_data>
  dwHmacKeyLen       : 00000000 - 0
  pbHmackKey         :
  algHash            : 0000800e - 32782 (CALG_SHA_512)
  dwAlgHashLen       : 00000200 - 512
  dwHmac2KeyLen      : 00000020 - 32
  pbHmack2Key        : <hex_data>
  dwDataLen          : 00000f50 - 3920
  pbData             :  <hex_data>
  dwSignLen          : 00000040 - 64
  pbSign             :  <hex_data>

Decrypting Credential:
 * volatile cache: GUID:{c2bc45ee-c920-468d-b1a3-ecb7254a46c5};KeyHash:f9eb130c630784e996a2e9de17fe8134cf9c2a59;Key:available
**CREDENTIAL**
  credFlags      : 00000030 - 48
  credSize       : 00000f4e - 3918
  credUnk0       : 00000000 - 0

  Type           : 00000001 - 1 - generic
  Flags          : 00000000 - 0
  LastWritten    : 24.10.2023 5:05:40
  unkFlagsOrSize : 00000000 - 0
  Persist        : 00000002 - 2 - local_machine
  AttributeCount : 0000000b - 11
  unk0           : 00000000 - 0
  unk1           : 00000000 - 0
  TargetName     : LegacyGeneric:target=MicrosoftAccount:user=<email>
  UnkData        : (null)
  Comment        : PersistedCredential
  TargetAlias    : (null)
  UserName       : <email>
  **CredentialBlob : (null)**
  CredentialBlobSize : 0

In kuhl_m_dpapi_cred.c in function kuhl_m_dpapi_cred we have kull_m_cred_create invocation for non legacy cred and it does not know how to parse correct size of a blob. the size is 0, however it is not.
Is there any fixes for this?

@BubbleMaker2089
Copy link
Author

BubbleMaker2089 commented Oct 25, 2023

The line

cred->CredentialBlobSize = *(PDWORD) ((PBYTE) cred->UserName + cred->dwUserName);

results in zero length for credentials blob.

PKULL_M_CRED_BLOB kull_m_cred_create(PVOID data/*, DWORD size*/)
{
	PKULL_M_CRED_BLOB cred = NULL;
	if(cred = (PKULL_M_CRED_BLOB) LocalAlloc(LPTR, sizeof(KULL_M_CRED_BLOB)))
	{
		RtlCopyMemory(cred, data, FIELD_OFFSET(KULL_M_CRED_BLOB, TargetName));
		cred->TargetName = (LPWSTR) ((PBYTE) data + FIELD_OFFSET(KULL_M_CRED_BLOB, TargetName));
		cred->dwUnkData = *(PDWORD) ((PBYTE) cred->TargetName + cred->dwTargetName);
		cred->UnkData = (LPWSTR) ((PBYTE) cred->TargetName + cred->dwTargetName + sizeof(DWORD));
		cred->dwComment = *(PDWORD) ((PBYTE) cred->UnkData + cred->dwUnkData);
		cred->Comment = (LPWSTR) ((PBYTE) cred->UnkData + cred->dwUnkData + sizeof(DWORD));
		cred->dwTargetAlias = *(PDWORD) ((PBYTE) cred->Comment + cred->dwComment);
		cred->TargetAlias = (LPWSTR) ((PBYTE) cred->Comment + cred->dwComment + sizeof(DWORD));
		cred->dwUserName = *(PDWORD) ((PBYTE) cred->TargetAlias + cred->dwTargetAlias);
		cred->UserName = (LPWSTR) ((PBYTE) cred->TargetAlias + cred->dwTargetAlias + sizeof(DWORD));
		cred->CredentialBlobSize = *(PDWORD) ((PBYTE) cred->UserName + cred->dwUserName);
		cred->CredentialBlob = (PBYTE) cred->UserName + cred->dwUserName + sizeof(DWORD);
		kprintf(L"In kull_m_cred_create: %d\n", cred->CredentialBlobSize); // 0 size
		// kprintf(L"In kull_m_cred_create %*s" L"  CredentialBlob      : %d\n", L"", cred->CredentialBlob);

		if(cred->AttributeCount)
			kull_m_cred_attributes_create(((PBYTE) cred->CredentialBlob + cred->CredentialBlobSize + (cred->CredentialBlobSize & 1)), &cred->Attributes, cred->AttributeCount);			

		kull_m_string_ptr_replace(&cred->TargetName, cred->dwTargetName);
		kull_m_string_ptr_replace(&cred->TargetAlias, cred->dwTargetAlias);
		kull_m_string_ptr_replace(&cred->Comment, cred->dwComment);
		kull_m_string_ptr_replace(&cred->UnkData, cred->dwUnkData);
		kull_m_string_ptr_replace(&cred->UserName, cred->dwUserName);
		kull_m_string_ptr_replace(&cred->CredentialBlob, cred->CredentialBlobSize);
	}
	return cred;
}

@BubbleMaker2089
Copy link
Author

Maybe I'm wrong, because for the same type of credential for another service I have non-zero blob size. Is it correct that Outlook does not store a password in credential file anymore?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant