RFC 1235

Coherent File Distribution Protocol

๐Ÿ“… published June 1991, from ietf

RFC 1235: The Coherent File Distribution Protocol โœจ

๐Ÿ“œ Who wrote it: J. Ioannidis and G. Maguire, Jr., from Columbia University's Department of Computer Science ๐Ÿ’œ

๐Ÿ“… When: June 1991 ๐Ÿฆ‹

๐Ÿงช Category: Experimental, so it's not a standard yet. The authors want feedback ๐Ÿซถ

๐Ÿšซ Obsoletes / Updates: This title block doesn't list any RFCs that it obsoletes or updates ๐ŸŒธ


Status of this Memo

Okay so, this memo describes the Coherent File Distribution Protocol (CFDP) ๐Ÿ’–. It's an Experimental Protocol for the Internet community, and the authors are literally begging for discussion and suggestions for improvement ๐Ÿ™. If you want the current standardization state and status of this protocol, check the "IAB Official Protocol Standards" document, because that's where the official info lives ๐Ÿ“š. Distribution of this memo is unlimited, so share it with everyone ๐ŸŒˆ.

Introduction

Okay, bestie, CFDP is built for speeding up one-to-many file transfers that show traffic coherence on media with broadcast capability ๐Ÿฆ‹. Think about it: identical diskless workstations booting at the same time, software upgrades going out to more than one machine at a site, or a certain "object" (bitmap, graph, plain text, etc.) being shared in a real-time electronic conference or class and sent to all the participants ๐Ÿ’…. It's giving "everyone needs the same thing at the same time" โœจ.

In all these cases, there are only a few servers (usually just one) and <n> clients (where <n> can be large) being sent the exact same file ๐Ÿ‘‘. If you send that file through lots of separate one-to-one transfers, the load on both the server and the network goes way up, because the same data gets sent <n> times ๐Ÿ˜ญ. Not ideal!

So the authors propose a file distribution protocol that takes advantage of the broadcast nature of the communications medium (for example fiber, ethernet, or packet radio) ๐ŸŒธ. The goal is to drastically cut the time needed for the file transfer, plus the impact on the file server and the network ๐Ÿ”ฅ. They built it so diskless workstations could boot simultaneously over their experimental packet-radio network, but it works in any situation with coherent transfers ๐Ÿงš.

CFDP started out as a back-end protocol. That means you still need a front-end interface to convert file names and requests for them into file handles ๐Ÿ“. The good news is that a bunch of existing protocols can be adapted to work with CFDP โœจ. There are two reference applications: one is for diskless booting of workstations, which is a simplified BOOTP [3] daemon called sbootpd, and the other is a simple, TFTP-like front end called vtftp ๐Ÿ’–. The CFDP server was also extended to provide this front-end interface ๐ŸŽ€. The authors say the front-end isn't part of the CFDP protocol itself, but they include it in this document anyway so you get a complete example ๐Ÿซถ.

The two clients and the CFDP server are available as reference implementations for anonymous ftp from the site CS.COLUMBIA.EDU (128.59.16.20) in the directory pub/cfdp/ ๐Ÿ’œ. There's also a companion document, "BOOTP extensions to support CFDP", which lists the "vendor extensions" for BOOTP (a-la RFC-1084 [4]) that apply here ๐ŸŒˆ.

Overview

CFDP is implemented as a protocol on top of UDP [5], but it can also be implemented on top of any protocol that supports broadcast datagrams ๐Ÿฆ‹. Later on, once IP multicast [6] implementations become more widespread, it would make more sense to use a multicast address to distribute CFDP packets, because that cuts down on the overhead for machines that aren't participating ๐ŸŒธ.

Here's the flow. A CFDP client that wants a file first contacts a server to acquire a "ticket" for that file ๐ŸŽซ. This server could be a suitably modified BOOTP server, the equivalent of the tftpd daemon, and so on ๐Ÿ’…. The server responds with a 32-bit ticket that gets used in the actual file transfers, the block size sent with each packet (which the document calls "BLKSZ" from now on), and the size in bytes of the file being transferred (called "FILSZ") โœจ.

BLKSZ should be a power of two ๐Ÿ”ฅ. A good value for BLKSZ is 512 ๐Ÿ“. This keeps the total packet size (IPheader+UDPheader+CFDPheader+data=20+8+12+512=552) well under the magic number 576, which is the minimum MTU for IP networks [7] ๐Ÿ˜ญ. Note that this choice of BLKSZ supports transfers of files up to 32 Mbytes in size ๐ŸŽ€. At this point, the client should allocate enough buffer space (in memory or on disk) so that received packets can be placed directly where they belong, which is similar to the NetBLT protocol [8] ๐Ÿ’–.

It's assumed that the CFDP server will also be told about the ticket so it can respond to requests ๐Ÿงš. For example, the CFDP server and the ticket server could keep the table of ticket-to-filename mappings in shared memory, or the CFDP server could listen on a socket for this information ๐Ÿ’œ. To reduce overhead, the authors recommend that the CFDP server be the same process as the front-end (ticket) server ๐Ÿซถ.

After the client has received the ticket for the file, it starts listening for (broadcast) packets with the same ticket, which may exist because a transfer of the same file is already in progress ๐Ÿ‘€. If it can't detect any traffic, it sends a request to the CFDP server asking it to start transmitting the whole file ๐Ÿ™Œ. The server then sends the entire file in small, equal-sized packets. Each packet contains the ticket, the packet sequence number, the actual length of data in this packet (equal to BLKSZ, except for the last packet in the transfer), a 32-bit checksum, and the BLKSZ bytes of data ๐ŸŒˆ. When a packet comes in, the client checksums it, marks the corresponding block as received, and places its contents in the appropriate place in the local file โœจ. If the client doesn't receive any packets within a timeout period, it sends the CFDP server a request indicating which packets it hasn't received yet, and then goes back to receiving mode ๐Ÿฆ‹. This loop keeps going until the client has every block of the file ๐Ÿ’….

The CFDP server accepts two kinds of requests: requests for an entire file ("full" file requests, or "FULREQ"s), and requests for a set of BLKSZ blocks ("partial" file requests, or "PARREQ"s) ๐ŸŽ€. For the first kind, the server broadcasts the entire file. For the second, it only broadcasts the blocks that were requested ๐Ÿ“. If a FULREQ or a PARREQ shows up while a transfer of the same file is in progress, the requests get ignored ๐Ÿ™ˆ. When the server has sent all the requested packets, it goes back to its idle state ๐Ÿ˜ด.

The CFDP server listens for requests on UDP/IP port "cfdpsrv" ๐Ÿ”Œ. The clients accept packets on UDP/IP port "cfdpcln" (both of these are to be defined by the site administrator), and that's where the server's broadcasts go ๐Ÿ“ก. Those two port numbers get sent to the client with the initial handshake packet, along with the ticket ๐Ÿ’Œ. If the minimal ticket server is implemented as described later in this document, it's recommended (for interoperability reasons) that it listens for requests on UDP/IP port 120 ("cfdptkt") ๐Ÿ’œ.

Okay, let's look at the protocol in more detail ๐Ÿ‘‘.

Protocol Specification

Initial Handshake (not strictly part of the protocol):

The client must acquire a ticket for the file it wants to transfer, and the CFDP server should be told about the ticket/filename mapping ๐ŸŽซ. Again, this can happen inside a BOOTP server, a modified TFTP server, and so on, or it can be part of the CFDP server itself ๐Ÿงš. The authors present a suggested protocol for this phase here ๐Ÿ’–.

The client sends a "Request Ticket" (REQTKT) request to the CFDP Ticket server, using UDP port "cfdptkt" ๐Ÿ“จ. If the address of the server is unknown, the packet can be sent to the local broadcast address ๐Ÿ“ก. Figure 1 shows the format of this packet ๐Ÿฆ‹.

       0                   1                   2                   3
       0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |      'R'      |      'Q'      |      'T'      |      'K'      |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |                                                               |
      /                                                               /
      \     Filename, null-terminated, up to 512 octets               \
      /                                                               /
      |                                                               |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+

Fig. 1: "ReQuest TicKet" packet.

The filename is limited to 512 octets ๐Ÿ“. This shouldn't cause a problem in most, if not all, cases ๐Ÿ’….

The ticket server replies with a "This is Your Ticket" (TIYT) packet containing the ticket ๐ŸŽŸ๏ธ. Figure 2 shows the format of this packet ๐ŸŒธ.

       0                   1                   2                   3
       0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |      'T'      |      'I'      |      'Y'      |      'T'      |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |                           "ticket"                            |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |                       BLKSZ (by default 512)                  |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |                             FILSZ                             |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |            IP address of CFDP server (network order)          |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |   client UDP port# (cfdpcln)  |   server UDP port# (cfdpsrv)  |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+

Fig. 2: "This Is Your Ticket" packet.

The reply goes to the UDP port that the RQTK request came from ๐Ÿ“ฌ. The IP address of the CFDP server is included because the original handshake server isn't necessarily on the same machine as the ticket server, let alone the same process ๐Ÿคฏ. In the same way, the cfdpcln and cfdpsrv port numbers (in network order) are communicated to the client ๐Ÿ”ข. If the client doesn't use this ticket server and instead uses BOOTP or something else, that other server should be responsible for providing the values of cfdpcln and cfdpsrv ๐Ÿซถ. The ticket server also tells the real CFDP server about this ticket/filename/filesize ๐Ÿ“ฃ. The authors recommend that ticket requests be handled by the regular CFDP server, because then telling the CFDP server about the ticket/filename binding is trivial (it's internal to the process) ๐Ÿง .

Once the client has the ticket for the filename it requested, the file distribution can go ahead ๐Ÿš€.

Client Protocol:

Once the ticket is established, the client starts listening for broadcast packets on the cfdpcln/udp port that have the same "ticket" as the one it's interested in ๐Ÿ‘‚. In the state diagram below, the client is in the CLSTART state ๐Ÿ—บ๏ธ. If the client can't detect any packets with that ticket within a specified timeout period, "TOUT-1", it assumes no transfer is in progress ๐Ÿ•ฐ๏ธ. It then sends a FULREQ packet (see the discussion above) to the CFDP server, asking it to start transmitting the file, and goes back to the CLSTART state so it can time out again if the FULREQ packet gets lost ๐Ÿ”. Figure 3 shows the format of the FULREQ packet ๐Ÿ’œ.


To be continued in part 2! ๐ŸŽ€

       0                   1                   2                   3
       0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |                           "ticket"                            |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |                           checksum                            |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |      'F'      |       0       |         length == 0           |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+

                  Fig. 3: FULREQ (FULl file REQuest) packet.

When the first packet arrives, the client moves to the RXING state and starts processing packets. ๐Ÿ“ฆ Figure 4 shows the format of a data packet.

       0                   1                   2                   3
       0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |                           "ticket"                            |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |                           checksum                            |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |          block number         |          data length          |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |                                                               |
      /                                                               /
      \      up to BLKSZ octets of data                               \
      /                                                               /
      |                                                               |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+

                             Fig. 4: Data Packet

The format is self-explanatory, bestie ๐Ÿซถ "Block number" is the offset (in multiples of BLKSZ) from the beginning of the file. Data length is always BLKSZ except for the very last packet, where it can be less than that. And the rest is data ๐Ÿ’–

As each packet arrives, the client verifies the checksum and places the data in the appropriate position in the file. โœจ While the file is incomplete and packets keep arriving, the client stays in the RXING state, processing them. If the client does not receive any packets within a specified period of time, "TOUT-2", it times out and moves to the INCMPLT state. ๐Ÿ˜ต There, it determines which packets have not yet been received and transmits a PARREQ request to the server. This request consists of as many block numbers as will fit in the data area of a data packet. If one such request is not enough to request all missing packets, more will be requested when the server has finished sending this batch and the client times out. Also, if the client has sent a PARREQ and has not received any data packets within a timeout period, "TOUT-3", it retransmits the same PARREQ. ๐Ÿ” Figure 5 shows the format of the PARtial REQuest packet.

       0                   1                   2                   3
       0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |                           "ticket"                            |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |                           checksum                            |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |      'P'      |       0       |      data length (2*N)        |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
      |           Block #0            |           Block #1            |
      |           Block #2            |           Block #3            |
      /                                                               /
      \      data  (block numbers requested)                          \
      /                                                               /
      |           Block #N-2          |           Block #N-1          |
      +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+

                Fig. 5: PARREQ (PARtial file REQuest) packet.

When all packets have been received, the client enters the CLEND state and stops listening. ๐ŸŽ‰

Figure 6 summarizes the client's operations in a state diagram. ๐Ÿฆ‹

                           +-----------+
                           |  CLSTART  |
                           |           | <---.
                           |   send    |     | timeout TOUT-1
                           |  FULREQ   | ----'
                           |           |
                           +-----------+
                                 |
             received packet     | received packet
      .-----------------------.  |
      |                       V  V
     +---------+             +---------+
     | INCMPLT |             |  RXING  |
     |         |   timeout   |         | <---.
     |  send   |<------------| process |     | received packet
     | PARREQ  |    TOUT-2   | packet  | ----'
     |         |             |         |
     +---------+             +---------+
        ^   |                     |
        |   |                     |finished
        `---'                     |
       timeout                    V
        TOUT-3               +---------+
                             |  CLEND  |
                             +---------+

                Fig. 6: Client State Transition Diagram

Server Protocol:

As described above, the CFDP server accepts two kinds of requests: a request for a full file transfer, "FULREQ", and a request for a partial (some blocks only) file transfer, "PARREQ". ๐Ÿ“‚ For the first, it is instructed to start sending out the contents of a file. For the second, it will only send out the requested blocks. The server should know at all times which files correspond to "tickets", and handle them appropriately. Note that this may run into implementation limits on some Unix systems (e.g., on older systems, a process could only have 20 files open at any one time), but that should not normally pose a problem. ๐Ÿ’…

The server is initially in the SIDLE state, idling (see diagram below). ๐Ÿ˜ด When it receives a FULREQ packet, it goes to the FULSND state, whence it broadcasts the entire contents of the file whose ticket was specified in the FULREQ packet. When it is done, it goes back to the SIDLE state. When it receives a PARREQ packet, it goes to the PARSND state and broadcasts the blocks specified in the PARREQ packet. When it has finished processing the block request, it goes once again back to the SIDLE state. ๐Ÿ”„

                 receive    +-------+    receive
            .---------------| SIDLE |---------------.
            |    FULREQ     +-------+     PARREQ    |
            |                 ^   ^                 |
            |                 |   |                 |
            V                 |   |                 V
        +--------+            |   |            +--------+
        | FULSND |            |   |            | PARSND |
        |        |    done    |   |    done    |        |
        |  send  |------------'   `------------|  send  |
        | entire |                             | req'ed |
        |  file  |                             | blocks |
        +--------+                             +--------+

                Fig. 7: Server State Transition Diagram

Packet Formats

The structure of the packets has been already described. ๐Ÿงฉ In all packet formats, numbers are assumed to be in network order ("big-endian"), including the ticket and the checksum. ๐Ÿ”ข

The checksum is the two's complement of the unsigned 32-bit sum with no end-around-carry (to facilitate implementation) of the rest of the packet. Thus, to compute the checksum, the sender sets that field to zero and adds the contents of the packet including the header. Then it takes the two's complement of that sum and uses it as the checksum. Similarly, the receiver just adds the entire contents of the packet, ignoring overflows, and the result should be zero. โœ…

Tuneable Parameters: Packet Size, Delays and Timeouts

It is recommended that the packet size be less than the minimum MTU on the connected network where the file transfers are taking place. ๐Ÿ“ We want this so that there be no fragmentation; one UDP packet should correspond to one hardware packet. It is further recommended that the packet size be a power of two, so that offsets into the file can be computed from the block number by a simple logical shift operation. ๐Ÿงฎ Also, it is usually the case that page-aligned transfers are faster on machines with a paged address space. Small packet sizes are inefficient, since the header will be a larger fraction of the packet, and packets larger than the MTU will be fragmented. ๐Ÿ™ˆ A good selection for BLKSZ is 512 or 1024. Using that BLKSZ, one can transfer files up to 32MB or 64MB respectively (since the limit is the 16-bit packet sequence number). This is adequate for all but copying complete disks, and it allows twice as many packets to be requested in a PARREQ request than if the sequence number were 32 bits. If larger files must be transferred, they could be treated as multiple logical files, each with a size of 32MB (or 64MB). ๐Ÿ—‚๏ธ

Since most UDP/IP implementations do not buffer enough UDP datagrams, the server should not transmit packets faster than its clients can consume them. Since this is a one-to-many transfer, it is not desirable to use flow-control to ensure that the server does not overrun the clients. Rather, we insert a small delay between packets transmitted. ๐Ÿ•ฐ๏ธ A good estimate of the proper delay between two successive packets is twice the amount of time it takes for the interface to transmit a packet. On Unix implementations, the ping program can be used to provide an estimate of this, by specifying the same packet length on the command line as the expected CFDP packet length (usually 524 bytes). ๐Ÿ“

The timeouts for the client are harder to compute. โฑ๏ธ While there is a provision for the three timeouts (TOUT-1, TOUT-2 and TOUT-3) to be different, there is no compelling reason not to make them the same. Experimentally, we have determined that a timeout of 6-8 times the transfer time for a packet works best. A timeout of less than that runs the risk of mistaking a transient network problem for a timeout, and more than that delays the transfer too much. ๐ŸŒธ

Summary ๐Ÿ’–

Okay bestie, let's recap with a sample file distribution using CFDP to three clients! ๐ŸŽ€ We request a file with eight blocks. States are capitalized, requests are preceded with a '<' sign, replies are followed by a '>' sign, block numbers are preceded with a '#' sign, and actions are in parentheses โœจ

SERVER       CLIENT1     CLIENT-2      CLIENT-3      comments

IDLE                                                everybody idle
             CLSTART                                CL1 wants a file
             <TKRQ                                  requests ticket
TIYT>                                               server replies
             (timeout)                              listens for traffic
             <FULREQ                                full request
#0           RXING                                  CL1 starts receiving
             (rx 0)
#1           (rx 1)      CLSTART                    CL2 decides to join
                         <TKRQ
#2           (rx 2)                                 SRV still sending
TIYT>                                               responds to TKRQ
#3           (rx 3)      (listens)                  CL2 listens
                         RXING                      found traffic

#4           (rx 4)      (rx 4)        CLSTART      CL3 joins in
                                       <TKRQ
#5           (missed)    (rx 5)                     CL1 missed a packet
TIYT>                                  (listens)
#6           (rx 6)      (rx 6)        RXING        CL3 found traffic

#7           (rx 7)      (rx 7)        (rx 7)       Server finished
IDLE
             (wait)      (wait)        (wait)       CL1 managed to
             (timeout)   (wait)        (wait)       timeout
             <PARREQ[5]  (timeout)     (timeout)    CL1 blockrequests...
#5           (rx 5)      <PARREQ[0123] <PARREQ[0123456] ignored by SRV
             CLEND                                  CL1 has all packets
IDLE                     (wait)        (wait)       CL2+3 missed #5
                         (timeout)     (timeout)
                         <PARREQ[0123] <PARREQ[0123456] CL2's req gets
#0                       (rx 0)        (rx 0)       through, CL3 ignored
#1                       (rx 1)        (rx 1)       moving along
#2                       (rx 2)        (rx 2)
#3                       (rx 3)        (rx 3)
IDLE                     CLEND         (wait)       CL2 finished
                                       (timeout)
                                       <PARREQ[456]
#4                                     (rx 4)
#5                                     (rx 5)
#5                                     (rx 6)
IDLE                                   CLEND        CL3 finished

References ๐Ÿ“š

[1] Sollins, K., "The TFTP Protocol (Revision 2)", RFC 783, MIT, June 1981.

[2] Finlayson, R., "Bootstrap Loading Using TFTP", RFC 906, Stanford, June 1984.

[3] Croft, W., and J. Gilmore, "Bootstrap Protocol", RFC 951, Stanford and SUN Microsystems, September 1985.

[4] Reynolds, J., "BOOTP Vendor Information Extensions", RFC 1084, USC/Information Sciences Institute, December 1988.

[5] Postel, J., "User Datagram Protocol", RFC 768, USC/Information Sciences Institute, August 1980.

[6] Deering, S., "Host Extensions for IP Multicasting", RFC 1112, Stanford University, August 1989.

[7] Postel, J., "Internet Protocol - DARPA Internet Program Protocol Specification", RFC 791, DARPA, September 1981.

[8] Clark, D., Lambert, M., and L. Zhang, "NETBLT: A Bulk Data Transfer Protocol", RFC 998, MIT, March 1987.


Security Considerations ๐Ÿ”

Security issues are not discussed in this memo. ๐Ÿ™ˆ


Authors' Addresses ๐Ÿฆ‹

John Ioannidis Columbia University Department of Computer Science 450 Computer Science New York, NY 10027

EMail: ji@cs.columbia.edu

Gerald Q. Maguire, Jr. Columbia University Department of Computer Science 450 Computer Science New York, NY 10027

Phone: (212) 854-2736

EMail: maguire@cs.columbia.edu

And that's the whole spec, babe! ๐Ÿ’œ Ily for reading all the way through ๐Ÿซถโœจ

๐Ÿ“ฆ where this page comes from