summaryrefslogtreecommitdiff
path: root/sql/sql_bootstrap.cc
blob: c5e88739df73e5acb55db31f0252e28256d501b4 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
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
/* Copyright (c) 2010, Oracle and/or its affiliates.

   This program is free software; you can redistribute it and/or modify
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation; version 2 of the License.

   This program 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 General Public License for more details.

   You should have received a copy of the GNU General Public License
   along with this program; if not, write to the Free Software Foundation,
   51 Franklin Street, Suite 500, Boston, MA 02110-1335 USA */


#include <ctype.h>
#include <string.h>
#include "sql_bootstrap.h"

int read_bootstrap_query(char *query, int *query_length,
                         fgets_input_t input, fgets_fn_t fgets_fn)
{
  char line_buffer[MAX_BOOTSTRAP_LINE_SIZE];
  const char *line;
  int len;
  int query_len= 0;

  for ( ; ; )
  {
    line= (*fgets_fn)(line_buffer, sizeof(line_buffer), input);

    if (line == NULL)
      return (query_len ? READ_BOOTSTRAP_ERROR : READ_BOOTSTRAP_EOF);

    len= strlen(line);

    /*
      Remove trailing whitespace characters.
      This assumes:
      - no multibyte encoded character can be found at the very end of a line,
      - whitespace characters from the "C" locale only.
     which is sufficient for the kind of queries found
     in the bootstrap scripts.
    */
    while (len && (isspace(line[len - 1])))
      len--;
    /*
      Cleanly end the string, so we don't have to test len > x
      all the time before reading line[x], in the code below.
    */
    line_buffer[len]= '\0';

    /* Skip blank lines */
    if (len == 0)
      continue;

    /* Skip # comments */
    if (line[0] == '#')
      continue;
    
    /* Skip -- comments */
    if ((line[0] == '-') && (line[1] == '-'))
      continue;

    /* Skip delimiter, ignored. */
    if (strncmp(line, "delimiter", 9) == 0)
      continue;

    /* Append the current line to a multi line query. */

    if (query_len + len + 1 >= MAX_BOOTSTRAP_QUERY_SIZE)
      return READ_BOOTSTRAP_ERROR;

    if (query_len != 0)
    {
      /*
        Append a \n to the current line, if any,
        to preserve the intended presentation.
       */
      query[query_len]= '\n';
      query_len++;
    }
    memcpy(query + query_len, line, len);
    query_len+= len;

    if (line[len - 1] == ';')
    {
      /*
        The last line is terminated by ';'.
        Return the query found.
      */
      query[query_len]= '\0';
      *query_length= query_len;
      return 0;
    }
  }
}