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 * $FreeBSD$ 42f8307e12SArchie Cobbs */ 43f8307e12SArchie Cobbs 44e20480bfSRuslan Ermilov #ifndef _NETGRAPH_NG_PARSE_H_ 45e20480bfSRuslan Ermilov #define _NETGRAPH_NG_PARSE_H_ 46f8307e12SArchie Cobbs 47f8307e12SArchie Cobbs /* 48f8307e12SArchie Cobbs 49f8307e12SArchie Cobbs This defines a library of routines for converting between various C 50f8307e12SArchie Cobbs language types in binary form and ASCII strings. Types are user 5163e2ac54SArchie Cobbs definable. Several pre-defined types are supplied, for some common 5263e2ac54SArchie Cobbs C types: structures, variable and fixed length arrays, integer types, 5363e2ac54SArchie Cobbs variable and fixed length strings, IP addresses, etc. 5463e2ac54SArchie Cobbs 5563e2ac54SArchie Cobbs A netgraph node type may provide a list of types that correspond to 5663e2ac54SArchie Cobbs the structures it expects to send and receive in the arguments field 5763e2ac54SArchie Cobbs of a control message. This allows these messages to be converted 5863e2ac54SArchie Cobbs between their native binary form and the corresponding ASCII form. 5963e2ac54SArchie Cobbs 6063e2ac54SArchie Cobbs A future use of the ASCII form may be for inter-machine communication 6163e2ac54SArchie Cobbs of control messages, because the ASCII form is machine independent 6263e2ac54SArchie Cobbs whereas the native binary form is not. 63f8307e12SArchie Cobbs 64f8307e12SArchie Cobbs Syntax 65f8307e12SArchie Cobbs ------ 66f8307e12SArchie Cobbs 67f8307e12SArchie Cobbs Structures: 68f8307e12SArchie Cobbs 69f8307e12SArchie Cobbs '{' [ <name>=<value> ... ] '}' 70f8307e12SArchie Cobbs 71f8307e12SArchie Cobbs Omitted fields have their default values by implication. 72f8307e12SArchie Cobbs The order in which the fields are specified does not matter. 73f8307e12SArchie Cobbs 74f8307e12SArchie Cobbs Arrays: 75f8307e12SArchie Cobbs 76f8307e12SArchie Cobbs '[' [ [index=]<value> ... ] ']' 77f8307e12SArchie Cobbs 78f8307e12SArchie Cobbs Element value may be specified with or without the "<index>=" prefix; 79f8307e12SArchie Cobbs If omitted, the index after the previous element is used. 80f8307e12SArchie Cobbs Omitted fields have their default values by implication. 81f8307e12SArchie Cobbs 82f8307e12SArchie Cobbs Strings: 83f8307e12SArchie Cobbs 84f8307e12SArchie Cobbs "foo bar blah\r\n" 85f8307e12SArchie Cobbs 86f8307e12SArchie Cobbs That is, strings are specified just like C strings. The usual 87f8307e12SArchie Cobbs backslash escapes are accepted. 88f8307e12SArchie Cobbs 8963e2ac54SArchie Cobbs Other simple types (integers, IP addresses) have their obvious forms. 90f8307e12SArchie Cobbs 91f8307e12SArchie Cobbs Example 92f8307e12SArchie Cobbs ------- 93f8307e12SArchie Cobbs 9463e2ac54SArchie Cobbs Suppose we have a netgraph command that takes as an argument 9563e2ac54SArchie Cobbs a 'struct foo' shown below. Here is an example of a possible 9663e2ac54SArchie Cobbs value for the structure, and the corresponding ASCII encoding 9763e2ac54SArchie Cobbs of that value: 9863e2ac54SArchie Cobbs 9963e2ac54SArchie Cobbs Structure Binary value 10063e2ac54SArchie Cobbs --------- ------------ 101f8307e12SArchie Cobbs 102f8307e12SArchie Cobbs struct foo { 10363e2ac54SArchie Cobbs struct in_addr ip; 01 02 03 04 104f8307e12SArchie Cobbs int bar; 00 00 00 00 10563e2ac54SArchie Cobbs char label[8]; 61 62 63 0a 00 00 00 00 10663e2ac54SArchie Cobbs u_char alen; 03 00 10763e2ac54SArchie Cobbs short ary[0]; 05 00 00 00 0a 00 108f8307e12SArchie Cobbs }; 109f8307e12SArchie Cobbs 11063e2ac54SArchie Cobbs ASCII value 11163e2ac54SArchie Cobbs ----------- 112f8307e12SArchie Cobbs 11363e2ac54SArchie Cobbs { ip=1.2.3.4 label="abc\n" alen=3 ary=[ 5 2=10 ] } 11463e2ac54SArchie Cobbs 11563e2ac54SArchie Cobbs Note that omitted fields and array elements get their default 11663e2ac54SArchie Cobbs values ("bar" and ary[2]), and that the alignment is handled 11763e2ac54SArchie Cobbs automatically (the extra 00 byte after "num"). Also, since byte 11863e2ac54SArchie Cobbs order and alignment are inherently machine dependent, so is this 11963e2ac54SArchie Cobbs conversion process. The above example shows an x86 (little 12063e2ac54SArchie Cobbs endian) encoding. Also the above example is tricky because the 12163e2ac54SArchie Cobbs structure is variable length, depending on 'alen', the number of 12263e2ac54SArchie Cobbs elements in the array 'ary'. 12363e2ac54SArchie Cobbs 12463e2ac54SArchie Cobbs Here is how one would define a parse type for the above structure, 12563e2ac54SArchie Cobbs subclassing the pre-defined types below. We construct the type in 12663e2ac54SArchie Cobbs a 'bottom up' fashion, defining each field's type first, then the 12763e2ac54SArchie Cobbs type for the whole structure ('//' comments used to avoid breakage). 12863e2ac54SArchie Cobbs 12963e2ac54SArchie Cobbs // Super-type info for 'label' field 130c1b9e5f2SArchie Cobbs struct ng_parse_fixedstring_info foo_label_info = { 8 }; 13163e2ac54SArchie Cobbs 13263e2ac54SArchie Cobbs // Parse type for 'label' field 13363e2ac54SArchie Cobbs struct ng_parse_type foo_label_type = { 13463e2ac54SArchie Cobbs &ng_parse_fixedstring_type // super-type 13563e2ac54SArchie Cobbs &foo_label_info // super-type info 13663e2ac54SArchie Cobbs }; 13763e2ac54SArchie Cobbs 13863e2ac54SArchie Cobbs #define OFFSETOF(s, e) ((char *)&((s *)0)->e - (char *)((s *)0)) 13963e2ac54SArchie Cobbs 14063e2ac54SArchie Cobbs // Function to compute the length of the array 'ary', which 14163e2ac54SArchie Cobbs // is variable length, depending on the previous field 'alen'. 14263e2ac54SArchie Cobbs // Upon entry 'buf' will be pointing at &ary[0]. 14363e2ac54SArchie Cobbs int 14463e2ac54SArchie Cobbs foo_ary_getLength(const struct ng_parse_type *type, 14563e2ac54SArchie Cobbs const u_char *start, const u_char *buf) 14663e2ac54SArchie Cobbs { 14763e2ac54SArchie Cobbs const struct foo *f; 14863e2ac54SArchie Cobbs 14963e2ac54SArchie Cobbs f = (const struct foo *)(buf - OFFSETOF(struct foo, ary)); 15063e2ac54SArchie Cobbs return f->alen; 15163e2ac54SArchie Cobbs } 15263e2ac54SArchie Cobbs 15363e2ac54SArchie Cobbs // Super-type info for 'ary' field 15463e2ac54SArchie Cobbs struct ng_parse_array_info foo_ary_info = { 15563e2ac54SArchie Cobbs &ng_parse_int16_type, // element type 15663e2ac54SArchie Cobbs &foo_ary_getLength // func to get array length 15763e2ac54SArchie Cobbs } 15863e2ac54SArchie Cobbs 15963e2ac54SArchie Cobbs // Parse type for 'ary' field 16063e2ac54SArchie Cobbs struct ng_parse_type foo_ary_type = { 16163e2ac54SArchie Cobbs &ng_parse_array_type, // super-type 16263e2ac54SArchie Cobbs &foo_ary_info // super-type info 16363e2ac54SArchie Cobbs }; 16463e2ac54SArchie Cobbs 16563e2ac54SArchie Cobbs // Super-type info for struct foo 166f0184ff8SArchie Cobbs struct ng_parse_struct_field foo_fields[] = { 16763e2ac54SArchie Cobbs { "ip", &ng_parse_ipaddr_type }, 16863e2ac54SArchie Cobbs { "bar", &ng_parse_int32_type }, 16963e2ac54SArchie Cobbs { "label", &foo_label_type }, 1707b3bf3f9SArchie Cobbs { "alen", &ng_parse_uint8_type }, 17163e2ac54SArchie Cobbs { "ary", &foo_ary_type }, 17263e2ac54SArchie Cobbs { NULL } 17363e2ac54SArchie Cobbs }; 17463e2ac54SArchie Cobbs 17563e2ac54SArchie Cobbs // Parse type for struct foo 17663e2ac54SArchie Cobbs struct ng_parse_type foo_type = { 17763e2ac54SArchie Cobbs &ng_parse_struct_type, // super-type 17863e2ac54SArchie Cobbs &foo_fields // super-type info 17963e2ac54SArchie Cobbs }; 180f8307e12SArchie Cobbs 181f8307e12SArchie Cobbs To define a type, you can define it as a sub-type of a predefined 18263e2ac54SArchie Cobbs type as shown above, possibly overriding some of the predefined 18363e2ac54SArchie Cobbs type's methods, or define an entirely new syntax, with the restriction 18463e2ac54SArchie Cobbs that the ASCII representation of your type's value must not contain 18563e2ac54SArchie Cobbs any whitespace or any of these characters: { } [ ] = " 18663e2ac54SArchie Cobbs 18763e2ac54SArchie Cobbs See ng_ksocket.c for an example of how to do this for 'struct sockaddr'. 18863e2ac54SArchie Cobbs See ng_parse.c to see implementations of the pre-defined types below. 189f8307e12SArchie Cobbs 190f8307e12SArchie Cobbs */ 191f8307e12SArchie Cobbs 192f8307e12SArchie Cobbs /************************************************************************ 193f8307e12SArchie Cobbs METHODS REQUIRED BY A TYPE 194f8307e12SArchie Cobbs ************************************************************************/ 195f8307e12SArchie Cobbs 196f8307e12SArchie Cobbs /* 197f8307e12SArchie Cobbs * Three methods are required for a type. These may be given explicitly 19863e2ac54SArchie Cobbs * or, if NULL, inherited from the super-type. The 'getDefault' method 19963e2ac54SArchie Cobbs * is always optional; the others are required if there is no super-type. 200f8307e12SArchie Cobbs */ 201f8307e12SArchie Cobbs 202f8307e12SArchie Cobbs struct ng_parse_type; 203f8307e12SArchie Cobbs 204f8307e12SArchie Cobbs /* 205f8307e12SArchie Cobbs * Convert ASCII to binary according to the supplied type. 206f8307e12SArchie Cobbs * 207f8307e12SArchie Cobbs * The ASCII characters begin at offset *off in 'string'. The binary 208f8307e12SArchie Cobbs * representation is put into 'buf', which has at least *buflen bytes. 209f8307e12SArchie Cobbs * 'start' points to the first byte output by ng_parse() (ie, start <= buf). 210f8307e12SArchie Cobbs * 211f8307e12SArchie Cobbs * Upon return, *buflen contains the length of the new binary data, and 212f8307e12SArchie Cobbs * *off is updated to point just past the end of the parsed range of 213f8307e12SArchie Cobbs * characters, or, in the case of an error, to the offending character(s). 214f8307e12SArchie Cobbs * 215f8307e12SArchie Cobbs * Return values: 216f8307e12SArchie Cobbs * 0 Success; *buflen holds the length of the data 217f8307e12SArchie Cobbs * and *off points just past the last char parsed. 218f8307e12SArchie Cobbs * EALREADY Field specified twice 219f8307e12SArchie Cobbs * ENOENT Unknown field 220f8307e12SArchie Cobbs * E2BIG Array or character string overflow 221f8307e12SArchie Cobbs * ERANGE Output was longer than *buflen bytes 222f8307e12SArchie Cobbs * EINVAL Parse failure or other invalid content 223f8307e12SArchie Cobbs * ENOMEM Out of memory 224f8307e12SArchie Cobbs * EOPNOTSUPP Mandatory array/structure element missing 225f8307e12SArchie Cobbs */ 226f8307e12SArchie Cobbs typedef int ng_parse_t(const struct ng_parse_type *type, const char *string, 227f8307e12SArchie Cobbs int *off, const u_char *start, 228f8307e12SArchie Cobbs u_char *buf, int *buflen); 229f8307e12SArchie Cobbs 230f8307e12SArchie Cobbs /* 231f8307e12SArchie Cobbs * Convert binary to ASCII according to the supplied type. 232f8307e12SArchie Cobbs * 233f8307e12SArchie Cobbs * The results are put into 'buf', which is at least buflen bytes long. 234f8307e12SArchie Cobbs * *off points to the current byte in 'data' and should be updated 235f8307e12SArchie Cobbs * before return to point just past the last byte unparsed. 236f8307e12SArchie Cobbs * 237f8307e12SArchie Cobbs * Returns: 238f8307e12SArchie Cobbs * 0 Success 239f8307e12SArchie Cobbs * ERANGE Output was longer than buflen bytes 240f8307e12SArchie Cobbs */ 241f8307e12SArchie Cobbs typedef int ng_unparse_t(const struct ng_parse_type *type, 242f8307e12SArchie Cobbs const u_char *data, int *off, char *buf, int buflen); 243f8307e12SArchie Cobbs 244f8307e12SArchie Cobbs /* 245f8307e12SArchie Cobbs * Compute the default value according to the supplied type. 246f8307e12SArchie Cobbs * 247f8307e12SArchie Cobbs * Store the result in 'buf', which is at least *buflen bytes long. 248f8307e12SArchie Cobbs * Upon return *buflen contains the length of the output. 249f8307e12SArchie Cobbs * 250f8307e12SArchie Cobbs * Returns: 251f8307e12SArchie Cobbs * 0 Success 252f8307e12SArchie Cobbs * ERANGE Output was longer than *buflen bytes 253f8307e12SArchie Cobbs * EOPNOTSUPP Default value is not specified for this type 254f8307e12SArchie Cobbs */ 255f8307e12SArchie Cobbs typedef int ng_getDefault_t(const struct ng_parse_type *type, 256f8307e12SArchie Cobbs const u_char *start, u_char *buf, int *buflen); 257f8307e12SArchie Cobbs 258f8307e12SArchie Cobbs /* 259f8307e12SArchie Cobbs * Return the alignment requirement of this type. Zero is same as one. 260f8307e12SArchie Cobbs */ 261f8307e12SArchie Cobbs typedef int ng_getAlign_t(const struct ng_parse_type *type); 262f8307e12SArchie Cobbs 263f8307e12SArchie Cobbs /************************************************************************ 264f8307e12SArchie Cobbs TYPE DEFINITION 265f8307e12SArchie Cobbs ************************************************************************/ 266f8307e12SArchie Cobbs 267f8307e12SArchie Cobbs /* 268f8307e12SArchie Cobbs * This structure describes a type, which may be a sub-type of another 26963e2ac54SArchie Cobbs * type by pointing to it with 'supertype' and possibly omitting methods. 27063e2ac54SArchie Cobbs * Typically the super-type requires some type-specific info, which is 27163e2ac54SArchie Cobbs * supplied by the 'info' field. 27263e2ac54SArchie Cobbs * 27363e2ac54SArchie Cobbs * The 'private' field is ignored by all of the pre-defined types. 27463e2ac54SArchie Cobbs * Sub-types may use it as they see fit. 27563e2ac54SArchie Cobbs * 27663e2ac54SArchie Cobbs * The 'getDefault' method may always be omitted (even if there is no 27763e2ac54SArchie Cobbs * super-type), which means the value for any item of this type must 27863e2ac54SArchie Cobbs * always be explicitly given. 279f8307e12SArchie Cobbs */ 280f8307e12SArchie Cobbs struct ng_parse_type { 281f8307e12SArchie Cobbs const struct ng_parse_type *supertype; /* super-type, if any */ 282f8307e12SArchie Cobbs const void *info; /* type-specific info */ 283f8307e12SArchie Cobbs void *private; /* client private info */ 284f8307e12SArchie Cobbs ng_parse_t *parse; /* parse method */ 285f8307e12SArchie Cobbs ng_unparse_t *unparse; /* unparse method */ 286f8307e12SArchie Cobbs ng_getDefault_t *getDefault; /* get default value method */ 287f8307e12SArchie Cobbs ng_getAlign_t *getAlign; /* get alignment */ 288f8307e12SArchie Cobbs }; 289f8307e12SArchie Cobbs 290f8307e12SArchie Cobbs /************************************************************************ 291f8307e12SArchie Cobbs PRE-DEFINED TYPES 292f8307e12SArchie Cobbs ************************************************************************/ 293f8307e12SArchie Cobbs 294f8307e12SArchie Cobbs /* 29563e2ac54SArchie Cobbs * STRUCTURE TYPE 29663e2ac54SArchie Cobbs * 29763e2ac54SArchie Cobbs * This type supports arbitrary C structures. The normal field alignment 29863e2ac54SArchie Cobbs * rules for the local machine are applied. Fields are always parsed in 29963e2ac54SArchie Cobbs * field order, no matter what order they are listed in the ASCII string. 300f8307e12SArchie Cobbs * 301f8307e12SArchie Cobbs * Default value: Determined on a per-field basis 302f0184ff8SArchie Cobbs * Additional info: struct ng_parse_struct_field * 303f8307e12SArchie Cobbs */ 304f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_struct_type; 305f8307e12SArchie Cobbs 306f8307e12SArchie Cobbs /* Each field has a name, type, and optional alignment override. If the 307f8307e12SArchie Cobbs override is non-zero, the alignment is determined from the field type. 308f8307e12SArchie Cobbs Note: add an extra struct ng_parse_struct_field with name == NULL 309f8307e12SArchie Cobbs to indicate the end of the list. */ 310f8307e12SArchie Cobbs struct ng_parse_struct_field { 311f8307e12SArchie Cobbs const char *name; /* field name */ 312f0184ff8SArchie Cobbs const struct ng_parse_type *type; /* field type */ 313f8307e12SArchie Cobbs int alignment; /* override alignment */ 314f8307e12SArchie Cobbs }; 315f8307e12SArchie Cobbs 316f8307e12SArchie Cobbs /* 31763e2ac54SArchie Cobbs * FIXED LENGTH ARRAY TYPE 318f8307e12SArchie Cobbs * 31963e2ac54SArchie Cobbs * This type supports fixed length arrays, having any element type. 32063e2ac54SArchie Cobbs * 32163e2ac54SArchie Cobbs * Default value: As returned by getDefault for each index 322f8307e12SArchie Cobbs * Additional info: struct ng_parse_fixedarray_info * 323f8307e12SArchie Cobbs */ 324f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_fixedarray_type; 325f8307e12SArchie Cobbs 32663e2ac54SArchie Cobbs /* 32763e2ac54SArchie Cobbs * Get the default value for the element at index 'index'. This method 32863e2ac54SArchie Cobbs * may be NULL, in which case the default value is computed from the 32963e2ac54SArchie Cobbs * element type. Otherwise, it should fill in the default value at *buf 33063e2ac54SArchie Cobbs * (having size *buflen) and update *buflen to the length of the filled-in 33163e2ac54SArchie Cobbs * value before return. If there is not enough routine return ERANGE. 33263e2ac54SArchie Cobbs */ 333f8307e12SArchie Cobbs typedef int ng_parse_array_getDefault_t(const struct ng_parse_type *type, 334f8307e12SArchie Cobbs int index, const u_char *start, 335f8307e12SArchie Cobbs u_char *buf, int *buflen); 336f8307e12SArchie Cobbs 337f8307e12SArchie Cobbs struct ng_parse_fixedarray_info { 338f8307e12SArchie Cobbs const struct ng_parse_type *elementType; 339f8307e12SArchie Cobbs int length; 340f8307e12SArchie Cobbs ng_parse_array_getDefault_t *getDefault; 341f8307e12SArchie Cobbs }; 342f8307e12SArchie Cobbs 343f8307e12SArchie Cobbs /* 34463e2ac54SArchie Cobbs * VARIABLE LENGTH ARRAY TYPE 34563e2ac54SArchie Cobbs * 34663e2ac54SArchie Cobbs * Same as fixed length arrays, except that the length is determined 34763e2ac54SArchie Cobbs * by a function instead of a constant value. 348f8307e12SArchie Cobbs * 349f8307e12SArchie Cobbs * Default value: Same as with fixed length arrays 350f8307e12SArchie Cobbs * Additional info: struct ng_parse_array_info * 351f8307e12SArchie Cobbs */ 352f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_array_type; 353f8307e12SArchie Cobbs 35463e2ac54SArchie Cobbs /* 35563e2ac54SArchie Cobbs * Return the length of the array. If the array is a field in a structure, 35663e2ac54SArchie Cobbs * all prior fields are guaranteed to be filled in already. Upon entry, 35763e2ac54SArchie Cobbs * 'start' is equal to the first byte parsed in this run, while 'buf' points 35863e2ac54SArchie Cobbs * to the first element of the array to be filled in. 35963e2ac54SArchie Cobbs */ 36063e2ac54SArchie Cobbs typedef int ng_parse_array_getLength_t(const struct ng_parse_type *type, 36163e2ac54SArchie Cobbs const u_char *start, const u_char *buf); 36263e2ac54SArchie Cobbs 363f8307e12SArchie Cobbs struct ng_parse_array_info { 364f8307e12SArchie Cobbs const struct ng_parse_type *elementType; 365f8307e12SArchie Cobbs ng_parse_array_getLength_t *getLength; 366f8307e12SArchie Cobbs ng_parse_array_getDefault_t *getDefault; 367f8307e12SArchie Cobbs }; 368f8307e12SArchie Cobbs 369f8307e12SArchie Cobbs /* 37063e2ac54SArchie Cobbs * ARBITRARY LENGTH STRING TYPE 37163e2ac54SArchie Cobbs * 37263e2ac54SArchie Cobbs * For arbirary length, NUL-terminated strings. 373f8307e12SArchie Cobbs * 374f8307e12SArchie Cobbs * Default value: Empty string 375f8307e12SArchie Cobbs * Additional info: None required 376f8307e12SArchie Cobbs */ 377f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_string_type; 378f8307e12SArchie Cobbs 379f8307e12SArchie Cobbs /* 38063e2ac54SArchie Cobbs * BOUNDED LENGTH STRING TYPE 38163e2ac54SArchie Cobbs * 38263e2ac54SArchie Cobbs * These are strings that have a fixed-size buffer, and always include 38363e2ac54SArchie Cobbs * a terminating NUL character. 384f8307e12SArchie Cobbs * 385f8307e12SArchie Cobbs * Default value: Empty string 386c1b9e5f2SArchie Cobbs * Additional info: struct ng_parse_fixedstring_info * 387f8307e12SArchie Cobbs */ 388f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_fixedstring_type; 389f8307e12SArchie Cobbs 390c1b9e5f2SArchie Cobbs struct ng_parse_fixedstring_info { 391f8307e12SArchie Cobbs int bufSize; /* size of buffer (including NUL) */ 392f8307e12SArchie Cobbs }; 393f8307e12SArchie Cobbs 394f8307e12SArchie Cobbs /* 39527121ab1SBrian Somers * EXPLICITLY SIZED STRING TYPE 39627121ab1SBrian Somers * 39727121ab1SBrian Somers * These are strings that have a two byte length field preceding them. 39827121ab1SBrian Somers * Parsed strings are NOT NUL-terminated. 39927121ab1SBrian Somers * 40027121ab1SBrian Somers * Default value: Empty string 40127121ab1SBrian Somers * Additional info: None 40227121ab1SBrian Somers */ 40327121ab1SBrian Somers extern const struct ng_parse_type ng_parse_sizedstring_type; 40427121ab1SBrian Somers 40527121ab1SBrian Somers /* 40663e2ac54SArchie Cobbs * COMMONLY USED BOUNDED LENGTH STRING TYPES 407f8307e12SArchie Cobbs */ 40887e2c66aSHartmut Brandt extern const struct ng_parse_type ng_parse_nodebuf_type; /* NG_NODESIZ */ 40987e2c66aSHartmut Brandt extern const struct ng_parse_type ng_parse_hookbuf_type; /* NG_HOOKSIZ */ 41087e2c66aSHartmut Brandt extern const struct ng_parse_type ng_parse_pathbuf_type; /* NG_PATHSIZ */ 41187e2c66aSHartmut Brandt extern const struct ng_parse_type ng_parse_typebuf_type; /* NG_TYPESIZ */ 41287e2c66aSHartmut Brandt extern const struct ng_parse_type ng_parse_cmdbuf_type; /* NG_CMDSTRSIZ */ 413f8307e12SArchie Cobbs 414f8307e12SArchie Cobbs /* 41563e2ac54SArchie Cobbs * INTEGER TYPES 416f8307e12SArchie Cobbs * 417f8307e12SArchie Cobbs * Default value: 0 418f8307e12SArchie Cobbs * Additional info: None required 419f8307e12SArchie Cobbs */ 420f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_int8_type; 421f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_int16_type; 422f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_int32_type; 423f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_int64_type; 424f8307e12SArchie Cobbs 4257b3bf3f9SArchie Cobbs /* Same thing but unparse as unsigned quantities */ 4267b3bf3f9SArchie Cobbs extern const struct ng_parse_type ng_parse_uint8_type; 4277b3bf3f9SArchie Cobbs extern const struct ng_parse_type ng_parse_uint16_type; 4287b3bf3f9SArchie Cobbs extern const struct ng_parse_type ng_parse_uint32_type; 4297b3bf3f9SArchie Cobbs extern const struct ng_parse_type ng_parse_uint64_type; 4307b3bf3f9SArchie Cobbs 4317b3bf3f9SArchie Cobbs /* Same thing but unparse as hex quantities, e.g., "0xe7" */ 4327b3bf3f9SArchie Cobbs extern const struct ng_parse_type ng_parse_hint8_type; 4337b3bf3f9SArchie Cobbs extern const struct ng_parse_type ng_parse_hint16_type; 4347b3bf3f9SArchie Cobbs extern const struct ng_parse_type ng_parse_hint32_type; 4357b3bf3f9SArchie Cobbs extern const struct ng_parse_type ng_parse_hint64_type; 4367b3bf3f9SArchie Cobbs 437f8307e12SArchie Cobbs /* 43863e2ac54SArchie Cobbs * IP ADDRESS TYPE 439f8307e12SArchie Cobbs * 440f8307e12SArchie Cobbs * Default value: 0.0.0.0 441f8307e12SArchie Cobbs * Additional info: None required 442f8307e12SArchie Cobbs */ 443f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_ipaddr_type; 444f8307e12SArchie Cobbs 445f8307e12SArchie Cobbs /* 4468c7e4101SRuslan Ermilov * ETHERNET ADDRESS TYPE 4478c7e4101SRuslan Ermilov * 4488c7e4101SRuslan Ermilov * Default value: None 4498c7e4101SRuslan Ermilov * Additional info: None required 4508c7e4101SRuslan Ermilov */ 4518c7e4101SRuslan Ermilov extern const struct ng_parse_type ng_parse_enaddr_type; 4528c7e4101SRuslan Ermilov 4538c7e4101SRuslan Ermilov /* 45463e2ac54SArchie Cobbs * VARIABLE LENGTH BYTE ARRAY TYPE 45563e2ac54SArchie Cobbs * 45663e2ac54SArchie Cobbs * The bytes are displayed in hex. The ASCII form may be either an 45763e2ac54SArchie Cobbs * array of bytes or a string constant, in which case the array is 45863e2ac54SArchie Cobbs * zero-filled after the string bytes. 459f8307e12SArchie Cobbs * 460f8307e12SArchie Cobbs * Default value: All bytes are zero 461f8307e12SArchie Cobbs * Additional info: ng_parse_array_getLength_t * 462f8307e12SArchie Cobbs */ 463f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_bytearray_type; 464f8307e12SArchie Cobbs 465f8307e12SArchie Cobbs /* 46663e2ac54SArchie Cobbs * NETGRAPH CONTROL MESSAGE TYPE 46763e2ac54SArchie Cobbs * 46863e2ac54SArchie Cobbs * This is the parse type for a struct ng_mesg. 469f8307e12SArchie Cobbs * 470f8307e12SArchie Cobbs * Default value: All fields zero 471f8307e12SArchie Cobbs * Additional info: None required 472f8307e12SArchie Cobbs */ 473f8307e12SArchie Cobbs extern const struct ng_parse_type ng_parse_ng_mesg_type; 474f8307e12SArchie Cobbs 475f8307e12SArchie Cobbs /************************************************************************ 476f8307e12SArchie Cobbs CONVERSTION AND PARSING ROUTINES 477f8307e12SArchie Cobbs ************************************************************************/ 478f8307e12SArchie Cobbs 479f8307e12SArchie Cobbs /* Tokens for parsing structs and arrays */ 480f8307e12SArchie Cobbs enum ng_parse_token { 481f8307e12SArchie Cobbs T_LBRACE, /* '{' */ 482f8307e12SArchie Cobbs T_RBRACE, /* '}' */ 483f8307e12SArchie Cobbs T_LBRACKET, /* '[' */ 484f8307e12SArchie Cobbs T_RBRACKET, /* ']' */ 485f8307e12SArchie Cobbs T_EQUALS, /* '=' */ 486f8307e12SArchie Cobbs T_STRING, /* string in double quotes */ 487f8307e12SArchie Cobbs T_ERROR, /* error parsing string in double quotes */ 488f8307e12SArchie Cobbs T_WORD, /* anything else containing no whitespace */ 489f8307e12SArchie Cobbs T_EOF, /* end of string reached */ 490f8307e12SArchie Cobbs }; 491f8307e12SArchie Cobbs 492f8307e12SArchie Cobbs /* 493f8307e12SArchie Cobbs * See typedef ng_parse_t for definition 494f8307e12SArchie Cobbs */ 495f8307e12SArchie Cobbs extern int ng_parse(const struct ng_parse_type *type, const char *string, 496f8307e12SArchie Cobbs int *off, u_char *buf, int *buflen); 497f8307e12SArchie Cobbs 498f8307e12SArchie Cobbs /* 499f8307e12SArchie Cobbs * See typedef ng_unparse_t for definition (*off assumed to be zero). 500f8307e12SArchie Cobbs */ 501f8307e12SArchie Cobbs extern int ng_unparse(const struct ng_parse_type *type, 502f8307e12SArchie Cobbs const u_char *data, char *buf, int buflen); 503f8307e12SArchie Cobbs 504f8307e12SArchie Cobbs /* 505f8307e12SArchie Cobbs * See typedef ng_getDefault_t for definition 506f8307e12SArchie Cobbs */ 507f8307e12SArchie Cobbs extern int ng_parse_getDefault(const struct ng_parse_type *type, 508f8307e12SArchie Cobbs u_char *buf, int *buflen); 509f8307e12SArchie Cobbs 510f8307e12SArchie Cobbs /* 511f8307e12SArchie Cobbs * Parse a token: '*startp' is the offset to start looking. Upon 512f8307e12SArchie Cobbs * successful return, '*startp' equals the beginning of the token 513f8307e12SArchie Cobbs * and '*lenp' the length. If error, '*startp' points at the 514f8307e12SArchie Cobbs * offending character(s). 515f8307e12SArchie Cobbs */ 516f8307e12SArchie Cobbs extern enum ng_parse_token ng_parse_get_token(const char *s, 517f8307e12SArchie Cobbs int *startp, int *lenp); 518f8307e12SArchie Cobbs 519f8307e12SArchie Cobbs /* 520f8307e12SArchie Cobbs * Like above, but specifically for getting a string token and returning 521f8307e12SArchie Cobbs * the string value. The string token must be enclosed in double quotes 522f8307e12SArchie Cobbs * and the normal C backslash escapes are recognized. The caller must 523f8307e12SArchie Cobbs * eventually free() the returned result. Returns NULL if token is 52427121ab1SBrian Somers * not a string token, or parse or other error. Otherwise, *lenp contains 52527121ab1SBrian Somers * the number of characters parsed, and *slenp (if not NULL) contains 52627121ab1SBrian Somers * the actual number of characters in the parsed string. 527f8307e12SArchie Cobbs */ 52827121ab1SBrian Somers extern char *ng_get_string_token(const char *s, int *startp, 52927121ab1SBrian Somers int *lenp, int *slenp); 530f8307e12SArchie Cobbs 531f8307e12SArchie Cobbs /* 532f8307e12SArchie Cobbs * Convert a raw string into a doubly-quoted string including any 533f8307e12SArchie Cobbs * necessary backslash escapes. Caller must free the result. 53427121ab1SBrian Somers * Returns NULL if ENOMEM. Normally "slen" should equal strlen(s) 53527121ab1SBrian Somers * unless you want to encode NUL bytes. 536f8307e12SArchie Cobbs */ 53727121ab1SBrian Somers extern char *ng_encode_string(const char *s, int slen); 538f8307e12SArchie Cobbs 539e20480bfSRuslan Ermilov #endif /* _NETGRAPH_NG_PARSE_H_ */ 540f8307e12SArchie Cobbs 541