Print this page
Address Robert's feedback
@@ -10,23 +10,26 @@
*/
/*
* Copyright 2017 Jason King.
*/
-
+#include <ctype.h>
#include <errno.h>
+#include <locale.h>
#include <string.h>
#include <setjmp.h>
#include <stdio.h>
#include <stdlib.h>
#include <sys/isa_defs.h>
#include <sys/debug.h>
#include "sysdemangle.h"
#include "sysdemangle_int.h"
-#include "cpp.h"
+#include "cxx.h"
+#ifndef ARRAY_SIZE
#define ARRAY_SIZE(x) (sizeof (x) / sizeof (x[0]))
+#endif
#define CPP_QUAL_CONST (1U)
#define CPP_QUAL_VOLATILE (2U)
#define CPP_QUAL_RESTRICT (4U)
@@ -41,10 +44,11 @@
unsigned cpp_depth;
boolean_t cpp_parsed_ctor_dtor_cv;
boolean_t cpp_tag_templates;
boolean_t cpp_fix_forward_references;
boolean_t cpp_try_to_parse_template_args;
+ locale_t cpp_loc;
} cpp_db_t;
#define CK(x) \
do { \
if (!(x)) \
@@ -53,12 +57,10 @@
#define TOP_L(db) (&(name_top(&(db)->cpp_name)->strp_l))
#define RLEN(f, l) ((size_t)((l) - (f)))
#define NAMT(db, n) (nlen(db) - n)
-static inline boolean_t is_digit(int);
-static inline boolean_t is_upper(int);
static inline boolean_t is_xdigit(int);
static boolean_t nempty(cpp_db_t *);
static size_t nlen(cpp_db_t *);
static void nadd_l(cpp_db_t *, const char *, size_t);
@@ -74,11 +76,11 @@
static void tsub(cpp_db_t *, size_t);
static void tpush(cpp_db_t *);
static void tpop(cpp_db_t *);
static void tsave(cpp_db_t *, size_t);
-static void db_init(cpp_db_t *, sysdem_ops_t *);
+static boolean_t db_init(cpp_db_t *, sysdem_ops_t *);
static void db_fini(cpp_db_t *);
static void dump(cpp_db_t *, FILE *);
static void demangle(const char *, const char *, cpp_db_t *);
@@ -89,20 +91,20 @@
static const char *parse_dot_suffix(const char *, const char *, cpp_db_t *);
static const char *parse_block_invoke(const char *, const char *, cpp_db_t *);
static const char *parse_special_name(const char *, const char *, cpp_db_t *);
static const char *parse_name(const char *, const char *, boolean_t *,
cpp_db_t *);
-static const char *parse_call_offset(const char *, const char *);
-static const char *parse_number(const char *, const char *);
+static const char *parse_call_offset(const char *, const char *, locale_t);
+static const char *parse_number(const char *, const char *, locale_t);
static const char *parse_nested_name(const char *, const char *, boolean_t *,
cpp_db_t *);
static const char *parse_local_name(const char *, const char *, boolean_t *,
cpp_db_t *);
static const char *parse_unscoped_name(const char *, const char *, cpp_db_t *);
static const char *parse_template_args(const char *, const char *, cpp_db_t *);
static const char *parse_substitution(const char *, const char *, cpp_db_t *);
-static const char *parse_discriminator(const char *, const char *);
+static const char *parse_discriminator(const char *, const char *, locale_t);
static const char *parse_cv_qualifiers(const char *, const char *, unsigned *);
static const char *parse_template_param(const char *, const char *, cpp_db_t *);
static const char *parse_decltype(const char *, const char *, cpp_db_t *);
static const char *parse_template_args(const char *, const char *, cpp_db_t *);
static const char *parse_unqualified_name(const char *, const char *,
@@ -164,12 +166,12 @@
{
char *result = NULL;
cpp_db_t db;
size_t srclen = strlen(src);
- db_init(&db, ops);
-
+ if (!db_init(&db, ops))
+ goto done;
if (setjmp(db.cpp_jmp) != 0)
goto done;
errno = 0;
demangle(src, src + srclen, &db);
@@ -269,11 +271,11 @@
}
static const char *
parse_dot_suffix(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (first == last || first[0] != '.')
return (first);
if (nempty(db))
@@ -291,11 +293,11 @@
* _block_invoke_<digit>+
*/
static const char *
parse_block_invoke(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 13)
return (first);
const char test[] = "_block_invoke";
@@ -308,16 +310,16 @@
if (t == last)
goto done;
if (t[0] == '_') {
/* need at least one digit */
- if (t + 1 == last || !is_digit(t[1]))
+ if (t + 1 == last || !isdigit_l(t[1], db->cpp_loc))
return (first);
t += 2;
}
- while (t < last && is_digit(t[0]))
+ while (t < last && isdigit_l(t[0], db->cpp_loc))
t++;
done:
if (nempty(db))
return (first);
@@ -332,11 +334,11 @@
* ::= <special name>
*/
static const char *
parse_encoding(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (first == last)
return (first);
const char *t = NULL;
@@ -405,11 +407,11 @@
* a bit of a hack, but a template substitution can apparently be
* an empty string at the end of an argument list, so avoid
* <...., >
*/
if (NAMT(db, n) > 1 && str_pair_len(name_top(&db->cpp_name)) == 0)
- (void) name_pop(&db->cpp_name, NULL);
+ name_pop(&db->cpp_name, NULL);
njoin(db, NAMT(db, n), ", ");
nfmt(db, "({0})", NULL);
str_t *s = TOP_L(db);
@@ -463,11 +465,11 @@
* extension ::= GR <object name> # reference temporary for object
*/
static const char *
parse_special_name(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
const char *t = first;
const char *t1 = NULL;
size_t n = nlen(db);
@@ -493,14 +495,14 @@
nadd_l(db, "typeinfo name for", 0);
t = parse_type(first + 2, last, db);
break;
case 'c':
nadd_l(db, "covariant return thunk to", 0);
- t1 = parse_call_offset(first + 2, last);
+ t1 = parse_call_offset(first + 2, last, db->cpp_loc);
if (t1 == t)
return (first);
- t = parse_call_offset(t1, last);
+ t = parse_call_offset(t1, last, db->cpp_loc);
if (t == t1)
return (first);
t1 = parse_encoding(t, last, db);
if (t1 == t)
return (first);
@@ -507,11 +509,11 @@
break;
case 'C':
t = parse_type(first + 2, last, db);
if (t == first + 2)
return (first);
- t1 = parse_number(t, last);
+ t1 = parse_number(t, last, db->cpp_loc);
if (*t1 != '_')
return (first);
t = parse_type(t1 + 1, last, db);
if (t == t1 + 1 || nlen(db) < 2)
return (first);
@@ -531,11 +533,11 @@
nadd_l(db, "virtual thunk to", 0);
} else {
nadd_l(db, "non-virtual thunk to", 0);
}
- t = parse_call_offset(first + 1, last);
+ t = parse_call_offset(first + 1, last, db->cpp_loc);
if (t == first + 1)
return (first);
t1 = parse_encoding(t, last, db);
if (t == t1)
return (first);
@@ -578,13 +580,13 @@
*
* <v-offset> ::= <offset number> _ <virtual offset number>
* # virtual base override, with vcall offset
*/
static const char *
-parse_call_offset(const char *first, const char *last)
+parse_call_offset(const char *first, const char *last, locale_t loc)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
const char *t = NULL;
const char *t1 = NULL;
if (first == last)
@@ -591,21 +593,21 @@
return (first);
if (first[0] != 'h' && first[0] != 'v')
return (first);
- t = parse_number(first + 1, last);
+ t = parse_number(first + 1, last, loc);
if (t == first + 1 || t == last || t[0] != '_')
return (first);
/* skip _ */
t++;
if (first[0] == 'h')
return (t);
- t1 = parse_number(t, last);
+ t1 = parse_number(t, last, loc);
if (t == t1 || t1 == last || t1[0] != '_')
return (first);
/* skip _ */
t1++;
@@ -624,11 +626,11 @@
*/
static const char *
parse_name(const char *first, const char *last,
boolean_t *ends_with_template_args, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
const char *t = first;
const char *t1 = NULL;
if (last - first < 2)
@@ -687,11 +689,11 @@
/* END CSTYLED */
const char *
parse_local_name(const char *first, const char *last,
boolean_t *ends_with_template_args, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
const char *t = NULL;
const char *t1 = NULL;
const char *t2 = NULL;
@@ -700,22 +702,22 @@
t = parse_encoding(first + 1, last, db);
if (t == first + 1 || t == last || t[0] != 'E')
return (first);
- ASSERT(!nempty(db));
+ VERIFY(!nempty(db));
/* skip E */
t++;
if (t[0] == 's') {
nfmt(db, "{0:L}::string literal", "{0:R}");
- return (parse_discriminator(t, last));
+ return (parse_discriminator(t, last, db->cpp_loc));
}
if (t[0] == 'd') {
- t1 = parse_number(t + 1, last);
+ t1 = parse_number(t + 1, last, db->cpp_loc);
if (t1[0] != '_')
return (first);
t1++;
} else {
t1 = t;
@@ -727,11 +729,11 @@
nfmt(db, "{1:L}::{0}", "{1:R}");
/* parsed, but ignored */
if (t[0] != 'd')
- t2 = parse_discriminator(t2, last);
+ t2 = parse_discriminator(t2, last, db->cpp_loc);
return (t2);
}
/* BEGIN CSTYLED */
@@ -755,11 +757,11 @@
/* END CSTYLED */
static const char *
parse_nested_name(const char *first, const char *last,
boolean_t *ends_with_template_args, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (first == last || first[0] != 'N')
return (first);
unsigned cv = 0;
@@ -808,11 +810,11 @@
return (first);
if (!more) {
nfmt(db, "{0}", NULL);
} else {
- ASSERT3U(nlen(db), >, 1);
+ VERIFY3U(nlen(db), >, 1);
nfmt(db, "{1:L}::{0}", "{1:R}");
save_top(db, 1);
}
more = B_TRUE;
@@ -826,11 +828,11 @@
return (first);
if (!more) {
nfmt(db, "{0}", NULL);
} else {
- ASSERT3U(nlen(db), >, 1);
+ VERIFY3U(nlen(db), >, 1);
nfmt(db, "{1:L}::{0}", "{1:R}");
}
save_top(db, 1);
more = B_TRUE;
@@ -846,11 +848,11 @@
return (first);
if (!more) {
nfmt(db, "{0}", NULL);
} else {
- ASSERT3U(nlen(db), >, 1);
+ VERIFY3U(nlen(db), >, 1);
nfmt(db, "{1:L}::{0}", "{1:R}");
}
save_top(db, 1);
more = B_TRUE;
@@ -868,11 +870,11 @@
t1 = parse_template_args(t, last, db);
if (t1 == t || t1 == last)
return (first);
- ASSERT3U(nlen(db), >, 1);
+ VERIFY3U(nlen(db), >, 1);
nfmt(db, "{1:L}{0}", "{1:R}");
save_top(db, 1);
t = t1;
component_ends_with_template_args = B_TRUE;
continue;
@@ -892,11 +894,11 @@
return (first);
if (!more) {
nfmt(db, "{0}", NULL);
} else {
- ASSERT3U(nlen(db), >, 1);
+ VERIFY3U(nlen(db), >, 1);
nfmt(db, "{1:L}::{0}", "{1:R}");
}
save_top(db, 1);
more = B_TRUE;
@@ -929,11 +931,11 @@
* ::= LZ <encoding> E # extension
*/
static const char *
parse_template_arg(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
const char *t = NULL;
const char *t1 = NULL;
if (first == last)
@@ -1129,11 +1131,11 @@
#undef PN
static const char *
parse_expression(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 2)
return (first);
for (size_t i = 0; i < ARRAY_SIZE(expr_tbl); i++) {
@@ -1173,11 +1175,11 @@
static const char *
parse_binary_expr(const char *first, const char *last, const char *op,
cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 2)
return (first);
size_t n = nlen(db);
@@ -1193,11 +1195,11 @@
return (first);
if (NAMT(db, n) != 3)
return (first);
- ASSERT3U(nlen(db), >, 2);
+ VERIFY3U(nlen(db), >, 2);
nfmt(db, "({2}) {1} ({0})", NULL);
if (strcmp(op, ">") == 0)
nfmt(db, "({0})", NULL);
@@ -1206,11 +1208,11 @@
static const char *
parse_prefix_expr(const char *first, const char *last, const char *op,
cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 2)
return (first);
nadd_l(db, op, 0);
@@ -1218,20 +1220,20 @@
const char *t = parse_expression(first + 2, last, db);
if (t == first + 2) {
return (first);
}
- ASSERT3U(nlen(db), >, 1);
+ VERIFY3U(nlen(db), >, 1);
nfmt(db, "{1}({0})", NULL);
return (t);
}
static const char *
parse_gs(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
const char *t = NULL;
if (last - first < 4)
return (first);
@@ -1244,11 +1246,11 @@
return (first);
if (t == first + 2)
return (first);
- ASSERT3U(nlen(db), >, 0);
+ VERIFY3U(nlen(db), >, 0);
nfmt(db, "::{0}", NULL);
return (t);
}
@@ -1260,28 +1262,28 @@
* <initializer> ::= pi <expression>* E # parenthesized initialization
*/
static const char *
parse_new_expr(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
/* note [gs] is already handled by parse_gs() */
if (last - first < 3)
return (first);
- ASSERT3U(first[0], ==, 'n');
- ASSERT(first[1] == 'a' || first[1] == 'w');
+ VERIFY3U(first[0], ==, 'n');
+ VERIFY(first[1] == 'a' || first[1] == 'w');
const char *t1 = first + 2;
const char *t2 = NULL;
size_t n = nlen(db);
nadd_l(db, (first[1] == 'w') ? "new" : "new[]", 0);
while (t1 != last && t1[0] != '_') {
t2 = parse_expression(t1, last, db);
- ASSERT3P(t2, !=, NULL);
+ VERIFY3P(t2, !=, NULL);
if (t2 == t1)
return (first);
t1 = t2;
}
if (t1 == last)
@@ -1327,17 +1329,17 @@
}
static const char *
parse_del_expr(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 3)
return (first);
- ASSERT3U(first[0], ==, 'd');
- ASSERT(first[1] == 'l' || first[1] == 'a');
+ VERIFY3U(first[0], ==, 'd');
+ VERIFY(first[1] == 'l' || first[1] == 'a');
size_t n = nlen(db);
const char *t = parse_expression(first + 2, last, db);
if (t == first + 2 || NAMT(db, n) != 1)
return (first);
@@ -1347,13 +1349,13 @@
}
static const char *
parse_idx_expr(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
- ASSERT3U(first[0], ==, 'i');
- ASSERT3U(first[1], ==, 'x');
+ VERIFY3P(first, <=, last);
+ VERIFY3U(first[0], ==, 'i');
+ VERIFY3U(first[1], ==, 'x');
size_t n = nlen(db);
const char *t1 = parse_expression(first + 2, last, db);
if (t1 == first + 2)
return (first);
@@ -1368,11 +1370,11 @@
static const char *
parse_ppmm_expr(const char *first, const char *last, const char *fmt,
cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 3)
return (first);
const char *t = NULL;
@@ -1394,32 +1396,32 @@
}
static const char *
parse_mm_expr(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
- ASSERT3U(first[0], ==, 'm');
- ASSERT3U(first[1], ==, 'm');
+ VERIFY3P(first, <=, last);
+ VERIFY3U(first[0], ==, 'm');
+ VERIFY3U(first[1], ==, 'm');
return (parse_ppmm_expr(first, last, "({0})--", db));
}
static const char *
parse_pp_expr(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
- ASSERT3U(first[0], ==, 'p');
- ASSERT3U(first[0], ==, 'p');
+ VERIFY3U(first[0], ==, 'p');
+ VERIFY3U(first[0], ==, 'p');
return (parse_ppmm_expr(first, last, "({0})++", db));
}
static const char *
parse_trinary_expr(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
const char *t1, *t2, *t3;
size_t n = nlen(db);
if (last - first < 2)
@@ -1443,11 +1445,11 @@
}
static const char *
parse_noexcept_expr(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 2)
return (first);
size_t n = nlen(db);
@@ -1466,11 +1468,11 @@
* sc <type> <expression> # static_cast<type> (expression)
*/
static const char *
parse_cast_expr(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 2)
return (first);
const char *fmt = NULL;
@@ -1489,31 +1491,31 @@
break;
default:
return (first);
}
- ASSERT3U(first[1], ==, 'c');
+ VERIFY3U(first[1], ==, 'c');
const char *t1 = parse_type(first + 2, last, db);
if (t1 == first + 2)
return (first);
const char *t2 = parse_expression(t1, last, db);
if (t2 == t1)
return (first);
- ASSERT3U(nlen(db), >, 1);
+ VERIFY3U(nlen(db), >, 1);
nfmt(db, fmt, NULL);
return (t2);
}
/* pt <expression> <expression> # expr->name */
static const char *
parse_arrow_expr(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 4)
return (first);
size_t n = nlen(db);
@@ -1574,11 +1576,11 @@
*/
/* END CSTYLED */
static const char *
parse_type(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (first == last)
return (first);
switch (first[0]) {
@@ -1741,14 +1743,14 @@
if (t != name->str_s + 9) {
nfmt(db, "{1}<{0}>", NULL);
str_pair_t save = {0};
- (void) name_pop(&db->cpp_name, &save);
+ name_pop(&db->cpp_name, &save);
/* get rid of 'objcproto' */
- (void) name_pop(&db->cpp_name, NULL);
+ name_pop(&db->cpp_name, NULL);
CK(name_add_str(&db->cpp_name, &save.strp_l,
&save.strp_r));
} else {
nfmt(db, "{1} {0}", NULL);
}
@@ -1839,11 +1841,11 @@
}
static const char *
parse_qual_type(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
const char *t = NULL;
const char *t1 = NULL;
unsigned cv = 0;
@@ -1914,11 +1916,11 @@
* az <expression> # alignof (a expression)
*/
static const char *
parse_alignof(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 2)
return (first);
const char *(*fn)(const char *, const char *, cpp_db_t *);
@@ -1939,16 +1941,16 @@
* sz <expr> # sizeof (a expression)
*/
static const char *
parse_sizeof(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 2)
return (first);
- ASSERT3U(first[0], ==, 's');
+ VERIFY3U(first[0], ==, 's');
const char *t = NULL;
size_t n = nlen(db);
switch (first[1]) {
@@ -1977,31 +1979,31 @@
*/
/* END CSTYLED */
static const char *
parse_function_param(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 3 || first[0] != 'f')
return (first);
const char *t1 = first + 2;
const char *t2 = NULL;
unsigned cv = 0;
if (first[1] == 'L') {
- t2 = parse_number(t1, last);
+ t2 = parse_number(t1, last, db->cpp_loc);
if (t2 == last || t2[0] != 'p')
return (first);
t1 = t2;
}
if (first[1] != 'p')
return (first);
t1 = parse_cv_qualifiers(t1, last, &cv);
- t2 = parse_number(t1, last);
+ t2 = parse_number(t1, last, db->cpp_loc);
if (t2 == last || t2[0] != '_')
return (first);
if (t2 - t1 > 0)
nadd_l(db, t1, (size_t)(t2 - t1));
@@ -2017,17 +2019,17 @@
* sZ <function-param> # size of a function parameter pack
*/
static const char *
parse_sizeof_param_pack_expr(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 3)
return (first);
- ASSERT3U(first[0], ==, 's');
- ASSERT3U(first[1], ==, 'Z');
+ VERIFY3U(first[0], ==, 's');
+ VERIFY3U(first[1], ==, 'Z');
if (first[2] != 'T' && first[2] != 'f')
return (first);
const char *t = NULL;
@@ -2051,17 +2053,17 @@
* ti <type> # typeid (type)
*/
static const char *
parse_typeid_expr(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 3)
return (first);
- ASSERT3U(first[0], ==, 't');
- ASSERT(first[1] == 'e' || first[1] == 'i');
+ VERIFY3U(first[0], ==, 't');
+ VERIFY(first[1] == 'e' || first[1] == 'i');
const char *t = NULL;
size_t n = nlen(db);
if (first[1] == 'e')
@@ -2081,17 +2083,17 @@
* tw <expression> # throw expression
*/
static const char *
parse_throw_expr(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 3)
return (first);
- ASSERT3U(first[0], ==, 't');
- ASSERT(first[1] == 'w' || first[1] == 'r');
+ VERIFY3U(first[0], ==, 't');
+ VERIFY(first[1] == 'w' || first[1] == 'r');
if (first[1] == 'r') {
nadd_l(db, "throw", 0);
return (first + 2);
}
@@ -2107,17 +2109,17 @@
/* ds <expression> <expression> # expr.*expr */
static const char *
parse_dot_star_expr(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 3)
return (first);
- ASSERT3U(first[0], ==, 'd');
- ASSERT3U(first[1], ==, 's');
+ VERIFY3U(first[0], ==, 'd');
+ VERIFY3U(first[1], ==, 's');
size_t n = nlen(db);
const char *t = parse_expression(first + 2, last, db);
if (t == first + 2)
return (first);
@@ -2132,17 +2134,17 @@
/* dt <expression> <unresolved-name> # expr.name */
static const char *
parse_dot_expr(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 3)
return (first);
- ASSERT3U(first[0], ==, 'd');
- ASSERT3U(first[1], ==, 't');
+ VERIFY3U(first[0], ==, 'd');
+ VERIFY3U(first[1], ==, 't');
const char *t = parse_expression(first + 2, last, db);
if (t == first + 2)
return (first);
@@ -2156,17 +2158,17 @@
/* cl <expression>+ E # call */
static const char *
parse_call_expr(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 4)
return (first);
- ASSERT3U(first[0], ==, 'c');
- ASSERT3U(first[1], ==, 'l');
+ VERIFY3U(first[0], ==, 'c');
+ VERIFY3U(first[1], ==, 'l');
const char *t = first + 2;
const char *t1 = NULL;
size_t n = nlen(db);
@@ -2182,11 +2184,11 @@
return (first);
njoin(db, amt - 1, ", ");
nfmt(db, "{1}({0})", NULL);
- ASSERT3U(t[0], ==, 'E');
+ VERIFY3U(t[0], ==, 'E');
return (t + 1);
}
/* BEGIN CSTYLED */
/*
@@ -2195,17 +2197,17 @@
*/
/* END CSTYLED */
static const char *
parse_conv_expr(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 3)
return (first);
- ASSERT3U(first[0], ==, 'c');
- ASSERT3U(first[1], ==, 'v');
+ VERIFY3U(first[0], ==, 'c');
+ VERIFY3U(first[1], ==, 'v');
const char *t = NULL;
const char *t1 = NULL;
size_t n = nlen(db);
@@ -2252,11 +2254,11 @@
/* <simple-id> ::= <source-name> [ <template-args> ] */
static const char *
parse_simple_id(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
const char *t = parse_source_name(first, last, db);
if (t == first)
return (t);
@@ -2274,11 +2276,11 @@
* ::= <substitution>
*/
static const char *
parse_unresolved_type(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (first == last)
return (first);
const char *t = first;
@@ -2287,11 +2289,11 @@
switch (first[0]) {
case 'T':
t = parse_template_param(first, last, db);
if (t == first || NAMT(db, n) != 1) {
for (size_t i = 0; i < NAMT(db, n); i++)
- (void) name_pop(&db->cpp_name, NULL);
+ name_pop(&db->cpp_name, NULL);
return (first);
}
save_top(db, 1);
return (t);
@@ -2324,17 +2326,17 @@
/* sp <expression> # pack expansion */
static const char *
parse_pack_expansion(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 3)
return (first);
- ASSERT3U(first[0], ==, 's');
- ASSERT3U(first[1], ==, 'p');
+ VERIFY3U(first[0], ==, 's');
+ VERIFY3U(first[1], ==, 'p');
const char *t = parse_expression(first + 2, last, db);
if (t == first +2)
return (first);
@@ -2347,11 +2349,11 @@
* extension ::= StL<unqualified-name>
*/
static const char *
parse_unscoped_name(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 2)
return (first);
const char *t = first;
@@ -2383,11 +2385,11 @@
* ::= <unnamed-type-name>
*/
const char *
parse_unqualified_name(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (first == last)
return (first);
switch (*first) {
@@ -2422,11 +2424,11 @@
* # Parameter types or "v" if the lambda has no parameters
*/
static const char *
parse_unnamed_type_name(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 2 || first[0] != 'U')
return (first);
if (first[1] != 't' && first[1] != 'l')
@@ -2434,11 +2436,12 @@
const char *t1 = first + 2;
const char *t2 = NULL;
if (first[1] == 't') {
- while (t1 != last && t1[0] != '_' && is_digit(t1[0]))
+ while (t1 != last && t1[0] != '_' &&
+ isdigit_l(t1[0], db->cpp_loc))
t1++;
if (t1[0] != '_')
return (first);
@@ -2477,11 +2480,11 @@
/* E */
t1++;
t2 = t1;
while (t2 != last && t2[0] != '_') {
- if (!is_digit(*t2++))
+ if (!isdigit_l(*t2++, db->cpp_loc))
return (first);
}
if (t2[0] != '_')
return (first);
@@ -2570,11 +2573,11 @@
}
}
}
out:
- ASSERT3P(end, >=, start);
+ VERIFY3P(end, >=, start);
if (end - start < 2) {
nadd_l(db, "", 0);
return;
}
@@ -2584,11 +2587,11 @@
start++;
break;
}
}
- ASSERT3P(end, >=, start);
+ VERIFY3P(end, >=, start);
nadd_l(db, start, (size_t)(end - start));
}
/*
@@ -2602,11 +2605,11 @@
* extension ::= D5 # ?
*/
static const char *
parse_ctor_dtor_name(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 2 || nempty(db) || str_length(TOP_L(db)) == 0)
return (first);
switch (first[0]) {
@@ -2645,13 +2648,13 @@
static const char *
parse_integer_literal(const char *first, const char *last, const char *fmt,
cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
- const char *t = parse_number(first, last);
+ const char *t = parse_number(first, last, db->cpp_loc);
const char *start = first;
if (t == first || t == last || t[0] != 'E')
return (first);
@@ -2678,12 +2681,12 @@
};
static const char *
parse_floating_literal(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
- ASSERT(first[0] == 'f' || first[0] == 'd' || first[0] == 'e');
+ VERIFY3P(first, <=, last);
+ VERIFY(first[0] == 'f' || first[0] == 'd' || first[0] == 'e');
const struct float_data_s *fd = NULL;
for (size_t i = 0; i < ARRAY_SIZE(float_info); i++) {
if (float_info[i].type != first[0])
@@ -2730,24 +2733,24 @@
#if defined(_BIG_ENDIAN)
for (t = first + 1; t != last; t++, e++) {
if (!is_xdigit(t[0]))
return (first);
- unsigned d1 = is_digit(t[0]) ? t[0] - '0' : t[0] - 'a' + 10;
+ unsigned d1 = isdigit_l(t[0], db->cpp_loc) ? t[0] - '0' : t[0] - 'a' + 10;
t++;
- unsigned d0 = is_digit(t[0]) ? t[0] - '0' : t[0] - 'a' + 10;
+ unsigned d0 = isdigit_l(t[0], db->cpp_loc) ? t[0] - '0' : t[0] - 'a' + 10;
*e = (d1 << 4) + d0;
}
#elif defined(_LITTLE_ENDIAN)
for (t = last - 1; t > first; t--, e++) {
if (!is_xdigit(t[0]))
return (first);
- unsigned d0 = is_digit(t[0]) ? t[0] - '0' : t[0] - 'a' + 10;
+ unsigned d0 = isdigit_l(t[0], db->cpp_loc) ? t[0] - '0' : t[0] - 'a' + 10;
t--;
- unsigned d1 = is_digit(t[0]) ? t[0] - '0' : t[0] - 'a' + 10;
+ unsigned d1 = isdigit_l(t[0], db->cpp_loc) ? t[0] - '0' : t[0] - 'a' + 10;
*e = (d1 << 4) + d0;
}
t = last;
#else
@@ -2824,11 +2827,11 @@
};
static const char *
parse_expr_primary(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 4 || first[0] != 'L')
return (first);
const char *t = NULL;
@@ -2888,11 +2891,11 @@
if (t[0] == 'E')
return (t + 1);
const char *n;
- for (n = t; n != last && is_digit(n[0]); n++)
+ for (n = t; n != last && isdigit_l(n[0], db->cpp_loc); n++)
;
if (n == last || nempty(db) || n[0] != 'E')
return (first);
if (n == t)
return (t);
@@ -3011,11 +3014,11 @@
};
static const char *
parse_operator_name(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 2)
return (first);
for (size_t i = 0; i < ARRAY_SIZE(op_tbl); i++) {
@@ -3036,11 +3039,11 @@
nfmt(db, "operator\"\" {0}", NULL);
return (t);
}
if (first[0] == 'v') {
- if (!is_digit(first[1]))
+ if (!isdigit_l(first[1], db->cpp_loc))
return (first);
t = parse_source_name(first + 2, last, db);
if (t == first + 2)
return (first);
@@ -3109,11 +3112,11 @@
};
static const char *
parse_builtin_type(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (first == last)
return (first);
size_t i;
@@ -3145,23 +3148,23 @@
return (first);
}
static const char *
-parse_base36(const char *first, const char *last, size_t *val)
+parse_base36(const char *first, const char *last, size_t *val, locale_t loc)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
const char *t;
for (t = first, *val = 0; t != last; t++) {
- if (!is_digit(t[0]) && !is_upper(t[0]))
+ if (!isdigit_l(t[0], loc) && !isupper_l(t[0], loc))
return (t);
*val *= 36;
- if (is_digit(t[0]))
+ if (isdigit_l(t[0], loc))
*val += t[0] - '0';
else
*val += t[0] - 'A' + 10;
}
return (t);
@@ -3177,11 +3180,11 @@
};
static const char *
parse_substitution(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (first == last || last - first < 2)
return (first);
if (first[0] != 'S')
@@ -3196,11 +3199,11 @@
const char *t = first + 1;
size_t n = 0;
if (t[0] != '_') {
- t = parse_base36(first + 1, last, &n);
+ t = parse_base36(first + 1, last, &n, db->cpp_loc);
if (t == first + 1 || t[0] != '_')
return (first);
/*
* S_ == substitution 0,
@@ -3214,27 +3217,27 @@
return (first);
sub(db, n);
/* skip _ */
- ASSERT3U(t[0], ==, '_');
+ VERIFY3U(t[0], ==, '_');
return (t + 1);
}
static const char *
parse_source_name(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (first == last)
return (first);
const char *t = NULL;
size_t n = 0;
- for (t = first; t != last && is_digit(t[0]); t++) {
+ for (t = first; t != last && isdigit_l(t[0], db->cpp_loc); t++) {
/* make sure we don't overflow */
size_t nn = n * 10;
if (nn < n)
return (first);
@@ -3266,23 +3269,23 @@
* ::= p # AltiVec vector pixel
*/
static const char *
parse_vector_type(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 3)
return (first);
- ASSERT3U(first[0], ==, 'D');
- ASSERT3U(first[1], ==, 'v');
+ VERIFY3U(first[0], ==, 'D');
+ VERIFY3U(first[1], ==, 'v');
const char *t = first + 2;
const char *t1 = NULL;
- if (is_digit(first[2]) && first[2] != '0') {
- t1 = parse_number(t, last);
+ if (isdigit_l(first[2], db->cpp_loc) && first[2] != '0') {
+ t1 = parse_number(t, last, db->cpp_loc);
if (t1 == last || t1 + 1 == last || t1[0] != '_')
return (first);
nadd_l(db, t, (size_t)(t1 - t));
@@ -3327,16 +3330,16 @@
*/
/* END CSTYLED */
static const char *
parse_decltype(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 4)
return (first);
- ASSERT3U(first[0], ==, 'D');
+ VERIFY3U(first[0], ==, 'D');
if (first[1] != 't' && first[1] != 'T')
return (first);
size_t n = nlen(db);
@@ -3355,23 +3358,23 @@
* ::= A [<dimension expression>] _ <element type>
*/
static const char *
parse_array_type(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
- ASSERT3U(first[0], ==, 'A');
+ VERIFY3P(first, <=, last);
+ VERIFY3U(first[0], ==, 'A');
if (last - first < 3)
return (first);
const char *t = first + 1;
const char *t1 = NULL;
size_t n = nlen(db);
if (t[0] != '_') {
- if (is_digit(t[0]) && t[0] != '0') {
- t1 = parse_number(t, last);
+ if (isdigit_l(t[0], db->cpp_loc) && t[0] != '0') {
+ t1 = parse_number(t, last, db->cpp_loc);
if (t1 == last)
return (first);
nadd_l(db, t, (size_t)(t1 - t));
} else {
@@ -3386,11 +3389,11 @@
t = t1;
} else {
nadd_l(db, "", 0);
}
- ASSERT3U(t[0], ==, '_');
+ VERIFY3U(t[0], ==, '_');
t1 = parse_type(t + 1, last, db);
if (t1 == t + 1 || NAMT(db, n) != 2)
return (first);
@@ -3408,16 +3411,16 @@
/* <pointer-to-member-type> ::= M <class type> <member type> */
static const char *
parse_pointer_to_member_type(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 3)
return (first);
- ASSERT3U(first[0], ==, 'M');
+ VERIFY3U(first[0], ==, 'M');
const char *t1 = first + 1;
const char *t2 = NULL;
size_t n = nlen(db);
@@ -3457,11 +3460,11 @@
*/
/* END CSTYLED */
static const char *
parse_unresolved_name(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 2)
return (first);
const char *t = first;
@@ -3505,11 +3508,11 @@
nfmt(db, "{1:L}{0}", "{1:R}");
t = t2;
}
- ASSERT3U(NAMT(db, n), ==, 1);
+ VERIFY3U(NAMT(db, n), ==, 1);
while (t[0] != 'E') {
size_t nn = nlen(db);
t2 = parse_unresolved_qualifier_level(t, last, db);
if (t == t2 || t == last || NAMT(db, nn) != 1)
@@ -3577,11 +3580,11 @@
/* <unresolved-qualifier-level> ::= <simple-id> */
static const char *
parse_unresolved_qualifier_level(const char *first, const char *last,
cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
return (parse_simple_id(first, last, db));
}
/* BEGIN CSTYLED */
/*
@@ -3595,11 +3598,11 @@
*/
/* END CSTYLED */
static const char *
parse_base_unresolved_name(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 2)
return (first);
const char *t = NULL;
@@ -3644,11 +3647,11 @@
* ::= <simple-id> # e.g., ~A<2*N>
*/
static const char *
parse_destructor_name(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (first == last)
return (first);
const char *t = parse_unresolved_type(first, last, db);
@@ -3670,16 +3673,16 @@
* <function-type> ::= F [Y] <bare-function-type> [<ref-qualifier>] E
*/
static const char *
parse_function_type(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 2)
return (first);
- ASSERT3U(first[0], ==, 'F');
+ VERIFY3U(first[0], ==, 'F');
const char *t = first + 1;
/* extern "C" */
if (t[0] == 'Y')
@@ -3746,20 +3749,20 @@
* ::= T <parameter-2 non-negative number> _
*/
static const char *
parse_template_param(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 2 || first[0] != 'T')
return (first);
const char *t = first + 1;
size_t idx = 0;
while (t != last && t[0] != '_') {
- if (!is_digit(t[0]))
+ if (!isdigit_l(t[0], db->cpp_loc))
return (first);
idx *= 10;
idx += t[0] - '0';
t++;
@@ -3766,11 +3769,11 @@
}
if (t == last)
return (first);
- ASSERT3U(t[0], ==, '_');
+ VERIFY3U(t[0], ==, '_');
/*
* T_ -> idx 0
* T0 -> idx 1
* T1 -> idx 2
@@ -3800,11 +3803,11 @@
* extension, the abi says <template-arg>+
*/
static const char *
parse_template_args(const char *first, const char *last, cpp_db_t *db)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (last - first < 2 || first[0] != 'I')
return (first);
if (db->cpp_tag_templates)
@@ -3836,15 +3839,15 @@
* ugly, but if the last thing pushed was an empty string,
* get rid of it so we dont get "<..., >"
*/
if (NAMT(db, n) > 1 &&
str_pair_len(name_top(&db->cpp_name)) == 0)
- (void) name_pop(&db->cpp_name, NULL);
+ name_pop(&db->cpp_name, NULL);
njoin(db, NAMT(db, n), ", ");
- ASSERT3U(nlen(db), >, 0);
+ VERIFY3U(nlen(db), >, 0);
/* make sure we don't bitshift ourselves into oblivion */
str_t *top = TOP_L(db);
if (str_length(top) > 0 &&
top->str_s[top->str_len - 1] == '>')
@@ -3860,21 +3863,21 @@
* <discriminator> := _ <non-negative number> # when number < 10
* := __ <non-negative number> _ # when number >= 10
* extension := decimal-digit+ # at the end of string
*/
static const char *
-parse_discriminator(const char *first, const char *last)
+parse_discriminator(const char *first, const char *last, locale_t loc)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
const char *t = NULL;
if (first == last)
return (first);
- if (is_digit(first[0])) {
- for (t = first; t != last && is_digit(t[0]); t++)
+ if (isdigit_l(first[0], loc)) {
+ for (t = first; t != last && isdigit_l(t[0], loc); t++)
;
/* not at the end of the string */
if (t != last)
return (first);
@@ -3883,17 +3886,17 @@
} else if (first[0] != '_' || first + 1 == last) {
return (first);
}
t = first + 1;
- if (is_digit(t[0]))
+ if (isdigit_l(t[0], loc))
return (t + 1);
if (t[0] != '_' || t + 1 == last)
return (first);
- for (t++; t != last && is_digit(t[0]); t++)
+ for (t++; t != last && isdigit_l(t[0], loc); t++)
;
if (t == last || t[0] != '_')
return (first);
return (t);
@@ -3901,11 +3904,11 @@
/* <CV-qualifiers> ::= [r] [V] [K] */
const char *
parse_cv_qualifiers(const char *first, const char *last, unsigned *cv)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
if (first == last)
return (first);
*cv = 0;
@@ -3927,51 +3930,37 @@
/*
* <number> ::= [n] <non-negative decimal integer>
*/
static const char *
-parse_number(const char *first, const char *last)
+parse_number(const char *first, const char *last, locale_t loc)
{
- ASSERT3P(first, <=, last);
+ VERIFY3P(first, <=, last);
const char *t = first;
- if (first == last || (first[0] != 'n' && !is_digit(first[0])))
+ if (first == last || (first[0] != 'n' && !isdigit_l(first[0], loc)))
return (first);
if (t[0] == 'n')
t++;
if (t[0] == '0')
return (t + 1);
- while (is_digit(t[0]))
+ while (isdigit_l(t[0], loc))
t++;
return (t);
}
/*
- * we only ever use ASCII versions of these
+ * Like isxdigit(3C), except we can only accept lower case letters as
+ * that's only what is allowed when [de]mangling floating point constants into
+ * their hex representation.
*/
static inline boolean_t
-is_digit(int c)
-{
- if (c < '0' || c > '9')
- return (B_FALSE);
- return (B_TRUE);
-}
-
-static inline boolean_t
-is_upper(int c)
-{
- if (c < 'A' || c > 'Z')
- return (B_FALSE);
- return (B_TRUE);
-}
-
-static inline boolean_t
is_xdigit(int c)
{
if ((c >= '0' && c <= '9') || (c >= 'a' && c <= 'f'))
return (B_TRUE);
return (B_FALSE);
@@ -4055,11 +4044,11 @@
tsave(cpp_db_t *db, size_t amt)
{
CK(templ_save(&db->cpp_name, amt, &db->cpp_templ));
}
-static void
+static boolean_t
db_init(cpp_db_t *db, sysdem_ops_t *ops)
{
(void) memset(db, 0, sizeof (*db));
db->cpp_ops = ops;
name_init(&db->cpp_name, ops);
@@ -4066,18 +4055,21 @@
sub_init(&db->cpp_subs, ops);
templ_init(&db->cpp_templ, ops);
db->cpp_tag_templates = B_TRUE;
db->cpp_try_to_parse_template_args = B_TRUE;
tpush(db);
+ db->cpp_loc = newlocale(LC_CTYPE_MASK, "C", 0);
+ return ((db->cpp_loc != NULL) ? B_TRUE : B_FALSE);
}
static void
db_fini(cpp_db_t *db)
{
name_fini(&db->cpp_name);
sub_fini(&db->cpp_subs);
templ_fini(&db->cpp_templ);
+ freelocale(db->cpp_loc);
(void) memset(db, 0, sizeof (*db));
}
static void
print_sp(const str_pair_t *sp, FILE *out)
@@ -4105,11 +4097,11 @@
}
(void) fputc('\n', out);
}
-
+/* Print a base-36 number (for substitutions) */
static char *
base36(char *buf, size_t val)
{
char tmp[16] = { 0 };
char *p = tmp;