Esempio n. 1
0
static EFI_STATUS
get_info(CHAR16 *name, update_table *info_out)
{
	EFI_STATUS rc;
	update_info *info = NULL;
	UINTN info_size = 0;
	UINT32 attributes = 0;
	void *info_ptr = NULL;

	rc = read_variable(name, fwupdate_guid, &info_ptr, &info_size,
			   &attributes);
	if (EFI_ERROR(rc))
		return rc;
	info = (update_info *)info_ptr;

	if (info_size < sizeof (*info)) {
		Print(L"Update \"%s\" is is too small.\n", name);
		delete_variable(name, fwupdate_guid, attributes);
		return EFI_INVALID_PARAMETER;
	}

	if (info_size - sizeof (EFI_DEVICE_PATH) <= sizeof (*info)) {
		Print(L"Update \"%s\" is malformed, "
		      L"and cannot hold a file path.\n", name);
		delete_variable(name, fwupdate_guid, attributes);
		return EFI_INVALID_PARAMETER;
	}

	EFI_DEVICE_PATH *hdr = (EFI_DEVICE_PATH *)&info->dp;
	INTN is = EFI_FIELD_OFFSET(update_info, dp);
	if (is > (INTN)info_size) {
		Print(L"Update \"%s\" has an invalid file path.\n"
		      L"Device path offset is %d, but total size is %d\n",
		      name, is, info_size);
		delete_variable(name, fwupdate_guid, attributes);
		return EFI_INVALID_PARAMETER;
	}

	is = info_size - is;
	INTN sz = dp_size(hdr, info_size);
	if (sz < 0 || is < 0) {
invalid_size:
		Print(L"Update \"%s\" has an invalid file path.\n"
		      L"update info size: %d dp size: %d size for dp: %d\n",
		      name, info_size, sz, is);
		delete_variable(name, fwupdate_guid, attributes);
		return EFI_INVALID_PARAMETER;
	}
	if (is > (INTN)info_size)
		goto invalid_size;
	if (is != sz)
		goto invalid_size;

	info_out->info = info;
	info_out->size = info_size;
	info_out->attributes = attributes;

	return EFI_SUCCESS;
}
//
// read control space
//
VOID BdReadControlSpace(DBGKD_MANIPULATE_STATE64* manipulateState, STRING* additionalData, CONTEXT* contextRecord)
{
	STRING messageHeader;
	DBGKD_READ_MEMORY64* readMemory											= &manipulateState->ReadMemory;
	messageHeader.Length													= sizeof(DBGKD_MANIPULATE_STATE64);
	messageHeader.Buffer													= static_cast<CHAR8*>(static_cast<VOID*>(manipulateState));
	UINT32 readLength														= readMemory->TransferCount;
	if(readMemory->TransferCount > PACKET_MAX_SIZE - sizeof(DBGKD_MANIPULATE_STATE64))
		readLength															= PACKET_MAX_SIZE - sizeof(DBGKD_MANIPULATE_STATE64);

	switch(readMemory->TargetBaseAddress)
	{
	case 0:
		readLength															= sizeof(BdPcr->GdtBase);
		BdCopyMemory(additionalData->Buffer, &BdPcr->GdtBase, readLength);
		additionalData->Length												= static_cast<UINT16>(readLength);
		manipulateState->ReturnStatus										= STATUS_SUCCESS;
		readMemory->ActualBytesRead											= readLength;
		break;

	case 1:
		readLength															= EFI_FIELD_OFFSET(KPRCB, CurrentThread);
		BdCopyMemory(additionalData->Buffer, BdPcr, readLength);
		additionalData->Length												= static_cast<UINT16>(readLength);
		manipulateState->ReturnStatus										= STATUS_SUCCESS;
		readMemory->ActualBytesRead											= readLength;
		break;

	case 2:
		readLength															= BdMoveMemory(additionalData->Buffer, &BdPrcb->ProcessorState.SpecialRegisters, sizeof(KSPECIAL_REGISTERS));
		additionalData->Length												= static_cast<UINT16>(readLength);
		manipulateState->ReturnStatus										= STATUS_SUCCESS;
		readMemory->ActualBytesRead											= readLength;
		break;

	default:
		manipulateState->ReturnStatus										= STATUS_UNSUCCESSFUL;
		readMemory->ActualBytesRead											= 0;
		additionalData->Length												= 0;
		break;
	}

	BdSendPacket(PACKET_TYPE_KD_STATE_MANIPULATE, &messageHeader, additionalData);
}