-- XFileIOImpl.mesa
-- Created by Jeff Weinstein on 6-May-87 23:10:07
DIRECTORY
CString,
Heap,
MFile,
MStream,
Stream,
String,
XFileIO;
XFileIOImpl:PROGRAM IMPORTS CString, Heap, MFile, MStream, Stream, String EXPORTS XFileIO =
BEGIN
z:UNCOUNTED ZONE ← Heap.systemZone;
FiOpenForRead:PUBLIC PROCEDURE[name:CString.CString] RETURNS [fid:Stream.Handle] =
BEGIN
string:LONG STRING ← CString.CStringToLongString[name,z];
fid ← MStream.ReadOnly[string,[NIL,NIL] ! MStream.Error => { fid ← NIL; CONTINUE;}];
String.FreeString[z, string];
END;
FiClose:PUBLIC PROCEDURE[fid:Stream.Handle] =
BEGIN
Stream.Delete[fid];
END;
FiRead:PUBLIC PROCEDURE[buf:LONG POINTER, itemsize:CARDINAL, nitem:CARDINAL, fid:Stream.Handle] RETURNS[itemsRead:CARDINAL] =
BEGIN
why:Stream.CompletionCode;
bytes:CARDINAL;
[bytesTransferred:bytes,why:why] ← Stream.GetBlock[fid,[buf,0,nitem*itemsize]];
itemsRead ← bytes / itemsize;
END;
SetDefaultFontPath:PUBLIC PROCEDURE[name:CString.CString] =
BEGIN
string:LONG STRING ← CString.CStringToLongString[name,z];
path:MFile.SearchPath ← z.NEW[MFile.SearchPathObject[1]];
path.length ← 1;
path.directories[0] ← string;
[] ← MFile.SetSearchPath[path];
String.FreeString[z,string];
z.FREE[@path];
END;
SetFontPath:PUBLIC PROCEDURE[path:XFileIO.FontPath] =
BEGIN
sPath:MFile.SearchPath ← z.NEW[MFile.SearchPathObject[path.npaths]];
sPath.length ← path.npaths;
FOR i:INTEGER IN [0..path.npaths) DO
sPath.directories[i] ← CString.CStringToLongString[path.paths[i],z];
ENDLOOP;
[] ← MFile.SetSearchPath[sPath];
FOR i:INTEGER IN [0..path.npaths) DO
String.FreeString[z,sPath.directories[i]];
ENDLOOP;
z.FREE[@sPath];
END;
ExpandFontName:PUBLIC PROCEDURE[name:CString.CString, pathName:LONG POINTER TO CString.CString, zone:UNCOUNTED ZONE] RETURNS[nameLen:CARDINAL] =
BEGIN
numNames:CARDINAL;
names:LONG POINTER TO ARRAY [0..0) OF LONG STRING;
pattern:LONG STRING ← CString.CStringToLongString[name,z];
[names,numNames] ← LookupFiles[pattern, 1];
IF numNames # 1 THEN
BEGIN
nameLen ← 0;
pathName↑ ← LOOPHOLE[LONG[0]];
END
ELSE
BEGIN
nameLen ← names[0].length;
pathName↑ ← CString.LongStringToCString[names[0],zone];
END;
FreeNames[names,numNames];
String.FreeString[z,pattern];
END;
ExpandFontNamePattern:PUBLIC PROCEDURE[pattern:CString.CString, maxNames:CARDINAL, zone:UNCOUNTED ZONE] RETURNS [paths:XFileIO.FontPath] =
BEGIN
names:LONG POINTER TO ARRAY [0..0) OF LONG STRING;
numNames:CARDINAL;
string:LONG STRING ← CString.CStringToLongString[pattern,z];
paths ← zone.NEW[XFileIO.FontPathRec];
[names, numNames] ← LookupFiles[string,maxNames];
IF numNames > 0 THEN
BEGIN
paths.npaths ← numNames;
-- paths.length ← zone.NEW[ARRAY[0..numNames) OF INTEGER];
-- paths.paths ← zone.NEW[ARRAY[0..numNames) OF CString.CString];
paths.length ← Heap.MakeNode[z:zone, n:SIZE[INTEGER]*numNames];
paths.paths ← Heap.MakeNode[z:zone, n:SIZE[CString.CString]*numNames];
FOR i:CARDINAL IN [0..numNames) DO
paths.length[i] ← names[i].length;
paths.paths[i] ← CString.LongStringToCString[names[i],zone];
ENDLOOP;
END
ELSE
paths↑ ← [0,NIL,NIL];
FreeNames[names,numNames];
String.FreeString[z,string];
END;
LookupFiles:PROCEDURE[pattern:LONG STRING, maxNames:CARDINAL] RETURNS [names:LONG POINTER TO ARRAY [0..0) OF LONG STRING, numNames:CARDINAL] =
BEGIN
EnumProc:MFile.EnumerateProc =
BEGIN
names[numNames] ← String.CopyToNewString[fullName,z];
numNames ← numNames + 1;
IF numNames >= maxNames THEN
done ← TRUE;
END;
numNames ← 0;
-- names ← z.NEW[ARRAY[0..maxNames) OF LONG STRING];
names ← Heap.MakeNode[z:z, n:SIZE[LONG STRING]*maxNames];
MFile.EnumerateDirectory[name:pattern, proc:EnumProc, which:filesOnly];
END;
FreeNames:PROCEDURE[names:LONG POINTER TO ARRAY [0..0) OF LONG STRING, numNames:CARDINAL] =
BEGIN
FOR i:CARDINAL IN [0..numNames) DO
String.FreeString[z,names[i]];
ENDLOOP;
z.FREE[@names];
END;
END...