Skip to content

Fix IRK-only mode to prevent heuristic fallback + auto battery optimization - #310

Merged
d4rken merged 4 commits into
d4rken-org:mainfrom
wnerhs:fix-irk-heuristic-fallback
Jun 30, 2025
Merged

Fix IRK-only mode to prevent heuristic fallback + auto battery optimization#310
d4rken merged 4 commits into
d4rken-org:mainfrom
wnerhs:fix-irk-heuristic-fallback

Conversation

@wnerhs

@wnerhs wnerhs commented Jun 30, 2025

Copy link
Copy Markdown
Contributor

Problem

When IRK/ENC keys are configured, the app still falls back to heuristic detection when no IRK match is found. This causes false positives where other people's AirPods are identified as "my device" in crowded places like subway stations.

Solution

  • Added state tracking for last IRK-matched device (lastIrkMatchedDevice)
  • When IRK keys are configured but no current match found, maintain last known IRK device instead of falling back to heuristic detection
  • Bonus: Automatic battery optimization - switches to LOW_POWER scan mode when IRK device is connected

Changes

  • Added lastIrkMatchedDevice variable to track IRK-matched state
  • Modified determineMainDevice() to prevent heuristic fallback when IRK keys are configured
  • Added automatic LOW_POWER scan mode when IRK device is found
  • Maintains backward compatibility for users without IRK keys

Benefits

  • ✅ Eliminates false positives in crowded places
  • ✅ Automatic battery saving when IRK device is connected
  • ✅ No configuration needed - works automatically
  • ✅ Minimal code changes with maximum impact

This addresses the issue discussed in the GitHub issue where IRK-only mode was requested.

Testing

  • Tested with IRK keys configured
  • Tested without IRK keys (backward compatibility)
  • No build errors
  • Battery optimization verified

Closes #309

…zation

- Prevent heuristic device detection when IRK/ENC keys are configured
- Maintain last IRK-matched device state instead of fallback
- Auto-enable LOW_POWER scan mode when IRK device is found
- Fixes false positives in crowded places
@d4rken

d4rken commented Jun 30, 2025

Copy link
Copy Markdown
Member

Thanks for the PR

@d4rken d4rken left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think the solution can be very minimalistic, we maybe just need something like:

if(identityKey != null && irkHit == null) {
    log(...)....
    return null
}

What do you think?

BTW: Not an issue, just curious, did you generate this with an AI tool? Copilot?

Comment thread app-common/src/main/java/eu/darken/capod/monitor/core/PodMonitor.kt Outdated
Comment thread app-common/src/main/java/eu/darken/capod/monitor/core/PodMonitor.kt Outdated
Comment thread app-common/src/main/java/eu/darken/capod/monitor/core/PodMonitor.kt Outdated
@d4rken
d4rken requested a review from Copilot June 30, 2025 09:36

This comment was marked as outdated.

@wnerhs
wnerhs requested a review from d4rken June 30, 2025 10:31
d4rken added 2 commits June 30, 2025 12:42
This commit modifies `PodMonitor.kt` to ensure that the `isIRKMatch` flag is only used to determine the main device if an Identity Resolving Key (IRK) is actually configured in the general settings.

If no IRK is set, the main device determination will fall back to other logic, preventing a device from being incorrectly selected as "main" solely based on an IRK match when no specific IRK is being looked for.
d4rken
d4rken previously approved these changes Jun 30, 2025

@d4rken d4rken left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd still like to merge this PR, have you show in the contributors list 👍

So my idea was a simple check like this. If an IRK is configured, only an IRK match will be returned, if there is none then no main device.

What do you think?

@wnerhs

wnerhs commented Jun 30, 2025

Copy link
Copy Markdown
Contributor Author

Thank you so much!

Your approach is much better than mine - I overcomplicated it because I'm still learning. Really appreciate you cleaning it up properly!

Excited to be in the contributors list!

This commit modifies the handling of Identity Resolving Key (IRK) and Encryption Key (EncKey) to allow users to clear these values by providing an empty input.

Specifically:
- In `GeneralSettingsFragment.kt`, the `onKey` callbacks for both IRK and EncKey dialogs now use `takeIf { it.isNotEmpty() }` after converting the input hex string to a byte array. This ensures that an empty input results in `null` being set for the respective key.
- In `PodMonitor.kt`, when determining the main device, `mainDeviceIdentityKey.value` is now checked with `takeIf { it.isNotEmpty() }` to ensure an empty IRK is treated as no IRK being configured.
- In `AppleFactory.kt`, when attempting to decrypt the private payload, `mainDeviceEncryptionKey.value` is now checked with `takeIf { it.isNotEmpty() }` to ensure an empty EncKey prevents decryption attempts.
@d4rken
d4rken merged commit 977f135 into d4rken-org:main Jun 30, 2025
@wnerhs
wnerhs deleted the fix-irk-heuristic-fallback branch June 30, 2025 13:46
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Feature Request] IRK/ENC key filtering for device detection

3 participants