Merge from vendor branch LIBARCHIVE:
[dragonfly.git] / sys / sys / syslink.h
1 /*
2  * Copyright (c) 2004-2007 The DragonFly Project.  All rights reserved.
3  * 
4  * This code is derived from software contributed to The DragonFly Project
5  * by Matthew Dillon <dillon@backplane.com>
6  * 
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  * 
11  * 1. Redistributions of source code must retain the above copyright
12  *    notice, this list of conditions and the following disclaimer.
13  * 2. Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in
15  *    the documentation and/or other materials provided with the
16  *    distribution.
17  * 3. Neither the name of The DragonFly Project nor the names of its
18  *    contributors may be used to endorse or promote products derived
19  *    from this software without specific, prior written permission.
20  * 
21  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
24  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE
25  * COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
26  * INCIDENTAL, SPECIAL, EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING,
27  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
28  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
29  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
30  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
31  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
32  * SUCH DAMAGE.
33  *
34  * $DragonFly: src/sys/sys/syslink.h,v 1.7 2007/04/26 02:11:00 dillon Exp $
35  */
36
37 /*
38  * The syslink infrastructure implements an optimized RPC mechanism across a 
39  * communications link.  RPC functions are grouped together into larger
40  * protocols.  Prototypes are typically associated with system structures
41  * but do not have to be.
42  *
43  * syslink      - Implements a communications end-point and protocol.  A
44  *                syslink is typically directly embedded in a related
45  *                structure.
46  *
47  * syslink_proto- Specifies a set of RPC functions.
48  *
49  * syslink_desc - Specifies a single RPC function within a protocol.
50  */
51
52 #ifndef _SYS_SYSLINK_H_
53 #define _SYS_SYSLINK_H_
54
55 #ifndef _SYS_TYPES_H_
56 #include <sys/types.h>
57 #endif
58 #ifndef _SYS_TREE_H_
59 #include <sys/tree.h>
60 #endif
61 #ifndef _SYS_SOCKET_H_
62 #include <sys/socket.h>
63 #endif
64
65 /*
66  * SYSIDs are 64 bit entities and come in two varieties.  Physical SYSIDs
67  * are used to efficiently route messages across the mesh, while Logical
68  * SYSIDs are persistently assigned identifiers representing specific devices
69  * or specific media or named filesystems.  That is, the logical SYSID
70  * assigned to a filesystem or ANVIL partition can be stored in that
71  * filesystem's superblock and allows the filesystem to migrate or
72  * be multi-homed (have multiple physical SYSIDs representing the same
73  * logical entity).
74  *
75  * Physical SYSIDs can be ever-changing, and any given logical SYSID could
76  * in fact have multiple physical SYSIDs associated with it.  The mesh is
77  * self-healing and the combination of the logical and physical sysid
78  * basically validates the message at the target and determines whether
79  * the physical SYSID must be recalculated (looked up again) or not.
80  */
81 typedef u_int64_t       sysid_t;
82
83 /***************************************************************************
84  *                              PROTOCOL API/ABI                           *
85  ***************************************************************************
86  *
87  * These structures implement the programming interface for end-points and
88  * RPC calls.
89  */
90
91 struct syslink;
92 struct syslink_ops;
93 struct syslink_proto;
94 struct syslink_transport;
95 struct syslink_desc;
96 struct syslink_generic_args;
97
98 typedef int (*syslink_func_t)(struct syslink_generic_args *);
99
100 /*
101  * Commands for the syslink system call.
102  *
103  * CREATE:      Create a new syslink route node with the route node sysid
104  *              and label information specified in the passed info structure.
105  *              0 on success, -1 on failure or if the route node already
106  *              exists.  
107  *
108  *              The info structure must also contain the number of bits of
109  *              address space you wish this route node to use.
110  *
111  * DESTROY:     Destroy the existing syslink route node with the route node
112  *              sysid specified in the passed info structure.
113  *              0 on success, -1 on failure.
114  *
115  * LOCATE:      Locate the first syslink route node with a sysid greater or
116  *              equal to the sysid specified in the passed info structure.
117  *              The info structure will be loaded on success and the linkid
118  *              field will also be cleared.
119  *
120  *              To scan route nodes, start by specifying a sysid 0.  On
121  *              success, increment the sysid in the info structure and loop.
122  *
123  *              You can also use the contents of the info structure to
124  *              initiate a scan of links within the route node via the FIND
125  *              command.  The sysid will remain unchanged through the scan
126  *              and on completion you can increment it and loop up to 
127  *              the next LOCATE.
128  *
129  * ADD:         Add a link to the route node specified in the info structure.
130  *              The route node must exist and must contain sufficient
131  *              address space to handle the new link.  If associating a file
132  *              descriptor, 0 is returned on success and -1 on failure.
133  *              If obtaining a direct syslink file descriptor, the new
134  *              descriptor is returned on success or -1 on failure.
135  *
136  *              On return, the linkid in the info structure is filled in and
137  *              other adjustments may also have been made.
138  *
139  *              The info structure must contain the number of bits of
140  *              address space required by the link.  If 0 is specified,
141  *              a direct stream or connected socket is expected.  If
142  *              non-zero, a switch is assumed (typically a switched UDP
143  *              socket).  An all 0's address is reserved and an all 1's
144  *              address implies a broadcast.  All other addresses imply
145  *              single targets within the switched infrastructure.
146  *              
147  *              FLAGS SUPPORTED:
148  *
149  *              SENDTO          This allows you to directly associate a
150  *                              UDP socket and subnet with a syslink route
151  *                              node.  To use this option the info structure
152  *                              must contain a sockaddr representing the
153  *                              broadcast address.  The low bits are adjusted
154  *                              based on the size of the subnet (as
155  *                              specified with PHYSBITS) to forward messages.
156  *                              If not specified, write() is used and the
157  *                              target is responsible for any switch
158  *                              demultiplexing.
159  *
160  *              PACKET          Indicates that messages are packetized.
161  *                              syslink will aggregate multiple syslink
162  *                              messages into a single packet if possible,
163  *                              but will not exceed 16384 bytes per packet
164  *                              and will not attempt to pad messages to
165  *                              align them for FIFO debuffering.
166  *
167  * REM:         Disassociate a link using the route node and linkid
168  *              specified in the info structure. 
169  *
170  *              The syslink route node will close() the related descriptor
171  *              (or cause an EOF to occur for any direct syslink descriptor).
172  *
173  * FIND:        Locate the first linkid greater or equal to the linkid
174  *              in the passed info structure for the route node sysid 
175  *              specified in the info structure, and fill in the rest of the
176  *              structure as appropriate.
177  *
178  *              To locate the first link for any given route sysid, set
179  *              linkid to 0.  To scan available links, increment the
180  *              returned linkid before looping.
181  */
182
183 #define SYSLINK_CMD_CREATE      0x00000001      /* create route node */
184 #define SYSLINK_CMD_DESTROY     0x00000002      /* destroy route node */
185 #define SYSLINK_CMD_LOCATE      0x00000003      /* locate first route node */
186 #define SYSLINK_CMD_ADD         0x00000004      /* add link */
187 #define SYSLINK_CMD_REM         0x00000005      /* remove link */
188 #define SYSLINK_CMD_FIND        0x00000006      /* locate link info */
189
190 #define SYSLINK_LABEL_SIZE      32
191 #define SYSLINK_ROUTER_MAXBITS  20
192
193 enum syslink_type { SYSLINK_TYPE_ROUTER, SYSLINK_TYPE_MANAGER, SYSLINK_TYPE_SEED, SYSLINK_TYPE_TERMINAL };
194
195 /*
196  * syslink_info structure
197  *
198  * This structure contains information about a syslink route node or 
199  * linkage.
200  */
201 struct syslink_info {
202         int version;                    /* info control structure version */
203         int fd;                         /* file descriptor (CMD_ADD) */
204         int linkid;                     /* linkid (base physical address) */
205         int bits;                       /* physical address bits if switched */
206         int flags;                      /* message control/switch flags */
207         enum syslink_type type;
208         sysid_t sysid;                  /* route node sysid */
209         char label[SYSLINK_LABEL_SIZE]; /* symbolic name */
210         char reserved[32];
211         union {
212                 struct sockaddr sa;     /* required for SLIF_SENDTO */
213         } u;
214 };
215
216 /*
217  * SLIF_PACKET - specify when the descriptor represents packetized data,
218  *               where a single read or write reads or writes whole packets.
219  *               For example, a UDP socket.  Otherwise a stream is assumed.
220  *
221  * SLIF_XSWITCH- specify when the descriptor represents a switched message
222  *               source where the target has no means of discerning the
223  *               subnet address the message is being sent to.
224  *
225  *               This case occurs when a stream connection is used to
226  *               represented a switch instead of a single end-to-end
227  *               connection.  Instead of trying to tag the stream
228  *               messages with some kind of mac header, we instead require
229  *               that the originator pre-adjust the syslink_msg header's
230  *               src and dst fields based on the number of bits being
231  *               switched.  The target will then renormalize the address
232  *               fields to merge its own linkid base in.
233  */
234 #define SLIF_PACKET     0x0001          /* packetized, else stream */
235 #define SLIF_XSWITCH    0x0002          /* router must extract/gen IP addrs */
236 #if defined(_KERNEL) || defined(_KERNEL_STRUCTURES)
237 #define SLIF_RQUIT      0x0400
238 #define SLIF_WQUIT      0x0800
239 #define SLIF_RDONE      0x1000
240 #define SLIF_WDONE      0x2000
241 #define SLIF_DESTROYED  0x4000
242 #define SLIF_ERROR      0x8000
243 #endif
244
245 #define SLIF_USERFLAGS          (SLIF_PACKET|SLIF_XSWITCH)
246
247 #if !defined(_KERNEL)
248 int syslink(int, struct syslink_info *, size_t);
249 #endif
250
251 #endif