blob: ac2ba42e48a3e4c574ee13ec2e3e4d44d3f0693a [file] [log] [blame]
// Copyright 2020 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef SRC_CONNECTIVITY_BLUETOOTH_CORE_BT_HOST_TESTING_FAKE_SIGNALING_SERVER_H_
#define SRC_CONNECTIVITY_BLUETOOTH_CORE_BT_HOST_TESTING_FAKE_SIGNALING_SERVER_H_
#include "fake_dynamic_channel.h"
#include "fake_l2cap.h"
#include "src/connectivity/bluetooth/core/bt-host/common/byte_buffer.h"
#include "src/connectivity/bluetooth/core/bt-host/common/packet_view.h"
#include "src/connectivity/bluetooth/core/bt-host/hci-spec/protocol.h"
#include "src/connectivity/bluetooth/core/bt-host/l2cap/l2cap_defs.h"
namespace bt::testing {
// This class unpacks signaling packets (generally received over a FakeL2cap
// link). Each FakePeer should own its own FakeSignalingServer.
class FakeSignalingServer final {
public:
FakeSignalingServer() = default;
// Registers this FakeSignalingServer's HandleSdu function with |l2cap_| on
// kSignalingChannelId such that all packets processed by |l2cap_| with the
// ChannelId kSignalingChanneld will be processed by this server.
// FakeL2cap will also handle actually sending packets generated by this
// FakeSignalingServer instance.
void RegisterWithL2cap(FakeL2cap* l2cap_);
// Handles the service data unit |sdu| received over link with handle |conn|
// by confirming that the received packet is valid and then calling
// ProcessSignalingPacket.
void HandleSdu(hci::ConnectionHandle conn, const ByteBuffer& sdu);
// Parses the InformationRequest signaling packet |info_req| and then
// calls the appropriate function to construct and send a response packet
// over handle |conn| and ID |id|.
void ProcessInformationRequest(hci::ConnectionHandle conn, l2cap::CommandId id,
const ByteBuffer& info_req);
// Handle incoming ConnectionRequest |connection_req| by validating the
// request, creating a FakeDynamicChannel object, and registering that
// channel with the associated FakeL2cap module. Also will use the server's
// SendFrameCallback to send a ConnectionResponse and ConfigurationRequest
// over handle |conn| and ID |id|.
void ProcessConnectionRequest(hci::ConnectionHandle conn, l2cap::CommandId id,
const ByteBuffer& connection_req);
// Handle incoming ConfigurationRequest |configuration_req|. Note that
// because the all channels here are basic mode, this is simply part of the
// connection process and does not actually configure specific parameters
// of the associated FakeDynamicChannel aside from enabling data transfer
// when both sides send and receive connection requests.
// The emulator assumes that the ProcessConnectionRequest function handles
// sending the initial ConfigurationRequest from FakePeer, so if the emulator
// received a ConfigurationRequest from bt-host, it will assume the
// channel is ready to open.
// FakePeer will still respond with a ConfigurationResponse over handle
// |conn| using the ID |id| and send it using the FakeL2cap instance's
// SendFrameCallback.
void ProcessConfigurationRequest(hci::ConnectionHandle conn, l2cap::CommandId id,
const ByteBuffer& configuration_req);
// Handle configuration responses sent by bt-host. The emulator assumes that the
// ProcessConnectionRequest function handles sending the initial
// ConfigurationRequest from FakePeer, so it disregards this
// ConnfigurationResponse and instead only processes bt-host's inbound
// ConfigurationRequest.
void ProcessConfigurationResponse(hci::ConnectionHandle conn, l2cap::CommandId id,
const ByteBuffer& configuration_res);
// Upon receiving the disconnection request |disconnection_req|, close and
// delete the associated channel from the map associated with fake_l2cap_,
// and then send back a disconnection response with connection handle
// |conn| and ID |id| and send it using the FakeL2cap instance's
// SendFrameCallback..
void ProcessDisconnectionRequest(hci::ConnectionHandle conn, l2cap::CommandId id,
const ByteBuffer& disconnection_req);
// Helper function for sending an individual payload buffer |payload_buffer|
// by assembling a header with CommandCode |code| and CommandId |id| and then
// send it over handle |conn| and with the FakeL2cap instance's
// SendFrameCallback.
void SendCFrame(hci::ConnectionHandle conn, l2cap::CommandCode code, l2cap::CommandId id,
DynamicByteBuffer& payload_buffer);
// Reject a command packet for some |reason|. Assemble a command reject
// packet using the handle |conn| and the CommandId |id| and send with the
// FakeL2cap instance's SendFrameCallback.
void SendCommandReject(hci::ConnectionHandle conn, l2cap::CommandId id,
l2cap::RejectReason reason);
// Respond to a received fixed channels InformationRequest packet with a
// InformationResponse. Assemble the InformationResponse using the handle
// |conn| and id |id|. Send with the FakeL2cap instance's SendFrameCallback.
void SendInformationResponseFixedChannels(hci::ConnectionHandle conn, l2cap::CommandId id);
// Respond to a received extended features InformationRequest packet with a
// InformationResponse. Assemble the InformationResponse using the handle
// |conn| and id |id|. Send with the FakeL2cap instance's SendFrameCallback.
void SendInformationResponseExtendedFeatures(hci::ConnectionHandle conn, l2cap::CommandId id);
// Respond to a received ConnectionRequest packet with a ConnectionResponse.
// Assemble the ConnectionResponse using the handle |conn|, id |id|, local
// channel |local_id|, remote channel |remote_id|, ConnectionResult |result|,
// and ConnectionStatus |status|. Send with the FakeL2cap instance's
// SendFrameCallback.
void SendConnectionResponse(hci::ConnectionHandle conn, l2cap::CommandId id,
l2cap::ChannelId local_cid, l2cap::ChannelId remote_id,
l2cap::ConnectionResult result, l2cap::ConnectionStatus status);
// Send a ConfigurationRequest packet following a ConnectionResponse.
// Assemble the ConfigurationRequest using the handle |conn|, id |id|,
// and remote ID |remote_cid|. Send with the FakeL2cap instance's
// SendFrameCallback.
void SendConfigurationRequest(hci::ConnectionHandle conn, l2cap::CommandId id,
l2cap::ChannelId remote_cid);
// Respond to a received ConfigurationRequest packet with a ConfigurationResposne.
// Assemble the ConfigurationResposne using the handle |conn|, id |id|,
// local ID |local_cid|, and ConfigurationResult |result|. Send with the
/// FakeL2cap instance's SendFrameCallback.
void SendConfigurationResponse(hci::ConnectionHandle conn, l2cap::CommandId id,
l2cap::ChannelId local_cid, l2cap::ConfigurationResult result);
// Respond to a received DisconnectionRequest packet with a DisconnectionResponse.
// Assemble the DisconnectionREsponse using the handle |conn|, id |id|,
// local ID |local_cid|, and remote ID |remote_cid|. Send with the FakeL2cap
// instance's SendFrameCallback.
void SendDisconnectionResponse(hci::ConnectionHandle conn, l2cap::CommandId id,
l2cap::ChannelId local_cid, l2cap::ChannelId remote_cid);
// Return the FakeL2cap instance associated with this FakeSignalingServer.
FakeL2cap* fake_l2cap() { return fake_l2cap_; }
private:
// FakeL2cap instance associated with this server, populated after this
// FakeSignalingServer registers itself with FakeL2cap.
FakeL2cap* fake_l2cap_;
DISALLOW_COPY_AND_ASSIGN_ALLOW_MOVE(FakeSignalingServer);
};
} // namespace bt::testing
#endif // SRC_CONNECTIVITY_BLUETOOTH_CORE_BT_HOST_TESTING_FAKE_SIGNALING_SERVER_H_