Fix LogitechHIDPP20Controller probe negative cache
This commit is contained in:
+24
-10
@@ -1530,6 +1530,12 @@ uint8_t LogitechHIDPP20Controller::GetFeatureIndex(uint16_t feature_page,
|
||||
}
|
||||
else
|
||||
{
|
||||
/*---------------------------------------------*\
|
||||
| The device answered: absent is an answer, |
|
||||
| cache it. |
|
||||
\*---------------------------------------------*/
|
||||
caps.feature_map[feature_page] = 0;
|
||||
|
||||
LOG_DEBUG("%s Feature 0x%04X not present", LOG_TAG, feature_page);
|
||||
}
|
||||
|
||||
@@ -1537,11 +1543,10 @@ uint8_t LogitechHIDPP20Controller::GetFeatureIndex(uint16_t feature_page,
|
||||
}
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| Cache misses too so failed lookups are not re-queried |
|
||||
| No answer describes the link, not the feature: do not |
|
||||
| cache it, or retries would answer from the map. |
|
||||
\*-----------------------------------------------------*/
|
||||
caps.feature_map[feature_page] = 0;
|
||||
|
||||
LOG_DEBUG("%s Feature 0x%04X not found", LOG_TAG, feature_page);
|
||||
LOG_DEBUG("%s Feature 0x%04X did not answer", LOG_TAG, feature_page);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -3333,6 +3338,15 @@ bool LogitechHIDPP20Controller::Probe()
|
||||
\*-----------------------------------------------------*/
|
||||
uint8_t test_idx = 0;
|
||||
|
||||
/*-----------------------------------------------------*\
|
||||
| A receiver-paired device is known to speak HID++, so |
|
||||
| it gets the wider first-contact budget; an unknown |
|
||||
| node keeps the tight probe and fails fast. |
|
||||
\*-----------------------------------------------------*/
|
||||
const HIDPP20RetryPolicy& first_contact = wireless
|
||||
? HIDPP20_POLICY_FIRST_CONTACT
|
||||
: HIDPP20_POLICY_PROBE;
|
||||
|
||||
if(transport.type == HIDPP20_TRANSPORT_CENTURION)
|
||||
{
|
||||
/*-------------------------------------------------*\
|
||||
@@ -3419,16 +3433,16 @@ bool LogitechHIDPP20Controller::Probe()
|
||||
else
|
||||
{
|
||||
LOG_DEBUG("%s No CentPPBridge: Centurion direct connection", LOG_TAG);
|
||||
test_idx = GetFeatureIndex(HIDPP20_FEAT_FEATURE_SET, HIDPP20_POLICY_PROBE);
|
||||
test_idx = GetFeatureIndex(HIDPP20_FEAT_FEATURE_SET, first_contact);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/*-------------------------------------------------*\
|
||||
| Standard HID++: probe FeatureSet (0x0001): |
|
||||
| fast-fail. The probe policy already includes |
|
||||
| its own retry; the outer loop is preserved for |
|
||||
| buffer-flushing behavior between attempts. |
|
||||
| Standard HID++: probe FeatureSet (0x0001). The |
|
||||
| policy retries on the wire; the outer loop adds a |
|
||||
| buffer flush between bursts to clear stale |
|
||||
| queued responses. |
|
||||
\*-------------------------------------------------*/
|
||||
for(int attempt = 0; attempt < 3 && test_idx == 0; attempt++)
|
||||
{
|
||||
@@ -3443,7 +3457,7 @@ bool LogitechHIDPP20Controller::Probe()
|
||||
LOG_DEBUG("%s IRoot retry %d at %s", LOG_TAG, attempt + 1, location.c_str());
|
||||
}
|
||||
|
||||
test_idx = GetFeatureIndex(HIDPP20_FEAT_FEATURE_SET, HIDPP20_POLICY_PROBE);
|
||||
test_idx = GetFeatureIndex(HIDPP20_FEAT_FEATURE_SET, first_contact);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -454,6 +454,8 @@ static constexpr uint16_t HIDPP20_BACKOFF_RELIABLE[] =
|
||||
{ 0, 63, 125, 250, 500, 1000, 2000 };
|
||||
static constexpr uint16_t HIDPP20_BACKOFF_PROBE[] =
|
||||
{ 0, 100 };
|
||||
static constexpr uint16_t HIDPP20_BACKOFF_FIRST_CONTACT[] =
|
||||
{ 0, 100, 250, 500 };
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| SW-control reclaim backoff. Used by ReconnectDevice |
|
||||
@@ -557,6 +559,20 @@ static constexpr HIDPP20RetryPolicy HIDPP20_POLICY_PROBE = {
|
||||
"probe"
|
||||
};
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| First-contact policy: probe budget for a device named by |
|
||||
| a receiver's pairing table. A radio leaving power save |
|
||||
| can miss the first frames; worst case ~1.2s. |
|
||||
\*---------------------------------------------------------*/
|
||||
static constexpr HIDPP20RetryPolicy HIDPP20_POLICY_FIRST_CONTACT = {
|
||||
HIDPP20_BACKOFF_FIRST_CONTACT,
|
||||
sizeof(HIDPP20_BACKOFF_FIRST_CONTACT) / sizeof(uint16_t),
|
||||
300, // read window
|
||||
true, // flush_before
|
||||
true, // retry_on_busy
|
||||
"first-contact"
|
||||
};
|
||||
|
||||
/*---------------------------------------------------------*\
|
||||
| Rolling resync. The per-key stream is a delta and takes |
|
||||
| an ACK as proof of paint, so a write the device answers |
|
||||
|
||||
Reference in New Issue
Block a user