src->tokens = deque_expand (&src->deque, src->tokens, sizeof *src->tokens);
token = &src->tokens[deque_push_front (&src->deque)];
- token_init (&token->token);
+ token->token = (struct token) { .type = T_STOP };
return token;
}
return lex_source_next__ (src, n);
else
{
- static const struct lex_token stop_token =
- { TOKEN_INITIALIZER (T_STOP, 0.0, ""), 0, 0, 0, 0 };
-
+ static const struct lex_token stop_token = { .token = { .type = T_STOP } };
return &stop_token;
}
}
#include "libpspp/cast.h"
#include "libpspp/misc.h"
-
#include "gl/ftoastr.h"
#include "gl/xalloc.h"
-/* Initializes TOKEN with an arbitrary type, number 0, and a null string. */
+/* Initializes DST as a copy of SRC. */
void
-token_init (struct token *token)
+token_copy (struct token *dst, const struct token *src)
{
- token->type = 0;
- token->number = 0.0;
- token->string = ss_empty ();
+ *dst = (struct token) {
+ .type = src->type,
+ .number = src->number,
+ };
+ ss_alloc_substring (&dst->string, src->string);
}
/* Frees the string that TOKEN contains. */
token_uninit (struct token *token)
{
if (token != NULL)
- ss_dealloc (&token->string);
+ {
+ ss_dealloc (&token->string);
+ *token = (struct token) { .type = T_STOP };
+ }
+}
+
+/* Returns true if A and B are the same token, false otherwise. */
+bool
+token_equal (const struct token *a, const struct token *b)
+{
+ if (a->type != b->type)
+ return false;
+
+ switch (a->type)
+ {
+ case T_POS_NUM:
+ case T_NEG_NUM:
+ return a->number == b->number;
+
+ case T_ID:
+ case T_MACRO_ID:
+ case T_MACRO_PUNCT:
+ case T_STRING:
+ return ss_equals (a->string, b->string);
+
+ default:
+ return true;
+ }
}
static char *
return string_representation (token->string);
default:
- return xstrdup_if_nonnull (token_type_to_name (token->type));
+ return xstrdup_if_nonnull (token_type_to_string (token->type));
}
}
putc ('\n', stream);
}
+/* Returns true if T is a numeric token for an integer in the range of "long",
+ except that LONG_MIN is excluded. */
bool
token_is_integer (const struct token *t)
{
&& floor (t->number) == t->number);
}
+/* Returns the "long int" value of T, which must satisfy token_is_integer(T). */
long
token_integer (const struct token *t)
{
#ifndef TOKEN_H
#define TOKEN_H 1
+#include <stdbool.h>
#include <stdio.h>
#include "libpspp/assertion.h"
#include "libpspp/str.h"
struct substring string;
};
-#define TOKEN_INITIALIZER(TYPE, NUMBER, STRING) \
- { TYPE, NUMBER, SS_LITERAL_INITIALIZER (STRING) }
-
-void token_init (struct token *);
+void token_copy (struct token *, const struct token *);
void token_uninit (struct token *);
+bool token_equal (const struct token *, const struct token *);
+
char *token_to_string (const struct token *);
void token_print (const struct token *, FILE *);