2 * $Id: mac.c 443 2006-05-30 04:37:13Z darren $
4 * Copyright (c) 2001, Maarten L. Hekkelman
6 * Author: Maarten L. Hekkelman <maarten@hekkelman.com>
7 * http://www.hekkelman.com
9 * This source code is released for free distribution under the terms of the
10 * GNU General Public License. It is provided on an as-is basis and no
11 * responsibility is accepted for its failure to perform as expected.
13 * This module contains support functions for Exuberant Ctags on Macintosh.
22 #include <TextUtils.h>
28 * FUNCTION DEFINITIONS
31 static int get_path(const char* in_unix_path
, unsigned char* out_mac_path
)
33 int l
= strlen(in_unix_path
);
40 const char* s
= in_unix_path
;
41 char *d
= (char*)out_mac_path
+ 1;
50 if (s
[0] == '.' && s
[1] == '.' && s
[2] == '/')
55 else if (s
[0] == '.' && s
[1] == '/')
69 out_mac_path
[0] = (d
- (char*)out_mac_path
) - 1;
75 DIR *opendir(const char *dirname
)
77 DIR* dirp
= (DIR*)calloc(1, sizeof(DIR));
83 CInfoPBRec pb
= { 0 };
85 if (strcmp(dirname
, "."))
88 pb
.hFileInfo
.ioNamePtr
= s
;
91 pb
.hFileInfo
.ioNamePtr
= NULL
;
93 err
= PBGetCatInfoSync(&pb
);
94 if (err
!= noErr
|| (pb
.hFileInfo
.ioFlAttrib
& ioDirMask
) == 0)
101 dirp
->file
.vRefNum
= pb
.hFileInfo
.ioVRefNum
;
102 dirp
->file
.parID
= pb
.hFileInfo
.ioDirID
;
103 dirp
->file
.name
[0] = '\0';
111 struct dirent
*readdir(DIR *dirp
)
115 CInfoPBRec pb
= { 0 };
117 pb
.hFileInfo
.ioVRefNum
= dirp
->file
.vRefNum
;
118 pb
.hFileInfo
.ioDirID
= dirp
->file
.parID
;
119 pb
.hFileInfo
.ioFDirIndex
= dirp
->index
++;
120 pb
.hFileInfo
.ioNamePtr
= dirp
->file
.name
;
122 if (PBGetCatInfoSync(&pb
) != noErr
)
125 memcpy(dirp
->ent
.d_name
, dirp
->file
.name
+ 1, dirp
->file
.name
[0]);
126 dirp
->ent
.d_name
[dirp
->file
.name
[0]] = 0;
132 int closedir(DIR *dirp
)
139 void rewinddir(DIR *dirp
)
145 int mstat(const char* file
, struct stat
* st
)
148 unsigned char path
[256];
151 memset(&pb
, 0, sizeof(CInfoPBRec
));
153 if (strcmp(file
, ".") == 0)
155 memset(st
, 0, sizeof(struct stat
));
156 st
->st_mode
= S_IFDIR
;
161 result
= get_path(file
, path
);
165 pb
.hFileInfo
.ioNamePtr
= path
;
167 if (PBGetCatInfoSync(&pb
) != noErr
)
171 memset(st
, 0, sizeof(struct stat
));
173 if (pb
.hFileInfo
.ioFlAttrib
& ioDirMask
)
174 st
->st_mode
= S_IFDIR
;
176 st
->st_mode
= S_IFREG
;
178 st
->st_ino
= pb
.hFileInfo
.ioFlStBlk
;
179 st
->st_dev
= pb
.hFileInfo
.ioVRefNum
;
181 st
->st_size
= pb
.hFileInfo
.ioFlLgLen
;
182 st
->st_atime
= pb
.hFileInfo
.ioFlMdDat
;
183 st
->st_mtime
= pb
.hFileInfo
.ioFlMdDat
;
184 st
->st_ctime
= pb
.hFileInfo
.ioFlCrDat
;
194 FILE* mfopen(const char* file
, const char* mode
)
196 unsigned char path
[256];
198 if (get_path(file
, path
) == 0)
201 memmove(path
, path
+ 1, l
);
203 return fopen((char*)path
, mode
);
209 char* getcwd(char* out_path
, int out_path_len
)
215 if (out_path
== NULL
)
217 if (out_path_len
< PATH_MAX
)
218 out_path_len
= PATH_MAX
;
219 out_path
= (char*)malloc(out_path_len
);
222 err
= FSMakeFSSpec(0, 0, "\p:", &cwd
);
224 if (cwd
.parID
== fsRtParID
)
227 memcpy(out_path
+ 1, cwd
.name
+ 1, cwd
.name
[0]);
228 out_path
[1 + cwd
.name
[0]] = 0;
232 /* The object isn't a volume */
234 /* Is the object a file or a directory? */
239 s
= t
+ PATH_MAX
- cwd
.name
[0] - 1;
240 memcpy(s
, cwd
.name
+ 1, cwd
.name
[0]);
243 /* Get the ancestor directory names */
244 pb
.dirInfo
.ioNamePtr
= cwd
.name
;
245 pb
.dirInfo
.ioVRefNum
= cwd
.vRefNum
;
246 pb
.dirInfo
.ioDrParID
= cwd
.parID
;
247 do /* loop until we have an error or find the root directory */
249 pb
.dirInfo
.ioFDirIndex
= -1;
250 pb
.dirInfo
.ioDrDirID
= pb
.dirInfo
.ioDrParID
;
251 err
= PBGetCatInfoSync(&pb
);
256 memcpy(s
, cwd
.name
+ 1, cwd
.name
[0]);
259 while (err
== noErr
&& pb
.dirInfo
.ioDrDirID
!= fsRtDirID
&& s
> t
+ 1);
267 strcpy(out_path
, ".");
273 /* vi:set tabstop=4 shiftwidth=4: */