28
28
* Implementation of the server's date and time string matching utility.
31
#include "drizzled/global.h"
33
33
#include "drizzled/temporal_format.h"
34
34
#include "drizzled/temporal.h"
36
#include <string> /** C++ string class used */
36
37
#include <string.h>
37
39
#include PCRE_HEADER
47
TemporalFormat::TemporalFormat(const char *pattern) :
44
TemporalFormat::TemporalFormat(const char *pattern)
74
int32_t match_vector[OUT_VECTOR_SIZE]; /**< Stores match substring indexes */
76
/* Make sure we've got no junk in the match_vector. */
77
memset(match_vector, 0, sizeof(match_vector));
79
75
/* Simply check the subject against the compiled regular expression */
80
76
int32_t result= pcre_exec(_re
81
77
, NULL /* No extra data */
113
109
/* C++ string class easy to use substr() method is very useful here */
114
string copy_data(data, data_len);
110
std::string copy_data(data, data_len);
116
112
* OK, we have the expected substring matches, so grab
117
113
* the various temporal parts from the subject string
124
120
if (_year_part_index > 1)
126
size_t year_start= match_vector[_year_part_index];
127
size_t year_len= match_vector[_year_part_index + 1] - match_vector[_year_part_index];
122
size_t year_start= _match_vector[_year_part_index];
123
size_t year_len= _match_vector[_year_part_index + 1] - _match_vector[_year_part_index];
128
124
to->_years= atoi(copy_data.substr(year_start, year_len).c_str());
129
125
if (year_len == 2)
130
126
to->_years+= (to->_years >= DRIZZLE_YY_PART_YEAR ? 1900 : 2000);
132
128
if (_month_part_index > 1)
134
size_t month_start= match_vector[_month_part_index];
135
size_t month_len= match_vector[_month_part_index + 1] - match_vector[_month_part_index];
130
size_t month_start= _match_vector[_month_part_index];
131
size_t month_len= _match_vector[_month_part_index + 1] - _match_vector[_month_part_index];
136
132
to->_months= atoi(copy_data.substr(month_start, month_len).c_str());
138
134
if (_day_part_index > 1)
140
size_t day_start= match_vector[_day_part_index];
141
size_t day_len= match_vector[_day_part_index + 1] - match_vector[_day_part_index];
136
size_t day_start= _match_vector[_day_part_index];
137
size_t day_len= _match_vector[_day_part_index + 1] - _match_vector[_day_part_index];
142
138
to->_days= atoi(copy_data.substr(day_start, day_len).c_str());
144
140
if (_hour_part_index > 1)
146
size_t hour_start= match_vector[_hour_part_index];
147
size_t hour_len= match_vector[_hour_part_index + 1] - match_vector[_hour_part_index];
142
size_t hour_start= _match_vector[_hour_part_index];
143
size_t hour_len= _match_vector[_hour_part_index + 1] - _match_vector[_hour_part_index];
148
144
to->_hours= atoi(copy_data.substr(hour_start, hour_len).c_str());
150
146
if (_minute_part_index > 1)
152
size_t minute_start= match_vector[_minute_part_index];
153
size_t minute_len= match_vector[_minute_part_index + 1] - match_vector[_minute_part_index];
148
size_t minute_start= _match_vector[_minute_part_index];
149
size_t minute_len= _match_vector[_minute_part_index + 1] - _match_vector[_minute_part_index];
154
150
to->_minutes= atoi(copy_data.substr(minute_start, minute_len).c_str());
156
152
if (_second_part_index > 1)
158
size_t second_start= match_vector[_second_part_index];
159
size_t second_len= match_vector[_second_part_index + 1] - match_vector[_second_part_index];
154
size_t second_start= _match_vector[_second_part_index];
155
size_t second_len= _match_vector[_second_part_index + 1] - _match_vector[_second_part_index];
160
156
to->_seconds= atoi(copy_data.substr(second_start, second_len).c_str());
162
158
if (_usecond_part_index > 1)
164
size_t usecond_start= match_vector[_usecond_part_index];
165
size_t usecond_len= match_vector[_usecond_part_index + 1] - match_vector[_usecond_part_index];
160
size_t usecond_start= _match_vector[_usecond_part_index];
161
size_t usecond_len= _match_vector[_usecond_part_index + 1] - _match_vector[_usecond_part_index];
167
163
* For microseconds, which are millionth of 1 second,
168
164
* we must ensure that we produce a correct result,
181
177
if (_nsecond_part_index > 1)
183
size_t nsecond_start= match_vector[_nsecond_part_index];
184
size_t nsecond_len= match_vector[_nsecond_part_index + 1] - match_vector[_nsecond_part_index];
179
size_t nsecond_start= _match_vector[_nsecond_part_index];
180
size_t nsecond_len= _match_vector[_nsecond_part_index + 1] - _match_vector[_nsecond_part_index];
186
182
* For nanoseconds, which are 1 billionth of a second,
187
183
* we must ensure that we produce a correct result,
251
248
, {"^(\\d{1,2})\\.(\\d{1,6})$", 0, 0, 0, 0, 0, 1, 2, 0} /* [S]S.uuuuuu */
254
vector<TemporalFormat *> known_datetime_formats;
255
vector<TemporalFormat *> known_date_formats;
256
vector<TemporalFormat *> known_time_formats;
257
vector<TemporalFormat *> all_temporal_formats;
251
std::vector<drizzled::TemporalFormat *> known_datetime_formats;
252
std::vector<drizzled::TemporalFormat *> known_date_formats;
253
std::vector<drizzled::TemporalFormat *> known_time_formats;
254
std::vector<drizzled::TemporalFormat *> all_temporal_formats;
260
257
* We allocate and initialize all known date/time formats.
264
261
bool init_temporal_formats()
266
263
/* Compile all the regular expressions for the datetime formats */
264
drizzled::TemporalFormat *tmp;
268
265
struct temporal_format_args current_format_args;
271
268
for (x= 0; x<COUNT_KNOWN_FORMATS; ++x)
273
270
current_format_args= __format_args[x];
274
tmp= new TemporalFormat(current_format_args.pattern);
271
tmp= new drizzled::TemporalFormat(current_format_args.pattern);
275
272
tmp->set_year_part_index(current_format_args.year_part_index);
276
273
tmp->set_month_part_index(current_format_args.month_part_index);
277
274
tmp->set_day_part_index(current_format_args.day_part_index);