/* * Copyright 2001 Perforce Software. All rights reserved. * * This file is part of Perforce - the FAST SCM System. */ /* * macfile.h - Abstract file layer to handle the many differences on Mac OS X and * Classic Mac OS * * NOTE: ----------------------------------------------------------------- * * Some of the following documentation is obsolete but is left for * historical purposes. The need for Mac OS 9 compatibility has gone * as has the need for an abstraction that works both with FSRef and FSSpec. * * MacFile is now a single class with no subclasses and deals solely with * FSRefs. Supporting 'apple' files is more of a legacy compatibility * feature of Perforce so these classes have been simplified. * * TextEncodingConverter is no longer needed and the path delimiter is * always '/' * * In the platform table below, the only platform left is MOSX. * * Okay, on with the docs... * * ----------------------------------------------------------------------- * * On the Macintosh, there are many different kinds of system apis available that * depend on what version of the OS is running, whether or not it is the Classic * Mac OS or Mac OS X, and finally, if you are using Carbon, certain APIs expect * different input based on if the Carbon app is running on Classic Mac OS or * Mac OS X. * * Some concepts and terminology: * ------------------------------ * FSSpec API - the old file API from Apple that was limited to < 32 char, * system codepage filenames. * * FSRef API - the new file API from Apple that allow * for < 256 char, Unicode filenames. * * CFURL API - the API from Apple that allows us to interchange different * path styles (ie: colons on Classic Mac and '/' on MOSX). * Requires the use of CFStrings. * * CFString API - the API from Apple that allows easy manipulation of * strings between different codepages and Unicode. * Also allows modification of a string as an object. * * TextEncodingConverter - the API from Apple that allows conversion of * different runs of characters from one * codepage to another. The big difference between * it and CFString is it only works on raw byte arrays. * There is no concept of a string object. It is super * lo level. * Here is a table: * ---------------- * 3 Binaries of P4 builds: Classic, Carbonized, Mac OS X * * 'MOS8.6' = Standard Mac 8.6 install running Classic P4 * 'Carbon MOS' = MacOS 8.6/9 with Carbon running Carbon P4 * 'MOS9' = Standard Mac OS 9 install running Classic P4 * 'Carbon MOSX' = Mac OS X running Carbon P4 * 'MOSX' = Mac OS X running Mac OS X P4 (partial Std-C/Carbon calls (for speed)) * * | MOS8.6 | Carbon MOS | MOS9 | Carbon MOSX | MOSX *---------------------------------------------------------------------------- * File API | FSSpec | FSRef | FSRef | FSRef | FSRef * Path delimiter | ':' | ':' | ':' | '/' | '/' * CFURL? | | X | | X | X * CFString? | | X | | X | X * TextEncodingConverter? | X | X | X | X | X * Perforce Path Delimiter | ':' | ':' | ':' | ':' | '/' * * There are many different compile options (static) and many different * cases to handle as the code runs (dynamic). * * Static * ------ * - Should use on CFString, CFURL? (yes, with Carbon/MOSX ) * - What is the path delimiter from Perforce? * - Should only use FSRef (yes, with Carbon/MOSX) * * Dynamic * ------- * - Path delimiter of System (For Carbon) * - Are FSRefs available? Fallback to FSSpec (For Classic) * * * Public methods: * * MACFILE * ------------- * MacFile is an object that represents a file on the disk. You can use this * to read and write resource and data forks, set and get comment info, get and * set additional Finder Info, and set and get type and creator info (although * you can do that with the Finder Info as well). * * Creation * -------- * GetFromPath() - takes a path, a style, and an encoding and returns an object to * represent it. Returns NULL if no object could be made from the path. * GetFromFSRef() - If you alread have an FSRef, you can make a MacFile from it. * CreateFromPath() - takes a path, style, and encoding and creates a file (or * directory) on the disk where the path points. It will not * create subdirectories automatically. Returns NULL if no object * could be made from the path. * * GetFileSystem * ------------- * GetFileSystem() - Get the kind of file system the file is on. This only makes * sense on Mac OS X. * IsDir * -------- * IsDir() - Let's you know if the file is a firectory or not. Some methods should * not be called if the file is a directory. * * Metadata * -------- * GetFInfo() - returns the finder information for this file * SetFInfo() - sets the finder information for this file * GetFXInfo() - gets the extended finder information for this file * SetFXInfo() - sets the extended finder information for this file * * IsHidden() - determines if the file has its hidden attribute set * CreateBundle() - Creates a Core Foundation Bundle from this file. Returns * NULL if there is no bundle for this file. * IsUnbundledApp() - determines if the file is an application in a single file * (the traditional Mac way of making an app) * IsBundledApp() - determines if the file is an application directory. (the new * way of packaging an application. Like the ".app" programs * you get on Mac OS X) * * IsLocked() - determines if the file has its immutable bit set * SetLocked() - sets the file's locked attribute * * GetTypeAndCreator() - retrieves the type and creator. You can pass NULL if you are * not interested in one of them. * SetTypeAndCreator() - sets the type and creator. * * GetComment() - returns the comment and the length. * SetComment() - fills in the file comment with the bytes. You pass in the buffer * and the size of it * * Reading and Writing * ------------------- * HasDataFork() - returns if the file has a data fork * GetDataForkSize() - returns the size in bytes of the data fork * OpenDataFork() - opens the data fork for writing * ReadDataFork() - reads data out of the fork. Tries to read requestCount bytes * into buffer and returns actualCount bytes as the number acutally * read. * WriteDataFork() - reads data out of the fork. Tries to write requestCount bytes * from buffer and returns actualCount bytes as the number acutally * written. * SetDataForkPosition() - sets the position relative to the beginning of the file. * CloseDataFork() - closes the data for for writing. * * HasResourceFork() - returns if the file has a rsrc fork * GetResourceForkSize() - returns the size in bytes of the rsrc fork * OpenResourceFork() - opens the rsrc fork for writing * ReadResourceFork() - reads data out of the fork. Tries to read requestCount bytes * into buffer and returns actualCount bytes as the number * acutally read. * WriteResourceFork() - reads data out of the fork. Tries to write requestCount * bytes from buffer and returns actualCount bytes as the * number acutally written. * CloseResourceFork() - closes the fork for for writing. * * Misc * ---- * GetPrintableFullPath() - returns a C String that you can use for printing which is * in the native path format and encoding for the filesystem. * GetFSSpec() - returns an FSSpec for the file. If you want a const one, you can * capture the return value. If you want a changeable one, pass it in * to the method. You can pass NULL (0) in if you like. * GetFSRef() - returns an GetFSRef for the file. Can return NULL if one is not * available. If you want a const one, you can capture the return value. * If you want a changeable one, pass it in to the method. You can * pass NULL (0) in if you like. * * */ # if defined (OS_MACOSX) # ifndef __MACFILE_H__ # define __MACFILE_H__ # include <CoreServices/CoreServices.h> # define kMacPathStylePerforce kCFURLPOSIXPathStyle // This switch prefers the 64-bit compatible FSIORefNum type (OS 10.5 and // later) to the standard SInt16 type (OS 10.4 and earlier) #ifdef __MAC_OS_X_VERSION_MAX_ALLOWED #if __MAC_OS_X_VERSION_MIN_ALLOWED <= 1050 # define P4IORefNum FSIORefNum # else # define P4IORefNum SInt16 # endif # else # define P4IORefNum SInt16 #endif /* ============================= *\ * * ABSTRACT BASE CLASSES * \* ============================= */ class MacFile { public: enum { FS_HFS = 0, FS_UFS, FS_NFS }; // // Creation // static MacFile * GetFromPath( const char * path, OSErr * error ); static MacFile * GetFromFSRef( const FSRef * ref, OSErr * error ); static MacFile * CreateFromPath( const char * path, Boolean isDirectory, OSErr * error ); static MacFile * CreateFromDirAndName( const FSRef & dir, CFStringRef name, Boolean isDirectory, OSErr * outErr ); virtual ~MacFile(); // // File Deletion // OSErr Delete(); // // Determing the file system. // int GetFileSystemType() const; // // Is Directory // Boolean IsDir() const; // // Metadata // const FInfo * GetFInfo() const; OSErr SetFInfo( const FInfo * ); static void SwapFInfo( FInfo * ); const FXInfo * GetFXInfo() const; OSErr SetFXInfo( const FXInfo * ); static void SwapFXInfo( FXInfo * ); Boolean IsHidden() const; CFBundleRef CreateBundle() const; Boolean IsUnbundledApp() const; Boolean IsBundledApp() const; Boolean IsLocked() const; OSErr SetLocked( Boolean lock ); OSErr GetTypeAndCreator( UInt32 * type, UInt32 * creator ) const; OSErr SetTypeAndCreator( UInt32 type, UInt32 creator ); const char * GetComment( int *bufferLength ) const; OSErr SetComment( char * buffer, int bufferLength ); // // Reading and Writing // Boolean HasDataFork() const; ByteCount GetDataForkSize() const; OSErr OpenDataFork( SInt8 permissions ); OSErr ReadDataFork( ByteCount requestCount, void * buffer, ByteCount * actualCount ); OSErr WriteDataFork( ByteCount requestCount, const void * buffer, ByteCount * actualCount ); OSErr SetDataForkPosition( ByteCount offset ); OSErr CloseDataFork(); Boolean HasResourceFork() const; ByteCount GetResourceForkSize() const; OSErr OpenResourceFork( SInt8 permissions ); OSErr ReadResourceFork( ByteCount requestCount, void * buffer, ByteCount * actualCount ); OSErr WriteResourceFork( ByteCount requestCount, const void * buffer, ByteCount * actualCount ); OSErr CloseResourceFork(); // // Misc // const char * GetPrintableFullPath() const; const FSRef * GetFSRef( FSRef * spec ) const; private: MacFile( FSRef * file ); OSErr LoadCatalogInfo() const; OSErr SaveCatalogInfo(); OSErr PreloadComment() const; char * fullPath; FSRef * file; mutable FSCatalogInfo fileInfo; FSCatalogInfoBitmap changedInfoBitmap; P4IORefNum dataForkRef; P4IORefNum rsrcForkRef; mutable char * comment; mutable short commentLength; }; /* ============================= *\ * * UTILIY METHODS * \* ============================= */ UniChar GetSystemFileSeparator(); CFURLPathStyle GetSystemPathStyle(); char * FSRefToPath( const FSRef * ref ); # endif // __MACFILE_H__ # endif // defined (OS_MACOSX)