Files
AVR/AVR Working Controller/AVRInterface.cpp
David 49edca0238 Add support for .ini file,
Add support for extended messages (advanced protocol),
Add handy command lines for Power, Volume in db, and Mute.
2026-01-31 14:39:37 -06:00

1386 lines
61 KiB
C++

//
// The AVR Interface object and interaction methods
//
#include <stdio.h>
#include <memory.h>
#include <string.h>
#include <malloc.h>
#include <ctype.h>
#include "AVRInterface.h"
#include "AVRCommandDecoder.h"
#define LONGESTTEXT 150
using AVRSubsys = AVRInterface::AVRSubsystem_T;
using AVRFunc = AVRInterface::AVRFunction_E;
using AVRArg = AVRInterface::AVRArg_T;
typedef enum {
eReady,
ePowerOn,
ePowerOff,
eVolumeUp,
eVolumeDown,
eMute,
eUnMute,
} AVRCommands_E;
typedef struct {
AVRCommands_E MsgID;
const char *pMsg;
uint16_t MsgLen;
} Message_T;
typedef struct {
//uint8_t type; // 0 to 4, and 0xFF for don't care
//uint8_t guard; // 0 to 2, and 0xFF for don't care
uint8_t rCmd;
uint8_t configOffset; // offset into the Config DT0 - DT155 array, or 0xFF for no action
uint8_t numToTransfer; // number of bytes to transfer into the Config array, or 0 for no action
bool showAll; // true to call ShowAllStatusInfo after processing
const char *TextFormatter; // used primarily for development printf(TextFormatter, value)
const char *(*fncValueToText)(uint8_t rDat);
} MessageHandler_T;
static const char * StateText[] = {
"Powering Up",
"Awaiting Ready Response",
"Initializing",
"Retry Initializing",
"Ready",
"Awaiting Response",
"Unknown State"
};
// This is based on the longest thing from the MessageHandlers text field and the generated text
// "MultiCh Surround" "Surround"
const char *PCMessageFormat = "%18s %-20s";
const uint8_t LengthCheck = 40;
// rCmd: 2-ASCII Hex Bytes converted to uint8_t
// configOffset: offset into avrStatus.config.DTxx
// numToTransfer: number of bytes to transfer from message to config (0 = none)
// show all status
// fncHelper: optional function to call upon receipt
//
static const MessageHandler_T MessageHandlers[] = {
//
// Configuration Map for Response Messages
//
// +--------------------------- rCmd
// | +----------------------- DT Block Offset
// | | +-------------------- Number of Bytes to transfer into the DT Block
// | | | +----------------- Force a 'show all' status screen update
// | | | |
// | | | | +-------- sprintf format string for the following Helper
// | | | | | +--- Helper to convert numeric value to text
// | | | | | |
{ 0x00, 7, 1, 1, "System Report: %s", BusyToText },
{ 0x01, 0, 0, 0, "Warning Report: %s", WarnToText },
{ 0x10, 31, 1, 1, "Playback Report: %s", PlaybackToText },
{ 0x11, 32, 1, 1, "Fs Report: %s", FsToText },
{ 0x12, 33, 1, 1, "Ex/Ex: %s", OffMatrixDiscreteText }, // EX/EX
{ 0x13, 34, 1, 1, "Thr Bypass: %s", OffOnText }, // Thr / Bypass
{ 0x14, 35, 1, 1, "RED dts: %s", ReleaseWaitText}, // RED dts
{ 0x15, 38, 1, 1, "Tuner tuned: %s", NotTunedTunedText}, // Tuner tuned
{ 0x16, 43, 1, 1, "DTS 96/24: %s", OffOnText}, // Dts 96/24
{ 0x20, 8, 0, 1, "Zone Power: %s", ZonePower },
{ 0x21, 9, 1, 1, "Input: %s", InputText}, // Input Source
{ 0x22, 11, 1, 1, "Input Mode: %s", InputModeText}, // Input Mode
{ 0x23, 12, 1, 1, "Mute: %s", OffOnText },
{ 0x24, 13, 1, 1, "Zone 2 Input: %s", InputText}, // Zone 2 Input Source
{ 0x25, 14, 1, 1, "Zone 2 Mute: %s", OffOnText },
{ 0x26, 15, 2, 1, "Volume: %s", VolumeDB },
{ 0x27, 17, 2, 1, "Zone 2 Vol: %s", VolumeDB}, // Zone 2 Vol
{ 0x28, 19, 2, 1, "Program: %s", ProgramName }, // Program
{ 0x29, 25, 1, 1, "Tuner Page: %s", PresetLabelText}, // Tuner Page
{ 0x2A, 26, 1, 1, "Tuner Preset: %s", PresetNumberText}, // Tuner Preset Number
{ 0x2B, 23, 1, 1, "OSD: %s", OSDFullShortOffText}, // OSD
{ 0x2C, 24, 1, 1, "Sleep: %s", SleepTimerText}, // Sleep Timer
{ 0x2D, 22, 1, 1, "EX/ES(Key): %s", OffMatrixDiscreteAutoText}, // EX/ES(Key)
{ 0x2E, 29, 1, 1, "SP Relay A: ", OffOnText}, // Speaker Relay A
{ 0x2F, 30, 1, 1, "SP Relay B: ", OffOnText}, // Speaker Relay B
{ 0x30, 0, 0, 0, "Home Preset:%s", PresetLabelText }, // Preset A, B, ... F
{ 0x31, 0, 0, 0, "Home Memory:%s", PresetLabelText }, // Preset A, B, ... F
{ 0x32, 0, 0, 0, "Home Vol Preset: %s", PresetLabelText }, // Preset A, B, ... F
{ 0x33, 0, 0, 0, "Home Vol Memory: %s", PresetLabelText }, // Preset A, B, ... F
{ 0x34, 36, 1, 1, "Headphone: %s", OffOnText },
{ 0x35, 37, 1, 1, "FM/AM: %s", FMAMText },
{ 0x36, 39, 1, 1, "DC1 Trigger Out: %s", OffOnText },
{ 0x37, 0, 0, 0, "Home Zone 2 Vol Preset: %s", PresetLabelText },
{ 0x38, 0, 0, 0, "Home Zone 2 Vol: %s", PresetLabelText },
{ 0x39, 0, 0, 0, "Dual Mono: %s", MainSubAllText },
{ 0x3A, 42, 1, 1, "DC1 Trigger Control: %s", WhichZoneText },
{ 0x3B, 44, 1, 1, "DC2 Trigger Control: %s", WhichZoneText },
{ 0x3C, 45, 1, 1, "DC2 Trigger Out: %s", OffOnText },
{ 0x3D, 104, 0, 0, "Main Level: %s", Norm10dbDownText },
{ 0x3E, 46, 1, 1, "SP B Set: %s", Zone1Zone2Text },
{ 0x3F, 47, 1, 1, "Zone 2 Speaker: %s", OffOnText },
{ 0x40, 48, 2, 1, "Level Main R: %s", PM10dbText },
{ 0x41, 50, 2, 1, "Level Main L: %s", PM10dbText },
{ 0x42, 52, 2, 1, "Level Center: %s", PM10dbText },
{ 0x43, 54, 2, 1, "Level Rear R: %s", PM10dbText },
{ 0x44, 56, 2, 1, "Level Rear L: %s", PM10dbText },
{ 0x45, 58, 2, 1, "Level Sur Back R: %s", PM10dbText },
{ 0x46, 60, 2, 1, "Level Sur Back L: %s", PM10dbText },
{ 0x47, 62, 2, 1, "Level Front R: %s", PM10dbText },
{ 0x48, 64, 2, 1, "Level Front L: %s", PM10dbText },
{ 0x49, 66, 2, 1, "Level Swfr 1: %s", PM10dbText },
{ 0x4A, 0, 0, 0, "Level Swfr 2: %s", PM10dbText },
{ 0x50, 0, 0, 0, "Main L/R Bal: %s", BalanceText },
{ 0x51, 74, 2, 1, "LFE Level SP: %s", M20P0dbText },
{ 0x52, 76, 2, 1, "LFE Level HP: %s", M20P0dbText },
{ 0x53, 78, 2, 1, "Audio Delay: %s", ZeroTo160msText },
{ 0x54, 0, 0, 0, "SP Delay Center: %s", ZeroTo5msText },
{ 0x55, 0, 0, 0, "SP Delay Rear CT: %s", ZeroTo30msText },
{ 0x60, 84, 1, 1, "Input Mode: %s", AutoLastText },
{ 0x61, 85, 1, 1, "Dimmer: %s", M4To0Text },
{ 0x62, 87, 2, 1, "OSD Shift: %s", M5toP5Text },
{ 0x63, 89, 1, 1, "Gray Back: %s", OffAutoText },
{ 0x64, 91, 1, 1, "Dynamic Range SP: %s", MaxStdMinText },
{ 0x65, 92, 1, 1, "Dynamic Range HP: %s", MaxStdMinText },
{ 0x66, 93, 0, 0, "Zone 2 Vol out: %s", VarFixText },
{ 0x67, 0, 0, 0, "Zone 2 Mode: %s", Mode1Mode2Text },
{ 0x68, 95, 1, 1, "Mem Guard: %s", OffOnText },
{ 0x69, 90, 1, 1, "Video Conv: %s", OffOnText },
{ 0x6A, 136, 1, 1, "Comp OSD: %s", OffOnText },
{ 0x6B, 0, 0, 0, "Zone 3 Vol out: %s", VarFixText },
{ 0x70, 96, 1, 1, "Center Sp Size: %s", LSNText },
{ 0x71, 97, 1, 1, "Main Sp Size: %s", LSNText },
{ 0x72, 98, 1, 1, "Rear LR Sp Size: %s", LSNText },
{ 0x73, 99, 1, 1, "Sur Back Size: %s", LLSSNText },
{ 0x74, 100, 1, 1, "Front Sp: %s", YesNoneText },
{ 0x75, 101, 1, 1, "LFE Bass Out: %s", SwfrMainBothText },
{ 0x76, 134, 1, 1, "SW1: %s", LrFrNoneText },
{ 0x78, 102, 1, 1, "6 Ch Center: %s", CenterMainText },
{ 0x79, 103, 1, 1, "6 Ch Swfr: %s", SwfrMainText },
{ 0x7A, 133, 1, 1, "6 Ch Surround: %s", SurrMainText },
{ 0x7B, 0, 0, 0, "Multi Ch Select: %s", SixEightText },
{ 0x7E, 135, 1, 1, "SW Crossover", CrossOverText },
{ 0x80, 105, 1, 1, "Test Mode: %s", OffDolbyDspText },
{ 0x81, 0, 0, 0, "Analog Special: %s", OffOn2OnMultiText },
{ 0x82, 27, 1, 1, "Night Mode: %s", OffOnText },
{ 0x90, 0, 0, 0, "Multi Ch Level Main R: %s", M10P10dbText },
{ 0x91, 0, 0, 0, "Multi Ch Level Main L: %s", M10P10dbText },
{ 0x92, 0, 0, 0, "Multi Ch Level Center: %s", M10P10dbText },
{ 0x93, 0, 0, 0, "Multi Ch Level Rear R: %s", M10P10dbText },
{ 0x94, 0, 0, 0, "Multi Ch Level Rear L: %s", M10P10dbText },
{ 0x95, 0, 0, 0, "Multi Ch Level Sur B R: %s", M10P10dbText },
{ 0x96, 0, 0, 0, "Multi Ch Level Sur B L: %s", M10P10dbText },
{ 0x97, 0, 0, 0, "Multi Ch Level Front R: %s", M10P10dbText },
{ 0x98, 0, 0, 0, "Multi Ch Level Front L: %s", M10P10dbText },
{ 0x99, 0, 0, 0, "Multi Ch Level Swfr 1: %s", M20P0dbText },
{ 0x9A, 0, 0, 0, "Multi Ch Level Swfr 2: %s", M20P0dbText },
{ 0xA1, 0, 0, 0, "Zone 3 Mute: %s\n", OffOnText },
};
AVRInterface::AVRInterface(bool (*SendMessage)(const uint8_t *buffer, uint16_t len)) {
SendMethod = SendMessage;
IsSanityCheckOK();
MessageHandlerSanityCheck();
Initialize();
}
AVRInterface::~AVRInterface() {
FreeMemory();
}
bool AVRInterface::IsSanityCheckOK() {
return true;
}
// MessageReport
//
// Generate a text record to provide buffer to the console, translating non-printable
// characters into hex codes enclosed in square brackets.
//
// Consider line-wrapping to align the next line
//
void AVRInterface::MessageReport(const char *prefix, const void *buf, size_t len) {
int i = 0;
const char *p = (const char *)buf;
uint32_t now_ms = lastTick_ms;
char txtBuf[LONGESTTEXT] = "";
char smallBuf[10] = "";
char *pTxtAppend = txtBuf;
if (len == 0) len = strlen(p);
pTxtAppend += sprintf_s(txtBuf, LONGESTTEXT, "%9.3f: [%3d]%s", (float)(now_ms - firstTick_ms) / 1000.0f, (int)strlen(p), prefix);
while (*p && ((unsigned)(p - (const char *)buf) < len)) {
if (isprint(*p)) {
*pTxtAppend++ = *p;
*pTxtAppend = 0; // Keep it null-terminated
i++;
} else if (*p == '\r') {
if (ReportInformation) { // Guard it
(*ReportInformation)(mtInfo, txtBuf);
}
txtBuf[0] = 0; // clear it
} else if (*p == '\n') {
// skip it
} else {
sprintf_s(smallBuf, 10, "[%02X]", (unsigned char)*p);
strcat_s(txtBuf, LONGESTTEXT, smallBuf);
pTxtAppend = txtBuf + strlen(txtBuf);
}
if ((i & 3) == 0) {
if (strlen(txtBuf) > 100) {
if (ReportInformation) { // Guard it
(*ReportInformation)(mtInfo, txtBuf);
}
sprintf_s(txtBuf, LONGESTTEXT, " "); // new line
pTxtAppend = txtBuf + strlen(txtBuf);
} else {
strcat_s(txtBuf, LONGESTTEXT, " ");
pTxtAppend++;
}
i = 0;
}
p++;
}
if (strlen(txtBuf)) {
if (ReportInformation) { // Guard it
(*ReportInformation)(mtInfo, txtBuf);
}
}
}
AVRInterface::AVRState_T AVRInterface::Tick(uint32_t now_ms) {
if (!bFirstTickInitialized) {
bFirstTickInitialized = true;
firstTick_ms = now_ms;
}
lastTick_ms = now_ms;
uint32_t elapsed_ms = now_ms - sentAtTime_ms;
char buf[LONGESTTEXT] = "";
if (oldState != state && ReportInformation) {
(*ReportInformation)(mtStatus, StateText[state]);
}
oldState = state;
switch (state) {
default:
case AVRState_T::stPoweringUp:
readyResponsReceived = false;
AVRCommand(sysCommand, fncReady, eOn);
(*ReportInformation)(mtInfo, "Send Ready");
sentAtTime_ms = now_ms;
readyTries++;
state = stAwaitingReadyResponse;
break;
case stAwaitingReadyResponse:
if (readyResponsReceived) {
state = stReady;
} else if (elapsed_ms > RETRY_INTERVAL_ms) {
if (readyTries > MAXTRIES) {
// fail
state = stFailed;
} else {
state = stPoweringUp;
}
}
break;
case AVRState_T::stInitializing:
break;
case AVRState_T::stRetryInitializing:
break;
case AVRState_T::stAwaitingResponse:
if (commandResponseReceived) {
state = stReady;
} else if (elapsed_ms > RETRY_INTERVAL_ms) {
ProcessSerialQueue();
state = stAwaitingResponse;
}
break;
case AVRState_T::stReady:
ProcessSerialQueue();
break;
}
return state;
}
/// @brief Handle a just received message by parsing it
///
/// Given a response string, typically of the form:
/// [02] .... [03] // Command Responses from the AVR
/// [11] .... [03] // Commands to
/// [12] .... [03]
/// [14] ............ [03]
///
/// @param buffer contains the message
/// @param len of the message
/// @return true, if data was accepted and the overall status changed, so might be shown
///
bool AVRInterface::HandleMessage(const uint8_t *buffer, uint16_t len) {
bool showAllFlag = false;
MessageReport("<", buffer, len);
switch (state) {
case stAwaitingReadyResponse:
switch (buffer[0]) {
case 0x02: // STX <msg> ETX
commandResponseReceived = true;
showAllFlag = ProcessReportResponse(buffer, len);
break;
case 0x11: // DC1 <msg> ETX
// AVR does not send any DC1 messages, these are for commands to the AVR
break;
case 0x12: // DC2 <msg> ETX
if (CheckTheChecksum(buffer, len)) {
if (len == 21) { // Short message when power is off
memcpy(&avrStatus.header, &buffer[1], sizeof(AVR_StatusHeader_T));
len = Hex2Dec(&avrStatus.header.length[0], 2);
memcpy(&avrStatus.config.DT0, &buffer[9], len); // Copy bits of the config
avrStatus.headerValid = true;
showAllFlag = true;
} else if (len == 150) { // Long message when power is on
memcpy(&avrStatus.header, &buffer[1], sizeof(AVR_StatusHeader_T));
len = Hex2Dec(&avrStatus.header.length[0], 2);
memcpy(&avrStatus.config.DT0, &buffer[9], len); // Copy the config
avrStatus.headerValid = true;
avrStatus.configValid = true;
showAllFlag = true;
} else {
printf("***** Received message of unexpected length [%u]\n", len);
}
readyResponsReceived = true;
}
break;
case 0x14: // DC4 <extended response> ETX
// DecodeExtendedResponse(buffer, len); // once I figure out what is in here...
break;
default:
break;
}
break;
case stAwaitingResponse:
// @TODO Process the message here...
commandResponseReceived = true;
break;
case stReady:
switch (buffer[0]) {
case 0x02: // STX <msg> ETX
commandResponseReceived = true;
showAllFlag = ProcessReportResponse(buffer, len);
break;
case 0x11: // DC1 <msg> ETX
break;
case 0x12: // DC2 <msg> ETX
if (CheckTheChecksum(buffer, len)) {
if (len == 21) { // Short message when power is off
memcpy(&avrStatus.header, &buffer[1], sizeof(AVR_StatusHeader_T));
len = Hex2Dec(&avrStatus.header.length[0], 2);
memcpy(&avrStatus.config.DT0, &buffer[9], len); // Copy bits of the config
avrStatus.headerValid = true;
showAllFlag = true;
} else if (len == 150) { // Long message when power is on
memcpy(&avrStatus.header, &buffer[1], sizeof(AVR_StatusHeader_T));
len = Hex2Dec(&avrStatus.header.length[0], 2);
memcpy(&avrStatus.config.DT0, &buffer[9], len); // Copy the config
avrStatus.headerValid = true;
avrStatus.configValid = true;
showAllFlag = true;
} else {
printf("***** Received message of unexpected length [%u]\n", len);
}
readyResponsReceived = true;
}
break;
case 0x14: // DC4 <extended response> ETX
// DecodeExtendedResponse(buffer, len); // once I figure out what is in here...
break;
default:
break;
}
break;
}
return showAllFlag;
}
bool AVRInterface::Initialize() {
state = AVRState_T::stPoweringUp;
return true;
}
bool AVRInterface::RegisterInformationCallback(void(*StatusChangeCallback)(AVRMessageType_T type, const char *msg)) {
ReportInformation = StatusChangeCallback;
return true;
}
bool AVRInterface::AVRSendOSDMessage(const char *pMsg) {
const char valid[] = " !#%&()*+,-.0123456789:<=>?ABCDEFGHIJKLMNOPQRSTUVWXYZ[]_abcdefghijklmnopqrstuvwxyz";
char buf[17] = { 0 };
if (strlen(pMsg) <= 16) {
for (size_t i = 0; i < 16; i++) {
if (*pMsg == '\0') {
buf[i] = ' ';
} else if (strchr(valid, *pMsg)) {
buf[i] = *pMsg++;
} else {
return false; // Invalid character
}
}
ProcessSerialQueue("\x02" "21000" "\x03", 7); // Start the OSD message
char msg[8];
for (int i = 0; i < 16; i += 4) {
strcpy_s(msg, sizeof(msg), "\x02"); // Each chunk
strcat_s(msg, sizeof(msg), "3");
strncat_s(msg, sizeof(msg), &buf[i], 4);
strcat_s(msg, sizeof(msg), "\x03");
ProcessSerialQueue(msg, 7);
}
return true;
} else {
return false;
}
}
bool AVRInterface::ProcessSerialQueue(const void *msg, uint16_t len) {
const char *p = (const char *)msg;
bool retVal = false; // assume fail
static bool freshData = false;
if (p && len) {
if (serialQueueCount < SERIALQUEUESIZE) {
MessageReport(">", msg, len);
serialQueue[serialQueueCount].messageToSend = (uint8_t *)malloc(len + 1);
if (serialQueue[serialQueueCount].messageToSend) {
memcpy(serialQueue[serialQueueCount].messageToSend, p, len);
*(serialQueue[serialQueueCount].messageToSend + len) = '\0';
serialQueue[serialQueueCount].len = len;
serialQueueCount++;
retVal = true;
freshData = true;
}
}
}
if (serialQueueCount) {
if ((*SendMethod)((const uint8_t *)serialQueue[0].messageToSend, serialQueue[0].len)) {
--serialQueueCount;
free(serialQueue[0].messageToSend);
serialQueue[0].messageToSend = NULL;
for (int i = 0; i < serialQueueCount; i++) {
serialQueue[i] = serialQueue[i + 1];
}
retVal = true;
}
state = stAwaitingResponse;
}
return retVal;
}
void AVRInterface::FreeMemory() {
for (int i = 0; i < serialQueueCount; i++) {
if (serialQueue[0].messageToSend)
free(serialQueue[0].messageToSend);
}
}
bool AVRInterface::CheckTheChecksum(const uint8_t *szBuffer, uint32_t num) {
uint8_t sum = 0;
for (uint16_t i = 1; i < num - 3; i++) {
sum += szBuffer[i];
}
uint8_t cksum = (uint8_t)Hex2Dec(&szBuffer[num - 3], 2);
return (sum == cksum);
}
// Hex2Dec
//
// All responses are pretty much Hex-ASCII, so
// we sometimes want to convert it to decimal
// This takes a buffer and converts the specified
// number of characters.
//
uint16_t AVRInterface::Hex2Dec(const uint8_t *p, int dig) {
uint16_t x = 0;
while (dig--) {
if (*p >= '0' && *p <= '9')
x = x * 16 + *p - '0';
else if (*p >= 'a' && *p <= 'f')
x = x * 16 + 0x0a + *p - 'a';
else if (*p >= 'A' && *p <= 'F')
x = x * 16 + 0x0a + *p - 'A';
p++;
}
return x;
}
// ProcessReportResponse
//
// @param[in] szBuffer is the received message
// @param[in] len is the null terminated string length of the message
//
// Typical Message:
// '\x02' 'type' 'guard' 'rcmd0' 'rcmd1' 'rdat0' 'rdat1' '\x03'
// [0] [1] [2] [3] [4] [5] [6] [7]
//
bool AVRInterface::ProcessReportResponse(const uint8_t *szBuffer, uint32_t len) {
// These don't have a checksum ...
// Example: [02] 4026 66[03]
// 4 - controlled by encoder
// 0 - guard status 0 = no guard
// 26 - master vol
// 66 - volume setting (-54.6db)
uint8_t type = (uint8_t)Hex2Dec(&szBuffer[1], 1);
uint8_t guard = (uint8_t)Hex2Dec(&szBuffer[2], 1);
uint8_t rcmd = (uint8_t)Hex2Dec(&szBuffer[3], 2);
uint8_t rdat = (uint8_t)Hex2Dec(&szBuffer[5], 2);
char buf[LONGESTTEXT];
(void)len; // not used
bool showAllFlag = false;
bool found = false;
for (int i = 0; i < sizeof(MessageHandlers) / sizeof(MessageHandlers[0]); i++) {
if (MessageHandlers[i].rCmd == rcmd) {
found = true;
if (MessageHandlers[i].numToTransfer == 1) {
memcpy(&avrStatus.config.DT0 + MessageHandlers[i].configOffset, &szBuffer[6], 1);
}
if (MessageHandlers[i].numToTransfer == 2) {
memcpy(&avrStatus.config.DT0 + MessageHandlers[i].configOffset, &szBuffer[5], 2);
}
if (MessageHandlers[i].TextFormatter && MessageHandlers[i].fncValueToText) {
if (ReportInformation) { // Guard it
sprintf_s(buf, LONGESTTEXT, MessageHandlers[i].TextFormatter, MessageHandlers[i].fncValueToText(rdat));
(*ReportInformation)(mtInfo, buf);
}
}
if (MessageHandlers[i].showAll) {
showAllFlag = true; // ShowAllStatusInfo();
}
break; // no need to scan more
}
}
if (!found && ReportInformation) {
sprintf_s(buf, LONGESTTEXT, "***** type: %X, guard: %X, cmd: %02X, data: %02X", type, guard, rcmd, rdat);
(*ReportInformation)(mtInfo, buf);
}
return showAllFlag;
}
void AVRInterface::MessageHandlerSanityCheck() {
uint8_t usedCommands[256] = { 0 };
uint8_t blockOffset[256] = { 0 };
bool fail = false;
// Ensure that the MessageHandlers table is correct
for (int i = 0; i < sizeof(MessageHandlers) / sizeof(MessageHandlers[0]); i++) {
usedCommands[MessageHandlers[i].rCmd]++;
if (usedCommands[MessageHandlers[i].rCmd] > 1) {
printf("***** MessageHandler entry %d has duplicate rCmd of 0x%02X\n", i, MessageHandlers[i].rCmd);
fail = true;
}
blockOffset[MessageHandlers[i].configOffset]++;
if (MessageHandlers[i].configOffset != 0 && blockOffset[MessageHandlers[i].configOffset] > 1) {
printf("***** MessageHandler entry %d has duplicate configOffset of %d\n", i, MessageHandlers[i].configOffset);
fail = true;
}
if (MessageHandlers[i].numToTransfer > 2) {
printf("***** MessageHandler entry %d has invalid numToTransfer of %d\n", i, MessageHandlers[i].numToTransfer);
}
if (MessageHandlers[i].configOffset + MessageHandlers[i].numToTransfer > sizeof(AVR_Configuration_T)) {
printf("***** MessageHandler entry %d has invalid configOffset of %d\n", i, MessageHandlers[i].configOffset);
}
}
if (fail) {
printf("***** MessageHandler table sanity check failed. Exiting.\n");
}
return;
}
// PCMessage
//
// Various responses need to be formatted and shown on screen
// The last param will allow resetting the column counter
// and pre and post-pending \n
//
void AVRInterface::PCMessage(const char *msg, int len, uint8_t **src, const char *(fncHelper)(uint8_t val)) {
char buf[LONGESTTEXT] = "";
const char *p = buf;
if (fncHelper) {
// Get the binary value if we need it
uint8_t val = (uint8_t)Hex2Dec(*src, len);
p = (*fncHelper)(val);
*src += len;
} else {
// Create a string value when we need that
strncpy_s(buf, LONGESTTEXT, (char *)*src, len); // s/w
*src += len;
buf[len] = '\0';
}
char outBuf[LONGESTTEXT] = "";
sprintf_s(outBuf, LONGESTTEXT, PCMessageFormat,
msg,
p
);
if (ReportInformation) { // Guard it
(*ReportInformation)(mtStream, outBuf);
}
}
typedef const struct {
AVRInterface::AVRSubsystem_T subsystem;
AVRInterface::AVRFunction_E function;
AVRInterface::AVRArg_T arg;
const char *Message;
uint16_t MessageLen;
// Helper?
} MessageTable_T;
MessageTable_T MessageTable[] = {
// System Commands
{ AVRSubsys::sysCommand, AVRFunc::fncReady, AVRInterface::eOn, "\x11" "000" "\x03", 5 },
{ AVRSubsys::sysCommand, AVRFunc::fncReportEnable, AVRInterface::eOn, "\x02" "20000" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncReportEnable, AVRInterface::eOff, "\x02" "20001" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncReportDelay, AVRInterface::e0ms, "\x02" "20100" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncReportDelay, AVRInterface::e50ms, "\x02" "20101" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncReportDelay, AVRInterface::e100ms, "\x02" "20102" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncReportDelay, AVRInterface::e150ms, "\x02" "20103" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncReportDelay, AVRInterface::e200ms, "\x02" "20104" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncReportDelay, AVRInterface::e250ms, "\x02" "20105" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncReportDelay, AVRInterface::e300ms, "\x02" "20106" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncReportDelay, AVRInterface::e350ms, "\x02" "20107" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncReportDelay, AVRInterface::e400ms, "\x02" "20108" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncRequest, AVRInterface::eTuningFreq, "\x02" "22000" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncRequest, AVRInterface::eMainVolDB, "\x02" "22001" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncRequest, AVRInterface::eZone2VolDB, "\x02" "22002" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncRequest, AVRInterface::eInputName, "\x02" "22003" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncRequest, AVRInterface::eZone2InputName, "\x02" "22004" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncRequest, AVRInterface::eZoneXVolDB, "\x02" "22005" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncRequest, AVRInterface::eZoneXInputName, "\x02" "22006" "\x03", 7 },
// System Commands with variable data
{ AVRSubsys::sysCommand, AVRFunc::fncSetValue, AVRInterface::eMasterVol, "\x02" "230xx" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncSetValue, AVRInterface::eZone2Vol, "\x02" "231xx" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncSetValue, AVRInterface::eMainLRBal, "\x02" "232xx" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncSetValue, AVRInterface::eMainLevel, "\x02" "233xx" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncSetValue, AVRInterface::eZone3Vol, "\x02" "234xx" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncSetValue, AVRInterface::eMainLevelR, "\x02" "240xx" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncSetValue, AVRInterface::eMainLevelL, "\x02" "241xx" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncSetValue, AVRInterface::eCenterLevel, "\x02" "242xx" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncSetValue, AVRInterface::eRearR, "\x02" "243xx" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncSetValue, AVRInterface::eRearL, "\x02" "244xx" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncSetValue, AVRInterface::eFrontR, "\x02" "245xx" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncSetValue, AVRInterface::eFrontL, "\x02" "246xx" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncSetValue, AVRInterface::eSurBackR, "\x02" "247xx" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncSetValue, AVRInterface::eSurBackL, "\x02" "248xx" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncSetValue, AVRInterface::eSwfr1, "\x02" "249xx" "\x03", 7 },
{ AVRSubsys::sysCommand, AVRFunc::fncSetValue, AVRInterface::eSwfr2, "\x02" "24Axx" "\x03", 7 },
// Operation Commands
{ AVRSubsys::subMain, AVRFunc::fncPower, AVRInterface::eOn, "\x02" "07A1D" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncPower, AVRInterface::eOff, "\x02" "07A1E" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncVolume, AVRInterface::eUp, "\x02" "07A1A" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncVolume, AVRInterface::eDown, "\x02" "07A1B" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncMute, AVRInterface::eOn, "\x02" "07EA2" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncMute, AVRInterface::eOff, "\x02" "07EA3" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncOSD, AVRInterface::eOSDOff, "\x02" "07EB0" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncOSD, AVRInterface::eOSDShort, "\x02" "07EB1" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncOSD, AVRInterface::eOSDFull, "\x02" "07EB2" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncNightModeOnOff, AVRInterface::eOn, "\x02" "07E9B" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncNightModeOnOff, AVRInterface::eOff, "\x02" "07E9C" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncSleep, AVRInterface::eSleepOff, "\x02" "07EB3" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncSleep, AVRInterface::eSleep120, "\x02" "07EB4" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncSleep, AVRInterface::eSleep90, "\x02" "07EB5" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncSleep, AVRInterface::eSleep60, "\x02" "07EB6" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncSleep, AVRInterface::eSleep30, "\x02" "07EB7" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncSpeakerAOnOff, AVRInterface::eOn, "\x02" "07EAB" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncSpeakerAOnOff, AVRInterface::eOff, "\x02" "07EAC" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncSpeakerBOnOff, AVRInterface::eOn, "\x02" "07EAD" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncSpeakerBOnOff, AVRInterface::eOff, "\x02" "07EAE" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncDC1TrigControl, AVRInterface::eZone1, "\x02" "07E32" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncDC1TrigControl, AVRInterface::eZone2, "\x02" "07E33" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncDC1TrigControl, AVRInterface::eZone3, "\x02" "07E31" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncDualMono, AVRInterface::eDualMain, "\x02" "07E93" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncDualMono, AVRInterface::eDualSub, "\x02" "07E94" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncDualMono, AVRInterface::eDualAll, "\x02" "07E95" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncDC1TrigControl, AVRInterface::eZone1, "\x02" "07E96" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncDC1TrigControl, AVRInterface::eZone2, "\x02" "07E97" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncDC1TrigControl, AVRInterface::eZone3, "\x02" "07E9F" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncDC1TrigControl, AVRInterface::eZoneOR, "\x02" "07E98" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncSpeakerBZone, AVRInterface::eZone1, "\x02" "07E28" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncSpeakerBZone, AVRInterface::eZone2, "\x02" "07E29" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncZone2SpeakerOnOff, AVRInterface::eOn, "\x02" "07E99" "\x03", 7 },
{ AVRSubsys::subMain, AVRFunc::fncZone2SpeakerOnOff, AVRInterface::eOff, "\x02" "07E9A" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioBand, AVRInterface::eFM, "\x02" "07EBC" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioBand, AVRInterface::eAM, "\x02" "07EBD" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioTune, AVRInterface::eUp, "\x02" "07EBE" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioTune, AVRInterface::eDown, "\x02" "07EBF" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetPage, AVRInterface::eA, "\x02" "07AE0" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetPage, AVRInterface::eB, "\x02" "07AE1" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetPage, AVRInterface::eC, "\x02" "07AE2" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetPage, AVRInterface::eD, "\x02" "07AE3" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetPage, AVRInterface::eE, "\x02" "07AE4" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetNumber, AVRInterface::e1, "\x02" "07AE5" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetNumber, AVRInterface::e2, "\x02" "07AE6" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetNumber, AVRInterface::e3, "\x02" "07AE7" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetNumber, AVRInterface::e4, "\x02" "07AE8" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetNumber, AVRInterface::e5, "\x02" "07AE9" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetNumber, AVRInterface::e6, "\x02" "07AEA" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetNumber, AVRInterface::e7, "\x02" "07AEB" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetNumber, AVRInterface::e8, "\x02" "07AEC" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetMemory, AVRInterface::eA, "\x02" "07E2B" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetMemory, AVRInterface::eB, "\x02" "07E2C" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetMemory, AVRInterface::eC, "\x02" "07E2D" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetMemory, AVRInterface::eD, "\x02" "07E2E" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetMemory, AVRInterface::eE, "\x02" "07E2F" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetMemory, AVRInterface::eF, "\x02" "07E20" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetRecall, AVRInterface::eA, "\x02" "07E35" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetRecall, AVRInterface::eB, "\x02" "07E36" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetRecall, AVRInterface::eC, "\x02" "07E37" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetRecall, AVRInterface::eD, "\x02" "07E38" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetRecall, AVRInterface::eE, "\x02" "07E39" "\x03", 7 },
{ AVRSubsys::subRadio, AVRFunc::fncRadioPresetRecall, AVRInterface::eF, "\x02" "07E3A" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fnc6ChInput, AVRInterface::eOn, "\x02" "07EA4" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fnc6ChInput, AVRInterface::eOff, "\x02" "07EA5" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncInputMode, AVRInterface::eInpAuto, "\x02" "07EA6" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncInputMode, AVRInterface::eDD_RF, "\x02" "07EA7" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncInputMode, AVRInterface::eDTS, "\x02" "07EA8" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncInputMode, AVRInterface::eDigital, "\x02" "07EA9" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncInputMode, AVRInterface::eAnalog, "\x02" "07EAA" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncInputMode, AVRInterface::eAAC, "\x02" "07E3B" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncEx_EsOnOff, AVRInterface::eOnMatrix, "\x02" "07EB8" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncEx_EsOnOff, AVRInterface::eESESOff, "\x02" "07EB9" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncEx_EsOnOff, AVRInterface::eAuto, "\x02" "07E7C" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncEx_EsOnOff, AVRInterface::eDiscrete, "\x02" "07E7D" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncEffect, AVRInterface::eEffectOn, "\x02" "07E27" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncEffect, AVRInterface::eStereo, "\x02" "07EE0" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Hall_A, "\x02" "07EE1" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Hall_B, "\x02" "07EE2" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Hall_C, "\x02" "07EE3" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Hall_USA, "\x02" "07EE4" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Hall_E, "\x02" "07EE5" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Live_Concert, "\x02" "07EE6" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Tokyo, "\x02" "07EE7" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Freiburg, "\x02" "07EE8" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Royaumont, "\x02" "07EE9" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Village_Gate, "\x02" "07EEA" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Village_Vanguard, "\x02" "07EEB" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::The_Bottom_Line, "\x02" "07EEC" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::The_Roxy_Theater, "\x02" "07EED" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Warehouse_Loft, "\x02" "07EEE" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Arena, "\x02" "07EEF" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Disco, "\x02" "07EF0" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Party, "\x02" "07EF1" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Game, "\x02" "07EF2" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Stereo_6_8Ch, "\x02" "07EFF" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Pop_Rock, "\x02" "07EF3" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::DJ, "\x02" "07EF4" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Opera, "\x02" "07EF5" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Pavillion, "\x02" "07EF6" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Mono_Movie, "\x02" "07EF7" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Variety_Sports, "\x02" "07EF8" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Spectacre, "\x02" "07EF9" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Sci_Fi, "\x02" "07EFA" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Adventure, "\x02" "07EFB" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::General, "\x02" "07EFC" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Normal, "\x02" "07EFD" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Enhanced, "\x02" "07EFE" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::PLII_Movie, "\x02" "07E67" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::PLII_Music, "\x02" "07E68" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Neo_6_Movie, "\x02" "07E69" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Neo_6_Music, "\x02" "07E6A" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Direct_2Ch, "\x02" "07EC1" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::Stereo_2Ch, "\x02" "07EC0" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::THX_Ultra_PL, "\x02" "07EC2" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::THX_Music, "\x02" "07EC3" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::THX_Ultra_PL2, "\x02" "07EC7" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncDSPSoundScape, AVRInterface::THX_Ultra_NEO6, "\x02" "07EC8" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncVolumeMemory, AVRInterface::eA, "\x02" "07E6B" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncVolumeMemory, AVRInterface::eB, "\x02" "07E6C" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncVolumeMemory, AVRInterface::eC, "\x02" "07E6D" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncVolumeMemory, AVRInterface::eD, "\x02" "07E6E" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncVolumeMemory, AVRInterface::eE, "\x02" "07E6F" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncVolumeMemory, AVRInterface::eF, "\x02" "07E60" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncVolumeRecall, AVRInterface::eA, "\x02" "07E75" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncVolumeRecall, AVRInterface::eB, "\x02" "07E76" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncVolumeRecall, AVRInterface::eC, "\x02" "07E77" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncVolumeRecall, AVRInterface::eD, "\x02" "07E78" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncVolumeRecall, AVRInterface::eE, "\x02" "07E79" "\x03", 7 },
{ AVRSubsys::subAudio, AVRFunc::fncVolumeRecall, AVRInterface::eF, "\x02" "07E7A" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncPower, AVRInterface::eOn, "\x02" "07E7E" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncPower, AVRInterface::eOff, "\x02" "07E7F" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncInput, AVRInterface::ePhono, "\x02" "07A14" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncInput, AVRInterface::eCD, "\x02" "07A15" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncInput, AVRInterface::eTuner, "\x02" "07A16" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncInput, AVRInterface::eCDR, "\x02" "07A19" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncInput, AVRInterface::eMD_Tape, "\x02" "07AC9" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncInput, AVRInterface::eDVD, "\x02" "07AC1" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncInput, AVRInterface::eDTV, "\x02" "07A54" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncInput, AVRInterface::eCable, "\x02" "07AC0" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncInput, AVRInterface::eSat, "\x02" "07ACA" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncInput, AVRInterface::eVCR1, "\x02" "07A0F" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncInput, AVRInterface::eVCR2_DVR, "\x02" "07A13" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncInput, AVRInterface::eVCR3, "\x02" "07AC8" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncInput, AVRInterface::eV_Aux, "\x02" "07A55" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncDC1OnOff, AVRInterface::eOn, "\x02" "07E73" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncDC1OnOff, AVRInterface::eOff, "\x02" "07E74" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncDC2OnOff, AVRInterface::eOn, "\x02" "07E3E" "\x03", 7 },
{ AVRSubsys::subZone1, AVRFunc::fncDC2OnOff, AVRInterface::eOff, "\x02" "07E3F" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncVolume, AVRInterface::eUp, "\x02" "07ADA" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncVolume, AVRInterface::eDown, "\x02" "07ADB" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncMute, AVRInterface::eOn, "\x02" "07EA0" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncMute, AVRInterface::eOff, "\x02" "07EA1" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncInput, AVRInterface::ePhono, "\x02" "07AD0" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncInput, AVRInterface::eCD, "\x02" "07AD1" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncInput, AVRInterface::eTuner, "\x02" "07AD2" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncInput, AVRInterface::eCDR, "\x02" "07AD4" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncInput, AVRInterface::eMD_Tape, "\x02" "07ACF" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncInput, AVRInterface::eDVD, "\x02" "07ACD" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncInput, AVRInterface::eDTV, "\x02" "07AD9" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncInput, AVRInterface::eCable, "\x02" "07ACC" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncInput, AVRInterface::eSat, "\x02" "07ACB" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncInput, AVRInterface::eVCR1, "\x02" "07AD6" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncInput, AVRInterface::eVCR2_DVR, "\x02" "07AD7" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncInput, AVRInterface::eVCR3, "\x02" "07ACE" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncInput, AVRInterface::eV_Aux, "\x02" "07AD8" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncPower, AVRInterface::eOn, "\x02" "07EBA" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncPower, AVRInterface::eOff, "\x02" "07EBB" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncVolumeMemory, AVRInterface::eA, "\x02" "07E87" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncVolumeMemory, AVRInterface::eB, "\x02" "07E88" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncVolumeMemory, AVRInterface::eC, "\x02" "07E89" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncVolumeMemory, AVRInterface::eD, "\x02" "07E8A" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncVolumeMemory, AVRInterface::eE, "\x02" "07E8B" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncVolumeMemory, AVRInterface::eF, "\x02" "07E8C" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncVolumeRecall, AVRInterface::eA, "\x02" "07E8D" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncVolumeRecall, AVRInterface::eB, "\x02" "07E8E" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncVolumeRecall, AVRInterface::eC, "\x02" "07E8F" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncVolumeRecall, AVRInterface::eD, "\x02" "07E90" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncVolumeRecall, AVRInterface::eE, "\x02" "07E91" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncVolumeRecall, AVRInterface::eF, "\x02" "07E92" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncDC1OnOff, AVRInterface::eOn, "\x02" "07E71" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncDC1OnOff, AVRInterface::eOff, "\x02" "07E72" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncDC2OnOff, AVRInterface::eOn, "\x02" "07E3C" "\x03", 7 },
{ AVRSubsys::subZone2, AVRFunc::fncDC2OnOff, AVRInterface::eOff, "\x02" "07E3D" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncPower, AVRInterface::eOn, "\x02" "07AED" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncPower, AVRInterface::eStandby, "\x02" "07AEE" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncMute, AVRInterface::eOn, "\x02" "07E26" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncMute, AVRInterface::eOff, "\x02" "07E66" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncVolume, AVRInterface::eUp, "\x02" "07AFD" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncVolume, AVRInterface::eDown, "\x02" "07AFE" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncInput, AVRInterface::ePhono, "\x02" "07AF1" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncInput, AVRInterface::eCD, "\x02" "07AF2" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncInput, AVRInterface::eTuner, "\x02" "07AF3" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncInput, AVRInterface::eCDR, "\x02" "07AF5" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncInput, AVRInterface::eMD_Tape, "\x02" "07AF4" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncInput, AVRInterface::eDVD, "\x02" "07AFC" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncInput, AVRInterface::eDTV, "\x02" "07AF6" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncInput, AVRInterface::eCable, "\x02" "07AF7" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncInput, AVRInterface::eSat, "\x02" "07AF8" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncInput, AVRInterface::eVCR1, "\x02" "07AF9" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncInput, AVRInterface::eVCR2_DVR, "\x02" "07AFA" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncInput, AVRInterface::eVCR3, "\x02" "07AFB" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncInput, AVRInterface::eV_Aux, "\x02" "07AF0" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncVolumeMemory, AVRInterface::eA, "\x02" "07E20" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncVolumeMemory, AVRInterface::eB, "\x02" "07E21" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncVolumeMemory, AVRInterface::eC, "\x02" "07E22" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncVolumeMemory, AVRInterface::eD, "\x02" "07E23" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncVolumeMemory, AVRInterface::eE, "\x02" "07E24" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncVolumeMemory, AVRInterface::eF, "\x02" "07E25" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncVolumeRecall, AVRInterface::eA, "\x02" "07E60" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncVolumeRecall, AVRInterface::eB, "\x02" "07E61" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncVolumeRecall, AVRInterface::eC, "\x02" "07E62" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncVolumeRecall, AVRInterface::eD, "\x02" "07E63" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncVolumeRecall, AVRInterface::eE, "\x02" "07E64" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncVolumeRecall, AVRInterface::eF, "\x02" "07E65" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncDC1OnOff, AVRInterface::eOn, "\x02" "07E83" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncDC1OnOff, AVRInterface::eOff, "\x02" "07E84" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncDC2OnOff, AVRInterface::eOn, "\x02" "07E85" "\x03", 7 },
{ AVRSubsys::subZone3, AVRFunc::fncDC2OnOff, AVRInterface::eOff, "\x02" "07E86" "\x03", 7 },
};
bool AVRInterface::AVRCommand(AVRInterface::AVRSubsystem_T subsystem,
AVRInterface::AVRFunction_E function,
AVRArg_T arg, uint8_t variableData) {
bool found = false;
for (int i = 0; i < sizeof(MessageTable) / sizeof(MessageTable_T); i++) {
if (MessageTable[i].subsystem == subsystem && MessageTable[i].function == function and MessageTable[i].arg == arg) {
found = true;
const char *p = strchr(MessageTable[i].Message, 'x');
if (p) {
char hexBuf[3] = "";
char *bigBuf = (char *)malloc(MessageTable[i].MessageLen + 1);
if (bigBuf) {
sprintf_s(hexBuf, 3, "%0X", variableData);
memcpy(bigBuf, MessageTable[i].Message, MessageTable[i].MessageLen);
p = strchr(bigBuf, 'x');
memcpy((void *)p, hexBuf, 2);
ProcessSerialQueue(bigBuf, MessageTable[i].MessageLen);
free(bigBuf);
} else {
(*ReportInformation)(mtInfo, "***** Memory allocation failed!");
}
} else {
ProcessSerialQueue(MessageTable[i].Message, MessageTable[i].MessageLen);
}
break;
}
}
if (!found) {
char buf[LONGESTTEXT] = "";
sprintf_s(buf, LONGESTTEXT, "AVRCommand(%d,%d,%d) is invalid.", subsystem, function, arg);
(*ReportInformation)(mtInfo, buf);
}
return true;
}
void AVRInterface::ExportInformation(AVRInterface::AVRSubsystem_T subsystem,
AVRInterface::AVRFunction_E function,
AVRArg_T arg) {
char buf[LONGESTTEXT] = "";
typedef struct {
uint16_t value;
const char *helpText;
} ValuePurpose_T;
const ValuePurpose_T subsysList[] = {
{ sysCommand, "System Command" },
{ subMain, "Main Subsystem" },
{ subRadio, "Radio Control" },
{ subAudio, "Audio Control" },
{ subZone1, "Zone 1 Control" },
{ subZone2, "Zone 2 Control" },
{ subZone3, "Zone 3 Control" },
};
const ValuePurpose_T funcList[] = {
{ fncReady, "Ready Check" },
{ fncReportEnable, "Report Enable" },
{ fncReportDelay, "Report Delay" },
{ fncRequest, "Report Request" },
{ fncSetValue, "Set Function Value" },
{ fncPower, "Power" },
{ fncVolume, "Volume" },
{ fncMute, "Mute" },
{ fncVolumeMemory, "Volume Memory" },
{ fncVolumeRecall, "Volume Memory Recall" },
{ fncSpeakerAOnOff, "Speaker A" },
{ fncSpeakerBOnOff, "Speaker B" },
{ fncSpeakerBZone, "Speaker B Zone Assignment" },
{ fncZone2SpeakerOnOff, "Zone 2 Speaker" },
{ fncNightModeOnOff, "Night Mode Sound Level" },
{ fncEffect, "Effect <something> " },
{ fncDSPSoundScape, "DSP Sound Scape" },
{ fncInput, "Input Selection" },
{ fncRadioBand, "Radio Band Selection" },
{ fncRadioTune, "Radio Tune" },
{ fncRadioPresetPage, "Radio Preset Page" },
{ fncRadioPresetNumber, "Radio Preset Number" },
{ fncRadioPresetMemory, "Radio Preset Memory" },
{ fncRadioPresetRecall, "Radio Preset Recall" },
{ fncSleep, "Sleep Timer" },
{ fncOSD, "On Screen Display Control" },
{ fnc6ChInput, "6 Channel Input mode" },
{ fncEx_EsOnOff, "EX / ES Mode" },
{ fncInputMode, "Input Mode" },
{ fncDualMono, "Dual Mono" },
{ fncDC1TrigControl, "DC1 Trigger Control" },
{ fncDC2TrigControl, "DC2 Trigger Control" },
{ fncDC1OnOff, "DC1" },
{ fncDC2OnOff, "DC2" },
};
const ValuePurpose_T valueList[] = {
{ eOn, "On" },
{ eOff, "Off" },
{ eStandby, "Standby" },
{ eUp, "Up" },
{ eDown, "Down" },
{ eOSDOff, "Off" },
{ eOSDShort, "Short" },
{ eOSDFull, "Full" },
{ eSleepOff, "Off" },
{ eSleep120, "120" },
{ eSleep90, "90" },
{ eSleep60, "60" },
{ eSleep30, "30" },
{ eOnMatrix, "EX-ES Mode Matrix On" },
{ eESESOff, "EX-ES Mode Off" },
{ eAuto, "EX-ES Mode Auto" },
{ eDiscrete, "EX-ES Mode Discrete" },
{ eEffectOn, "Effect On" },
{ eStereo, "Effect Stereo" },
{ eFM, "FM Band" },
{ eAM, "AM Band" },
{ eA, "Group A" },
{ eB, "Group B" },
{ eC, "Group C" },
{ eD, "Group D" },
{ eE, "Group E" },
{ eF, "Group F" },
{ e1, "Preset 1" },
{ e2, "Preset 2" },
{ e3, "Preset 3" },
{ e4, "Preset 4" },
{ e5, "Preset 5" },
{ e6, "Preset 6" },
{ e7, "Preset 7" },
{ e8, "Preset 8" },
{ ePhono, "Phono" },
{ eCD, "CD" },
{ eTuner, "Tuner" },
{ eCDR, "CDR" },
{ eMD_Tape, "MD_Tape" },
{ eDVD, "DVD" },
{ eDTV, "DTV" },
{ eCable, "Cable" },
{ eSat, "Sat" },
{ eVCR1, "VCR1" },
{ eVCR2_DVR, "VCR2_DVR" },
{ eVCR3, "VCR3" },
{ eV_Aux, "V Aux" },
{ Hall_A, "Hall A" },
{ Hall_B, "Hall B" },
{ Hall_C, "Hall C" },
{ Hall_USA, "Hall USA" },
{ Hall_E, "Hall E" },
{ Live_Concert, "Live Concert" },
{ Tokyo, "Tokyo" },
{ Freiburg, "Freiburg" },
{ Royaumont, "Royaumont" },
{ Village_Gate, "Village Gate" },
{ Village_Vanguard, "Village Vanguard" },
{ The_Bottom_Line, "The Bottom Line" },
{ The_Roxy_Theater, "The Roxy Theater" },
{ Warehouse_Loft, "Warehouse Loft" },
{ Arena, "Arena" },
{ Disco, "Disco" },
{ Party, "Party" },
{ Game, "Game" },
{ Stereo_6_8Ch, "Stereo 6/8Ch" },
{ Pop_Rock, "Pop/Rock" },
{ DJ, "DJ" },
{ Opera, "Opera" },
{ Pavillion, "Pavillion" },
{ Mono_Movie, "Mono/Movie" },
{ Variety_Sports, "Variety/Sports" },
{ Spectacre, "Spectacre" },
{ Sci_Fi, "Sci-Fi" },
{ Adventure, "Adventure" },
{ General, "General" },
{ Normal, "Normal" },
{ Enhanced, "Enhanced" },
{ PLII_Movie, "PLII Movie" },
{ PLII_Music, "PLII Music" },
{ Neo_6_Movie, "Neo 6 Movie" },
{ Neo_6_Music, "Neo 6 Music" },
{ Direct_2Ch, "Direct 2Ch" },
{ Stereo_2Ch, "Stereo 2Ch" },
{ THX_Ultra_PL, "THX Ultra PL" },
{ THX_Music, "THX Music" },
{ THX_Ultra_PL2, "THX Ultra PL2" },
{ THX_Ultra_NEO6, "THX Ultra NEO6" },
{ eInpAuto, "Input Auto" },
{ eDD_RF, "Input DD/RF" },
{ eDTS, "Input DTS" },
{ eDigital, "Input Digital" },
{ eAnalog, "Input Analog" },
{ eAAC, "Input AAC" },
{ eZone1, "Zone 1" },
{ eZone2, "Zone 2" },
{ eZone3, "Zone 3" },
{ eZoneOR, "Zone OR" },
{ eDualMain, "Dual Main" },
{ eDualSub, "Dual Sub" },
{ eDualAll, "Dual All" },
{ e0ms, "0 ms" },
{ e50ms, "50 ms" },
{ e100ms, "100 ms" },
{ e150ms, "150 ms" },
{ e200ms, "200 ms" },
{ e250ms, "250 ms" },
{ e300ms, "300 ms" },
{ e350ms, "350 ms" },
{ e400ms, "400 ms" },
{ eTuningFreq, "Tuning Frequency" },
{ eMainVolDB, "Main Volume" },
{ eZone2VolDB, "Zone 2 Volume" },
{ eInputName, "Zone 1 Input Name" },
{ eZone2InputName, "Zone 2 Input Name" },
{ eZoneXVolDB, "Zone X Volume" },
{ eZoneXInputName, "Zone X Input Name" },
{ eMasterVol, "Master Volume" },
{ eZone2Vol, "Zone 2 Volume" },
{ eMainLRBal, "Left-Right Balance" },
{ eMainLevel, "Main Level" },
{ eZone3Vol, "Zone 3 Volume" },
{ eMainLevelR, "Main Level R" },
{ eMainLevelL, "Main Level L" },
{ eCenterLevel, "Center Level" },
{ eRearR, "Rear Level R" },
{ eRearL, "Rear Level L" },
{ eFrontR, "Front Level R" },
{ eFrontL, "Front Level L" },
{ eSurBackR, "Surround Back R" },
{ eSurBackL, "Surround Back L" },
{ eSwfr1, "Subwoofer 1" },
{ eSwfr2, "Subwoofer 2" },
{ e0ms, "0 ms" },
};
ReportInformation(mtInfo, "");
ReportInformation(mtInfo, "AVR Command Line Control uses 3 numeric parameters:");
ReportInformation(mtInfo, " 1) Subsystem Identifier for the subsystem control");
ReportInformation(mtInfo, " 2) Function Identifier valid for the subsystem");
ReportInformation(mtInfo, " 3) Value Identifier valid for the subsystem and function");
ReportInformation(mtInfo, "");
ReportInformation(mtInfo, " NOTE: Most commands are unavailable when the system is off.");
ReportInformation(mtInfo, " ");
ReportInformation(mtInfo, "");
sprintf_s(buf, LONGESTTEXT, "%8d: %-21s | %3d: %-28s | %3d: %-22s | %-13s",
1, "Subsystem Identifier", 2, "Function Identifier", 3, "Value Identifier", "Stream"
);
ReportInformation(mtInfo, buf);
sprintf_s(buf, LONGESTTEXT, " %2s: %-21s | %3s: %-28s | %3s: %22s | %13s",
"##", "#####################", "##", "############################", "##", "######################", "#############"
);
ReportInformation(mtInfo, buf);
AVRSubsystem_T refSub = subsystemCount;
AVRFunction_E refFnc = fncFunctionCount;
const char *pSubsystemText = NULL, *pFunctionText = NULL, *pValueText = NULL;
for (int i = 0; i < sizeof(MessageTable) / sizeof(MessageTable_T); i++) {
// Subsystem scan or filter
//
if (subsystem != subsystemCount && subsystem != MessageTable[i].subsystem) {
continue;
}
if (function != fncFunctionCount && function != MessageTable[i].function) {
continue;
}
if (arg != eARGCount && arg != MessageTable[i].arg) {
continue;
}
if (refSub != MessageTable[i].subsystem) {
refSub = MessageTable[i].subsystem;
for (int j = 0; j < sizeof(subsysList) / sizeof(ValuePurpose_T); j++) {
if (subsysList[j].value == refSub) {
pSubsystemText = subsysList[j].helpText;
break;
} else {
pSubsystemText = "";
}
}
} else {
pSubsystemText = "";
}
//
// function choices
//
if (refFnc != MessageTable[i].function) {
refFnc = MessageTable[i].function;
for (int j = 0; j < sizeof(funcList) / sizeof(ValuePurpose_T); j++) {
if (funcList[j].value == refFnc) {
pFunctionText = funcList[j].helpText;
break;
} else {
pFunctionText = "";
}
}
} else {
pFunctionText = "";
}
//
// argument choices
//
for (int j = 0; j < sizeof(valueList) / sizeof(ValuePurpose_T); j++) {
if (valueList[j].value == MessageTable[i].arg) {
pValueText = valueList[j].helpText;
break;
} else {
pValueText = "";
}
}
sprintf_s(buf, LONGESTTEXT, "%8d: %-21s | %3d: %-28s | %3d: %-22s | %s",
refSub, pSubsystemText,
refFnc, pFunctionText,
MessageTable[i].arg, pValueText,
MessageToText(MessageTable[i].Message, MessageTable[i].MessageLen)
);
ReportInformation(mtInfo, buf);
}
};
const char *AVRInterface::MessageToText(const char *p, size_t len) {
static char privateBuffer[LONGESTTEXT] = "";
char *pOut = privateBuffer;
for (int i = 0; i < len; i++) {
if (isprint(*p)) {
*pOut++ = *p++;
} else {
pOut += sprintf_s(pOut, LONGESTTEXT - strlen(privateBuffer), "[%02X]", *p++);
}
*pOut = '\0'; // keep it null terminated
}
return privateBuffer;
}
//
// Single Linear according to the on-screen display of Volume
// db = 0.5 x - 99.5
// therefore:
// db + 99.5 = 0.5 x
// 0.5 x == db + 99.5
// x = 2 * (db + 99.5)
//
uint8_t AVRInterface::VolumeDBtoAPIValue(float db) {
if (db >= -80.0f && db <= +16.5f) {
return (uint8_t)(2 * (db + 99.5));
} else {
return (0); // mute
}
}
/// ReportAllStatus
///
/// This emits (via a callback) all the status, in DT0 to DT137 order.
/// You cannot rearrange the sequence to make grouping more logical.
///
void AVRInterface::ReportAllStatus() {
if (avrStatus.headerValid && ReportInformation) {
char buf[LONGESTTEXT];
sprintf_s(buf, LONGESTTEXT, "Model ID: %c%c%c%c%c, ver: %c\n", avrStatus.header.type[0], avrStatus.header.type[1],
avrStatus.header.type[2], avrStatus.header.type[3], avrStatus.header.type[4],
avrStatus.header.version);
(*ReportInformation)(mtModelInfo, buf);
uint8_t *p = (uint8_t *)&avrStatus.config;
(*ReportInformation)(mtStreamStart, "---- AVR Status Report ----\n");
PCMessage("Baud Rate", 1, &p);
PCMessage("Rx Buffer", 2, &p);
PCMessage("Cmd Timeout", 3, &p);
PCMessage("Handshake", 1, &p);
PCMessage("Busy", 1, &p, BusyToText);
PCMessage("Power", 1, &p, OffOnText);
if (avrStatus.configValid) {
PCMessage("Zone 1 Input", 1, &p, InputText);
PCMessage("6 ch", 1, &p, OffOnText);
PCMessage("Inp mode", 1, &p, InputModeText);
PCMessage("Mute", 1, &p, OffOnText);
PCMessage("Zone 2 Input", 1, &p, InputText);
PCMessage("Zone 2 Mute", 1, &p, OffOnText);
PCMessage("Volume", 2, &p, VolumeDB);
PCMessage("Zone 2 Volume", 2, &p, VolumeDB);
PCMessage("Prog", 2, &p, ProgramName);
PCMessage("Effect", 1, &p, OffOnText);
PCMessage("6.1/es status", 1, &p, OffMatrixDiscreteAutoText);
PCMessage("OSD", 1, &p, OSDFullShortOffText);
PCMessage("Sleep", 1, &p, SleepTimerText);
PCMessage("Tuner Pg", 1, &p, PresetLabelText);
PCMessage("Tuner #", 1, &p, PresetNumberText);
PCMessage("Night", 1, &p, OffOnText);
PCMessage("?????", 1, &p);
PCMessage("Spkr A", 1, &p, OffOnText);
PCMessage("Spkr B", 1, &p, OffOnText);
PCMessage("Playback", 1, &p, PlaybackToText);
PCMessage("Fs", 1, &p, FsToText);
PCMessage("Ex/Es", 1, &p, OffMatrixDiscreteText);
PCMessage("Thr Bypass", 1, &p, OffOnText);
PCMessage("Red DTS", 1, &p, ReleaseWaitText);
PCMessage("Headphone", 1, &p, OffOnText);
PCMessage("Tuner Band", 1, &p, FMAMText);
PCMessage("Tuner Tuned", 1, &p, NotTunedTunedText);
PCMessage("DC1 Control Out", 1, &p, OffOnText);
PCMessage("?????", 2, &p);
PCMessage("DC1 Trig Ctrl", 1, &p);
PCMessage("DTS 96/24", 1, &p, OffOnText);
PCMessage("DC2 Trig Ctrl", 1, &p, WhichZoneText);
PCMessage("DC2 Trig Out", 1, &p, OffOnText);
PCMessage("Spkr B Set", 1, &p, Zone1Zone2Text);
PCMessage("Zone 2 SP out", 1, &p, OffOnText);
PCMessage("Main R", 2, &p, PM10dbText);
PCMessage("Main L", 2, &p, PM10dbText);
PCMessage("Center", 2, &p, PM10dbText);
PCMessage("Rear R", 2, &p, PM10dbText);
PCMessage("Rear L", 2, &p, PM10dbText);
PCMessage("Sur Bk R", 2, &p, PM10dbText);
PCMessage("Sur Bk L", 2, &p, PM10dbText);
PCMessage("Front R", 2, &p, PM10dbText);
PCMessage("Front L", 2, &p, PM10dbText);
PCMessage("Subwfr 1", 2, &p, PM10dbText);
PCMessage("?????", 6, &p);
PCMessage("LFE SP", 2, &p, M20P0dbText);
PCMessage("LFE HP", 2, &p, M20P0dbText);
PCMessage("Audio Delay", 2, &p, ZeroTo160msText);
PCMessage("?????", 4, &p);
PCMessage("Inp Mode Set", 1, &p, AutoLastText);
PCMessage("Dimmer", 1, &p, M4To0Text);
PCMessage("OSD Msg", 1, &p);
PCMessage("OSD Shift", 2, &p, M5toP5Text);
PCMessage("Gray Back", 1, &p, OffAutoText);
PCMessage("Video Conv", 1, &p, OffOnText);
PCMessage("D Range SP", 1, &p, MaxStdMinText);
PCMessage("D Range HP", 1, &p, MaxStdMinText);
PCMessage("Zone 2 Vol out", 1, &p, VarFixText);
PCMessage("?????", 1, &p); // "Zone 2 Mode: %s", Mode1Mode2Text ???
PCMessage("Memory Guard", 1, &p, OffOnText);
PCMessage("SP set center", 1, &p);
PCMessage("SP set main", 1, &p);
PCMessage("SP set rear L/R", 1, &p);
PCMessage("SP set rear ct", 1, &p);
PCMessage("SP set front", 1, &p);
PCMessage("SP set LFE/Bass", 1, &p, SwfrMainBothText);
PCMessage("6 ch center", 1, &p);
PCMessage("6 ch sub", 1, &p);
PCMessage("Main level", 1, &p);
PCMessage("Test Mode", 1, &p, OffDolbyDspText);
PCMessage("?????", 1, &p);
PCMessage("Lvl 6 Ch main L", 2, &p, M10P10dbText);
PCMessage("Lvl 6 Ch main R", 2, &p, M10P10dbText);
PCMessage("Lvl 6 Ch center", 2, &p, M10P10dbText);
PCMessage("Lvl 6 Ch sl", 2, &p, M10P10dbText);
PCMessage("Lvl 6 Ch sr", 2, &p, M10P10dbText);
PCMessage("Lvl 6 Ch sbl", 2, &p, M10P10dbText);
PCMessage("Lvl 6 Ch sbr", 2, &p, M10P10dbText);
PCMessage("Lvl 6 Ch F L", 2, &p, M10P10dbText);
PCMessage("Lvl 6 Ch F R", 2, &p, M10P10dbText);
PCMessage("Lvl 6 Ch swfr", 2, &p, M20P0dbText );
PCMessage("Zone 3 Input", 1, &p, PlaybackToText);
PCMessage("Zone 3 Mute", 1, &p, OffOnText);
PCMessage("Zone 3 Volume", 2, &p, VolumeDB);
PCMessage("?????", 1, &p);
PCMessage("MultiCh Select", 1, &p, SixEightText);
PCMessage("MultiCh Surround", 1, &p, SurrMainText);
PCMessage("SP Set SW1", 1, &p, LrFrNoneText);
PCMessage("SP Set Crossover", 1, &p, CrossOverText);
PCMessage("Component OSD", 1, &p, OffOnText);
PCMessage("PB/SB Select", 1, &p, PRSBText);
}
}
}