/* * Copyright (C) 2014 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.server.hdmi; import android.util.SparseArray; /** * This class handles the incoming messages when HdmiCecService is in the standby mode. */ public final class HdmiCecStandbyModeHandler { private interface CecMessageHandler { boolean handle(HdmiCecMessage message); } private static final class Bystander implements CecMessageHandler { @Override public boolean handle(HdmiCecMessage message) { return true; } } private static final class Bypasser implements CecMessageHandler { @Override public boolean handle(HdmiCecMessage message) { return false; } } private final class Aborter implements CecMessageHandler { private final int mReason; public Aborter(int reason) { mReason = reason; } @Override public boolean handle(HdmiCecMessage message) { mService.maySendFeatureAbortCommand(message, mReason); return true; } } private final class AutoOnHandler implements CecMessageHandler { @Override public boolean handle(HdmiCecMessage message) { if (!mTv.getAutoWakeup()) { mAborterRefused.handle(message); return true; } return false; } } private final class UserControlProcessedHandler implements CecMessageHandler { @Override public boolean handle(HdmiCecMessage message) { // The power status here is always standby. if (HdmiCecLocalDevice.isPowerOnOrToggleCommand(message)) { return false; } else if (HdmiCecLocalDevice.isPowerOffOrToggleCommand(message)) { return true; } return mAborterIncorrectMode.handle(message); } } private final HdmiControlService mService; private final HdmiCecLocalDeviceTv mTv; private final SparseArray mCecMessageHandlers = new SparseArray<>(); private final CecMessageHandler mDefaultHandler = new Aborter( Constants.ABORT_UNRECOGNIZED_OPCODE); private final CecMessageHandler mAborterIncorrectMode = new Aborter( Constants.ABORT_NOT_IN_CORRECT_MODE); private final CecMessageHandler mAborterRefused = new Aborter(Constants.ABORT_REFUSED); private final CecMessageHandler mAutoOnHandler = new AutoOnHandler(); private final CecMessageHandler mBypasser = new Bypasser(); private final CecMessageHandler mBystander = new Bystander(); private final UserControlProcessedHandler mUserControlProcessedHandler = new UserControlProcessedHandler(); public HdmiCecStandbyModeHandler(HdmiControlService service, HdmiCecLocalDeviceTv tv) { mService = service; mTv = tv; addHandler(Constants.MESSAGE_IMAGE_VIEW_ON, mAutoOnHandler); addHandler(Constants.MESSAGE_TEXT_VIEW_ON, mAutoOnHandler); addHandler(Constants.MESSAGE_ACTIVE_SOURCE, mBystander); addHandler(Constants.MESSAGE_REQUEST_ACTIVE_SOURCE, mBystander); addHandler(Constants.MESSAGE_ROUTING_CHANGE, mBystander); addHandler(Constants.MESSAGE_ROUTING_INFORMATION, mBystander); addHandler(Constants.MESSAGE_SET_STREAM_PATH, mBystander); addHandler(Constants.MESSAGE_STANDBY, mBystander); addHandler(Constants.MESSAGE_SET_MENU_LANGUAGE, mBystander); addHandler(Constants.MESSAGE_DEVICE_VENDOR_ID, mBystander); addHandler(Constants.MESSAGE_USER_CONTROL_RELEASED, mBystander); addHandler(Constants.MESSAGE_REPORT_POWER_STATUS, mBystander); addHandler(Constants.MESSAGE_FEATURE_ABORT, mBystander); addHandler(Constants.MESSAGE_INACTIVE_SOURCE, mBystander); addHandler(Constants.MESSAGE_SYSTEM_AUDIO_MODE_STATUS, mBystander); addHandler(Constants.MESSAGE_REPORT_AUDIO_STATUS, mBystander); // If TV supports the following messages during power-on, ignore them and do nothing, // else reply with ["Unrecognized Opcode"] // , , , addHandler(Constants.MESSAGE_RECORD_STATUS, mBystander); // If TV supports the following messages during power-on, reply with ["Not // in correct mode to respond"], else reply with ["Unrecognized Opcode"] // ,