⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 af.c

📁 一些基于IRA环境开发的zigbee实例程序
💻 C
📖 第 1 页 / 共 2 页
字号:
  if ( (pfnDescCB = afGetDescCB( srcEP )) )
  {
    uint16 *pID = (uint16 *)(pfnDescCB(
                                 AF_DESCRIPTOR_PROFILE_ID, srcEP->endPoint ));
    if ( pID )
    {
      req.profileID = *pID;
      osal_mem_free( pID );
    }
  }
  else if ( srcEP->simpleDesc )
  {
    req.profileID = srcEP->simpleDesc->AppProfId;
  }

  req.txOptions = 0;

  if ( ( options & AF_ACK_REQUEST              ) &&
       ( req.dstAddr.addrMode != AddrBroadcast ) &&
       ( req.dstAddr.addrMode != AddrGroup     )    )
  {
    req.txOptions |=  APS_TX_OPTIONS_ACK;
  }

  if ( options & AF_SKIP_ROUTING )
  {
    req.txOptions |=  APS_TX_OPTIONS_SKIP_ROUTING;
  }

  if ( options & AF_EN_SECURITY )
  {
    req.txOptions |= APS_TX_OPTIONS_SECURITY_ENABLE;
    mtu.aps.secure = TRUE;
  }
  else
  {
    mtu.aps.secure = FALSE;
  }

  mtu.kvp = FALSE;

  req.transID       = *transID;
  req.srcEP         = srcEP->endPoint;
  req.dstEP         = dstAddr->endPoint;
  req.clusterID     = cID;
  req.asduLen       = len;
  req.asdu          = buf;
  req.discoverRoute = TRUE;//(uint8)((options & AF_DISCV_ROUTE) ? 1 : 0);
  req.radiusCounter = radius;

  if (len > afDataReqMTU( &mtu ) )
  {
    if (apsfSendFragmented)
    {
      req.txOptions |= AF_FRAGMENTED | APS_TX_OPTIONS_ACK;
      stat = (*apsfSendFragmented)( &req );
    }
    else
    {
      stat = afStatus_INVALID_PARAMETER;
    }
  }
  else
  {
    stat = APSDE_DataReq( &req );
  }

  /*
   * If this is an EndPoint-to-EndPoint message on the same device, it will not
   * get added to the NWK databufs. So it will not go OTA and it will not get
   * a MACCB_DATA_CONFIRM_CMD callback. Thus it is necessary to generate the
   * AF_DATA_CONFIRM_CMD here. Note that APSDE_DataConfirm() only generates one
   * message with the first in line TransSeqNumber, even on a multi message.
   * Also note that a reflected msg will not have its confirmation generated
   * here.
   */
  if ( (req.dstAddr.addrMode == Addr16Bit) &&
       (req.dstAddr.addr.shortAddr == NLME_GetShortAddr()) )
  {
    afDataConfirm( srcEP->endPoint, *transID, stat );
  }

  if ( stat == afStatus_SUCCESS )
  {
    (*transID)++;
  }

  return (afStatus_t)stat;
}

/*********************************************************************
 * @fn      afFindEndPointDescList
 *
 * @brief   Find the endpoint description entry from the endpoint
 *          number.
 *
 * @param   EndPoint - Application Endpoint to look for
 *
 * @return  the address to the endpoint/interface description entry
 */
static epList_t *afFindEndPointDescList( byte EndPoint )
{
  epList_t *epSearch;

  // Start at the beginning
  epSearch = epList;

  // Look through the list until the end
  while ( epSearch )
  {
    // Is there a match?
    if ( epSearch->epDesc->endPoint == EndPoint )
    {
      return ( epSearch );
    }
    else
      epSearch = epSearch->nextDesc;  // Next entry
  }

  return ( (epList_t *)NULL );
}

/*********************************************************************
 * @fn      afFindEndPointDesc
 *
 * @brief   Find the endpoint description entry from the endpoint
 *          number.
 *
 * @param   EndPoint - Application Endpoint to look for
 *
 * @return  the address to the endpoint/interface description entry
 */
endPointDesc_t *afFindEndPointDesc( byte EndPoint )
{
  epList_t *epSearch;

  // Look for the endpoint
  epSearch = afFindEndPointDescList( EndPoint );

  if ( epSearch )
    return ( epSearch->epDesc );
  else
    return ( (endPointDesc_t *)NULL );
}

/*********************************************************************
 * @fn      afFindSimpleDesc
 *
 * @brief   Find the Simple Descriptor from the endpoint number.
 *
 * @param   EP - Application Endpoint to look for.
 *
 * @return  Non-zero to indicate that the descriptor memory must be freed.
 */
byte afFindSimpleDesc( SimpleDescriptionFormat_t **ppDesc, byte EP )
{
  epList_t *epItem = afFindEndPointDescList( EP );
  byte rtrn = FALSE;

  if ( epItem )
  {
    if ( epItem->pfnDescCB )
    {
      *ppDesc = epItem->pfnDescCB( AF_DESCRIPTOR_SIMPLE, EP );
      rtrn = TRUE;
    }
    else
    {
      *ppDesc = epItem->epDesc->simpleDesc;
    }
  }
  else
  {
    *ppDesc = NULL;
  }

  return rtrn;
}

/*********************************************************************
 * @fn      afGetDescCB
 *
 * @brief   Get the Descriptor callback function.
 *
 * @param   epDesc - pointer to the endpoint descriptor
 *
 * @return  function pointer or NULL
 */
static pDescCB afGetDescCB( endPointDesc_t *epDesc )
{
  epList_t *epSearch;

  // Start at the beginning
  epSearch = epList;

  // Look through the list until the end
  while ( epSearch )
  {
    // Is there a match?
    if ( epSearch->epDesc == epDesc )
    {
      return ( epSearch->pfnDescCB );
    }
    else
      epSearch = epSearch->nextDesc;  // Next entry
  }

  return ( (pDescCB)NULL );
}

/*********************************************************************
 * @fn      afDataReqMTU
 *
 * @brief   Get the Data Request MTU(Max Transport Unit).
 *
 * @param   fields - afDataReqMTU_t
 *
 * @return  uint8(MTU)
 */
uint8 afDataReqMTU( afDataReqMTU_t* fields )
{
  uint8 len;
  uint8 hdr;

  if ( fields->kvp == TRUE )
  {
    hdr = AF_HDR_KVP_MAX_LEN;
  }
  else
  {
    hdr = AF_HDR_V1_1_MAX_LEN;
  }

  len = (uint8)(APSDE_DataReqMTU(&fields->aps) - hdr);

  return len;
}

/*********************************************************************
 * @fn      afGetMatch
 *
 * @brief   Set the allow response flag.
 *
 * @param   ep - Application Endpoint to look for
 * @param   action - true - allow response, false - no response
 *
 * @return  TRUE allow responses, FALSE no response
 */
uint8 afGetMatch( uint8 ep )
{
  epList_t *epSearch;

  // Look for the endpoint
  epSearch = afFindEndPointDescList( ep );

  if ( epSearch )
  {
    if ( epSearch->flags & eEP_AllowMatch )
      return ( TRUE );
    else
      return ( FALSE );
  }
  else
    return ( FALSE );
}

/*********************************************************************
 * @fn      afSetMatch
 *
 * @brief   Set the allow response flag.
 *
 * @param   ep - Application Endpoint to look for
 * @param   action - true - allow response, false - no response
 *
 * @return  TRUE if success, FALSE if endpoint not found
 */
uint8 afSetMatch( uint8 ep, uint8 action )
{
  epList_t *epSearch;

  // Look for the endpoint
  epSearch = afFindEndPointDescList( ep );

  if ( epSearch )
  {
    if ( action )
    {
      epSearch->flags |= eEP_AllowMatch;
    }
    else
    {
      epSearch->flags &= (0xff ^ eEP_AllowMatch);
    }
    return ( TRUE );
  }
  else
    return ( FALSE );
}

/*********************************************************************
 * @fn      afNumEndPoints
 *
 * @brief   Returns the number of endpoints defined (including 0)
 *
 * @param   none
 *
 * @return  number of endpoints
 */
byte afNumEndPoints( void )
{
  epList_t *epSearch;
  byte endpoints;

  // Start at the beginning
  epSearch = epList;
  endpoints = 0;

  while ( epSearch )
  {
    endpoints++;
    epSearch = epSearch->nextDesc;
  }

  return ( endpoints );
}

/*********************************************************************
 * @fn      afEndPoints
 *
 * @brief   Fills in the passed in buffer with the endpoint (numbers).
 *          Use afNumEndPoints to find out how big a buffer to supply.
 *
 * @param   epBuf - pointer to mem used
 *
 * @return  void
 */
void afEndPoints( byte *epBuf, byte skipZDO )
{
  epList_t *epSearch;
  byte endPoint;

  // Start at the beginning
  epSearch = epList;

  while ( epSearch )
  {
    endPoint = epSearch->epDesc->endPoint;

    if ( !skipZDO || endPoint != 0 )
      *epBuf++ = endPoint;

    epSearch = epSearch->nextDesc;
  }
}

/*********************************************************************
 * Semi-Precision fuctions
 */

#if ( AF_FLOAT_SUPPORT )
/*********************************************************************
 * @fn      afCnvtSP_uint16
 *
 * @brief   Converts uint16 to semi-precision structure format
 *
 * @param   sp - semi-precision structure format
 *
 * @return  16 bit value for semiprecision.
 */
uint16 afCnvtSP_uint16( afSemiPrecision_t sp )
{
  return ( ((sp.sign & 0x0001) << 15)
              | ((sp.exponent & 0x001F) << 10)
              | (sp.mantissa & 0x03FF) );
}

/*********************************************************************
 * @fn      afCnvtuint16_SP
 *
 * @brief   Converts uint16 to semi-precision structure format
 *
 * @param   rawSP - Raw representation of SemiPrecision
 *
 * @return  SemiPrecision conversion.
 */
afSemiPrecision_t afCnvtuint16_SP( uint16 rawSP )
{
  afSemiPrecision_t sp = {0,0,0};

  sp.sign = ((rawSP >> 15) & 0x0001);
  sp.exponent = ((rawSP >> 10) & 0x001F);
  sp.mantissa = (rawSP & 0x03FF);
  return ( sp );
}

/*********************************************************************
 * @fn      afCnvtFloat_SP
 *
 * @brief   Converts float to semi-precision structure format
 *
 * @param   f - float value to convert from
 *
 * NOTE: This function will convert to the closest possible
 *       representation in a 16 bit format.  Meaning that
 *       the number may not be exact.  For example, 10.7 will
 *       convert to 10.69531, because .7 is a repeating binary
 *       number.  The mantissa for afSemiPrecision_t is 10 bits
 *       and .69531 is the 10 bit representative of .7.
 *
 * @return  SemiPrecision conversion.
 */
afSemiPrecision_t afCnvtFloat_SP( float f )
{
  afSemiPrecision_t sp = {0,0,0};
  unsigned long mantissa;
  unsigned int oldexp;
  int tempexp;
  float calcMant;
  unsigned long *uf;

  if ( f < 0 )
  {
    sp.sign = 1;
    f = f * -1;
  }
  else
    sp.sign = 0;

  if ( f == 0 )
  {
    sp.exponent = (unsigned int)0;
    sp.mantissa = (unsigned int)0;
  }
  else
  {
    uf = (void*)&f;

    mantissa = *uf & 0x7fffff;
    oldexp = (unsigned int)((*uf >> 23) & 0xff);
    tempexp = oldexp - 127;

    calcMant = (float)((float)(mantissa) / (float)(0x800000));
    mantissa = (unsigned long)(calcMant * 1024);

    sp.exponent = (unsigned int)(tempexp + 15);
    sp.mantissa = (unsigned int)(mantissa);
  }

  return ( sp );
}

/*********************************************************************
 * @fn      afCnvtSP_Float
 *
 * @brief   Converts semi-precision structure format to float
 *
 * @param   sp - afSemiPrecision format to convert from
 *
 * @return  float
 */
float afCnvtSP_Float( afSemiPrecision_t sp )
{
  float a, b, c;

  if ( sp.exponent == 0 && sp.mantissa == 0 )
  {
    a = 0;
    b = 0;
  }
  else
  {
    a = (float)((float)1 + (float)((float)(sp.mantissa)/1024));

#if defined( __MWERKS__ )
    b = powf( 2.0, (float)((float)sp.exponent - 15.0) );
#else
    b = (float)pow( 2.0, sp.exponent - 15 );
#endif
  }

  if ( sp.sign )
    c = a * b * -1;
  else
    c = a * b;

  return ( c );
}
#endif

void afCopyAddress ( afAddrType_t *afAddr, zAddrType_t *zAddr )
{
  afAddr->addrMode = (afAddrMode_t)zAddr->addrMode;
  afAddr->addr.shortAddr = zAddr->addr.shortAddr;
}

/*********************************************************************
*********************************************************************/

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -