~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to mysys/mf_pack.c

  • Committer: Brian Aker
  • Date: 2008-09-12 06:42:41 UTC
  • mto: (322.2.8 stdize-code)
  • mto: This revision was merged to the branch mainline in revision 386.
  • Revision ID: brian@tangent.org-20080912064241-520utxq2078904l2
Remove 3 byte UTF8 collation

Show diffs side-by-side

added added

removed removed

Lines of Context:
19
19
#ifdef HAVE_PWD_H
20
20
#include <pwd.h>
21
21
#endif
 
22
#ifdef VMS
 
23
#include <rms.h>
 
24
#include <iodef.h>
 
25
#include <descrip.h>
 
26
#endif /* VMS */
22
27
 
23
28
static char * expand_tilde(char * *path);
24
29
 
28
33
 
29
34
void pack_dirname(char * to, const char *from)
30
35
{
31
 
  int getcwd_error= 0;
 
36
  int cwd_err;
32
37
  size_t d_length,length,buff_length= 0;
33
38
  char * start;
34
39
  char buff[FN_REFLEN];
42
47
#endif
43
48
    start=to;
44
49
 
45
 
  if (!(getcwd(buff, FN_REFLEN)))
 
50
  if (!(cwd_err= my_getwd(buff,FN_REFLEN,MYF(0))))
46
51
  {
47
 
    getcwd_error= errno;
48
52
    buff_length= strlen(buff);
49
53
    d_length= (size_t) (start-to);
50
54
    if ((start == to ||
51
 
        (buff_length == d_length && !memcmp(buff,start,d_length))) &&
52
 
        *start != FN_LIBCHAR && *start)
 
55
         (buff_length == d_length && !memcmp(buff,start,d_length))) &&
 
56
        *start != FN_LIBCHAR && *start)
53
57
    {                                           /* Put current dir before */
54
 
      bchange((unsigned char*) to, d_length, (unsigned char*) buff, buff_length, strlen(to)+1);
 
58
      bchange((uchar*) to, d_length, (uchar*) buff, buff_length, strlen(to)+1);
55
59
    }
56
60
  }
57
61
 
62
66
    {
63
67
      length= strlen(home_dir);
64
68
      if (home_dir[length-1] == FN_LIBCHAR)
65
 
        length--;                               /* Don't test last '/' */
 
69
        length--;                               /* Don't test last '/' */
66
70
    }
67
71
    if (length > 1 && length < d_length)
68
72
    {                                           /* test if /xx/yy -> ~/yy */
69
73
      if (memcmp(to,home_dir,length) == 0 && to[length] == FN_LIBCHAR)
70
74
      {
71
 
        to[0]=FN_HOMELIB;                       /* Filename begins with ~ */
72
 
        (void) strcpy(to+1,to+length);
 
75
        to[0]=FN_HOMELIB;                       /* Filename begins with ~ */
 
76
        (void) strmov_overlapp(to+1,to+length);
73
77
      }
74
78
    }
75
 
    if (! getcwd_error)
 
79
    if (! cwd_err)
76
80
    {                                           /* Test if cwd is ~/... */
77
81
      if (length > 1 && length < buff_length)
78
82
      {
79
 
        if (memcmp(buff,home_dir,length) == 0 && buff[length] == FN_LIBCHAR)
80
 
        {
81
 
          buff[0]=FN_HOMELIB;
82
 
          (void) strcpy(buff+1,buff+length);
83
 
        }
 
83
        if (memcmp(buff,home_dir,length) == 0 && buff[length] == FN_LIBCHAR)
 
84
        {
 
85
          buff[0]=FN_HOMELIB;
 
86
          (void) strmov_overlapp(buff+1,buff+length);
 
87
        }
84
88
      }
85
89
      if (is_prefix(to,buff))
86
90
      {
87
 
        length= strlen(buff);
88
 
        if (to[length])
89
 
          (void) strcpy(to,to+length);  /* Remove everything before */
90
 
        else
91
 
        {
92
 
          to[0]= FN_CURLIB;                     /* Put ./ instead of cwd */
93
 
          to[1]= FN_LIBCHAR;
94
 
          to[2]= '\0';
95
 
        }
 
91
        length= strlen(buff);
 
92
        if (to[length])
 
93
          (void) strmov_overlapp(to,to+length); /* Remove everything before */
 
94
        else
 
95
        {
 
96
          to[0]= FN_CURLIB;                     /* Put ./ instead of cwd */
 
97
          to[1]= FN_LIBCHAR;
 
98
          to[2]= '\0';
 
99
        }
96
100
      }
97
101
    }
98
102
  }
117
121
  Unpacks current dir if if "./.." used
118
122
 
119
123
  RETURN
120
 
    #  length of new name
 
124
    #  length of new name   
121
125
*/
122
126
 
123
127
size_t cleanup_dirname(register char *to, const char *from)
138
142
  if ((pos=strrchr(from_ptr,FN_DEVCHAR)) != 0)
139
143
  {                                             /* Skip device part */
140
144
    length=(size_t) (pos-from_ptr)+1;
141
 
    start= strncpy(buff,from_ptr,length);
142
 
    start+= strlen(from_ptr);
143
 
    from_ptr+=length;
 
145
    start=stpncpy(buff,from_ptr,length); from_ptr+=length;
144
146
  }
145
147
#endif
146
148
 
147
149
  parent[0]=FN_LIBCHAR;
148
 
  length= (size_t)((strcpy(parent+1,FN_PARENTDIR)+strlen(FN_PARENTDIR))-parent);
 
150
  length=(size_t) (stpcpy(parent+1,FN_PARENTDIR)-parent);
149
151
  for (pos=start ; (*pos= *from_ptr++) != 0 ; pos++)
150
152
  {
151
153
#ifdef BACKSLASH_MBTAIL
152
 
    uint32_t l;
 
154
    uint l;
153
155
    if (use_mb(fs) && (l= my_ismbchar(fs, from_ptr - 1, from_ptr + 2)))
154
156
    {
155
157
      for (l-- ; l ; *++pos= *from_ptr++, l--);
175
177
              pos+=length+1;                    /* Don't unpack ~/.. */
176
178
              continue;
177
179
            }
178
 
            pos= strcpy(buff,home_dir)+strlen(home_dir)-1;      /* Unpacks ~/.. */
 
180
            pos=stpcpy(buff,home_dir)-1;        /* Unpacks ~/.. */
179
181
            if (*pos == FN_LIBCHAR)
180
182
              pos--;                            /* home ended with '/' */
181
183
          }
182
184
          if (*pos == FN_CURLIB && (pos == start || pos[-1] == FN_LIBCHAR))
183
185
          {
184
 
            if (getcwd(curr_dir,FN_REFLEN))
 
186
            if (my_getwd(curr_dir,FN_REFLEN,MYF(0)))
185
187
            {
186
188
              pos+=length+1;                    /* Don't unpack ./.. */
187
189
              continue;
188
190
            }
189
 
            pos= strcpy(buff,curr_dir)+strlen(curr_dir)-1;      /* Unpacks ./.. */
 
191
            pos=stpcpy(buff,curr_dir)-1;        /* Unpacks ./.. */
190
192
            if (*pos == FN_LIBCHAR)
191
193
              pos--;                            /* home ended with '/' */
192
194
          }
195
197
            pos--;
196
198
          if (pos[1] == FN_HOMELIB || memcmp(pos,parent,length) == 0)
197
199
          {                                     /* Don't remove ~user/ */
198
 
            pos= strcpy(end_parentdir+1,parent)+strlen(parent);
 
200
            pos=stpcpy(end_parentdir+1,parent);
199
201
            *pos=FN_LIBCHAR;
200
202
            continue;
201
203
          }
221
223
      }
222
224
    }
223
225
  }
224
 
  (void) strcpy(to,buff);
 
226
  (void) stpcpy(to,buff);
225
227
  return((size_t) (pos-buff));
226
228
} /* cleanup_dirname */
227
229
 
228
230
 
229
231
/*
230
232
  On system where you don't have symbolic links, the following
231
 
  code will allow you to create a file:
 
233
  code will allow you to create a file: 
232
234
  directory-name.sym that should contain the real path
233
235
  to the directory.  This will be used if the directory name
234
236
  doesn't exists
247
249
    File file;
248
250
    size_t length;
249
251
    char temp= *(--pos);            /* May be "/" or "\" */
250
 
    strcpy(pos,".sym");
 
252
    stpcpy(pos,".sym");
251
253
    file= my_open(dir, O_RDONLY, MYF(0));
252
254
    *pos++=temp; *pos=0;          /* Restore old filename */
253
255
    if (file >= 0)
254
256
    {
255
257
      if ((length= my_read(file, buff, sizeof(buff), MYF(0))) > 0)
256
258
      {
257
 
        for (pos= buff + length ;
258
 
             pos > buff && (iscntrl(pos[-1]) || isspace(pos[-1])) ;
259
 
             pos --);
260
 
 
261
 
        /* Ensure that the symlink ends with the directory symbol */
262
 
        if (pos == buff || pos[-1] != FN_LIBCHAR)
263
 
          *pos++=FN_LIBCHAR;
264
 
 
265
 
        strncpy(dir,buff, FN_REFLEN-1);
 
259
        for (pos= buff + length ;
 
260
             pos > buff && (iscntrl(pos[-1]) || isspace(pos[-1])) ;
 
261
             pos --);
 
262
 
 
263
        /* Ensure that the symlink ends with the directory symbol */
 
264
        if (pos == buff || pos[-1] != FN_LIBCHAR)
 
265
          *pos++=FN_LIBCHAR;
 
266
 
 
267
        strmake(dir,buff, (size_t) (pos-buff));
266
268
      }
267
269
      my_close(file, MYF(0));
268
270
    }
319
321
        if (tilde_expansion[h_length-1] == FN_LIBCHAR)
320
322
          h_length--;
321
323
        if (buff+h_length < suffix)
322
 
          memmove(buff+h_length, suffix, length);
 
324
          memcpy(buff+h_length, suffix, length);
323
325
        else
324
 
          bmove_upp((unsigned char*) buff+h_length+length, (unsigned char*) suffix+length, length);
325
 
        memmove(buff, tilde_expansion, h_length);
 
326
          bmove_upp((uchar*) buff+h_length+length, (uchar*) suffix+length, length);
 
327
        memcpy(buff, tilde_expansion, h_length);
326
328
      }
327
329
    }
328
330
  }
389
391
  n_length=unpack_dirname(buff,buff);
390
392
  if (n_length+strlen(from+length) < FN_REFLEN)
391
393
  {
392
 
    (void) strcpy(buff+n_length,from+length);
 
394
    (void) stpcpy(buff+n_length,from+length);
393
395
    length= system_filename(to,buff);           /* Fix to usably filename */
394
396
  }
395
397
  else
405
407
size_t system_filename(char * to, const char *from)
406
408
{
407
409
#ifndef FN_C_BEFORE_DIR
408
 
  return strlen(strncpy(to,from,FN_REFLEN-1));
 
410
  return (size_t) (strmake(to,from,FN_REFLEN-1)-to);
409
411
#else   /* VMS */
410
412
 
411
413
        /* change 'dev:lib/xxx' to 'dev:[lib]xxx' */
421
423
  char buff[FN_REFLEN];
422
424
 
423
425
  libchar_found=0;
424
 
  (void) strcpy(buff,from);                      /* If to == from */
 
426
  (void) stpcpy(buff,from);                      /* If to == from */
425
427
  from_pos= buff;
426
428
  if ((pos=strrchr(from_pos,FN_DEVCHAR)))       /* Skip device part */
427
429
  {
428
430
    pos++;
429
 
    to_pos= strncpy(to,from_pos,(size_t) (pos-from_pos));
430
 
    to_pos+= strlen(to);
 
431
    to_pos=stpncpy(to,from_pos,(size_t) (pos-from_pos));
431
432
    from_pos=pos;
432
433
  }
433
434
  else
443
444
      from_pos+=strlen(FN_ROOTDIR);             /* Actually +1 but... */
444
445
      if (! strchr(from_pos,FN_LIBCHAR))
445
446
      {                                         /* No dir, use [000000] */
446
 
        to_pos= strcpy(to_pos,FN_C_ROOT_DIR)+strlen(FN_C_ROOT_DIR);
 
447
        to_pos=stpcpy(to_pos,FN_C_ROOT_DIR);
447
448
        libchar_found++;
448
449
      }
449
450
    }
453
454
    while ((pos=strchr(from_pos,FN_LIBCHAR)))
454
455
    {
455
456
      if (libchar_found++)
456
 
        *(to_pos++)=FN_C_DIR_SEP;               /* Add '.' between dirs */
 
457
        *(to_pos++)=FN_C_DIR_SEP;               /* Add '.' between dirs */
457
458
      if (strstr(from_pos,FN_PARENTDIR) == from_pos &&
458
 
          from_pos+strlen(FN_PARENTDIR) == pos) {
459
 
        to_pos= strcpy(to_pos,FN_C_PARENT_DIR); /* Found '../' */
460
 
        to_pos+= strlen(FN_C_PARENT_DIR);
461
 
      }
 
459
          from_pos+strlen(FN_PARENTDIR) == pos)
 
460
        to_pos=stpcpy(to_pos,FN_C_PARENT_DIR);  /* Found '../' */
462
461
      else
463
 
      {
464
 
        to_pos= strncpy(to_pos,from_pos,(size_t) (pos-from_pos));
465
 
        to_pos+= strlen(to_pos);
466
 
      }
 
462
        to_pos=stpncpy(to_pos,from_pos,(size_t) (pos-from_pos));
467
463
      from_pos=pos+1;
468
464
    }
469
465
    *(to_pos++)=FN_C_AFTER_DIR;
470
466
  }
471
 
 
472
 
  strcpy(to_pos, from_pos);
473
 
  length= strlen(to);
 
467
  length= (size_t) (stpcpy(to_pos,from_pos)-to);
474
468
  return(length);
475
469
#endif
476
470
} /* system_filename */
484
478
  char buff[FN_REFLEN];
485
479
  if (from == to)
486
480
  {                                             /* Dirname may destroy from */
487
 
    strcpy(buff,from);
 
481
    stpcpy(buff,from);
488
482
    from=buff;
489
483
  }
490
484
  length= dirname_part(to, from, &to_length);   /* Copy dirname & fix chars */
491
 
  (void) strcpy(to + to_length,from+length);
 
485
  (void) stpcpy(to + to_length,from+length);
492
486
  return (to);
493
487
} /* intern_filename */