HRESULT avcUnitNotifyCheck(LM_CONTEXT* notifyList, NOTIFY_CHECK_CALLBACK notifyCheckCB, NOTIFY_UPDATE_CALLBACK notifyUpdateCB) { HRESULT hResult = NO_ERROR; uint32 pos = 0; uint32 index = 0; pDataStream pStream = NULL; UNION_NOTIFY* notify = NULL; AVC_HEADER avcHeader; BOOL bChanged = FALSE; PB *packetBlock; // determine if there is a notify on the specified subunit DO_FOREVER { hResult = lmGetNthElement(notifyList, (void **) ¬ify, pos, &index); if (hResult != NO_ERROR) return NO_ERROR; bChanged = FALSE; // call callback to make notify specific check on notify state hResult = (* notifyCheckCB) (notify, &bChanged); if (bChanged) { #ifdef _SYSDEBUG if (sysDebugIsEnabled(SYSDEBUG_TRACE_AVC & SYSDEBUG_TRACE_ERRORS)) //SYSDEBUG_TRACE_AVC { sysPrintCurTime(); sysDebugPrintf("avcUnitNotify changed state for notify\n\r"); } #endif //_SYSDEBUG hResult = pbGetApplicationDatastream(notify->notifyComm.packetBlock, &pStream); if (hResult != NO_ERROR) break; hResult = avcDecodeHeader(pStream, &avcHeader); if (hResult != NO_ERROR) break; hResult = dsGotoMarker(pStream, DSMARKER_OPERAND_0); if (hResult != NO_ERROR) break; hResult = dsSwitchMode(pStream, dsMODE_WRITE); if (hResult != NO_ERROR) break; // call callback to write notify specific data into stream (from operand[0]) hResult = (* notifyUpdateCB) (notify, pStream); if (hResult != NO_ERROR) break; packetBlock = notify->notifyComm.packetBlock; hResult = lmReleaseElement(notifyList, index); if (hResult != NO_ERROR) break; hResult = lmRemoveElement(notifyList, index); if (hResult != NO_ERROR) break; hResult = avcReplyResponse (AVC_RESPONSE_CHANGED, packetBlock); if (hResult != NO_ERROR) break; } else { lmReleaseElement(notifyList, index); pos++; } } lmReleaseElement(notifyList, index); return hResult; }
HRESULT avcHandlePacketBlock(PB* packetBlock) { HRESULT hResult = NO_ERROR; AVC_HEADER avcHeader; uint32 response = 0; pDataStream pStream = NULL; BOOL bReceivedResponse = FALSE; BOOL bSendResponse = FALSE; hResult = pbGetApplicationDatastream(packetBlock, &pStream); if (hResult != NO_ERROR) return hResult; // Log the AV/C message in hResult = avcDecodeHeader(pStream, &avcHeader); if (hResult != NO_ERROR) // there is some fault with the packet { hResult = E_PKT_AVC_NOT_IMPLEMENTED; } bReceivedResponse = avcCtypeIsResponse(avcHeader.ctype); if (hResult == NO_ERROR) { hResult = avcUnitReserveCheck(&avcHeader, packetBlock); // check if (sub-) unit is reserved etc. } if (hResult == NO_ERROR) { if (rmInMap(avcHeader.opcode, avcDescriptorOpcodesRangeMap)) { // pass descriptor command off to the DescriptorManager (includes responses from our descriptor reads) hResult = avcCallDescriptorHandler(&avcHeader, packetBlock); } else { // command is not mapped as a descriptor command so now we want to handle this normally hResult = avcHandleCallback(&avcHeader, packetBlock); } } if (hResult != NO_ERROR) { // need to take care of the response here // verify packet ctypes for response codes if (bReceivedResponse == FALSE) { bSendResponse = TRUE; switch (hResult) { case E_PKT_AVC_ACCEPTED: response = AVC_RESPONSE_ACCEPTED; break; case E_PKT_AVC_IMPLEMENTED: response = AVC_RESPONSE_IMPLEMENTED; break; // command is supported - send IMPLEMENTED response case E_PKT_AVC_SUBUNIT_BUSY: response = AVC_RESPONSE_REJECTED; break; // subunit cannot accept packet at this time - send REJECTED response case E_PKT_AVC_REJECTED: response = AVC_RESPONSE_REJECTED; break; // send REJECTED response case E_PKT_AVC_NOT_IMPLEMENTED: response = AVC_RESPONSE_NOT_IMPLEMENTED; break; // send NOT IMPLEMENTED response case E_PKT_AVC_INTERIM: response = AVC_RESPONSE_INTERIM; break; // send INTERIM response case E_PKT_AVC_STABLE: response = AVC_RESPONSE_STABLE; break; // send STABLE response default: bSendResponse = FALSE; break; } if (pbPacketIsBroadcast(packetBlock) == TRUE) { if (response == AVC_RESPONSE_NOT_IMPLEMENTED) { bSendResponse = FALSE; } } if (bSendResponse) { avcReplyResponse(response, packetBlock); } } } return hResult; }