move sections
[python/dscho.git] / Mac / Modules / file / filesupport.py
blob88f88cd9dc359777de0167211340bb1a2b4d826c
1 # This script generates a Python interface for an Apple Macintosh Manager.
2 # It uses the "bgen" package to generate C code.
3 # The function specifications are generated by scanning the mamager's header file,
4 # using the "scantools" package (customized for this particular manager).
6 # XXXX TO DO:
7 # - Implement correct missing FSSpec handling for Alias methods
8 # - Implement FInfo
10 # WARNING WARNING WARNING
11 # The file _Filemodule.c was modified manually, don't run this script
12 # unless you really know what you're doing.
14 import sys
15 sys.exit(42)
17 import string
19 # Declarations that change for each manager
20 #MACHEADERFILE = 'Files.h' # The Apple header file
21 MODNAME = '_File' # The name of the module
22 LONGMODNAME = 'Carbon.File' # The "normal" external name of the module
24 # The following is *usually* unchanged but may still require tuning
25 MODPREFIX = 'File' # The prefix for module-wide routines
26 INPUTFILE = string.lower(MODPREFIX) + 'gen.py' # The file generated by the scanner
27 OUTPUTFILE = MODNAME + "module.c" # The file generated by this program
29 from macsupport import *
31 # Various integers:
32 SInt64 = Type("SInt64", "L")
33 UInt64 = Type("UInt64", "L")
34 FNMessage = Type("FNMessage", "l")
35 FSAllocationFlags = Type("FSAllocationFlags", "H")
36 FSCatalogInfoBitmap = Type("FSCatalogInfoBitmap", "l")
37 FSIteratorFlags = Type("FSIteratorFlags", "l")
38 FSVolumeRefNum = Type("FSVolumeRefNum", "h")
39 AliasInfoType = Type("AliasInfoType", "h")
41 # Various types of strings:
42 #class UniCharCountBuffer(InputOnlyType):
43 # pass
44 class VarReverseInputBufferType(ReverseInputBufferMixin, VarInputBufferType):
45 pass
46 FullPathName = VarReverseInputBufferType()
47 ConstStr31Param = OpaqueArrayType("Str31", "PyMac_BuildStr255", "PyMac_GetStr255")
48 ConstStr32Param = OpaqueArrayType("Str32", "PyMac_BuildStr255", "PyMac_GetStr255")
49 ConstStr63Param = OpaqueArrayType("Str63", "PyMac_BuildStr255", "PyMac_GetStr255")
50 Str63 = OpaqueArrayType("Str63", "PyMac_BuildStr255", "PyMac_GetStr255")
52 HFSUniStr255 = OpaqueType("HFSUniStr255", "PyMac_BuildHFSUniStr255", "PyMac_GetHFSUniStr255")
53 UInt8_ptr = InputOnlyType("UInt8 *", "s")
55 # Other types:
56 class OptionalFSxxxType(OpaqueByValueType):
57 def declare(self, name):
58 Output("%s %s__buf__;", self.typeName, name)
59 Output("%s *%s = &%s__buf__;", self.typeName, name, name)
61 class FSCatalogInfoAndBitmapType(InputOnlyType):
63 def __init__(self):
64 InputOnlyType.__init__(self, "BUG", "BUG")
66 def declare(self, name):
67 Output("PyObject *%s__object = NULL;", name)
68 Output("FSCatalogInfoBitmap %s__bitmap = 0;", name)
69 Output("FSCatalogInfo %s;", name)
71 def getargsFormat(self):
72 return "lO"
74 def getargsArgs(self, name):
75 return "%s__bitmap, %s__object"%(name, name)
77 def getargsCheck(self, name):
78 Output("if (!convert_FSCatalogInfo(%s__object, %s__bitmap, &%s)) return NULL;", name, name, name)
80 def passInput(self, name):
81 return "%s__bitmap, &%s"% (name, name)
83 def passOutput(self, name):
84 return "%s__bitmap, &%s"% (name, name)
86 def mkvalueFormat(self):
87 return "O"
89 def mkvalueArgs(self, name):
90 return "%s__object" % (name)
92 def xxxxmkvalueCheck(self, name):
93 Output("if ((%s__object = new_FSCatalogInfo(%s__bitmap, &%s)) == NULL) return NULL;", name, name)
95 class FSCatalogInfoAndBitmap_inType(FSCatalogInfoAndBitmapType, InputOnlyMixIn):
97 def xxxxmkvalueCheck(self, name):
98 pass
100 class FSCatalogInfoAndBitmap_outType(FSCatalogInfoAndBitmapType):
102 def getargsFormat(self):
103 return "l"
105 def getargsArgs(self, name):
106 return "%s__bitmap" % name
108 def getargsCheck(self, name):
109 pass
111 FInfo = OpaqueType("FInfo", "FInfo")
112 FInfo_ptr = OpaqueType("FInfo", "FInfo")
113 AliasHandle = OpaqueByValueType("AliasHandle", "Alias")
114 FSSpec = OpaqueType("FSSpec", "FSSpec")
115 FSSpec_ptr = OpaqueType("FSSpec", "FSSpec")
116 OptFSSpecPtr = OptionalFSxxxType("FSSpec", "BUG", "myPyMac_GetOptFSSpecPtr")
117 FSRef = OpaqueType("FSRef", "FSRef")
118 FSRef_ptr = OpaqueType("FSRef", "FSRef")
119 OptFSRefPtr = OptionalFSxxxType("FSRef", "BUG", "myPyMac_GetOptFSRefPtr")
120 FSCatalogInfo = OpaqueType("FSCatalogInfo", "FSCatalogInfo")
121 FSCatalogInfo_ptr = OpaqueType("FSCatalogInfo", "FSCatalogInfo")
123 # To be done:
124 #CatPositionRec
125 #FSCatalogInfo
126 #FSForkInfo
127 #FSIterator
128 #FSVolumeInfo
129 #FSSpecArrayPtr
131 includestuff = includestuff + """
132 #include <Carbon/Carbon.h>
134 #ifdef USE_TOOLBOX_OBJECT_GLUE
135 extern int _PyMac_GetFSSpec(PyObject *v, FSSpec *spec);
136 extern int _PyMac_GetFSRef(PyObject *v, FSRef *fsr);
137 extern PyObject *_PyMac_BuildFSSpec(FSSpec *spec);
138 extern PyObject *_PyMac_BuildFSRef(FSRef *spec);
140 #define PyMac_GetFSSpec _PyMac_GetFSSpec
141 #define PyMac_GetFSRef _PyMac_GetFSRef
142 #define PyMac_BuildFSSpec _PyMac_BuildFSSpec
143 #define PyMac_BuildFSRef _PyMac_BuildFSRef
144 #else
145 extern int PyMac_GetFSSpec(PyObject *v, FSSpec *spec);
146 extern int PyMac_GetFSRef(PyObject *v, FSRef *fsr);
147 extern PyObject *PyMac_BuildFSSpec(FSSpec *spec);
148 extern PyObject *PyMac_BuildFSRef(FSRef *spec);
149 #endif
151 /* Forward declarations */
152 static PyObject *FInfo_New(FInfo *itself);
153 static PyObject *FSRef_New(FSRef *itself);
154 static PyObject *FSSpec_New(FSSpec *itself);
155 static PyObject *Alias_New(AliasHandle itself);
156 static int FInfo_Convert(PyObject *v, FInfo *p_itself);
157 #define FSRef_Convert PyMac_GetFSRef
158 #define FSSpec_Convert PyMac_GetFSSpec
159 static int Alias_Convert(PyObject *v, AliasHandle *p_itself);
162 ** UTCDateTime records
164 static int
165 UTCDateTime_Convert(PyObject *v, UTCDateTime *ptr)
167 return PyArg_Parse(v, "(HlH)", &ptr->highSeconds, &ptr->lowSeconds, &ptr->fraction);
170 static PyObject *
171 UTCDateTime_New(UTCDateTime *ptr)
173 return Py_BuildValue("(HlH)", ptr->highSeconds, ptr->lowSeconds, ptr->fraction);
177 ** Optional fsspec and fsref pointers. None will pass NULL
179 static int
180 myPyMac_GetOptFSSpecPtr(PyObject *v, FSSpec **spec)
182 if (v == Py_None) {
183 *spec = NULL;
184 return 1;
186 return PyMac_GetFSSpec(v, *spec);
189 static int
190 myPyMac_GetOptFSRefPtr(PyObject *v, FSRef **ref)
192 if (v == Py_None) {
193 *ref = NULL;
194 return 1;
196 return PyMac_GetFSRef(v, *ref);
200 ** Parse/generate objsect
202 static PyObject *
203 PyMac_BuildHFSUniStr255(HFSUniStr255 *itself)
206 return Py_BuildValue("u#", itself->unicode, itself->length);
209 #ifndef __LP64__
211 ** Get pathname for a given FSSpec
213 static OSErr
214 _PyMac_GetFullPathname(FSSpec *fss, char *path, int len)
216 FSRef fsr;
217 OSErr err;
219 *path = '\0';
220 err = FSpMakeFSRef(fss, &fsr);
221 if (err == fnfErr) {
222 /* FSSpecs can point to non-existing files, fsrefs can't. */
223 FSSpec fss2;
224 int tocopy;
226 err = FSMakeFSSpec(fss->vRefNum, fss->parID, "", &fss2);
227 if (err)
228 return err;
229 err = FSpMakeFSRef(&fss2, &fsr);
230 if (err)
231 return err;
232 err = (OSErr)FSRefMakePath(&fsr, path, len-1);
233 if (err)
234 return err;
235 /* This part is not 100% safe: we append the filename part, but
236 ** I'm not sure that we don't run afoul of the various 8bit
237 ** encodings here. Will have to look this up at some point...
239 strcat(path, "/");
240 tocopy = fss->name[0];
241 if ((strlen(path) + tocopy) >= len)
242 tocopy = len - strlen(path) - 1;
243 if (tocopy > 0)
244 strncat(path, fss->name+1, tocopy);
246 else {
247 if (err)
248 return err;
249 err = (OSErr)FSRefMakePath(&fsr, path, len);
250 if (err)
251 return err;
253 return 0;
255 #endif /* !__LP64__ */
259 finalstuff = finalstuff + """
261 #ifndef __LP64__
263 PyMac_GetFSSpec(PyObject *v, FSSpec *spec)
265 Str255 path;
266 short refnum;
267 long parid;
268 OSErr err;
269 FSRef fsr;
271 if (FSSpec_Check(v)) {
272 *spec = ((FSSpecObject *)v)->ob_itself;
273 return 1;
276 if (PyArg_Parse(v, "(hlO&)",
277 &refnum, &parid, PyMac_GetStr255, &path)) {
278 err = FSMakeFSSpec(refnum, parid, path, spec);
279 if ( err && err != fnfErr ) {
280 PyMac_Error(err);
281 return 0;
283 return 1;
285 PyErr_Clear();
286 /* Otherwise we try to go via an FSRef. On OSX we go all the way,
287 ** on OS9 we accept only a real FSRef object
289 if ( PyMac_GetFSRef(v, &fsr) ) {
290 err = FSGetCatalogInfo(&fsr, kFSCatInfoNone, NULL, NULL, spec, NULL);
291 if (err != noErr) {
292 PyMac_Error(err);
293 return 0;
295 return 1;
297 return 0;
300 #endif /* !__LP64__ */
303 PyMac_GetFSRef(PyObject *v, FSRef *fsr)
305 OSStatus err;
306 FSSpec fss;
308 if (FSRef_Check(v)) {
309 *fsr = ((FSRefObject *)v)->ob_itself;
310 return 1;
313 /* On OSX we now try a pathname */
314 if ( PyString_Check(v) || PyUnicode_Check(v)) {
315 char *path = NULL;
316 if (!PyArg_Parse(v, "et", Py_FileSystemDefaultEncoding, &path))
317 return 0;
318 if ( (err=FSPathMakeRef(path, fsr, NULL)) )
319 PyMac_Error(err);
320 PyMem_Free(path);
321 return !err;
323 /* XXXX Should try unicode here too */
324 /* Otherwise we try to go via an FSSpec */
325 #ifndef __LP64__
326 if (FSSpec_Check(v)) {
327 fss = ((FSSpecObject *)v)->ob_itself;
328 if ((err=FSpMakeFSRef(&fss, fsr)) == 0)
329 return 1;
330 PyMac_Error(err);
331 return 0;
333 PyErr_SetString(PyExc_TypeError, "FSRef, FSSpec or pathname required");
334 #else /* __LP64__ */
335 PyErr_SetString(PyExc_TypeError, "FSRef or pathname required");
336 #endif /* __LP64__ */
337 return 0;
340 #ifndef __LP64__
341 extern PyObject *
342 PyMac_BuildFSSpec(FSSpec *spec)
344 return FSSpec_New(spec);
346 #endif /* __LP64__ */
348 extern PyObject *
349 PyMac_BuildFSRef(FSRef *spec)
351 return FSRef_New(spec);
355 initstuff = initstuff + """
356 #ifndef __LP64__
357 PyMac_INIT_TOOLBOX_OBJECT_NEW(FSSpec *, PyMac_BuildFSSpec);
358 PyMac_INIT_TOOLBOX_OBJECT_CONVERT(FSSpec, PyMac_GetFSSpec);
359 #endif /* !__LP64__*/
360 PyMac_INIT_TOOLBOX_OBJECT_NEW(FSRef *, PyMac_BuildFSRef);
361 PyMac_INIT_TOOLBOX_OBJECT_CONVERT(FSRef, PyMac_GetFSRef);
364 execfile(string.lower(MODPREFIX) + 'typetest.py')
366 # Our object types:
367 class FSCatalogInfoDefinition(PEP253Mixin, ObjectDefinition):
368 getsetlist = [
369 ("nodeFlags",
370 "return Py_BuildValue(\"H\", self->ob_itself.nodeFlags);",
371 "return PyArg_Parse(v, \"H\", &self->ob_itself.nodeFlags)-1;",
372 None
374 ("volume",
375 "return Py_BuildValue(\"h\", self->ob_itself.volume);",
376 "return PyArg_Parse(v, \"h\", &self->ob_itself.volume)-1;",
377 None
379 ("parentDirID",
380 "return Py_BuildValue(\"l\", self->ob_itself.parentDirID);",
381 "return PyArg_Parse(v, \"l\", &self->ob_itself.parentDirID)-1;",
382 None
384 ("nodeID",
385 "return Py_BuildValue(\"l\", self->ob_itself.nodeID);",
386 "return PyArg_Parse(v, \"l\", &self->ob_itself.nodeID)-1;",
387 None
389 ("createDate",
390 "return Py_BuildValue(\"O&\", UTCDateTime_New, &self->ob_itself.createDate);",
391 "return PyArg_Parse(v, \"O&\", UTCDateTime_Convert, &self->ob_itself.createDate)-1;",
392 None
394 ("contentModDate",
395 "return Py_BuildValue(\"O&\", UTCDateTime_New, &self->ob_itself.contentModDate);",
396 "return PyArg_Parse(v, \"O&\", UTCDateTime_Convert, &self->ob_itself.contentModDate)-1;",
397 None
399 ("attributeModDate",
400 "return Py_BuildValue(\"O&\", UTCDateTime_New, &self->ob_itself.attributeModDate);",
401 "return PyArg_Parse(v, \"O&\", UTCDateTime_Convert, &self->ob_itself.attributeModDate)-1;",
402 None
404 ("accessDate",
405 "return Py_BuildValue(\"O&\", UTCDateTime_New, &self->ob_itself.accessDate);",
406 "return PyArg_Parse(v, \"O&\", UTCDateTime_Convert, &self->ob_itself.accessDate)-1;",
407 None
409 ("backupDate",
410 "return Py_BuildValue(\"O&\", UTCDateTime_New, &self->ob_itself.backupDate);",
411 "return PyArg_Parse(v, \"O&\", UTCDateTime_Convert, &self->ob_itself.backupDate)-1;",
412 None
414 ("permissions",
415 "return Py_BuildValue(\"(llll)\", self->ob_itself.permissions[0], self->ob_itself.permissions[1], self->ob_itself.permissions[2], self->ob_itself.permissions[3]);",
416 "return PyArg_Parse(v, \"(llll)\", &self->ob_itself.permissions[0], &self->ob_itself.permissions[1], &self->ob_itself.permissions[2], &self->ob_itself.permissions[3])-1;",
417 None
419 # XXXX FinderInfo TBD
420 # XXXX FinderXInfo TBD
421 ("valence",
422 "return Py_BuildValue(\"l\", self->ob_itself.valence);",
423 "return PyArg_Parse(v, \"l\", &self->ob_itself.valence)-1;",
424 None
426 ("dataLogicalSize",
427 "return Py_BuildValue(\"l\", self->ob_itself.dataLogicalSize);",
428 "return PyArg_Parse(v, \"l\", &self->ob_itself.dataLogicalSize)-1;",
429 None
431 ("dataPhysicalSize",
432 "return Py_BuildValue(\"l\", self->ob_itself.dataPhysicalSize);",
433 "return PyArg_Parse(v, \"l\", &self->ob_itself.dataPhysicalSize)-1;",
434 None
436 ("rsrcLogicalSize",
437 "return Py_BuildValue(\"l\", self->ob_itself.rsrcLogicalSize);",
438 "return PyArg_Parse(v, \"l\", &self->ob_itself.rsrcLogicalSize)-1;",
439 None
441 ("rsrcPhysicalSize",
442 "return Py_BuildValue(\"l\", self->ob_itself.rsrcPhysicalSize);",
443 "return PyArg_Parse(v, \"l\", &self->ob_itself.rsrcPhysicalSize)-1;",
444 None
446 ("sharingFlags",
447 "return Py_BuildValue(\"l\", self->ob_itself.sharingFlags);",
448 "return PyArg_Parse(v, \"l\", &self->ob_itself.sharingFlags)-1;",
449 None
451 ("userPrivileges",
452 "return Py_BuildValue(\"b\", self->ob_itself.userPrivileges);",
453 "return PyArg_Parse(v, \"b\", &self->ob_itself.userPrivileges)-1;",
454 None
457 # The same info, but in a different form
458 INITFORMAT = "HhllO&O&O&O&O&llllllb"
459 INITARGS = """&((FSCatalogInfoObject *)_self)->ob_itself.nodeFlags,
460 &((FSCatalogInfoObject *)_self)->ob_itself.volume,
461 &((FSCatalogInfoObject *)_self)->ob_itself.parentDirID,
462 &((FSCatalogInfoObject *)_self)->ob_itself.nodeID,
463 UTCDateTime_Convert, &((FSCatalogInfoObject *)_self)->ob_itself.createDate,
464 UTCDateTime_Convert, &((FSCatalogInfoObject *)_self)->ob_itself.contentModDate,
465 UTCDateTime_Convert, &((FSCatalogInfoObject *)_self)->ob_itself.attributeModDate,
466 UTCDateTime_Convert, &((FSCatalogInfoObject *)_self)->ob_itself.accessDate,
467 UTCDateTime_Convert, &((FSCatalogInfoObject *)_self)->ob_itself.backupDate,
468 &((FSCatalogInfoObject *)_self)->ob_itself.valence,
469 &((FSCatalogInfoObject *)_self)->ob_itself.dataLogicalSize,
470 &((FSCatalogInfoObject *)_self)->ob_itself.dataPhysicalSize,
471 &((FSCatalogInfoObject *)_self)->ob_itself.rsrcLogicalSize,
472 &((FSCatalogInfoObject *)_self)->ob_itself.rsrcPhysicalSize,
473 &((FSCatalogInfoObject *)_self)->ob_itself.sharingFlags,
474 &((FSCatalogInfoObject *)_self)->ob_itself.userPrivileges"""
475 INITNAMES = """
476 "nodeFlags",
477 "volume",
478 "parentDirID",
479 "nodeID",
480 "createDate",
481 "contentModDate",
482 "atributeModDate",
483 "accessDate",
484 "backupDate",
485 "valence",
486 "dataLogicalSize",
487 "dataPhysicalSize",
488 "rsrcLogicalSize",
489 "rsrcPhysicalSize",
490 "sharingFlags",
491 "userPrivileges"
494 def __init__(self, name, prefix, itselftype):
495 ObjectDefinition.__init__(self, name, prefix, itselftype)
496 self.argref = "*" # Store FSSpecs, but pass them by address
498 def outputCheckNewArg(self):
499 Output("if (itself == NULL) { Py_INCREF(Py_None); return Py_None; }")
501 def output_tp_newBody(self):
502 Output("PyObject *self;");
503 Output()
504 Output("if ((self = type->tp_alloc(type, 0)) == NULL) return NULL;")
505 Output("memset(&((%s *)self)->ob_itself, 0, sizeof(%s));",
506 self.objecttype, self.itselftype)
507 Output("return self;")
509 def output_tp_initBody(self):
510 Output("static char *kw[] = {%s, 0};", self.INITNAMES)
511 Output()
512 Output("if (!PyArg_ParseTupleAndKeywords(_args, _kwds, \"|%s\", kw, %s))",
513 self.INITFORMAT, self.INITARGS)
514 OutLbrace()
515 Output("return -1;")
516 OutRbrace()
517 Output("return 0;")
519 class FInfoDefinition(PEP253Mixin, ObjectDefinition):
520 getsetlist = [
521 ("Type",
522 "return Py_BuildValue(\"O&\", PyMac_BuildOSType, self->ob_itself.fdType);",
523 "return PyArg_Parse(v, \"O&\", PyMac_GetOSType, &self->ob_itself.fdType)-1;",
524 "4-char file type"
526 ("Creator",
527 "return Py_BuildValue(\"O&\", PyMac_BuildOSType, self->ob_itself.fdCreator);",
528 "return PyArg_Parse(v, \"O&\", PyMac_GetOSType, &self->ob_itself.fdCreator)-1;",
529 "4-char file creator"
531 ("Flags",
532 "return Py_BuildValue(\"H\", self->ob_itself.fdFlags);",
533 "return PyArg_Parse(v, \"H\", &self->ob_itself.fdFlags)-1;",
534 "Finder flag bits"
536 ("Location",
537 "return Py_BuildValue(\"O&\", PyMac_BuildPoint, self->ob_itself.fdLocation);",
538 "return PyArg_Parse(v, \"O&\", PyMac_GetPoint, &self->ob_itself.fdLocation)-1;",
539 "(x, y) location of the file's icon in its parent finder window"
541 ("Fldr",
542 "return Py_BuildValue(\"h\", self->ob_itself.fdFldr);",
543 "return PyArg_Parse(v, \"h\", &self->ob_itself.fdFldr)-1;",
544 "Original folder, for 'put away'"
549 def __init__(self, name, prefix, itselftype):
550 ObjectDefinition.__init__(self, name, prefix, itselftype)
551 self.argref = "*" # Store FSSpecs, but pass them by address
553 def outputCheckNewArg(self):
554 Output("if (itself == NULL) return PyMac_Error(resNotFound);")
556 def output_tp_newBody(self):
557 Output("PyObject *self;");
558 Output()
559 Output("if ((self = type->tp_alloc(type, 0)) == NULL) return NULL;")
560 Output("memset(&((%s *)self)->ob_itself, 0, sizeof(%s));",
561 self.objecttype, self.itselftype)
562 Output("return self;")
564 def output_tp_initBody(self):
565 Output("%s *itself = NULL;", self.itselftype)
566 Output("static char *kw[] = {\"itself\", 0};")
567 Output()
568 Output("if (PyArg_ParseTupleAndKeywords(_args, _kwds, \"|O&\", kw, FInfo_Convert, &itself))")
569 OutLbrace()
570 Output("if (itself) memcpy(&((%s *)_self)->ob_itself, itself, sizeof(%s));",
571 self.objecttype, self.itselftype)
572 Output("return 0;")
573 OutRbrace()
574 Output("return -1;")
576 class FSSpecDefinition(PEP253Mixin, ObjectDefinition):
577 getsetlist = [
578 ("data",
579 "return PyString_FromStringAndSize((char *)&self->ob_itself, sizeof(self->ob_itself));",
580 None,
581 "Raw data of the FSSpec object"
585 def __init__(self, name, prefix, itselftype):
586 ObjectDefinition.__init__(self, name, prefix, itselftype)
587 self.argref = "*" # Store FSSpecs, but pass them by address
589 def outputCheckNewArg(self):
590 Output("if (itself == NULL) return PyMac_Error(resNotFound);")
592 # We do Convert ourselves (with PyMac_GetFSxxx)
593 def outputConvert(self):
594 pass
596 def output_tp_newBody(self):
597 Output("PyObject *self;");
598 Output()
599 Output("if ((self = type->tp_alloc(type, 0)) == NULL) return NULL;")
600 Output("memset(&((%s *)self)->ob_itself, 0, sizeof(%s));",
601 self.objecttype, self.itselftype)
602 Output("return self;")
604 def output_tp_initBody(self):
605 Output("PyObject *v = NULL;")
606 Output("char *rawdata = NULL;")
607 Output("int rawdatalen = 0;")
608 Output("static char *kw[] = {\"itself\", \"rawdata\", 0};")
609 Output()
610 Output("if (!PyArg_ParseTupleAndKeywords(_args, _kwds, \"|Os#\", kw, &v, &rawdata, &rawdatalen))")
611 Output("return -1;")
612 Output("if (v && rawdata)")
613 OutLbrace()
614 Output("PyErr_SetString(PyExc_TypeError, \"Only one of itself or rawdata may be specified\");")
615 Output("return -1;")
616 OutRbrace()
617 Output("if (!v && !rawdata)")
618 OutLbrace()
619 Output("PyErr_SetString(PyExc_TypeError, \"One of itself or rawdata must be specified\");")
620 Output("return -1;")
621 OutRbrace()
622 Output("if (rawdata)")
623 OutLbrace()
624 Output("if (rawdatalen != sizeof(%s))", self.itselftype)
625 OutLbrace()
626 Output("PyErr_SetString(PyExc_TypeError, \"%s rawdata incorrect size\");",
627 self.itselftype)
628 Output("return -1;")
629 OutRbrace()
630 Output("memcpy(&((%s *)_self)->ob_itself, rawdata, rawdatalen);", self.objecttype)
631 Output("return 0;")
632 OutRbrace()
633 Output("if (PyMac_GetFSSpec(v, &((%s *)_self)->ob_itself)) return 0;", self.objecttype)
634 Output("return -1;")
636 def outputRepr(self):
637 Output()
638 Output("static PyObject * %s_repr(%s *self)", self.prefix, self.objecttype)
639 OutLbrace()
640 Output("char buf[512];")
641 Output("""PyOS_snprintf(buf, sizeof(buf), \"%%s((%%d, %%ld, '%%.*s'))\",
642 self->ob_type->tp_name,
643 self->ob_itself.vRefNum,
644 self->ob_itself.parID,
645 self->ob_itself.name[0], self->ob_itself.name+1);""")
646 Output("return PyString_FromString(buf);")
647 OutRbrace()
649 class FSRefDefinition(PEP253Mixin, ObjectDefinition):
650 getsetlist = [
651 ("data",
652 "return PyString_FromStringAndSize((char *)&self->ob_itself, sizeof(self->ob_itself));",
653 None,
654 "Raw data of the FSRef object"
658 def __init__(self, name, prefix, itselftype):
659 ObjectDefinition.__init__(self, name, prefix, itselftype)
660 self.argref = "*" # Store FSRefs, but pass them by address
662 def outputCheckNewArg(self):
663 Output("if (itself == NULL) return PyMac_Error(resNotFound);")
665 # We do Convert ourselves (with PyMac_GetFSxxx)
666 def outputConvert(self):
667 pass
669 def output_tp_newBody(self):
670 Output("PyObject *self;");
671 Output()
672 Output("if ((self = type->tp_alloc(type, 0)) == NULL) return NULL;")
673 Output("memset(&((%s *)self)->ob_itself, 0, sizeof(%s));",
674 self.objecttype, self.itselftype)
675 Output("return self;")
677 def output_tp_initBody(self):
678 Output("PyObject *v = NULL;")
679 Output("char *rawdata = NULL;")
680 Output("int rawdatalen = 0;")
681 Output("static char *kw[] = {\"itself\", \"rawdata\", 0};")
682 Output()
683 Output("if (!PyArg_ParseTupleAndKeywords(_args, _kwds, \"|Os#\", kw, &v, &rawdata, &rawdatalen))")
684 Output("return -1;")
685 Output("if (v && rawdata)")
686 OutLbrace()
687 Output("PyErr_SetString(PyExc_TypeError, \"Only one of itself or rawdata may be specified\");")
688 Output("return -1;")
689 OutRbrace()
690 Output("if (!v && !rawdata)")
691 OutLbrace()
692 Output("PyErr_SetString(PyExc_TypeError, \"One of itself or rawdata must be specified\");")
693 Output("return -1;")
694 OutRbrace()
695 Output("if (rawdata)")
696 OutLbrace()
697 Output("if (rawdatalen != sizeof(%s))", self.itselftype)
698 OutLbrace()
699 Output("PyErr_SetString(PyExc_TypeError, \"%s rawdata incorrect size\");",
700 self.itselftype)
701 Output("return -1;")
702 OutRbrace()
703 Output("memcpy(&((%s *)_self)->ob_itself, rawdata, rawdatalen);", self.objecttype)
704 Output("return 0;")
705 OutRbrace()
706 Output("if (PyMac_GetFSRef(v, &((%s *)_self)->ob_itself)) return 0;", self.objecttype)
707 Output("return -1;")
709 class AliasDefinition(PEP253Mixin, ObjectDefinition):
710 # XXXX Should inherit from resource?
711 getsetlist = [
712 ("data",
713 """int size;
714 PyObject *rv;
716 size = GetHandleSize((Handle)self->ob_itself);
717 HLock((Handle)self->ob_itself);
718 rv = PyString_FromStringAndSize(*(Handle)self->ob_itself, size);
719 HUnlock((Handle)self->ob_itself);
720 return rv;
721 """,
722 None,
723 "Raw data of the alias object"
727 def outputCheckNewArg(self):
728 Output("if (itself == NULL) return PyMac_Error(resNotFound);")
730 def outputStructMembers(self):
731 ObjectDefinition.outputStructMembers(self)
732 Output("void (*ob_freeit)(%s ptr);", self.itselftype)
734 def outputInitStructMembers(self):
735 ObjectDefinition.outputInitStructMembers(self)
736 Output("it->ob_freeit = NULL;")
738 def outputCleanupStructMembers(self):
739 Output("if (self->ob_freeit && self->ob_itself)")
740 OutLbrace()
741 Output("self->ob_freeit(self->ob_itself);")
742 OutRbrace()
743 Output("self->ob_itself = NULL;")
745 def output_tp_newBody(self):
746 Output("PyObject *self;");
747 Output()
748 Output("if ((self = type->tp_alloc(type, 0)) == NULL) return NULL;")
749 Output("((%s *)self)->ob_itself = NULL;", self.objecttype)
750 Output("return self;")
752 def output_tp_initBody(self):
753 Output("%s itself = NULL;", self.itselftype)
754 Output("char *rawdata = NULL;")
755 Output("int rawdatalen = 0;")
756 Output("Handle h;")
757 Output("static char *kw[] = {\"itself\", \"rawdata\", 0};")
758 Output()
759 Output("if (!PyArg_ParseTupleAndKeywords(_args, _kwds, \"|O&s#\", kw, %s_Convert, &itself, &rawdata, &rawdatalen))",
760 self.prefix)
761 Output("return -1;")
762 Output("if (itself && rawdata)")
763 OutLbrace()
764 Output("PyErr_SetString(PyExc_TypeError, \"Only one of itself or rawdata may be specified\");")
765 Output("return -1;")
766 OutRbrace()
767 Output("if (!itself && !rawdata)")
768 OutLbrace()
769 Output("PyErr_SetString(PyExc_TypeError, \"One of itself or rawdata must be specified\");")
770 Output("return -1;")
771 OutRbrace()
772 Output("if (rawdata)")
773 OutLbrace()
774 Output("if ((h = NewHandle(rawdatalen)) == NULL)")
775 OutLbrace()
776 Output("PyErr_NoMemory();")
777 Output("return -1;")
778 OutRbrace()
779 Output("HLock(h);")
780 Output("memcpy((char *)*h, rawdata, rawdatalen);")
781 Output("HUnlock(h);")
782 Output("((%s *)_self)->ob_itself = (%s)h;", self.objecttype, self.itselftype)
783 Output("return 0;")
784 OutRbrace()
785 Output("((%s *)_self)->ob_itself = itself;", self.objecttype)
786 Output("return 0;")
788 # Alias methods come in two flavors: those with the alias as arg1 and
789 # those with the alias as arg 2.
790 class Arg2MethodGenerator(OSErrMethodGenerator):
791 """Similar to MethodGenerator, but has self as second argument"""
793 def parseArgumentList(self, args):
794 args0, arg1, argsrest = args[:1], args[1], args[2:]
795 t0, n0, m0 = arg1
796 args = args0 + argsrest
797 if m0 != InMode:
798 raise ValueError, "method's 'self' must be 'InMode'"
799 self.itself = Variable(t0, "_self->ob_itself", SelfMode)
800 FunctionGenerator.parseArgumentList(self, args)
801 self.argumentList.insert(2, self.itself)
803 # From here on it's basically all boiler plate...
805 # Create the generator groups and link them
806 module = MacModule(MODNAME, MODPREFIX, includestuff, finalstuff, initstuff,
807 longname=LONGMODNAME)
809 fscataloginfoobject = FSCatalogInfoDefinition('FSCatalogInfo', 'FSCatalogInfo', 'FSCatalogInfo')
810 finfoobject = FInfoDefinition('FInfo', 'FInfo', 'FInfo')
811 aliasobject = AliasDefinition('Alias', 'Alias', 'AliasHandle')
812 fsspecobject = FSSpecDefinition('FSSpec', 'FSSpec', 'FSSpec')
813 fsrefobject = FSRefDefinition('FSRef', 'FSRef', 'FSRef')
815 module.addobject(fscataloginfoobject)
816 module.addobject(finfoobject)
817 module.addobject(aliasobject)
818 module.addobject(fsspecobject)
819 module.addobject(fsrefobject)
821 # Create the generator classes used to populate the lists
822 Function = OSErrFunctionGenerator
823 Method = OSErrMethodGenerator
825 # Create and populate the lists
826 functions = []
827 alias_methods = []
828 fsref_methods = []
829 fsspec_methods = []
830 execfile(INPUTFILE)
832 # Manual generators:
833 FSRefMakePath_body = """
834 OSStatus _err;
835 #define MAXPATHNAME 1024
836 UInt8 path[MAXPATHNAME];
837 UInt32 maxPathSize = MAXPATHNAME;
839 if (!PyArg_ParseTuple(_args, ""))
840 return NULL;
841 _err = FSRefMakePath(&_self->ob_itself,
842 path,
843 maxPathSize);
844 if (_err != noErr) return PyMac_Error(_err);
845 _res = Py_BuildValue("s", path);
846 return _res;
848 f = ManualGenerator("FSRefMakePath", FSRefMakePath_body)
849 f.docstring = lambda: "() -> string"
850 fsref_methods.append(f)
852 FSRef_as_pathname_body = """
853 if (!PyArg_ParseTuple(_args, ""))
854 return NULL;
855 _res = FSRef_FSRefMakePath(_self, _args);
856 return _res;
858 f = ManualGenerator("as_pathname", FSRef_as_pathname_body)
859 f.docstring = lambda: "() -> string"
860 fsref_methods.append(f)
862 FSSpec_as_pathname_body = """
863 char strbuf[1024];
864 OSErr err;
866 if (!PyArg_ParseTuple(_args, ""))
867 return NULL;
868 err = _PyMac_GetFullPathname(&_self->ob_itself, strbuf, sizeof(strbuf));
869 if ( err ) {
870 PyMac_Error(err);
871 return NULL;
873 _res = PyString_FromString(strbuf);
874 return _res;
876 f = ManualGenerator("as_pathname", FSSpec_as_pathname_body)
877 f.docstring = lambda: "() -> string"
878 fsspec_methods.append(f)
880 FSSpec_as_tuple_body = """
881 if (!PyArg_ParseTuple(_args, ""))
882 return NULL;
883 _res = Py_BuildValue("(iis#)", _self->ob_itself.vRefNum, _self->ob_itself.parID,
884 &_self->ob_itself.name[1], _self->ob_itself.name[0]);
885 return _res;
887 f = ManualGenerator("as_tuple", FSSpec_as_tuple_body)
888 f.docstring = lambda: "() -> (vRefNum, dirID, name)"
889 fsspec_methods.append(f)
891 pathname_body = """
892 PyObject *obj;
894 if (!PyArg_ParseTuple(_args, "O", &obj))
895 return NULL;
896 if (PyString_Check(obj)) {
897 Py_INCREF(obj);
898 return obj;
900 if (PyUnicode_Check(obj))
901 return PyUnicode_AsEncodedString(obj, "utf8", "strict");
902 _res = PyObject_CallMethod(obj, "as_pathname", NULL);
903 return _res;
905 f = ManualGenerator("pathname", pathname_body)
906 f.docstring = lambda: "(str|unicode|FSSpec|FSref) -> pathname"
907 functions.append(f)
909 # add the populated lists to the generator groups
910 # (in a different wordl the scan program would generate this)
911 for f in functions: module.add(f)
912 for f in alias_methods: aliasobject.add(f)
913 for f in fsspec_methods: fsspecobject.add(f)
914 for f in fsref_methods: fsrefobject.add(f)
916 # generate output (open the output file as late as possible)
917 SetOutputFileName(OUTPUTFILE)
918 module.generate()