#define VL_POWERED_DOWN 0x01
#define VL_UNKNOWN1 0x06
+#define VL_REQUEST_POWER_STATUS_TIMEOUT 5000
+
using namespace CEC;
using namespace PLATFORM;
int64_t iActiveSourcePending /* = 0 */) :
CCECCommandHandler(busDevice, iTransmitTimeout, iTransmitWait, iTransmitRetries, iActiveSourcePending),
m_iPowerUpEventReceived(0),
- m_bCapabilitiesSent(false)
+ m_bCapabilitiesSent(false),
+ m_iPowerStatusRequested(0)
{
m_vendorId = CEC_VENDOR_PANASONIC;
}
int CVLCommandHandler::HandleDeviceVendorCommandWithId(const cec_command &command)
{
+ if (!m_processor->IsHandledByLibCEC(command.destination))
+ return CEC_ABORT_REASON_INVALID_OPERAND;
+
if (command.parameters[0] != 0x00 ||
command.parameters[1] != 0x80 ||
command.parameters[2] != 0x45)
// send capabilties
SendVendorCommandCapabilities(m_processor->GetLogicalAddress(), command.initiator);
+
+ // reactivate the source, so the tv switches channels
+ if (m_processor->IsActiveSource(m_processor->GetLogicalAddress()))
+ m_processor->GetDevice(m_processor->GetLogicalAddress())->TransmitActiveSource(false);
}
else if (command.parameters.At(4) == VL_POWERED_DOWN)
{
if (m_busDevice->GetLogicalAddress() != CECDEVICE_TV)
{
+ CCECBusDevice* tv = m_processor->GetTV();
+ if (tv && tv->GetStatus() != CEC_DEVICE_STATUS_PRESENT)
+ return true;
+
// get the status from the TV
- CCECBusDevice *tv = m_processor->GetTV();
if (tv && tv->GetCurrentVendorId() == CEC_VENDOR_PANASONIC)
{
CVLCommandHandler *handler = static_cast<CVLCommandHandler *>(tv->GetHandler());
{
CLockObject lock(m_mutex);
m_iPowerUpEventReceived = 0;
+ m_bCapabilitiesSent = false;
}
return CCECCommandHandler::HandleStandby(command);
bool bTransmit(false);
{
CLockObject lock(m_mutex);
- bTransmit = m_bCapabilitiesSent;
+ bTransmit = !m_bCapabilitiesSent;
}
if (bTransmit)
SendVendorCommandCapabilities(m_processor->GetLogicalAddress(), CECDEVICE_TV);
void CVLCommandHandler::SendVendorCommandCapabilities(const cec_logical_address initiator, const cec_logical_address destination)
{
- cec_command response;
- cec_command::Format(response, initiator, destination, CEC_OPCODE_VENDOR_COMMAND);
- uint8_t iResponseData[] = {0x10, 0x02, 0xFF, 0xFF, 0x00, 0x05, 0x05, 0x45, 0x55, 0x5c, 0x58, 0x32};
- response.PushArray(12, iResponseData);
-
- if (Transmit(response, false, true))
+ if (PowerUpEventReceived())
{
- if (PowerUpEventReceived())
+ cec_command response;
+ cec_command::Format(response, initiator, destination, CEC_OPCODE_VENDOR_COMMAND);
+ uint8_t iResponseData[] = {0x10, 0x02, 0xFF, 0xFF, 0x00, 0x05, 0x05, 0x45, 0x55, 0x5c, 0x58, 0x32};
+ response.PushArray(12, iResponseData);
+
+ if (Transmit(response, false, true))
{
CLockObject lock(m_mutex);
m_bCapabilitiesSent = true;
if (command.parameters.size == 3 &&
command.parameters[0] == 0x10 &&
command.parameters[1] == 0x01 &&
- command.parameters[2] == 0x05)
+ command.parameters[2] == 0x05 &&
+ m_processor->IsHandledByLibCEC(command.destination))
{
SendVendorCommandCapabilities(m_processor->GetLogicalAddress(), command.initiator);
return COMMAND_HANDLED;
return CEC_ABORT_REASON_INVALID_OPERAND;
}
+bool CVLCommandHandler::TransmitRequestPowerStatus(const cec_logical_address iInitiator, const cec_logical_address iDestination, bool bWaitForResponse /* = true */)
+{
+ m_iPowerStatusRequested = GetTimeMs();
+ return CCECCommandHandler::TransmitRequestPowerStatus(iInitiator, iDestination, bWaitForResponse);
+}
+
bool CVLCommandHandler::SourceSwitchAllowed(void)
{
+ int64_t now(GetTimeMs());
+ if (!PowerUpEventReceived() && now - m_iPowerStatusRequested > VL_REQUEST_POWER_STATUS_TIMEOUT)
+ TransmitRequestPowerStatus(m_processor->GetPrimaryDevice()->GetLogicalAddress(), CECDEVICE_TV, false);
+
return PowerUpEventReceived();
}