1
mirror of https://github.com/rapid7/metasploit-payloads synced 2025-03-24 18:16:24 +01:00
2014-12-09 14:27:50 -06:00

139 lines
3.5 KiB
C

/*!
* @file adsi.c
* @brief Definitions for ADSI functionality.
*/
#include "extapi.h"
#include "wshelpers.h"
#include "adsi.h"
#include "adsi_interface.h"
/*! @brief The default page size to use when no page size is specified */
#define DEFAULT_PAGE_SIZE 1000
/*!
* @brief Perform an ADSI query against a domain.
* @param remote Pointer to the \c Remote instance.
* @param packet Pointer to the incoming \c Packet instance.
* @returns Indication of success or failure.
* @remark Real error codes are returned to the caller via a response packet.
*/
DWORD request_adsi_domain_query(Remote *remote, Packet *packet)
{
DWORD dwResult = ERROR_SUCCESS;
LPSTR lpValue = NULL;
LPWSTR lpwDomain = NULL;
LPWSTR lpwFilter = NULL;
LPWSTR* lpwFields = NULL;
DWORD fieldCount = 0;
DWORD fieldIndex = 0;
Packet * response = packet_create_response(packet);
Tlv fieldTlv;
DWORD maxResults;
DWORD pageSize;
do
{
if (!response)
{
BREAK_WITH_ERROR("[EXTAPI ADSI] Unable to create response packet", ERROR_OUTOFMEMORY);
}
lpValue = packet_get_tlv_value_string(packet, TLV_TYPE_EXT_ADSI_DOMAIN);
dprintf("[EXTAPI ADSI] Domain: %s", lpValue);
dwResult = to_wide_string(lpValue, &lpwDomain);
if (dwResult != ERROR_SUCCESS)
{
dprintf("[EXTAPI ADSI] Failed to get Domain");
break;
}
lpValue = packet_get_tlv_value_string(packet, TLV_TYPE_EXT_ADSI_FILTER);
dprintf("[EXTAPI ADSI] Filter: %s", lpValue);
dwResult = to_wide_string(lpValue, &lpwFilter);
if (dwResult != ERROR_SUCCESS)
{
dprintf("[EXTAPI ADSI] Failed to get Filter");
break;
}
maxResults = packet_get_tlv_value_uint(packet, TLV_TYPE_EXT_ADSI_MAXRESULTS);
dprintf("[EXTAPI ADSI] Max results will be %u", maxResults);
pageSize = packet_get_tlv_value_uint(packet, TLV_TYPE_EXT_ADSI_PAGESIZE);
dprintf("[EXTAPI ADSI] Page size specified as %u", pageSize);
// Set the page size to something sensible if not given.
if (pageSize == 0)
{
pageSize = DEFAULT_PAGE_SIZE;
}
// If max results is given, there's no point in having a page size
// that's bigger!
if (maxResults != 0)
{
pageSize = min(pageSize, maxResults);
}
dprintf("[EXTAPI ADSI] Page size will be %u", pageSize);
while (packet_enum_tlv(packet, fieldCount, TLV_TYPE_EXT_ADSI_FIELD, &fieldTlv) == ERROR_SUCCESS)
{
lpValue = (char*)fieldTlv.buffer;
dprintf("[EXTAPI ADSI] Field %u: %s", fieldCount, lpValue);
lpwFields = (LPWSTR*)realloc(lpwFields, sizeof(LPWSTR) * (fieldCount + 1));
if (lpwFields == NULL)
{
BREAK_WITH_ERROR("[EXTAPI ADSI] Unable to allocate memory", ERROR_OUTOFMEMORY);
}
dwResult = to_wide_string(lpValue, &lpwFields[fieldCount]);
if (dwResult != ERROR_SUCCESS)
{
dprintf("[EXTAPI ADSI] Failed to get field as wide string");
break;
}
++fieldCount;
}
dprintf("[EXTAPI ADSI] Field count: %u", fieldCount, lpValue);
if (dwResult == ERROR_SUCCESS)
{
dprintf("[EXTAPI ADSI] Beginning user enumeration");
dwResult = domain_query(lpwDomain, lpwFilter, lpwFields, fieldCount, maxResults, pageSize, response);
dprintf("[EXTAPI ADSI] Result of processing: %u (0x%x)", dwResult, dwResult);
}
} while (0);
if (lpwFields)
{
for (fieldIndex = 0; fieldIndex < fieldCount; ++fieldIndex)
{
if (lpwFields[fieldIndex])
{
free(lpwFields[fieldIndex]);
}
}
free(lpwFields);
}
if (lpwFilter)
{
free(lpwFilter);
}
if (lpwDomain)
{
free(lpwDomain);
}
dprintf("[EXTAPI ADSI] Transmitting response back to caller.");
if (response)
{
packet_transmit_response(dwResult, remote, response);
}
return dwResult;
}