xref: /freebsd/sys/netgraph/ng_parse.h (revision 2ff63af9b88c7413b7d71715b5532625752a248e)
1f8307e12SArchie Cobbs /*
2f8307e12SArchie Cobbs  * ng_parse.h
3c398230bSWarner Losh  */
4c398230bSWarner Losh 
5c398230bSWarner Losh /*-
6f8307e12SArchie Cobbs  * Copyright (c) 1999 Whistle Communications, Inc.
7f8307e12SArchie Cobbs  * All rights reserved.
8f8307e12SArchie Cobbs  *
9f8307e12SArchie Cobbs  * Subject to the following obligations and disclaimer of warranty, use and
10f8307e12SArchie Cobbs  * redistribution of this software, in source or object code forms, with or
11f8307e12SArchie Cobbs  * without modifications are expressly permitted by Whistle Communications;
12f8307e12SArchie Cobbs  * provided, however, that:
13f8307e12SArchie Cobbs  * 1. Any and all reproductions of the source or object code must include the
14f8307e12SArchie Cobbs  *    copyright notice above and the following disclaimer of warranties; and
15f8307e12SArchie Cobbs  * 2. No rights are granted, in any manner or form, to use Whistle
16f8307e12SArchie Cobbs  *    Communications, Inc. trademarks, including the mark "WHISTLE
17f8307e12SArchie Cobbs  *    COMMUNICATIONS" on advertising, endorsements, or otherwise except as
18f8307e12SArchie Cobbs  *    such appears in the above copyright notice or in the software.
19f8307e12SArchie Cobbs  *
20f8307e12SArchie Cobbs  * THIS SOFTWARE IS BEING PROVIDED BY WHISTLE COMMUNICATIONS "AS IS", AND
21f8307e12SArchie Cobbs  * TO THE MAXIMUM EXTENT PERMITTED BY LAW, WHISTLE COMMUNICATIONS MAKES NO
22f8307e12SArchie Cobbs  * REPRESENTATIONS OR WARRANTIES, EXPRESS OR IMPLIED, REGARDING THIS SOFTWARE,
23f8307e12SArchie Cobbs  * INCLUDING WITHOUT LIMITATION, ANY AND ALL IMPLIED WARRANTIES OF
24f8307e12SArchie Cobbs  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, OR NON-INFRINGEMENT.
25f8307e12SArchie Cobbs  * WHISTLE COMMUNICATIONS DOES NOT WARRANT, GUARANTEE, OR MAKE ANY
26f8307e12SArchie Cobbs  * REPRESENTATIONS REGARDING THE USE OF, OR THE RESULTS OF THE USE OF THIS
27f8307e12SArchie Cobbs  * SOFTWARE IN TERMS OF ITS CORRECTNESS, ACCURACY, RELIABILITY OR OTHERWISE.
28f8307e12SArchie Cobbs  * IN NO EVENT SHALL WHISTLE COMMUNICATIONS BE LIABLE FOR ANY DAMAGES
29f8307e12SArchie Cobbs  * RESULTING FROM OR ARISING OUT OF ANY USE OF THIS SOFTWARE, INCLUDING
30f8307e12SArchie Cobbs  * WITHOUT LIMITATION, ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY,
31f8307e12SArchie Cobbs  * PUNITIVE, OR CONSEQUENTIAL DAMAGES, PROCUREMENT OF SUBSTITUTE GOODS OR
32f8307e12SArchie Cobbs  * SERVICES, LOSS OF USE, DATA OR PROFITS, HOWEVER CAUSED AND UNDER ANY
33f8307e12SArchie Cobbs  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
34f8307e12SArchie Cobbs  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
35f8307e12SArchie Cobbs  * THIS SOFTWARE, EVEN IF WHISTLE COMMUNICATIONS IS ADVISED OF THE POSSIBILITY
36f8307e12SArchie Cobbs  * OF SUCH DAMAGE.
37f8307e12SArchie Cobbs  *
38cc3bbd68SJulian Elischer  * Author: Archie Cobbs <archie@freebsd.org>
39f8307e12SArchie Cobbs  *
40f8307e12SArchie Cobbs  * $Whistle: ng_parse.h,v 1.2 1999/11/29 01:43:48 archie Exp $
41f8307e12SArchie Cobbs  */
42f8307e12SArchie Cobbs 
43e20480bfSRuslan Ermilov #ifndef _NETGRAPH_NG_PARSE_H_
44e20480bfSRuslan Ermilov #define _NETGRAPH_NG_PARSE_H_
45f8307e12SArchie Cobbs 
46f8307e12SArchie Cobbs /*
47f8307e12SArchie Cobbs 
48f8307e12SArchie Cobbs   This defines a library of routines for converting between various C
49f8307e12SArchie Cobbs   language types in binary form and ASCII strings.  Types are user
5063e2ac54SArchie Cobbs   definable.  Several pre-defined types are supplied, for some common
5163e2ac54SArchie Cobbs   C types: structures, variable and fixed length arrays, integer types,
5263e2ac54SArchie Cobbs   variable and fixed length strings, IP addresses, etc.
5363e2ac54SArchie Cobbs 
5463e2ac54SArchie Cobbs   A netgraph node type may provide a list of types that correspond to
5563e2ac54SArchie Cobbs   the structures it expects to send and receive in the arguments field
5663e2ac54SArchie Cobbs   of a control message.  This allows these messages to be converted
5763e2ac54SArchie Cobbs   between their native binary form and the corresponding ASCII form.
5863e2ac54SArchie Cobbs 
5963e2ac54SArchie Cobbs   A future use of the ASCII form may be for inter-machine communication
6063e2ac54SArchie Cobbs   of control messages, because the ASCII form is machine independent
6163e2ac54SArchie Cobbs   whereas the native binary form is not.
62f8307e12SArchie Cobbs 
63f8307e12SArchie Cobbs   Syntax
64f8307e12SArchie Cobbs   ------
65f8307e12SArchie Cobbs 
66f8307e12SArchie Cobbs     Structures:
67f8307e12SArchie Cobbs 
68f8307e12SArchie Cobbs       '{' [ <name>=<value> ... ] '}'
69f8307e12SArchie Cobbs 
70f8307e12SArchie Cobbs       Omitted fields have their default values by implication.
71f8307e12SArchie Cobbs       The order in which the fields are specified does not matter.
72f8307e12SArchie Cobbs 
73f8307e12SArchie Cobbs     Arrays:
74f8307e12SArchie Cobbs 
75f8307e12SArchie Cobbs       '[' [ [index=]<value> ... ] ']'
76f8307e12SArchie Cobbs 
77f8307e12SArchie Cobbs       Element value may be specified with or without the "<index>=" prefix;
78f8307e12SArchie Cobbs       If omitted, the index after the previous element is used.
79f8307e12SArchie Cobbs       Omitted fields have their default values by implication.
80f8307e12SArchie Cobbs 
81f8307e12SArchie Cobbs     Strings:
82f8307e12SArchie Cobbs 
83f8307e12SArchie Cobbs       "foo bar blah\r\n"
84f8307e12SArchie Cobbs 
85f8307e12SArchie Cobbs       That is, strings are specified just like C strings. The usual
86f8307e12SArchie Cobbs       backslash escapes are accepted.
87f8307e12SArchie Cobbs 
8863e2ac54SArchie Cobbs     Other simple types (integers, IP addresses) have their obvious forms.
89f8307e12SArchie Cobbs 
90f8307e12SArchie Cobbs   Example
91f8307e12SArchie Cobbs   -------
92f8307e12SArchie Cobbs 
9363e2ac54SArchie Cobbs     Suppose we have a netgraph command that takes as an argument
9463e2ac54SArchie Cobbs     a 'struct foo' shown below.  Here is an example of a possible
9563e2ac54SArchie Cobbs     value for the structure, and the corresponding ASCII encoding
9663e2ac54SArchie Cobbs     of that value:
9763e2ac54SArchie Cobbs 
9863e2ac54SArchie Cobbs 	Structure			Binary value
9963e2ac54SArchie Cobbs 	---------			------------
100f8307e12SArchie Cobbs 
101f8307e12SArchie Cobbs 	struct foo {
10263e2ac54SArchie Cobbs 	    struct in_addr ip;  	01 02 03 04
103f8307e12SArchie Cobbs 	    int bar;			00 00 00 00
10463e2ac54SArchie Cobbs 	    char label[8];		61 62 63 0a 00 00 00 00
10563e2ac54SArchie Cobbs 	    u_char alen;		03 00
106d56ace09SRuslan Ermilov 	    short ary[];	  	05 00 00 00 0a 00
107f8307e12SArchie Cobbs 	};
108f8307e12SArchie Cobbs 
10963e2ac54SArchie Cobbs 	ASCII value
11063e2ac54SArchie Cobbs 	-----------
11163e2ac54SArchie Cobbs 	{ ip=1.2.3.4 label="abc\n" alen=3 ary=[ 5 2=10 ] }
11263e2ac54SArchie Cobbs 
11363e2ac54SArchie Cobbs     Note that omitted fields and array elements get their default
11463e2ac54SArchie Cobbs     values ("bar" and ary[2]), and that the alignment is handled
115d62d2396SRoman Kurakin     automatically (the extra 00 byte after "alen").  Also, since byte
11663e2ac54SArchie Cobbs     order and alignment are inherently machine dependent, so is this
11763e2ac54SArchie Cobbs     conversion process.  The above example shows an x86 (little
11863e2ac54SArchie Cobbs     endian) encoding.  Also the above example is tricky because the
11963e2ac54SArchie Cobbs     structure is variable length, depending on 'alen', the number of
12063e2ac54SArchie Cobbs     elements in the array 'ary'.
12163e2ac54SArchie Cobbs 
12263e2ac54SArchie Cobbs     Here is how one would define a parse type for the above structure,
12363e2ac54SArchie Cobbs     subclassing the pre-defined types below.  We construct the type in
12463e2ac54SArchie Cobbs     a 'bottom up' fashion, defining each field's type first, then the
12563e2ac54SArchie Cobbs     type for the whole structure ('//' comments used to avoid breakage).
12663e2ac54SArchie Cobbs 
12763e2ac54SArchie Cobbs     // Super-type info for 'label' field
128c1b9e5f2SArchie Cobbs     struct ng_parse_fixedstring_info foo_label_info = { 8 };
12963e2ac54SArchie Cobbs 
13063e2ac54SArchie Cobbs     // Parse type for 'label' field
13163e2ac54SArchie Cobbs     struct ng_parse_type foo_label_type = {
13263e2ac54SArchie Cobbs 	    &ng_parse_fixedstring_type		// super-type
13363e2ac54SArchie Cobbs 	    &foo_label_info			// super-type info
13463e2ac54SArchie Cobbs     };
13563e2ac54SArchie Cobbs 
13663e2ac54SArchie Cobbs     #define OFFSETOF(s, e) ((char *)&((s *)0)->e - (char *)((s *)0))
13763e2ac54SArchie Cobbs 
13863e2ac54SArchie Cobbs     // Function to compute the length of the array 'ary', which
13963e2ac54SArchie Cobbs     // is variable length, depending on the previous field 'alen'.
14063e2ac54SArchie Cobbs     // Upon entry 'buf' will be pointing at &ary[0].
14163e2ac54SArchie Cobbs     int
14263e2ac54SArchie Cobbs     foo_ary_getLength(const struct ng_parse_type *type,
14363e2ac54SArchie Cobbs 	    const u_char *start, const u_char *buf)
14463e2ac54SArchie Cobbs     {
14563e2ac54SArchie Cobbs 	    const struct foo *f;
14663e2ac54SArchie Cobbs 
14763e2ac54SArchie Cobbs 	    f = (const struct foo *)(buf - OFFSETOF(struct foo, ary));
14863e2ac54SArchie Cobbs 	    return f->alen;
14963e2ac54SArchie Cobbs     }
15063e2ac54SArchie Cobbs 
15163e2ac54SArchie Cobbs     // Super-type info for 'ary' field
15263e2ac54SArchie Cobbs     struct ng_parse_array_info foo_ary_info = {
15363e2ac54SArchie Cobbs 	    &ng_parse_int16_type,		// element type
15463e2ac54SArchie Cobbs 	    &foo_ary_getLength			// func to get array length
15563e2ac54SArchie Cobbs     }
15663e2ac54SArchie Cobbs 
15763e2ac54SArchie Cobbs     // Parse type for 'ary' field
15863e2ac54SArchie Cobbs     struct ng_parse_type foo_ary_type = {
15963e2ac54SArchie Cobbs 	    &ng_parse_array_type,		// super-type
16063e2ac54SArchie Cobbs 	    &foo_ary_info			// super-type info
16163e2ac54SArchie Cobbs     };
16263e2ac54SArchie Cobbs 
16363e2ac54SArchie Cobbs     // Super-type info for struct foo
164f0184ff8SArchie Cobbs     struct ng_parse_struct_field foo_fields[] = {
16563e2ac54SArchie Cobbs 	    { "ip",	&ng_parse_ipaddr_type	},
16663e2ac54SArchie Cobbs 	    { "bar",	&ng_parse_int32_type	},
16763e2ac54SArchie Cobbs 	    { "label",	&foo_label_type		},
1687b3bf3f9SArchie Cobbs 	    { "alen",	&ng_parse_uint8_type	},
16963e2ac54SArchie Cobbs 	    { "ary",	&foo_ary_type		},
17063e2ac54SArchie Cobbs 	    { NULL }
17163e2ac54SArchie Cobbs     };
17263e2ac54SArchie Cobbs 
17363e2ac54SArchie Cobbs     // Parse type for struct foo
17463e2ac54SArchie Cobbs     struct ng_parse_type foo_type = {
17563e2ac54SArchie Cobbs 	    &ng_parse_struct_type,		// super-type
17663e2ac54SArchie Cobbs 	    &foo_fields				// super-type info
17763e2ac54SArchie Cobbs     };
178f8307e12SArchie Cobbs 
179f8307e12SArchie Cobbs   To define a type, you can define it as a sub-type of a predefined
18063e2ac54SArchie Cobbs   type as shown above, possibly overriding some of the predefined
18163e2ac54SArchie Cobbs   type's methods, or define an entirely new syntax, with the restriction
18263e2ac54SArchie Cobbs   that the ASCII representation of your type's value must not contain
18363e2ac54SArchie Cobbs   any whitespace or any of these characters: { } [ ] = "
18463e2ac54SArchie Cobbs 
18563e2ac54SArchie Cobbs   See ng_ksocket.c for an example of how to do this for 'struct sockaddr'.
18663e2ac54SArchie Cobbs   See ng_parse.c to see implementations of the pre-defined types below.
187f8307e12SArchie Cobbs 
188f8307e12SArchie Cobbs */
189f8307e12SArchie Cobbs 
190f8307e12SArchie Cobbs /************************************************************************
191f8307e12SArchie Cobbs 			METHODS REQUIRED BY A TYPE
192f8307e12SArchie Cobbs  ************************************************************************/
193f8307e12SArchie Cobbs 
194f8307e12SArchie Cobbs /*
195f8307e12SArchie Cobbs  * Three methods are required for a type. These may be given explicitly
19663e2ac54SArchie Cobbs  * or, if NULL, inherited from the super-type.  The 'getDefault' method
19763e2ac54SArchie Cobbs  * is always optional; the others are required if there is no super-type.
198f8307e12SArchie Cobbs  */
199f8307e12SArchie Cobbs 
200f8307e12SArchie Cobbs struct ng_parse_type;
201f8307e12SArchie Cobbs 
202f8307e12SArchie Cobbs /*
203f8307e12SArchie Cobbs  * Convert ASCII to binary according to the supplied type.
204f8307e12SArchie Cobbs  *
205f8307e12SArchie Cobbs  * The ASCII characters begin at offset *off in 'string'.  The binary
206f8307e12SArchie Cobbs  * representation is put into 'buf', which has at least *buflen bytes.
207f8307e12SArchie Cobbs  * 'start' points to the first byte output by ng_parse() (ie, start <= buf).
208f8307e12SArchie Cobbs  *
209f8307e12SArchie Cobbs  * Upon return, *buflen contains the length of the new binary data, and
210f8307e12SArchie Cobbs  * *off is updated to point just past the end of the parsed range of
211f8307e12SArchie Cobbs  * characters, or, in the case of an error, to the offending character(s).
212f8307e12SArchie Cobbs  *
213f8307e12SArchie Cobbs  * Return values:
214f8307e12SArchie Cobbs  *	0		Success; *buflen holds the length of the data
215f8307e12SArchie Cobbs  *			and *off points just past the last char parsed.
216f8307e12SArchie Cobbs  *	EALREADY	Field specified twice
217f8307e12SArchie Cobbs  *	ENOENT		Unknown field
218f8307e12SArchie Cobbs  *	E2BIG		Array or character string overflow
219f8307e12SArchie Cobbs  *	ERANGE		Output was longer than *buflen bytes
220f8307e12SArchie Cobbs  *	EINVAL		Parse failure or other invalid content
221f8307e12SArchie Cobbs  *	ENOMEM		Out of memory
222f8307e12SArchie Cobbs  *	EOPNOTSUPP	Mandatory array/structure element missing
223f8307e12SArchie Cobbs  */
224f8307e12SArchie Cobbs typedef	int	ng_parse_t(const struct ng_parse_type *type, const char *string,
225f8307e12SArchie Cobbs 			int *off, const u_char *start,
226f8307e12SArchie Cobbs 			u_char *buf, int *buflen);
227f8307e12SArchie Cobbs 
228f8307e12SArchie Cobbs /*
229f8307e12SArchie Cobbs  * Convert binary to ASCII according to the supplied type.
230f8307e12SArchie Cobbs  *
231f8307e12SArchie Cobbs  * The results are put into 'buf', which is at least buflen bytes long.
232f8307e12SArchie Cobbs  * *off points to the current byte in 'data' and should be updated
233f8307e12SArchie Cobbs  * before return to point just past the last byte unparsed.
234f8307e12SArchie Cobbs  *
235f8307e12SArchie Cobbs  * Returns:
236f8307e12SArchie Cobbs  *	0		Success
237f8307e12SArchie Cobbs  *	ERANGE		Output was longer than buflen bytes
238f8307e12SArchie Cobbs  */
239f8307e12SArchie Cobbs typedef	int	ng_unparse_t(const struct ng_parse_type *type,
240f8307e12SArchie Cobbs 			const u_char *data, int *off, char *buf, int buflen);
241f8307e12SArchie Cobbs 
242f8307e12SArchie Cobbs /*
243f8307e12SArchie Cobbs  * Compute the default value according to the supplied type.
244f8307e12SArchie Cobbs  *
245f8307e12SArchie Cobbs  * Store the result in 'buf', which is at least *buflen bytes long.
246f8307e12SArchie Cobbs  * Upon return *buflen contains the length of the output.
247f8307e12SArchie Cobbs  *
248f8307e12SArchie Cobbs  * Returns:
249f8307e12SArchie Cobbs  *	0		Success
250f8307e12SArchie Cobbs  *	ERANGE		Output was longer than *buflen bytes
251f8307e12SArchie Cobbs  *	EOPNOTSUPP	Default value is not specified for this type
252f8307e12SArchie Cobbs  */
253f8307e12SArchie Cobbs typedef	int	ng_getDefault_t(const struct ng_parse_type *type,
254f8307e12SArchie Cobbs 			const u_char *start, u_char *buf, int *buflen);
255f8307e12SArchie Cobbs 
256f8307e12SArchie Cobbs /*
257f8307e12SArchie Cobbs  * Return the alignment requirement of this type.  Zero is same as one.
258f8307e12SArchie Cobbs  */
259f8307e12SArchie Cobbs typedef	int	ng_getAlign_t(const struct ng_parse_type *type);
260f8307e12SArchie Cobbs 
261f8307e12SArchie Cobbs /************************************************************************
262f8307e12SArchie Cobbs 			TYPE DEFINITION
263f8307e12SArchie Cobbs  ************************************************************************/
264f8307e12SArchie Cobbs 
265f8307e12SArchie Cobbs /*
266f8307e12SArchie Cobbs  * This structure describes a type, which may be a sub-type of another
26763e2ac54SArchie Cobbs  * type by pointing to it with 'supertype' and possibly omitting methods.
26863e2ac54SArchie Cobbs  * Typically the super-type requires some type-specific info, which is
26963e2ac54SArchie Cobbs  * supplied by the 'info' field.
27063e2ac54SArchie Cobbs  *
27163e2ac54SArchie Cobbs  * The 'private' field is ignored by all of the pre-defined types.
27263e2ac54SArchie Cobbs  * Sub-types may use it as they see fit.
27363e2ac54SArchie Cobbs  *
27463e2ac54SArchie Cobbs  * The 'getDefault' method may always be omitted (even if there is no
27563e2ac54SArchie Cobbs  * super-type), which means the value for any item of this type must
27663e2ac54SArchie Cobbs  * always be explicitly given.
277f8307e12SArchie Cobbs  */
278f8307e12SArchie Cobbs struct ng_parse_type {
279f8307e12SArchie Cobbs 	const struct ng_parse_type *supertype;	/* super-type, if any */
280f8307e12SArchie Cobbs 	const void		*info;		/* type-specific info */
281f8307e12SArchie Cobbs 	void			*private;	/* client private info */
282f8307e12SArchie Cobbs 	ng_parse_t		*parse;		/* parse method */
283f8307e12SArchie Cobbs 	ng_unparse_t		*unparse;	/* unparse method */
284f8307e12SArchie Cobbs 	ng_getDefault_t		*getDefault;	/* get default value method */
285f8307e12SArchie Cobbs 	ng_getAlign_t		*getAlign;	/* get alignment */
286f8307e12SArchie Cobbs };
287f8307e12SArchie Cobbs 
288f8307e12SArchie Cobbs /************************************************************************
289f8307e12SArchie Cobbs 			PRE-DEFINED TYPES
290f8307e12SArchie Cobbs  ************************************************************************/
291f8307e12SArchie Cobbs 
292f8307e12SArchie Cobbs /*
29363e2ac54SArchie Cobbs  * STRUCTURE TYPE
29463e2ac54SArchie Cobbs  *
29563e2ac54SArchie Cobbs  * This type supports arbitrary C structures.  The normal field alignment
29663e2ac54SArchie Cobbs  * rules for the local machine are applied.  Fields are always parsed in
29763e2ac54SArchie Cobbs  * field order, no matter what order they are listed in the ASCII string.
298f8307e12SArchie Cobbs  *
299f8307e12SArchie Cobbs  *   Default value:		Determined on a per-field basis
300f0184ff8SArchie Cobbs  *   Additional info:		struct ng_parse_struct_field *
301f8307e12SArchie Cobbs  */
302f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_struct_type;
303f8307e12SArchie Cobbs 
304f8307e12SArchie Cobbs /* Each field has a name, type, and optional alignment override. If the
305f8307e12SArchie Cobbs    override is non-zero, the alignment is determined from the field type.
306f8307e12SArchie Cobbs    Note: add an extra struct ng_parse_struct_field with name == NULL
307f8307e12SArchie Cobbs    to indicate the end of the list. */
308f8307e12SArchie Cobbs struct ng_parse_struct_field {
309f8307e12SArchie Cobbs 	const char			*name;		/* field name */
310f0184ff8SArchie Cobbs 	const struct ng_parse_type	*type;		/* field type */
311f8307e12SArchie Cobbs 	int				alignment;	/* override alignment */
312f8307e12SArchie Cobbs };
313f8307e12SArchie Cobbs 
314f8307e12SArchie Cobbs /*
31563e2ac54SArchie Cobbs  * FIXED LENGTH ARRAY TYPE
316f8307e12SArchie Cobbs  *
31763e2ac54SArchie Cobbs  * This type supports fixed length arrays, having any element type.
31863e2ac54SArchie Cobbs  *
31963e2ac54SArchie Cobbs  *   Default value:		As returned by getDefault for each index
320f8307e12SArchie Cobbs  *   Additional info:		struct ng_parse_fixedarray_info *
321f8307e12SArchie Cobbs  */
322f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_fixedarray_type;
323f8307e12SArchie Cobbs 
32463e2ac54SArchie Cobbs /*
32563e2ac54SArchie Cobbs  * Get the default value for the element at index 'index'.  This method
32663e2ac54SArchie Cobbs  * may be NULL, in which case the default value is computed from the
32763e2ac54SArchie Cobbs  * element type.  Otherwise, it should fill in the default value at *buf
32863e2ac54SArchie Cobbs  * (having size *buflen) and update *buflen to the length of the filled-in
32963e2ac54SArchie Cobbs  * value before return.  If there is not enough routine return ERANGE.
33063e2ac54SArchie Cobbs  */
331f8307e12SArchie Cobbs typedef	int	ng_parse_array_getDefault_t(const struct ng_parse_type *type,
332f8307e12SArchie Cobbs 				int index, const u_char *start,
333f8307e12SArchie Cobbs 				u_char *buf, int *buflen);
334f8307e12SArchie Cobbs 
335f8307e12SArchie Cobbs struct ng_parse_fixedarray_info {
336f8307e12SArchie Cobbs 	const struct ng_parse_type	*elementType;
337f8307e12SArchie Cobbs 	int				length;
338f8307e12SArchie Cobbs 	ng_parse_array_getDefault_t	*getDefault;
339f8307e12SArchie Cobbs };
340f8307e12SArchie Cobbs 
341f8307e12SArchie Cobbs /*
34263e2ac54SArchie Cobbs  * VARIABLE LENGTH ARRAY TYPE
34363e2ac54SArchie Cobbs  *
34463e2ac54SArchie Cobbs  * Same as fixed length arrays, except that the length is determined
34563e2ac54SArchie Cobbs  * by a function instead of a constant value.
346f8307e12SArchie Cobbs  *
347f8307e12SArchie Cobbs  *   Default value:		Same as with fixed length arrays
348f8307e12SArchie Cobbs  *   Additional info:		struct ng_parse_array_info *
349f8307e12SArchie Cobbs  */
350f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_array_type;
351f8307e12SArchie Cobbs 
35263e2ac54SArchie Cobbs /*
35363e2ac54SArchie Cobbs  * Return the length of the array.  If the array is a field in a structure,
35463e2ac54SArchie Cobbs  * all prior fields are guaranteed to be filled in already.  Upon entry,
35563e2ac54SArchie Cobbs  * 'start' is equal to the first byte parsed in this run, while 'buf' points
35663e2ac54SArchie Cobbs  * to the first element of the array to be filled in.
35763e2ac54SArchie Cobbs  */
35863e2ac54SArchie Cobbs typedef int	ng_parse_array_getLength_t(const struct ng_parse_type *type,
35963e2ac54SArchie Cobbs 				const u_char *start, const u_char *buf);
36063e2ac54SArchie Cobbs 
361f8307e12SArchie Cobbs struct ng_parse_array_info {
362f8307e12SArchie Cobbs 	const struct ng_parse_type	*elementType;
363f8307e12SArchie Cobbs 	ng_parse_array_getLength_t	*getLength;
364f8307e12SArchie Cobbs 	ng_parse_array_getDefault_t	*getDefault;
365f8307e12SArchie Cobbs };
366f8307e12SArchie Cobbs 
367f8307e12SArchie Cobbs /*
36863e2ac54SArchie Cobbs  * ARBITRARY LENGTH STRING TYPE
36963e2ac54SArchie Cobbs  *
37063e2ac54SArchie Cobbs  * For arbirary length, NUL-terminated strings.
371f8307e12SArchie Cobbs  *
372f8307e12SArchie Cobbs  *   Default value:		Empty string
373f8307e12SArchie Cobbs  *   Additional info:		None required
374f8307e12SArchie Cobbs  */
375f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_string_type;
376f8307e12SArchie Cobbs 
377f8307e12SArchie Cobbs /*
37863e2ac54SArchie Cobbs  * BOUNDED LENGTH STRING TYPE
37963e2ac54SArchie Cobbs  *
38063e2ac54SArchie Cobbs  * These are strings that have a fixed-size buffer, and always include
38163e2ac54SArchie Cobbs  * a terminating NUL character.
382f8307e12SArchie Cobbs  *
383f8307e12SArchie Cobbs  *   Default value:		Empty string
384c1b9e5f2SArchie Cobbs  *   Additional info:		struct ng_parse_fixedstring_info *
385f8307e12SArchie Cobbs  */
386f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_fixedstring_type;
387f8307e12SArchie Cobbs 
388c1b9e5f2SArchie Cobbs struct ng_parse_fixedstring_info {
389f8307e12SArchie Cobbs 	int	bufSize;	/* size of buffer (including NUL) */
390f8307e12SArchie Cobbs };
391f8307e12SArchie Cobbs 
392f8307e12SArchie Cobbs /*
39327121ab1SBrian Somers  * EXPLICITLY SIZED STRING TYPE
39427121ab1SBrian Somers  *
39527121ab1SBrian Somers  * These are strings that have a two byte length field preceding them.
39627121ab1SBrian Somers  * Parsed strings are NOT NUL-terminated.
39727121ab1SBrian Somers  *
39827121ab1SBrian Somers  *   Default value:		Empty string
39927121ab1SBrian Somers  *   Additional info:		None
40027121ab1SBrian Somers  */
40127121ab1SBrian Somers extern const struct ng_parse_type ng_parse_sizedstring_type;
40227121ab1SBrian Somers 
40327121ab1SBrian Somers /*
40463e2ac54SArchie Cobbs  * COMMONLY USED BOUNDED LENGTH STRING TYPES
405f8307e12SArchie Cobbs  */
40687e2c66aSHartmut Brandt extern const struct ng_parse_type ng_parse_nodebuf_type;  /* NG_NODESIZ */
40787e2c66aSHartmut Brandt extern const struct ng_parse_type ng_parse_hookbuf_type;  /* NG_HOOKSIZ */
40887e2c66aSHartmut Brandt extern const struct ng_parse_type ng_parse_pathbuf_type;  /* NG_PATHSIZ */
40987e2c66aSHartmut Brandt extern const struct ng_parse_type ng_parse_typebuf_type;  /* NG_TYPESIZ */
41087e2c66aSHartmut Brandt extern const struct ng_parse_type ng_parse_cmdbuf_type;   /* NG_CMDSTRSIZ */
411f8307e12SArchie Cobbs 
412f8307e12SArchie Cobbs /*
41363e2ac54SArchie Cobbs  * INTEGER TYPES
414f8307e12SArchie Cobbs  *
415f8307e12SArchie Cobbs  *   Default value:		0
416f8307e12SArchie Cobbs  *   Additional info:		None required
417f8307e12SArchie Cobbs  */
418f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_int8_type;
419f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_int16_type;
420f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_int32_type;
421f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_int64_type;
422f8307e12SArchie Cobbs 
4237b3bf3f9SArchie Cobbs /* Same thing but unparse as unsigned quantities */
4247b3bf3f9SArchie Cobbs extern const struct ng_parse_type ng_parse_uint8_type;
4257b3bf3f9SArchie Cobbs extern const struct ng_parse_type ng_parse_uint16_type;
4267b3bf3f9SArchie Cobbs extern const struct ng_parse_type ng_parse_uint32_type;
4277b3bf3f9SArchie Cobbs extern const struct ng_parse_type ng_parse_uint64_type;
4287b3bf3f9SArchie Cobbs 
4297b3bf3f9SArchie Cobbs /* Same thing but unparse as hex quantities, e.g., "0xe7" */
4307b3bf3f9SArchie Cobbs extern const struct ng_parse_type ng_parse_hint8_type;
4317b3bf3f9SArchie Cobbs extern const struct ng_parse_type ng_parse_hint16_type;
4327b3bf3f9SArchie Cobbs extern const struct ng_parse_type ng_parse_hint32_type;
4337b3bf3f9SArchie Cobbs extern const struct ng_parse_type ng_parse_hint64_type;
4347b3bf3f9SArchie Cobbs 
435f8307e12SArchie Cobbs /*
43663e2ac54SArchie Cobbs  * IP ADDRESS TYPE
437f8307e12SArchie Cobbs  *
438f8307e12SArchie Cobbs  *   Default value:		0.0.0.0
439f8307e12SArchie Cobbs  *   Additional info:		None required
440f8307e12SArchie Cobbs  */
441f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_ipaddr_type;
442f8307e12SArchie Cobbs 
443f8307e12SArchie Cobbs /*
4448c7e4101SRuslan Ermilov  * ETHERNET ADDRESS TYPE
4458c7e4101SRuslan Ermilov  *
4468c7e4101SRuslan Ermilov  *   Default value:		None
4478c7e4101SRuslan Ermilov  *   Additional info:		None required
4488c7e4101SRuslan Ermilov  */
4498c7e4101SRuslan Ermilov extern const struct ng_parse_type ng_parse_enaddr_type;
4508c7e4101SRuslan Ermilov 
4518c7e4101SRuslan Ermilov /*
45263e2ac54SArchie Cobbs  * VARIABLE LENGTH BYTE ARRAY TYPE
45363e2ac54SArchie Cobbs  *
45463e2ac54SArchie Cobbs  * The bytes are displayed in hex.  The ASCII form may be either an
45563e2ac54SArchie Cobbs  * array of bytes or a string constant, in which case the array is
45663e2ac54SArchie Cobbs  * zero-filled after the string bytes.
457f8307e12SArchie Cobbs  *
458f8307e12SArchie Cobbs  *   Default value:		All bytes are zero
459f8307e12SArchie Cobbs  *   Additional info:		ng_parse_array_getLength_t *
460f8307e12SArchie Cobbs  */
461f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_bytearray_type;
462f8307e12SArchie Cobbs 
463f8307e12SArchie Cobbs /*
46463e2ac54SArchie Cobbs  * NETGRAPH CONTROL MESSAGE TYPE
46563e2ac54SArchie Cobbs  *
46663e2ac54SArchie Cobbs  * This is the parse type for a struct ng_mesg.
467f8307e12SArchie Cobbs  *
468f8307e12SArchie Cobbs  *   Default value:		All fields zero
469f8307e12SArchie Cobbs  *   Additional info:		None required
470f8307e12SArchie Cobbs  */
471f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_ng_mesg_type;
472f8307e12SArchie Cobbs 
473f8307e12SArchie Cobbs /************************************************************************
474f8307e12SArchie Cobbs 		CONVERSTION AND PARSING ROUTINES
475f8307e12SArchie Cobbs  ************************************************************************/
476f8307e12SArchie Cobbs 
477f8307e12SArchie Cobbs /* Tokens for parsing structs and arrays */
478f8307e12SArchie Cobbs enum ng_parse_token {
479f8307e12SArchie Cobbs 	T_LBRACE,		/* '{' */
480f8307e12SArchie Cobbs 	T_RBRACE,		/* '}' */
481f8307e12SArchie Cobbs 	T_LBRACKET,		/* '[' */
482f8307e12SArchie Cobbs 	T_RBRACKET,		/* ']' */
483f8307e12SArchie Cobbs 	T_EQUALS,		/* '=' */
484f8307e12SArchie Cobbs 	T_STRING,		/* string in double quotes */
485f8307e12SArchie Cobbs 	T_ERROR,		/* error parsing string in double quotes */
486f8307e12SArchie Cobbs 	T_WORD,			/* anything else containing no whitespace */
487f8307e12SArchie Cobbs 	T_EOF,			/* end of string reached */
488f8307e12SArchie Cobbs };
489f8307e12SArchie Cobbs 
490f8307e12SArchie Cobbs /*
491f8307e12SArchie Cobbs  * See typedef ng_parse_t for definition
492f8307e12SArchie Cobbs  */
493f8307e12SArchie Cobbs extern int	ng_parse(const struct ng_parse_type *type, const char *string,
494f8307e12SArchie Cobbs 			int *off, u_char *buf, int *buflen);
495f8307e12SArchie Cobbs 
496f8307e12SArchie Cobbs /*
497f8307e12SArchie Cobbs  * See typedef ng_unparse_t for definition (*off assumed to be zero).
498f8307e12SArchie Cobbs  */
499f8307e12SArchie Cobbs extern int	ng_unparse(const struct ng_parse_type *type,
500f8307e12SArchie Cobbs 			const u_char *data, char *buf, int buflen);
501f8307e12SArchie Cobbs 
502f8307e12SArchie Cobbs /*
503f8307e12SArchie Cobbs  * See typedef ng_getDefault_t for definition
504f8307e12SArchie Cobbs  */
505f8307e12SArchie Cobbs extern int	ng_parse_getDefault(const struct ng_parse_type *type,
506f8307e12SArchie Cobbs 			u_char *buf, int *buflen);
507f8307e12SArchie Cobbs 
508f8307e12SArchie Cobbs /*
509f8307e12SArchie Cobbs  * Parse a token: '*startp' is the offset to start looking.  Upon
510f8307e12SArchie Cobbs  * successful return, '*startp' equals the beginning of the token
511f8307e12SArchie Cobbs  * and '*lenp' the length.  If error, '*startp' points at the
512f8307e12SArchie Cobbs  * offending character(s).
513f8307e12SArchie Cobbs  */
514f8307e12SArchie Cobbs extern enum	ng_parse_token ng_parse_get_token(const char *s,
515f8307e12SArchie Cobbs 			int *startp, int *lenp);
516f8307e12SArchie Cobbs 
517f8307e12SArchie Cobbs /*
518f8307e12SArchie Cobbs  * Like above, but specifically for getting a string token and returning
519f8307e12SArchie Cobbs  * the string value.  The string token must be enclosed in double quotes
520f8307e12SArchie Cobbs  * and the normal C backslash escapes are recognized.  The caller must
521f8307e12SArchie Cobbs  * eventually free() the returned result.  Returns NULL if token is
52227121ab1SBrian Somers  * not a string token, or parse or other error. Otherwise, *lenp contains
52327121ab1SBrian Somers  * the number of characters parsed, and *slenp (if not NULL) contains
52427121ab1SBrian Somers  * the actual number of characters in the parsed string.
525f8307e12SArchie Cobbs  */
52627121ab1SBrian Somers extern char	*ng_get_string_token(const char *s, int *startp,
52727121ab1SBrian Somers 			int *lenp, int *slenp);
528f8307e12SArchie Cobbs 
529f8307e12SArchie Cobbs /*
530f8307e12SArchie Cobbs  * Convert a raw string into a doubly-quoted string including any
531f8307e12SArchie Cobbs  * necessary backslash escapes.  Caller must free the result.
53227121ab1SBrian Somers  * Returns NULL if ENOMEM. Normally "slen" should equal strlen(s)
53327121ab1SBrian Somers  * unless you want to encode NUL bytes.
534f8307e12SArchie Cobbs  */
53527121ab1SBrian Somers extern char	*ng_encode_string(const char *s, int slen);
536f8307e12SArchie Cobbs 
537e20480bfSRuslan Ermilov #endif /* _NETGRAPH_NG_PARSE_H_ */
538