Retired Document
Important: This sample code may not represent best practices for current development. The project may use deprecated symbols and illustrate technologies and techniques that are no longer recommended.
Sources/FileClass.cp
/* |
File: FileClass.cp |
Contains: TFile is a simple object that does file manipulations |
TFile.cp contains the TFile class and subclass member functions. |
Written by: Kent Sandvik |
Copyright: Copyright © 1992-1999 by Apple Computer, Inc., All Rights Reserved. |
You may incorporate this Apple sample source code into your program(s) without |
restriction. This Apple sample source code has been provided "AS IS" and the |
responsibility for its operation is yours. You are not permitted to redistribute |
this Apple sample source code as "Apple sample source code" after having made |
changes. If you're going to re-distribute the source, we require that you make |
it clear in the source that the code was descended from Apple sample source |
code, but that you've made changes. |
Change History (most recent first): |
8/18/1999 Karl Groethe Updated for Metrowerks Codewarror Pro 2.1 |
*/ |
#ifndef _FILECLASS_ |
#include "FileClass.h" |
#endif |
// _________________________________________________________________________________________________________ // |
// TFile |
#pragma segment File |
TFile::TFile(char* name) |
// Create a file object based on the name. |
{ |
this->Initialize(); // initialize internal fields to known values |
// We are going to assume a lot of things for the default setting |
// and files, for instance that we are creating files in the current working directory (folder) |
WDPBRec folderBlock; |
folderBlock.ioNamePtr = nil; |
fError = ::PBHGetVolSync(&folderBlock); |
VASSERT(fError == noErr, ("Problems with PBHGetVol = %d", fError)); |
fFileSpec.vRefNum = folderBlock.ioVRefNum; |
fFileSpec.parID = folderBlock.ioWDDirID; |
c2p(name); |
Pstrcpy(fFileSpec.name, (StringPtr)name); |
} |
#pragma segment File |
TFile::TFile(FSSpec theSpec) |
// Create a file object based on the FSSpec. |
{ |
this->Initialize(); // initialize internal fields to known values |
fFileSpec.vRefNum = theSpec.vRefNum; // store the FSSpec |
fFileSpec.parID = theSpec.parID; |
Pstrcpy(fFileSpec.name, theSpec.name); |
} |
#pragma segment File |
TFile::TFile(short volume, |
long dirID, |
Str63 name) |
// Create a file object based on the volume no, directory ID and the name. |
{ |
this->Initialize(); // initialize internal fields to known values |
fFileSpec.vRefNum = volume; // store values into the FSSpec |
fFileSpec.parID = dirID; |
Pstrcpy(fFileSpec.name, name); |
} |
#pragma segment File |
TFile::~TFile() |
// Default destructor -- empty for the time being. |
{ |
} |
#pragma segment File |
void TFile::Initialize() |
// Initialize fields to known values. |
{ |
fFileType = kDefaultType; // gee, we assume everyone's reading/writing text files |
fCreator = kDefaultCreator; // and who's that? |
fOpened = false; // not open yetÉ |
fFlushing = false; // assume things are OK, so we don't flush unless something's critical |
} |
// MAIN INTERFACE |
#pragma segment File |
Boolean TFile::Create() |
// Create a new file. |
{ |
if (!this->FileExists()) |
{ |
fError = ::HCreate(fFileSpec.vRefNum, fFileSpec.parID, fFileSpec.name, fCreator, fFileType); |
VASSERT(fError == noErr, ("Problems with HCreate = %d\n", fError)); |
goto CreateOK; |
} |
return false; |
CreateOK:return true; |
} |
#pragma segment File |
Boolean TFile::Rename(char* newName) |
// Rename the file. |
{ |
if (this->FileExists()) |
{ |
c2p(newName); |
fError = ::HRename(fFileSpec.vRefNum, fFileSpec.parID, fFileSpec.name, (StringPtr)newName); |
VASSERT(fError == noErr, ("Problems with HRename = %d", fError)); |
Pstrcpy(fFileSpec.name, (StringPtr)newName); |
goto RenameOK; |
} |
return false; |
RenameOK:return true; |
} |
#pragma segment File |
void TFile::Delete() |
// Delete the file. |
{ |
if (fOpened) |
this->Close(); // first close the file |
fError = ::HDelete(fFileSpec.vRefNum, fFileSpec.parID, fFileSpec.name); |
VASSERT(fError == noErr, ("nProblems with HDelete = %d", fError)); |
} |
#pragma segment File |
Boolean TFile::FileExists() |
// Test if the file exists or not. |
{ |
FInfo info; |
fError = HGetFInfo(fFileSpec.vRefNum, fFileSpec.parID, fFileSpec.name, &info); |
return (fError == noErr); |
} |
// ACCESSORS AND MUTATORS |
#pragma segment File |
void TFile::SetType(const OSType creator, |
const OSType fileType) |
// Set file type. |
{ |
fCreator = creator; |
fFileType = fileType; |
} |
#pragma segment File |
void TFile::SetFileName(const Str63 fileName) |
// Set file name. |
{ |
Pstrcpy(fFileSpec.name, (StringPtr)fileName); |
} |
#pragma segment File |
FInfo TFile::GetFileInfo() |
// Get FInfo from the specified file. |
{ |
FInfo info; |
fError = ::HGetFInfo(fFileSpec.vRefNum, fFileSpec.parID, fFileSpec.name, &info); |
VASSERT(fError == noErr, ("Problems with HGetFInfo = %d", fError)); |
return info; |
} |
// _________________________________________________________________________________________________________ // |
// TDataFile |
// CONSTRUCTORS AND DESTRUCTORS |
#pragma segment File |
TDataFile::TDataFile(char* name) : |
TFile(name) |
// Default constructor, create a file based on the name. |
{ |
} |
#pragma segment File |
TDataFile::~TDataFile() |
// Default destructor -- empty for the time being. |
{ |
} |
// MAIN INTERFACE |
#pragma segment File |
Boolean TDataFile::Open(SignedByte permission) |
// Open a file for data fork only access. |
{ |
fError = ::HOpen(fFileSpec.vRefNum, fFileSpec.parID, fFileSpec.name, permission, &fRefNum); |
VASSERT(fError == noErr, ("Problems with HOpen = %d", fError)); |
if (fError == noErr) |
fOpened = true; |
return (fError == noErr); |
} |
#pragma segment File |
Boolean TDataFile::Close() |
// Close the file. |
{ |
fError = ::FSClose(fRefNum); |
VASSERT(fError == noErr, ("Problems with FSClose = %d", fError)); |
if (fError == noErr) |
fOpened = false; |
if (fFlushing) // if flagged, flush the volume |
{ |
fError = ::FlushVol(NULL, fFileSpec.vRefNum); |
VASSERT(fError == noErr, ("Problems with FlushVol = %d", fError)); |
} |
return (fError == noErr); |
} |
#pragma segment File |
Boolean TDataFile::WriteHandle(Handle h) |
// Write a handle to file (the whole handle). |
{ |
long len = ::GetHandleSize(h); // get lenght of handle |
fError = ::SetFPos(fRefNum, fsFromStart, kNoOffset);// move pointer to beginning of file |
VASSERT(fError == noErr, ("Problems with SetFPos = %d", fError)); |
fError = ::FSWrite(fRefNum, &len, *h); // write the handle to disk |
VASSERT(fError == noErr, ("Problems with FSWrite = %d", fError)); |
fError = ::SetEOF(fRefNum, len); // change size of file if needed |
VASSERT(fError == noErr, ("Problems with SetEOF = %d", fError)); |
if (fFlushing) |
{ |
fError = ::FlushVol(NULL, fFileSpec.vRefNum); |
VASSERT(fError == noErr, ("Problems with FlushVol = %d", fError)); |
} |
return (fError == noErr); |
} |
#pragma segment File |
Handle TDataFile::ReadHandle() |
// Read handle from the file (the whole handle). |
{ |
Handle h = NULL; |
long len; |
fError = ::GetEOF(fRefNum, &len); // get size of handle in file |
VASSERT(fError == noErr, ("Problems with GetEOF = %d", fError)); |
h = ::NewHandle(len); // create a new handle |
if (h == NULL) // problems creating a handle |
{ |
ASSERT(fError == noErr, "\pProblems with NewHandle"); |
goto ReadHandleFalse; |
} |
fError = ::SetFPos(fRefNum, fsFromStart, kNoOffset); |
VASSERT(fError == noErr, ("Problems with SetFPos = %d", fError)); |
fError = ::FSRead(fRefNum, &len, *h); // read into handle |
VASSERT(fError == noErr, ("Problems with SetFPos = %d", fError)); |
return h; |
ReadHandleFalse:return NULL; |
} |
#pragma segment File |
Boolean TDataFile::Write(Ptr buffer, |
long bytes) |
// Write N bytes from buffer to file. |
{ |
fError = ::FSWrite(fRefNum, &bytes, buffer); |
VASSERT(fError == noErr, ("Problems with FSWrite = %d", fError)); |
return (fError == noErr); |
} |
#pragma segment File |
Boolean TDataFile::Read(Ptr buffer, |
long bytes) |
// Read N bytes from file to buffer. |
{ |
fError = ::FSRead(fRefNum, &bytes, buffer); |
VASSERT(fError == noErr, ("Problems with FSWrite = %d", fError)); |
return (fError == noErr); |
} |
#pragma segment File |
Boolean TDataFile::SetMark(short from, |
long offset) |
// Set file mark (beginning, end, offset). |
{ |
if (fOpened) // have an open file? |
{ |
fError = ::SetFPos(fRefNum, from, offset); |
VASSERT(fError == noErr, ("Problems with SetFPos = %d", fError)); |
goto SetMarkOK; |
} |
else |
return false; |
SetMarkOK:return (fError == noErr); |
} |
#pragma segment File |
long TDataFile::GetMark() |
// Get file mark (offset). |
{ |
long offset = 0; |
fError = ::GetFPos(fRefNum, &offset); |
VASSERT(fError == noErr, ("Problems with GetFPos = %d", fError)); |
return offset; |
} |
#pragma segment File |
Boolean TDataFile::Reset() |
// Set file mark to beginning of file. |
{ |
return (this->SetMark(fsFromStart, kNoOffset));// set mark to beginning of file |
} |
#pragma segment File |
Boolean TDataFile::GotoEndOfFile() |
// Set file mark to end of file. |
{ |
return (this->SetMark(fsFromLEOF, kNoOffset));// set mark to end of file |
} |
// _________________________________________________________________________________________________________ // |
// TResourceFile |
// CONSTRUCTORS AND DESTRUCTORS |
#pragma segment File |
TResourceFile::TResourceFile(char* name) : |
TFile(name) |
// Default destructor, create a TResourceFile object. |
{ |
} |
#pragma segment File |
TResourceFile::~TResourceFile() |
// Default destructor -- not used for the time being. |
{ |
} |
// MAIN INTERFACE |
#pragma segment File |
Boolean TResourceFile::Create() |
// Create the actual resource file. |
{ |
if (!this->FileExists()) |
{ |
Boolean result = TFile::Create(); // call inherited create |
if (result) // if OK |
{ |
::HCreateResFile(fFileSpec.vRefNum, fFileSpec.parID, fFileSpec.name); |
goto CreateResourceOK; |
} |
else |
goto CreateResourceFalse; // result = false |
} |
else |
goto CreateResourceFalse; // couldn't create a file that exists |
CreateResourceFalse:return false; |
CreateResourceOK:if (ResError() == noErr) |
return true; |
else |
return false; |
} |
#pragma segment File |
Boolean TResourceFile::Open(SignedByte permission) |
// Open the resource file. |
{ |
if (fOpened) |
{ |
fRefNum = ::HOpenResFile(fFileSpec.vRefNum, fFileSpec.parID, fFileSpec.name, permission); |
VASSERT(fRefNum != -1, ("Problems with HOpenResFile = %d", ::ResError())); |
if (::ResError() == 0) |
goto ResourceFileOpenOK; |
else |
goto ResourceFileOpenFalse; |
} |
else |
goto ResourceFileOpenFalse; // can't open an already open file |
ResourceFileOpenFalse:return false; |
ResourceFileOpenOK:fOpened = true; |
return true; |
} |
#pragma segment File |
Boolean TResourceFile::Close() |
// Close the resource file. |
{ |
if (fOpened) |
{ |
::CloseResFile(fRefNum); |
VASSERT(fRefNum != -1, ("Problems with CloseResFile = %d", ::ResError())); |
if (::ResError() == 0) |
goto ResourceFileCloseOK; |
else |
goto ResourceFileCloseFalse; |
} |
ResourceFileCloseFalse:return false; |
ResourceFileCloseOK:fRefNum = 0; |
fOpened = false; |
return true; |
} |
#pragma segment File |
Boolean TResourceFile::HasResourceFork() |
// Check if the supposed resource file actually has a resource fork. |
{ |
HFileParam pb; |
pb.ioNamePtr = fFileSpec.name; // get the name |
pb.ioVRefNum = fFileSpec.vRefNum; // and the volume |
pb.ioDirID = fFileSpec.parID; // and the DirID |
pb.ioFDirIndex = 0; // zero this one |
fError = ::PBHGetFInfoSync((HParmBlkPtr) & pb);// call the right trap |
VASSERT(fError == noErr, ("Problems with PBHGetFInfo = %d", fError)); |
return (pb.ioFlRLgLen != 0); // if the resource fork is non-zero, then we got one |
} |
#pragma segment File |
void TResourceFile::Update() |
// Update the resource file. |
{ |
if (fOpened) |
{ |
::UpdateResFile(fRefNum); |
VASSERT(::ResError() == noErr, ("Problems with UpdateResFile = %d", ::ResError())); |
if (fFlushing) |
{ |
fError = ::FlushVol(NULL, fFileSpec.vRefNum); |
VASSERT(fError == noErr, ("Problems with FlushVol = %d", fError)); |
} |
} |
} |
#pragma segment File |
void TResourceFile::Assign() |
// Make sure that we are using this specified resource file. |
{ |
if (fOpened) |
::UseResFile(fRefNum); |
} |
// _________________________________________________________________________________________________________ // |
/* Change History (most recent last): |
No Init. Date Comment |
1 khs 12/27/92 New file |
2 khs 1/14/93 Cleanup |
*/ |
Copyright © 2003 Apple Computer, Inc. All Rights Reserved. Terms of Use | Privacy Policy | Updated: 2003-01-14