1149 lines
No EOL
99 KiB
HTML
1149 lines
No EOL
99 KiB
HTML
|
||
<!DOCTYPE html>
|
||
|
||
|
||
|
||
|
||
<html lang="en">
|
||
<head>
|
||
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||
|
||
<title>4.6. UDP Socket Programming: DNS — Computer Systems Fundamentals</title>
|
||
|
||
<link rel="stylesheet" href="_static/css/bootstrap.min.css" integrity="sha384-ggOyR0iXCbMQv3Xipma34MD+dH/1fQ784/j6cY/iJTQUOhcWr7x9JvoRxT2MZw1T" crossorigin="anonymous" />
|
||
<link rel="stylesheet" href="_static/css/pygments.css" type="text/css" />
|
||
<link rel="stylesheet" href="_static/css/normalize.css" type="text/css" />
|
||
<link rel="stylesheet" href="../../../JSAV/css/JSAV.css" type="text/css" />
|
||
<link rel="stylesheet" href="../../../lib/odsaMOD-min.css" type="text/css" />
|
||
<link rel="stylesheet" href="_static/css/jquery-1.11.4-smoothness-ui.css" type="text/css" />
|
||
<link rel="stylesheet" href="../../../lib/odsaStyle-min.css" type="text/css" />
|
||
<link rel="stylesheet" href="_static/css/csf.css" type="text/css" />
|
||
|
||
<style>
|
||
.underline { text-decoration: underline; }
|
||
</style>
|
||
|
||
<script type="text/javascript">
|
||
var DOCUMENTATION_OPTIONS = {
|
||
URL_ROOT: './',
|
||
VERSION: '0.4.1',
|
||
COLLAPSE_INDEX: false,
|
||
FILE_SUFFIX: '.html',
|
||
HAS_SOURCE: true
|
||
};
|
||
</script>
|
||
|
||
<script type="text/x-mathjax-config">
|
||
MathJax.Hub.Config({
|
||
tex2jax: {
|
||
inlineMath: [['$','$'], ['\\(','\\)']],
|
||
displayMath: [ ['$$','$$'], ["\\[","\\]"] ],
|
||
processEscapes: true
|
||
},
|
||
"HTML-CSS": {
|
||
scale: "80"
|
||
}
|
||
});
|
||
</script>
|
||
<link rel="shortcut icon" href="_static/favicon.ico"/>
|
||
<link rel="index" title="Index" href="genindex.html" />
|
||
<link rel="search" title="Search" href="search.html" />
|
||
<link rel="index" title="Computer Systems Fundamentals" href="index.html" />
|
||
<link rel="next" title="7. Application-Layer Broadcasting: DHCP" href="AppBroadcast.html" />
|
||
<link rel="prev" title="5. TCP Socket Programming: HTTP" href="TCPSockets.html" />
|
||
|
||
</head><body>
|
||
|
||
<nav class="navbar navbar-expand-md navbar-dark navbar-custom fixed-top">
|
||
|
||
<a class="navbar-brand py-0" href="index.html"><img src="_static/CSF-Logo-Square-Text.png" alt="OpenCSF Logo" height="40em" class="py-1 px-2 mb-0 align-center rounded-lg bg-white" /></a>
|
||
<!-- Show a navbar toggler on mobile -->
|
||
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#defaultNavbars" aria-controls="defaultNavbars" aria-expanded="false" aria-label="Toggle navigation">
|
||
<span class="navbar-toggler-icon"></span>
|
||
</button>
|
||
<div class="collapse navbar-collapse" id="defaultNavbars">
|
||
<ul class="navbar-nav mr-auto">
|
||
<li class="nav-item dropdown">
|
||
<a class="nav-link dropdown-toggle jmu-gold rounded" href="UDPSockets.html#" id="navbarDropdownChapters" role="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">Contents</a>
|
||
<div class="dropdown-menu scrollable-menu" role="menu" aria-labelledby="navbarDropdownChapters">
|
||
<a class="dropdown-item" tabindex="-1" href="UDPSockets.html#"><b>Chapter 1</b></a>
|
||
<a class="dropdown-item" href="IntroConcSysOverview.html"> 1.1. Introduction to Concurrent Systems</a>
|
||
<a class="dropdown-item" href="SysAndModels.html"> 1.2. Systems and Models</a>
|
||
<a class="dropdown-item" href="Themes.html"> 1.3. Themes and Guiding Principles</a>
|
||
<a class="dropdown-item" href="Architectures.html"> 1.4. System Architectures</a>
|
||
<a class="dropdown-item" href="StateModels.html"> 1.5. State Models in UML</a>
|
||
<a class="dropdown-item" href="SequenceModels.html"> 1.6. Sequence Models in UML</a>
|
||
<a class="dropdown-item" href="StateModelImplementation.html"> 1.7. Extended Example: State Model Implementation</a>
|
||
<div class="dropdown-divider"></div>
|
||
<a class="dropdown-item disabled"><b>Chapter 2</b></a>
|
||
<a class="dropdown-item" href="ProcessesOverview.html"> 2.1. Processes and OS Basics</a>
|
||
<a class="dropdown-item" href="Multiprogramming.html"> 2.2. Processes and Multiprogramming</a>
|
||
<a class="dropdown-item" href="KernelMechanics.html"> 2.3. Kernel Mechanics</a>
|
||
<a class="dropdown-item" href="Syscall.html"> 2.4. System Call Interface</a>
|
||
<a class="dropdown-item" href="ProcessCycle.html"> 2.5. Process Life Cycle</a>
|
||
<a class="dropdown-item" href="UnixFile.html"> 2.6. The UNIX File Abstraction</a>
|
||
<a class="dropdown-item" href="EventsSignals.html"> 2.7. Events and Signals</a>
|
||
<a class="dropdown-item" href="Extended2Processes.html"> 2.8. Extended Example: Listing Files with Processes</a>
|
||
<div class="dropdown-divider"></div>
|
||
<a class="dropdown-item disabled"><b>Chapter 3</b></a>
|
||
<a class="dropdown-item" href="IPCOverview.html"> 3.1. Concurrency with IPC</a>
|
||
<a class="dropdown-item" href="IPCModels.html"> 3.2. IPC Models</a>
|
||
<a class="dropdown-item" href="Pipes.html"> 3.3. Pipes and FIFOs</a>
|
||
<a class="dropdown-item" href="MMap.html"> 3.4. Shared Memory With Memory-mapped Files</a>
|
||
<a class="dropdown-item" href="POSIXvSysV.html"> 3.5. POSIX vs. System V IPC</a>
|
||
<a class="dropdown-item" href="MQueues.html"> 3.6. Message Passing With Message Queues</a>
|
||
<a class="dropdown-item" href="ShMem.html"> 3.7. Shared Memory</a>
|
||
<a class="dropdown-item" href="IPCSems.html"> 3.8. Semaphores</a>
|
||
<a class="dropdown-item" href="Extended3Bash.html"> 3.9. Extended Example: Bash-lite: A Simple Command-line Shell</a>
|
||
<div class="dropdown-divider"></div>
|
||
<a class="dropdown-item disabled"><b>Chapter 4</b></a>
|
||
<a class="dropdown-item" href="SocketsOverview.html"> 4.1. Networked Concurrency</a>
|
||
<a class="dropdown-item" href="FiveLayer.html"> 4.2. The TCP/IP Internet Model</a>
|
||
<a class="dropdown-item" href="NetApps.html"> 4.3. Network Applications and Protocols</a>
|
||
<a class="dropdown-item" href="Sockets.html"> 4.4. The Socket Interface</a>
|
||
<a class="dropdown-item" href="TCPSockets.html"> 4.5. TCP Socket Programming: HTTP</a>
|
||
<a class="dropdown-item" href="UDPSockets.html"> 4.6. UDP Socket Programming: DNS</a>
|
||
<a class="dropdown-item" href="AppBroadcast.html"> 4.7. Application-Layer Broadcasting: DHCP</a>
|
||
<a class="dropdown-item" href="Extended4CGI.html"> 4.8. Extended Example: CGI Web Server</a>
|
||
<div class="dropdown-divider"></div>
|
||
<a class="dropdown-item disabled"><b>Chapter 5</b></a>
|
||
<a class="dropdown-item" href="InternetOverview.html"> 5.1. The Internet and Connectivity</a>
|
||
<a class="dropdown-item" href="AppLayer.html"> 5.2. Application Layer: Overlay Networks</a>
|
||
<a class="dropdown-item" href="TransLayer.html"> 5.3. Transport Layer</a>
|
||
<a class="dropdown-item" href="NetSec.html"> 5.4. Network Security Fundamentals</a>
|
||
<a class="dropdown-item" href="NetLayer.html"> 5.5. Network Layer: IP</a>
|
||
<a class="dropdown-item" href="LinkLayer.html"> 5.6. Link Layer</a>
|
||
<a class="dropdown-item" href="Wireless.html"> 5.7. Wireless Connectivity: Wi-Fi, Bluetooth, and Zigbee</a>
|
||
<a class="dropdown-item" href="Extended5DNS.html"> 5.8. Extended Example: DNS client</a>
|
||
<div class="dropdown-divider"></div>
|
||
<a class="dropdown-item disabled"><b>Chapter 6</b></a>
|
||
<a class="dropdown-item" href="ThreadsOverview.html"> 6.1. Concurrency with Multithreading</a>
|
||
<a class="dropdown-item" href="ProcVThreads.html"> 6.2. Processes vs. Threads</a>
|
||
<a class="dropdown-item" href="RaceConditions.html"> 6.3. Race Conditions and Critical Sections</a>
|
||
<a class="dropdown-item" href="POSIXThreads.html"> 6.4. POSIX Thread Library</a>
|
||
<a class="dropdown-item" href="ThreadArgs.html"> 6.5. Thread Arguments and Return Values</a>
|
||
<a class="dropdown-item" href="ImplicitThreads.html"> 6.6. Implicit Threading and Language-based Threads</a>
|
||
<a class="dropdown-item" href="Extended6Input.html"> 6.7. Extended Example: Keyboard Input Listener</a>
|
||
<a class="dropdown-item" href="Extended6Primes.html"> 6.8. Extended Example: Concurrent Prime Number Search</a>
|
||
<div class="dropdown-divider"></div>
|
||
<a class="dropdown-item disabled"><b>Chapter 7</b></a>
|
||
<a class="dropdown-item" href="SynchOverview.html"> 7.1. Synchronization Primitives</a>
|
||
<a class="dropdown-item" href="CritSect.html"> 7.2. Critical Sections and Peterson's Solution</a>
|
||
<a class="dropdown-item" href="Locks.html"> 7.3. Locks</a>
|
||
<a class="dropdown-item" href="Semaphores.html"> 7.4. Semaphores</a>
|
||
<a class="dropdown-item" href="Barriers.html"> 7.5. Barriers</a>
|
||
<a class="dropdown-item" href="Condvars.html"> 7.6. Condition Variables</a>
|
||
<a class="dropdown-item" href="Deadlock.html"> 7.7. Deadlock</a>
|
||
<a class="dropdown-item" href="Extended7Events.html"> 7.8. Extended Example: Event Log File</a>
|
||
<div class="dropdown-divider"></div>
|
||
<a class="dropdown-item disabled"><b>Chapter 8</b></a>
|
||
<a class="dropdown-item" href="SynchProblemsOverview.html"> 8.1. Synchronization Patterns and Problems</a>
|
||
<a class="dropdown-item" href="SynchDesign.html"> 8.2. Basic Synchronization Design Patterns</a>
|
||
<a class="dropdown-item" href="ProdCons.html"> 8.3. Producer-Consumer Problem</a>
|
||
<a class="dropdown-item" href="ReadWrite.html"> 8.4. Readers-Writers Problem</a>
|
||
<a class="dropdown-item" href="DiningPhil.html"> 8.5. Dining Philosophers Problem and Deadlock</a>
|
||
<a class="dropdown-item" href="CigSmokers.html"> 8.6. Cigarette Smokers Problem and the Limits of Semaphores and Locks</a>
|
||
<a class="dropdown-item" href="Extended8ModExp.html"> 8.7. Extended Example: Parallel Modular Exponentiation</a>
|
||
<div class="dropdown-divider"></div>
|
||
<a class="dropdown-item disabled"><b>Chapter 9</b></a>
|
||
<a class="dropdown-item" href="ParallelDistributedOverview.html"> 9.1. Parallel and Distributed Systems</a>
|
||
<a class="dropdown-item" href="ParVConc.html"> 9.2. Parallelism vs. Concurrency</a>
|
||
<a class="dropdown-item" href="ParallelDesign.html"> 9.3. Parallel Design Patterns</a>
|
||
<a class="dropdown-item" href="Scaling.html"> 9.4. Limits of Parallelism and Scaling</a>
|
||
<a class="dropdown-item" href="DistTiming.html"> 9.5. Timing in Distributed Environments</a>
|
||
<a class="dropdown-item" href="DistDataStorage.html"> 9.6. Reliable Data Storage and Location</a>
|
||
<a class="dropdown-item" href="DistConsensus.html"> 9.7. Consensus in Distributed Systems</a>
|
||
<a class="dropdown-item" href="Extended9Blockchain.html"> 9.8. Extended Example: Blockchain Proof-of-Work</a>
|
||
<div class="dropdown-divider"></div>
|
||
<a class="dropdown-item disabled"><b>Appendix A</b></a>
|
||
<a class="dropdown-item" href="CLangOverview.html"> A.1. C Language Reintroduction</a>
|
||
<a class="dropdown-item" href="Debugging.html"> A.2. Documentation and Debugging</a>
|
||
<a class="dropdown-item" href="BasicTypes.html"> A.3. Basic Types and Pointers</a>
|
||
<a class="dropdown-item" href="Arrays.html"> A.4. Arrays, Structs, Enums, and Type Definitions</a>
|
||
<a class="dropdown-item" href="Functions.html"> A.5. Functions and Scope</a>
|
||
<a class="dropdown-item" href="Pointers.html"> A.6. Pointers and Dynamic Allocation</a>
|
||
<a class="dropdown-item" href="Strings.html"> A.7. Strings</a>
|
||
<a class="dropdown-item" href="FunctionPointers.html"> A.8. Function Pointers</a>
|
||
<a class="dropdown-item" href="Files.html"> A.9. Files</a>
|
||
</div>
|
||
</li>
|
||
|
||
|
||
|
||
</ul>
|
||
</div>
|
||
|
||
<ul class="navbar-nav flex-row ml-md-auto d-none d-md-flex">
|
||
<li class="nav-item"><a class="nav-link jmu-gold" href="https://w3.cs.jmu.edu/kirkpams/OpenCSF/Books/csf/source/UDPSockets.rst"
|
||
target="_blank" rel="nofollow">Show Source</a></li>
|
||
|
||
</ul>
|
||
</nav>
|
||
|
||
|
||
<div class="container center">
|
||
«  <a id="prevmod" href="TCPSockets.html">4.5. TCP Socket Programming: HTTP</a>
|
||
  ::  
|
||
<a class="uplink" href="index.html">Contents</a>
|
||
  ::  
|
||
<a id="nextmod" href="AppBroadcast.html">4.7. Application-Layer Broadcasting: DHCP</a>  »
|
||
|
||
</div>
|
||
<br />
|
||
|
||
|
||
|
||
<script type="text/javascript" src="_static/js/jquery-2.1.4.min.js"></script>
|
||
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.1/MathJax.js?config=TeX-AMS-MML_HTMLorMML"></script>
|
||
<script type="text/javascript" src="_static/js/jquery-1.11.4-ui.min.js"></script>
|
||
<script type="text/javascript" src="_static/js/forge-0.7.0.min.js"></script>
|
||
<script type="text/javascript" src="../../../JSAV/lib/jquery.transit.js"></script>
|
||
<script type="text/javascript" src="../../../JSAV/lib/raphael.js"></script>
|
||
<script type="text/javascript" src="../../../JSAV/build/JSAV-min.js"></script>
|
||
<script type="text/javascript" src="_static/js/config.js"></script>
|
||
<script type="text/javascript" src="../../../lib/odsaUtils-min.js"></script>
|
||
<script type="text/javascript" src="../../../lib/odsaMOD-min.js"></script>
|
||
<script type="text/javascript" src="_static/js/d3-4.13.0.min.js"></script>
|
||
<script type="text/javascript" src="_static/js/d3-selection-multi.v1.min.js"></script>
|
||
<script type="text/javascript" src="../../../lib/dataStructures.js"></script>
|
||
|
||
|
||
|
||
|
||
|
||
|
||
<div class="container">
|
||
|
||
<script>ODSA.SETTINGS.DISP_MOD_COMP = true;ODSA.SETTINGS.MODULE_NAME = "UDPSockets";ODSA.SETTINGS.MODULE_LONG_NAME = "UDP Socket Programming: DNS";ODSA.SETTINGS.MODULE_CHAPTER = "Networked Concurrency"; ODSA.SETTINGS.BUILD_DATE = "2021-06-11 17:38:24"; ODSA.SETTINGS.BUILD_CMAP = false;JSAV_OPTIONS['lang']='en';JSAV_EXERCISE_OPTIONS['code']='java';</script><div class="section" id="udp-socket-programming-dns">
|
||
<h1>4.6. UDP Socket Programming: DNS<a class="headerlink" href="UDPSockets.html#udp-socket-programming-dns" title="Permalink to this headline">¶</a></h1>
|
||
<div class="figure mb-2 align-right" id="id17" style="width: 40%">
|
||
<span id="dnshier"></span><a class="reference internal image-reference" href="_images/CSF-Images.4.11.png"><img class="p-3 mb-2 align-center border border-dark rounded-lg" alt="The DNS name space is organized as a hierarchy of zones of authority" src="_images/CSF-Images.4.11.png" style="width: 95%;" /></a>
|
||
<p class="caption align-center px-3"><span class="caption-text"> Figure 4.6.1: The DNS name space is organized as a hierarchy of zones of authority</span></p>
|
||
</div>
|
||
<p>The <a class="reference internal" href="Glossary.html#term-domain-name-system"><span class="xref std std-term">Domain Name System</span></a> (DNS) is a distributed database that resolves human-readable URLs
|
||
(such as <code class="docutils literal notranslate"><span class="pre">stuff.com</span></code> or <code class="docutils literal notranslate"><span class="pre">k12.county.edu</span></code>) into IP addresses. The basic structure and operation
|
||
of DNS is defined in RFCs 1034 and 1035. DNS defines a hierarchical name space, illustrated in
|
||
<a href="UDPSockets.html#dnshier">Figure 4.6.1</a>, that are controlled by multiple <a class="reference internal" href="Glossary.html#term-name-server"><span class="xref std std-term">name servers</span></a>. At the
|
||
highest level is the <a class="reference internal" href="Glossary.html#term-root-name-server"><span class="xref std std-term">root name server</span></a>, which is denoted with a dot (<code class="docutils literal notranslate"><span class="pre">"."</span></code>). The
|
||
<a class="reference internal" href="Glossary.html#term-internet-corporation-for-assigned-names-and-numbers"><span class="xref std std-term">Internet Corporation for Assigned Names and Numbers</span></a> (ICANN) is a nonprofit organization that
|
||
governs and maintains the root structures of the DNS hierarchy. The level just below the root is the
|
||
set of <a class="reference internal" href="Glossary.html#term-top-level-domain"><span class="xref std std-term">top-level domains</span></a> (TLDs), which provide structure based on the
|
||
type of service that the registered organization provides. Each TLD is governed and maintained by a
|
||
separate company or organization, such as Verisign. These organizations coordinate their work with
|
||
ICANN to maintain the core of the DNS hierarchy.</p>
|
||
<p>Levels in the DNS hierarchy are indicated by dots within the domain name. For instance, an education
|
||
institution (such as a university or school district) would register their domain names under the
|
||
<code class="docutils literal notranslate"><span class="pre">.edu</span></code> TLD, establishing ownership of a domain name such as <code class="docutils literal notranslate"><span class="pre">university.edu</span></code>. Commercial
|
||
enterprises and other businesses use the <code class="docutils literal notranslate"><span class="pre">.com</span></code> TLD, reserving domain names like <code class="docutils literal notranslate"><span class="pre">business.com</span></code>.
|
||
Non-profit organizations register domain names under the <code class="docutils literal notranslate"><span class="pre">.org</span></code> TLD, establishing names like
|
||
<code class="docutils literal notranslate"><span class="pre">charity.org</span></code>.</p>
|
||
<div class="topic border border-dark rounded-lg bg-light px-2 mb-3">
|
||
<div class="figure align-left">
|
||
<a class="reference internal image-reference" href="_images/CSF-Images-Note.png"><img alt="Decorative note icon" src="_images/CSF-Images-Note.png" style="width: 100%;" /></a>
|
||
</div>
|
||
<p class="topic-title first pt-2 mb-1">Note</p><hr class="mt-1" />
|
||
<p>The names <code class="docutils literal notranslate"><span class="pre">university.edu</span></code>, <code class="docutils literal notranslate"><span class="pre">business.com</span></code>, and <code class="docutils literal notranslate"><span class="pre">charity.org</span></code> are intended to illustrate the
|
||
types of entities that might use these TLDs. These domains are actually registered to real
|
||
organizations (CapStone University, a private registrant, and Global Impact, respectively). None of
|
||
the addresses or descriptions in this section are intended to refer to these specific entities.</p>
|
||
</div>
|
||
<p>Organizations themselves can extend the DNS hierarchy based on their own needs and services. The
|
||
organizations manage this by setting up and running their own authoritative name servers. For
|
||
instance, <code class="docutils literal notranslate"><span class="pre">charity.org</span></code> might use the separate domain names <code class="docutils literal notranslate"><span class="pre">mail.charity.org</span></code> and
|
||
<code class="docutils literal notranslate"><span class="pre">www.charity.org</span></code> to distinguish their email server from the server for their web page. These
|
||
names are considered subdomains of the <code class="docutils literal notranslate"><span class="pre">charity.org</span></code> domain name.</p>
|
||
<div class="topic border border-dark rounded-lg alert-danger px-2 mb-3">
|
||
<div class="figure align-left">
|
||
<a class="reference internal image-reference" href="_images/CSF-Images-BugWarning.png"><img alt="Decorative bug warning" src="_images/CSF-Images-BugWarning.png" style="width: 90%;" /></a>
|
||
</div>
|
||
<p class="topic-title first pt-2 mb-1">Bug Warning</p><hr class="mt-1" />
|
||
<p>Once an organization has registered a domain name with the appropriate TLD, that organization has
|
||
established control of all subdomains within their zone of authority. That is, the organization
|
||
that has set up the authoritative name server for <code class="docutils literal notranslate"><span class="pre">charity.org</span></code> has administrative control over
|
||
every domain name that ends with those fields. Note, though, that this control does not extend to
|
||
similar-looking domain names. The key distinction is the presence of the <code class="docutils literal notranslate"><span class="pre">"."</span></code> immediately
|
||
preceding <code class="docutils literal notranslate"><span class="pre">charity.org</span></code> in a domain name. That is, the owners of <code class="docutils literal notranslate"><span class="pre">charity.org</span></code> would have the
|
||
authority for the domain names <code class="docutils literal notranslate"><span class="pre">mail.charity.org</span></code> and <code class="docutils literal notranslate"><span class="pre">www.charity.org</span></code>; they would not,
|
||
however, have control over <code class="docutils literal notranslate"><span class="pre">mailcharity.org</span></code> or <code class="docutils literal notranslate"><span class="pre">wwwcharity.org</span></code>. Registering similar-looking
|
||
domain names is a common technique for criminal or other malicious groups that are attempting to
|
||
take advantage of users who make a mistake typing the URL or those who might overlook the missing
|
||
<code class="docutils literal notranslate"><span class="pre">"."</span></code> as part of a spam email message in a phishing attack.</p>
|
||
</div>
|
||
<p>DNS is designed to be a resilient system for resolving addresses. As such, there is not actually a
|
||
single root DNS server. As of this writing, there are currently 13 root servers operating
|
||
world-wide. These 13 root servers communicate with each other to maintain a consistent database of
|
||
IP addresses for the TLD servers. Again, as of this writing, there are currently over 1500 TLD
|
||
extensions. These extensions include the original seven TLDs (<code class="docutils literal notranslate"><span class="pre">.com</span></code>, <code class="docutils literal notranslate"><span class="pre">.edu</span></code>, <code class="docutils literal notranslate"><span class="pre">.gov</span></code>,
|
||
<code class="docutils literal notranslate"><span class="pre">.int</span></code>, <code class="docutils literal notranslate"><span class="pre">.mil</span></code>, <code class="docutils literal notranslate"><span class="pre">.net</span></code>, and <code class="docutils literal notranslate"><span class="pre">.org</span></code>). Other TLD extensions indicate country codes (such as
|
||
<code class="docutils literal notranslate"><span class="pre">.uk</span></code> for the United Kingdom or <code class="docutils literal notranslate"><span class="pre">.ca</span></code> for Canada), though many companies repurposed country
|
||
codes to make their domain names more readable. Some examples of this practice include
|
||
<code class="docutils literal notranslate"><span class="pre">del.icio.us</span></code> and <code class="docutils literal notranslate"><span class="pre">bit.ly</span></code>, which used the country codes for the United State and Libya to
|
||
create readable domain names; in the former case, a company registered the domain name <code class="docutils literal notranslate"><span class="pre">icio.us</span></code>
|
||
with the US domain registrar, then created the <code class="docutils literal notranslate"><span class="pre">del.icio.us</span></code> entry within its own authoritative
|
||
name server. In more recent years, ICANN has expanded the TLD extensions to include topical names,
|
||
such as <code class="docutils literal notranslate"><span class="pre">.car</span></code>, <code class="docutils literal notranslate"><span class="pre">.hospital</span></code>, or <code class="docutils literal notranslate"><span class="pre">.restaurant</span></code>.</p>
|
||
<div class="section" id="resolving-dns-queries">
|
||
<h2>4.6.1. Resolving DNS Queries<a class="headerlink" href="UDPSockets.html#resolving-dns-queries" title="Permalink to this headline">¶</a></h2>
|
||
<p>To translate a domain name into an IP address, a user program (such as a web browser) contacts a
|
||
local process known as a <em>resolver</em>. The resolver maintains a <em>master file</em> that
|
||
contains a local database of pre-defined addresses along with a cache of recently translated
|
||
addresses. If the master file contains the address for the requested domain name, the resolver can
|
||
return the answer immediately. For addresses that are not in the master file, the resolver would
|
||
then consult the larger DNS structure. The pre-defined addresses in the master file include the
|
||
addresses of the 13 root servers. For instance, the root name server <code class="docutils literal notranslate"><span class="pre">a.root-servers.net</span></code> has a
|
||
persistent IP address of 198.41.0.4. These addresses serve as the entry point to the Internet’s DNS
|
||
database.</p>
|
||
<p>DNS defines two strategies that resolvers can adopt. In the <em>iterative</em> strategy, a DNS
|
||
resolver will send repeated queries to different servers until it can resolve the request. For
|
||
instance, a home user’s laptop may send a DNS request to their ISP or a public DNS service like
|
||
OpenDNS. This DNS resolver had only the root server addresses, it would contact a root server to get
|
||
the address of the TLD server; this same DNS resolver would then send a request to the TLD
|
||
requesting the address of the authoritative name server, and so on. In the <em>recursive</em>
|
||
strategy, the DNS resolver would simply forward the request to a different resolver that would take
|
||
control. This approach is illustrated by the same scenario, because the laptop itself has a DNS
|
||
resolver; instead of iteratively contacting the name servers to resolve the request, the laptop sent
|
||
a single request to the ISP DNS resolver or OpenDNS. The DNS specification requires all resolvers
|
||
implement an iterative solution, while the recursive strategy is optional.</p>
|
||
<div class="figure mb-2 align-right" id="id18" style="width: 55%">
|
||
<span id="dnsiter"></span><a class="reference internal image-reference" href="_images/CSF-Images.4.12.png"><img class="p-3 mb-2 align-center border border-dark rounded-lg" alt="Iterative sequence of DNS requests" src="_images/CSF-Images.4.12.png" style="width: 95%;" /></a>
|
||
<p class="caption align-center px-3"><span class="caption-text"> Figure 4.6.4: Iterative sequence of DNS requests</span></p>
|
||
</div>
|
||
<p><a href="UDPSockets.html#dnsiter">Figure 4.6.4</a> illustrates the iterative sequence of messages sent when a web browser
|
||
tries to resolve <code class="docutils literal notranslate"><span class="pre">www.charity.org</span></code>. <a class="footnote-reference" href="UDPSockets.html#f27" id="id1">[1]</a> The resolver finds the root server address and sends a
|
||
query to 198.41.0.4 to look up the <code class="docutils literal notranslate"><span class="pre">.org</span></code> TLD address. The root name server responds with
|
||
199.19.56.1 as the address for the <code class="docutils literal notranslate"><span class="pre">.org</span></code> TLD name server. The resolver then contacts that server
|
||
to get the address of the authoritative name server for <code class="docutils literal notranslate"><span class="pre">.charity.org</span></code>, which is at address
|
||
12.34.56.78. Finally, the resolver contacts the authoritative name server that indicates
|
||
<code class="docutils literal notranslate"><span class="pre">www.charity.org</span></code> can be found at 12.34.56.80.</p>
|
||
<p>If every DNS query required the steps in <a href="UDPSockets.html#dnsiter">Figure 4.6.4</a>, the system would suffer from
|
||
terrible performance. Every time someone accessed a web page, sent an email, or streamed a piece of
|
||
music, the client would have to contact one of the 13 root servers; these servers would quickly
|
||
crash from the strain of handling these requests. Instead, all levels of the DNS system employ an
|
||
extensive amount of caching. As such, except under rare circumstances, the master file on the local
|
||
machine already has the IP address for the <code class="docutils literal notranslate"><span class="pre">.org</span></code> TLD when the original request is received.
|
||
Similarly, if the request for <code class="docutils literal notranslate"><span class="pre">www.charity.org</span></code> is followed by requests for <code class="docutils literal notranslate"><span class="pre">www-1.charity.org</span></code>,
|
||
<code class="docutils literal notranslate"><span class="pre">mail.charity.org</span></code>, or any other subdomain, the resolver would not contact either the root or
|
||
<code class="docutils literal notranslate"><span class="pre">.org</span></code> TLD name servers, as the resolver’s cache would already have the address of the needed
|
||
authoritative name server. In addition to caching, the TLD and authoritative name servers also
|
||
employ <a class="reference internal" href="Glossary.html#term-343"><span class="xref std std-term">replication</span></a> across multiple IP addresses. That is, 199.19.56.1 is one of several IP
|
||
addresses that correspond to the <code class="docutils literal notranslate"><span class="pre">.org</span></code> TLD. The resolver can contact any of these addresses and
|
||
is likely to get the same results.</p>
|
||
</div>
|
||
<div class="section" id="dns-resource-record-structure">
|
||
<h2>4.6.2. DNS Resource Record Structure<a class="headerlink" href="UDPSockets.html#dns-resource-record-structure" title="Permalink to this headline">¶</a></h2>
|
||
<p>The translation information for DNS queries are stored and sent in structures known as
|
||
<em>resource records</em>. <a class="reference external" href="UDPSockets.html#tbl4-6">Table 4.6</a> shows the generic structure of
|
||
every resource record. The <code class="docutils literal notranslate"><span class="pre">NAME</span></code> and <code class="docutils literal notranslate"><span class="pre">RDATA</span></code> fields (indicated with the wavy lines in the
|
||
table) are variable length; all other fields are exactly 16 bits wide. The <code class="docutils literal notranslate"><span class="pre">NAME</span></code> field (also
|
||
called the owner) is the human-readable domain name of the record. The <code class="docutils literal notranslate"><span class="pre">TYPE</span></code> provides information
|
||
about the resource under consideration, as described below. The <code class="docutils literal notranslate"><span class="pre">CLASS</span></code> designates the protocol
|
||
stack in use, which is <code class="docutils literal notranslate"><span class="pre">IN</span></code> to indicate Internet. The <code class="docutils literal notranslate"><span class="pre">TTL</span></code> field indicates how many seconds the
|
||
record should be considered valid in the local host’s cache; once the record expires, the resolver
|
||
should repeat the query to check if the record has been updated. Finally, the <code class="docutils literal notranslate"><span class="pre">RDATA</span></code> field
|
||
includes the actual data of the record, which is tied to the type, and the <code class="docutils literal notranslate"><span class="pre">RDLENGTH</span></code> indicates
|
||
the length of <code class="docutils literal notranslate"><span class="pre">RDATA</span></code>.</p>
|
||
<center>
|
||
<div class="col-md-6">
|
||
<table class="table table-bordered">
|
||
<thead class="jmu-dark-purple-bg text-light">
|
||
<tr>
|
||
<th class="p-0 center">0</th> <th class="p-0 center">1</th>
|
||
<th class="p-0 center">2</th> <th class="p-0 center">3</th>
|
||
<th class="p-0 center">4</th> <th class="p-0 center">5</th>
|
||
<th class="p-0 center">6</th> <th class="p-0 center">7</th>
|
||
<th class="p-0 center">8</th> <th class="p-0 center">9</th>
|
||
<th class="p-0 center">10</th> <th class="p-0 center">11</th>
|
||
<th class="p-0 center">12</th> <th class="p-0 center">13</th>
|
||
<th class="p-0 center">14</th> <th class="p-0 center">15</th>
|
||
</tr>
|
||
</thead>
|
||
<tbody>
|
||
<tr> <td class="p-0 center" colspan="16"><div class="xborder-highlight"><code>NAME</code></div></td> </tr>
|
||
<tr> <td class="py-0 center" colspan="16"><code>TYPE</code></td> </tr>
|
||
<tr> <td class="py-0 center" colspan="16"><code>CLASS</code></td> </tr>
|
||
<tr> <td class="py-0 center" colspan="16"><code>TTL</code></td> </tr>
|
||
<tr> <td class="py-0 center" colspan="16"><code>RDLENGTH</code></td> </tr>
|
||
<tr> <td class="p-0 center" colspan="16"><div class="xborder-highlight"><code>RDATA</code></div></td> </tr>
|
||
</tbody>
|
||
</table>
|
||
</div>
|
||
<p>
|
||
Table 4.6: Generic structure of a DNS resource record
|
||
</p>
|
||
<br />
|
||
</center><p>There are several common types of resources records. The <code class="docutils literal notranslate"><span class="pre">A</span></code> type denotes a host address, so the
|
||
<code class="docutils literal notranslate"><span class="pre">RDATA</span></code> field would contain the IP address for the domain name. The <code class="docutils literal notranslate"><span class="pre">CNAME</span></code> type denotes a
|
||
<a class="reference internal" href="Glossary.html#term-canonical-name"><span class="xref std std-term">canonical name</span></a> record that maps an alias to the definitive domain name. For instance, a
|
||
company might create the subdomains <code class="docutils literal notranslate"><span class="pre">ftp.example.com</span></code> and <code class="docutils literal notranslate"><span class="pre">www.example.com</span></code>, though both of
|
||
these addresses are handled by the server identified by the name <code class="docutils literal notranslate"><span class="pre">example.com</span></code>. Resource records
|
||
for example.com would have an <code class="docutils literal notranslate"><span class="pre">A</span></code> type with the server’s IP address, while resource records for both
|
||
<code class="docutils literal notranslate"><span class="pre">ftp.example.com</span></code> and <code class="docutils literal notranslate"><span class="pre">www.example.com</span></code> would have <code class="docutils literal notranslate"><span class="pre">CNAME</span></code> type, with <code class="docutils literal notranslate"><span class="pre">example.com</span></code> in the
|
||
<code class="docutils literal notranslate"><span class="pre">RDATA</span></code> field. A third common resource record type is <code class="docutils literal notranslate"><span class="pre">NS</span></code>, which indicates the authoritative name
|
||
server for the domain. For instance, the <code class="docutils literal notranslate"><span class="pre">RDATA</span></code> field for the <code class="docutils literal notranslate"><span class="pre">NS</span></code> record for <code class="docutils literal notranslate"><span class="pre">example.com</span></code>
|
||
would contain the domain name of the authoritative server for the <code class="docutils literal notranslate"><span class="pre">example.com</span></code> domain. Finally,
|
||
an <code class="docutils literal notranslate"><span class="pre">MX</span></code> record type is used to store information about mail exchange servers that are responsible
|
||
for delivering email.</p>
|
||
<p>To illustrate the example, consider again the fictional scenario in <a href="UDPSockets.html#dnsiter">Figure 4.6.4</a>. When
|
||
the resolver contacted the <code class="docutils literal notranslate"><span class="pre">.org</span></code> TLD name server at 199.19.56.1, this server might first reply
|
||
with an NS resource record for the <code class="docutils literal notranslate"><span class="pre">charity.org</span></code> domain. This authoritative name server might have
|
||
a domain name like <code class="docutils literal notranslate"><span class="pre">ns.charity.org</span></code>, which would be the contents of the <code class="docutils literal notranslate"><span class="pre">RDATA</span></code> field for the NS
|
||
resource record. To resolve this address, a second response would contain a resource record with the
|
||
A type containing the address of the name server 12.34.56.78. Complicating matters further, this
|
||
authoritative name server might initially respond with a <code class="docutils literal notranslate"><span class="pre">CNAME</span></code> resource record to indicate that
|
||
<code class="docutils literal notranslate"><span class="pre">www.charity.org</span></code> is an alias for <code class="docutils literal notranslate"><span class="pre">a0.web.charity.org</span></code>. A second response from the
|
||
<code class="docutils literal notranslate"><span class="pre">charity.org</span></code> authoritative name server would then return an A resource record to indicate that
|
||
<code class="docutils literal notranslate"><span class="pre">a0.web.charity.org</span></code> can be accessed at 12.34.56.80.</p>
|
||
</div>
|
||
<div class="section" id="dns-protocol-messages">
|
||
<h2>4.6.3. DNS Protocol Messages<a class="headerlink" href="UDPSockets.html#dns-protocol-messages" title="Permalink to this headline">¶</a></h2>
|
||
<p>Like HTTP/1.0, the DNS protocol is a simple request-response protocol with no persistent state
|
||
between messages, but DNS uses UDP instead of TCP. That is, a DNS client can construct the datagram
|
||
format specified by the RFC and send it to an arbitrary server as a UDP message with no prior
|
||
connection. The server would then respond to the IP address in the UDP datagram header with the
|
||
response. The DNS message itself contains five fields. The <code class="docutils literal notranslate"><span class="pre">header</span></code> field indicates if the message
|
||
contains a query, a response, or another type of message. The question field contains the domain
|
||
name that is being queried (the <code class="docutils literal notranslate"><span class="pre">QNAME</span></code>), along with the class (<code class="docutils literal notranslate"><span class="pre">QCLASS</span></code>) and type (<code class="docutils literal notranslate"><span class="pre">QTYPE</span></code>)
|
||
of resource record requested. For a DNS response, the <code class="docutils literal notranslate"><span class="pre">answer</span></code> field would contain the resource
|
||
record. The <code class="docutils literal notranslate"><span class="pre">authority</span></code> and <code class="docutils literal notranslate"><span class="pre">additional</span></code> fields provide additional information.</p>
|
||
<p>To illustrate the structure of a DNS query and response, consider a request to resolve the domain
|
||
name <code class="docutils literal notranslate"><span class="pre">example.com</span></code>. <a class="footnote-reference" href="UDPSockets.html#f28" id="id2">[2]</a> <a class="reference external" href="UDPSockets.html#tbl4-7">Table 4.7</a> shows the interpretation of the bytes of the
|
||
request. (Note that the exact structure of the UDP datagram consists of just the bytes shown,
|
||
concatenated in order: <code class="docutils literal notranslate"><span class="pre">123401000001...</span></code>) The header starts with a 16-bit randomly chosen
|
||
identifier denoted as XID (<code class="docutils literal notranslate"><span class="pre">1234</span></code> in our example), followed by a 16-bit value that serves as a bit
|
||
mask. The structure of the bit mask is shown in <a class="reference external" href="UDPSockets.html#tbl4-8">Table 4.8</a>. The rest of the header after the
|
||
bit-mask indicates how many entries are in each of the other fields, each as a 16-bit value.</p>
|
||
<center>
|
||
<table class="table table-bordered">
|
||
<tbody>
|
||
<tr>
|
||
<td class="py-0" rowspan="3">Header</td>
|
||
<td class="py-0"><code>1234</code></td>
|
||
<td class="py-0"><code>XID=0x1234 [random identifier]</code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0"><code>0100</code></td>
|
||
<td class="py-0"><code>OPCODE=SQUERY</code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0"><code>0001 0000 0000 0000</code></td>
|
||
<td class="py-0"><code>1 question field</code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0" rowspan="2">Question</td>
|
||
<td class="py-0"><code>0765 7861 6d70 6c65 0363 6f6d 00</code></td>
|
||
<td class="py-0"><code>QNAME=EXAMPLE.COM.,</code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0"><code>0001 0001</code></td>
|
||
<td class="py-0"><code>QCLASS=IN, QTYPE=A </code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0">Answer</td>
|
||
<td class="py-0"> </td>
|
||
<td class="py-0"><code><empty></code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0">Authority</td>
|
||
<td class="py-0"> </td>
|
||
<td class="py-0"><code><empty></code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0">Additional</td>
|
||
<td class="py-0"> </td>
|
||
<td class="py-0"><code><empty></code></td>
|
||
</tr>
|
||
</tbody>
|
||
</table>
|
||
<p>
|
||
Table 4.7: Sequence of bytes and their interpretation to query DNS for example.com
|
||
</p>
|
||
<br />
|
||
</center><p><a class="reference external" href="UDPSockets.html#tbl4-8">Table 4.8</a> illustrates the structure of the 16-bit flag field that follows the XID field of
|
||
a DNS header. In the message shown in <a class="reference external" href="UDPSockets.html#tbl4-7">Table 4.7</a>, the only bit set is the <code class="docutils literal notranslate"><span class="pre">Recursion</span> <span class="pre">Desired</span></code>
|
||
(<code class="docutils literal notranslate"><span class="pre">RD</span></code>) bit. The <code class="docutils literal notranslate"><span class="pre">Opcode</span></code> field indicates that this is a standard query (<code class="docutils literal notranslate"><span class="pre">SQUERY</span> <span class="pre">=</span> <span class="pre">0000</span></code>). In
|
||
the response shown in <a class="reference external" href="UDPSockets.html#tbl4-9">Table 4.9</a>, the flag value is <code class="docutils literal notranslate"><span class="pre">0x8180</span></code>, which means that the Query
|
||
Response (<code class="docutils literal notranslate"><span class="pre">QR</span></code>) bit has been set to indicate the message is a response, as well as the <code class="docutils literal notranslate"><span class="pre">Recursion</span>
|
||
<span class="pre">Available</span></code> (<code class="docutils literal notranslate"><span class="pre">RA</span></code>) bit. The <code class="docutils literal notranslate"><span class="pre">RCODE</span></code> field is used to indicate if an error occurs, and all 0 bits
|
||
there indicates there was no error processing the query. Information on the other fields is
|
||
available in RFC 1035.</p>
|
||
<center>
|
||
<table class="table table-bordered">
|
||
<thead class="jmu-dark-purple-bg text-light">
|
||
<tr>
|
||
<td class="py-0 center">Bit Index</td>
|
||
<th class="py-0 center">0</th> <th class="py-0 center">1</th>
|
||
<th class="py-0 center">2</th> <th class="py-0 center">3</th>
|
||
<th class="py-0 center">4</th> <th class="py-0 center">5</th>
|
||
<th class="py-0 center">6</th> <th class="py-0 center">7</th>
|
||
<th class="py-0 center">8</th> <th class="py-0 center">9</th>
|
||
<th class="py-0 center">10</th> <th class="py-0 center">11</th>
|
||
<th class="py-0 center">12</th> <th class="py-0 center">13</th>
|
||
<th class="py-0 center">14</th> <th class="py-0 center">15</th>
|
||
</tr>
|
||
</thead>
|
||
<tbody>
|
||
<tr>
|
||
<td class="py-0 center">Meaning</td>
|
||
<td class="py-0 center"><code>QR</code></td>
|
||
<td class="py-0 center" colspan="4"><code>Opcode</code></td>
|
||
<td class="py-0 center"><code>AA</code></td>
|
||
<td class="py-0 center"><code>TC</code></td>
|
||
<td class="py-0 center"><code>RD</code></td>
|
||
<td class="py-0 center"><code>RA</code></td>
|
||
<td class="py-0 center" colspan="3"><code>Z</code></td>
|
||
<td class="py-0 center" colspan="4"><code>RCODE</code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0 center">Value</td>
|
||
<td class="py-0 center">0</td>
|
||
<td class="py-0 center">0</td>
|
||
<td class="py-0 center">0</td>
|
||
<td class="py-0 center">0</td>
|
||
<td class="py-0 center">0</td>
|
||
<td class="py-0 center">0</td>
|
||
<td class="py-0 center">0</td>
|
||
<td class="py-0 center">1</td>
|
||
<td class="py-0 center">0</td>
|
||
<td class="py-0 center">0</td>
|
||
<td class="py-0 center">0</td>
|
||
<td class="py-0 center">0</td>
|
||
<td class="py-0 center">0</td>
|
||
<td class="py-0 center">0</td>
|
||
<td class="py-0 center">0</td>
|
||
<td class="py-0 center">0</td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0 center">Hex Value</td>
|
||
<td class="py-0 center" colspan="4">0</td>
|
||
<td class="py-0 center" colspan="4">1</td>
|
||
<td class="py-0 center" colspan="4">0</td>
|
||
<td class="py-0 center" colspan="4">0</td>
|
||
</tr>
|
||
</tbody>
|
||
</table>
|
||
<p>
|
||
Table 4.8: Structure of the flags field in a DNS query header
|
||
</p>
|
||
<br />
|
||
</center><p>The question field of the request starts with the fields of the domain name, with each field
|
||
preceded by the number of bytes in the field. That is, the domain name in the question does not
|
||
contain the standard dotted format for the name. In this example, the domain name (<code class="docutils literal notranslate"><span class="pre">QNAME</span></code>
|
||
<a class="footnote-reference" href="UDPSockets.html#f29" id="id5">[3]</a>) starts with 7 characters (<code class="docutils literal notranslate"><span class="pre">65</span> <span class="pre">78</span> <span class="pre">61</span> <span class="pre">6d</span> <span class="pre">70</span> <span class="pre">6c</span> <span class="pre">65</span> <span class="pre">=</span> <span class="pre">"EXAMPLE"</span></code>) followed by a field with 3
|
||
characters (<code class="docutils literal notranslate"><span class="pre">63</span> <span class="pre">6f</span> <span class="pre">6d</span> <span class="pre">=</span> <span class="pre">"COM"</span></code>). The QNAME continues until the first 0-byte (<code class="docutils literal notranslate"><span class="pre">00</span></code>) is
|
||
encountered, as this indicates a 0-length field. The remainder of the question indicate the class
|
||
(<code class="docutils literal notranslate"><span class="pre">0001</span> <span class="pre">=</span> <span class="pre">IN</span></code>) and the type of resource record sought (<code class="docutils literal notranslate"><span class="pre">0001</span> <span class="pre">=</span> <span class="pre">A</span></code>).</p>
|
||
<p><a class="reference external" href="UDPSockets.html#tbl4-9">Table 4.9</a> shows the response for the query from <a class="reference external" href="UDPSockets.html#tbl4-7">Table 4.7</a>. In the response, the
|
||
<code class="docutils literal notranslate"><span class="pre">header</span></code> is almost identical to that of the request. The randomly chosen identifier <code class="docutils literal notranslate"><span class="pre">XID</span></code> should
|
||
match the original request; if the resolver has sent multiple requests, the <code class="docutils literal notranslate"><span class="pre">XID</span></code> field allows the
|
||
resolver to determine which request is being answered. The bit mask has been modified to denote that
|
||
this message is a response and the recursive resolution strategy is available. The <code class="docutils literal notranslate"><span class="pre">header</span></code> also
|
||
indicates that a single answer has been provided. The <code class="docutils literal notranslate"><span class="pre">question</span></code> field is identical to the
|
||
original request.</p>
|
||
<center>
|
||
<table class="table table-bordered py-0">
|
||
<tbody>
|
||
<tr>
|
||
<td class="py-0" rowspan="3">Header</td>
|
||
<td class="py-0"><code>1234</code></td>
|
||
<td class="py-0"><code>XID=0x1234 [random identifier]</code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0"><code>8180</code></td>
|
||
<td class="py-0"><code>OPCODE=SQUERY, RESPONSE, RA</code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0"><code>0001 0001 0000 0000</code></td>
|
||
<td class="py-0"><code>1 question and 1 answer</code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0" rowspan="2">Question</td>
|
||
<td class="py-0"><code>0765 7861 6d70 6c65 0363 6f6d 00</code></td>
|
||
<td class="py-0"><code>QNAME=EXAMPLE.COM.,</code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0"><code>0001 0001</code></td>
|
||
<td class="py-0"><code>QCLASS=IN, QTYPE=A </code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0" rowspan="6">Answer</td>
|
||
<td class="py-0"> </td>
|
||
<td class="py-0"><code><empty></code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0"><code>c00c</code></td>
|
||
<td class="py-0"><code>QNAME=EXAMPLE.COM. [compressed]</code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0"><code>0001</code></td>
|
||
<td class="py-0"><code>QTYPE=A</code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0"><code>0001</code></td>
|
||
<td class="py-0"><code>QCLASS=IN</code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0"><code>0000 e949</code></td>
|
||
<td class="py-0"><code>TTL = 0xe949 = 59721</code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0"><code>04</code></td>
|
||
<td class="py-0"><code>RDLENGTH = 4</code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0"><code>5db8 d822</code></td>
|
||
<td class="py-0"><code>RDATA = 0x5db8d822 [93.184.216.34]</code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0">Authority</td>
|
||
<td class="py-0"> </td>
|
||
<td class="py-0"><code><empty></code></td>
|
||
</tr>
|
||
<tr>
|
||
<td class="py-0">Additional</td>
|
||
<td class="py-0"> </td>
|
||
<td class="py-0"><code><empty></code></td>
|
||
</tr>
|
||
</tbody>
|
||
</table>
|
||
<p>
|
||
Table 4.9: Sequence of bytes and their interpretation for the example.com DNS response
|
||
</p>
|
||
<br />
|
||
</center><p>The answer field contains the resource record, which adheres to the general structure defined in
|
||
<a class="reference external" href="UDPSockets.html#tbl4-6">Table 4.6</a>. The record is an <code class="docutils literal notranslate"><span class="pre">A</span></code>-type Internet (<code class="docutils literal notranslate"><span class="pre">IN</span></code> class) with a time-to-live of
|
||
59,721 seconds. The <code class="docutils literal notranslate"><span class="pre">RDLENGTH</span></code> indicates a length of four bytes for the <code class="docutils literal notranslate"><span class="pre">RDATA</span></code>, which contains
|
||
an IPv4 address. Note that the address is simply a 32-bit number <code class="docutils literal notranslate"><span class="pre">0x4db8d822</span></code>; by interpreting
|
||
each byte as a separate number, this denotes the dotted decimal address 93.184.216.34.</p>
|
||
<p>The <code class="docutils literal notranslate"><span class="pre">QNAME</span></code> field of the resource record is employing a compression technique to keep the message
|
||
as small as possible. That is, since the question field already contains the domain name, there is
|
||
no need to repeat the string in the answer. DNS indicates the compression is being used by setting
|
||
the first two bits of the answer field to <code class="docutils literal notranslate"><span class="pre">11</span></code> (hence the first byte is <code class="docutils literal notranslate"><span class="pre">0xc</span></code>). Ignoring those
|
||
two bits, the next 14 bits (<code class="docutils literal notranslate"><span class="pre">0x000c</span></code> after clearing out the two “<code class="docutils literal notranslate"><span class="pre">11</span></code>” bits) indicate the
|
||
location of the name as a byte offset within the message. That is, the answer is pointing to the
|
||
byte offset 12 (<code class="docutils literal notranslate"><span class="pre">0xc</span></code>) within the datagram, which is where the <code class="docutils literal notranslate"><span class="pre">07657861...</span></code> starts.</p>
|
||
</div>
|
||
<div class="section" id="constructing-dns-queries-with-sockets">
|
||
<h2>4.6.4. Constructing DNS Queries with Sockets<a class="headerlink" href="UDPSockets.html#constructing-dns-queries-with-sockets" title="Permalink to this headline">¶</a></h2>
|
||
<p>To illustrate how to work with DNS in code, we start by declaring the following types for a DNS
|
||
header and question. The <code class="docutils literal notranslate"><span class="pre">dns_header_t</span></code> and <code class="docutils literal notranslate"><span class="pre">dns_question_t</span></code> type definitions are those used in
|
||
the macOS DNS implementation and are present in the <code class="docutils literal notranslate"><span class="pre">dns_util.h</span></code> header file. However, these are
|
||
not part of the POSIX standard, so they do not exist on other systems. <a class="footnote-reference" href="UDPSockets.html#f30" id="id9">[4]</a> We use them here for
|
||
convenience to construct the query.</p>
|
||
<div class="highlight-c border border-dark rounded-lg bg-light px-0 mb-3 notranslate"><table class="highlighttable"><tr><td class="linenos px-0 mx-0"><div class="linenodiv"><pre class="mb-0"> 1
|
||
2
|
||
3
|
||
4
|
||
5
|
||
6
|
||
7
|
||
8
|
||
9
|
||
10
|
||
11
|
||
12
|
||
13
|
||
14</pre></div></td><td class="code"><div class="highlight bg-light"><pre class="mb-0"><span></span><span class="k">typedef</span> <span class="k">struct</span> <span class="p">{</span>
|
||
<span class="kt">uint16_t</span> <span class="n">xid</span><span class="p">;</span> <span class="cm">/* Randomly chosen identifier */</span>
|
||
<span class="kt">uint16_t</span> <span class="n">flags</span><span class="p">;</span> <span class="cm">/* Bit-mask to indicate request/response */</span>
|
||
<span class="kt">uint16_t</span> <span class="n">qdcount</span><span class="p">;</span> <span class="cm">/* Number of questions */</span>
|
||
<span class="kt">uint16_t</span> <span class="n">ancount</span><span class="p">;</span> <span class="cm">/* Number of answers */</span>
|
||
<span class="kt">uint16_t</span> <span class="n">nscount</span><span class="p">;</span> <span class="cm">/* Number of authority records */</span>
|
||
<span class="kt">uint16_t</span> <span class="n">arcount</span><span class="p">;</span> <span class="cm">/* Number of additional records */</span>
|
||
<span class="p">}</span> <span class="n">dns_header_t</span><span class="p">;</span>
|
||
|
||
<span class="k">typedef</span> <span class="k">struct</span> <span class="p">{</span>
|
||
<span class="kt">char</span> <span class="o">*</span><span class="n">name</span><span class="p">;</span> <span class="cm">/* Pointer to the domain name in memory */</span>
|
||
<span class="kt">uint16_t</span> <span class="n">dnstype</span><span class="p">;</span> <span class="cm">/* The QTYPE (1 = A) */</span>
|
||
<span class="kt">uint16_t</span> <span class="n">dnsclass</span><span class="p">;</span> <span class="cm">/* The QCLASS (1 = IN) */</span>
|
||
<span class="p">}</span> <span class="n">dns_question_t</span><span class="p">;</span>
|
||
</pre></div>
|
||
</td></tr></table></div>
|
||
<p><a class="reference external" href="UDPSockets.html#cl4-17">Code Listing 4.17</a> illustrates how to start creating a DNS query using the OpenDNS service. This same request could be sent to any DNS server, such as the DNS server operated by the reader’s ISP. <a class="footnote-reference" href="UDPSockets.html#f31" id="id10">[5]</a> As with HTTP before, the code starts by creating a socket, but this socket uses the <code class="docutils literal notranslate"><span class="pre">SOCK_DGRAM</span></code> type to create a UDP socket. OpenDNS’s DNS server IPv4 address is available at 208.67.222.222, which is the hexadecimal value <code class="docutils literal notranslate"><span class="pre">0xd043dede</span></code>. DNS servers listen on port 53, so that value is also set. For the DNS header, we can randomly assign any value to the <code class="docutils literal notranslate"><span class="pre">XID</span></code> field, which has no inherent meaning to the server itself. The flag field is set to declare the message is a request (<code class="docutils literal notranslate"><span class="pre">Q=0</span></code>) and to indicate that recursion is desired (<code class="docutils literal notranslate"><span class="pre">RD=1</span></code>). Finally, we declare that we will be sending a single question in this request. Note that all of the numeric values are set using the <code class="docutils literal notranslate"><span class="pre">htons()</span></code> and <code class="docutils literal notranslate"><span class="pre">htonl()</span></code> standard C functions to ensure that the values in the datagram will be in the correct byte order.</p>
|
||
<div class="highlight-c border border-dark rounded-lg bg-light px-0 mb-3 notranslate" id="cl4-17"><table class="highlighttable"><tr><td class="linenos px-0 mx-0"><div class="linenodiv"><pre class="mb-0"> 1
|
||
2
|
||
3
|
||
4
|
||
5
|
||
6
|
||
7
|
||
8
|
||
9
|
||
10
|
||
11
|
||
12
|
||
13
|
||
14
|
||
15
|
||
16
|
||
17
|
||
18</pre></div></td><td class="code"><div class="highlight bg-light"><pre class="mb-0"><span></span><span class="cm">/* Code Listing 4.17:</span>
|
||
<span class="cm"> Creating a DNS header and question to send to OpenDNS</span>
|
||
<span class="cm"> */</span>
|
||
|
||
<span class="kt">int</span> <span class="n">socketfd</span> <span class="o">=</span> <span class="n">socket</span> <span class="p">(</span><span class="n">AF_INET</span><span class="p">,</span> <span class="n">SOCK_DGRAM</span><span class="p">,</span> <span class="mi">0</span><span class="p">);</span>
|
||
<span class="k">struct</span> <span class="n">sockaddr_in</span> <span class="n">address</span><span class="p">;</span>
|
||
<span class="n">address</span><span class="p">.</span><span class="n">sin_family</span> <span class="o">=</span> <span class="n">AF_INET</span><span class="p">;</span>
|
||
<span class="cm">/* OpenDNS is currently at 208.67.222.222 (0xd043dede) */</span>
|
||
<span class="n">address</span><span class="p">.</span><span class="n">sin_addr</span><span class="p">.</span><span class="n">s_addr</span> <span class="o">=</span> <span class="n">htonl</span> <span class="p">(</span><span class="mh">0xd043dede</span><span class="p">);</span>
|
||
<span class="cm">/* DNS runs on port 53 */</span>
|
||
<span class="n">address</span><span class="p">.</span><span class="n">sin_port</span> <span class="o">=</span> <span class="n">htons</span> <span class="p">(</span><span class="mi">53</span><span class="p">);</span>
|
||
|
||
<span class="cm">/* Set up the DNS header */</span>
|
||
<span class="n">dns_header_t</span> <span class="n">header</span><span class="p">;</span>
|
||
<span class="n">memset</span> <span class="p">(</span><span class="o">&</span><span class="n">header</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="k">sizeof</span> <span class="p">(</span><span class="n">dns_header_t</span><span class="p">));</span>
|
||
<span class="n">header</span><span class="p">.</span><span class="n">xid</span><span class="o">=</span> <span class="n">htons</span> <span class="p">(</span><span class="mh">0x1234</span><span class="p">);</span> <span class="cm">/* Randomly chosen ID */</span>
|
||
<span class="n">header</span><span class="p">.</span><span class="n">flags</span> <span class="o">=</span> <span class="n">htons</span> <span class="p">(</span><span class="mh">0x0100</span><span class="p">);</span> <span class="cm">/* Q=0, RD=1 */</span>
|
||
<span class="n">header</span><span class="p">.</span><span class="n">qdcount</span> <span class="o">=</span> <span class="n">htons</span> <span class="p">(</span><span class="mi">1</span><span class="p">);</span> <span class="cm">/* Sending 1 question */</span>
|
||
</pre></div>
|
||
</td></tr></table></div>
|
||
<p><a class="reference external" href="UDPSockets.html#cl4-18">Code Listing 4.18</a> illustrates the initial steps for setting up the question field. The
|
||
length of this field is not fixed, as it depends on the length of the domain name being translated.
|
||
As such, the <code class="docutils literal notranslate"><span class="pre">dns_question_t</span></code> type does not contain the full contents of the question itself,
|
||
using a pointer to the name field within the program instead. For this scenario, we are only
|
||
requesting an Internet address record, so we set the <code class="docutils literal notranslate"><span class="pre">QTYPE</span></code> to 1 (<code class="docutils literal notranslate"><span class="pre">A</span></code>) and <code class="docutils literal notranslate"><span class="pre">QCLASS</span></code> to 1 (<code class="docutils literal notranslate"><span class="pre">IN</span></code>).</p>
|
||
<div class="highlight-c border border-dark rounded-lg bg-light px-0 mb-3 notranslate"><table class="highlighttable"><tr><td class="linenos px-0 mx-0"><div class="linenodiv"><pre class="mb-0"> 1
|
||
2
|
||
3
|
||
4
|
||
5
|
||
6
|
||
7
|
||
8
|
||
9
|
||
10
|
||
11
|
||
12</pre></div></td><td class="code"><div class="highlight bg-light"><pre class="mb-0"><span></span><span class="cm">/* Code Listing 4.18:</span>
|
||
<span class="cm"> Creating a DNS header and question to send to OpenDNS</span>
|
||
<span class="cm"> */</span>
|
||
|
||
<span class="cm">/* Set up the DNS question */</span>
|
||
<span class="n">dns_question_t</span> <span class="n">question</span><span class="p">;</span>
|
||
<span class="n">question</span><span class="p">.</span><span class="n">dnstype</span> <span class="o">=</span> <span class="n">htons</span> <span class="p">(</span><span class="mi">1</span><span class="p">);</span> <span class="cm">/* QTYPE 1=A */</span>
|
||
<span class="n">question</span><span class="p">.</span><span class="n">dnsclass</span> <span class="o">=</span> <span class="n">htons</span> <span class="p">(</span><span class="mi">1</span><span class="p">);</span> <span class="cm">/* QCLASS 1=IN */</span>
|
||
|
||
<span class="cm">/* DNS name format requires two bytes more than the length of the</span>
|
||
<span class="cm"> domain name as a string */</span>
|
||
<span class="n">question</span><span class="p">.</span><span class="n">name</span> <span class="o">=</span> <span class="n">calloc</span> <span class="p">(</span><span class="n">strlen</span> <span class="p">(</span><span class="n">hostname</span><span class="p">)</span> <span class="o">+</span> <span class="mi">2</span><span class="p">,</span> <span class="k">sizeof</span> <span class="p">(</span><span class="kt">char</span><span class="p">));</span>
|
||
</pre></div>
|
||
</td></tr></table></div>
|
||
<p>Recall the domain name formatting in <a class="reference external" href="UDPSockets.html#tbl4-7">Table 4.7</a> and <a class="reference external" href="UDPSockets.html#tbl4-9">Table 4.9</a>. Given a human
|
||
readable domain name, such as <code class="docutils literal notranslate"><span class="pre">www.charity.org</span></code>, the string is broken apart into distinct fields
|
||
based on the dot; in this case, the three fields are <code class="docutils literal notranslate"><span class="pre">"www"</span></code>, <code class="docutils literal notranslate"><span class="pre">"charity"</span></code>, and <code class="docutils literal notranslate"><span class="pre">"org"</span></code>. Within
|
||
the DNS question, each field is preceded by a one-byte value that indicates the length of the field.
|
||
The name is considered terminated once the null-byte is used to indicate a zero-length field. <a class="reference external" href="UDPSockets.html#cl4-19">Code
|
||
Listing 4.19</a> shows an algorithm to convert a human readable name into the DNS question
|
||
format. The code starts by copying the hostname into the second byte of the space allocated for the
|
||
name; the reason for this is to leave one byte of space for the length of the first field (which
|
||
will be 3 for <code class="docutils literal notranslate"><span class="pre">"www"</span></code>), which will be determined later. Throughout the rest of the algorithm the
|
||
prev pointer is used to keep track of the location of the byte where the current field’s length will
|
||
be stored. As such, prev is initialized to the first byte of the space for the name.</p>
|
||
<div class="highlight-c border border-dark rounded-lg bg-light px-0 mb-3 notranslate"><table class="highlighttable"><tr><td class="linenos px-0 mx-0"><div class="linenodiv"><pre class="mb-0"> 1
|
||
2
|
||
3
|
||
4
|
||
5
|
||
6
|
||
7
|
||
8
|
||
9
|
||
10
|
||
11
|
||
12
|
||
13
|
||
14
|
||
15
|
||
16
|
||
17
|
||
18
|
||
19
|
||
20
|
||
21
|
||
22
|
||
23
|
||
24
|
||
25</pre></div></td><td class="code"><div class="highlight bg-light"><pre class="mb-0"><span></span><span class="cm">/* Code Listing 4.19:</span>
|
||
<span class="cm"> Algorithm for converting a hostname string to DNS question fields</span>
|
||
<span class="cm"> */</span>
|
||
|
||
<span class="cm">/* Leave the first byte blank for the first field length */</span>
|
||
<span class="n">memcpy</span> <span class="p">(</span><span class="n">question</span><span class="p">.</span><span class="n">name</span> <span class="o">+</span> <span class="mi">1</span><span class="p">,</span> <span class="n">hostname</span><span class="p">,</span> <span class="n">strlen</span> <span class="p">(</span><span class="n">hostname</span><span class="p">));</span>
|
||
<span class="kt">uint8_t</span> <span class="o">*</span><span class="n">prev</span> <span class="o">=</span> <span class="p">(</span><span class="kt">uint8_t</span> <span class="o">*</span><span class="p">)</span> <span class="n">question</span><span class="p">.</span><span class="n">name</span><span class="p">;</span>
|
||
<span class="kt">uint8_t</span> <span class="n">count</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="cm">/* Used to count the bytes in a field */</span>
|
||
|
||
<span class="cm">/* Traverse through the name, looking for the . locations */</span>
|
||
<span class="k">for</span> <span class="p">(</span><span class="kt">size_t</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o"><</span> <span class="n">strlen</span> <span class="p">(</span><span class="n">hostname</span><span class="p">);</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span>
|
||
<span class="p">{</span>
|
||
<span class="cm">/* A . indicates the end of a field */</span>
|
||
<span class="k">if</span> <span class="p">(</span><span class="n">hostname</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">==</span> <span class="sc">'.'</span><span class="p">)</span>
|
||
<span class="p">{</span>
|
||
<span class="cm">/* Copy the length to the byte before this field, then</span>
|
||
<span class="cm"> update prev to the location of the . */</span>
|
||
<span class="o">*</span><span class="n">prev</span> <span class="o">=</span> <span class="n">count</span><span class="p">;</span>
|
||
<span class="n">prev</span> <span class="o">=</span> <span class="n">question</span><span class="p">.</span><span class="n">name</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="mi">1</span><span class="p">;</span>
|
||
<span class="n">count</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span>
|
||
<span class="p">}</span>
|
||
<span class="k">else</span>
|
||
<span class="n">count</span><span class="o">++</span><span class="p">;</span>
|
||
<span class="p">}</span>
|
||
<span class="o">*</span><span class="n">prev</span> <span class="o">=</span> <span class="n">count</span><span class="p">;</span>
|
||
</pre></div>
|
||
</td></tr></table></div>
|
||
<p>When the hostname is copied into the space for the question, the string still contains the dot characters. In the DNS question format, these dots are replaced by the lengths of the field that follows. Returning to the example of <code class="docutils literal notranslate"><span class="pre">www.charity.org</span></code>, the first dot should be replaced by 7, indicating the length of the field <code class="docutils literal notranslate"><span class="pre">"charity"</span></code>. The for-loop in <a class="reference external" href="UDPSockets.html#cl4-19">Code Listing 4.19</a> replaces the dots with the field name, by keeping prev pointing to the location of the dot preceding the current field. As such, once another dot is encountered, the code can update the byte where the previous dot is stored with the length of the field that just ended. The count variable is then reset to 0 (starting to count the length of a new field), and prev is updated to point to the new dot. When the loop ends, prev is still pointing to the location of the last dot, so its value can be modified with the length of the last field.</p>
|
||
<div class="topic border border-dark rounded-lg alert-danger px-2 mb-3">
|
||
<div class="figure align-left">
|
||
<a class="reference internal image-reference" href="_images/CSF-Images-BugWarning.png"><img alt="Decorative bug warning" src="_images/CSF-Images-BugWarning.png" style="width: 90%;" /></a>
|
||
</div>
|
||
<p class="topic-title first pt-2 mb-1">Bug Warning</p><hr class="mt-1" />
|
||
<p>The correctness of <a class="reference external" href="UDPSockets.html#cl4-19">Code Listing 4.19</a> relies on correct handling of two common mistakes
|
||
with pointers. First, it is important to distinguish between updating where in memory the prev
|
||
pointer is pointing <code class="docutils literal notranslate"><span class="pre">(prev</span> <span class="pre">=</span> <span class="pre">query</span> <span class="pre">+</span> <span class="pre">i</span> <span class="pre">+</span> <span class="pre">1)</span></code> and updating the value stored at that memory
|
||
location <code class="docutils literal notranslate"><span class="pre">(*prev</span> <span class="pre">=</span> <span class="pre">count)</span></code>. Typos involving the <code class="docutils literal notranslate"><span class="pre">*</span></code> are notorious sources of bugs with
|
||
pointers. The second critical dependency is the use of <code class="docutils literal notranslate"><span class="pre">calloc()</span></code> in <a class="reference external" href="UDPSockets.html#cl4-18">Code Listing 4.18</a> instead of <code class="docutils literal notranslate"><span class="pre">malloc()</span></code>. Using <code class="docutils literal notranslate"><span class="pre">calloc()</span></code> initializes the space that question.name
|
||
points to with all zeroes. Consequently, we do not need to explicitly null-terminate the string,
|
||
because there is already a zero there. Since <code class="docutils literal notranslate"><span class="pre">malloc()</span></code> does not guarantee initialization of the
|
||
allocated memory space, the byte that indicates the zero-length field might not actually store 0.
|
||
This could lead to incorrect behavior in the DNS processing, including buffer overflows at either
|
||
the client or server.</p>
|
||
</div>
|
||
<p>Once the header and question fields have been constructed, all that remains is to assemble these
|
||
bytes into a packet and send the request through the UDP socket. <a class="reference external" href="UDPSockets.html#cl4-20">Code Listing 4.20</a>
|
||
illustrates this procedure. First, the total packet length needs to be determined. DNS headers are
|
||
fixed size, but the questions are not. The length of the question is based on the extended length of
|
||
the hostname (including the byte for the first field’s length and the final null-terminating byte).
|
||
The question also contains two 16-bit values to indicate the <code class="docutils literal notranslate"><span class="pre">QTYPE</span></code> and <code class="docutils literal notranslate"><span class="pre">QCLASS</span></code>. Once the size
|
||
is determined and the space is dynamically allocated, the code concatenates all fields as necessary.
|
||
The header is copied in first, followed immediately by the <code class="docutils literal notranslate"><span class="pre">QNAME</span></code>, with the <code class="docutils literal notranslate"><span class="pre">QTYPE</span></code> and
|
||
<code class="docutils literal notranslate"><span class="pre">QCLASS</span></code> at the end. Since DNS is based on UDP for transport, the code must use <code class="docutils literal notranslate"><span class="pre">sendto()</span></code> to
|
||
deliver the message to the socket.</p>
|
||
<div class="highlight-c border border-dark rounded-lg bg-light px-0 mb-3 notranslate"><table class="highlighttable"><tr><td class="linenos px-0 mx-0"><div class="linenodiv"><pre class="mb-0"> 1
|
||
2
|
||
3
|
||
4
|
||
5
|
||
6
|
||
7
|
||
8
|
||
9
|
||
10
|
||
11
|
||
12
|
||
13
|
||
14
|
||
15
|
||
16
|
||
17
|
||
18
|
||
19
|
||
20
|
||
21
|
||
22
|
||
23
|
||
24</pre></div></td><td class="code"><div class="highlight bg-light"><pre class="mb-0"><span></span><span class="cm">/* Code Listing 4.20:</span>
|
||
<span class="cm"> Assembling the DNS header and question to send via a UDP packet</span>
|
||
<span class="cm"> */</span>
|
||
|
||
<span class="cm">/* Copy all fields into a single, concatenated packet */</span>
|
||
<span class="kt">size_t</span> <span class="n">packetlen</span> <span class="o">=</span> <span class="k">sizeof</span> <span class="p">(</span><span class="n">header</span><span class="p">)</span> <span class="o">+</span> <span class="n">strlen</span> <span class="p">(</span><span class="n">hostname</span><span class="p">)</span> <span class="o">+</span> <span class="mi">2</span> <span class="o">+</span>
|
||
<span class="k">sizeof</span> <span class="p">(</span><span class="n">question</span><span class="p">.</span><span class="n">dnstype</span><span class="p">)</span> <span class="o">+</span> <span class="k">sizeof</span> <span class="p">(</span><span class="n">question</span><span class="p">.</span><span class="n">dnsclass</span><span class="p">);</span>
|
||
<span class="kt">uint8_t</span> <span class="o">*</span><span class="n">packet</span> <span class="o">=</span> <span class="n">calloc</span> <span class="p">(</span><span class="n">packetlen</span><span class="p">,</span> <span class="k">sizeof</span> <span class="p">(</span><span class="kt">uint8_t</span><span class="p">));</span>
|
||
<span class="kt">uint8_t</span> <span class="o">*</span><span class="n">p</span> <span class="o">=</span> <span class="p">(</span><span class="kt">uint8_t</span> <span class="o">*</span><span class="p">)</span><span class="n">packet</span><span class="p">;</span>
|
||
|
||
<span class="cm">/* Copy the header first */</span>
|
||
<span class="n">memcpy</span> <span class="p">(</span><span class="n">p</span><span class="p">,</span> <span class="o">&</span><span class="n">header</span><span class="p">,</span> <span class="k">sizeof</span> <span class="p">(</span><span class="n">header</span><span class="p">));</span>
|
||
<span class="n">p</span> <span class="o">+=</span> <span class="k">sizeof</span> <span class="p">(</span><span class="n">header</span><span class="p">);</span>
|
||
|
||
<span class="cm">/* Copy the question name, QTYPE, and QCLASS fields */</span>
|
||
<span class="n">memcpy</span> <span class="p">(</span><span class="n">p</span><span class="p">,</span> <span class="n">question</span><span class="p">.</span><span class="n">name</span><span class="p">,</span> <span class="n">strlen</span> <span class="p">(</span><span class="n">hostname</span><span class="p">)</span> <span class="o">+</span> <span class="mi">1</span><span class="p">);</span>
|
||
<span class="n">p</span> <span class="o">+=</span> <span class="n">strlen</span> <span class="p">(</span><span class="n">hostname</span><span class="p">)</span> <span class="o">+</span> <span class="mi">2</span><span class="p">;</span> <span class="cm">/* includes 0 octet for end */</span>
|
||
<span class="n">memcpy</span> <span class="p">(</span><span class="n">p</span><span class="p">,</span> <span class="o">&</span><span class="n">question</span><span class="p">.</span><span class="n">dnstype</span><span class="p">,</span> <span class="k">sizeof</span> <span class="p">(</span><span class="n">question</span><span class="p">.</span><span class="n">dnstype</span><span class="p">));</span>
|
||
<span class="n">p</span> <span class="o">+=</span> <span class="k">sizeof</span> <span class="p">(</span><span class="n">question</span><span class="p">.</span><span class="n">dnstype</span><span class="p">);</span>
|
||
<span class="n">memcpy</span> <span class="p">(</span><span class="n">p</span><span class="p">,</span> <span class="o">&</span><span class="n">question</span><span class="p">.</span><span class="n">dnsclass</span><span class="p">,</span> <span class="k">sizeof</span> <span class="p">(</span><span class="n">question</span><span class="p">.</span><span class="n">dnsclass</span><span class="p">));</span>
|
||
|
||
<span class="cm">/* Send the packet to OpenDNS, then request the response */</span>
|
||
<span class="n">sendto</span> <span class="p">(</span><span class="n">socketfd</span><span class="p">,</span> <span class="n">packet</span><span class="p">,</span> <span class="n">packetlen</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="p">(</span><span class="k">struct</span> <span class="n">sockaddr</span> <span class="o">*</span><span class="p">)</span> <span class="o">&</span><span class="n">addr</span><span class="p">,</span>
|
||
<span class="p">(</span><span class="kt">socklen_t</span><span class="p">)</span> <span class="k">sizeof</span> <span class="p">(</span><span class="n">addr</span><span class="p">));</span>
|
||
</pre></div>
|
||
</td></tr></table></div>
|
||
</div>
|
||
<div class="section" id="processing-dns-query-responses">
|
||
<h2>4.6.5. Processing DNS Query Responses<a class="headerlink" href="UDPSockets.html#processing-dns-query-responses" title="Permalink to this headline">¶</a></h2>
|
||
<p>To receive the response from the DNS server, <a class="reference external" href="UDPSockets.html#cl4-21">Code Listing 4.21</a> starts by allocating and
|
||
clearing the contents of a 512-byte buffer in memory. The length of this buffer can be hard-coded in
|
||
this way, as the DNS specification mandates a maximum of 512 bytes for all messages. The actual
|
||
length of the received data is set when <code class="docutils literal notranslate"><span class="pre">recvfrom()</span></code> retrieves the response from the socket.</p>
|
||
<div class="highlight-c border border-dark rounded-lg bg-light px-0 mb-3 notranslate"><table class="highlighttable"><tr><td class="linenos px-0 mx-0"><div class="linenodiv"><pre class="mb-0"> 1
|
||
2
|
||
3
|
||
4
|
||
5
|
||
6
|
||
7
|
||
8
|
||
9
|
||
10</pre></div></td><td class="code"><div class="highlight bg-light"><pre class="mb-0"><span></span><span class="cm">/* Code Listing 4.21:</span>
|
||
<span class="cm"> Receiving a DNS header and confirming there were no errors</span>
|
||
<span class="cm"> */</span>
|
||
|
||
<span class="kt">socklen_t</span> <span class="n">length</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span>
|
||
<span class="kt">uint8_t</span> <span class="n">response</span><span class="p">[</span><span class="mi">512</span><span class="p">];</span>
|
||
<span class="n">memset</span> <span class="p">(</span><span class="o">&</span><span class="n">response</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">512</span><span class="p">);</span>
|
||
|
||
<span class="cm">/* Receive the response from OpenDNS into a local buffer */</span>
|
||
<span class="kt">ssize_t</span> <span class="n">bytes</span> <span class="o">=</span> <span class="n">recvfrom</span> <span class="p">(</span><span class="n">socketfd</span><span class="p">,</span> <span class="n">response</span><span class="p">,</span> <span class="mi">512</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="p">(</span><span class="k">struct</span> <span class="n">sockaddr</span> <span class="o">*</span><span class="p">)</span> <span class="o">&</span><span class="n">addr</span><span class="p">,</span> <span class="o">&</span><span class="n">length</span><span class="p">);</span>
|
||
</pre></div>
|
||
</td></tr></table></div>
|
||
<p>The response from the server (assuming the request is successfully processed) would consist of the
|
||
fixed-size header, a question field identical to that sent in the request, and an answer containing
|
||
the information from a resource record. The structure of the answer depends on several factors,
|
||
including the IP version (IPv4 or IPv6) and the type of record requested. That is, the responses for
|
||
address (<code class="docutils literal notranslate"><span class="pre">A</span></code>), namespace (<code class="docutils literal notranslate"><span class="pre">NS</span></code>), or canonical name (<code class="docutils literal notranslate"><span class="pre">CNAME</span></code>) records vary in structure. In
|
||
this scenario, we are requesting an IPv4 address, so the bytes in the request would match the
|
||
following <code class="docutils literal notranslate"><span class="pre">struct</span></code> definition.</p>
|
||
<div class="highlight-c border border-dark rounded-lg bg-light px-0 mb-3 notranslate"><table class="highlighttable"><tr><td class="linenos px-0 mx-0"><div class="linenodiv"><pre class="mb-0">1
|
||
2
|
||
3
|
||
4
|
||
5
|
||
6
|
||
7
|
||
8
|
||
9</pre></div></td><td class="code"><div class="highlight bg-light"><pre class="mb-0"><span></span><span class="cm">/* Structure of the bytes for an IPv4 answer */</span>
|
||
<span class="k">typedef</span> <span class="k">struct</span> <span class="p">{</span>
|
||
<span class="kt">uint16_t</span> <span class="n">compression</span><span class="p">;</span>
|
||
<span class="kt">uint16_t</span> <span class="n">type</span><span class="p">;</span>
|
||
<span class="kt">uint16_t</span> <span class="n">class</span><span class="p">;</span>
|
||
<span class="kt">uint32_t</span> <span class="n">ttl</span><span class="p">;</span>
|
||
<span class="kt">uint16_t</span> <span class="n">length</span><span class="p">;</span>
|
||
<span class="k">struct</span> <span class="n">in_addr</span> <span class="n">addr</span><span class="p">;</span>
|
||
<span class="p">}</span> <span class="n">__attribute__</span><span class="p">((</span><span class="n">packed</span><span class="p">))</span> <span class="n">dns_record_a_t</span><span class="p">;</span>
|
||
</pre></div>
|
||
</td></tr></table></div>
|
||
<div class="topic border border-dark rounded-lg alert-danger px-2 mb-3">
|
||
<div class="figure align-left">
|
||
<a class="reference internal image-reference" href="_images/CSF-Images-BugWarning.png"><img alt="Decorative bug warning" src="_images/CSF-Images-BugWarning.png" style="width: 90%;" /></a>
|
||
</div>
|
||
<p class="topic-title first pt-2 mb-1">Bug Warning</p><hr class="mt-1" />
|
||
<p>The use of <code class="docutils literal notranslate"><span class="pre">__attribute__((packed))</span></code> in this <code class="docutils literal notranslate"><span class="pre">struct</span></code> declaration is critical to tell the
|
||
compiler not to re-order the fields of the <code class="docutils literal notranslate"><span class="pre">struct</span></code> within the program. When reading data from
|
||
the network, the bytes will occur in a particular order. When we use a <code class="docutils literal notranslate"><span class="pre">struct</span></code> to impose a
|
||
logical meaning on those bytes in a program, we would expect the interpretation to look like
|
||
this:</p>
|
||
<div class="figure mb-2 align-center">
|
||
<a class="reference internal image-reference" href="_images/CSF-Images.4.0.1.png"><img class="p-3 mb-2 align-center border border-dark rounded-lg" alt="DNS structures are packed in a way that does not preserve word alignment" src="_images/CSF-Images.4.0.1.png" style="width: 50%;" /></a>
|
||
</div>
|
||
<p>However, compilers routinely re-order the fields in a <code class="docutils literal notranslate"><span class="pre">struct</span></code> to preserve <em>word alignment</em>,
|
||
trying to group the bytes into chunks of 32 bits as much as possible. In this case, many compilers
|
||
would swap the <code class="docutils literal notranslate"><span class="pre">ttl</span></code> and <code class="docutils literal notranslate"><span class="pre">length</span></code> fields, which would impose the wrong structure on the
|
||
sequence of bytes received from the network:</p>
|
||
<div class="figure mb-2 align-center">
|
||
<a class="reference internal image-reference" href="_images/CSF-Images.4.0.2.png"><img class="p-3 mb-2 align-center border border-dark rounded-lg" alt="Failing to declare a DNS record ``struct`` as packed can mislabel bytes due to word alignment" src="_images/CSF-Images.4.0.2.png" style="width: 50%;" /></a>
|
||
</div>
|
||
</div>
|
||
<p><a class="reference external" href="UDPSockets.html#cl4-22">Code Listing 4.22</a> shows how the client can take the received response and interpret it
|
||
correctly for an IPv4 A record. By casting the response as a <code class="docutils literal notranslate"><span class="pre">dns_header_t</span> <span class="pre">*</span></code> variable, the code
|
||
can refer to the fields within the header based on the struct declaration. By applying the <code class="docutils literal notranslate"><span class="pre">0xf</span></code>
|
||
bit mask, we can examine just the <code class="docutils literal notranslate"><span class="pre">RCODE</span></code> field of the flag to detect if an error occurs. If the
|
||
<code class="docutils literal notranslate"><span class="pre">RCODE</span></code> is 0, then the request was processed correctly. Next, we need to traverse through the
|
||
question field, which begins with the variable-length <code class="docutils literal notranslate"><span class="pre">QNAME</span></code>. The <code class="docutils literal notranslate"><span class="pre">start_of_name</span></code> pointer is
|
||
created to keep track of where the name starts. Each iteration of the loop determines where the next
|
||
field length byte will occur and replaces it with a dot, while calculating the total length of the
|
||
name.</p>
|
||
<div class="highlight-c border border-dark rounded-lg bg-light px-0 mb-3 notranslate"><table class="highlighttable"><tr><td class="linenos px-0 mx-0"><div class="linenodiv"><pre class="mb-0"> 1
|
||
2
|
||
3
|
||
4
|
||
5
|
||
6
|
||
7
|
||
8
|
||
9
|
||
10
|
||
11
|
||
12
|
||
13
|
||
14
|
||
15
|
||
16
|
||
17
|
||
18
|
||
19</pre></div></td><td class="code"><div class="highlight bg-light"><pre class="mb-0"><span></span><span class="cm">/* Code Listing 4.22:</span>
|
||
<span class="cm"> Checking the header and question name of the DNS response</span>
|
||
<span class="cm"> */</span>
|
||
|
||
<span class="n">dns_header_t</span> <span class="o">*</span><span class="n">response_header</span> <span class="o">=</span> <span class="p">(</span><span class="n">dns_header_t</span> <span class="o">*</span><span class="p">)</span><span class="n">response</span><span class="p">;</span>
|
||
<span class="n">assert</span> <span class="p">((</span><span class="n">ntohs</span> <span class="p">(</span><span class="n">response_header</span><span class="o">-></span><span class="n">flags</span><span class="p">)</span> <span class="o">&</span> <span class="mh">0xf</span><span class="p">)</span> <span class="o">==</span> <span class="mi">0</span><span class="p">);</span>
|
||
|
||
<span class="cm">/* Get a pointer to the start of the question name, and</span>
|
||
<span class="cm"> reconstruct it from the fields */</span>
|
||
<span class="kt">uint8_t</span> <span class="o">*</span><span class="n">start_of_name</span> <span class="o">=</span> <span class="p">(</span><span class="kt">uint8_t</span> <span class="o">*</span><span class="p">)</span> <span class="p">(</span><span class="n">response</span> <span class="o">+</span> <span class="k">sizeof</span> <span class="p">(</span><span class="n">dns_header_t</span><span class="p">));</span>
|
||
<span class="kt">uint8_t</span> <span class="n">total</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span>
|
||
<span class="kt">uint8_t</span> <span class="o">*</span><span class="n">field_length</span> <span class="o">=</span> <span class="n">start_of_name</span><span class="p">;</span>
|
||
<span class="k">while</span> <span class="p">(</span><span class="o">*</span><span class="n">field_length</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">)</span>
|
||
<span class="p">{</span>
|
||
<span class="cm">/* Restore the dot in the name and advance to next length */</span>
|
||
<span class="n">total</span> <span class="o">+=</span> <span class="o">*</span><span class="n">field_length</span> <span class="o">+</span> <span class="mi">1</span><span class="p">;</span>
|
||
<span class="o">*</span><span class="n">field_length</span> <span class="o">=</span> <span class="sc">'.'</span><span class="p">;</span>
|
||
<span class="n">field_length</span> <span class="o">=</span> <span class="n">start_of_name</span> <span class="o">+</span> <span class="n">total</span><span class="p">;</span>
|
||
<span class="p">}</span>
|
||
</pre></div>
|
||
</td></tr></table></div>
|
||
<p>Once we have determined the total length of the domain name in the question field, we can skip
|
||
directly to the resource records in the answer. Immediately after the while loop in <a class="reference external" href="UDPSockets.html#cl4-22">Code Listing
|
||
4.22</a>, the <code class="docutils literal notranslate"><span class="pre">field_length</span></code> pointer will be pointing to the null byte at the end of the
|
||
name. The records begin five bytes later, after the null byte, the <code class="docutils literal notranslate"><span class="pre">QTYPE</span></code>, and the <code class="docutils literal notranslate"><span class="pre">QCLASS</span></code>
|
||
fields. Casting the remaining bytes as a <code class="docutils literal notranslate"><span class="pre">dns_record_a_t</span> <span class="pre">*</span></code> allows <a class="reference external" href="UDPSockets.html#cl4-23">Code Listing 4.23</a>
|
||
to treat this data as an array of records. The fields of these records can then be cast using the
|
||
<code class="docutils literal notranslate"><span class="pre">struct</span></code> definition from above.</p>
|
||
<div class="highlight-c border border-dark rounded-lg bg-light px-0 mb-3 notranslate"><table class="highlighttable"><tr><td class="linenos px-0 mx-0"><div class="linenodiv"><pre class="mb-0"> 1
|
||
2
|
||
3
|
||
4
|
||
5
|
||
6
|
||
7
|
||
8
|
||
9
|
||
10
|
||
11
|
||
12
|
||
13
|
||
14</pre></div></td><td class="code"><div class="highlight bg-light"><pre class="mb-0"><span></span><span class="cm">/* Code Listing 4.23:</span>
|
||
<span class="cm"> Printing the DNS resource records returned</span>
|
||
<span class="cm"> */</span>
|
||
|
||
<span class="cm">/* Skip null byte, qtype, and qclass to get to first answer */</span>
|
||
<span class="n">dns_record_a_t</span> <span class="o">*</span><span class="n">records</span> <span class="o">=</span> <span class="p">(</span><span class="n">dns_record_a_t</span> <span class="o">*</span><span class="p">)</span> <span class="p">(</span><span class="n">field_length</span> <span class="o">+</span> <span class="mi">5</span><span class="p">);</span>
|
||
<span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o"><</span> <span class="n">ntohs</span> <span class="p">(</span><span class="n">response_header</span><span class="o">-></span><span class="n">ancount</span><span class="p">);</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span>
|
||
<span class="p">{</span>
|
||
<span class="n">printf</span> <span class="p">(</span><span class="s">"TYPE: %"</span> <span class="n">PRId16</span> <span class="s">"</span><span class="se">\n</span><span class="s">"</span><span class="p">,</span> <span class="n">ntohs</span> <span class="p">(</span><span class="n">records</span><span class="p">[</span><span class="n">i</span><span class="p">].</span><span class="n">type</span><span class="p">));</span>
|
||
<span class="n">printf</span> <span class="p">(</span><span class="s">"CLASS: %"</span> <span class="n">PRId16</span> <span class="s">"</span><span class="se">\n</span><span class="s">"</span><span class="p">,</span> <span class="n">ntohs</span> <span class="p">(</span><span class="n">records</span><span class="p">[</span><span class="n">i</span><span class="p">].</span><span class="n">class</span><span class="p">));</span>
|
||
<span class="n">printf</span> <span class="p">(</span><span class="s">"TTL: %"</span> <span class="n">PRIx32</span> <span class="s">"</span><span class="se">\n</span><span class="s">"</span><span class="p">,</span> <span class="n">ntohl</span> <span class="p">(</span><span class="n">records</span><span class="p">[</span><span class="n">i</span><span class="p">].</span><span class="n">ttl</span><span class="p">));</span>
|
||
<span class="n">printf</span> <span class="p">(</span><span class="s">"IPv4: %08"</span> <span class="n">PRIx32</span> <span class="s">"</span><span class="se">\n</span><span class="s">"</span><span class="p">,</span> <span class="n">ntohl</span> <span class="p">(</span><span class="n">records</span><span class="p">[</span><span class="n">i</span><span class="p">].</span><span class="n">addr</span><span class="p">));</span>
|
||
<span class="n">printf</span> <span class="p">(</span><span class="s">"IPv4: %s</span><span class="se">\n</span><span class="s">"</span><span class="p">,</span> <span class="n">inet_ntoa</span> <span class="p">(</span><span class="n">records</span><span class="p">[</span><span class="n">i</span><span class="p">].</span><span class="n">addr</span><span class="p">));</span>
|
||
<span class="p">}</span>
|
||
</pre></div>
|
||
</td></tr></table></div>
|
||
<p>The Extended Example for Chapter 5 combines all of the preceding code segments, along with some
|
||
additional statements for printing, into a single program to run as a basic DNS client. If this
|
||
program is compiled into the current directory as an executable called <code class="docutils literal notranslate"><span class="pre">dns</span></code>, the output would
|
||
look like the following when querying the address <code class="docutils literal notranslate"><span class="pre">example.com</span></code>. Note that this example only works
|
||
with some domain names, as our basic client only supports a limited subset of the required
|
||
functionality as defined in RFC 1034 and RFC 1035.</p>
|
||
<div class="highlight-none border border-dark rounded-lg bg-light px-2 mb-3 notranslate"><div class="highlight bg-light"><pre class="mb-0"><span></span>$ ./dns example.com
|
||
Lookup example.com
|
||
1234 0100 0001 0000 0000 0000 0765 7861
|
||
6d70 6c65 0363 6f6d 0000 0100 01
|
||
Received 45 bytes from 208.67.222.222:
|
||
1234 8180 0001 0001 0000 0000 0765 7861
|
||
6d70 6c65 0363 6f6d 0000 0100 01c0 0c00
|
||
0100 0100 00e9 4900 045d b8d8 22
|
||
TYPE: 1
|
||
CLASS: 1
|
||
TTL: e949
|
||
IPv4: 5db8d822
|
||
IPv4: 93.184.216.34
|
||
</pre></div>
|
||
</div>
|
||
<table class="docutils footnote" frame="void" id="f27" rules="none">
|
||
<colgroup><col class="label" /><col /></colgroup>
|
||
<tbody valign="top">
|
||
<tr><td class="label"><a class="fn-backref" href="UDPSockets.html#id1">[1]</a></td><td>The domain name and IP address for <code class="docutils literal notranslate"><span class="pre">www.charity.org</span></code> are fictional and provided for
|
||
illustrative purposes only. The addresses 198.41.0.4 and 199.19.56.1 are the real addresses for the
|
||
root and .org TLD name servers, however.</td></tr>
|
||
</tbody>
|
||
</table>
|
||
<table class="docutils footnote" frame="void" id="f28" rules="none">
|
||
<colgroup><col class="label" /><col /></colgroup>
|
||
<tbody valign="top">
|
||
<tr><td class="label"><a class="fn-backref" href="UDPSockets.html#id2">[2]</a></td><td>The Internet Assigned Name Authority (IANA) is one portion of ICANN. IANA maintains
|
||
<code class="docutils literal notranslate"><span class="pre">example.com</span></code> specifically as a public resource for illustrating DNS functioning.</td></tr>
|
||
</tbody>
|
||
</table>
|
||
<table class="docutils footnote" frame="void" id="f29" rules="none">
|
||
<colgroup><col class="label" /><col /></colgroup>
|
||
<tbody valign="top">
|
||
<tr><td class="label"><a class="fn-backref" href="UDPSockets.html#id5">[3]</a></td><td>The DNS specification prepends a <code class="docutils literal notranslate"><span class="pre">"Q"</span></code> to the beginning of field names to indicate that
|
||
the field is for a query, even though the distinction has no practical impact for basic queries.
|
||
Hence, the reader should treat <code class="docutils literal notranslate"><span class="pre">NAME</span></code> and <code class="docutils literal notranslate"><span class="pre">QNAME</span> <span class="pre">``</span> <span class="pre">as</span> <span class="pre">the</span> <span class="pre">same,</span> <span class="pre">likewise</span> <span class="pre">for</span> <span class="pre">``CLASS</span></code> and
|
||
<code class="docutils literal notranslate"><span class="pre">QCLASS</span></code>, and so on.</td></tr>
|
||
</tbody>
|
||
</table>
|
||
<table class="docutils footnote" frame="void" id="f30" rules="none">
|
||
<colgroup><col class="label" /><col /></colgroup>
|
||
<tbody valign="top">
|
||
<tr><td class="label"><a class="fn-backref" href="UDPSockets.html#id9">[4]</a></td><td>Linux contains similar structs in <code class="docutils literal notranslate"><span class="pre"><arpa/nameser.h></span></code> and <code class="docutils literal notranslate"><span class="pre"><arpa/nameser_compat.h></span></code>,
|
||
but they are more complex than shown here. For instance, the Linux version contains names to access
|
||
the individual bits of the <code class="docutils literal notranslate"><span class="pre">flags</span></code> field.</td></tr>
|
||
</tbody>
|
||
</table>
|
||
<table class="docutils footnote" frame="void" id="f31" rules="none">
|
||
<colgroup><col class="label" /><col /></colgroup>
|
||
<tbody valign="top">
|
||
<tr><td class="label"><a class="fn-backref" href="UDPSockets.html#id10">[5]</a></td><td>By using OpenDNS in this scenario, we can illustrate the full process of the network
|
||
request, including setting up the UDP socket with an IP address that is functional as of this
|
||
writing. OpenDNS also provides a number of other benefits, such as increased privacy and security
|
||
services. For more information, consult their site at <code class="docutils literal notranslate"><span class="pre">https://www.opendns.com</span></code>.</td></tr>
|
||
</tbody>
|
||
</table>
|
||
<div
|
||
id="AppUDPSumm"
|
||
class="embedContainer"
|
||
data-exer-name="AppUDPSumm"
|
||
data-long-name="UDP socket programming questions"
|
||
data-short-name="AppUDPSumm"
|
||
data-frame-src="../../../Exercises/Sockets/AppUDPSumm.html?selfLoggingEnabled=false&localMode=true&module=UDPSockets&JXOP-debug=true&JOP-lang=en&JXOP-code=java"
|
||
data-frame-width="950"
|
||
data-frame-height="550"
|
||
data-external="false"
|
||
data-points="1.0"
|
||
data-required="True"
|
||
data-showhide="show"
|
||
data-threshold="5"
|
||
data-type="ka"
|
||
data-exer-id="">
|
||
|
||
<div class="center">
|
||
<div id="AppUDPSumm_iframe"></div>
|
||
</div>
|
||
</div>
|
||
</div>
|
||
</div>
|
||
|
||
|
||
</div>
|
||
|
||
|
||
|
||
<div class="container">
|
||
|
||
<div class="mt-4 container center">
|
||
«  <a id="prevmod1" href="TCPSockets.html">4.5. TCP Socket Programming: HTTP</a>
|
||
  ::  
|
||
<a class="uplink" href="index.html">Contents</a>
|
||
  ::  
|
||
<a id="nextmod1" href="AppBroadcast.html">4.7. Application-Layer Broadcasting: DHCP</a>  »
|
||
</div>
|
||
|
||
|
||
</div>
|
||
|
||
<br />
|
||
|
||
<div class="row jmu-dark-purple-bg">
|
||
<div class="col-md-12">
|
||
<center>
|
||
<a id="contact_us" class="btn button-link-no-blue jmu-gold" rel="nofollow" href="mailto:webmaster@opencsf.org" role="button">Contact Us</a>
|
||
<a id="license" class="btn button-link-no-blue jmu-gold" rel="nofollow" href="https://w3.cs.jmu.edu/kirkpams/OpenCSF/lib/license.html" target="_blank">License</a>
|
||
</center>
|
||
</div>
|
||
</div>
|
||
|
||
|
||
|
||
|
||
|
||
|
||
<script src="_static/js/popper.js-1.14.7-min.js" integrity="sha384-UO2eT0CpHqdSJQ6hJty5KVphtPhzWj9WO1clHTMGa3JDZwrnQq4sF86dIHNDz0W1" crossorigin="anonymous"></script>
|
||
<script src="_static/js/bootstrap.min.js" integrity="sha384-JjSmVgyd0p3pXB1rRibZUAYoIIy6OrQ6VrjIEaFf/nJGzIxFDsf4x0xIM+B07jRM" crossorigin="anonymous"></script>
|
||
</body>
|
||
</html> |