One document matched: draft-ietf-lwig-coap-00.xml
<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" href="rfc2629.xslt" ?>
<!DOCTYPE rfc SYSTEM "rfc2629.dtd" [
]>
<rfc ipr="trust200902" docName="draft-ietf-lwig-coap-00" category="info">
<?rfc toc="yes"?>
<?rfc tocdepth="3"?>
<?rfc sortrefs="yes"?>
<?rfc symrefs="yes"?>
<front>
<title>CoAP Implementation Guidance</title>
<author initials="M." surname="Kovatsch" fullname="Matthias Kovatsch">
<organization>ETH Zurich</organization>
<address>
<postal>
<street>Universitätstrasse 6</street>
<city>CH-8092 Zurich</city>
<country>Switzerland</country>
</postal>
<email>kovatsch@inf.ethz.ch</email>
</address>
</author>
<author initials="O." surname="Bergmann" fullname="Olaf Bergmann">
<organization>Universitaet Bremen TZI</organization>
<address>
<postal>
<street>Postfach 330440</street>
<city>D-28359 Bremen</city>
<country>Germany</country>
</postal>
<email>bergmann@tzi.org</email>
</address>
</author>
<author initials="E." surname="Dijk" fullname="Esko Dijk">
<organization>Philips Research</organization>
<address>
<email>esko.dijk@philips.com</email>
</address>
</author>
<author initials="X." surname="He" fullname="Xuan He">
<organization>Hitachi (China) R&D Corp.</organization>
<address>
<postal>
<street>301, Tower C North, Raycom, 2 Kexuyuan Nanlu</street>
<city>Beijing, 100190</city>
<country>P.R.China</country>
</postal>
<email>xhe@hitachi.cn</email>
</address>
</author>
<author initials="C." surname="Bormann" fullname="Carsten Bormann" role="editor">
<organization>Universitaet Bremen TZI</organization>
<address>
<postal>
<street>Postfach 330440</street>
<city>D-28359 Bremen</city>
<country>Germany</country>
</postal>
<phone>+49-421-218-63921</phone>
<email>cabo@tzi.org</email>
</address>
</author>
<date year="2014" month="April" day="01"/>
<area>Internet</area>
<workgroup>LWIG Working Group</workgroup>
<keyword>Internet-Draft</keyword>
<abstract>
<t>The Constrained Application Protocol (CoAP) is designed for
resource-constrained nodes and networks, e.g., sensor nodes in a low-power
lossy network (LLN). Yet to implement this Internet protocol on
Class 1 devices (i.e., ~ 10 KiB of RAM and ~ 100 KiB of ROM) also lightweight
implementation techniques are necessary. This document provides
lessons learned from implementing CoAP for tiny, battery-operated networked
embedded systems. In particular, it provides guidance on correct implementation
of the CoAP specification <xref target="I-D.ietf-core-coap"/>, memory optimizations, and
customized protocol parameters.</t>
</abstract>
</front>
<middle>
<section anchor="introduction" title="Introduction">
<t>The Constrained Application Protocol <xref target="I-D.ietf-core-coap"/> has been designed
specifically for machine-to-machine communication in networks with very
constrained nodes. Typical application scenarios therefore include building
automation, process optimization, and the Internet of Things. The major design
objectives have been set on small protocol overhead, robustness against packet
loss, and against high latency induced by small bandwidth shares or slow
request processing in end nodes. To leverage integration of constrained nodes
with the world-wide Internet, the protocol design was led by the REST
architectural style that accounts for the scalability and robustness of the
Hypertext Transfer Protocol <xref target="RFC2616"/>.</t>
<t>Lightweight implementations benefit from this design in many
respects: First, the use of Uniform Resource Identifiers (URIs) for
naming resources and the transparent forwarding of their
representations in a server-stateless request/response protocol make
protocol translation to HTTP a straightforward task. Second, the
set of protocol elements that are unavoidable for the core protocol
and thus must be implemented on every node has been kept very small,
minimizing the unnecessary accumulation of “optional” features. Options
that – when present – are critical for message processing are
explicitly marked as such to force immediate rejection of messages
with unknown critical options. Third, the syntax of protocol data
units is easy to parse and is carefully defined to avoid creation of
state in servers where possible.</t>
<t>Although these features enable lightweight implementations of the
Constrained Application Protocol, there is still a tradeoff between
robustness and latency of constrained nodes on one hand and resource
demands on the other.
For constrained nodes of Class 1 or even Class 2, the most limiting
factors usually are dynamic memory needs, static code size, and energy.
Most implementations therefore need to optimize internal buffer usage,
omit idle protocol feature, and maximize sleeping cycles.</t>
<t>The present document gives possible strategies to solve this tradeoff
for very constrained nodes (i.e., Class 1 in <xref target="I-D.ietf-lwig-terminology"/>).
For this, it provides guidance on correct implementation of the
CoAP specification <xref target="I-D.ietf-core-coap"/>, memory optimizations, and
customized protocol parameters.</t>
</section>
<section anchor="protocol-implementation" title="Protocol Implementation">
<t>In the programming styles supported by very simple operating systems as
found on constrained nodes, preemptive multi-threading is not an option.
Instead, all operations are triggered by an event loop system, e.g.,
in a send-receive-dispatch cycle.
It is also common practice to allocate memory statically to ensure stable
behavior, as no memory management unit (MMU) or other abstractions are
available. For a CoAP node, the two key parameters for memory usage are
the number of (re)transmission buffers and the maximum message size that
must be supported by each buffer. Often the maximum message size is set
far below the 1280-byte MTU of 6LoWPAN to allow more than one open Confirmable
transmission at a time (in particular for parallel observe notifications).
Note that implementations on constrained platforms often not even
support the full MTU. Larger messages must then use blockwise
transfers <xref target="I-D.ietf-core-block"/>, while a good tradeoff between
6LoWPAN fragmentation and CoAP header overhead must be found.
Usually the amount of available free RAM dominates this decision.
For Class 1 devices, the maximum message size is typically 128 or 256
bytes (blockwise) payload plus an estimate of the maximum header size
with a worst case option setting.</t>
<section anchor="client-server" title="Client/Server Model">
<t>In general, CoAP servers can be implemented more efficiently than clients.
REST allows them to keep the communication stateless and piggy-backed
responses are not stored for retransmission, saving buffer space.
The use of idempotent requests also allows to relax deduplication, which
further decreases memory usage.
It is also easy to estimate the required maximum size of message buffers,
since URI paths, supported options, and maximum payload sizes of the
application are known at compile time. Hence, when the application is
distributed over constrained and unconstrained nodes, the constrained ones
should preferably have the server role.</t>
<t>HTTP-based applications have established an inverse model because of the
need for simple push notifications: A constrained client uses POST requests
to update resources on an unconstrained server whenever an event, e.g., a
new sensor reading, is triggered. This requirement is solved by the Observe
option <xref target="I-D.ietf-core-observe"/> of CoAP. It allows servers to initiate
communication and send push notifications to interested client nodes. This
allows a more efficient and also more natural model for CoAP-based
applications, where the information source is in server role and can benefit
from caching.</t>
</section>
<section anchor="message-processing" title="Message Processing">
<t>Apart from the required buffers, message processing is symmetric for clients
and servers. First the 4-byte base header has to be parsed and thereby checked
if it is a CoAP message. Since the encoding is very dense, only a wrong
Version or a datagram size smaller than four bytes identify non-CoAP
datagrams. These MUST be silently ignored. All other message format errors,
such as an incomplete datagram length or the usage of reserved values, MUST be
rejected with a Reset (RST) message. Next the Token is read based on the TKL
field. For the following header options, there are two alternatives: Either
process the header on the fly when an option is accessed or initially parse
all values into an internal data structure.</t>
<section anchor="on-the-fly-processing" title="On-the-fly Processing">
<t>The advantage of on-the-fly processing is that no additional memory needs to
be allocated to store the option values, which are stored efficiently inline
in the buffer for incoming messages. Once the message is
accepted for further processing, the set of options contained in the received
message must be decoded to check for unknown critical options. To avoid
multiple passes through the option list, the option parser might maintain a
bit-vector where each bit represents an option number that is present in the
received request. With the wide and sparse range of option numbers, the number
itself cannot be used to indicate the number of left-shift operations to mask
the corresponding bit. Hence, an implementation-specific enum of supported
options should be used to mask the present options of a message in the bitmap.
In addition, the byte index of every option (a direct pointer) can be added
to a sparse list (e.g., a one-dimensional array) for fast retrieval.</t>
<t>This particularly enables efficient handling of options that might occur more
than once such as Uri-Path. In this implementation strategy, the delta is zero
for any subsequent path segment, hence the stored byte index for this option
(e.g., 11 for Uri-Path) would be overwritten to hold a pointer to only the last
occurrence of that option. The Uri-Path can be resolved on the fly, though,
and a pointer to the targeted resource stored directly in the sparse list.
In simpler cases, conditionals can preselect one of the repeated option values. </t>
<t>Once the option list has been processed, all known critical option and all
elective options can be masked out in the bit-vector to determine if any
unknown critical option was present. If this is the case, this information can
be used to create a 4.02 response accordingly. Note that full processing must
only be done up to the highest supported option number. Beyond that, only the
least significant bit (Critical or Elective) needs to be checked. Otherwise,
if all critical options are supported, the sparse list of option pointers is
used for further handling of the message.</t>
</section>
<section anchor="internal-data-structure" title="Internal Data Structure">
<t>Using an internal data structure for all parsed options has advantage when
working on the option values, as they are already in a variable of
corresponding type, e.g., an integer in host byte order. The incoming payload
and byte strings of the header can be accessed directly in the buffer for
incoming messages using pointers (similar to on-the-fly processing). This
approach also benefits from a bitmap. Otherwise special values must be
reserved to encode an unset option, which might require a larger type than
required for the actual value range (e.g., a 32-bit integer instead of 16-bit).</t>
<t>The byte strings (e.g., the URI) are usually not required when generating the
response. And since all important values were copied, this alternative
facilitates using the buffer for incoming messages also for the assembly of
outgoing messages – which can be the shared IP buffer provided by the OS.</t>
<t>Setting options for outgoing messages is also easier with an internal data
structure. Application developers can set options independent from the option
number, whose order is required for the delta encoding. The CoAP encoding is
then applied in a serialization step before sending. In contrast, assembling
outgoing messages with on-the-fly processing requires either extensive memmove
operations to insert new header options or restrictions for developers to set
options in their correct order.</t>
</section>
</section>
<section anchor="duplicate-rejection" title="Duplicate Rejection">
<t>If CoAP is used directly on top of UDP (i.e., in NoSec mode), it needs to cope
with the fact that the UDP datagram transport can reorder and duplicate
messages. (In contrast to UDP, DTLS has its own duplicate detection.) CoAP has
been designed with protocol functionality such that rejection of duplicate
messages is always possible. It is at the discretion of the receiver if it
actually wants to make use of this functionality. Processing of duplicate
messages comes at a cost, but so does the management of the state associated
with duplicate rejection. The number of remote endpoints that need to be
managed might be vast. This can be costly in particular for unconstrained
nodes that have throughput in the order of one hundred thousand requests per
second (i.e., about 16 GiB of RAM only for duplicate rejection). Deduplication
is also heavy for servers on Class 1 devices, as also piggy-backed responses
need to be stored for the case that the ACK message is lost.
Hence, a receiver may have good reasons to decide not to do the deduplication.</t>
<t>If duplicate rejection is indeed necessary, e.g., for non-idempotent
requests, it is important to control the amount of state that needs to
be stored. It can be reduced for instance by deduplication at resource level:
Knowledge of the application and supported representations can minimize the
amount of state that needs to be kept. Duplicate rejection on the client side
can be simplified by choosing clever Tokens and only filter based on this
information (e.g., a list of Tokens currently in use or an obscured counter
in the Token value).</t>
</section>
<section anchor="token-usage" title="Token Usage">
<t>Tokens are chosen by the client and help to identify request/response pairs
that span several messages (e.g., a separate response, which has a new MID).
Servers do not generate Tokens and only mirror what they receive from the
clients. Tokens must be unique within the namespace of a client throughout their
lifetime. This begins when being assigned to a request and ends when the open
request is closed by receiving and matching the final response. Neither empty
ACKs nor notifications (i.e., responses carrying the Observe option) terminate
the lifetime of a Token.</t>
<t>As already mentioned, a clever assignment of Tokens can help to simplify
duplicate rejection. Yet this is also important for coping with client crashes.
When a client restarts during an open request and (unknowingly) re-uses the
same Token, it might match the response from the previous request to the
current one. Hence, when only the Token is used for matching, which is always
the case for separate responses, randomized Tokens with enough entropy should
be used. The 8-byte range for Tokens even allows for one-time usage throughout
the lifetime of a client node. When DTLS is used, client crashes/restarts
will lead to a new security handshake, thereby solving the problem of
mismatching responses and/or notifications.</t>
<section anchor="tokens-for-observe" title="Tokens for Observe">
<t>In the case of Observe <xref target="I-D.ietf-core-observe"/>, a request will be answered
with multiple notifications and it can become hard to determine the end of
a Token lifetime. When establishing an Observe relationship, the Token is
registered at the server. Hence, the client partially loses control of the used
Token. A client can attempt to cancel the relationship, which frees the Token
upon success (i.e., the message with code 7.31 is acknowledged; see
<xref target="I-D.ietf-core-observe"/> section 3.6). However, the client might never
receive the ACK due to a temporary network outages or worse, a server crash.
Although a network outage will also affect notifications so that the Observe
garbage collection could apply, the server might simply not send CON
notifications during that time. Alternative Observe lifetime models such as
Stubbornness(tm) might also keep relationships alive for longer periods.</t>
<t>Thus, Observe requests should never use the empty Token, but carefully chose
the value. One option is to assign and re-use dedicated Tokens for each Observe
relationship the client will establish. This is, however, critical for spoofing
attacks in NoSec mode. The recommendation is to use randomized Tokens with a
length of at least four bytes. Thus, dedicated ranges within the 8-byte Token
space should be used when in NoSec mode. This also solves the problem of
mismatching notifications after a client crash/restart.</t>
</section>
<section anchor="tokens-for-blockwise-transfers" title="Tokens for Blockwise Transfers">
<t>In general, blockwise transfers are independent from the Token and are
correlated through client endpoint address and server address and resource path
(destination URI). Thus, each block may be transferred using a different Token.
Still it can be beneficial to use the same Token (it is freed upon reception
of a response block) for all blocks, e.g., to easily route received blocks to
the same response handler.</t>
<t>Special care has to be taken when Block2 is combined with Observe.
Notifications only carry the first block and it is up to the client to retrieve
the remaining ones. These GET requests do not carry the Observe option and MUST
use a different Token, since the Token from the notification is still in use.</t>
</section>
</section>
<section anchor="fsms" title="Transmission States">
<t>CoAP endpoints must keep transmission state to manage open requests, to handle
the different response modes, and to implement reliable delivery at the message
layer. The following finite state machines (FSMs) model the transmissions of a
CoAP exchange at the request/response layer and the message layer. These layers
are linked through actions. The M_CMD() action triggers a corresponding
transition at the message layer and the RR_EVT() action triggers a transition
at the request/response layer. The FSMs also use guard conditions to
distinguish between information that is only available through the other layer
(e.g., whether a request was sent using a CON or NON message).</t>
<section anchor="requestresponse-layer" title="Request/Response Layer">
<t><xref target="fsm_rr_c"/> depicts the two states at the request/response layer of a
CoAP client. When a request is issued, a “reliable_send” or “unreliable_send”
is triggered at the message layer. The WAITING state can be left through three
transitions: Either the client cancels the request and triggers cancellation of
a CON transmission at the message layer, the client receives a failure event
from the message layer, or a receive event containing a response.</t>
<figure title="CoAP Client Request/Response Layer FSM" anchor="fsm_rr_c"><artwork><![CDATA[
+------------CANCEL-------------------------------+
| / M_CMD(cancel) |
| V
| +------+
+-------+ -------RR_EVT(fail)--------------------> | |
|WAITING| | IDLE |
+-------+ -------RR_EVT(rx)[is Response]---------> | |
^ / M_CMD(accept) +------+
| |
+--------------------REQUEST----------------------+
/ M_CMD((un)reliable_send)
]]></artwork></figure>
<t>A server resource can decide at the request/response layer whether to respond
with a piggy-backed or a separate response. Thus, there are two busy states in
<xref target="fsm_rr_s"/>, SERVING and SEPARATE. An incoming receive event with a NON
request directly triggers the transition to the SEPARATE state.</t>
<figure title="CoAP Server Request/Response Layer FSM" anchor="fsm_rr_s"><artwork><![CDATA[
+--------+ <----------RR_EVT(rx)[is NON]---------- +------+
|SEPARATE| | |
+--------+ ----------------RESPONSE--------------> | IDLE |
^ / M_CMD((un)reliable_send) | |
| +---> +------+
|EMPTY_ACK | |
|/M_CMD(accept) | |
| | |
| | |
+--------+ | |
|SERVING | --------------RESPONSE------------+ |
+--------+ / M_CMD(accept) |
^ |
+------------------------RR_EVT(rx)[is CON]--------+
]]></artwork></figure>
</section>
<section anchor="message-layer" title="Message Layer">
<t><xref target="fsm_m"/> shows the different states of a CoAP endpoint per message exchange.
Besides the linking action RR_EVT(), the message layer has a TX action to send
a message. For sending and receiving NONs, the endpoint remains in its CLOSED
state. When sending a CON, the endpoint remains in RELIABLE_TX and keeps
retransmitting until the transmission times out, it receives a matching RST,
the request/response layer cancels the transmission, or the endpoint receives
an implicit acknowledgement through a matching NON or CON. Whenever the
endpoint receives a CON, it transitions into the ACK_PENDING state, which can
be left by sending the corresponding ACK.</t>
<figure title="CoAP Message Layer FSM" anchor="fsm_m"><artwork><![CDATA[
+-----------+ <-------M_CMD(reliable_send)-----+
| | / TX(con) \
| | +--------------+
| | ---TIMEOUT(RETX_WINDOW)------> | |
|RELIABLE_TX| / RR_EVT(fail) | |
| | ---------------------RX_RST--> | | <----+
| | / RR_EVT(fail) | | |
+-----------+ ----M_CMD(cancel)------------> | CLOSED | |
^ | | \ \ | | --+ |
| | | \ +-------------------RX_ACK---> | | | |
+*1+ | \ / RR_EVT(rx) | | | |
| +----RX_NON-------------------> +--------------+ | |
| / RR_EVT(rx) ^ ^ ^ ^ | | | | | |
| | | | | | | | | | |
| | | | +*2+ | | | | |
| | | +--*3--+ | | | |
| | +----*4----+ | | |
| +------*5------+ | |
| +---------------+ | |
| | ACK_PENDING | <--RX_CON-------------+ |
+----RX_CON----> | | / RR_EVT(rx) |
/ RR_EVT(rx) +---------------+ ---------M_CMD(accept)---+
/ TX(ack)
*1: TIMEOUT(RETX_TIMEOUT) / TX(con)
*2: M_CMD(unreliable_send) / TX(non)
*3: RX_NON / RR_EVT(rx)
*4: RX_RST / REMOVE_OBSERVER
*5: RX_ACK
]]></artwork></figure>
<t>T.B.D.: (i) Rejecting messages (can be triggered at message and request/response
layer). (ii) ACKs can also be triggered at both layers.</t>
<!--
## Taxonomy of Cases
MK:
This section was removed, as it is unclear whether it is needed.
Maybe single interesting cases can be picked for further explanation.
Restore the figures from the SVN (Rev. 12)
-->
</section>
</section>
<section anchor="out-of-band-information" title="Out-of-band Information">
<t>They CoAP implementation can also leverage out-of-band information, that might
also trigger some of the transitions shown in <xref target="fsms"/>. In particular ICMP
messages can inform about unreachable remote endpoints or whole network
outages. This information can be used to pause or cancel ongoing transmission
to conserve energy. Providing ICMP information to the CoAP implementation is
easier in constrained environments, where developers usually can adapt the
underlying OS (or firmware). This is not the case on general purpose platforms
that have full-fledged OSes and make use of high-level programming frameworks.</t>
<t>The most important ICMP messages are host, network, port, or protocol
unreachable errors. They should cause the cancellation of ongoing CON
transmissions and clearing of Observe relationships. Requests to this
destination should be paused for a sensible interval. In addition, the device
could indicate of this error through a notification to a management endpoint
or external status indicator, since the cause could be a misconfiguration or
general unavailability of the required service. Problems reported through the
Parameter Problem message are usually caused through a similar fundamental
problem.</t>
<t>The CoAP specification recommends to ignore Source Quench and Time Exceeded
ICMP messages, though. Source Quench messages inform the sender to reduce the
rate of packets. However, this mechanism is deprecated through <xref target="RFC6633"/>.
CoAP also comes with its own congestion control mechanism, which is already
designed conservatively. If an advanced mechanism is required to better
utilize the network, <xref target="I-D.bormann-core-cocoa"/> should be implemented. Time
Exceeded messages inform about possible routing loops or a too small initial
Hop Limit value. This is out of scope for CoAP implementations, though.</t>
</section>
<section anchor="programming-model" title="Programming Model">
<t>The event-driven approach, which is common in event-loop-based firmware, has
also proven very efficient for embedded operating systems <xref target="TinyOS"/>,
<xref target="Contiki"/>. Note that an OS is not necessarily required and a traditional
firmware approach can suffice for Class 1 devices. Event-driven systems use
split-phase operations (i.e., there are no blocking functions, but functions
return and an event handler is called once a long-lasting operation completes)
to enable cooperative multi-threading with a single stack.</t>
<t>Bringing a Web transfer protocol to constrained environments does not
only change the networking of the corresponding systems, but also the
programming model. The complexity of event-driven systems can be hidden
through APIs that resemble classic RESTful Web service implementations. </t>
<section anchor="client" title="Client">
<t>An API for asynchronous requests with response handler functions goes
hand-in-hand with the event-driven approach. Synchronous requests with a
blocking send function can facilitate applications that require strictly
ordered, sequential request execution (e.g., to control a physical process) or
other checkpointing (e.g., starting operation only after registration with the
resource directory was successful). However, this can also be solved by
triggering the next operation in the response handlers. Furthermore, as
mentioned in <xref target="client-server"/>, it is more like that complex control flow is
done by more powerful devices and Class 1 devices predominantly run a CoAP
server (which might include a minimal client to communicate with a resource
directory).</t>
</section>
<section anchor="server" title="Server">
<t>On CoAP servers, the event-driven nature can be hidden through resource handler
abstractions as known from traditional REST frameworks. The following types of
RESTful resources have proven useful to provide an intuitive API on constrained
event-driven systems:</t>
<t><list style='hanging'>
<t hangText='NORMAL'>
A normal resource defined by a static Uri-Path and an associated resource
handler function. Allowed methods could already be filtered by the
implementation based on flags. This is the basis for all other resource
types.</t>
<t hangText='PARENT'>
A parent resource manages several sub-resources under a given base path
by programmatically evaluating the Uri-Path. Defining a URI template (see
<xref target="RFC6570"/>) would be a convenient way to pre-parse arguments given
in the Uri-Path.</t>
<t hangText='PERIODIC'>
A resource that has an additional handler function that is
triggered periodically by the CoAP implementation with a resource-specific
interval. It can be used to sample a sensor or perform
similar periodic updates of its state. Usually, a periodic resource is
observable and sends the notifications by triggering its normal resource
handler from the periodic handler. These periodic tasks are quite common
for sensor nodes, thus it makes sense to provide this functionality in the
CoAP implementation and avoid redundant code in every resource.</t>
<t hangText='EVENT'>
An event resource is similar to an periodic resource, only
that the second handler is called by an irregular event such as a
button.</t>
<t hangText='SEPARATE'>
Separate responses are usually used when handling a request takes more time,
e.g., due to a slow sensor or UART-based subsystems. To not fully block the
system during this time, the handler should also employ split-phase execution:
The resource handler returns as soon as possible and an event handler resumes
responding when the result is ready. The separate resource type can abstract
from the split-phase operation and take care of temporarily storing the
request information that is required later in the result handler to send the
response (e.g., source address and Token).</t>
</list></t>
</section>
</section>
</section>
<section anchor="optimizations" title="Optimizations">
<section anchor="message-buffers" title="Message Buffers">
<t>The cooperative multi-threading of an event loop system allows to optimize
memory usage through in-place processing and reuse of buffers, in particular
the IP buffer provided by the OS or firmware.</t>
<t>CoAP servers can significantly benefit from in-place processing, as
they can create responses directly in the incoming IP buffer. Note that an
embedded OS usually only has a single buffer for incoming and outgoing IP
packets.
The first few bytes of the basic header are usually parsed into
an internal data structure and can be overwritten without harm.
Thus, empty ACKs and RST messages can promptly be assembled and sent using
the IP buffer. Also when a CoAP server only sends piggy-backed or
Non-confirmable responses, no additional buffer is required at the application
layer. This, however, requires careful timing so that no incoming data is
overwritten before it was processed. Because of cooperative multi-threading,
this requirement is relaxed, though. Once the message is sent, the IP buffer
can accept new messages again. This does not work for Confirmable messages,
however. They need to be stored for retransmission and would block any
further IP communication.</t>
<t>Depending on the number of requests that can be handled in
parallel, an implementation might create a stub response filled with
any option that has to be copied from the original request to the
separate response, especially the Token option. The drawback of
this technique is that the server must be prepared to receive
retransmissions of the previous (Confirmable) request to which a new
acknowledgement must be generated. If memory is an issue, a single
buffer can be used for both tasks: Only the message type and code
must be updated, changing the message id is optional. Once the
resource representation is known, it is added as new payload at the
end of the stub response. Acknowledgements still can be sent as
described before as long as no additional options are required to
describe the payload.</t>
</section>
<section anchor="retransmissions" title="Retransmissions">
<t>CoAP’s reliable transmissions require the before-mentioned
retransmission buffers. Messages, such as the requests of a client,
should be stored in serialized form. For servers, retransmissions
apply for Confirmable separate responses and Confirmable
notifications <xref target="I-D.ietf-core-observe"/>. As separate responses stem
from long-lasting resource handlers, the response should be stored
for retransmission instead of re-dispatching a stored request (which
would allow for updating the representation). For Confirmable
notifications, please see Section 2.6, as simply storing the response
can break the concept of eventual consistency.</t>
<t>String payloads such as JSON require a buffer to print to. By
splitting the retransmission buffer into header and payload part, it
can be reused. First to generate the payload and then storing the
CoAP message by serializing into the same memory. Thus, providing a
retransmission for any message type can save the need for a separate
application buffer. This, however, requires an estimation about the
maximum expected header size to split the buffer and a memmove to
concatenate the two parts.</t>
<t>For platforms that disable clock tick interrupts in sleep states, the
application must take into consideration the clock deviation that occurs
during sleep (or ensure to remain in idle state until the message has been
acknowledged or the maximum number of retransmissions is reached).
Since CoAP allows up to four retransmissions with a binary
exponential back-off it could take up to 45 seconds until the send
operation is complete. Even in idle state, this means substantial
energy consumption for low-power nodes. Implementers therefore
might choose a two-step strategy: First, do one or two
retransmissions and then, in the later phases of back-off, go to sleep
until the next retransmission is due. In the meantime, the node could
check for new messages including the acknowledgement for any
Confirmable message to send.</t>
</section>
<section anchor="observable-resources" title="Observable Resources">
<t>For each observer, the server needs to store at least address, port, token,
and the last outgoing message ID. The latter is needed to match incoming
RST messages and cancel the observe relationship.</t>
<t>It is favorable to have one retransmission buffer per observable resource
that is shared among all observers. Each notification is serialized once
into this buffer and only address, port, and token are changed when
iterating over the observer list (note that different token lengths
might require realignment). The advantage becomes clear for
Confirmable notifications: Instead of one retransmission buffer per
observer, only one buffer and only individual retransmission counters
and timers in the list entry need to be stored. When the
notifications can be sent fast enough, even a single timer would
suffice. Furthermore, per-resource buffers simplify the update with
a new resource state during open deliveries.</t>
</section>
<section anchor="blockwise-transfers" title="Blockwise Transfers">
<t>Blockwise transfers have the main purpose of providing fragmentation
at the application layer, where partial information can be processed.
This is not possible at lower layers such as 6LoWPAN, as only
assembled packets can be passed up the stack. While
<xref target="I-D.ietf-core-block"/> also anticipates atomic handling of blocks,
i.e., only fully received CoAP messages, this is not possible on
Class 1 devices.</t>
<t>When receiving a blockwise transfer, each blocks is usually passed to
a handler function that for instance performs stream processing or
writes the blocks to external memory such as flash. Although there
are no restrictions in <xref target="I-D.ietf-core-block"/>, it is beneficial for
Class 1 devices to only allow ordered transmission of blocks.
Otherwise on-the-fly processing would not be possible.</t>
<t>When sending a blockwise transfer, Class 1 devices usually do not
have sufficient memory to print the full message into a buffer, and
slice and send it in a second step. When transferring the CoRE Link
Format from /.well-known/core for instance, a generator function is
required that generates slices of a large string with a specific
offset length (a ‘sonprintf()’). This functionality is required
recurrently and should be included in a library.</t>
</section>
<section anchor="deduplication-with-sequential-mids" title="Deduplication with Sequential MIDs">
<t>CoAP’s duplicate rejection functionality can be straightforwardly
implemented in a CoAP
endpoint by storing, for each remote CoAP endpoint (“peer”) that it
communicates with, a list of recently received CoAP Message IDs (MIDs)
along with some timing information.
A CoAP message from a peer with a MID that is in the list for that peer
can simply be discarded.</t>
<t>The timing information in the list can then be used to time out
entries that are older than the <spanx style='emph'>expected extent of the re-ordering</spanx>,
an upper bound for which can be estimated by adding the <spanx style='emph'>potential
retransmission window</spanx> (<xref target="I-D.ietf-core-coap"/> section “Reliable
Messages”) and the time packets can stay alive in the network.</t>
<t>Such a straightforward implementation is suitable in case other CoAP
endpoints generate random MIDs. However, this storage method may
consume substantial RAM in specific cases, such as:</t>
<t><list style='symbols'>
<t>many clients are making periodic, non-idempotent requests to a
single CoAP server;</t>
<t>one client makes periodic requests to a large number of CoAP
servers and/or requests a large number of resources; where servers
happen to mostly generate separate CoAP responses (not piggy-backed);</t>
</list></t>
<t>For example, consider the first case where the expected extent of re-ordering
is 50 seconds, and N clients are sending periodic POST
requests to a single CoAP server during a period of high system
activity, each on average sending one client request per second.
The server would need 100 * N bytes of RAM to store the MIDs only.
This amount of RAM may be significant on a RAM-constrained
platform. On a number of platforms, it may be easier to allocate some
extra program memory (e.g. Flash or ROM) to the CoAP protocol handler
process than to allocate extra RAM. Therefore, one may try to reduce
RAM usage of a CoAP implementation at the cost of some additional
program memory usage and implementation complexity.</t>
<t>Some CoAP clients generate MID values by a using a Message ID variable
<xref target="I-D.ietf-core-coap"/> that is incremented by one each time a new MID
needs to be generated. (After the maximum value 65535 it wraps back
to 0.) We call this behavior “sequential” MIDs. One approach to
reduce RAM use exploits the redundancy in sequential MIDs for a more
efficient MID storage in CoAP servers.</t>
<t>Naturally such an approach requires, in order to actually reduce RAM
usage in an implementation, that a large part of the peers follow the
sequential MID behavior. To realize this optimization, the authors
therefore RECOMMEND that CoAP endpoint implementers employ the
“sequential MID” scheme if there are no reasons to prefer another
scheme, such as randomly generated MID values.</t>
<t>Security considerations might call for a choice for (pseudo)randomized
MIDs. Note however that with truly randomly generated MIDs the
probability of MID collision is rather high in use cases as mentioned
before, following from the Birthday Paradox. For example, in a
sequence of 52 randomly drawn 16-bit values the probability of finding
at least two identical values is about 2 percent.</t>
<t>From here on we consider efficient storage implementations for MIDs in
CoAP endpoints, that are optimized to store “sequential”
MIDs. Because CoAP messages may be lost or arrive out-of-order, a
solution has to take into
account that received MIDs of CoAP messages are not actually arriving
in a sequential fashion, due to lost or reordered messages. Also a
peer might reset and lose its MID counter(s) state. In addition, a
peer may have a single Message ID variable used in messages to many
CoAP endpoints it communicates with, which partly breaks
sequentiality from the receiving CoAP endpoint’s
perspective. Finally, some peers might use a randomly generated MID
values approach. Due to these specific conditions, existing sliding
window bitfield implementations for storing received sequence numbers
are typically not directly suitable for efficiently storing MIDs.</t>
<t><xref target="mid-store"/> shows one example for a per-peer MID storage design: a
table with a bitfield of a defined length <spanx style='emph'>K</spanx> per entry to store
received MIDs (one per bit) that have a value in the range
[MID_i + 1 , MID_i + K].</t>
<texttable title="A per-peer table for storing MIDs based on MID_i" anchor="mid-store">
<ttcol align='left'>MID base</ttcol>
<ttcol align='left'>K-bit bitfield</ttcol>
<ttcol align='left'>base time value</ttcol>
<c>MID_0</c>
<c>010010101001</c>
<c>t_0</c>
<c>MID_1</c>
<c>111101110111</c>
<c>t_1</c>
<c>… etc.</c>
<c> </c>
<c> </c>
</texttable>
<t>The presence of a table row with base MID_i (regardless of the
bitfield values) indicates that a value MID_i has been received at a
time t_i. Subsequently, each bitfield bit k (0…K-1) in a row i
corresponds to a received MID value of MID_i + k + 1. If a bit k is
0, it means a message with corresponding MID has not yet been
received. A bit 1 indicates such a message has been received already
at approximately time t_i. This storage structure allows e.g. with
k=64 to store in best case up to 130 MID values using 20 bytes, as
opposed to 260 bytes that would be needed for a non-sequential storage
scheme.</t>
<t>The time values t_i are used for removing rows from the table
after a preset timeout period, to keep the MID store small in size and
enable these MIDs to be safely re-used in future communications.
(Note that the table only stores one time value per row, which
therefore needs to be updated on receipt of another MID that is stored
as a single bit in this row. As a consequence of only storing one
time value per row, older MID entries typically time out later than
with a simple per-MID time value storage scheme. The endpoint
therefore needs to ensure that this additional delay before MID
entries are removed from the table is much smaller than the time
period after which a peer starts to re-use MID values due to
wrap-around of a peer’s MID variable. One solution is to check that a
value t_i in a table row is still recent enough, before using the row
and updating the
value t_i to current time. If not recent enough, e.g. older than N
seconds, a new row with an empty bitfield is
created.)
[Clearly, these optimizations would benefit if the peer were much more conservative about re-using MIDs than currently required in the protocol specification.]</t>
<t>The optimization described is less efficient for storing randomized
MIDs that a CoAP endpoint may encounter from certain peers. To solve
this, a storage algorithm may start in a simple MID storage mode,
first assuming that the peer produces non-sequential MIDs. While
storing MIDs, a heuristic is then applied based on monitoring some
“hit rate”, for example, the number of MIDs received that have a Most
Significant Byte equal to that of the previous MID divided by the
total number of MIDs received. If the hit rate tends towards 1 over a
period of time, the MID store may decide that this particular CoAP
endpoint uses sequential MIDs and in response improve efficiency by
switching its mode to the bitfield based storage.</t>
</section>
</section>
<section anchor="alternative-configurations" title="Alternative Configurations">
<section anchor="transmission-parameters" title="Transmission Parameters">
<t>When a constrained network of CoAP nodes is not communicating over the
Internet, for instance because it is shielded by a proxy or a
closed deployment, alternative transmission parameters can be used.
Consequently, the derived time values provided in <xref target="I-D.ietf-core-coap"/>
section 4.8.2 will also need to be adjusted, since most implementations
will encode their absolute values.</t>
<t>Static adjustments require a fixed deployment with a constant number or upper
bound for the number of nodes, number of hops, and expected concurrent
transmissions. Furthermore, the stability of the wireless links should be
evaluated. ACK_TIMEOUT should be chosen above the xx% percentile of the
round-trip time distribution. ACK_RANDOM_FACTOR depends on the number of nodes
on the network. MAX_RETRANSMIT should be chosen suitable for the targeted
application. A lower bound for LEISURE can be calculated as</t>
<t>lb_Leisure = S * G / R</t>
<t>where S is the estimated response size, G the group size, and R the target data
transfer rate (see <xref target="I-D.ietf-core-coap"/> section 8.2). NSTART and
PROBING_RATE depend on estimated network utilization. If the main cause for
loss are weak links, higher values can be chosen.</t>
<t>Dynamic adjustments will be performed by advanced congestion control mechanisms
such as <xref target="I-D.bormann-core-cocoa"/>. They are required if the main cause for
message loss is network or endpoint congestion. Semi-dynamic adjustments
could be implemented by disseminating new static transmission parameters to
all nodes when the network configuration changes (e.g., new nodes are added
or long-lasting interference is detected).</t>
</section>
<section anchor="coap-over-ipv4" title="CoAP over IPv4">
<t>CoAP was designed for the properties of IPv6, which is dominating in constrained
environments because of the 6LoWPAN adaption layer <xref target="RFC6282"/>. In particular,
the size limitations of CoAP are tailored to the minimal MTU of 1280 bytes.
Until the transition towards IPv6 converges, CoAP nodes might also communicate
over IPv4, though. Sections 4.2 and 4.6 of the base specification
<xref target="I-D.ietf-core-coap"/> already provide guidance and implementation notes to
handle the smaller minimal MTUs of IPv4. </t>
<!-- LocalWords: CoAP lossy LLN KiB optimizations scalability URIs
-->
<!-- LocalWords: tradeoff Confirmable MTU blockwise LoWPAN datagram
-->
<!-- LocalWords: retransmission deduplication datagrams RST TKL URI
-->
<!-- LocalWords: preselect IP memmove UDP NoSec DTLS GiB ACK ACKs
-->
<!-- LocalWords: namespace FSM NONs retransmitting acknowledgement
-->
<!-- LocalWords: ICMP misconfiguration APIs RESTful API Uri UART
-->
<!-- LocalWords: checkpointing programmatically confirmable CoAP's
-->
<!-- LocalWords: retransmissions Acknowledgements JSON Implementers
-->
<!-- LocalWords: CoRE MIDs implementers sequentiality bitfield IPv
-->
<!-- LocalWords: MTUs
-->
</section>
</section>
</middle>
<back>
<references title='Normative References'>
<reference anchor='RFC2616'>
<front>
<title abbrev='HTTP/1.1'>Hypertext Transfer Protocol -- HTTP/1.1</title>
<author initials='R.' surname='Fielding' fullname='Roy T. Fielding'>
<organization abbrev='UC Irvine'>Department of Information and Computer Science</organization>
<address>
<postal>
<street>University of California, Irvine</street>
<city>Irvine</city>
<region>CA</region>
<code>92697-3425</code></postal>
<facsimile>+1(949)824-1715</facsimile>
<email>fielding@ics.uci.edu</email></address></author>
<author initials='J.' surname='Gettys' fullname='James Gettys'>
<organization abbrev='Compaq/W3C'>World Wide Web Consortium</organization>
<address>
<postal>
<street>MIT Laboratory for Computer Science, NE43-356</street>
<street>545 Technology Square</street>
<city>Cambridge</city>
<region>MA</region>
<code>02139</code></postal>
<facsimile>+1(617)258-8682</facsimile>
<email>jg@w3.org</email></address></author>
<author initials='J.' surname='Mogul' fullname='Jeffrey C. Mogul'>
<organization abbrev='Compaq'>Compaq Computer Corporation</organization>
<address>
<postal>
<street>Western Research Laboratory</street>
<street>250 University Avenue</street>
<city>Palo Alto</city>
<region>CA</region>
<code>94305</code></postal>
<email>mogul@wrl.dec.com</email></address></author>
<author initials='H.' surname='Frystyk' fullname='Henrik Frystyk Nielsen'>
<organization abbrev='W3C/MIT'>World Wide Web Consortium</organization>
<address>
<postal>
<street>MIT Laboratory for Computer Science, NE43-356</street>
<street>545 Technology Square</street>
<city>Cambridge</city>
<region>MA</region>
<code>02139</code></postal>
<facsimile>+1(617)258-8682</facsimile>
<email>frystyk@w3.org</email></address></author>
<author initials='L.' surname='Masinter' fullname='Larry Masinter'>
<organization abbrev='Xerox'>Xerox Corporation</organization>
<address>
<postal>
<street>MIT Laboratory for Computer Science, NE43-356</street>
<street>3333 Coyote Hill Road</street>
<city>Palo Alto</city>
<region>CA</region>
<code>94034</code></postal>
<email>masinter@parc.xerox.com</email></address></author>
<author initials='P.' surname='Leach' fullname='Paul J. Leach'>
<organization abbrev='Microsoft'>Microsoft Corporation</organization>
<address>
<postal>
<street>1 Microsoft Way</street>
<city>Redmond</city>
<region>WA</region>
<code>98052</code></postal>
<email>paulle@microsoft.com</email></address></author>
<author initials='T.' surname='Berners-Lee' fullname='Tim Berners-Lee'>
<organization abbrev='W3C/MIT'>World Wide Web Consortium</organization>
<address>
<postal>
<street>MIT Laboratory for Computer Science, NE43-356</street>
<street>545 Technology Square</street>
<city>Cambridge</city>
<region>MA</region>
<code>02139</code></postal>
<facsimile>+1(617)258-8682</facsimile>
<email>timbl@w3.org</email></address></author>
<date year='1999' month='June' />
<abstract>
<t>
The Hypertext Transfer Protocol (HTTP) is an application-level
protocol for distributed, collaborative, hypermedia information
systems. It is a generic, stateless, protocol which can be used for
many tasks beyond its use for hypertext, such as name servers and
distributed object management systems, through extension of its
request methods, error codes and headers . A feature of HTTP is
the typing and negotiation of data representation, allowing systems
to be built independently of the data being transferred.
</t>
<t>
HTTP has been in use by the World-Wide Web global information
initiative since 1990. This specification defines the protocol
referred to as "HTTP/1.1", and is an update to RFC 2068 .
</t></abstract></front>
<seriesInfo name='RFC' value='2616' />
<format type='TXT' octets='422317' target='http://www.rfc-editor.org/rfc/rfc2616.txt' />
<format type='PS' octets='5529857' target='http://www.rfc-editor.org/rfc/rfc2616.ps' />
<format type='PDF' octets='550558' target='http://www.rfc-editor.org/rfc/rfc2616.pdf' />
<format type='HTML' octets='637302' target='http://xml.resource.org/public/rfc/html/rfc2616.html' />
<format type='XML' octets='493420' target='http://xml.resource.org/public/rfc/xml/rfc2616.xml' />
</reference>
<reference anchor='RFC6570'>
<front>
<title>URI Template</title>
<author initials='J.' surname='Gregorio' fullname='J. Gregorio'>
<organization /></author>
<author initials='R.' surname='Fielding' fullname='R. Fielding'>
<organization /></author>
<author initials='M.' surname='Hadley' fullname='M. Hadley'>
<organization /></author>
<author initials='M.' surname='Nottingham' fullname='M. Nottingham'>
<organization /></author>
<author initials='D.' surname='Orchard' fullname='D. Orchard'>
<organization /></author>
<date year='2012' month='March' />
<abstract>
<t>A URI Template is a compact sequence of characters for describing a range of Uniform Resource Identifiers through variable expansion. This specification defines the URI Template syntax and the process for expanding a URI Template into a URI reference, along with guidelines for the use of URI Templates on the Internet. [STANDARDS-TRACK]</t></abstract></front>
<seriesInfo name='RFC' value='6570' />
<format type='TXT' octets='79813' target='http://www.rfc-editor.org/rfc/rfc6570.txt' />
</reference>
<reference anchor='RFC6633'>
<front>
<title>Deprecation of ICMP Source Quench Messages</title>
<author initials='F.' surname='Gont' fullname='F. Gont'>
<organization /></author>
<date year='2012' month='May' />
<abstract>
<t>This document formally deprecates the use of ICMP Source Quench messages by transport protocols, formally updating RFC 792, RFC 1122, and RFC 1812. [STANDARDS-TRACK]</t></abstract></front>
<seriesInfo name='RFC' value='6633' />
<format type='TXT' octets='16367' target='http://www.rfc-editor.org/rfc/rfc6633.txt' />
</reference>
<reference anchor='RFC6282'>
<front>
<title>Compression Format for IPv6 Datagrams over IEEE 802.15.4-Based Networks</title>
<author initials='J.' surname='Hui' fullname='J. Hui'>
<organization /></author>
<author initials='P.' surname='Thubert' fullname='P. Thubert'>
<organization /></author>
<date year='2011' month='September' />
<abstract>
<t>This document updates RFC 4944, "Transmission of IPv6 Packets over IEEE 802.15.4 Networks". This document specifies an IPv6 header compression format for IPv6 packet delivery in Low Power Wireless Personal Area Networks (6LoWPANs). The compression format relies on shared context to allow compression of arbitrary prefixes. How the information is maintained in that shared context is out of scope. This document specifies compression of multicast addresses and a framework for compressing next headers. UDP header compression is specified within this framework. [STANDARDS-TRACK]</t></abstract></front>
<seriesInfo name='RFC' value='6282' />
<format type='TXT' octets='52588' target='http://www.rfc-editor.org/rfc/rfc6282.txt' />
</reference>
<reference anchor='I-D.ietf-core-coap'>
<front>
<title>Constrained Application Protocol (CoAP)</title>
<author initials='Z' surname='Shelby' fullname='Zach Shelby'>
<organization />
</author>
<author initials='K' surname='Hartke' fullname='Klaus Hartke'>
<organization />
</author>
<author initials='C' surname='Bormann' fullname='Carsten Bormann'>
<organization />
</author>
<date month='June' day='28' year='2013' />
<abstract><t>The Constrained Application Protocol (CoAP) is a specialized web transfer protocol for use with constrained nodes and constrained (e.g., low-power, lossy) networks. The nodes often have 8-bit microcontrollers with small amounts of ROM and RAM, while constrained networks such as 6LoWPAN often have high packet error rates and a typical throughput of 10s of kbit/s. The protocol is designed for machine-to-machine (M2M) applications such as smart energy and building automation. CoAP provides a request/response interaction model between application endpoints, supports built-in discovery of services and resources, and includes key concepts of the Web such as URIs and Internet media types. CoAP is designed to easily interface with HTTP for integration with the Web while meeting specialized requirements such as multicast support, very low overhead and simplicity for constrained environments.</t></abstract>
</front>
<seriesInfo name='Internet-Draft' value='draft-ietf-core-coap-18' />
<format type='TXT'
target='http://www.ietf.org/internet-drafts/draft-ietf-core-coap-18.txt' />
</reference>
<reference anchor='I-D.ietf-core-observe'>
<front>
<title>Observing Resources in CoAP</title>
<author initials='K' surname='Hartke' fullname='Klaus Hartke'>
<organization />
</author>
<date month='February' day='14' year='2014' />
<abstract><t>CoAP is a RESTful application protocol for constrained nodes and networks. The state of a resource on a CoAP server can change over time. This document specifies a simple protocol extension for CoAP that enables CoAP clients to "observe" resources, i.e., to retrieve a representation of a resource and keep this representation updated by the server over a period of time. The protocol follows a best- effort approach for sending new representations to clients and provides eventual consistency between the state observed by each client and the actual resource state at the server.</t></abstract>
</front>
<seriesInfo name='Internet-Draft' value='draft-ietf-core-observe-12' />
<format type='TXT'
target='http://www.ietf.org/internet-drafts/draft-ietf-core-observe-12.txt' />
</reference>
<reference anchor='I-D.ietf-core-block'>
<front>
<title>Blockwise transfers in CoAP</title>
<author initials='C' surname='Bormann' fullname='Carsten Bormann'>
<organization />
</author>
<author initials='Z' surname='Shelby' fullname='Zach Shelby'>
<organization />
</author>
<date month='October' day='21' year='2013' />
<abstract><t>CoAP is a RESTful transfer protocol for constrained nodes and networks. Basic CoAP messages work well for the small payloads we expect from temperature sensors, light switches, and similar building-automation devices. Occasionally, however, applications will need to transfer larger payloads -- for instance, for firmware updates. With HTTP, TCP does the grunt work of slicing large payloads up into multiple packets and ensuring that they all arrive and are handled in the right order. CoAP is based on datagram transports such as UDP or DTLS, which limits the maximum size of resource representations that can be transferred without too much fragmentation. Although UDP supports larger payloads through IP fragmentation, it is limited to 64 KiB and, more importantly, doesn't really work well for constrained applications and networks. Instead of relying on IP fragmentation, this specification extends basic CoAP with a pair of "Block" options, for transferring multiple blocks of information from a resource representation in multiple request-response pairs. In many important cases, the Block options enable a server to be truly stateless: the server can handle each block transfer separately, with no need for a connection setup or other server-side memory of previous block transfers. In summary, the Block options provide a minimal way to transfer larger representations in a block-wise fashion.</t></abstract>
</front>
<seriesInfo name='Internet-Draft' value='draft-ietf-core-block-14' />
<format type='TXT'
target='http://www.ietf.org/internet-drafts/draft-ietf-core-block-14.txt' />
</reference>
<reference anchor='I-D.bormann-core-cocoa'>
<front>
<title>CoAP Simple Congestion Control/Advanced</title>
<author initials='C' surname='Bormann' fullname='Carsten Bormann'>
<organization />
</author>
<date month='February' day='14' year='2014' />
<abstract><t>The CoAP protocol needs to be implemented in such a way that it does not cause persistent congestion on the network it uses. The CoRE CoAP specification defines basic behavior that exhibits low risk of congestion with minimal implementation requirements. It also leaves room for combining the base specification with advanced congestion control mechanisms with higher performance. This specification defines some simple advanced CoRE Congestion Control mechanisms, Simple CoCoA. In the present version -01, it is already making use of some input from simulations, but might still benefit from simplifying it further.</t></abstract>
</front>
<seriesInfo name='Internet-Draft' value='draft-bormann-core-cocoa-01' />
<format type='TXT'
target='http://www.ietf.org/internet-drafts/draft-bormann-core-cocoa-01.txt' />
</reference>
</references>
<references title='Informative References'>
<reference anchor='I-D.ietf-lwig-terminology'>
<front>
<title>Terminology for Constrained Node Networks</title>
<author initials='C' surname='Bormann' fullname='Carsten Bormann'>
<organization />
</author>
<author initials='M' surname='Ersue' fullname='Mehmet Ersue'>
<organization />
</author>
<author initials='A' surname='Keranen' fullname='Ari Keranen'>
<organization />
</author>
<date month='February' day='10' year='2014' />
<abstract><t>The Internet Protocol Suite is increasingly used on small devices with severe constraints on power, memory and processing resources, creating constrained node networks. This document provides a number of basic terms that have turned out to be useful in the standardization work for constrained node networks.</t></abstract>
</front>
<seriesInfo name='Internet-Draft' value='draft-ietf-lwig-terminology-07' />
<format type='TXT'
target='http://www.ietf.org/internet-drafts/draft-ietf-lwig-terminology-07.txt' />
</reference>
<reference anchor="TinyOS" >
<front>
<title>TinyOS: An Operating System for Sensor Networks</title>
<author initials="P." surname="Levis">
<organization></organization>
</author>
<author initials="S." surname="Madden">
<organization></organization>
</author>
<author initials="J." surname="Polastre">
<organization></organization>
</author>
<author initials="R." surname="Szewczyk">
<organization></organization>
</author>
<author initials="K." surname="Whitehouse">
<organization></organization>
</author>
<author initials="A." surname="Woo">
<organization></organization>
</author>
<author initials="D." surname="Gay">
<organization></organization>
</author>
<author initials="A." surname="Woo">
<organization></organization>
</author>
<author initials="J." surname="Hill">
<organization></organization>
</author>
<author initials="M." surname="Welsh">
<organization></organization>
</author>
<author initials="E." surname="Brewer">
<organization></organization>
</author>
<author initials="D." surname="Culler">
<organization></organization>
</author>
<date year="2005"/>
</front>
<seriesInfo name="Ambient intelligence, Springer (Berlin Heidelberg), ISBN 978-3-540-27139-0" value=""/>
</reference>
<reference anchor="Contiki" >
<front>
<title>Contiki - a Lightweight and Flexible Operating System for Tiny Networked Sensors</title>
<author initials="A." surname="Dunkels" fullname="Adam Dunkels">
<organization></organization>
</author>
<author initials="B." surname="Grönvall" fullname="Björn Grönvall">
<organization></organization>
</author>
<author initials="T." surname="Voigt" fullname="Thiemo Voigt">
<organization></organization>
</author>
<date year="2004" month="November"/>
</front>
<seriesInfo name="Proceedings of the First IEEE Workshop on Embedded Networked Sensors" value=""/>
</reference>
</references>
</back>
</rfc>
| PAFTECH AB 2003-2026 | 2026-04-23 05:08:59 |