2018-08-02 Nathan Sidwell <nathan@acm.org>
+ libcpp/
+ * include/cpplib.h (enum node_type): Remove NT_ASSERTION.
+ (NTV_NONE): Delete.
+ (CPP_HASHNODE_VALUE_IDX): Adjust.
+ * macro.c (_cpp_free_definition): Zap macro pointer.
+ (_cpp_create_definition): Move _cpp_free_definition call.
+ * directives.c (find_answer): Initialize result.
+ (_cpp_test_assertion): Check macro pointer.
+ (do_assert): Likewise.
+ (do_unassert): Don't node type.
+ * pch.c (write_macdef, count_Defs, write_defs)
+ (save_macros): Adjust fo loss of NT_ASSERTION.
+
Asserts are now macro variants
libcpp/
* directives.c (parse_answer, parse_assertion, find_answer): Use
find_answer (cpp_hashnode *node, const cpp_macro *candidate)
{
unsigned int i;
- cpp_macro **result;
+ cpp_macro **result = NULL;
for (result = &node->value.macro; *result; result = &(*result)->parm.next)
{
*value = 0;
if (node)
- *value = (node->type == NT_ASSERTION &&
- (answer == 0 || *find_answer (node, answer) != 0));
+ {
+ if (node->value.macro)
+ *value = !answer || *find_answer (node, answer);
+ }
else if (pfile->cur_token[-1].type == CPP_EOF)
_cpp_backup_tokens (pfile, 1);
if (node)
{
- cpp_macro *next = NULL;
-
/* Place the new answer in the answer list. First check there
is not a duplicate. */
- if (node->type == NT_ASSERTION)
+ if (*find_answer (node, answer))
{
- if (*find_answer (node, answer))
- {
- cpp_error (pfile, CPP_DL_WARNING, "\"%s\" re-asserted",
- NODE_NAME (node) + 1);
- return;
- }
- next = node->value.macro;
+ cpp_error (pfile, CPP_DL_WARNING, "\"%s\" re-asserted",
+ NODE_NAME (node) + 1);
+ return;
}
/* Commit or allocate storage for the answer. */
(pfile, sizeof (cpp_macro) - sizeof (cpp_token)
+ sizeof (cpp_token) * answer->count);
- answer->parm.next = next;
+ answer->parm.next = node->value.macro;
- node->type = NT_ASSERTION;
+ node->type = NT_MACRO;
node->value.macro = answer;
check_eol (pfile, false);
static void
do_unassert (cpp_reader *pfile)
{
- cpp_hashnode *node;
cpp_macro *answer;
+ cpp_hashnode *node = parse_assertion (pfile, T_UNASSERT, &answer);
- node = parse_assertion (pfile, T_UNASSERT, &answer);
/* It isn't an error to #unassert something that isn't asserted. */
- if (node && node->type == NT_ASSERTION)
+ if (node)
{
if (answer)
{
/* The structure of a node in the hash table. The hash table has
entries for all identifiers: either macros defined by #define
commands (type NT_MACRO), assertions created with #assert
- (NT_ASSERTION), or neither of the above (NT_VOID). Builtin macros
+ (NT_MACRO), or neither of the above (NT_VOID). Builtin macros
like __LINE__ are flagged NODE_BUILTIN. Poisoned identifiers are
flagged NODE_POISONED. NODE_OPERATOR (C++ only) indicates an
identifier that behaves like an operator such as "xor".
enum node_type
{
NT_VOID = 0, /* No definition yet. */
- NT_MACRO, /* A macro of some form. */
- NT_ASSERTION /* Predicate for #assert. */
+ NT_MACRO /* A macro or assert. */
};
/* Different flavors of builtin macro. _Pragma is an operator, but we
enum {
NTV_MACRO,
NTV_BUILTIN,
- NTV_ARGUMENT,
- NTV_NONE
+ NTV_ARGUMENT
};
#define CPP_HASHNODE_VALUE_IDX(HNODE) \
- ((HNODE.flags & NODE_MACRO_ARG) ? NTV_ARGUMENT \
- : HNODE.type == NT_MACRO ? ((HNODE.flags & NODE_BUILTIN) \
- ? NTV_BUILTIN : NTV_MACRO) \
- : HNODE.type == NT_ASSERTION ? NTV_MACRO \
- : NTV_NONE)
+ ((HNODE).flags & NODE_MACRO_ARG ? NTV_ARGUMENT \
+ : (HNODE).flags & NODE_BUILTIN ? NTV_BUILTIN \
+ : NTV_MACRO)
/* The common part of an identifier node shared amongst all 3 C front
ends. Also used to store CPP identifiers, which are a superset of
h->type = NT_VOID;
/* Clear builtin flag in case of redefinition. */
h->flags &= ~(NODE_BUILTIN | NODE_DISABLED | NODE_USED);
+ h->value.macro = NULL;
}
/* Save parameter NODE (spelling SPELLING) to the parameter list of
node->value.macro->line, 0,
"this is the location of the previous definition");
}
+ _cpp_free_definition (node);
}
- if (node->type != NT_VOID)
- _cpp_free_definition (node);
-
/* Enter definition in hash table. */
node->type = NT_MACRO;
node->value.macro = macro;
/* FALLTHRU */
case NT_MACRO:
- if ((hn->flags & NODE_BUILTIN)
- && (!pfile->cb.user_builtin_macro
- || !pfile->cb.user_builtin_macro (pfile, hn)))
+ if (hn->flags & NODE_BUILTIN)
+ {
+ if (!pfile->cb.user_builtin_macro
+ || !pfile->cb.user_builtin_macro (pfile, hn))
+ return 1;
+ }
+ else if (hn->value.macro->kind == cmk_assert)
return 1;
{
}
return 1;
- case NT_ASSERTION:
- /* Not currently implemented. */
- return 1;
-
default:
abort ();
}
case NT_MACRO:
if (hn->flags & NODE_BUILTIN)
return 1;
+ if (hn->value.macro->kind == cmk_assert)
+ return 1;
/* fall through. */
}
return 1;
- case NT_ASSERTION:
- /* Not currently implemented. */
- return 1;
-
default:
abort ();
}
case NT_MACRO:
if (hn->flags & NODE_BUILTIN)
return 1;
+ if (hn->value.macro->kind == cmk_assert)
+ return 1;
/* fall through. */
}
return 1;
- case NT_ASSERTION:
- /* Not currently implemented. */
- return 1;
-
default:
abort ();
}
{
struct save_macro_data *data = (struct save_macro_data *)data_p;
- if ((h->flags & NODE_BUILTIN)
- && h->type == NT_MACRO
- && r->cb.user_builtin_macro)
- r->cb.user_builtin_macro (r, h);
+ if (h->type != NT_MACRO)
+ return 1;
- if (h->type != NT_VOID
- && (h->flags & NODE_BUILTIN) == 0)
+ if (h->flags & NODE_BUILTIN)
+ {
+ if (r->cb.user_builtin_macro)
+ r->cb.user_builtin_macro (r, h);
+ }
+ else if (h->value.macro->kind == cmk_assert)
+ return 1;
+ else
{
if (data->count == data->array_size)
{
data->defns = XRESIZEVEC (uchar *, data->defns, (data->array_size));
}
- switch (h->type)
- {
- case NT_ASSERTION:
- /* Not currently implemented. */
- return 1;
+ const uchar * defn = cpp_macro_definition (r, h);
+ size_t defnlen = ustrlen (defn);
- case NT_MACRO:
- {
- const uchar * defn = cpp_macro_definition (r, h);
- size_t defnlen = ustrlen (defn);
-
- data->defns[data->count] = (uchar *) xmemdup (defn, defnlen,
- defnlen + 2);
- data->defns[data->count][defnlen] = '\n';
- }
- break;
-
- default:
- abort ();
- }
+ data->defns[data->count] = (uchar *) xmemdup (defn, defnlen, defnlen + 2);
+ data->defns[data->count][defnlen] = '\n';
data->count++;
}
+
return 1;
}