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

Commit 9a70eff1 authored by Myles Watson's avatar Myles Watson Committed by android-build-merger
Browse files

RootCanal: Support LE 4.1 advertising am: f50a72c8

am: 5a493eb3

Change-Id: Ie450fe0b5a48d493f0f90345f75ef757fc477a85
parents fa5cbeaa 5a493eb3
Loading
Loading
Loading
Loading
+1 −1
Original line number Diff line number Diff line
@@ -193,7 +193,7 @@ enum class OpCode : uint16_t {
  LE_SET_ADVERTISING_PARAMETERS = LE_CONTROLLER | 0x0006,
  LE_READ_ADVERTISING_CHANNEL_TX_POWER = LE_CONTROLLER | 0x0007,
  LE_SET_ADVERTISING_DATA = LE_CONTROLLER | 0x0008,
  LE_SET_SCAN_RSPONSE_DATA = LE_CONTROLLER | 0x0009,
  LE_SET_SCAN_RESPONSE_DATA = LE_CONTROLLER | 0x0009,
  LE_SET_ADVERTISING_ENABLE = LE_CONTROLLER | 0x000A,
  LE_SET_SCAN_PARAMETERS = LE_CONTROLLER | 0x000B,
  LE_SET_SCAN_ENABLE = LE_CONTROLLER | 0x000C,
+27 −3
Original line number Diff line number Diff line
@@ -198,8 +198,10 @@ DualModeController::DualModeController(const std::string& properties_filename, u
  SET_HANDLER(OpCode::LE_READ_BUFFER_SIZE, HciLeReadBufferSize);
  SET_HANDLER(OpCode::LE_READ_LOCAL_SUPPORTED_FEATURES, HciLeReadLocalSupportedFeatures);
  SET_HANDLER(OpCode::LE_SET_RANDOM_ADDRESS, HciLeSetRandomAddress);
  SET_HANDLER(OpCode::LE_SET_ADVERTISING_DATA, HciLeSetAdvertisingData);
  SET_HANDLER(OpCode::LE_SET_ADVERTISING_PARAMETERS, HciLeSetAdvertisingParameters);
  SET_HANDLER(OpCode::LE_SET_ADVERTISING_DATA, HciLeSetAdvertisingData);
  SET_HANDLER(OpCode::LE_SET_SCAN_RESPONSE_DATA, HciLeSetScanResponseData);
  SET_HANDLER(OpCode::LE_SET_ADVERTISING_ENABLE, HciLeSetAdvertisingEnable);
  SET_HANDLER(OpCode::LE_SET_SCAN_PARAMETERS, HciLeSetScanParameters);
  SET_HANDLER(OpCode::LE_SET_SCAN_ENABLE, HciLeSetScanEnable);
  SET_HANDLER(OpCode::LE_CREATE_CONNECTION, HciLeCreateConnection);
@@ -287,7 +289,8 @@ void DualModeController::HandleCommand(std::shared_ptr<std::vector<uint8_t>> pac
    active_hci_commands_[opcode](command_packet.GetPayload());
  } else {
    SendCommandCompleteUnknownOpCodeEvent(opcode);
    LOG_INFO(LOG_TAG, "Command opcode: 0x%04X, OGF: 0x%04X, OCF: 0x%04X", opcode, opcode & 0xFC00, opcode & 0x03FF);
    LOG_INFO(LOG_TAG, "Command opcode: 0x%04X, OGF: 0x%04X, OCF: 0x%04X", opcode, (opcode & 0xFC00) >> 10,
             opcode & 0x03FF);
  }
}

@@ -817,15 +820,36 @@ void DualModeController::HciLeSetRandomAddress(packets::PacketView<true> args) {

void DualModeController::HciLeSetAdvertisingParameters(packets::PacketView<true> args) {
  CHECK(args.size() == 15) << __func__ << " size=" << args.size();
  auto args_itr = args.begin();
  properties_.SetLeAdvertisingParameters(
      args_itr.extract<uint16_t>() /* AdverisingIntervalMin */,
      args_itr.extract<uint16_t>() /* AdverisingIntervalMax */, args_itr.extract<uint8_t>() /* AdverisingType */,
      args_itr.extract<uint8_t>() /* OwnAddressType */, args_itr.extract<uint8_t>() /* PeerAddressType */,
      args_itr.extract<Address>() /* PeerAddress */, args_itr.extract<uint8_t>() /* AdvertisingChannelMap */,
      args_itr.extract<uint8_t>() /* AdvertisingFilterPolicy */
  );

  SendCommandCompleteSuccess(OpCode::LE_SET_ADVERTISING_PARAMETERS);
}

void DualModeController::HciLeSetAdvertisingData(packets::PacketView<true> args) {
  CHECK(args.size() > 0);
  CHECK(args.size() == 32) << __func__ << " size=" << args.size();
  properties_.SetLeAdvertisement(std::vector<uint8_t>(args.begin() + 1, args.end()));
  SendCommandCompleteSuccess(OpCode::LE_SET_ADVERTISING_DATA);
}

void DualModeController::HciLeSetScanResponseData(packets::PacketView<true> args) {
  CHECK(args.size() == 32) << __func__ << " size=" << args.size();
  properties_.SetLeScanResponse(std::vector<uint8_t>(args.begin() + 1, args.end()));
  SendCommandCompleteSuccess(OpCode::LE_SET_SCAN_RESPONSE_DATA);
}

void DualModeController::HciLeSetAdvertisingEnable(packets::PacketView<true> args) {
  CHECK(args.size() == 1) << __func__ << " size=" << args.size();
  hci::Status status = link_layer_controller_.SetLeAdvertisingEnable(args.begin().extract<uint8_t>());
  SendCommandCompleteOnlyStatus(OpCode::LE_SET_ADVERTISING_ENABLE, status);
}

void DualModeController::HciLeSetScanParameters(packets::PacketView<true> args) {
  CHECK(args.size() == 7) << __func__ << " size=" << args.size();
  link_layer_controller_.SetLeScanType(args[0]);
+6 −0
Original line number Diff line number Diff line
@@ -307,6 +307,12 @@ class DualModeController : public Device {
  // 7.8.7
  void HciLeSetAdvertisingData(packets::PacketView<true> args);

  // 7.8.8
  void HciLeSetScanResponseData(packets::PacketView<true> args);

  // 7.8.9
  void HciLeSetAdvertisingEnable(packets::PacketView<true> args);

  // 7.8.10
  void HciLeSetScanParameters(packets::PacketView<true> args);

+34 −3
Original line number Diff line number Diff line
@@ -55,7 +55,7 @@ static uint8_t GetRssi() {
  return -(rssi);
}

void LinkLayerController::SendLELinkLayerPacket(std::shared_ptr<LinkLayerPacketBuilder> packet) {
void LinkLayerController::SendLeLinkLayerPacket(std::shared_ptr<LinkLayerPacketBuilder> packet) {
  if (schedule_task_) {
    schedule_task_(milliseconds(50), [this, packet]() { send_to_remote_(packet, Phy::Type::LOW_ENERGY); });
  } else {
@@ -523,7 +523,7 @@ void LinkLayerController::IncomingLeAdvertisementPacket(LinkLayerPacketView inco
  if (le_scan_enable_ && le_scan_type_ == 1) {
    std::shared_ptr<LinkLayerPacketBuilder> to_send =
        LinkLayerPacketBuilder::WrapLeScan(properties_.GetLeAddress(), incoming.GetSourceAddress());
    SendLELinkLayerPacket(to_send);
    SendLeLinkLayerPacket(to_send);
  }
}

@@ -535,7 +535,7 @@ void LinkLayerController::IncomingLeScanPacket(LinkLayerPacketView incoming) {
      properties_.GetLeScanResponse());
  std::shared_ptr<LinkLayerPacketBuilder> to_send = LinkLayerPacketBuilder::WrapLeScanResponse(
      std::move(response), properties_.GetLeAddress(), incoming.GetSourceAddress());
  SendLELinkLayerPacket(to_send);
  SendLeLinkLayerPacket(to_send);
}

void LinkLayerController::IncomingLeScanResponsePacket(LinkLayerPacketView incoming) {
@@ -649,9 +649,40 @@ void LinkLayerController::IncomingResponsePacket(LinkLayerPacketView incoming) {
void LinkLayerController::TimerTick() {
  if (inquiry_state_ == Inquiry::InquiryState::INQUIRY) Inquiry();
  if (inquiry_state_ == Inquiry::InquiryState::INQUIRY) PageScan();
  LeAdvertising();
  Connections();
}

void LinkLayerController::LeAdvertising() {
  if (!le_advertising_enable_) {
    return;
  }
  steady_clock::time_point now = steady_clock::now();
  if (duration_cast<milliseconds>(now - last_le_advertisement_) < milliseconds(200)) {
    return;
  }

  LeAdvertisement::AddressType own_address_type =
      static_cast<LeAdvertisement::AddressType>(properties_.GetLeAdvertisingOwnAddressType());
  std::shared_ptr<packets::LinkLayerPacketBuilder> to_send;
  std::unique_ptr<packets::LeAdvertisementBuilder> ad;
  if (own_address_type == LeAdvertisement::AddressType::PUBLIC) {
    ad = packets::LeAdvertisementBuilder::Create(
        LeAdvertisement::AddressType::PUBLIC,
        static_cast<LeAdvertisement::AdvertisementType>(properties_.GetLeAdvertisementType()),
        properties_.GetLeAdvertisement());
    to_send = packets::LinkLayerPacketBuilder::WrapLeAdvertisement(std::move(ad), properties_.GetAddress());
  } else if (own_address_type == LeAdvertisement::AddressType::RANDOM) {
    ad = packets::LeAdvertisementBuilder::Create(
        LeAdvertisement::AddressType::RANDOM,
        static_cast<LeAdvertisement::AdvertisementType>(properties_.GetLeAdvertisementType()),
        properties_.GetLeAdvertisement());
    to_send = packets::LinkLayerPacketBuilder::WrapLeAdvertisement(std::move(ad), properties_.GetLeAddress());
  }
  CHECK(to_send != nullptr);
  SendLeLinkLayerPacket(to_send);
}

void LinkLayerController::Connections() {
  // TODO: Keep connections alive?
}
+13 −2
Original line number Diff line number Diff line
@@ -104,12 +104,20 @@ class LinkLayerController {
  void PageScan();
  void Connections();

  void LeAdvertising();

  void LeWhiteListClear();
  void LeWhiteListAddDevice(Address addr, uint8_t addr_type);
  void LeWhiteListRemoveDevice(Address addr, uint8_t addr_type);
  bool LeWhiteListContainsDevice(Address addr, uint8_t addr_type);
  bool LeWhiteListFull();

  hci::Status SetLeAdvertisingEnable(uint8_t le_advertising_enable) {
    le_advertising_enable_ = le_advertising_enable;
    // TODO: Check properties and return errors
    return hci::Status::SUCCESS;
  }

  void SetLeScanEnable(uint8_t le_scan_enable) {
    le_scan_enable_ = le_scan_enable;
  }
@@ -180,7 +188,7 @@ class LinkLayerController {
  hci::Status WriteLinkSupervisionTimeout(uint16_t handle, uint16_t timeout);

 protected:
  void SendLELinkLayerPacket(std::shared_ptr<packets::LinkLayerPacketBuilder> packet);
  void SendLeLinkLayerPacket(std::shared_ptr<packets::LinkLayerPacketBuilder> packet);
  void SendLinkLayerPacket(std::shared_ptr<packets::LinkLayerPacketBuilder> packet);
  void IncomingAclPacket(packets::LinkLayerPacketView packet);
  void IncomingAclAckPacket(packets::LinkLayerPacketView packet);
@@ -232,7 +240,10 @@ class LinkLayerController {

  std::vector<std::tuple<Address, uint8_t>> le_white_list_;

  uint8_t le_scan_enable_;
  uint8_t le_advertising_enable_{false};
  std::chrono::steady_clock::time_point last_le_advertisement_;

  uint8_t le_scan_enable_{false};
  uint8_t le_scan_type_;
  uint16_t le_scan_interval_;
  uint16_t le_scan_window_;
Loading