1*3f982cf4SFabien Sanglard // Copyright 2019 The Chromium Authors. All rights reserved. 2*3f982cf4SFabien Sanglard // Use of this source code is governed by a BSD-style license that can be 3*3f982cf4SFabien Sanglard // found in the LICENSE file. 4*3f982cf4SFabien Sanglard 5*3f982cf4SFabien Sanglard #ifndef DISCOVERY_MDNS_MDNS_READER_H_ 6*3f982cf4SFabien Sanglard #define DISCOVERY_MDNS_MDNS_READER_H_ 7*3f982cf4SFabien Sanglard 8*3f982cf4SFabien Sanglard #include <utility> 9*3f982cf4SFabien Sanglard #include <vector> 10*3f982cf4SFabien Sanglard 11*3f982cf4SFabien Sanglard #include "discovery/mdns/mdns_records.h" 12*3f982cf4SFabien Sanglard #include "platform/base/error.h" 13*3f982cf4SFabien Sanglard #include "util/big_endian.h" 14*3f982cf4SFabien Sanglard 15*3f982cf4SFabien Sanglard namespace openscreen { 16*3f982cf4SFabien Sanglard namespace discovery { 17*3f982cf4SFabien Sanglard 18*3f982cf4SFabien Sanglard struct Config; 19*3f982cf4SFabien Sanglard 20*3f982cf4SFabien Sanglard class MdnsReader : public BigEndianReader { 21*3f982cf4SFabien Sanglard public: 22*3f982cf4SFabien Sanglard MdnsReader(const Config& config, const uint8_t* buffer, size_t length); 23*3f982cf4SFabien Sanglard 24*3f982cf4SFabien Sanglard using BigEndianReader::Read; 25*3f982cf4SFabien Sanglard 26*3f982cf4SFabien Sanglard // The following methods return true if the method was able to successfully 27*3f982cf4SFabien Sanglard // read the value to |out| and advances current() to point right past the read 28*3f982cf4SFabien Sanglard // data. Returns false if the method failed to read the value to |out|, 29*3f982cf4SFabien Sanglard // current() remains unchanged. 30*3f982cf4SFabien Sanglard bool Read(TxtRecordRdata::Entry* out); 31*3f982cf4SFabien Sanglard bool Read(DomainName* out); 32*3f982cf4SFabien Sanglard bool Read(RawRecordRdata* out); 33*3f982cf4SFabien Sanglard bool Read(SrvRecordRdata* out); 34*3f982cf4SFabien Sanglard bool Read(ARecordRdata* out); 35*3f982cf4SFabien Sanglard bool Read(AAAARecordRdata* out); 36*3f982cf4SFabien Sanglard bool Read(PtrRecordRdata* out); 37*3f982cf4SFabien Sanglard bool Read(TxtRecordRdata* out); 38*3f982cf4SFabien Sanglard bool Read(NsecRecordRdata* out); 39*3f982cf4SFabien Sanglard 40*3f982cf4SFabien Sanglard // Reads a DNS resource record with its RDATA. 41*3f982cf4SFabien Sanglard // The correct type of RDATA to be read is determined by the type 42*3f982cf4SFabien Sanglard // specified in the record. 43*3f982cf4SFabien Sanglard bool Read(MdnsRecord* out); 44*3f982cf4SFabien Sanglard bool Read(MdnsQuestion* out); 45*3f982cf4SFabien Sanglard 46*3f982cf4SFabien Sanglard // Reads multiple mDNS questions and records that are a part of 47*3f982cf4SFabien Sanglard // a mDNS message being read. 48*3f982cf4SFabien Sanglard ErrorOr<MdnsMessage> Read(); 49*3f982cf4SFabien Sanglard 50*3f982cf4SFabien Sanglard private: 51*3f982cf4SFabien Sanglard struct NsecBitMapField { 52*3f982cf4SFabien Sanglard uint8_t window_block; 53*3f982cf4SFabien Sanglard uint8_t bitmap_length; 54*3f982cf4SFabien Sanglard const uint8_t* bitmap; 55*3f982cf4SFabien Sanglard }; 56*3f982cf4SFabien Sanglard 57*3f982cf4SFabien Sanglard bool Read(IPAddress::Version version, IPAddress* out); 58*3f982cf4SFabien Sanglard bool Read(DnsType type, Rdata* out); 59*3f982cf4SFabien Sanglard bool Read(Header* out); 60*3f982cf4SFabien Sanglard bool Read(std::vector<DnsType>* types, int remaining_length); 61*3f982cf4SFabien Sanglard bool Read(NsecBitMapField* out); 62*3f982cf4SFabien Sanglard 63*3f982cf4SFabien Sanglard template <class ItemType> Read(uint16_t count,std::vector<ItemType> * out)64*3f982cf4SFabien Sanglard bool Read(uint16_t count, std::vector<ItemType>* out) { 65*3f982cf4SFabien Sanglard Cursor cursor(this); 66*3f982cf4SFabien Sanglard out->reserve(count); 67*3f982cf4SFabien Sanglard for (uint16_t i = 0; i < count; ++i) { 68*3f982cf4SFabien Sanglard ItemType entry; 69*3f982cf4SFabien Sanglard if (!Read(&entry)) { 70*3f982cf4SFabien Sanglard return false; 71*3f982cf4SFabien Sanglard } 72*3f982cf4SFabien Sanglard out->emplace_back(std::move(entry)); 73*3f982cf4SFabien Sanglard } 74*3f982cf4SFabien Sanglard cursor.Commit(); 75*3f982cf4SFabien Sanglard return true; 76*3f982cf4SFabien Sanglard } 77*3f982cf4SFabien Sanglard 78*3f982cf4SFabien Sanglard template <class RdataType> Read(Rdata * out)79*3f982cf4SFabien Sanglard bool Read(Rdata* out) { 80*3f982cf4SFabien Sanglard RdataType rdata; 81*3f982cf4SFabien Sanglard if (Read(&rdata)) { 82*3f982cf4SFabien Sanglard *out = std::move(rdata); 83*3f982cf4SFabien Sanglard return true; 84*3f982cf4SFabien Sanglard } 85*3f982cf4SFabien Sanglard return false; 86*3f982cf4SFabien Sanglard } 87*3f982cf4SFabien Sanglard 88*3f982cf4SFabien Sanglard // Maximum allowed size for the rdata in any received record. 89*3f982cf4SFabien Sanglard const size_t kMaximumAllowedRdataSize; 90*3f982cf4SFabien Sanglard }; 91*3f982cf4SFabien Sanglard 92*3f982cf4SFabien Sanglard } // namespace discovery 93*3f982cf4SFabien Sanglard } // namespace openscreen 94*3f982cf4SFabien Sanglard 95*3f982cf4SFabien Sanglard #endif // DISCOVERY_MDNS_MDNS_READER_H_ 96