Simplify json lexing state
authorJohn Naylor <[email protected]>
Fri, 8 Jul 2022 07:53:20 +0000 (14:53 +0700)
committerJohn Naylor <[email protected]>
Fri, 8 Jul 2022 07:53:20 +0000 (14:53 +0700)
Instead of updating the length as we go, use a const pointer to end of
the input, which we know already at the start.

This simplifies the coding and may improve performance slightly, but
the real motivation for doing this is to make further changes in this
area easier to reason about.

Discussion: https://www.postgresql.org/message-id/CAFBsxsGhaR2KQ5eisaK%3D6Vm60t%3DaxhD8Ckj1qFoCH1pktZi%2B2w%40mail.gmail.com

src/common/jsonapi.c

index 98e4ef09426ac7eb2c18bd91551abaf106951939..eeedc0645a0a85a8df2a690caaee3940c8f87858 100644 (file)
@@ -519,26 +519,23 @@ JsonParseErrorType
 json_lex(JsonLexContext *lex)
 {
    char       *s;
-   int         len;
+   char       *const end = lex->input + lex->input_length;
    JsonParseErrorType result;
 
    /* Skip leading whitespace. */
    s = lex->token_terminator;
-   len = s - lex->input;
-   while (len < lex->input_length &&
-          (*s == ' ' || *s == '\t' || *s == '\n' || *s == '\r'))
+   while (s < end && (*s == ' ' || *s == '\t' || *s == '\n' || *s == '\r'))
    {
        if (*s++ == '\n')
        {
            ++lex->line_number;
            lex->line_start = s;
        }
-       len++;
    }
    lex->token_start = s;
 
    /* Determine token type. */
-   if (len >= lex->input_length)
+   if (s >= end)
    {
        lex->token_start = NULL;
        lex->prev_token_terminator = lex->token_terminator;
@@ -623,7 +620,7 @@ json_lex(JsonLexContext *lex)
                     * the whole word as an unexpected token, rather than just
                     * some unintuitive prefix thereof.
                     */
-                   for (p = s; p - s < lex->input_length - len && JSON_ALPHANUMERIC_CHAR(*p); p++)
+                   for (p = s; p < end && JSON_ALPHANUMERIC_CHAR(*p); p++)
                         /* skip */ ;
 
                    /*
@@ -672,7 +669,7 @@ static inline JsonParseErrorType
 json_lex_string(JsonLexContext *lex)
 {
    char       *s;
-   int         len;
+   char       *const end = lex->input + lex->input_length;
    int         hi_surrogate = -1;
 
    if (lex->strval != NULL)
@@ -680,13 +677,11 @@ json_lex_string(JsonLexContext *lex)
 
    Assert(lex->input_length > 0);
    s = lex->token_start;
-   len = lex->token_start - lex->input;
    for (;;)
    {
        s++;
-       len++;
        /* Premature end of the string. */
-       if (len >= lex->input_length)
+       if (s >= end)
        {
            lex->token_terminator = s;
            return JSON_INVALID_TOKEN;
@@ -704,8 +699,7 @@ json_lex_string(JsonLexContext *lex)
        {
            /* OK, we have an escape character. */
            s++;
-           len++;
-           if (len >= lex->input_length)
+           if (s >= end)
            {
                lex->token_terminator = s;
                return JSON_INVALID_TOKEN;
@@ -718,8 +712,7 @@ json_lex_string(JsonLexContext *lex)
                for (i = 1; i <= 4; i++)
                {
                    s++;
-                   len++;
-                   if (len >= lex->input_length)
+                   if (s >= end)
                    {
                        lex->token_terminator = s;
                        return JSON_INVALID_TOKEN;