summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBrant Thomsen <brant.thomsen@harman.com>2017-07-20 11:26:13 -0600
committerBrant Thomsen <brant.thomsen@harman.com>2017-07-20 11:26:13 -0600
commit5c2d2ac3902dfb2aa25a363fe13592981781ebec (patch)
tree295f9c9cec0fb01a438c9e9e8056f995bcb3f082
parentd1108941e160b90928bfb7fa3bb2150bf214be90 (diff)
downloadOpen-AVB-5c2d2ac3902dfb2aa25a363fe13592981781ebec.tar.gz
Added SET_STREAM_INFO implementation
When SET_STREAM_INFO is used, settings are sent to the client. Client uses those settings, or restores from the backup of the original settings, as appropriate. If the destination address is specified, then MAAP allocation will not be used. GET_STREAM_INFO updated to reflect the settings supplied for the Talker, and the settings currently in use for the Listener.
-rw-r--r--lib/avtp_pipeline/acmp/openavb_acmp_sm_talker.c1
-rw-r--r--lib/avtp_pipeline/aecp/openavb_aecp_sm_entity_model_entity.c153
-rw-r--r--lib/avtp_pipeline/aem/openavb_descriptor_stream_io_pub.h1
-rw-r--r--lib/avtp_pipeline/avdecc/openavb_avdecc_pipeline_interaction_pub.h10
-rw-r--r--lib/avtp_pipeline/avdecc_msg/openavb_avdecc_msg.h32
-rw-r--r--lib/avtp_pipeline/avdecc_msg/openavb_avdecc_msg_client.c130
-rw-r--r--lib/avtp_pipeline/avdecc_msg/openavb_avdecc_msg_server.c46
-rw-r--r--lib/avtp_pipeline/endpoint/openavb_endpoint.h5
-rw-r--r--lib/avtp_pipeline/endpoint/openavb_endpoint_client.c5
-rw-r--r--lib/avtp_pipeline/endpoint/openavb_endpoint_server.c16
-rw-r--r--lib/avtp_pipeline/platform/Linux/avdecc/openavb_avdecc_pipeline_interaction.c34
-rw-r--r--lib/avtp_pipeline/platform/Linux/avdecc_msg/openavb_avdecc_msg_osal.h3
-rw-r--r--lib/avtp_pipeline/tl/openavb_talker.h2
-rw-r--r--lib/avtp_pipeline/tl/openavb_talker_endpoint.c1
-rwxr-xr-xlib/avtp_pipeline/tl/openavb_tl_pub.h16
15 files changed, 415 insertions, 40 deletions
diff --git a/lib/avtp_pipeline/acmp/openavb_acmp_sm_talker.c b/lib/avtp_pipeline/acmp/openavb_acmp_sm_talker.c
index 16fa5495..37495ce1 100644
--- a/lib/avtp_pipeline/acmp/openavb_acmp_sm_talker.c
+++ b/lib/avtp_pipeline/acmp/openavb_acmp_sm_talker.c
@@ -652,6 +652,7 @@ void openavbAcmpSMTalker_updateStreamInfo(openavb_tl_data_cfg_t *pCfg)
pDescriptorStreamOutput->acmp_flags = response->flags;
// Save the stream information for reference later.
+ // (This is currently only used by Listeners, but it doesn't hurt to have it just in case.)
memcpy(pDescriptorStreamOutput->acmp_stream_id, response->stream_id, 8);
memcpy(pDescriptorStreamOutput->acmp_dest_addr, response->stream_dest_mac, 6);
pDescriptorStreamOutput->acmp_stream_vlan_id = response->stream_vlan_id;
diff --git a/lib/avtp_pipeline/aecp/openavb_aecp_sm_entity_model_entity.c b/lib/avtp_pipeline/aecp/openavb_aecp_sm_entity_model_entity.c
index 5f125244..6a846bfc 100644
--- a/lib/avtp_pipeline/aecp/openavb_aecp_sm_entity_model_entity.c
+++ b/lib/avtp_pipeline/aecp/openavb_aecp_sm_entity_model_entity.c
@@ -417,6 +417,106 @@ void processCommand()
case OPENAVB_AEM_COMMAND_CODE_GET_SENSOR_FORMAT:
break;
case OPENAVB_AEM_COMMAND_CODE_SET_STREAM_INFO:
+ {
+ openavb_aecp_commandresponse_data_set_stream_info_t *pCmd = &pCommand->entityModelPdu.command_data.setStreamInfoCmd;
+ openavb_aecp_commandresponse_data_set_stream_info_t *pRsp = &pCommand->entityModelPdu.command_data.setStreamInfoRsp;
+
+ if (processCommandCheckRestriction_CorrectController()) {
+ if (processCommandCheckRestriction_StreamNotRunning(pCmd->descriptor_type, pCmd->descriptor_index)) {
+ if (pCmd->descriptor_type == OPENAVB_AEM_DESCRIPTOR_STREAM_INPUT ||
+ pCmd->descriptor_type == OPENAVB_AEM_DESCRIPTOR_STREAM_OUTPUT) {
+ openavb_aem_descriptor_stream_io_t *pDescriptorStreamIO = openavbAemGetDescriptor(openavbAemGetConfigIdx(), pCmd->descriptor_type, pCmd->descriptor_index);
+ if (pDescriptorStreamIO) {
+ pCommand->headers.status = OPENAVB_AEM_COMMAND_STATUS_SUCCESS;
+
+ if ((pCmd->flags & OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_FORMAT_VALID) != 0) {
+ if (memcmp(&pDescriptorStreamIO->current_format, pCmd->stream_format, sizeof(pDescriptorStreamIO->current_format)) != 0) {
+ // AVDECC_TODO: Verify that the stream format is supported, and notify the Listener of the change.
+ //memcpy(&pDescriptorStreamInput->current_format, pCmd->stream_format, sizeof(pDescriptorStreamInput->current_format));
+ pCommand->headers.status = OPENAVB_AEM_COMMAND_STATUS_NOT_SUPPORTED;
+ }
+ }
+
+ // AVDECC_TODO: Add support for ENCRYPTED_PDU.
+ if ((pCmd->flags & OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_ENCRYPTED_PDU) != 0) {
+ pCommand->headers.status = OPENAVB_AEM_COMMAND_STATUS_NOT_SUPPORTED;
+ }
+
+ // AVDECC_TODO: Add support for accumulated latency.
+ // For now, just clear the flags and values.
+ pRsp->flags &= ~OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_MSRP_ACC_LAT_VALID;
+ pRsp->msrp_accumulated_latency = 0;
+ pRsp->flags &= ~OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_MSRP_FAILURE_VALID;
+ pRsp->msrp_failure_code = 0;
+ memset(pRsp->msrp_failure_bridge_id, 0, sizeof(pRsp->msrp_failure_bridge_id));
+
+ if (pCommand->headers.status != OPENAVB_AEM_COMMAND_STATUS_SUCCESS) {
+ // As there are already issues, don't bother trying anything following this.
+ }
+ else if (pCmd->descriptor_type == OPENAVB_AEM_DESCRIPTOR_STREAM_INPUT) {
+ // If the controller is trying to set the streaming information for the Listener, this is a problem.
+ // The Listener gets this information from the Talker when the connection starts, so setting it here makes no sense.
+ // We also ignore the CLASS_A flag (or absence of it), as the Talker will indicate that value as well.
+ if ((pCmd->flags &
+ (OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_ID_VALID |
+ OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_DEST_MAC_VALID |
+ OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_VLAN_ID_VALID)) != 0) {
+ AVB_LOG_ERROR("SET_STREAM_INFO cannot set stream parameters for Listener");
+ pCommand->headers.status = OPENAVB_AEM_COMMAND_STATUS_BAD_ARGUMENTS;
+ }
+ }
+ else {
+ // Get the streaming values to send to the Talker.
+ // Invalid values used to indicate those that should not be changed.
+ U8 sr_class = ((pCmd->flags & OPENAVB_ACMP_FLAG_CLASS_B) != 0 ? SR_CLASS_B : SR_CLASS_A);
+ U8 stream_id_valid = FALSE;
+ U8 stream_src_mac[6] = {0, 0, 0, 0, 0, 0};
+ U16 stream_uid = 0;
+ U8 stream_dest_valid = FALSE;
+ U8 stream_dest_mac[6] = {0, 0, 0, 0, 0, 0};
+ U8 stream_vlan_id_valid = FALSE;
+ U16 stream_vlan_id = VLAN_NULL;
+ if ((pCmd->flags & OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_ID_VALID) != 0) {
+ stream_id_valid = TRUE;
+ memcpy(stream_src_mac, pCmd->stream_format, 6);
+ stream_uid = ntohs(*(U16*) (pCmd->stream_format + 6));
+ AVB_LOGF_INFO("AVDECC-specified Stream ID " ETH_FORMAT "/%u for Talker", ETH_OCTETS(stream_src_mac), stream_uid);
+ }
+ if ((pCmd->flags & OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_DEST_MAC_VALID) != 0) {
+ stream_dest_valid = TRUE;
+ memcpy(stream_dest_mac, pCmd->stream_dest_mac, 6);
+ AVB_LOGF_INFO("AVDECC-specified Stream Dest Addr " ETH_FORMAT " for Talker", ETH_OCTETS(stream_dest_mac));
+ }
+ if ((pCmd->flags & OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_VLAN_ID_VALID) != 0) {
+ stream_vlan_id_valid = TRUE;
+ stream_vlan_id = pCmd->stream_vlan_id;
+ AVB_LOGF_INFO("AVDECC-specified Stream VLAN ID %u for Talker", stream_vlan_id);
+ }
+
+ // Pass the values to the Talker.
+ if (!openavbAVDECCSetTalkerStreamInfo(
+ pDescriptorStreamIO, sr_class,
+ stream_id_valid, stream_src_mac, stream_uid,
+ stream_dest_valid, stream_dest_mac,
+ stream_vlan_id_valid, stream_vlan_id)) {
+ AVB_LOG_ERROR("SET_STREAM_INFO error setting stream parameters for Talker");
+ pCommand->headers.status = OPENAVB_AEM_COMMAND_STATUS_NOT_SUPPORTED;
+ }
+ }
+ }
+ else {
+ pCommand->headers.status = OPENAVB_AEM_COMMAND_STATUS_NO_SUCH_DESCRIPTOR;
+ }
+ }
+ }
+ else {
+ pCommand->headers.status = OPENAVB_AEM_COMMAND_STATUS_STREAM_IS_RUNNING;
+ }
+ }
+ else {
+ pCommand->headers.status = OPENAVB_AEM_COMMAND_STATUS_ENTITY_ACQUIRED;
+ }
+ }
break;
case OPENAVB_AEM_COMMAND_CODE_GET_STREAM_INFO:
{
@@ -451,26 +551,57 @@ void processCommand()
pRsp->flags |= OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAMING_WAIT;
}
+ // For the Listener, use the streaming values we received from the current Talker.
+ if (pRsp->descriptor_type == OPENAVB_AEM_DESCRIPTOR_STREAM_INPUT) {
+ // Get the Stream ID.
+ memcpy(pRsp->stream_id, pDescriptorStreamIO->acmp_stream_id, 8);
+ if (memcmp(pRsp->stream_id, "\x00\x00\x00\x00\x00\x00\x00\x00", 8) != 0) {
+ pRsp->flags |= OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_ID_VALID;
+ }
+
+ // Get the Destination MAC Address.
+ memcpy(pRsp->stream_dest_mac, pDescriptorStreamIO->acmp_dest_addr, 6);
+ if (memcmp(pRsp->stream_id, "\x00\x00\x00\x00\x00\x00", 6) != 0) {
+ pRsp->flags |= OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_DEST_MAC_VALID;
+ }
+
+ // Get the Stream VLAN ID if the other stream identifiers are valid.
+ if (pDescriptorStreamIO->acmp_stream_vlan_id != VLAN_NULL &&
+ (pRsp->flags & (OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_ID_VALID | OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_DEST_MAC_VALID)) ==
+ (OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_ID_VALID | OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_DEST_MAC_VALID)) {
+ pRsp->stream_vlan_id = pDescriptorStreamIO->acmp_stream_vlan_id;
+ pRsp->flags |= OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_VLAN_ID_VALID;
+ }
+ }
+ }
+
+ // For the Talker, use the values we are or will use for a connection.
+ if (pRsp->descriptor_type == OPENAVB_AEM_DESCRIPTOR_STREAM_OUTPUT) {
// Get the Stream ID.
- memcpy(pRsp->stream_id, pDescriptorStreamIO->acmp_stream_id, 8);
- if (memcmp(pRsp->stream_id, "\x00\x00\x00\x00\x00\x00\x00\x00", 8) != 0) {
- pRsp->flags |= OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_ID_VALID;
+ if (pDescriptorStreamIO->stream->stream_addr.mac != NULL) {
+ memcpy(pRsp->stream_id, pDescriptorStreamIO->stream->stream_addr.buffer.ether_addr_octet, 6);
+ *(U16*)(pRsp->stream_id) = htons(pDescriptorStreamIO->stream->stream_uid);
+ if (memcmp(pRsp->stream_id, "\x00\x00\x00\x00\x00\x00\x00\x00", 8) != 0) {
+ pRsp->flags |= OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_ID_VALID;
+ }
}
// Get the Destination MAC Address.
- memcpy(pRsp->stream_dest_mac, pDescriptorStreamIO->acmp_dest_addr, 6);
- if (memcmp(pRsp->stream_id, "\x00\x00\x00\x00\x00\x00", 6) != 0) {
- pRsp->flags |= OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_DEST_MAC_VALID;
+ if (pDescriptorStreamIO->stream->dest_addr.mac != NULL) {
+ memcpy(pRsp->stream_dest_mac, pDescriptorStreamIO->stream->dest_addr.buffer.ether_addr_octet, 6);
+ if (memcmp(pRsp->stream_id, "\x00\x00\x00\x00\x00\x00", 6) != 0) {
+ pRsp->flags |= OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_DEST_MAC_VALID;
+ }
}
- // Get the Stream VLAN ID if the other stream identifiers are valid.
- if (pDescriptorStreamIO->acmp_stream_vlan_id != VLAN_NULL &&
- (pRsp->flags & (OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_ID_VALID | OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_DEST_MAC_VALID)) ==
- (OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_ID_VALID | OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_DEST_MAC_VALID)) {
- pRsp->stream_vlan_id = pDescriptorStreamIO->acmp_stream_vlan_id;
+ // Get the Stream VLAN ID.
+ if (pDescriptorStreamIO->stream->vlan_id != 0 &&
+ pDescriptorStreamIO->stream->vlan_id != VLAN_NULL) {
+ pRsp->stream_vlan_id = pDescriptorStreamIO->stream->vlan_id;
pRsp->flags |= OPENAVB_AEM_SET_STREAM_INFO_COMMAND_FLAG_STREAM_VLAN_ID_VALID;
}
}
+
// AVDECC_TODO: Add TALKER_FAILED flag support.
// Get the stream format.
diff --git a/lib/avtp_pipeline/aem/openavb_descriptor_stream_io_pub.h b/lib/avtp_pipeline/aem/openavb_descriptor_stream_io_pub.h
index ec4cd58b..91fc384f 100644
--- a/lib/avtp_pipeline/aem/openavb_descriptor_stream_io_pub.h
+++ b/lib/avtp_pipeline/aem/openavb_descriptor_stream_io_pub.h
@@ -90,6 +90,7 @@ typedef struct {
U16 acmp_flags;
// Streaming values for GET_STREAM_INFO from CONNECT_TX_RESPONSE or CONNECT_RX_RESPONSE.
+ // These values are currently only used for the Listener, as the Talker can get them from it's current configuration.
U8 acmp_stream_id[8];
U8 acmp_dest_addr[6];
U16 acmp_stream_vlan_id;
diff --git a/lib/avtp_pipeline/avdecc/openavb_avdecc_pipeline_interaction_pub.h b/lib/avtp_pipeline/avdecc/openavb_avdecc_pipeline_interaction_pub.h
index 6df3a4ad..c7edac96 100644
--- a/lib/avtp_pipeline/avdecc/openavb_avdecc_pipeline_interaction_pub.h
+++ b/lib/avtp_pipeline/avdecc/openavb_avdecc_pipeline_interaction_pub.h
@@ -45,9 +45,17 @@ bool openavbAVDECCRunTalker(openavb_aem_descriptor_stream_io_t *pDescriptorStrea
bool openavbAVDECCStopListener(openavb_aem_descriptor_stream_io_t *pDescriptorStreamInput, U16 configIdx, openavb_acmp_ListenerStreamInfo_t *pListenerStreamInfo);
bool openavbAVDECCStopTalker(openavb_aem_descriptor_stream_io_t *pDescriptorStreamOutput, U16 configIdx, openavb_acmp_TalkerStreamInfo_t *pTalkerStreamInfo);
-// Get talker stream details. Structure members in TalkerStrreamInfo will be filled.
+// Get talker stream details. Structure members in TalkerStreamInfo will be filled.
bool openavbAVDECCGetTalkerStreamInfo(openavb_aem_descriptor_stream_io_t *pDescriptorStreamOutput, U16 configIdx, openavb_acmp_TalkerStreamInfo_t *pTalkerStreamInfo);
+// Set talker stream details. The settings will be passed to the Talker to use for future connections
+bool openavbAVDECCSetTalkerStreamInfo(
+ openavb_aem_descriptor_stream_io_t *pDescriptorStreamOutput,
+ U8 sr_class,
+ U8 stream_id_valid, const U8 stream_src_mac[6], U16 stream_uid,
+ U8 stream_dest_valid, const U8 stream_dest_mac[6],
+ U8 stream_vlan_id_valid, U16 stream_vlan_id);
+
// Get the streaming state (stopped, running, paused, etc.) AVDECC told the talker or listener to use.
openavbAvdeccMsgStateType_t openavbAVDECCGetRequestedState(openavb_aem_descriptor_stream_io_t *pDescriptorStreamInput, U16 configIdx);
diff --git a/lib/avtp_pipeline/avdecc_msg/openavb_avdecc_msg.h b/lib/avtp_pipeline/avdecc_msg/openavb_avdecc_msg.h
index 135efc45..5efd90d2 100644
--- a/lib/avtp_pipeline/avdecc_msg/openavb_avdecc_msg.h
+++ b/lib/avtp_pipeline/avdecc_msg/openavb_avdecc_msg.h
@@ -88,12 +88,13 @@ typedef enum {
// Client-to-Server messages
OPENAVB_AVDECC_MSG_VERSION_REQUEST,
OPENAVB_AVDECC_MSG_CLIENT_INIT_IDENTIFY,
- OPENAVB_AVDECC_MSG_TALKER_STREAM_ID,
+ OPENAVB_AVDECC_MSG_C2S_TALKER_STREAM_ID,
OPENAVB_AVDECC_MSG_CLIENT_CHANGE_NOTIFICATION,
// Server-to-Client messages
OPENAVB_AVDECC_MSG_VERSION_CALLBACK,
OPENAVB_AVDECC_MSG_LISTENER_STREAM_ID,
+ OPENAVB_AVDECC_MSG_S2C_TALKER_STREAM_ID,
OPENAVB_AVDECC_MSG_CLIENT_CHANGE_REQUEST,
} openavbAvdeccMsgType_t;
@@ -114,7 +115,7 @@ typedef struct {
U16 stream_uid; // Stream ID value
U8 stream_dest_mac[6]; // Multicast address for the stream
U16 stream_vlan_id; // VLAN ID of the stream
-} openavbAvdeccMsgParams_TalkerStreamID_t;
+} openavbAvdeccMsgParams_C2S_TalkerStreamID_t;
typedef struct {
U8 current_state; // Convert to openavbAvdeccMsgStateType_t
@@ -136,6 +137,17 @@ typedef struct {
} openavbAvdeccMsgParams_ListenerStreamID_t;
typedef struct {
+ U8 sr_class; // SR_CLASS_A or SR_CLASS_B
+ U8 stream_id_valid; // The stream_src_mac and stream_uid values were supplied
+ U8 stream_src_mac[6]; // MAC Address for the Talker
+ U16 stream_uid; // Stream ID value
+ U8 stream_dest_valid; // The stream_dest_mac value was supplied
+ U8 stream_dest_mac[6]; // Multicast address for the stream
+ U8 stream_vlan_id_valid; // The stream_vlan_id value was supplied
+ U16 stream_vlan_id; // VLAN ID of the stream
+} openavbAvdeccMsgParams_S2C_TalkerStreamID_t;
+
+typedef struct {
U8 desired_state; // Convert to openavbAvdeccMsgStateType_t
} openavbAvdeccMsgParams_ClientChangeRequest_t;
@@ -173,7 +185,7 @@ void openavbAvdeccMsgClntCheckVerMatchesSrvr(int h, U32 AVBVersion);
bool openavbAvdeccMsgClntInitIdentify(int avdeccMsgHandle, const char * friendly_name, U8 talker);
bool openavbAvdeccMsgSrvrHndlInitIdentifyFromClient(int avdeccMsgHandle, char * friendly_name, U8 talker);
-// Client notify the server of the stream values for the Talker to use.
+// Client notify the server of the stream values the Talker will be using.
bool openavbAvdeccMsgClntTalkerStreamID(int avdeccMsgHandle, U8 sr_class, const U8 stream_src_mac[6], U16 stream_uid, const U8 stream_dest_mac[6], U16 stream_vlan_id);
bool openavbAvdeccMsgSrvrHndlTalkerStreamIDFromClient(int avdeccMsgHandle, U8 sr_class, const U8 stream_src_mac[6], U16 stream_uid, const U8 stream_dest_mac[6], U16 stream_vlan_id);
@@ -181,6 +193,20 @@ bool openavbAvdeccMsgSrvrHndlTalkerStreamIDFromClient(int avdeccMsgHandle, U8 sr
bool openavbAvdeccMsgSrvrListenerStreamID(int avdeccMsgHandle, U8 sr_class, const U8 stream_src_mac[6], U16 stream_uid, const U8 stream_dest_mac[6], U16 stream_vlan_id);
bool openavbAvdeccMsgClntHndlListenerStreamIDFromServer(int avdeccMsgHandle, U8 sr_class, const U8 stream_src_mac[6], U16 stream_uid, const U8 stream_dest_mac[6], U16 stream_vlan_id);
+// Server notify the client of the stream values for the Talker to use (supplied by the AVDECC controller).
+bool openavbAvdeccMsgSrvrTalkerStreamID(
+ int avdeccMsgHandle,
+ U8 sr_class,
+ U8 stream_id_valid, const U8 stream_src_mac[6], U16 stream_uid,
+ U8 stream_dest_valid, const U8 stream_dest_mac[6],
+ U8 stream_vlan_id_valid, U16 stream_vlan_id);
+bool openavbAvdeccMsgClntHndlTalkerStreamIDFromServer(
+ int avdeccMsgHandle,
+ U8 sr_class,
+ U8 stream_id_valid, const U8 stream_src_mac[6], U16 stream_uid,
+ U8 stream_dest_valid, const U8 stream_dest_mac[6],
+ U8 stream_vlan_id_valid, U16 stream_vlan_id);
+
// Server state change requests, and client notifications of state changes.
bool openavbAvdeccMsgSrvrChangeRequest(int avdeccMsgHandle, openavbAvdeccMsgStateType_t desiredState);
bool openavbAvdeccMsgClntHndlChangeRequestFromServer(int avdeccMsgHandle, openavbAvdeccMsgStateType_t desiredState);
diff --git a/lib/avtp_pipeline/avdecc_msg/openavb_avdecc_msg_client.c b/lib/avtp_pipeline/avdecc_msg/openavb_avdecc_msg_client.c
index 5e1c76cd..1dc9a27e 100644
--- a/lib/avtp_pipeline/avdecc_msg/openavb_avdecc_msg_client.c
+++ b/lib/avtp_pipeline/avdecc_msg/openavb_avdecc_msg_client.c
@@ -89,6 +89,18 @@ static bool openavbAvdeccMsgClntReceiveFromServer(int avdeccMsgHandle, openavbAv
msg->params.listenerStreamID.sr_class, msg->params.listenerStreamID.stream_src_mac, ntohs(msg->params.listenerStreamID.stream_uid),
msg->params.listenerStreamID.stream_dest_mac, ntohs(msg->params.listenerStreamID.stream_vlan_id));
break;
+ case OPENAVB_AVDECC_MSG_S2C_TALKER_STREAM_ID:
+ AVB_LOG_DEBUG("Message received: OPENAVB_AVDECC_MSG_S2C_TALKER_STREAM_ID");
+ openavbAvdeccMsgClntHndlTalkerStreamIDFromServer(avdeccMsgHandle,
+ msg->params.s2cTalkerStreamID.sr_class,
+ msg->params.s2cTalkerStreamID.stream_id_valid,
+ msg->params.s2cTalkerStreamID.stream_src_mac,
+ ntohs(msg->params.s2cTalkerStreamID.stream_uid),
+ msg->params.s2cTalkerStreamID.stream_dest_valid,
+ msg->params.s2cTalkerStreamID.stream_dest_mac,
+ msg->params.s2cTalkerStreamID.stream_vlan_id_valid,
+ ntohs(msg->params.s2cTalkerStreamID.stream_vlan_id));
+ break;
case OPENAVB_AVDECC_MSG_CLIENT_CHANGE_REQUEST:
AVB_LOG_DEBUG("Message received: OPENAVB_AVDECC_MSG_CLIENT_CHANGE_REQUEST");
openavbAvdeccMsgClntHndlChangeRequestFromServer(avdeccMsgHandle, (openavbAvdeccMsgStateType_t) msg->params.clientChangeRequest.desired_state);
@@ -188,9 +200,9 @@ bool openavbAvdeccMsgClntTalkerStreamID(int avdeccMsgHandle, U8 sr_class, const
// Send the stream information to the server.
memset(&msgBuf, 0, OPENAVB_AVDECC_MSG_LEN);
- msgBuf.type = OPENAVB_AVDECC_MSG_TALKER_STREAM_ID;
- openavbAvdeccMsgParams_TalkerStreamID_t * pParams =
- &(msgBuf.params.talkerStreamID);
+ msgBuf.type = OPENAVB_AVDECC_MSG_C2S_TALKER_STREAM_ID;
+ openavbAvdeccMsgParams_C2S_TalkerStreamID_t * pParams =
+ &(msgBuf.params.c2sTalkerStreamID);
pParams->sr_class = sr_class;
memcpy(pParams->stream_src_mac, stream_src_mac, 6);
pParams->stream_uid = htons(stream_uid);
@@ -242,12 +254,116 @@ bool openavbAvdeccMsgClntHndlListenerStreamIDFromServer(int avdeccMsgHandle, U8
pCfg->vlan_id = stream_vlan_id;
}
- AVB_LOGF_DEBUG("AVDECC-supplied sr_class: %u", pCfg->sr_class);
- AVB_LOGF_DEBUG("AVDECC-supplied stream_id: " ETH_FORMAT "/%u",
+ AVB_LOGF_DEBUG("AVDECC-supplied (Listener) sr_class: %u", pCfg->sr_class);
+ AVB_LOGF_DEBUG("AVDECC-supplied (Listener) stream_id: " ETH_FORMAT "/%u",
ETH_OCTETS(pCfg->stream_addr.buffer.ether_addr_octet), pCfg->stream_uid);
- AVB_LOGF_DEBUG("AVDECC-supplied dest_addr: " ETH_FORMAT,
+ AVB_LOGF_DEBUG("AVDECC-supplied (Listener) dest_addr: " ETH_FORMAT,
ETH_OCTETS(pCfg->dest_addr.buffer.ether_addr_octet));
- AVB_LOGF_DEBUG("AVDECC-supplied vlan_id: %u", pCfg->vlan_id);
+ AVB_LOGF_DEBUG("AVDECC-supplied (Listener) vlan_id: %u", pCfg->vlan_id);
+
+ AVB_TRACE_EXIT(AVB_TRACE_AVDECC_MSG);
+ return true;
+}
+
+bool openavbAvdeccMsgClntHndlTalkerStreamIDFromServer(int avdeccMsgHandle,
+ U8 sr_class, U8 stream_id_valid, const U8 stream_src_mac[6], U16 stream_uid, U8 stream_dest_valid, const U8 stream_dest_mac[6], U8 stream_vlan_id_valid, U16 stream_vlan_id)
+{
+ AVB_TRACE_ENTRY(AVB_TRACE_AVDECC_MSG);
+
+ avdecc_msg_state_t *pState = AvdeccMsgStateListGet(avdeccMsgHandle);
+ if (!pState) {
+ AVB_LOGF_ERROR("avdeccMsgHandle %d not valid", avdeccMsgHandle);
+ AVB_TRACE_EXIT(AVB_TRACE_AVDECC_MSG);
+ return false;
+ }
+
+ if (!pState->pTLState) {
+ AVB_LOGF_ERROR("avdeccMsgHandle %d state not valid", avdeccMsgHandle);
+ AVB_TRACE_EXIT(AVB_TRACE_AVDECC_MSG);
+ return false;
+ }
+
+ // Update the stream information supplied by the server.
+ openavb_tl_cfg_t * pCfg = &(pState->pTLState->cfg);
+ pCfg->sr_class = sr_class;
+ AVB_LOGF_DEBUG("AVDECC-supplied (Talker) sr_class: %u", pCfg->sr_class);
+ if (stream_id_valid) {
+ if (memcmp(stream_src_mac, "\x00\x00\x00\x00\x00\x00", 6) == 0 && stream_uid == 0) {
+ // Restore from the backup value.
+ if (pCfg->backup_stream_id_valid) {
+ memcpy(pCfg->stream_addr.buffer.ether_addr_octet, pCfg->backup_stream_addr, 6);
+ pCfg->stream_addr.mac = &(pCfg->stream_addr.buffer); // Indicate that the MAC Address is valid.
+ pCfg->stream_uid = pCfg->backup_stream_uid;
+ pCfg->backup_stream_id_valid = FALSE;
+ AVB_LOGF_DEBUG("AVDECC-supplied (Talker) reverted to default stream_id: " ETH_FORMAT "/%u",
+ ETH_OCTETS(pCfg->stream_addr.buffer.ether_addr_octet), pCfg->stream_uid);
+ }
+ }
+ else {
+ // Backup the current value.
+ if (!pCfg->backup_stream_id_valid) {
+ memcpy(pCfg->backup_stream_addr, pCfg->stream_addr.buffer.ether_addr_octet, 6);
+ pCfg->backup_stream_uid = pCfg->stream_uid;
+ pCfg->backup_stream_id_valid = TRUE;
+ }
+
+ // Save the new value.
+ memcpy(pCfg->stream_addr.buffer.ether_addr_octet, stream_src_mac, 6);
+ pCfg->stream_addr.mac = &(pCfg->stream_addr.buffer); // Indicate that the MAC Address is valid.
+ pCfg->stream_uid = stream_uid;
+ AVB_LOGF_DEBUG("AVDECC-supplied (Talker) stream_id: " ETH_FORMAT "/%u",
+ ETH_OCTETS(pCfg->stream_addr.buffer.ether_addr_octet), pCfg->stream_uid);
+ }
+ }
+ if (stream_dest_valid) {
+ if (memcmp(stream_dest_mac, "\x00\x00\x00\x00\x00\x00", 6) == 0) {
+ // Restore from the backup value.
+ if (pCfg->backup_dest_addr_valid) {
+ memcpy(pCfg->dest_addr.buffer.ether_addr_octet, pCfg->backup_dest_addr, 6);
+ pCfg->dest_addr.mac = &(pCfg->dest_addr.buffer); // Indicate that the MAC Address is valid.
+ pCfg->backup_dest_addr_valid = FALSE;
+ AVB_LOGF_DEBUG("AVDECC-supplied (Talker) reverted to default dest_addr: " ETH_FORMAT,
+ ETH_OCTETS(pCfg->dest_addr.buffer.ether_addr_octet));
+ }
+ }
+ else {
+ // Backup the current value.
+ if (!pCfg->backup_dest_addr_valid) {
+ memcpy(pCfg->backup_dest_addr, pCfg->dest_addr.buffer.ether_addr_octet, 6);
+ pCfg->backup_dest_addr_valid = TRUE;
+ }
+
+ // Save the new value.
+ memcpy(pCfg->dest_addr.buffer.ether_addr_octet, stream_dest_mac, 6);
+ pCfg->dest_addr.mac = &(pCfg->dest_addr.buffer); // Indicate that the MAC Address is valid.
+ AVB_LOGF_DEBUG("AVDECC-supplied (Talker) dest_addr: " ETH_FORMAT,
+ ETH_OCTETS(pCfg->dest_addr.buffer.ether_addr_octet));
+ }
+ }
+ if (stream_vlan_id_valid && stream_vlan_id != VLAN_NULL) {
+ if (stream_vlan_id == 0) {
+ // Restore from the backup value.
+ if (pCfg->backup_vlan_id_valid) {
+ pCfg->vlan_id = pCfg->backup_vlan_id;
+ pCfg->backup_vlan_id_valid = FALSE;
+ AVB_LOGF_DEBUG("AVDECC-supplied (Talker) reverted to default vlan_id: %u", pCfg->vlan_id);
+ }
+ }
+ else {
+ // Backup the current value.
+ if (!pCfg->backup_vlan_id_valid) {
+ pCfg->backup_vlan_id_valid = pCfg->vlan_id;
+ pCfg->backup_vlan_id_valid = TRUE;
+ }
+
+ // Save the new value.
+ pCfg->vlan_id = stream_vlan_id;
+ AVB_LOGF_DEBUG("AVDECC-supplied (Talker) vlan_id: %u", pCfg->vlan_id);
+ }
+ }
+
+ // Notify AVDECC of the Talker values to be used after the update.
+ openavbAvdeccMsgClntTalkerStreamID(avdeccMsgHandle, pCfg->sr_class, pCfg->stream_addr.buffer.ether_addr_octet, pCfg->stream_uid, pCfg->dest_addr.buffer.ether_addr_octet, pCfg->vlan_id);
AVB_TRACE_EXIT(AVB_TRACE_AVDECC_MSG);
return true;
diff --git a/lib/avtp_pipeline/avdecc_msg/openavb_avdecc_msg_server.c b/lib/avtp_pipeline/avdecc_msg/openavb_avdecc_msg_server.c
index fa1cd73c..39fb1a31 100644
--- a/lib/avtp_pipeline/avdecc_msg/openavb_avdecc_msg_server.c
+++ b/lib/avtp_pipeline/avdecc_msg/openavb_avdecc_msg_server.c
@@ -96,14 +96,14 @@ static bool openavbAvdeccMsgSrvrReceiveFromClient(int avdeccMsgHandle, openavbAv
msg->params.clientInitIdentify.friendly_name,
msg->params.clientInitIdentify.talker);
break;
- case OPENAVB_AVDECC_MSG_TALKER_STREAM_ID:
- AVB_LOG_DEBUG("Message received: OPENAVB_AVDECC_MSG_TALKER_STREAM_ID");
+ case OPENAVB_AVDECC_MSG_C2S_TALKER_STREAM_ID:
+ AVB_LOG_DEBUG("Message received: OPENAVB_AVDECC_MSG_C2S_TALKER_STREAM_ID");
ret = openavbAvdeccMsgSrvrHndlTalkerStreamIDFromClient(avdeccMsgHandle,
- msg->params.talkerStreamID.sr_class,
- msg->params.talkerStreamID.stream_src_mac,
- ntohs(msg->params.talkerStreamID.stream_uid),
- msg->params.talkerStreamID.stream_dest_mac,
- ntohs(msg->params.talkerStreamID.stream_vlan_id));
+ msg->params.c2sTalkerStreamID.sr_class,
+ msg->params.c2sTalkerStreamID.stream_src_mac,
+ ntohs(msg->params.c2sTalkerStreamID.stream_uid),
+ msg->params.c2sTalkerStreamID.stream_dest_mac,
+ ntohs(msg->params.c2sTalkerStreamID.stream_vlan_id));
break;
case OPENAVB_AVDECC_MSG_CLIENT_CHANGE_NOTIFICATION:
AVB_LOG_DEBUG("Message received: OPENAVB_AVDECC_MSG_CLIENT_CHANGE_NOTIFICATION");
@@ -276,6 +276,38 @@ bool openavbAvdeccMsgSrvrListenerStreamID(int avdeccMsgHandle, U8 sr_class, cons
return ret;
}
+bool openavbAvdeccMsgSrvrTalkerStreamID(int avdeccMsgHandle,
+ U8 sr_class, U8 stream_id_valid, const U8 stream_src_mac[6], U16 stream_uid, U8 stream_dest_valid, const U8 stream_dest_mac[6], U8 stream_vlan_id_valid, U16 stream_vlan_id)
+{
+ AVB_TRACE_ENTRY(AVB_TRACE_AVDECC_MSG);
+ openavbAvdeccMessage_t msgBuf;
+
+ avdecc_msg_state_t *pState = AvdeccMsgStateListGet(avdeccMsgHandle);
+ if (!pState) {
+ AVB_LOGF_ERROR("avdeccMsgHandle %d not valid", avdeccMsgHandle);
+ AVB_TRACE_EXIT(AVB_TRACE_AVDECC_MSG);
+ return false;
+ }
+
+ // Send the stream information to the client.
+ memset(&msgBuf, 0, OPENAVB_AVDECC_MSG_LEN);
+ msgBuf.type = OPENAVB_AVDECC_MSG_S2C_TALKER_STREAM_ID;
+ openavbAvdeccMsgParams_S2C_TalkerStreamID_t * pParams =
+ &(msgBuf.params.s2cTalkerStreamID);
+ pParams->sr_class = sr_class;
+ pParams->stream_id_valid = stream_id_valid;
+ memcpy(pParams->stream_src_mac, stream_src_mac, 6);
+ pParams->stream_uid = htons(stream_uid);
+ pParams->stream_dest_valid = stream_dest_valid;
+ memcpy(pParams->stream_dest_mac, stream_dest_mac, 6);
+ pParams->stream_vlan_id_valid = stream_vlan_id_valid;
+ pParams->stream_vlan_id = htons(stream_vlan_id);
+ bool ret = openavbAvdeccMsgSrvrSendToClient(avdeccMsgHandle, &msgBuf);
+
+ AVB_TRACE_EXIT(AVB_TRACE_AVDECC_MSG);
+ return ret;
+}
+
bool openavbAvdeccMsgSrvrChangeRequest(int avdeccMsgHandle, openavbAvdeccMsgStateType_t desiredState)
{
AVB_TRACE_ENTRY(AVB_TRACE_AVDECC_MSG);
diff --git a/lib/avtp_pipeline/endpoint/openavb_endpoint.h b/lib/avtp_pipeline/endpoint/openavb_endpoint.h
index cf7af178..a3f82078 100644
--- a/lib/avtp_pipeline/endpoint/openavb_endpoint.h
+++ b/lib/avtp_pipeline/endpoint/openavb_endpoint.h
@@ -75,6 +75,7 @@ typedef enum {
//////////////////////////////
typedef struct {
U8 destAddr[ETH_ALEN];
+ U8 noMaapAllocate;
AVBTSpec_t tSpec;
U8 srClass;
U8 srRank;
@@ -97,7 +98,7 @@ typedef struct {
//////////////////////////////
typedef struct {
char ifname[IFNAMSIZ + 10]; // Include space for the socket type prefix (e.g. "simple:eth0")
- U8 destAddr[ETH_ALEN];
+ U8 destAddr[ETH_ALEN];
openavbSrpLsnrDeclSubtype_t lsnrDecl;
U8 srClass;
U32 classRate;
@@ -210,6 +211,7 @@ void openavbEptClntCheckVerMatchesSrvr(int h, U32 AVBVersion);
bool openavbEptClntRegisterStream(int h,
AVBStreamID_t *streamID,
U8 destAddr[],
+ U8 noMaapAllocation,
AVBTSpec_t *tSpec,
U8 srClass,
U8 srRank,
@@ -218,6 +220,7 @@ bool openavbEptClntRegisterStream(int h,
bool openavbEptSrvrRegisterStream(int h,
AVBStreamID_t *streamID,
U8 destAddr[],
+ U8 noMaapAllocation,
AVBTSpec_t *tSpec,
U8 srClass,
U8 srRank,
diff --git a/lib/avtp_pipeline/endpoint/openavb_endpoint_client.c b/lib/avtp_pipeline/endpoint/openavb_endpoint_client.c
index 4d2b64cf..27d08cee 100644
--- a/lib/avtp_pipeline/endpoint/openavb_endpoint_client.c
+++ b/lib/avtp_pipeline/endpoint/openavb_endpoint_client.c
@@ -113,6 +113,7 @@ static bool openavbEptClntReceiveFromServer(int h, openavbEndpointMessage_t *msg
bool openavbEptClntRegisterStream(int h,
AVBStreamID_t *streamID,
U8 destAddr[],
+ U8 noMaapAllocate,
AVBTSpec_t *tSpec,
U8 srClass,
U8 srRank,
@@ -132,8 +133,10 @@ bool openavbEptClntRegisterStream(int h,
memset(&msgBuf, 0, OPENAVB_ENDPOINT_MSG_LEN);
msgBuf.type = OPENAVB_ENDPOINT_TALKER_REGISTER;
memcpy(&(msgBuf.streamID), streamID, sizeof(AVBStreamID_t));
- if (destAddr)
+ if (destAddr) {
memcpy(msgBuf.params.talkerRegister.destAddr, destAddr, ETH_ALEN);
+ msgBuf.params.talkerRegister.noMaapAllocate = noMaapAllocate;
+ }
msgBuf.params.talkerRegister.tSpec.maxFrameSize = tSpec->maxFrameSize;
msgBuf.params.talkerRegister.tSpec.maxIntervalFrames = tSpec->maxIntervalFrames;
msgBuf.params.talkerRegister.srClass = srClass;
diff --git a/lib/avtp_pipeline/endpoint/openavb_endpoint_server.c b/lib/avtp_pipeline/endpoint/openavb_endpoint_server.c
index ae2cf8fb..22208333 100644
--- a/lib/avtp_pipeline/endpoint/openavb_endpoint_server.c
+++ b/lib/avtp_pipeline/endpoint/openavb_endpoint_server.c
@@ -84,12 +84,13 @@ static bool openavbEptSrvrReceiveFromClient(int h, openavbEndpointMessage_t *msg
case OPENAVB_ENDPOINT_TALKER_REGISTER:
AVB_LOGF_DEBUG("TalkerRegister from client uid=%d", msg->streamID.uniqueID);
ret = openavbEptSrvrRegisterStream(h, &msg->streamID,
- msg->params.talkerRegister.destAddr,
- &msg->params.talkerRegister.tSpec,
- msg->params.talkerRegister.srClass,
- msg->params.talkerRegister.srRank,
- msg->params.talkerRegister.latency,
- msg->params.talkerRegister.txRate);
+ msg->params.talkerRegister.destAddr,
+ msg->params.talkerRegister.noMaapAllocate,
+ &msg->params.talkerRegister.tSpec,
+ msg->params.talkerRegister.srClass,
+ msg->params.talkerRegister.srRank,
+ msg->params.talkerRegister.latency,
+ msg->params.talkerRegister.txRate);
break;
case OPENAVB_ENDPOINT_LISTENER_ATTACH:
AVB_LOGF_DEBUG("ListenerAttach from client uid=%d", msg->streamID.uniqueID);
@@ -205,6 +206,7 @@ void openavbEptSrvrSendServerVersionToClient(int h, U32 AVBVersion)
bool openavbEptSrvrRegisterStream(int h,
AVBStreamID_t *streamID,
U8 destAddr[],
+ U8 noMaapAllocation,
AVBTSpec_t *tSpec,
U8 srClass,
U8 srRank,
@@ -238,7 +240,7 @@ bool openavbEptSrvrRegisterStream(int h,
ps->fwmark = INVALID_FWMARK;
// If MAAP is available, or no client-supplied address, allocate an address.
- if (openavbMaapDaemonAvailable() ||
+ if ((!noMaapAllocation && openavbMaapDaemonAvailable()) ||
memcmp(ps->destAddr, destAddr, ETH_ALEN) == 0) {
struct ether_addr addr;
ps->hndMaap = openavbMaapAllocate(1, &addr);
diff --git a/lib/avtp_pipeline/platform/Linux/avdecc/openavb_avdecc_pipeline_interaction.c b/lib/avtp_pipeline/platform/Linux/avdecc/openavb_avdecc_pipeline_interaction.c
index be38cf67..78819ca6 100644
--- a/lib/avtp_pipeline/platform/Linux/avdecc/openavb_avdecc_pipeline_interaction.c
+++ b/lib/avtp_pipeline/platform/Linux/avdecc/openavb_avdecc_pipeline_interaction.c
@@ -276,6 +276,40 @@ bool openavbAVDECCGetTalkerStreamInfo(openavb_aem_descriptor_stream_io_t *pDescr
return TRUE;
}
+bool openavbAVDECCSetTalkerStreamInfo(openavb_aem_descriptor_stream_io_t *pDescriptorStreamOutput,
+ U8 sr_class, U8 stream_id_valid, const U8 stream_src_mac[6], U16 stream_uid, U8 stream_dest_valid, const U8 stream_dest_mac[6], U8 stream_vlan_id_valid, U16 stream_vlan_id)
+{
+ AVB_TRACE_ENTRY(AVB_TRACE_AVDECC);
+
+ // Sanity tests.
+ if (!pDescriptorStreamOutput) {
+ AVB_LOG_ERROR("openavbAVDECCSetTalkerStreamInfo Invalid descriptor");
+ AVB_TRACE_EXIT(AVB_TRACE_AVDECC);
+ return FALSE;
+ }
+ if (!pDescriptorStreamOutput->stream) {
+ AVB_LOG_ERROR("openavbAVDECCSetTalkerStreamInfo Invalid StreamInput descriptor stream");
+ AVB_TRACE_EXIT(AVB_TRACE_AVDECC);
+ return FALSE;
+ }
+ if (!pDescriptorStreamOutput->stream->client) {
+ AVB_LOG_ERROR("openavbAVDECCSetTalkerStreamInfo Invalid stream client pointer");
+ AVB_TRACE_EXIT(AVB_TRACE_AVDECC);
+ return FALSE;
+ }
+
+ // Send the information to the client.
+ if (!openavbAvdeccMsgSrvrTalkerStreamID(pDescriptorStreamOutput->stream->client->avdeccMsgHandle,
+ sr_class, stream_id_valid, stream_src_mac, stream_uid, stream_dest_valid, stream_dest_mac, stream_vlan_id_valid, stream_vlan_id)) {
+ AVB_LOG_ERROR("Error sending stream info updates to Talker");
+ AVB_TRACE_EXIT(AVB_TRACE_AVDECC);
+ return FALSE;
+ }
+
+ AVB_TRACE_EXIT(AVB_TRACE_AVDECC);
+ return TRUE;
+}
+
openavbAvdeccMsgStateType_t openavbAVDECCGetRequestedState(openavb_aem_descriptor_stream_io_t *pDescriptorStream, U16 configIdx)
{
AVB_TRACE_ENTRY(AVB_TRACE_AVDECC);
diff --git a/lib/avtp_pipeline/platform/Linux/avdecc_msg/openavb_avdecc_msg_osal.h b/lib/avtp_pipeline/platform/Linux/avdecc_msg/openavb_avdecc_msg_osal.h
index f866c9dd..b68ea38d 100644
--- a/lib/avtp_pipeline/platform/Linux/avdecc_msg/openavb_avdecc_msg_osal.h
+++ b/lib/avtp_pipeline/platform/Linux/avdecc_msg/openavb_avdecc_msg_osal.h
@@ -46,12 +46,13 @@ typedef struct {
// Client-to-Server messages
openavbAvdeccMsgParams_VersionRequest_t versionRequest;
openavbAvdeccMsgParams_ClientInitIdentify_t clientInitIdentify;
- openavbAvdeccMsgParams_TalkerStreamID_t talkerStreamID;
+ openavbAvdeccMsgParams_C2S_TalkerStreamID_t c2sTalkerStreamID;
openavbAvdeccMsgParams_ClientChangeNotification_t clientChangeNotification;
// Server-to-Client messages
openavbAvdeccMsgParams_VersionCallback_t versionCallback;
openavbAvdeccMsgParams_ListenerStreamID_t listenerStreamID;
+ openavbAvdeccMsgParams_S2C_TalkerStreamID_t s2cTalkerStreamID;
openavbAvdeccMsgParams_ClientChangeRequest_t clientChangeRequest;
} params;
} openavbAvdeccMessage_t;
diff --git a/lib/avtp_pipeline/tl/openavb_talker.h b/lib/avtp_pipeline/tl/openavb_talker.h
index 0bdcf1ea..86bfc39e 100644
--- a/lib/avtp_pipeline/tl/openavb_talker.h
+++ b/lib/avtp_pipeline/tl/openavb_talker.h
@@ -41,7 +41,7 @@ https://github.com/benhoyt/inih/commit/74d2ca064fb293bc60a77b0bd068075b293cf175.
typedef struct {
// Data from callback
char ifname[IFNAMSIZ + 10]; // Include space for the socket type prefix (e.g. "simple:eth0")
- AVBStreamID_t streamID;
+ AVBStreamID_t streamID;
U8 destAddr[ETH_ALEN];
AVBTSpec_t tSpec;
U8 srClass;
diff --git a/lib/avtp_pipeline/tl/openavb_talker_endpoint.c b/lib/avtp_pipeline/tl/openavb_talker_endpoint.c
index 24262665..e3343e78 100644
--- a/lib/avtp_pipeline/tl/openavb_talker_endpoint.c
+++ b/lib/avtp_pipeline/tl/openavb_talker_endpoint.c
@@ -186,6 +186,7 @@ bool openavbTLRunTalkerInit(tl_state_t *pTLState)
return (openavbEptClntRegisterStream(pTLState->endpointHandle,
&streamID,
pCfg->dest_addr.mac->ether_addr_octet,
+ pCfg->backup_dest_addr_valid, // If we have a backup dest_addr, then the current one was forced and MAAP should not be used.
&pTalkerData->tSpec,
pCfg->sr_class,
pCfg->sr_rank,
diff --git a/lib/avtp_pipeline/tl/openavb_tl_pub.h b/lib/avtp_pipeline/tl/openavb_tl_pub.h
index 89d4784d..67472d5e 100755
--- a/lib/avtp_pipeline/tl/openavb_tl_pub.h
+++ b/lib/avtp_pipeline/tl/openavb_tl_pub.h
@@ -162,6 +162,22 @@ typedef struct {
openavb_map_initialize_fn_t pMapInitFn;
/// Initialization function in interface
openavb_intf_initialize_fn_t pIntfInitFn;
+
+ /// TRUE if backup_stream_addr and backup_stream_uid are valid.
+ bool backup_stream_id_valid;
+ /// Saved original MAC address of the source
+ U8 backup_stream_addr[ETH_ALEN];
+ /// Stream UID (has to be unique)
+ U16 backup_stream_uid;
+ /// TRUE if backup_dest_addr_valid is valid.
+ bool backup_dest_addr_valid;
+ /// Saved original MAC address of destination - multicast (talker only if SRP is enabled)
+ U8 backup_dest_addr[ETH_ALEN];
+ /// TRUE if backup_vlan_id_valid is valid.
+ bool backup_vlan_id_valid;
+ /// Saved original VLAN ID
+ U16 backup_vlan_id;
+
} openavb_tl_cfg_t;
/// Structure holding configuration of mapping and interface modules