gscanner.h 8.47 KB
Newer Older
1 2 3 4 5 6
/* GLIB - Library of useful routines for C programming
 * Copyright (C) 1995-1997  Peter Mattis, Spencer Kimball and Josh MacDonald
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
7
 * version 2.1 of the License, or (at your option) any later version.
8 9 10 11 12 13 14
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.	 See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
15
 * License along with this library; if not, see <http://www.gnu.org/licenses/>.
16 17 18 19 20 21
 */

/*
 * Modified by the GLib Team and others 1997-2000.  See the AUTHORS
 * file for a list of people on the GLib Team.  See the ChangeLog
 * files for a list of changes.  These files are distributed with
22
 * GLib at ftp://ftp.gtk.org/pub/gtk/.
23 24
 */

25 26 27
#ifndef __G_SCANNER_H__
#define __G_SCANNER_H__

28
#if !defined (__GLIB_H_INSIDE__) && !defined (GLIB_COMPILATION)
29 30 31
#error "Only <glib.h> can be included directly."
#endif

32
#include <glib/gdataset.h>
33
#include <glib/ghash.h>
34 35 36 37 38 39 40 41 42

G_BEGIN_DECLS

typedef struct _GScanner	GScanner;
typedef struct _GScannerConfig	GScannerConfig;
typedef union  _GTokenValue     GTokenValue;

typedef void		(*GScannerMsgFunc)	(GScanner      *scanner,
						 gchar	       *message,
43
						 gboolean	error);
44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105

/* GScanner: Flexible lexical scanner for general purpose.
 */

/* Character sets */
#define G_CSET_A_2_Z	"ABCDEFGHIJKLMNOPQRSTUVWXYZ"
#define G_CSET_a_2_z	"abcdefghijklmnopqrstuvwxyz"
#define G_CSET_DIGITS	"0123456789"
#define G_CSET_LATINC	"\300\301\302\303\304\305\306"\
			"\307\310\311\312\313\314\315\316\317\320"\
			"\321\322\323\324\325\326"\
			"\330\331\332\333\334\335\336"
#define G_CSET_LATINS	"\337\340\341\342\343\344\345\346"\
			"\347\350\351\352\353\354\355\356\357\360"\
			"\361\362\363\364\365\366"\
			"\370\371\372\373\374\375\376\377"

/* Error types */
typedef enum
{
  G_ERR_UNKNOWN,
  G_ERR_UNEXP_EOF,
  G_ERR_UNEXP_EOF_IN_STRING,
  G_ERR_UNEXP_EOF_IN_COMMENT,
  G_ERR_NON_DIGIT_IN_CONST,
  G_ERR_DIGIT_RADIX,
  G_ERR_FLOAT_RADIX,
  G_ERR_FLOAT_MALFORMED
} GErrorType;

/* Token types */
typedef enum
{
  G_TOKEN_EOF			=   0,
  
  G_TOKEN_LEFT_PAREN		= '(',
  G_TOKEN_RIGHT_PAREN		= ')',
  G_TOKEN_LEFT_CURLY		= '{',
  G_TOKEN_RIGHT_CURLY		= '}',
  G_TOKEN_LEFT_BRACE		= '[',
  G_TOKEN_RIGHT_BRACE		= ']',
  G_TOKEN_EQUAL_SIGN		= '=',
  G_TOKEN_COMMA			= ',',
  
  G_TOKEN_NONE			= 256,
  
  G_TOKEN_ERROR,
  
  G_TOKEN_CHAR,
  G_TOKEN_BINARY,
  G_TOKEN_OCTAL,
  G_TOKEN_INT,
  G_TOKEN_HEX,
  G_TOKEN_FLOAT,
  G_TOKEN_STRING,
  
  G_TOKEN_SYMBOL,
  G_TOKEN_IDENTIFIER,
  G_TOKEN_IDENTIFIER_NULL,
  
  G_TOKEN_COMMENT_SINGLE,
  G_TOKEN_COMMENT_MULTI,
Stef Walter's avatar
Stef Walter committed
106 107

  /*< private >*/
108 109 110 111 112 113 114 115 116 117
  G_TOKEN_LAST
} GTokenType;

union	_GTokenValue
{
  gpointer	v_symbol;
  gchar		*v_identifier;
  gulong	v_binary;
  gulong	v_octal;
  gulong	v_int;
118
  guint64       v_int64;
119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152
  gdouble	v_float;
  gulong	v_hex;
  gchar		*v_string;
  gchar		*v_comment;
  guchar	v_char;
  guint		v_error;
};

struct	_GScannerConfig
{
  /* Character sets
   */
  gchar		*cset_skip_characters;		/* default: " \t\n" */
  gchar		*cset_identifier_first;
  gchar		*cset_identifier_nth;
  gchar		*cpair_comment_single;		/* default: "#\n" */
  
  /* Should symbol lookup work case sensitive?
   */
  guint		case_sensitive : 1;
  
  /* Boolean values to be adjusted "on the fly"
   * to configure scanning behaviour.
   */
  guint		skip_comment_multi : 1;		/* C like comment */
  guint		skip_comment_single : 1;	/* single line comment */
  guint		scan_comment_multi : 1;		/* scan multi line comments? */
  guint		scan_identifier : 1;
  guint		scan_identifier_1char : 1;
  guint		scan_identifier_NULL : 1;
  guint		scan_symbols : 1;
  guint		scan_binary : 1;
  guint		scan_octal : 1;
  guint		scan_float : 1;
153 154
  guint		scan_hex : 1;			/* '0x0ff0' */
  guint		scan_hex_dollar : 1;		/* '$0ff0' */
155 156 157 158 159 160 161 162
  guint		scan_string_sq : 1;		/* string: 'anything' */
  guint		scan_string_dq : 1;		/* string: "\\-escapes!\n" */
  guint		numbers_2_int : 1;		/* bin, octal, hex => int */
  guint		int_2_float : 1;		/* int => G_TOKEN_FLOAT? */
  guint		identifier_2_string : 1;
  guint		char_2_token : 1;		/* return G_TOKEN_CHAR? */
  guint		symbol_2_token : 1;
  guint		scope_0_fallback : 1;		/* try scope 0 on lookups? */
163
  guint		store_int64 : 1; 		/* use value.v_int64 rather than v_int */
Stef Walter's avatar
Stef Walter committed
164 165

  /*< private >*/
Tim Janik's avatar
Tim Janik committed
166
  guint		padding_dummy;
167 168 169 170 171 172 173 174 175 176 177 178 179 180
};

struct	_GScanner
{
  /* unused fields */
  gpointer		user_data;
  guint			max_parse_errors;
  
  /* g_scanner_error() increments this field */
  guint			parse_errors;
  
  /* name of input stream, featured by the default message handler */
  const gchar		*input_name;
  
181 182
  /* quarked data */
  GData			*qdata;
183 184 185 186 187 188 189 190 191 192 193 194 195 196 197
  
  /* link into the scanner configuration */
  GScannerConfig	*config;
  
  /* fields filled in after g_scanner_get_next_token() */
  GTokenType		token;
  GTokenValue		value;
  guint			line;
  guint			position;
  
  /* fields filled in after g_scanner_peek_next_token() */
  GTokenType		next_token;
  GTokenValue		next_value;
  guint			next_line;
  guint			next_position;
Stef Walter's avatar
Stef Walter committed
198 199

  /*< private >*/
200 201 202 203 204 205 206
  /* to be considered private */
  GHashTable		*symbol_table;
  gint			input_fd;
  const gchar		*text;
  const gchar		*text_end;
  gchar			*buffer;
  guint			scope_id;
Stef Walter's avatar
Stef Walter committed
207 208

  /*< public >*/
209 210 211 212
  /* handler function for _warn and _error */
  GScannerMsgFunc	msg_handler;
};

213
GLIB_AVAILABLE_IN_ALL
214
GScanner*	g_scanner_new			(const GScannerConfig *config_templ);
215
GLIB_AVAILABLE_IN_ALL
216
void		g_scanner_destroy		(GScanner	*scanner);
217
GLIB_AVAILABLE_IN_ALL
218 219
void		g_scanner_input_file		(GScanner	*scanner,
						 gint		input_fd);
220
GLIB_AVAILABLE_IN_ALL
221
void		g_scanner_sync_file_offset	(GScanner	*scanner);
222
GLIB_AVAILABLE_IN_ALL
223 224 225
void		g_scanner_input_text		(GScanner	*scanner,
						 const	gchar	*text,
						 guint		text_len);
226
GLIB_AVAILABLE_IN_ALL
227
GTokenType	g_scanner_get_next_token	(GScanner	*scanner);
228
GLIB_AVAILABLE_IN_ALL
229
GTokenType	g_scanner_peek_next_token	(GScanner	*scanner);
230
GLIB_AVAILABLE_IN_ALL
231
GTokenType	g_scanner_cur_token		(GScanner	*scanner);
232
GLIB_AVAILABLE_IN_ALL
233
GTokenValue	g_scanner_cur_value		(GScanner	*scanner);
234
GLIB_AVAILABLE_IN_ALL
235
guint		g_scanner_cur_line		(GScanner	*scanner);
236
GLIB_AVAILABLE_IN_ALL
237
guint		g_scanner_cur_position		(GScanner	*scanner);
238
GLIB_AVAILABLE_IN_ALL
239
gboolean	g_scanner_eof			(GScanner	*scanner);
240
GLIB_AVAILABLE_IN_ALL
241 242
guint		g_scanner_set_scope		(GScanner	*scanner,
						 guint		 scope_id);
243
GLIB_AVAILABLE_IN_ALL
244 245 246 247
void		g_scanner_scope_add_symbol	(GScanner	*scanner,
						 guint		 scope_id,
						 const gchar	*symbol,
						 gpointer	value);
248
GLIB_AVAILABLE_IN_ALL
249 250 251
void		g_scanner_scope_remove_symbol	(GScanner	*scanner,
						 guint		 scope_id,
						 const gchar	*symbol);
252
GLIB_AVAILABLE_IN_ALL
253 254 255
gpointer	g_scanner_scope_lookup_symbol	(GScanner	*scanner,
						 guint		 scope_id,
						 const gchar	*symbol);
256
GLIB_AVAILABLE_IN_ALL
257 258 259 260
void		g_scanner_scope_foreach_symbol	(GScanner	*scanner,
						 guint		 scope_id,
						 GHFunc		 func,
						 gpointer	 user_data);
261
GLIB_AVAILABLE_IN_ALL
262 263
gpointer	g_scanner_lookup_symbol		(GScanner	*scanner,
						 const gchar	*symbol);
264
GLIB_AVAILABLE_IN_ALL
265 266 267 268 269 270 271
void		g_scanner_unexp_token		(GScanner	*scanner,
						 GTokenType	expected_token,
						 const gchar	*identifier_spec,
						 const gchar	*symbol_spec,
						 const gchar	*symbol_name,
						 const gchar	*message,
						 gint		 is_error);
272
GLIB_AVAILABLE_IN_ALL
273 274 275
void		g_scanner_error			(GScanner	*scanner,
						 const gchar	*format,
						 ...) G_GNUC_PRINTF (2,3);
276
GLIB_AVAILABLE_IN_ALL
277 278 279
void		g_scanner_warn			(GScanner	*scanner,
						 const gchar	*format,
						 ...) G_GNUC_PRINTF (2,3);
280 281 282

#ifndef G_DISABLE_DEPRECATED

283 284 285 286 287 288 289 290 291 292 293 294 295
/* keep downward source compatibility */
#define		g_scanner_add_symbol( scanner, symbol, value )	G_STMT_START { \
  g_scanner_scope_add_symbol ((scanner), 0, (symbol), (value)); \
} G_STMT_END
#define		g_scanner_remove_symbol( scanner, symbol )	G_STMT_START { \
  g_scanner_scope_remove_symbol ((scanner), 0, (symbol)); \
} G_STMT_END
#define		g_scanner_foreach_symbol( scanner, func, data )	G_STMT_START { \
  g_scanner_scope_foreach_symbol ((scanner), 0, (func), (data)); \
} G_STMT_END

/* The following two functions are deprecated and will be removed in
 * the next major release. They do no good. */
296 297 298 299
#define g_scanner_freeze_symbol_table(scanner) ((void)0)
#define g_scanner_thaw_symbol_table(scanner) ((void)0)

#endif /* G_DISABLE_DEPRECATED */
300 301 302 303

G_END_DECLS

#endif /* __G_SCANNER_H__ */