Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 7132b71b authored by Ying Hsu's avatar Ying Hsu Committed by Gerrit Code Review
Browse files

Merge "floss: Fix advertising parameters disallow issue"

parents 84692c29 819e1303
Loading
Loading
Loading
Loading
+69 −25
Original line number Diff line number Diff line
@@ -353,38 +353,76 @@ static REG_ID_COUNTER: AtomicIsize = AtomicIsize::new(0);
#[derive(Debug, PartialEq, Copy, Clone)]
pub(crate) struct AdvertisingSetInfo {
    /// Identifies the advertising set when it's started successfully.
    pub(crate) advertiser_id: Option<AdvertiserId>,
    adv_id: Option<AdvertiserId>,

    /// Identifies callback associated.
    callback_id: CallbackId,

    /// Identifies the advertising set when it's registered.
    reg_id: RegId,

    /// Whether the advertising set has been enabled.
    enabled: bool,

    /// Advertising duration, in 10 ms unit.
    adv_timeout: u16,

    /// Maximum number of extended advertising events the controller
    /// shall attempt to send before terminating the extended advertising.
    adv_events: u8,
}

impl AdvertisingSetInfo {
    pub(crate) fn new(callback_id: CallbackId) -> Self {
    pub(crate) fn new(callback_id: CallbackId, adv_timeout: u16, adv_events: u8) -> Self {
        AdvertisingSetInfo {
            advertiser_id: None,
            adv_id: None,
            callback_id,
            reg_id: REG_ID_COUNTER.fetch_add(1, Ordering::SeqCst) as RegId,
            enabled: false,
            adv_timeout,
            adv_events,
        }
    }

    /// Get advertising set registration ID.
    /// Gets advertising set registration ID.
    pub(crate) fn reg_id(&self) -> RegId {
        self.reg_id
    }

    /// Get associated callback ID.
    /// Gets associated callback ID.
    pub(crate) fn callback_id(&self) -> CallbackId {
        self.callback_id
    }

    /// Get adv_id, which is required for advertising |BleAdvertiserInterface|.
    /// Updates advertiser ID.
    pub(crate) fn set_adv_id(&mut self, id: Option<AdvertiserId>) {
        self.adv_id = id;
    }

    /// Gets advertiser ID, which is required for advertising |BleAdvertiserInterface|.
    pub(crate) fn adv_id(&self) -> u8 {
        // As advertiser_id was from topshim originally, type casting is safe.
        self.advertiser_id.unwrap_or(INVALID_ADV_ID) as u8
        // As advertiser ID was from topshim originally, type casting is safe.
        self.adv_id.unwrap_or(INVALID_ADV_ID) as u8
    }

    /// Updates advertising set status.
    pub(crate) fn set_enabled(&mut self, enabled: bool) {
        self.enabled = enabled;
    }

    /// Returns true if the advertising set has been enabled, false otherwise.
    pub(crate) fn is_enabled(&self) -> bool {
        self.enabled
    }

    /// Gets adv_timeout.
    pub(crate) fn adv_timeout(&self) -> u16 {
        self.adv_timeout
    }

    /// Gets adv_events.
    pub(crate) fn adv_events(&self) -> u8 {
        self.adv_events
    }
}

@@ -409,9 +447,9 @@ impl Advertisers {
        }
    }

    fn find_reg_id(&self, advertiser_id: AdvertiserId) -> Option<RegId> {
    fn find_reg_id(&self, adv_id: AdvertiserId) -> Option<RegId> {
        for (_, s) in &self.sets {
            if s.advertiser_id == Some(advertiser_id) {
            if s.adv_id == Some(adv_id) {
                return Some(s.reg_id());
            }
        }
@@ -423,17 +461,25 @@ impl Advertisers {
        self.sets.get_mut(&reg_id)
    }

    /// Returns a reference to the advertising set with the reg_id specified.
    /// Returns a shared reference to the advertising set with the reg_id specified.
    pub(crate) fn get_by_reg_id(&self, reg_id: RegId) -> Option<&AdvertisingSetInfo> {
        self.sets.get(&reg_id)
    }

    /// Returns a reference to the advertising set with the advertiser_id specified.
    pub(crate) fn get_by_advertiser_id(
        &self,
        advertiser_id: AdvertiserId,
    ) -> Option<&AdvertisingSetInfo> {
        if let Some(reg_id) = self.find_reg_id(advertiser_id) {
    /// Returns a mutable reference to the advertising set with the advertiser ID specified.
    pub(crate) fn get_mut_by_advertiser_id(
        &mut self,
        adv_id: AdvertiserId,
    ) -> Option<&mut AdvertisingSetInfo> {
        if let Some(reg_id) = self.find_reg_id(adv_id) {
            return self.get_mut_by_reg_id(reg_id);
        }
        None
    }

    /// Returns a shared reference to the advertising set with the advertiser ID specified.
    pub(crate) fn get_by_advertiser_id(&self, adv_id: AdvertiserId) -> Option<&AdvertisingSetInfo> {
        if let Some(reg_id) = self.find_reg_id(adv_id) {
            return self.get_by_reg_id(reg_id);
        }
        None
@@ -446,14 +492,14 @@ impl Advertisers {
        self.sets.remove(&reg_id)
    }

    /// Removes the advertising set with the specified advertiser_id.
    /// Removes the advertising set with the specified advertiser ID.
    ///
    /// Returns the advertising set if found, None otherwise.
    pub(crate) fn remove_by_advertiser_id(
        &mut self,
        advertiser_id: AdvertiserId,
        adv_id: AdvertiserId,
    ) -> Option<AdvertisingSetInfo> {
        if let Some(reg_id) = self.find_reg_id(advertiser_id) {
        if let Some(reg_id) = self.find_reg_id(adv_id) {
            return self.remove_by_reg_id(reg_id);
        }
        None
@@ -477,10 +523,8 @@ impl Advertisers {

    /// Removes an advertiser callback and unregisters all advertising sets associated with that callback.
    pub(crate) fn remove_callback(&mut self, callback_id: CallbackId, gatt: &mut Gatt) -> bool {
        for (_, s) in self
            .sets
            .iter()
            .filter(|(_, s)| s.callback_id() == callback_id && s.advertiser_id.is_some())
        for (_, s) in
            self.sets.iter().filter(|(_, s)| s.callback_id() == callback_id && s.adv_id.is_some())
        {
            gatt.advertiser.unregister(s.adv_id());
        }
@@ -523,7 +567,7 @@ mod tests {
    fn test_new_advising_set_info() {
        let mut uniq = HashSet::new();
        for callback_id in 0..256 {
            let s = AdvertisingSetInfo::new(callback_id);
            let s = AdvertisingSetInfo::new(callback_id, 0, 0);
            assert_eq!(s.callback_id(), callback_id);
            assert_eq!(uniq.insert(s.reg_id()), true);
        }
+25 −4
Original line number Diff line number Diff line
@@ -1046,7 +1046,7 @@ impl IBluetoothGatt for BluetoothGatt {
        let adv_timeout = clamp(duration, 0, 0xffff) as u16;
        let adv_events = clamp(max_ext_adv_events, 0, 0xff) as u8;

        let s = AdvertisingSetInfo::new(callback_id);
        let s = AdvertisingSetInfo::new(callback_id, adv_timeout, adv_events);
        let reg_id = s.reg_id();
        self.advertisers.add(s);

@@ -1130,7 +1130,24 @@ impl IBluetoothGatt for BluetoothGatt {
        let params = parameters.into();

        if let Some(s) = self.advertisers.get_by_advertiser_id(advertiser_id) {
            let was_enabled = s.is_enabled();
            if was_enabled {
                self.gatt.as_mut().unwrap().advertiser.enable(
                    s.adv_id(),
                    false,
                    s.adv_timeout(),
                    s.adv_events(),
                );
            }
            self.gatt.as_mut().unwrap().advertiser.set_parameters(s.adv_id(), params);
            if was_enabled {
                self.gatt.as_mut().unwrap().advertiser.enable(
                    s.adv_id(),
                    true,
                    s.adv_timeout(),
                    s.adv_events(),
                );
            }
        }
    }

@@ -2412,7 +2429,8 @@ impl BtifGattAdvCallbacks for BluetoothGatt {
        );

        if let Some(s) = self.advertisers.get_mut_by_reg_id(reg_id) {
            s.advertiser_id = Some(advertiser_id.into());
            s.set_adv_id(Some(advertiser_id.into()));
            s.set_enabled(status == GattStatus::Success);
        } else {
            return;
        }
@@ -2438,11 +2456,14 @@ impl BtifGattAdvCallbacks for BluetoothGatt {
        );

        let advertiser_id: i32 = adv_id.into();
        if None == self.advertisers.get_by_advertiser_id(advertiser_id) {

        if let Some(s) = self.advertisers.get_mut_by_advertiser_id(advertiser_id) {
            s.set_enabled(enabled);
        } else {
            return;
        }
        let s = self.advertisers.get_by_advertiser_id(advertiser_id).unwrap().clone();

        let s = self.advertisers.get_by_advertiser_id(advertiser_id).unwrap().clone();
        if let Some(cb) = self.advertisers.get_callback(&s) {
            cb.on_advertising_enabled(advertiser_id, enabled, status);
        }