Subject: [core] draft-ietf-core-block-00 comments

From: Peter Bigot <[email-masked]>
Date: Wed, 20 Oct 2010 13:22:00 -0500

As discussed in the thread culminating in
http://www.ietf.org/mail-archive/web/core/current/msg00716.html, for
correctness in certain conditions the server must not respond with a Block
option if the original request did not include a Block option, and must
include an ETag option in every response message containing a Block option.

Section 2.1:

Based on the discussion referred to above, the Block option should have no
default value.  A client capable of processing multi-part responses and
unsure whether this is necessary in a given request should always include a
block option with a value of 0x07 (first block, 2048-byte payload), or a
smaller number if it cannot accommodate a 2048-byte response.

Section 2.2.

Related to ticket #26, a new error code indicating "Representation Too
Large" must be provided to indicate that the server knows it cannot provide
the entire representation in a single message and that the client must
indicate its willingness to perform multi-part transactions by resubmitting
the request with a Block option in the header.  (The text in this section
allowing the server to select a transaction block size less than the size
requested for the first block eliminates the need to use this error code if
the server knows the path MTU is too small for the requested size, a concern
in the previous discussion.)

   If the Block option is used by the requestor, all GET requests in a
   single transaction (except for the last one with the M bit not set)
   MUST ultimately use the same size.  The server SHOULD use the block

This paragraph needs to be reworked.  I don't think the parenthetical remark
concerning the M bit is relevant; certainly not for GET requests, since the
client doesn't know whether there's more data, and not for the last
response, where the block size is irrelevant.  The rest of the paragraph
implies that the size in the block option should be fixed in the first
server response, taking into account the maximum size indicated by the
client in the initial request, and that both the server and the client must
continue to use this block size in all CoAP messages related to this REST
transaction.  Reference to GET requests throughout the paragraph makes this
unclear, unless it is not intended to apply to PUT or POST as well, which
might result in inconsistencies.

   resources.  In the latter case, the Block option SHOULD be used in
   conjunction with the Etag option, to ensure that the blocks being
   reassembled are from the same version of the representation.  When

s/SHOULD/MUST/.  See previous discussion thread.

  reassembler MUST compare Etag options.  If the Etag options do not
Shelby & Bormann         Expires April 21, 2011                 [Page
6]  <http://tools.ietf.org/html/draft-ietf-core-block-00#page-7>
Internet-Draft                 CoAP-block                   October 2010
   match in a GET transfer, the requestor has the option of attempting
   to retrieve fresh values for the blocks it retrieved first.  To
   minimize the resulting inefficiency, the server MAY cache the current
   value of a representation for an ongoing sequence of requests, but
   there is no requirement for the server to establish any state.  The
   client MAY facilitate identifying the sequence by using the Token
   option.

Things are getting messy here.  Assume I'm 50 blocks into receiving a
representation, and the 51st block comes with a new ETag, invalidating
everything I did before.  The text above suggests I can go back and request
the previous 50 blocks, using the new ETag.

This implies that using the block option to randomly access fragments of the
representation is valid, because here is a case where I'm not receiving the
blocks in strict sequence starting at the beginning.  It's also a case where
I'm asking for block zero again, which normally would allow a change in
block size, but maybe not in this case?  Like I said, getting messy.

It'd be a lot cleaner if use of the block option must be non-decreasing
(once you request block N, you can't request any block less than N; if you
can, we need an error code for when the server to use when it can no longer
provide that part of the representation).  Furthermore, the requests for
non-initial blocks should include the ETag for the representation being
constructed, and if the representation has changed an error response should
say so, telling the client to start over, rather than expecting it to cache
the Nth block then re-request the older stuff.  There may not even be an Nth
block in the new representation; what does the server do then?

This does change what ETag means, specifically with respect to what a server
does if a request includes it and the tagged representation is no longer
available (proxies request a new one from upstream; servers in block mode
send an error).  It may be that a new option is required for block, to keep
these behaviors separated.

It also rules out parallel active requests for multiple blocks.  I think
that's a reasonable limitation for constrained devices.

   If multiple concurrently proceeding block-wise PUT or POST operations
   are possible, the requestor SHOULD use the Token option to clearly
   separate the different sequences.  In this case, when reassembling

Maybe.  Token seems to be settling into an identifier for a specific REST
transaction.  Use of the block option is clearly described as splitting a
single REST transaction into multiple CoAP transactions, so I would say that
Token SHOULD be used in any block operation, and in fact the same Token
SHOULD be used in every block request that's part of the same underlying
REST transaction.  Since Token is client-specified, the server must further
distinguish these messages based on some other identifying information like
message source IP address (i.e., if the text above was supposed to relieve
the server of this obligation, it doesn't work).  Any client that doesn't
support asynchronous responses but does want to do simultaneous block
requests related to the same resource has a problem, but I'll suggest the
appropriate response is the good old "Don't do that".

The more I dig into this, the more I really think that using RFC2348 and
RFC1350 would be a lot simpler than trying to create an alternative like
CoAP block.  Now that I've found RFC2348, which allows TFTP packets to be
less than 512 bytes, I may very well just go that way for my deployment
environment.

Peter

---

From: Carsten Bormann <[email-masked]>
Date: Wed, 20 Oct 2010 21:27:14 +0200

Peter,

I think you are providing a lot of good input that will allow the new editor to develop editorial improvements of the document.

I do have a number of differences in philosophy, though, that lead me to different technical conclusions.

I'm going to address three points:
1) optionality of implementing block
2) resources that change during retrieval
3) random access
but not quite in this order.

First, block is not an option that is being designed into CoAP after the protocol has been out there for two years, so we maybe can use an approach to provide optionality that is less heavyweight than if we needed backwards-compatibility.

Sending an error code "too big" is always less preferable to sending back the first block.
If the client does have a preference for the block size, fine, it should have sent it in the request.
If it doesn't, not getting the data but having to rerequest it (hey, I really want it) is not making sense to me.
(Including the block option in every request, just in case, does not make sense in a constrained environment, either.)
If the client doesn't implement block but it somehow was configured to access a large resource, essentially something was misconfigured.
The presence of the block option in the response is as indicative of this misconfiguration as an error code would be.

ETag in responses is optional because there may be resources that don't ever change.
If I deploy a temp sensor, that may never change its /.well-known/core or a descriptive document referenced from that.
So why send an ETag?

The random-access issue is interesting.  To disallow random access, the server must have state.
So I think it is not meaningful to require the server to disallow access in other than sequential order.
But I think it would be a good change to indicate that clients should use sequential order.

If a resource is prone to change through its retrieval, block is not a very good mechanism to cope with that on its own.
But remember that we have REST available.
So a resource that is big and also changes a lot could redirect (by a link, or by a redirect mechanism we don't have yet) to a URI that provides a specific snapshot of it -- this would be a lot like the open(2) semantics of UNIX, where you get a file descriptor to a file that is still referring to the old one even if the file name link in the directory is replaced by a pointer to a new instance.
ETag is good enough to detect changes for rarely-changing resources where you don't want to have an open(2) style access.

Using the token to detect partial access to different versions of resources would require the server to keep (potentially unbounded) state, so I don't like that idea at all.

Block is using small integers to enumerate the slices of the resource representation for two reasons:
1) integers are small (at least for reasonably sized resource representations),
2) integers allow the server to be stateless, if it is able to provide indexed access into the binary form of the representation.
Robert Quattlebaum has this interesting usage example where the latter is not the case (1-wire enumeration), so he was proposing to be able to use non-numeric slice identifiers in a more/next protocol.
I can understand that, because it is a specific use case (and I would love to find a way to unify the advantages of block with his more/next protocol without increasing complexity).
I'd like to understand your use case, and in particular why you think TFTP's server side state identifiers (encoded in port numbers) are more appropriate for a REST protocol than the stateless block or more/next approach (i.e. to ping-pong the slice identifiers from server to client and back).

So my proposal would be to continue this discussion based on a specific usage example.

Gruesse, Carsten

---

From: Peter Bigot <[email-masked]>
Date: Wed, 20 Oct 2010 15:46:54 -0500

On Wed, Oct 20, 2010 at 2:27 PM, Carsten Bormann <[email-masked]> wrote:

> Peter,
>
> I think you are providing a lot of good input that will allow the new
> editor to develop editorial improvements of the document.
>
> First, block is not an option that is being designed into CoAP after the
> protocol has been out there for two years, so we maybe can use an approach
> to provide optionality that is less heavyweight than if we needed
> backwards-compatibility.
>
> If it doesn't, not getting the data but having to rerequest it (hey, I
> really want it) is not making sense to me.
> (Including the block option in every request, just in case, does not make
> sense in a constrained environment, either.)
> If the client doesn't implement block but it somehow was configured to
> access a large resource, essentially something was misconfigured.
> The presence of the block option in the response is as indicative of this
> misconfiguration as an error code would be.
>

See the referenced discussion from early September, which suggested that,
depending on network characteristics, pre-emptively sending a block response
when one was not requested could result in failures that the client cannot
diagnose and recover from, because it will never see the response.

On re-reading that thread myself, I see that because the default value of
the Block option is zero the server must send blocks that are 16-bytes long,
so it's pretty unlikely that the response will get dropped due to MTU
problems.  On the other hand, it's going to take a long time to get the data
that way, so my clients (on a network that supports 240-byte payloads) would
probably ignore that response and re-transmit the original request with an
explicit Block option specifying a larger block size.

The start of section 2.1 implies that the server is to switch to using Block
when the representation is "larger than can be comfortably[sic] transferred
in a single UDP datagram".  That size is 64kB, much larger than we
anticipate ever transferring, and certainly not an appropriate threshold.
What size should the server use as a cue that the representation is too
large?  Since the default Block option value has an encoded size of 16,
presumably a 20-byte representation technically should be converted to a
block transfer.  No?

So I don't see that you've saved anything by pre-emptively sending the first
16 bytes, instead of an error code warning the client that the resource
exceeds the server's estimation of the path MTU and it should be prepared
for that.  In the error response, you could even include an estimation of
the actual length, so a client with little memory wouldn't have to retrieve
a hundred pieces before finding out it couldn't accept the representation
anyway.

ETag in responses is optional because there may be resources that don't ever
> change.
If I deploy a temp sensor, that may never change its /.well-known/core or a
> descriptive document referenced from that.
> So why send an ETag?
>

So don't, for resources where the representation never changes.  The SHOULD
in that paragraph at the bottom of page 6 should still be changed to MUST,
since it refers to a GET of a resource for which the representation may
dynamically change.  Otherwise the client will unwittingly piece together an
invalid representation, and have no way of knowing it's done so.  Why would
we ever want to allow a server to enable this?

And again, what do we do if the representation changes and the client is
asking for a block that does not exist in the current representation because
it shrank?

The random-access issue is interesting.  To disallow random access, the
> server must have state.
So I think it is not meaningful to require the server to disallow access in
> other than sequential order.

I didn't mean that the server would be obliged to diagnose non-decreasing
access; I meant that a client should not assume it can do so.  My point is
that the server may generate some resource representations incrementally and
destructively, and not be able to regenerate earlier chunks.  There should
be a way for the server to indicate this has happened.

> If a resource is prone to change through its retrieval, block is not a very
> good mechanism to cope with that on its own.
> So a resource that is big and also changes a lot could redirect (by a link,
> or by a redirect mechanism we don't have yet) to a URI that provides a
> specific snapshot of it -- this would be a lot like the open(2) semantics of
> UNIX, where you get a file descriptor to a file that is still referring to
> the old one even if the file name link in the directory is replaced by a
> pointer to a new instance.
> ETag is good enough to detect changes for rarely-changing resources where
> you don't want to have an open(2) style access.
>
> Using the token to detect partial access to different versions of resources
> would require the server to keep (potentially unbounded) state, so I don't
> like that idea at all.
>

That comment was in reference to a multi-part PUT/PUSH operation.  The
server's already keeping potentially-unbounded state.

Block is using small integers to enumerate the slices of the resource
> representation for two reasons:
> 2) integers allow the server to be stateless, if it is able to provide
> indexed access into the binary form of the representation.
> Robert Quattlebaum has this interesting usage example where the latter is
> not the case (1-wire enumeration), so he was proposing to be able to use
> non-numeric slice identifiers in a more/next protocol.
> I can understand that, because it is a specific use case (and I would love
> to find a way to unify the advantages of block with his more/next protocol
> without increasing complexity).
>

I would argue that more/next, as a meta-characteristic not encoded in the
resource identifier, is inherently non-RESTful.  It mandates server state be
associated with a client's view of a specific resource.  Block does not,
because each request tells the server the necessary state, which is how REST
should work in such a case.  (I still believe that, if treated as an
independent REST transaction, use of the block option is nothing more than
syntactic sugar for a URI where a query-part defines a block size and a
fragment identifier specifies the block.)

I'd like to understand your use case, and in particular why you think TFTP's
> server side state identifiers (encoded in port numbers) are more appropriate
> for a REST protocol than the stateless block or more/next approach (i.e. to
> ping-pong the slice identifiers from server to client and back).
>

What level of REST are we talking about?  It's a single REST transaction:
one tftp get. That at the network level it comprises multiple messages in
each direction and some server state is irrelevant.  A REST request via HTTP
usually comprises multiple IP packets and requires server-side TCP state.

If the goal is to have REST principles maintained in CoAP at the IP level in
all cases, I think that's unrealistic.  Block might work, but group
(multicast) operations don't, and the observe solution really isn't RESTful
either.  I don't see that this is a problem.  CoAP can be used in a RESTful
way, and can integrate with other REST architectures, which means it should
meet the requirements of the smart grid and similar driving applications.
Security, for example, is certainly going to involve per-client server
state, whether it's visible in CoAP or not.  That the charter for CoAP
presumed all its requirements could be met by a RESTful solution is, simply,
a mistake.  It could be done, but only by adding overhead that is not
appropriate for its target domain.

My main point is that (a) TFTP is an existing, proven solution to transfer
of data that cannot be accomplished in a single IP packet in cases where a
stream-oriented protocol is not available, and (b) attempting to define a
new solution to that problem is a mistake.  I would respond to a CoAP
request for a large representation by redirecting the client to a server
using a protocol designed for that purpose.

Peter

---

From: Robert Quattlebaum <[email-masked]>
Date: Wed, 20 Oct 2010 22:51:45 -0700

Hello Peter!

On Oct 20, 2010, at 1:46 PM, Peter Bigot wrote:

> I would argue that more/next, as a meta-characteristic not encoded in the resource identifier, is inherently non-RESTful.  It mandates server state be associated with a client's view of a specific resource.  
> Block does not, because each request tells the server the necessary state, which is how REST should work in such a case.

Carsten and I have been discussing and developing my suggestion off-list. My proposal has changed pretty significantly since I first proposed it. I wanted to get more of Carsten's input before posting an updated proposal to the list. In light of this thread, I'll go ahead and clean up my proposal and post it to the list for wider discussion sometime tomorrow.

In the mean time, I'll just add that the whole point of the Next option is to allow the server to serve requests with large content responses as efficiently as possible for the server implementation. Sometimes you need more than just a block index to generate the requested content efficiently, but in cases where it can be done efficiently there is nothing stopping a server implementation from simply using the Next option to hold the same information the Block option would. The only difference in such a case between the Next option and the Block option would be that the client doesn't mutate the value of the Next option like would with the Block option.

More details later.

__________________
Robert Quattlebaum
Jabber: [email-masked]
eMail:  [email-masked]
www:    http://www.deepdarc.com/

---

From: Carsten Bormann <[email-masked]>
Date: Thu, 21 Oct 2010 10:49:54 +0200

On Oct 20, 2010, at 22:46, Peter Bigot wrote:

> because the default value of the Block option is zero the server must send blocks that are 16-bytes long

Section 2.1 says:

   The default value of the Block Option is zero, indicating
   that the current block is the first (block number 0) and only (M bit
   not set) block of the transfer; however, there is no explicit size
   implied by this default value.

The server is thus free to choose a size if a client does not indicate a preference.

(This may be a strange default, but there is never a need to provide an unspecified size except when the block number is also zero, so this is a good way not to spend bits for something that will be sent a lot.)

Gruesse, Carsten

---

From: Peter Bigot <[email-masked]>
Date: Thu, 21 Oct 2010 07:38:11 -0500

Good enough.  Then my objection that the protocol does not adequately
protect against network MTU characteristics stands.

I also raise a new objection that special-casing the interpretation of a
zero value when it is the default is unnecessarily confusing.  A better
solution would be to say there is no default value for the block option, but
the behavior when the representation is too large, the server supports the
Block option, but no Block option is present in the request should be (me)
reject the request or redirect to a different protocol (carsten) select a
block size and proceed with the first block.

BTW: "Core" CoAP would benefit from having available the error code
indicating that the server knows the representation is too big to be safely
carried in a packet addressed to the client requesting it.  Parameters to
that error response might include an estimate of the representation size,
and an alternative URI for retrieval by a different protocol.

Peter

On Thu, Oct 21, 2010 at 3:49 AM, Carsten Bormann <[email-masked]> wrote:

> (This may be a strange default, but there is never a need to provide an
> unspecified size except when the block number is also zero, so this is a
> good way not to spend bits for something that will be sent a lot.)
>
> Gruesse, Carsten
>
>

---

From: Carsten Bormann <[email-masked]>
Date: Thu, 21 Oct 2010 15:20:38 +0200

On Oct 21, 2010, at 14:38, Peter Bigot wrote:

> network MTU characteristics

I must admit that I have mainly focused on IPv6 here, which has a reasonable-to-large (for constrained networks) minimum MTU.  For IPv4, the situation may be a bit more complicated, if you actually want to set DF.
I'm not sure we want to do a lot to make things more efficient for IPv4 with unusual (< 1280) MTUs.
Maybe sending IPv4 CoAP responses with DF set is just not that great an idea.
The remaining question is whether we want to do anything special to accommodate IPv4's small minimum MRU (576 bytes).
I still like the number 1152 as a guideline for a maximum CoAP message size in IPv6.
(Block can encode a 2048-byte slice size because there are three bits to indicate the size and less than 16 bytes does not make a lot of sense with all the header overhead either; 16*2^7=2048.)

(And I like the proposal to rephrase what the absence of the block option means -- the current language is probably pretty confusing indeed.)

Gruesse, Carsten

---

From: Peter Bigot <[email-masked]>
Date: Thu, 21 Oct 2010 09:09:49 -0500

Nothing requires reference to IPv4.

Assume a pure IPv6 network, with devices A and B on an 802.3 wired segment
configured for jumbo frames that supports an 8192-byte MTU, and device C on
an 802.15.4 network that patches together support for IPv6's required
1280-byte MTU by doing link-layer reassembly of 127-byte frames (something
we really would rather avoid, but what the heck, IPv6 requires it).

A 1600-byte resource representation can be retrieved from A by B using CoAP
in a single IP datagram.  Device C cannot retrieve this resource without
using the block extension or an alternative protocol.

As I read draft-ietf-core-block section 2, the intent would be that C should
retrieve the data with blocks that fit within the link MTU (127 bytes).  C's
guess at the appropriate block size is more likely to be useful than A's,
which is why I'd prefer to always have the client propose the
characteristics of a multi-part block transaction.  The server can always
select a smaller value if it knows something the client doesn't.

Peter

On Thu, Oct 21, 2010 at 8:20 AM, Carsten Bormann <[email-masked]> wrote:

> I must admit that I have mainly focused on IPv6 here, which has a
> reasonable-to-large (for constrained networks) minimum MTU.  For IPv4, the
> situation may be a bit more complicated, if you actually want to set DF.
> The remaining question is whether we want to do anything special to
> accommodate IPv4's small minimum MRU (576 bytes).
> (Block can encode a 2048-byte slice size because there are three bits to
> indicate the size and less than 16 bytes does not make a lot of sense with
> all the header overhead either; 16*2^7=2048.)
>
> (And I like the proposal to rephrase what the absence of the block option
> means -- the current language is probably pretty confusing indeed.)
>
> Gruesse, Carsten
>
>

---

From: Peter Bigot <[email-masked]>
Date: Thu, 21 Oct 2010 09:09:49 -0500

Peter

---

From: Carsten Bormann <[email-masked]>
Date: Thu, 21 Oct 2010 17:10:11 +0200

I don't think CoAP messages should ever be larger than the IPv6 minimum MTU.
CoAP does not have a Path MTU discovery mechanism and probably shouldn't grow one.
I'm also assuming that all CoAP implementations do implement the IPv6 minimum MTU (at least nominally -- if a node never deals in information of that size, you won't find out).
So I think there is no interaction with *correctness* here -- the packet size discussion is all about *efficiency*.

One thing we should be discussing here is whether there should be a way for the endpoints to influence the slice size used for multi-slice transfers, and how common its usage will be.  The design of block-00 provides such a way, but assumes that clients most often don't want to influence the size -- that's why the initial block option is optional.

If we really think we should be sending a preferred response block size with most requests, we probably should find three bits in the base header where we can efficiently represent this information instead of sending it as another option with every request.

The granularity of the expression of slice size preference is mostly orthogonal to the rigidness of the actual slice sizes -- as Robert has pointed out, there are some applications where semantic fragmentation is more useful than slicing the representation up by number of bytes.  But maybe there is an important application where the slice size should be exactly 73 bytes; we would need to know about this application to accommodate it in the design.

Gruesse, Carsten

---

From: Peter Bigot <[email-masked]>
Date: Thu, 21 Oct 2010 10:47:25 -0500

CoAP is an IP protocol.  Not an IPv6 protocol.  It can assume the basics of
what's available in IP, generically.  Of course it shouldn't grow a PMTUD
mechanism; that's an optional part of IP, and some nodes may be able to
leverage it.

I don't believe it's acceptable for CoAP to impose IPv6-related assumptions
on the entire network path between nodes that communicate over CoAP.
Consequently, I believe CoAP must be robust in the presence of foreseeable
network issues like occasional restricted links along the route.  The block
option as currently defined does not meet this criterion.

I've said this before: I believe very few resources will require block
transfers.  There's no need to include information related to block in most
requests.  All I ask is, when a server determines that the representation is
too large to send to a client, that it tell the client this so the client
can determine how it wants to deal with the situation.  Pre-emptively
assuming that the client has implemented the block option and that the
server could determine the best block size to use to send to the client is
not just potentially inefficient.  The wrong decision (made without PMTUD)
means the client may never find out why it didn't get an answer to its
request.  In my world, given how easy it is to fix this at the protocol
level, that's correctness.

BTW: The payload length of a CoAP transaction message is fundamentally
determined by the datagram length.  I propose we change the concept of
"block" from being a fixed size to being a maximum size.  We've already
discussed situations that justify requiring clients to request the blocks in
order.  If individual elements are less than a full block size, and are
possibly different sizes, so what?  The REST resource representation is the
value resulting from concatenating the blocks in sequential order.  Robert
and others can use the block protocol as-is, as long as the block size
selected is at least the size of the largest record in the sequence.

Peter

On Thu, Oct 21, 2010 at 10:10 AM, Carsten Bormann <[email-masked]> wrote:

> I'm also assuming that all CoAP implementations do implement the IPv6
> minimum MTU (at least nominally -- if a node never deals in information of
> that size, you won't find out).
> So I think there is no interaction with *correctness* here -- the packet
> size discussion is all about *efficiency*.
>
> One thing we should be discussing here is whether there should be a way for
> the endpoints to influence the slice size used for multi-slice transfers,
> and how common its usage will be.  The design of block-00 provides such a
> way, but assumes that clients most often don't want to influence the size --
> that's why the initial block option is optional.
>
> If we really think we should be sending a preferred response block size
> with most requests, we probably should find three bits in the base header
> where we can efficiently represent this information instead of sending it as
> another option with every request.
>
> The granularity of the expression of slice size preference is mostly
> orthogonal to the rigidness of the actual slice sizes -- as Robert has
> pointed out, there are some applications where semantic fragmentation is
> more useful than slicing the representation up by number of bytes.  But
> maybe there is an important application where the slice size should be
> exactly 73 bytes; we would need to know about this application to
> accommodate it in the design.
>
> Gruesse, Carsten
>
>

---

From: Robert Quattlebaum <[email-masked]>
Date: Thu, 21 Oct 2010 10:10:37 -0700

Hello Peter!

On Oct 21, 2010, at 7:09 AM, Peter Bigot wrote:

> Assume a pure IPv6 network, with devices A and B on an 802.3 wired segment configured for jumbo frames that supports an 8192-byte MTU, and device C on an 802.15.4 network that patches together support for IPv6's required 1280-byte MTU by doing link-layer reassembly of 127-byte frames (something we really would rather avoid, but what the heck, IPv6 requires it).
> 
> A 1600-byte resource representation can be retrieved from A by B using CoAP in a single IP datagram.  Device C cannot retrieve this resource without using the block extension or an alternative protocol.

Can we assume that the intermediate router which dropped the 1600 byte response would send back an ICMP "Packet Too Big" response? If so, then perhaps the server could use that ICMP response as an indication that the block option would be required, and re-send with the block option. However, it is likely only possible to send an error message in this case without the server keeping state.

__________________
Robert Quattlebaum