using System; using System.Collections.Generic; using System.Net; using System.Text; using Ubiety.Dns.Core.Common; namespace Ubiety.Dns.Core { /// /// DNS Question record /// public class Question { private string _questionName; /// /// Initializes a new instance of the class /// /// Query name /// Question type /// Question class public Question(string questionName, QuestionType questionType, QuestionClass questionClass) { QuestionName = questionName; QuestionType = questionType; QuestionClass = questionClass; } /// /// Initializes a new instance of the class /// /// of the record public Question(RecordReader rr) { QuestionName = rr.ReadDomainName(); QuestionType = (QuestionType)rr.ReadUInt16(); QuestionClass = (QuestionClass)rr.ReadUInt16(); } /// /// Gets the question name /// public String QuestionName { get => _questionName; private set { _questionName = value; if (!_questionName.EndsWith(".", StringComparison.InvariantCulture)) { _questionName += "."; } } } /// /// Gets the query type /// public QuestionType QuestionType { get; } /// /// Gets the query class /// public QuestionClass QuestionClass { get; } /// /// String representation of the question /// /// String of the question public override String ToString() { return $"{QuestionName, -32}\t{QuestionClass}\t{QuestionType}"; } /// /// Gets the question as a byte array /// /// Byte array of the question data public IEnumerable GetData() { var data = new List(); data.AddRange(WriteName(QuestionName)); data.AddRange(WriteShort((UInt16)QuestionType)); data.AddRange(WriteShort((UInt16)QuestionClass)); return data.ToArray(); } private static IEnumerable WriteName(String src) { if (!src.EndsWith(".", StringComparison.InvariantCulture)) { src += "."; } if (src == ".") { return new Byte[1]; } var sb = new StringBuilder(); Int32 intI, intJ, intLen = src.Length; sb.Append('\0'); for (intI = 0, intJ = 0; intI < intLen; intI++, intJ++) { sb.Append(src[intI]); if (src[intI] != '.') { continue; } sb[intI - intJ] = (Char)(intJ & 0xff); intJ = -1; } sb[sb.Length - 1] = '\0'; return Encoding.ASCII.GetBytes(sb.ToString()); } private static Byte[] WriteShort(UInt16 value) { return BitConverter.GetBytes(IPAddress.HostToNetworkOrder((Int16)value)); } } }