blob: 683d0600e69102ee03f0da6120f49e45633791f7 [file] [log] [blame]
/*
* Copyright 2019 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include "l2cap/l2cap_packets.h"
#include <gtest/gtest.h>
#include <forward_list>
#include <memory>
#include "os/log.h"
#include "packet/bit_inserter.h"
#include "packet/raw_builder.h"
using bluetooth::packet::BitInserter;
using bluetooth::packet::RawBuilder;
using std::vector;
namespace {
vector<uint8_t> extended_information_start_frame = {
0x0B /* First size byte */,
0x00 /* Second size byte */,
0xc1 /* First ChannelId byte */,
0xc2,
0x4A /* 0x12 ReqSeq, Final, IFrame */,
0xD0 /* 0x13 ReqSeq */,
0x89 /* 0x21 TxSeq sar = START */,
0x8C /* 0x23 TxSeq */,
0x10 /* first length byte */,
0x11,
0x01 /* first payload byte */,
0x02,
0x03,
0x04,
0x05,
};
} // namespace
namespace bluetooth {
namespace l2cap {
TEST(L2capPacketTest, extendedInformationStartFrameTest) {
uint16_t channel_id = 0xc2c1;
uint16_t l2cap_sdu_length = 0x1110;
Final f = Final::POLL_RESPONSE;
uint16_t req_seq = 0x1312;
uint16_t tx_seq = 0x2321;
std::unique_ptr<RawBuilder> payload = std::make_unique<RawBuilder>();
payload->AddOctets4(0x04030201);
payload->AddOctets1(0x05);
auto packet = ExtendedInformationStartFrameBuilder::Create(channel_id, f, req_seq, tx_seq, l2cap_sdu_length,
std::move(payload));
ASSERT_EQ(extended_information_start_frame.size(), packet->size());
std::shared_ptr<std::vector<uint8_t>> packet_bytes = std::make_shared<std::vector<uint8_t>>();
BitInserter it(*packet_bytes);
packet->Serialize(it);
PacketView<true> packet_bytes_view(packet_bytes);
ASSERT_EQ(extended_information_start_frame.size(), packet_bytes_view.size());
BasicFrameView basic_frame_view = BasicFrameView::Create(packet_bytes_view);
ASSERT_TRUE(basic_frame_view.IsValid());
ASSERT_EQ(channel_id, basic_frame_view.GetChannelId());
StandardFrameView standard_frame_view = StandardFrameView::Create(basic_frame_view);
ASSERT_TRUE(standard_frame_view.IsValid());
ASSERT_EQ(FrameType::I_FRAME, standard_frame_view.GetFrameType());
}
vector<uint8_t> i_frame_with_fcs = {
0x0E, 0x00, 0x40, 0x00, 0x02, 0x00, 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x38, 0x61,
};
TEST(L2capPacketTest, iFrameWithFcsTest) {
uint16_t channel_id = 0x0040;
SegmentationAndReassembly sar = SegmentationAndReassembly::UNSEGMENTED; // 0
uint16_t req_seq = 0;
uint16_t tx_seq = 1;
RetransmissionDisable r = RetransmissionDisable::NORMAL; // 0
std::unique_ptr<RawBuilder> payload = std::make_unique<RawBuilder>();
vector<uint8_t> payload_bytes = {0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09};
payload->AddOctets(payload_bytes);
auto packet = StandardInformationFrameWithFcsBuilder::Create(channel_id, tx_seq, r, req_seq, sar, std::move(payload));
ASSERT_EQ(i_frame_with_fcs.size(), packet->size());
std::shared_ptr<std::vector<uint8_t>> packet_bytes = std::make_shared<std::vector<uint8_t>>();
BitInserter it(*packet_bytes);
packet->Serialize(it);
PacketView<true> packet_bytes_view(packet_bytes);
ASSERT_EQ(i_frame_with_fcs.size(), packet_bytes_view.size());
for (size_t i = 0; i < i_frame_with_fcs.size(); i++) {
ASSERT_EQ(i_frame_with_fcs[i], packet_bytes_view[i]);
}
BasicFrameWithFcsView basic_frame_view = BasicFrameWithFcsView::Create(packet_bytes_view);
ASSERT_TRUE(basic_frame_view.IsValid());
ASSERT_EQ(channel_id, basic_frame_view.GetChannelId());
StandardFrameWithFcsView standard_frame_view = StandardFrameWithFcsView::Create(basic_frame_view);
ASSERT_TRUE(standard_frame_view.IsValid());
ASSERT_EQ(FrameType::I_FRAME, standard_frame_view.GetFrameType());
StandardInformationFrameWithFcsView information_frame_view =
StandardInformationFrameWithFcsView::Create(standard_frame_view);
ASSERT_TRUE(information_frame_view.IsValid());
ASSERT_EQ(sar, information_frame_view.GetSar());
ASSERT_EQ(req_seq, information_frame_view.GetReqSeq());
ASSERT_EQ(tx_seq, information_frame_view.GetTxSeq());
ASSERT_EQ(r, information_frame_view.GetR());
}
vector<uint8_t> rr_frame_with_fcs = {
0x04, 0x00, 0x40, 0x00, 0x01, 0x01, 0xD4, 0x14,
};
TEST(L2capPacketTest, rrFrameWithFcsTest) {
uint16_t channel_id = 0x0040;
SupervisoryFunction s = SupervisoryFunction::RECEIVER_READY; // 0
RetransmissionDisable r = RetransmissionDisable::NORMAL; // 0
uint16_t req_seq = 1;
auto packet = StandardSupervisoryFrameWithFcsBuilder::Create(channel_id, s, r, req_seq);
ASSERT_EQ(rr_frame_with_fcs.size(), packet->size());
std::shared_ptr<std::vector<uint8_t>> packet_bytes = std::make_shared<std::vector<uint8_t>>();
BitInserter it(*packet_bytes);
packet->Serialize(it);
PacketView<true> packet_bytes_view(packet_bytes);
ASSERT_EQ(rr_frame_with_fcs.size(), packet_bytes_view.size());
for (size_t i = 0; i < rr_frame_with_fcs.size(); i++) {
ASSERT_EQ(rr_frame_with_fcs[i], packet_bytes_view[i]);
}
BasicFrameWithFcsView basic_frame_view = BasicFrameWithFcsView::Create(packet_bytes_view);
ASSERT_TRUE(basic_frame_view.IsValid());
ASSERT_EQ(channel_id, basic_frame_view.GetChannelId());
StandardFrameWithFcsView standard_frame_view = StandardFrameWithFcsView::Create(basic_frame_view);
ASSERT_TRUE(standard_frame_view.IsValid());
ASSERT_EQ(FrameType::S_FRAME, standard_frame_view.GetFrameType());
StandardSupervisoryFrameWithFcsView supervisory_frame_view =
StandardSupervisoryFrameWithFcsView::Create(standard_frame_view);
ASSERT_TRUE(supervisory_frame_view.IsValid());
ASSERT_EQ(s, supervisory_frame_view.GetS());
ASSERT_EQ(r, supervisory_frame_view.GetR());
ASSERT_EQ(req_seq, supervisory_frame_view.GetReqSeq());
}
} // namespace l2cap
} // namespace bluetooth