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
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
|
/*
* Macintosh version of UNIX directory access package
* (opendir, readdir, closedir).
* Public domain by Guido van Rossum, CWI, Amsterdam (July 1987).
*/
#include "dirent.h"
#include "macdefs.h"
static DIR opened;
/*
* Open a directory. This means calling PBOpenWD.
* The value returned is always the address of opened, or NULL.
* (I have as yet no use for multiple open directories; this could
* be implemented by allocating memory dynamically.)
*/
DIR *
opendir(path)
char *path;
{
#ifdef TARGET_API_MAC_CARBON
Str255 ppath;
FSSpec fss;
int plen;
OSErr err;
if (opened.nextfile != 0) {
errno = EBUSY;
return NULL; /* A directory is already open. */
}
plen = strlen(path);
c2pstrcpy(ppath, path);
if ( ppath[plen] != ':' )
ppath[++plen] = ':';
ppath[++plen] = 'x';
ppath[0] = plen;
if( (err = FSMakeFSSpec(0, 0, ppath, &fss)) < 0 && err != fnfErr ) {
errno = EIO;
return NULL;
}
opened.dirid = fss.parID;
opened.vrefnum = fss.vRefNum;
opened.nextfile = 1;
return &opened;
#else
union {
WDPBRec d;
VolumeParam v;
} pb;
char ppath[MAXPATH];
short err;
if (opened.nextfile != 0) {
errno = EBUSY;
return NULL; /* A directory is already open. */
}
strncpy(ppath+1, path, ppath[0]= strlen(path));
pb.d.ioNamePtr= (unsigned char *)ppath;
pb.d.ioVRefNum= 0;
pb.d.ioWDProcID= 0;
pb.d.ioWDDirID= 0;
err= PBOpenWD((WDPBPtr)&pb, 0);
if (err != noErr) {
errno = ENOENT;
return NULL;
}
opened.dirid= pb.d.ioVRefNum;
opened.nextfile= 1;
return &opened;
#endif
}
/*
* Close a directory.
*/
void
closedir(dirp)
DIR *dirp;
{
#ifdef TARGET_API_MAC_CARBON
dirp->nextfile = 0;
#else
WDPBRec pb;
pb.ioVRefNum= dirp->dirid;
(void) PBCloseWD(&pb, 0);
dirp->dirid= 0;
dirp->nextfile= 0;
#endif
}
/*
* Read the next directory entry.
*/
struct dirent *
readdir(dp)
DIR *dp;
{
union {
DirInfo d;
FileParam f;
HFileInfo hf;
} pb;
short err;
static struct dirent dir;
dir.d_name[0]= 0;
pb.d.ioNamePtr= (unsigned char *)dir.d_name;
#ifdef TARGET_API_MAC_CARBON
pb.d.ioVRefNum= dp->vrefnum;
pb.d.ioDrDirID= dp->dirid;
#else
pb.d.ioVRefNum= dp->dirid;
pb.d.ioDrDirID= 0;
#endif
pb.d.ioFDirIndex= dp->nextfile++;
err= PBGetCatInfo((CInfoPBPtr)&pb, 0);
if (err != noErr) {
errno = EIO;
return NULL;
}
#ifdef TARGET_API_MAC_CARBON
p2cstrcpy(dir.d_name, (StringPtr)dir.d_name);
#else
(void) p2cstr((unsigned char *)dir.d_name);
#endif
return &dir;
}
|