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

📄 mac_csp_tx.c

📁 Zigbee2006入门(源代码+文档讲解+系统推荐)
💻 C
📖 第 1 页 / 共 3 页
字号:
/**************************************************************************************************
    Filename:
    Revised:        $Date: 2007-03-28 18:21:19 -0700 (Wed, 28 Mar 2007) $
    Revision:       $Revision: 13888 $

    Description:

    Describe the purpose and contents of the file.

    Copyright (c) 2006 by Texas Instruments, Inc.
    All Rights Reserved.  Permission to use, reproduce, copy, prepare
    derivative works, modify, distribute, perform, display or sell this
    software and/or its documentation for any purpose is prohibited
    without the express written consent of Texas Instruments, Inc.
**************************************************************************************************/



/* ------------------------------------------------------------------------------------------------
 *                                           Includes
 * ------------------------------------------------------------------------------------------------
 */

/* hal */
#include "hal_types.h"
#include "hal_mcu.h"

/* high-level */
#include "mac_spec.h"
#include "mac_pib.h"

/* exported low-level */
#include "mac_low_level.h"

/* low-level specific */
#include "mac_csp_tx.h"
#include "mac_tx.h"
#include "mac_rx.h"
#include "mac_rx_onoff.h"

/* target specific */
#include "mac_radio_defs.h"

/* debug */
#include "mac_assert.h"


/* ------------------------------------------------------------------------------------------------
 *                                   CSP Defines / Macros
 * ------------------------------------------------------------------------------------------------
 */
/* immediate strobe commands */
#define ISSTART     0xFE
#define ISSTOP      0xFF

/* strobe processor instructions */
#define SKIP(s,c)   (0x00 | (((s) & 0x07) << 4) | ((c) & 0x0F))   /* skip 's' instructions if 'c' is true  */
#define WHILE(c)    SKIP(0,c)              /* pend while 'c' is true (derived instruction)        */
#define WAITW(w)    (0x80 | ((w) & 0x1F))  /* wait for 'w' number of MAC timer overflows          */
#define WEVENT      (0xB8)                 /* wait for MAC timer compare                          */
#define WAITX       (0xBB)                 /* wait for CPSX number of MAC timer overflows         */
#define LABEL       (0xBA)                 /* set next instruction as start of loop               */
#define RPT(c)      (0xA0 | ((c) & 0x0F))  /* if condition is true jump to last label             */
#define INT         (0xB9)                 /* assert IRQ_CSP_INT interrupt                        */
#define INCY        (0xBD)                 /* increment CSPY                                      */
#define INCMAXY(m)  (0xB0 | ((m) & 0x07))  /* increment CSPY but not above maximum value of 'm'   */
#define DECY        (0xBE)                 /* decrement CSPY                                      */
#define DECZ        (0xBF)                 /* decrement CSPZ                                      */
#define RANDXY      (0xBC)                 /* load the lower CSPY bits of CSPX with random value  */

/* strobe processor command instructions */
#define SSTOP       (0xDF)    /* stop program execution                                      */
#define SNOP        (0xC0)    /* no operation                                                */
#define STXCALN     (0xC1)    /* enable and calibrate frequency synthesizer for TX           */
#define SRXON       (0xC2)    /* turn on receiver                                            */
#define STXON       (0xC3)    /* transmit after calibration                                  */
#define STXONCCA    (0xC4)    /* transmit after calibration if CCA indicates clear channel   */
#define SRFOFF      (0xC5)    /* turn off RX/TX                                              */
#define SFLUSHRX    (0xC6)    /* flush receive FIFO                                          */
#define SFLUSHTX    (0xC7)    /* flush transmit FIFO                                         */
#define SACK        (0xC8)    /* send ACK frame                                              */
#define SACKPEND    (0xC9)    /* send ACK frame with pending bit set                         */

/* conditions for use with instructions SKIP and RPT */
#define C_CCA_IS_VALID        0x00
#define C_SFD_IS_ACTIVE       0x01
#define C_CPU_CTRL_IS_ON      0x02
#define C_END_INSTR_MEM       0x03
#define C_CSPX_IS_ZERO        0x04
#define C_CSPY_IS_ZERO        0x05
#define C_CSPZ_IS_ZERO        0x06

/* negated conditions for use with instructions SKIP and RPT */
#define C_NEGATE(c)   ((c) | 0x08)
#define C_CCA_IS_INVALID      C_NEGATE(C_CCA_IS_VALID)
#define C_SFD_IS_INACTIVE     C_NEGATE(C_SFD_IS_ACTIVE)
#define C_CPU_CTRL_IS_OFF     C_NEGATE(C_CPU_CTRL_IS_ON)
#define C_NOT_END_INSTR_MEM   C_NEGATE(C_END_INSTR_MEM)
#define C_CSPX_IS_NON_ZERO    C_NEGATE(C_CSPX_IS_ZERO)
#define C_CSPY_IS_NON_ZERO    C_NEGATE(C_CSPY_IS_ZERO)
#define C_CSPZ_IS_NON_ZERO    C_NEGATE(C_CSPZ_IS_ZERO)

///////////////////////////////////////////////////////////////////////////////////////
//  REV_B_WORKAROUND : part of a workaround to help ameliorate chip bug #273.
//  This bug could actually be the source of extant every-once-in-a-while problems.
//  When Rev B is obsolete, delete these defines and all references to them.
//  Compile errors should flag all related fixes.
#define __SNOP_SKIP__     1
#define __SNOP__          SNOP
///////////////////////////////////////////////////////////////////////////////////////


/* ------------------------------------------------------------------------------------------------
 *                                         Defines
 * ------------------------------------------------------------------------------------------------
 */

/* CSPY return values from CSP program */
#define CSPY_RXTX_COLLISION         0
#define CSPY_NO_RXTX_COLLISION      1

/* CSPZ return values from CSP program */
#define CSPZ_CODE_TX_DONE           0
#define CSPZ_CODE_CHANNEL_BUSY      1
#define CSPZ_CODE_TX_ACK_TIME_OUT   2


/* ------------------------------------------------------------------------------------------------
 *                                          Macros
 * ------------------------------------------------------------------------------------------------
 */
#define CSP_STOP_AND_CLEAR_PROGRAM()          st( RFST = ISSTOP;  )
#define CSP_START_PROGRAM()                   st( RFST = ISSTART; )
////////////////////////////////////////////////////////////////////////////////////////////////////
//  REV_B_WORKAROUND : workaround for chip bug #574, delete this whole mess when Rev B is obsolete.
//  Compile errors will flag all instances of macro call.  Delete those too.
#ifndef _REMOVE_REV_B_WORKAROUNDS
#define __FIX_T2CMP_BUG__()   st( if (T2CMP == 0) { T2CMP = 1;} )
#else
#define __FIX_T2CMP_BUG__()
#endif
////////////////////////////////////////////////////////////////////////////////////////////////////

/*
 *  These macros improve readability of using T2CMP in conjunction with WEVENT.
 *
 *  The timer2 compare, T2CMP, only compares one byte of the 16-bit timer register.
 *  It is configurable and has been set to compare against the upper byte of the timer value.
 *  The CSP instruction WEVENT waits for the timer value to be greater than or equal
 *  the value of T2CMP.
 *
 *  Reading the timer value is done by reading the low byte first.  This latches the
 *  high byte.  A trick with the ternary operator is used by a macro below to force a
 *  read of the low byte when returning the value of the high byte.
 *
 *  CSP_WEVENT_SET_TRIGGER_NOW()      - sets the WEVENT trigger point at the current timer count
 *  CSP_WEVENT_SET_TRIGGER_SYMBOLS(x) - sets the WEVENT trigger point in symbols
 *  CSP_WEVENT_READ_COUNT_SYMBOLS()   - reads the current timer count in symbols
 */
#define T2THD_TICKS_PER_SYMBOL                (MAC_RADIO_TIMER_TICKS_PER_SYMBOL() >> 8)

#define CSP_WEVENT_SET_TRIGGER_NOW()          st( uint8 temp=T2TLD;  T2CMP = T2THD;  __FIX_T2CMP_BUG__(); )
#define CSP_WEVENT_SET_TRIGGER_SYMBOLS(x)     st( MAC_ASSERT(x <= MAC_A_UNIT_BACKOFF_PERIOD); \
                                                  T2CMP = (x) * T2THD_TICKS_PER_SYMBOL; \
                                                  __FIX_T2CMP_BUG__(); )
#define CSP_WEVENT_READ_COUNT_SYMBOLS()       (((T2TLD) ? T2THD : T2THD) / T2THD_TICKS_PER_SYMBOL)

/*
 *  Number of bits used for aligning a slotted transmit to the backoff count (plus
 *  derived values).  There are restrictions on this value.  Compile time integrity
 *  checks will catch an illegal setting of this value.  A full explanation accompanies
 *  this compile time check (see bottom of this file).
 */
#define SLOTTED_TX_MAX_BACKOFF_COUNTDOWN_NUM_BITS     4
#define SLOTTED_TX_MAX_BACKOFF_COUNTDOWN              (1 << SLOTTED_TX_MAX_BACKOFF_COUNTDOWN_NUM_BITS)
#define SLOTTED_TX_BACKOFF_COUNT_ALIGN_BIT_MASK       (SLOTTED_TX_MAX_BACKOFF_COUNTDOWN - 1)



/* ------------------------------------------------------------------------------------------------
 *                                     Local Programs
 * ------------------------------------------------------------------------------------------------
 */
static void cspPrepForTxProgram(void);


/**************************************************************************************************
 * @fn          macCspTxReset
 *
 * @brief       Reset the CSP.  Immediately halts any running program.
 *
 * @param       none
 *
 * @return      none
 **************************************************************************************************
 */
void macCspTxReset(void)
{
  MAC_MCU_CSP_STOP_DISABLE_INTERRUPT();
  MAC_MCU_CSP_INT_DISABLE_INTERRUPT();
  CSP_STOP_AND_CLEAR_PROGRAM();
}


/*=================================================================================================
 * @fn          cspPrepForTxProgram
 *
 * @brief       Prepare and initialize for transmit CSP program.
 *              Call *before* loading the CSP program!
 *
 * @param       none
 *
 * @return      none
 *=================================================================================================
 */
static void cspPrepForTxProgram(void)
{
  MAC_ASSERT(!(RFIM & IM_CSP_STOP)); /* already an active CSP program */

  /* set up parameters for CSP transmit program */
  CSPY = CSPY_NO_RXTX_COLLISION;
  CSPZ = CSPZ_CODE_CHANNEL_BUSY;

  /* clear the currently loaded CSP, this generates a stop interrupt which must be cleared */
  CSP_STOP_AND_CLEAR_PROGRAM();
  MAC_MCU_CSP_STOP_CLEAR_INTERRUPT();
  MAC_MCU_CSP_INT_CLEAR_INTERRUPT();
}


/**************************************************************************************************
 * @fn          macCspTxPrepCsmaUnslotted
 *
 * @brief       Prepare CSP for "Unslotted CSMA" transmit.  Load CSP program and set CSP parameters.
 *
 * @param       none
 *
 * @return      none
 **************************************************************************************************
 */
void macCspTxPrepCsmaUnslotted(void)
{
  cspPrepForTxProgram();

  /*----------------------------------------------------------------------
   *  Load CSP program :  Unslotted CSMA transmit 
   */

  /*
   *  Wait for X number of backoffs, then wait for intra-backoff count
   *  to reach value set for WEVENT.
   */
  RFST = WAITX;
  RFST = WEVENT;

  /* wait for one backoff to guarantee receiver has been on at least that long */
  RFST = WAITW(1);
  RFST = WEVENT;
  
  /* sample CCA, if it fails exit from here, CSPZ indicates result */
  RFST = SKIP(1+__SNOP_SKIP__, C_CCA_IS_VALID);
  RFST = SSTOP;
  RFST = __SNOP__;
  
  /* CSMA has passed so transmit */
  RFST = STXON;

  /*
   *  If the SFD pin is high at this point, there was an RX-TX collision.
   *  In other words, TXON was strobed while receiving.  The CSP variable
   *  CSPY is decremented to indicate this happened.  The rest of the transmit
   *  continues normally.

⌨️ 快捷键说明

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