1 /***********************************************************
2 Copyright 1991-1997 by Stichting Mathematisch Centrum, Amsterdam,
7 Permission to use, copy, modify, and distribute this software and its
8 documentation for any purpose and without fee is hereby granted,
9 provided that the above copyright notice appear in all copies and that
10 both that copyright notice and this permission notice appear in
11 supporting documentation, and that the names of Stichting Mathematisch
12 Centrum or CWI not be used in advertising or publicity pertaining to
13 distribution of the software without specific, written prior permission.
15 STICHTING MATHEMATISCH CENTRUM DISCLAIMS ALL WARRANTIES WITH REGARD TO
16 THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
17 FITNESS, IN NO EVENT SHALL STICHTING MATHEMATISCH CENTRUM BE LIABLE
18 FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
19 WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
20 ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
21 OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
23 ******************************************************************/
25 /* Mac module implementation */
47 /* Remove defines from macstat.h */
56 #include <sys/types.h>
68 /* Optional routines, for some compiler/runtime combinations */
69 #if defined(USE_GUSI) || !defined(__MWERKS__)
72 #if defined(MPW) || defined(USE_GUSI)
87 #define MAXPATHLEN 1024
90 /* Prototypes for Unix simulation on Mac */
94 int chdir
Py_PROTO((const char *path
));
95 int mkdir
Py_PROTO((const char *path
, int mode
));
96 DIR * opendir
Py_PROTO((char *));
97 void closedir
Py_PROTO((DIR *));
98 struct dirent
* readdir
Py_PROTO((DIR *));
99 int rmdir
Py_PROTO((const char *path
));
100 int sync
Py_PROTO((void));
102 #if defined(THINK_C) || defined(__SC__)
103 int unlink
Py_PROTO((char *));
105 int unlink
Py_PROTO((const char *));
108 #endif /* USE_GUSI */
110 char *getwd
Py_PROTO((char *));
111 char *getbootvol
Py_PROTO((void));
114 static PyObject
*MacError
; /* Exception mac.error */
116 /* Set a MAC-specific error from errno, and return NULL */
121 return PyErr_SetFromErrno(MacError
);
124 /* MAC generic methods */
129 int (*func
) Py_FPROTO((const char *));
133 if (!PyArg_Parse(args
, "s", &path1
))
135 Py_BEGIN_ALLOW_THREADS
136 res
= (*func
)(path1
);
147 int (*func
) Py_FPROTO((const char *, const char *));
151 if (!PyArg_Parse(args
, "(ss)", &path1
, &path2
))
153 Py_BEGIN_ALLOW_THREADS
154 res
= (*func
)(path1
, path2
);
163 mac_strint(args
, func
)
165 int (*func
) Py_FPROTO((const char *, int));
170 if (!PyArg_Parse(args
, "(si)", &path
, &i
))
172 Py_BEGIN_ALLOW_THREADS
173 res
= (*func
)(path
, i
);
182 mac_chdir(self
, args
)
189 /* Change MacOS's idea of wd too */
190 rv
= mac_1str(args
, chdir
);
194 return mac_1str(args
, chdir
);
200 mac_close(self
, args
)
205 if (!PyArg_Parse(args
, "i", &fd
))
207 Py_BEGIN_ALLOW_THREADS
211 /* GUSI gives surious errors here? */
227 if (!PyArg_Parse(args
, "i", &fd
))
229 Py_BEGIN_ALLOW_THREADS
234 return PyInt_FromLong((long)fd
);
241 mac_fdopen(self
, args
)
245 extern int fclose
Py_PROTO((FILE *));
249 if (!PyArg_Parse(args
, "(is)", &fd
, &mode
))
251 Py_BEGIN_ALLOW_THREADS
252 fp
= fdopen(fd
, mode
);
256 return PyFile_FromFile(fp
, "(fdopen)", mode
, fclose
);
261 mac_getbootvol(self
, args
)
266 if (!PyArg_NoArgs(args
))
268 Py_BEGIN_ALLOW_THREADS
273 return PyString_FromString(res
);
277 mac_getcwd(self
, args
)
281 char path
[MAXPATHLEN
];
283 if (!PyArg_NoArgs(args
))
285 Py_BEGIN_ALLOW_THREADS
287 res
= getcwd(path
, sizeof path
);
293 PyErr_SetString(MacError
, path
);
296 return PyString_FromString(res
);
300 mac_listdir(self
, args
)
308 if (!PyArg_Parse(args
, "s", &name
))
310 Py_BEGIN_ALLOW_THREADS
311 if ((dirp
= opendir(name
)) == NULL
) {
315 if ((d
= PyList_New(0)) == NULL
) {
320 while ((ep
= readdir(dirp
)) != NULL
) {
321 v
= PyString_FromString(ep
->d_name
);
327 if (PyList_Append(d
, v
) != 0) {
342 mac_lseek(self
, args
)
350 if (!PyArg_Parse(args
, "(iii)", &fd
, &where
, &how
))
352 Py_BEGIN_ALLOW_THREADS
353 res
= lseek(fd
, (long)where
, how
);
357 return PyInt_FromLong(res
);
361 mac_mkdir(self
, args
)
367 int mode
= 0777; /* Unused */
368 if (!PyArg_ParseTuple(args
, "s|i", &path
, &mode
))
370 Py_BEGIN_ALLOW_THREADS
374 res
= mkdir(path
, mode
);
391 if (!PyArg_Parse(args
, "(si)", &path
, &mode
))
393 Py_BEGIN_ALLOW_THREADS
394 fd
= open(path
, mode
);
398 return PyInt_FromLong((long)fd
);
408 if (!PyArg_Parse(args
, "(ii)", &fd
, &size
))
410 buffer
= PyString_FromStringAndSize((char *)NULL
, size
);
413 Py_BEGIN_ALLOW_THREADS
414 size
= read(fd
, PyString_AsString(buffer
), size
);
420 _PyString_Resize(&buffer
, size
);
425 mac_rename(self
, args
)
429 return mac_2str(args
, rename
);
433 mac_rmdir(self
, args
)
437 return mac_1str(args
, rmdir
);
448 if (!PyArg_Parse(args
, "s", &path
))
450 Py_BEGIN_ALLOW_THREADS
451 res
= stat(path
, &st
);
455 return Py_BuildValue("(lllllllddd)",
465 (double)st
.st_ctime
);
470 mac_fstat(self
, args
)
477 if (!PyArg_Parse(args
, "l", &fd
))
479 Py_BEGIN_ALLOW_THREADS
480 res
= fstat((int)fd
, &st
);
484 return Py_BuildValue("(lllllllddd)",
494 (double)st
.st_ctime
);
496 #endif /* WEHAVE_FSTAT */
499 mac_xstat(self
, args
)
507 if (!PyArg_Parse(args
, "s", &path
))
510 ** Convoluted: we want stat() and xstat() to agree, so we call both
511 ** stat and macstat, and use the latter only for values not provided by
514 Py_BEGIN_ALLOW_THREADS
515 res
= macstat(path
, &mst
);
519 Py_BEGIN_ALLOW_THREADS
520 res
= stat(path
, &st
);
524 return Py_BuildValue("(llllllldddls#s#)",
546 if (!PyArg_NoArgs(args
))
548 Py_BEGIN_ALLOW_THREADS
558 mac_unlink(self
, args
)
562 return mac_1str(args
, (int (*)(const char *))unlink
);
566 mac_write(self
, args
)
572 if (!PyArg_Parse(args
, "(is#)", &fd
, &buffer
, &size
))
574 Py_BEGIN_ALLOW_THREADS
575 size
= write(fd
, buffer
, size
);
579 return PyInt_FromLong((long)size
);
582 #ifdef USE_MALLOC_DEBUG
584 mac_mstats(self
, args
)
592 #endif /* USE_MALLOC_DEBUG */
594 static struct PyMethodDef mac_methods
[] = {
595 {"chdir", mac_chdir
},
596 {"close", mac_close
},
601 {"fdopen", mac_fdopen
},
604 {"fstat", mac_fstat
},
606 {"getbootvol", mac_getbootvol
}, /* non-standard */
607 {"getcwd", mac_getcwd
},
608 {"listdir", mac_listdir
, 0},
609 {"lseek", mac_lseek
},
610 {"mkdir", mac_mkdir
, 1},
613 {"rename", mac_rename
},
614 {"rmdir", mac_rmdir
},
616 {"xstat", mac_xstat
},
618 {"remove", mac_unlink
},
619 {"unlink", mac_unlink
},
620 {"write", mac_write
},
621 #ifdef USE_MALLOC_DEBUG
622 {"mstats", mac_mstats
},
625 {NULL
, NULL
} /* Sentinel */
634 m
= Py_InitModule("mac", mac_methods
);
635 d
= PyModule_GetDict(m
);
637 /* Initialize mac.error exception */
638 MacError
= PyErr_NewException("mac.error", NULL
, NULL
);
639 PyDict_SetItemString(d
, "error", MacError
);