mirror of
https://github.com/espressif/openthread.git
synced 2026-08-11 13:17:48 +00:00
[data-poll-manager] add StopFastPolls() support (#3763)
This commit is contained in:
@@ -429,6 +429,9 @@ OTAPI uint32_t OTCALL otLinkGetPollPeriod(otInstance *aInstance);
|
||||
* @note Minimal non-zero value should be `OPENTHREAD_CONFIG_MINIMUM_POLL_PERIOD` (10ms).
|
||||
* Or zero to clear user-specified poll period.
|
||||
*
|
||||
* @note User-specified value should be no more than the maximal value 0x3FFFFFF ((1 << 26) - 1) allowed,
|
||||
* otherwise it would be cilpped by the maximal value.
|
||||
*
|
||||
* @param[in] aInstance A pointer to an OpenThread instance.
|
||||
* @param[in] aPollPeriod data poll period in milliseconds.
|
||||
*
|
||||
|
||||
@@ -53,8 +53,9 @@ namespace ot {
|
||||
DataPollManager::DataPollManager(Instance &aInstance)
|
||||
: InstanceLocator(aInstance)
|
||||
, mTimerStartTime(0)
|
||||
, mExternalPollPeriod(0)
|
||||
, mPollPeriod(0)
|
||||
, mExternalPollPeriod(0)
|
||||
, mFastPollsUsers(0)
|
||||
, mTimer(aInstance, &DataPollManager::HandlePollTimer, this)
|
||||
, mEnabled(false)
|
||||
, mAttachMode(false)
|
||||
@@ -89,6 +90,7 @@ void DataPollManager::StopPolling(void)
|
||||
mPollTimeoutCounter = 0;
|
||||
mPollTxFailureCounter = 0;
|
||||
mRemainingFastPolls = 0;
|
||||
mFastPollsUsers = 0;
|
||||
mEnabled = false;
|
||||
}
|
||||
|
||||
@@ -164,9 +166,15 @@ otError DataPollManager::SetExternalPollPeriod(uint32_t aPeriod)
|
||||
{
|
||||
otError error = OT_ERROR_NONE;
|
||||
|
||||
if (aPeriod != 0 && aPeriod < OPENTHREAD_CONFIG_MINIMUM_POLL_PERIOD)
|
||||
if (aPeriod != 0)
|
||||
{
|
||||
ExitNow(error = OT_ERROR_INVALID_ARGS);
|
||||
VerifyOrExit(aPeriod >= OPENTHREAD_CONFIG_MINIMUM_POLL_PERIOD, error = OT_ERROR_INVALID_ARGS);
|
||||
|
||||
// Clipped by the maximal value.
|
||||
if (aPeriod > kMaxExternalPeriod)
|
||||
{
|
||||
aPeriod = kMaxExternalPeriod;
|
||||
}
|
||||
}
|
||||
|
||||
if (mExternalPollPeriod != aPeriod)
|
||||
@@ -212,7 +220,12 @@ void DataPollManager::HandlePollSent(otError aError)
|
||||
if (mRemainingFastPolls != 0)
|
||||
{
|
||||
mRemainingFastPolls--;
|
||||
shouldRecalculatePollPeriod = (mRemainingFastPolls == 0);
|
||||
|
||||
if (mRemainingFastPolls == 0)
|
||||
{
|
||||
shouldRecalculatePollPeriod = true;
|
||||
mFastPollsUsers = 0;
|
||||
}
|
||||
}
|
||||
|
||||
if (mRetxMode == true)
|
||||
@@ -330,6 +343,11 @@ void DataPollManager::SendFastPolls(uint8_t aNumFastPolls)
|
||||
{
|
||||
bool shouldRecalculatePollPeriod = (mRemainingFastPolls == 0);
|
||||
|
||||
if (mFastPollsUsers < kMaxFastPollsUsers)
|
||||
{
|
||||
mFastPollsUsers++;
|
||||
}
|
||||
|
||||
if (aNumFastPolls == 0)
|
||||
{
|
||||
aNumFastPolls = kDefaultFastPolls;
|
||||
@@ -351,6 +369,27 @@ void DataPollManager::SendFastPolls(uint8_t aNumFastPolls)
|
||||
}
|
||||
}
|
||||
|
||||
otError DataPollManager::StopFastPolls(void)
|
||||
{
|
||||
otError error = OT_ERROR_NONE;
|
||||
|
||||
VerifyOrExit(mFastPollsUsers != 0);
|
||||
|
||||
// If `mFastPollsUsers` hits the max, let it be cleared
|
||||
// from `HandlePollSent()` (after all fast polls are sent).
|
||||
VerifyOrExit(mFastPollsUsers < kMaxFastPollsUsers);
|
||||
|
||||
mFastPollsUsers--;
|
||||
|
||||
VerifyOrExit(mFastPollsUsers == 0, error = OT_ERROR_BUSY);
|
||||
|
||||
mRemainingFastPolls = 0;
|
||||
ScheduleNextPoll(kRecalculatePollPeriod);
|
||||
|
||||
exit:
|
||||
return error;
|
||||
}
|
||||
|
||||
void DataPollManager::ScheduleNextPoll(PollPeriodSelector aPollPeriodSelector)
|
||||
{
|
||||
if (aPollPeriodSelector == kRecalculatePollPeriod)
|
||||
|
||||
@@ -62,8 +62,9 @@ class DataPollManager : public InstanceLocator
|
||||
public:
|
||||
enum
|
||||
{
|
||||
kDefaultFastPolls = 8, ///< Default number of fast poll transmissions (@sa StartFastPolls).
|
||||
kMaxFastPolls = 15, ///< Maximum number of fast poll transmissions allowed.
|
||||
kDefaultFastPolls = 8, ///< Default number of fast poll transmissions (@sa StartFastPolls).
|
||||
kMaxFastPolls = 15, ///< Maximum number of fast poll transmissions allowed.
|
||||
kMaxFastPollsUsers = 63, ///< Maximum number of the users of fast poll transmissions allowed.
|
||||
};
|
||||
|
||||
/**
|
||||
@@ -111,6 +112,9 @@ public:
|
||||
* Minimal non-zero value should be `OPENTHREAD_CONFIG_MINIMUM_POLL_PERIOD` (10ms). Or zero to clear user-specified
|
||||
* poll period.
|
||||
*
|
||||
* User-specified value should be no more than the maximal value 0x3FFFFFF ((1 << 26) - 1) allowed, otherwise it
|
||||
* would be cilpped by the maximal value.
|
||||
*
|
||||
* @param[in] aPeriod The data poll period in milliseconds.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Successfully set/cleared user-specified poll period.
|
||||
@@ -183,11 +187,26 @@ public:
|
||||
* If @p aNumFastPolls is zero the default value specified by `kDefaultFastPolls` is used instead. The number of
|
||||
* fast polls is clipped by maximum value specified by `kMaxFastPolls`.
|
||||
*
|
||||
* Note that per `SendFastPolls()` would increase the internal reference count until up to the allowed maximum
|
||||
* value. If there are retransmission mechanism in the caller component, it should be responsible to call
|
||||
* `StopFastPolls()` the same times as `SendFastPolls()` it triggered to decrease the reference count properly,
|
||||
* guaranteeing to exit fast poll mode gracefully. Otherwise, fast poll would continue until all data polls are sent
|
||||
* out.
|
||||
*
|
||||
* @param[in] aNumFastPolls If non-zero, number of fast polls to send, if zero, default value is used instead.
|
||||
*
|
||||
*/
|
||||
void SendFastPolls(uint8_t aNumFastPolls);
|
||||
|
||||
/**
|
||||
* This method asks data poll manager to stop fast polls when the expecting response is received.
|
||||
*
|
||||
* @retval OT_ERROR_NONE Successfully stopped fast polls when no other responses are expected.
|
||||
* @retval OT_ERROR_BUSY There are other callers who are waiting for responses.
|
||||
*
|
||||
*/
|
||||
otError StopFastPolls(void);
|
||||
|
||||
/**
|
||||
* This method gets the maximum data polling period in use.
|
||||
*
|
||||
@@ -204,6 +223,8 @@ private:
|
||||
kNoBufferRetxPollPeriod = 200, ///< Poll retx due to no buffer space.
|
||||
kFastPollPeriod = 188, ///< Period used for fast polls.
|
||||
kMinPollPeriod = OPENTHREAD_CONFIG_MINIMUM_POLL_PERIOD, ///< Minimum allowed poll period.
|
||||
kMaxExternalPeriod = ((1 << 26) - 1), ///< Maximum allowed user-specified period.
|
||||
///< i.e. (0x3FFFFF)ms, about 18.64 hours.
|
||||
};
|
||||
|
||||
enum
|
||||
@@ -225,8 +246,9 @@ private:
|
||||
uint32_t GetDefaultPollPeriod(void) const;
|
||||
|
||||
uint32_t mTimerStartTime;
|
||||
uint32_t mExternalPollPeriod;
|
||||
uint32_t mPollPeriod;
|
||||
uint32_t mExternalPollPeriod : 26; //< In milliseconds.
|
||||
uint8_t mFastPollsUsers : 6; //< Number of callers which request fast polls.
|
||||
|
||||
TimerMilli mTimer;
|
||||
|
||||
|
||||
@@ -2845,6 +2845,16 @@ otError Mle::HandleDataResponse(const Message &aMessage, const Ip6::MessageInfo
|
||||
otLogWarnMleErr(error, "Failed to process Data Response");
|
||||
}
|
||||
|
||||
if (mDataRequestState == kDataRequestNone && !IsRxOnWhenIdle())
|
||||
{
|
||||
// Here simply stops fast data poll request by Mle Data Request.
|
||||
// Note that in some cases fast data poll may continue after below stop operation until
|
||||
// running out the specified number. E.g. other component also trigger fast poll, and
|
||||
// is waiting for response; or the corner case where multiple Mle Data Request attempts
|
||||
// happened due to the retransmission mechanism.
|
||||
IgnoreReturnValue(Get<DataPollManager>().StopFastPolls());
|
||||
}
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user