~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to drizzled/identifier/table.cc

  • Committer: Brian Aker
  • Date: 2010-10-22 22:02:32 UTC
  • mfrom: (1864.3.17 catalogs)
  • Revision ID: brian@tangent.org-20101022220232-p4l1i9a3ud5asw0d
Merge in Brian. key creation should be improved after this (ie for share)

Show diffs side-by-side

added added

removed removed

Lines of Context:
46
46
 
47
47
static const char hexchars[]= "0123456789abcdef";
48
48
 
49
 
static bool tablename_to_filename(const char *from, char *to, size_t to_length);
 
49
static bool tablename_to_filename(const string &from, string &to);
50
50
 
51
51
/*
52
52
  Translate a cursor name to a table name (WL #1324).
203
203
    path length on success, 0 on failure
204
204
*/
205
205
 
206
 
size_t TableIdentifier::build_table_filename(std::string &path, const char *db, const char *table_name, bool is_tmp)
 
206
size_t TableIdentifier::build_table_filename(std::string &path, const std::string &db, const std::string &table_name, bool is_tmp)
207
207
{
208
 
  char dbbuff[FN_REFLEN];
209
 
  char tbbuff[FN_REFLEN];
210
208
  bool conversion_error= false;
211
209
 
212
 
  memset(tbbuff, 0, sizeof(tbbuff));
 
210
  conversion_error= tablename_to_filename(db, path);
 
211
  if (conversion_error)
 
212
  {
 
213
    errmsg_printf(ERRMSG_LVL_ERROR,
 
214
                  _("Schema name cannot be encoded and fit within filesystem "
 
215
                    "name length restrictions."));
 
216
    return 0;
 
217
  }
 
218
 
 
219
  path.append(FN_ROOTDIR);
 
220
 
213
221
  if (is_tmp) // It a conversion tmp
214
222
  {
215
 
    strncpy(tbbuff, table_name, sizeof(tbbuff));
 
223
    path.append(table_name);
216
224
  }
217
225
  else
218
226
  {
219
 
    conversion_error= tablename_to_filename(table_name, tbbuff, sizeof(tbbuff));
 
227
    conversion_error= tablename_to_filename(table_name, path);
220
228
    if (conversion_error)
221
229
    {
222
230
      errmsg_printf(ERRMSG_LVL_ERROR,
225
233
      return 0;
226
234
    }
227
235
  }
228
 
  memset(dbbuff, 0, sizeof(dbbuff));
229
 
  conversion_error= tablename_to_filename(db, dbbuff, sizeof(dbbuff));
230
 
  if (conversion_error)
231
 
  {
232
 
    errmsg_printf(ERRMSG_LVL_ERROR,
233
 
                  _("Schema name cannot be encoded and fit within filesystem "
234
 
                    "name length restrictions."));
235
 
    return 0;
236
 
  }
237
236
   
238
 
  path.append(dbbuff);
239
 
  path.append(FN_ROOTDIR);
240
 
  path.append(tbbuff);
241
 
 
242
237
  return path.length();
243
238
}
244
239
 
255
250
  RETURN
256
251
    true if errors happen. false on success.
257
252
*/
258
 
static bool tablename_to_filename(const char *from, char *to, size_t to_length)
 
253
static bool tablename_to_filename(const string &from, string &to)
259
254
{
260
255
  
261
 
  size_t length= 0;
262
 
  for (; *from  && length < to_length; length++, from++)
 
256
  string::const_iterator iter= from.begin();
 
257
  for (; iter != from.end(); ++iter)
263
258
  {
264
 
    if ((*from >= '0' && *from <= '9') ||
265
 
        (*from >= 'a' && *from <= 'z') ||
266
 
/* OSX defines an extra set of high-bit and multi-byte characters
267
 
   that cannot be used on the filesystem. Instead of trying to sort
268
 
   those out, we'll just escape encode all high-bit-set chars on OSX.
269
 
   It won't really hurt anything - it'll just make some filenames ugly. */
270
 
#if !defined(TARGET_OS_OSX)
271
 
        ((unsigned char)*from >= 128) ||
272
 
#endif
273
 
        (*from == '_') ||
274
 
        (*from == ' ') ||
275
 
        (*from == '-'))
 
259
    if (isascii(*iter))
276
260
    {
277
 
      to[length]= tolower(*from);
278
 
      continue;
279
 
    }
 
261
      if ((isdigit(*iter)) ||
 
262
          (islower(*iter)) ||
 
263
          (*iter == '_') ||
 
264
          (*iter == ' ') ||
 
265
          (*iter == '-'))
 
266
      {
 
267
        to.push_back(*iter);
 
268
        continue;
 
269
      }
280
270
 
281
 
    if ((*from >= 'A' && *from <= 'Z'))
282
 
    {
283
 
      to[length]= tolower(*from);
284
 
      continue;
 
271
      if (isupper(*iter))
 
272
      {
 
273
        to.push_back(tolower(*iter));
 
274
        continue;
 
275
      }
285
276
    }
286
277
   
287
 
    if (length + 3 >= to_length)
288
 
      return true;
289
 
 
290
278
    /* We need to escape this char in a way that can be reversed */
291
 
    to[length++]= '@';
292
 
    to[length++]= hexchars[(*from >> 4) & 15];
293
 
    to[length]= hexchars[(*from) & 15];
 
279
    to.push_back('@');
 
280
    to.push_back(hexchars[(*iter >> 4) & 15]);
 
281
    to.push_back(hexchars[(*iter) & 15]);
294
282
  }
295
283
 
296
 
  if (internal::check_if_legal_tablename(to) &&
297
 
      length + 4 < to_length)
 
284
  if (internal::check_if_legal_tablename(to.c_str()))
298
285
  {
299
 
    memcpy(to + length, "@@@", 4);
300
 
    length+= 3;
 
286
    to.append("@@@");
301
287
  }
302
288
  return false;
303
289
}
319
305
  case message::Table::FUNCTION:
320
306
  case message::Table::STANDARD:
321
307
    assert(path.size() == 0);
322
 
    build_table_filename(path, getSchemaName().c_str(), table_name.c_str(), false);
 
308
    build_table_filename(path, getSchemaName(), table_name, false);
323
309
    break;
324
310
  case message::Table::INTERNAL:
325
311
    assert(path.size() == 0);
326
 
    build_table_filename(path, getSchemaName().c_str(), table_name.c_str(), true);
 
312
    build_table_filename(path, getSchemaName(), table_name, true);
327
313
    break;
328
314
  case message::Table::TEMPORARY:
329
315
    if (path.empty())
337
323
  hash_value= hasher(path);
338
324
 
339
325
  key.resize(getKeySize());
340
 
  size_t key_length= TableIdentifier::createKey(&key[0], *this);
341
326
 
342
 
  assert(key_length == getKeySize()); // If this is off, then we have a memory issue.
 
327
  std::copy(getSchemaName().begin(), getSchemaName().end(), key.begin());
 
328
  std::copy(getTableName().begin(), getTableName().end(), key.begin() + getSchemaName().length() + 1);
343
329
}
344
330
 
345
331