Loading services/core/java/com/android/server/hdmi/FeatureAction.java +27 −2 Original line number Diff line number Diff line Loading @@ -18,11 +18,13 @@ package com.android.server.hdmi; import android.os.Handler; import android.os.Looper; import android.os.Message; import android.util.Pair; import android.util.Slog; import com.android.internal.annotations.VisibleForTesting; import com.android.server.hdmi.HdmiControlService.DevicePollingCallback; import java.util.ArrayList; import java.util.List; /** Loading Loading @@ -59,6 +61,8 @@ abstract class FeatureAction { // Timer that manages timeout events. protected ActionTimer mActionTimer; private ArrayList<Pair<FeatureAction, Runnable>> mOnFinishedCallbacks; FeatureAction(HdmiCecLocalDevice source) { mSource = source; mService = mSource.getService(); Loading Loading @@ -220,9 +224,23 @@ abstract class FeatureAction { * Finish up the action. Reset the state, and remove itself from the action queue. */ protected void finish() { finish(true); } void finish(boolean removeSelf) { clear(); if (removeSelf) { removeAction(this); } if (mOnFinishedCallbacks != null) { for (Pair<FeatureAction, Runnable> actionCallbackPair: mOnFinishedCallbacks) { if (actionCallbackPair.first.mState != STATE_NONE) { actionCallbackPair.second.run(); } } mOnFinishedCallbacks = null; } } protected final HdmiCecLocalDevice localDevice() { return mSource; Loading @@ -244,10 +262,17 @@ abstract class FeatureAction { return mSource.getDeviceInfo().getPhysicalAddress(); } protected void sendUserControlPressedAndReleased(int targetAddress, int uiCommand) { protected final void sendUserControlPressedAndReleased(int targetAddress, int uiCommand) { sendCommand(HdmiCecMessageBuilder.buildUserControlPressed( getSourceAddress(), targetAddress, uiCommand)); sendCommand(HdmiCecMessageBuilder.buildUserControlReleased( getSourceAddress(), targetAddress)); } protected final void addOnFinishedCallback(FeatureAction action, Runnable runnable) { if (mOnFinishedCallbacks == null) { mOnFinishedCallbacks = new ArrayList<>(); } mOnFinishedCallbacks.add(Pair.create(action, runnable)); } } services/core/java/com/android/server/hdmi/HdmiCecLocalDevice.java +5 −4 Original line number Diff line number Diff line Loading @@ -65,7 +65,7 @@ abstract class HdmiCecLocalDevice { // Note that access to this collection should happen in service thread. private final LinkedList<FeatureAction> mActions = new LinkedList<>(); private Handler mHandler = new Handler () { private final Handler mHandler = new Handler () { @Override public void handleMessage(Message msg) { switch (msg.what) { Loading Loading @@ -482,6 +482,7 @@ abstract class HdmiCecLocalDevice { @ServiceThreadOnly void removeAction(final FeatureAction action) { assertRunOnServiceThread(); action.finish(false); mActions.remove(action); checkIfPendingActionsCleared(); } Loading @@ -502,8 +503,8 @@ abstract class HdmiCecLocalDevice { while (iter.hasNext()) { FeatureAction action = iter.next(); if (action != exception && action.getClass().equals(clazz)) { action.clear(); mActions.remove(action); action.finish(false); iter.remove(); } } checkIfPendingActionsCleared(); Loading Loading @@ -645,7 +646,7 @@ abstract class HdmiCecLocalDevice { Iterator<FeatureAction> iter = mActions.iterator(); while (iter.hasNext()) { FeatureAction action = iter.next(); action.finish(); action.finish(false); iter.remove(); } } Loading services/core/java/com/android/server/hdmi/HdmiCecLocalDeviceTv.java +7 −0 Original line number Diff line number Diff line Loading @@ -537,10 +537,17 @@ final class HdmiCecLocalDeviceTv extends HdmiCecLocalDevice { } @ServiceThreadOnly // Seq #32 void changeSystemAudioMode(boolean enabled, IHdmiControlCallback callback) { assertRunOnServiceThread(); if (!mService.isControlEnabled() || hasAction(DeviceDiscoveryAction.class)) { setSystemAudioMode(false, true); invokeCallback(callback, HdmiControlManager.RESULT_INCORRECT_MODE); return; } HdmiCecDeviceInfo avr = getAvrDeviceInfo(); if (avr == null) { setSystemAudioMode(false, true); invokeCallback(callback, HdmiControlManager.RESULT_TARGET_NOT_AVAILABLE); return; } Loading services/core/java/com/android/server/hdmi/HotplugDetectionAction.java +1 −1 Original line number Diff line number Diff line Loading @@ -219,7 +219,7 @@ final class HotplugDetectionAction extends FeatureAction { return; } // Should ave only one Device Select Action // Should have only one Device Select Action DeviceSelectAction action = actions.get(0); if (action.getTargetAddress() == address) { removeAction(DeviceSelectAction.class); Loading services/core/java/com/android/server/hdmi/SystemAudioAction.java +25 −1 Original line number Diff line number Diff line Loading @@ -23,14 +23,20 @@ import android.hardware.hdmi.IHdmiControlCallback; import android.os.RemoteException; import android.util.Slog; import java.util.List; /** * Base feature action class for SystemAudioActionFromTv and SystemAudioActionFromAvr. */ abstract class SystemAudioAction extends FeatureAction { private static final String TAG = "SystemAudioAction"; // Transient state to differentiate with STATE_NONE where the on-finished callback // will not be called. private static final int STATE_CHECK_ROUTING_IN_PRGRESS = 1; // State in which waits for <SetSystemAudioMode>. private static final int STATE_WAIT_FOR_SET_SYSTEM_AUDIO_MODE = 1; private static final int STATE_WAIT_FOR_SET_SYSTEM_AUDIO_MODE = 2; private static final int MAX_SEND_RETRY_COUNT = 2; Loading Loading @@ -65,7 +71,25 @@ abstract class SystemAudioAction extends FeatureAction { mCallback = callback; } // Seq #27 protected void sendSystemAudioModeRequest() { mState = STATE_CHECK_ROUTING_IN_PRGRESS; List<RoutingControlAction> routingActions = getActions(RoutingControlAction.class); if (!routingActions.isEmpty()) { // Should have only one Routing Control Action RoutingControlAction routingAction = routingActions.get(0); routingAction.addOnFinishedCallback(this, new Runnable() { @Override public void run() { sendSystemAudioModeRequestInternal(); } }); return; } sendSystemAudioModeRequestInternal(); } private void sendSystemAudioModeRequestInternal() { int avrPhysicalAddress = tv().getAvrDeviceInfo().getPhysicalAddress(); HdmiCecMessage command = HdmiCecMessageBuilder.buildSystemAudioModeRequest( getSourceAddress(), Loading Loading
services/core/java/com/android/server/hdmi/FeatureAction.java +27 −2 Original line number Diff line number Diff line Loading @@ -18,11 +18,13 @@ package com.android.server.hdmi; import android.os.Handler; import android.os.Looper; import android.os.Message; import android.util.Pair; import android.util.Slog; import com.android.internal.annotations.VisibleForTesting; import com.android.server.hdmi.HdmiControlService.DevicePollingCallback; import java.util.ArrayList; import java.util.List; /** Loading Loading @@ -59,6 +61,8 @@ abstract class FeatureAction { // Timer that manages timeout events. protected ActionTimer mActionTimer; private ArrayList<Pair<FeatureAction, Runnable>> mOnFinishedCallbacks; FeatureAction(HdmiCecLocalDevice source) { mSource = source; mService = mSource.getService(); Loading Loading @@ -220,9 +224,23 @@ abstract class FeatureAction { * Finish up the action. Reset the state, and remove itself from the action queue. */ protected void finish() { finish(true); } void finish(boolean removeSelf) { clear(); if (removeSelf) { removeAction(this); } if (mOnFinishedCallbacks != null) { for (Pair<FeatureAction, Runnable> actionCallbackPair: mOnFinishedCallbacks) { if (actionCallbackPair.first.mState != STATE_NONE) { actionCallbackPair.second.run(); } } mOnFinishedCallbacks = null; } } protected final HdmiCecLocalDevice localDevice() { return mSource; Loading @@ -244,10 +262,17 @@ abstract class FeatureAction { return mSource.getDeviceInfo().getPhysicalAddress(); } protected void sendUserControlPressedAndReleased(int targetAddress, int uiCommand) { protected final void sendUserControlPressedAndReleased(int targetAddress, int uiCommand) { sendCommand(HdmiCecMessageBuilder.buildUserControlPressed( getSourceAddress(), targetAddress, uiCommand)); sendCommand(HdmiCecMessageBuilder.buildUserControlReleased( getSourceAddress(), targetAddress)); } protected final void addOnFinishedCallback(FeatureAction action, Runnable runnable) { if (mOnFinishedCallbacks == null) { mOnFinishedCallbacks = new ArrayList<>(); } mOnFinishedCallbacks.add(Pair.create(action, runnable)); } }
services/core/java/com/android/server/hdmi/HdmiCecLocalDevice.java +5 −4 Original line number Diff line number Diff line Loading @@ -65,7 +65,7 @@ abstract class HdmiCecLocalDevice { // Note that access to this collection should happen in service thread. private final LinkedList<FeatureAction> mActions = new LinkedList<>(); private Handler mHandler = new Handler () { private final Handler mHandler = new Handler () { @Override public void handleMessage(Message msg) { switch (msg.what) { Loading Loading @@ -482,6 +482,7 @@ abstract class HdmiCecLocalDevice { @ServiceThreadOnly void removeAction(final FeatureAction action) { assertRunOnServiceThread(); action.finish(false); mActions.remove(action); checkIfPendingActionsCleared(); } Loading @@ -502,8 +503,8 @@ abstract class HdmiCecLocalDevice { while (iter.hasNext()) { FeatureAction action = iter.next(); if (action != exception && action.getClass().equals(clazz)) { action.clear(); mActions.remove(action); action.finish(false); iter.remove(); } } checkIfPendingActionsCleared(); Loading Loading @@ -645,7 +646,7 @@ abstract class HdmiCecLocalDevice { Iterator<FeatureAction> iter = mActions.iterator(); while (iter.hasNext()) { FeatureAction action = iter.next(); action.finish(); action.finish(false); iter.remove(); } } Loading
services/core/java/com/android/server/hdmi/HdmiCecLocalDeviceTv.java +7 −0 Original line number Diff line number Diff line Loading @@ -537,10 +537,17 @@ final class HdmiCecLocalDeviceTv extends HdmiCecLocalDevice { } @ServiceThreadOnly // Seq #32 void changeSystemAudioMode(boolean enabled, IHdmiControlCallback callback) { assertRunOnServiceThread(); if (!mService.isControlEnabled() || hasAction(DeviceDiscoveryAction.class)) { setSystemAudioMode(false, true); invokeCallback(callback, HdmiControlManager.RESULT_INCORRECT_MODE); return; } HdmiCecDeviceInfo avr = getAvrDeviceInfo(); if (avr == null) { setSystemAudioMode(false, true); invokeCallback(callback, HdmiControlManager.RESULT_TARGET_NOT_AVAILABLE); return; } Loading
services/core/java/com/android/server/hdmi/HotplugDetectionAction.java +1 −1 Original line number Diff line number Diff line Loading @@ -219,7 +219,7 @@ final class HotplugDetectionAction extends FeatureAction { return; } // Should ave only one Device Select Action // Should have only one Device Select Action DeviceSelectAction action = actions.get(0); if (action.getTargetAddress() == address) { removeAction(DeviceSelectAction.class); Loading
services/core/java/com/android/server/hdmi/SystemAudioAction.java +25 −1 Original line number Diff line number Diff line Loading @@ -23,14 +23,20 @@ import android.hardware.hdmi.IHdmiControlCallback; import android.os.RemoteException; import android.util.Slog; import java.util.List; /** * Base feature action class for SystemAudioActionFromTv and SystemAudioActionFromAvr. */ abstract class SystemAudioAction extends FeatureAction { private static final String TAG = "SystemAudioAction"; // Transient state to differentiate with STATE_NONE where the on-finished callback // will not be called. private static final int STATE_CHECK_ROUTING_IN_PRGRESS = 1; // State in which waits for <SetSystemAudioMode>. private static final int STATE_WAIT_FOR_SET_SYSTEM_AUDIO_MODE = 1; private static final int STATE_WAIT_FOR_SET_SYSTEM_AUDIO_MODE = 2; private static final int MAX_SEND_RETRY_COUNT = 2; Loading Loading @@ -65,7 +71,25 @@ abstract class SystemAudioAction extends FeatureAction { mCallback = callback; } // Seq #27 protected void sendSystemAudioModeRequest() { mState = STATE_CHECK_ROUTING_IN_PRGRESS; List<RoutingControlAction> routingActions = getActions(RoutingControlAction.class); if (!routingActions.isEmpty()) { // Should have only one Routing Control Action RoutingControlAction routingAction = routingActions.get(0); routingAction.addOnFinishedCallback(this, new Runnable() { @Override public void run() { sendSystemAudioModeRequestInternal(); } }); return; } sendSystemAudioModeRequestInternal(); } private void sendSystemAudioModeRequestInternal() { int avrPhysicalAddress = tv().getAvrDeviceInfo().getPhysicalAddress(); HdmiCecMessage command = HdmiCecMessageBuilder.buildSystemAudioModeRequest( getSourceAddress(), Loading