summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--services/core/java/com/android/server/hdmi/HdmiCecMessageValidator.java56
-rw-r--r--services/tests/servicestests/src/com/android/server/hdmi/HdmiCecMessageValidatorTest.java24
2 files changed, 79 insertions, 1 deletions
diff --git a/services/core/java/com/android/server/hdmi/HdmiCecMessageValidator.java b/services/core/java/com/android/server/hdmi/HdmiCecMessageValidator.java
index f0fab26760c0..fe97f701e089 100644
--- a/services/core/java/com/android/server/hdmi/HdmiCecMessageValidator.java
+++ b/services/core/java/com/android/server/hdmi/HdmiCecMessageValidator.java
@@ -122,7 +122,6 @@ public class HdmiCecMessageValidator {
addValidationInfo(Constants.MESSAGE_RECORD_STATUS,
new RecordStatusInfoValidator(), DEST_DIRECT);
- // TODO: Handle messages for the Timer Programming.
addValidationInfo(
Constants.MESSAGE_CLEAR_ANALOG_TIMER, new AnalogueTimerValidator(), DEST_DIRECT);
addValidationInfo(
@@ -141,6 +140,7 @@ public class HdmiCecMessageValidator {
Constants.MESSAGE_TIMER_CLEARED_STATUS,
new TimerClearedStatusValidator(),
DEST_DIRECT);
+ addValidationInfo(Constants.MESSAGE_TIMER_STATUS, new TimerStatusValidator(), DEST_DIRECT);
// Messages for the System Information.
FixedLengthValidator oneByteValidator = new FixedLengthValidator(1);
@@ -592,6 +592,46 @@ public class HdmiCecMessageValidator {
return false;
}
+ private boolean isValidProgrammedInfo(int programedInfo) {
+ return (isWithinRange(programedInfo, 0x00, 0x0B));
+ }
+
+ private boolean isValidNotProgrammedErrorInfo(int nonProgramedErrorInfo) {
+ return (isWithinRange(nonProgramedErrorInfo, 0x00, 0x0E));
+ }
+
+ private boolean isValidTimerStatusData(byte[] params, int offset) {
+ int programedIndicator = params[offset] & 0x10;
+ boolean durationAvailable = false;
+ if (programedIndicator == 0x10) {
+ // Programmed
+ int programedInfo = params[offset] & 0x0F;
+ if (isValidProgrammedInfo(programedInfo)) {
+ if (programedInfo == 0x09 || programedInfo == 0x0B) {
+ durationAvailable = true;
+ } else {
+ return true;
+ }
+ }
+ } else {
+ // Non programmed
+ int nonProgramedErrorInfo = params[offset] & 0x0F;
+ if (isValidNotProgrammedErrorInfo(nonProgramedErrorInfo)) {
+ if (nonProgramedErrorInfo == 0x0E) {
+ durationAvailable = true;
+ } else {
+ return true;
+ }
+ }
+ }
+ offset = offset + 1;
+ // Duration Available (2 bytes)
+ if (durationAvailable && params.length - offset >= 2) {
+ return (isValidDurationHours(params[offset]) && isValidMinute(params[offset + 1]));
+ }
+ return false;
+ }
+
private class PhysicalAddressValidator implements ParameterValidator {
@Override
public int isValid(byte[] params) {
@@ -809,4 +849,18 @@ public class HdmiCecMessageValidator {
return toErrorCode(isWithinRange(params[0], 0x00, 0x02) || (params[0] & 0xFF) == 0x80);
}
}
+
+ /**
+ * Check if the given timer status data parameter is valid. A valid parameter should lie within
+ * the range description defined in CEC 1.4 Specification : Operand Descriptions (Section 17)
+ */
+ private class TimerStatusValidator implements ParameterValidator {
+ @Override
+ public int isValid(byte[] params) {
+ if (params.length < 1) {
+ return ERROR_PARAMETER_SHORT;
+ }
+ return toErrorCode(isValidTimerStatusData(params, 0));
+ }
+ }
}
diff --git a/services/tests/servicestests/src/com/android/server/hdmi/HdmiCecMessageValidatorTest.java b/services/tests/servicestests/src/com/android/server/hdmi/HdmiCecMessageValidatorTest.java
index c84e10b44de8..553df3bafd00 100644
--- a/services/tests/servicestests/src/com/android/server/hdmi/HdmiCecMessageValidatorTest.java
+++ b/services/tests/servicestests/src/com/android/server/hdmi/HdmiCecMessageValidatorTest.java
@@ -329,6 +329,30 @@ public class HdmiCecMessageValidatorTest {
assertMessageValidity("40:43:03").isEqualTo(ERROR_PARAMETER);
}
+ @Test
+ public void isValid_timerStatus() {
+ // Programmed - Space available
+ assertMessageValidity("40:35:58").isEqualTo(OK);
+ // Programmed - Not enough space available
+ assertMessageValidity("40:35:B9:32:1C:4F").isEqualTo(OK);
+ // Not programmed - Date out of range
+ assertMessageValidity("40:35:82:3B").isEqualTo(OK);
+ // Not programmed - Duplicate
+ assertMessageValidity("40:35:EE:52:0C").isEqualTo(OK);
+
+ assertMessageValidity("4F:35:58").isEqualTo(ERROR_DESTINATION);
+ assertMessageValidity("F0:35:82").isEqualTo(ERROR_SOURCE);
+ assertMessageValidity("40:35").isEqualTo(ERROR_PARAMETER_SHORT);
+ // Programmed - Invalid programmed info
+ assertMessageValidity("40:35:BD").isEqualTo(ERROR_PARAMETER);
+ // Non programmed - Invalid not programmed error info
+ assertMessageValidity("40:35:DE").isEqualTo(ERROR_PARAMETER);
+ // Programmed - Might not be enough space available - Invalid duration hours
+ assertMessageValidity("40:35:BB:96:1C").isEqualTo(ERROR_PARAMETER);
+ // Not programmed - Duplicate - Invalid duration minutes
+ assertMessageValidity("40:35:EE:52:4A").isEqualTo(ERROR_PARAMETER);
+ }
+
private IntegerSubject assertMessageValidity(String message) {
return assertThat(mHdmiCecMessageValidator.isValid(buildMessage(message)));
}