mirror of
https://gitlab.com/freepascal.org/fpc/pas2js.git
synced 2025-08-18 01:39:06 +02:00
* Add FindFirst/FindNext support
This commit is contained in:
parent
72b7d29497
commit
5d3abdcc5d
@ -43,14 +43,6 @@
|
|||||||
<Item0 Name="PasJSIsProjectHTMLFile" Value="1"/>
|
<Item0 Name="PasJSIsProjectHTMLFile" Value="1"/>
|
||||||
</CustomData>
|
</CustomData>
|
||||||
</Unit>
|
</Unit>
|
||||||
<Unit>
|
|
||||||
<Filename Value="wasitypes.pas"/>
|
|
||||||
<IsPartOfProject Value="True"/>
|
|
||||||
</Unit>
|
|
||||||
<Unit>
|
|
||||||
<Filename Value="wasizenfs.pas"/>
|
|
||||||
<IsPartOfProject Value="True"/>
|
|
||||||
</Unit>
|
|
||||||
</Units>
|
</Units>
|
||||||
</ProjectOptions>
|
</ProjectOptions>
|
||||||
<CompilerOptions>
|
<CompilerOptions>
|
||||||
|
@ -23,8 +23,8 @@ end;
|
|||||||
procedure TMyApplication.RunWasm;
|
procedure TMyApplication.RunWasm;
|
||||||
|
|
||||||
begin
|
begin
|
||||||
// Writeln('Enabling logging');
|
// Writeln('Enabling logging');
|
||||||
// WasiEnvironment.LogAPI:=True;
|
// WasiEnvironment.LogAPI:=True;
|
||||||
await(tjsobject, ZenFS.configure(
|
await(tjsobject, ZenFS.configure(
|
||||||
new(
|
new(
|
||||||
['mounts', new([
|
['mounts', new([
|
||||||
@ -33,6 +33,10 @@ begin
|
|||||||
])
|
])
|
||||||
)
|
)
|
||||||
);
|
);
|
||||||
|
if not ZenFS.existsSync('/tmp') then
|
||||||
|
begin
|
||||||
|
ZenFS.mkdirSync('/tmp',777);
|
||||||
|
end;
|
||||||
FS:=TWASIZenFS.Create;
|
FS:=TWASIZenFS.Create;
|
||||||
WasiEnvironment.FS:=FS;
|
WasiEnvironment.FS:=FS;
|
||||||
StartWebAssembly('fsdemo.wasm');
|
StartWebAssembly('fsdemo.wasm');
|
||||||
|
@ -10,6 +10,34 @@ Const
|
|||||||
{$Endif}
|
{$Endif}
|
||||||
OurFile = OurDir+'/test.txt';
|
OurFile = OurDir+'/test.txt';
|
||||||
|
|
||||||
|
Procedure ShowDir(aDir : String);
|
||||||
|
|
||||||
|
var
|
||||||
|
Info : TSearchRec;
|
||||||
|
aFileCount : Integer;
|
||||||
|
TotalSize : Int64;
|
||||||
|
S : String;
|
||||||
|
begin
|
||||||
|
TotalSize:=0;
|
||||||
|
aFileCount:=0;
|
||||||
|
If FindFirst(aDir+'*',faAnyFile,Info)=0 then
|
||||||
|
try
|
||||||
|
Repeat
|
||||||
|
S:=Info.Name;
|
||||||
|
if (Info.Attr and faDirectory)<>0 then
|
||||||
|
S:=S+'/';
|
||||||
|
if (Info.Attr and faSymLink)<>0 then
|
||||||
|
S:=S+'@';
|
||||||
|
Writeln(FormatDateTime('yyyy-mm-dd"T"hh:nn:ss',Info.TimeStamp),' ',Info.Size:10,' '+S);
|
||||||
|
TotalSize:=TotalSize+Info.Size;
|
||||||
|
inc(aFileCount);
|
||||||
|
until FindNext(Info)<>0;
|
||||||
|
finally
|
||||||
|
FindClose(Info)
|
||||||
|
end;
|
||||||
|
Writeln('Total: ',TotalSize,' bytes in ',aFileCount,' files');
|
||||||
|
end;
|
||||||
|
|
||||||
var
|
var
|
||||||
HasDir : Boolean;
|
HasDir : Boolean;
|
||||||
HasFile: Boolean;
|
HasFile: Boolean;
|
||||||
@ -17,7 +45,6 @@ var
|
|||||||
aSize,FD,byteCount : Integer;
|
aSize,FD,byteCount : Integer;
|
||||||
|
|
||||||
begin
|
begin
|
||||||
S:='Hello, WebAssembly World!';
|
|
||||||
HasDir:=DirectoryExists(OurDir);
|
HasDir:=DirectoryExists(OurDir);
|
||||||
if HasDir then
|
if HasDir then
|
||||||
Writeln('Directory already exists: ',OurDir)
|
Writeln('Directory already exists: ',OurDir)
|
||||||
@ -25,6 +52,8 @@ begin
|
|||||||
Writeln('Created new directory: ',OurDir)
|
Writeln('Created new directory: ',OurDir)
|
||||||
else
|
else
|
||||||
Writeln('Failed to create directory: ',OurDir);
|
Writeln('Failed to create directory: ',OurDir);
|
||||||
|
Writeln('Contents of root:');
|
||||||
|
ShowDir('/');
|
||||||
HasFile:=FileExists(OurFile);
|
HasFile:=FileExists(OurFile);
|
||||||
If HasFile then
|
If HasFile then
|
||||||
Writeln('File exists: ',OurFile)
|
Writeln('File exists: ',OurFile)
|
||||||
@ -37,12 +66,15 @@ begin
|
|||||||
else
|
else
|
||||||
begin
|
begin
|
||||||
Writeln('Got fileHandle: ',FD);
|
Writeln('Got fileHandle: ',FD);
|
||||||
|
S:='Hello, WebAssembly World!';
|
||||||
ByteCount:=FileWrite(FD,S[1],Length(S));
|
ByteCount:=FileWrite(FD,S[1],Length(S));
|
||||||
Writeln('Wrote ',byteCount,' bytes to file. Expected: ',Length(S));
|
Writeln('Wrote ',byteCount,' bytes to file. Expected: ',Length(S));
|
||||||
FileClose(FD);
|
FileClose(FD);
|
||||||
Writeln('Closed file');
|
Writeln('Closed file');
|
||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
Writeln('Contents of ',OurDir,':');
|
||||||
|
ShowDir(ourdir+'/');
|
||||||
If FileExists(OurFile) then
|
If FileExists(OurFile) then
|
||||||
begin
|
begin
|
||||||
Writeln('Opening file: ',OurFile);
|
Writeln('Opening file: ',OurFile);
|
||||||
|
@ -143,7 +143,7 @@ type
|
|||||||
function fd_prestat_get(fd: NativeInt; bufPtr: TWasmMemoryLocation) : NativeInt; virtual;
|
function fd_prestat_get(fd: NativeInt; bufPtr: TWasmMemoryLocation) : NativeInt; virtual;
|
||||||
function fd_pwrite(fd, iovs, iovsLen, offset, nwritten : NativeInt) : NativeInt;virtual;
|
function fd_pwrite(fd, iovs, iovsLen, offset, nwritten : NativeInt) : NativeInt;virtual;
|
||||||
function fd_read(fd: NativeInt; iovs : TWasmMemoryLocation; iovsLen: NativeInt; nread : TWasmMemoryLocation) : NativeInt; virtual;
|
function fd_read(fd: NativeInt; iovs : TWasmMemoryLocation; iovsLen: NativeInt; nread : TWasmMemoryLocation) : NativeInt; virtual;
|
||||||
function fd_readdir(fd, bufPtr, bufLen, cookie, bufusedPtr : NativeInt) : NativeInt; virtual;
|
function fd_readdir(fd : NativeInt; bufPtr: TWasmMemoryLocation; bufLen, cookie: NativeInt; bufusedPtr : TWasmMemoryLocation) : NativeInt; virtual;
|
||||||
function fd_renumber(afrom,ato : NativeInt) : NativeInt; virtual;
|
function fd_renumber(afrom,ato : NativeInt) : NativeInt; virtual;
|
||||||
function fd_seek(fd, offset, whence : NativeInt; newOffsetPtr : TWasmMemoryLocation) : NativeInt; virtual;
|
function fd_seek(fd, offset, whence : NativeInt; newOffsetPtr : TWasmMemoryLocation) : NativeInt; virtual;
|
||||||
function fd_sync(fd : NativeInt) : NativeInt; virtual;
|
function fd_sync(fd : NativeInt) : NativeInt; virtual;
|
||||||
@ -1434,7 +1434,6 @@ begin
|
|||||||
if LogAPI then
|
if LogAPI then
|
||||||
DoLog('TPas2JSWASIEnvironment.fd_seek(%d,%d,%d,[%x])',[fd,offset,whence,newOffsetPtr]);
|
DoLog('TPas2JSWASIEnvironment.fd_seek(%d,%d,%d,[%x])',[fd,offset,whence,newOffsetPtr]);
|
||||||
{$ENDIF}
|
{$ENDIF}
|
||||||
console.log('Unimplemented: TPas2JSWASIEnvironment.fd_seek');
|
|
||||||
if not Assigned(FS) then
|
if not Assigned(FS) then
|
||||||
Result:=WASI_ENOSYS
|
Result:=WASI_ENOSYS
|
||||||
else
|
else
|
||||||
@ -1633,15 +1632,51 @@ begin
|
|||||||
Result:=TJSUint8Array.New(0);
|
Result:=TJSUint8Array.New(0);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TPas2JSWASIEnvironment.fd_readdir(fd, bufPtr, bufLen, cookie,
|
function TPas2JSWASIEnvironment.fd_readdir(fd: NativeInt; bufPtr: TWasmMemoryLocation; bufLen, cookie: NativeInt;
|
||||||
bufusedPtr: NativeInt): NativeInt;
|
bufusedPtr: TWasmMemoryLocation): NativeInt;
|
||||||
|
|
||||||
|
var
|
||||||
|
Dirent : TWasiFSDirent;
|
||||||
|
NameArray : TJSUint8Array;
|
||||||
|
NameLen : integer;
|
||||||
|
Ptr : TWasmMemoryLocation;
|
||||||
|
Res,Used : Integer;
|
||||||
|
|
||||||
|
|
||||||
begin
|
begin
|
||||||
{$IFNDEF NO_WASI_DEBUG}
|
{$IFNDEF NO_WASI_DEBUG}
|
||||||
if LogAPI then
|
if LogAPI then
|
||||||
DoLog('TPas2JSWASIEnvironment.fd_readdir(%d,[%x],%d,%d,[%x])',[fd,bufPtr,buflen,cookie,bufusedptr]);
|
DoLog('TPas2JSWASIEnvironment.fd_readdir(%d,[%x],%d,%d,[%x])',[fd,bufPtr,buflen,cookie,bufusedptr]);
|
||||||
{$ENDIF}
|
{$ENDIF}
|
||||||
console.log('Unimplemented: TPas2JSWASIEnvironment.fd_readdir');
|
if not Assigned(FS) then
|
||||||
Result:= WASI_ENOSYS;
|
Result:=WASI_ENOSYS
|
||||||
|
else
|
||||||
|
try
|
||||||
|
Res:=FS.ReadDir(FD,AsIntNumber(Cookie),Dirent);
|
||||||
|
Result:=WASI_ESUCCESS;
|
||||||
|
Ptr:=BufPtr;
|
||||||
|
While ((Ptr-BufPtr)<BufLen) and (Res=WASI_ESUCCESS) do
|
||||||
|
begin
|
||||||
|
NameArray:=UTF8TextEncoder.encode(Dirent.name);
|
||||||
|
NameLen:=NameArray.byteLength;
|
||||||
|
Ptr:=SetMemInfoUInt64(Ptr,Dirent.Next);
|
||||||
|
Ptr:=SetMemInfoUInt64(Ptr,Dirent.ino);
|
||||||
|
Ptr:=SetMemInfoInt32(Ptr,NameLen);
|
||||||
|
Ptr:=SetMemInfoInt32(Ptr,DirentMap[Dirent.EntryType]);
|
||||||
|
if SetUTF8StringInMem(Ptr,BufLen-18,Dirent.Name)<>-1 then
|
||||||
|
begin
|
||||||
|
Ptr:=Ptr+NameLen;
|
||||||
|
Cookie:=Dirent.Next;
|
||||||
|
Res:=FS.ReadDir(FD,AsIntNumber(Cookie),Dirent)
|
||||||
|
end
|
||||||
|
else
|
||||||
|
Res:=WASI_ENOMEM;
|
||||||
|
end;
|
||||||
|
SetMemInfoInt32(bufusedPtr,Ptr-BufPtr);
|
||||||
|
except
|
||||||
|
On E : Exception do
|
||||||
|
Result:=ErrorToCode(E);
|
||||||
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TPas2JSWASIEnvironment.fd_renumber(afrom, ato: NativeInt): NativeInt;
|
function TPas2JSWASIEnvironment.fd_renumber(afrom, ato: NativeInt): NativeInt;
|
||||||
@ -1811,12 +1846,12 @@ begin
|
|||||||
Loc:=BufPtr;
|
Loc:=BufPtr;
|
||||||
Loc:=SetMemInfoInt64(Loc,Info.dev);
|
Loc:=SetMemInfoInt64(Loc,Info.dev);
|
||||||
Loc:=SetMemInfoUInt64(Loc,Info.Ino);
|
Loc:=SetMemInfoUInt64(Loc,Info.Ino);
|
||||||
Loc:=SetMemInfoInt8(Loc,Info.filetype);
|
Loc:=SetMemInfoUInt64(Loc,Info.filetype);
|
||||||
Loc:=SetMemInfoUInt64(Loc,Info.nLink);
|
Loc:=SetMemInfoUInt64(Loc,Info.nLink);
|
||||||
Loc:=SetMemInfoUInt64(Loc,Info.size);
|
Loc:=SetMemInfoUInt64(Loc,Info.size);
|
||||||
Loc:=SetMemInfoUInt64(Loc,Info.atim);
|
Loc:=SetMemInfoUInt64(Loc,Info.atim*1000*1000);
|
||||||
Loc:=SetMemInfoUInt64(Loc,Info.mtim);
|
Loc:=SetMemInfoUInt64(Loc,Info.mtim*1000*1000);
|
||||||
Loc:=SetMemInfoUInt64(Loc,Info.ctim);
|
Loc:=SetMemInfoUInt64(Loc,Info.ctim*1000*1000);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TPas2JSWASIEnvironment.path_filestat_get(fd, flags: NativeInt;
|
function TPas2JSWASIEnvironment.path_filestat_get(fd, flags: NativeInt;
|
||||||
@ -2064,7 +2099,7 @@ Var
|
|||||||
begin
|
begin
|
||||||
view:=getModuleMemoryDataView();
|
view:=getModuleMemoryDataView();
|
||||||
view.setint16(aLoc,aValue, IsLittleEndian);
|
view.setint16(aLoc,aValue, IsLittleEndian);
|
||||||
Result:=aValue+SizeInt16;
|
Result:=aLoc+SizeInt16;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TPas2JSWASIEnvironment.SetMemInfoInt32(aLoc: TWasmMemoryLocation;
|
function TPas2JSWASIEnvironment.SetMemInfoInt32(aLoc: TWasmMemoryLocation;
|
||||||
@ -2076,7 +2111,7 @@ Var
|
|||||||
begin
|
begin
|
||||||
view:=getModuleMemoryDataView();
|
view:=getModuleMemoryDataView();
|
||||||
view.setInt32(aLoc,aValue,IsLittleEndian);
|
view.setInt32(aLoc,aValue,IsLittleEndian);
|
||||||
Result:=aValue+SizeInt32;
|
Result:=aLoc+SizeInt32;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
function TPas2JSWASIEnvironment.SetMemInfoInt64(aLoc: TWasmMemoryLocation;
|
function TPas2JSWASIEnvironment.SetMemInfoInt64(aLoc: TWasmMemoryLocation;
|
||||||
|
@ -34,7 +34,7 @@ Type
|
|||||||
function fd_prestat_get(fd: NativeInt; bufPtr: TWasmMemoryLocation) : NativeInt;
|
function fd_prestat_get(fd: NativeInt; bufPtr: TWasmMemoryLocation) : NativeInt;
|
||||||
function fd_pwrite(fd, iovs, iovsLen, offset, nwritten : NativeInt) : NativeInt;
|
function fd_pwrite(fd, iovs, iovsLen, offset, nwritten : NativeInt) : NativeInt;
|
||||||
function fd_read(fd: NativeInt; iovs : TWasmMemoryLocation; iovsLen: NativeInt; nread : TWasmMemoryLocation) : NativeInt;
|
function fd_read(fd: NativeInt; iovs : TWasmMemoryLocation; iovsLen: NativeInt; nread : TWasmMemoryLocation) : NativeInt;
|
||||||
function fd_readdir(fd, bufPtr, bufLen, cookie, bufusedPtr : NativeInt) : NativeInt;
|
function fd_readdir(fd : NativeInt; bufPtr: TWasmMemoryLocation; bufLen, cookie: NativeInt; bufusedPtr : TWasmMemoryLocation) : NativeInt;
|
||||||
function fd_renumber(afrom,ato : NativeInt) : NativeInt;
|
function fd_renumber(afrom,ato : NativeInt) : NativeInt;
|
||||||
function fd_seek(fd, offset, whence : NativeInt; newOffsetPtr : TWasmMemoryLocation) : NativeInt;
|
function fd_seek(fd, offset, whence : NativeInt; newOffsetPtr : TWasmMemoryLocation) : NativeInt;
|
||||||
function fd_sync(fd : NativeInt) : NativeInt;
|
function fd_sync(fd : NativeInt) : NativeInt;
|
||||||
@ -646,6 +646,13 @@ type
|
|||||||
end;
|
end;
|
||||||
TWasiPreStat = __wasi_prestat_t;
|
TWasiPreStat = __wasi_prestat_t;
|
||||||
|
|
||||||
|
TDirentType = (dtUnknown,dtFile,dtDirectory,dtSymlink,dtSocket,dtBlockDevice,dtCharacterDevice,dtFIFO);
|
||||||
|
TWasiFSDirent = record
|
||||||
|
ino: NativeInt;
|
||||||
|
name : String;
|
||||||
|
EntryType: TDirentType;
|
||||||
|
next : NativeInt;
|
||||||
|
end;
|
||||||
|
|
||||||
{ EWasiFSError }
|
{ EWasiFSError }
|
||||||
|
|
||||||
@ -673,9 +680,21 @@ type
|
|||||||
function DataSync(FD : Integer) : NativeInt;
|
function DataSync(FD : Integer) : NativeInt;
|
||||||
function Seek(FD : integer; Offset : Integer; Whence : TSeekWhence; out NewPos : Integer) : NativeInt;
|
function Seek(FD : integer; Offset : Integer; Whence : TSeekWhence; out NewPos : Integer) : NativeInt;
|
||||||
Function Read(FD : Integer; Data : TJSUint8Array; AtPos : Integer; Out BytesRead : Integer) : NativeInt;
|
Function Read(FD : Integer; Data : TJSUint8Array; AtPos : Integer; Out BytesRead : Integer) : NativeInt;
|
||||||
|
function ReadDir(FD: Integer; Cookie: NativeInt; out DirEnt: TWasiFSDirent): NativeInt;
|
||||||
Function GetPrestat(FD: Integer) : String;
|
Function GetPrestat(FD: Integer) : String;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
Const
|
||||||
|
DirentMap : Array [TDirentType] of Integer =
|
||||||
|
(__WASI_FILETYPE_UNKNOWN,
|
||||||
|
__WASI_FILETYPE_REGULAR_FILE,
|
||||||
|
__WASI_FILETYPE_DIRECTORY,
|
||||||
|
__WASI_FILETYPE_SYMBOLIC_LINK,
|
||||||
|
__WASI_FILETYPE_SOCKET_STREAM,
|
||||||
|
__WASI_FILETYPE_BLOCK_DEVICE,
|
||||||
|
__WASI_FILETYPE_CHARACTER_DEVICE,
|
||||||
|
__WASI_FILETYPE_UNKNOWN);
|
||||||
|
|
||||||
implementation
|
implementation
|
||||||
|
|
||||||
end.
|
end.
|
||||||
|
@ -5,21 +5,26 @@ unit wasizenfs;
|
|||||||
interface
|
interface
|
||||||
|
|
||||||
uses
|
uses
|
||||||
JS, libzenfs, Wasitypes;
|
SysUtils, JS, libzenfs, Wasitypes;
|
||||||
|
|
||||||
Type
|
Type
|
||||||
|
EWASIZenFS = class(Exception);
|
||||||
|
|
||||||
{ TWASIZenFS }
|
{ TWASIZenFS }
|
||||||
|
|
||||||
TWASIZenFS = class (TObject,IWasiFS)
|
TWASIZenFS = class (TObject,IWasiFS)
|
||||||
private
|
private
|
||||||
FRoot : TZenFSDir;
|
FRoot : TZenFSDir;
|
||||||
|
FDirMap : TJSMap;
|
||||||
protected
|
protected
|
||||||
|
function AllocateDirFD(aDir: TZenFSDirentArray): Integer;
|
||||||
|
function IsDirEnt(FD : Integer) : TZenFSDirentArray;
|
||||||
|
Procedure RemoveDirent(FD : integer);
|
||||||
function PrependFD(FD: Integer; aPath: String): string;
|
function PrependFD(FD: Integer; aPath: String): string;
|
||||||
class function ExceptToError(E : TJSObject) : Integer;
|
class function ExceptToError(E : TJSObject) : Integer;
|
||||||
class function ZenFSDateToWasiTimeStamp(aDate: TJSDate): Nativeint;
|
class function ZenFSDateToWasiTimeStamp(aDate: TJSDate): Nativeint;
|
||||||
class function ZenStatToWasiStat(ZSTat: TZenFSStats): TWasiFileStat;
|
class function ZenStatToWasiStat(ZSTat: TZenFSStats): TWasiFileStat;
|
||||||
Public
|
Public
|
||||||
|
constructor create;
|
||||||
Function MkDirAt(FD : Integer; const aPath : String) : NativeInt;
|
Function MkDirAt(FD : Integer; const aPath : String) : NativeInt;
|
||||||
Function RmDirAt(FD : Integer; const aPath : String) : NativeInt;
|
Function RmDirAt(FD : Integer; const aPath : String) : NativeInt;
|
||||||
function StatAt(FD : Integer; const aPath : String; var stat: TWasiFileStat) : NativeInt;
|
function StatAt(FD : Integer; const aPath : String; var stat: TWasiFileStat) : NativeInt;
|
||||||
@ -38,6 +43,7 @@ Type
|
|||||||
function DataSync(FD : Integer) : NativeInt;
|
function DataSync(FD : Integer) : NativeInt;
|
||||||
function Seek(FD : integer; Offset : Integer; Whence : TSeekWhence; out NewPos : Integer) : NativeInt;
|
function Seek(FD : integer; Offset : Integer; Whence : TSeekWhence; out NewPos : Integer) : NativeInt;
|
||||||
Function Read(FD : Integer; Data : TJSUint8Array; AtPos : Integer; Out BytesRead : Integer) : NativeInt;
|
Function Read(FD : Integer; Data : TJSUint8Array; AtPos : Integer; Out BytesRead : Integer) : NativeInt;
|
||||||
|
function ReadDir(FD: Integer; Cookie: NativeInt; out DirEnt: TWasiFSDirent): NativeInt;
|
||||||
Function GetPrestat(FD: Integer) : String;
|
Function GetPrestat(FD: Integer) : String;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
@ -48,6 +54,33 @@ const
|
|||||||
|
|
||||||
{ TWASIZenFS }
|
{ TWASIZenFS }
|
||||||
|
|
||||||
|
function TWASIZenFS.AllocateDirFD(aDir : TZenFSDirentArray): Integer;
|
||||||
|
var
|
||||||
|
I : integer;
|
||||||
|
|
||||||
|
begin
|
||||||
|
I:=4;
|
||||||
|
While (I<100) and (FDirMap.has(i)) do
|
||||||
|
Inc(I);
|
||||||
|
if I=100 then
|
||||||
|
Raise EWASIZenFS.Create('Too many directories');
|
||||||
|
FDirMap.&set(I,aDir);
|
||||||
|
Result:=I;
|
||||||
|
end;
|
||||||
|
|
||||||
|
function TWASIZenFS.IsDirEnt(FD: Integer): TZenFSDirentArray;
|
||||||
|
begin
|
||||||
|
if FDirMap.has(FD) then
|
||||||
|
Result:=TZenFSDirentArray(FDirMap.get(FD))
|
||||||
|
else
|
||||||
|
Result:=Nil;
|
||||||
|
end;
|
||||||
|
|
||||||
|
procedure TWASIZenFS.RemoveDirent(FD: integer);
|
||||||
|
begin
|
||||||
|
FDirMap.delete(FD);
|
||||||
|
end;
|
||||||
|
|
||||||
function TWASIZenFS.PrependFD(FD: Integer; aPath: String) : string;
|
function TWASIZenFS.PrependFD(FD: Integer; aPath: String) : string;
|
||||||
|
|
||||||
begin
|
begin
|
||||||
@ -116,6 +149,11 @@ begin
|
|||||||
Result.ctim:=ZenFSDateToWasiTimeStamp(ZStat.cTime);
|
Result.ctim:=ZenFSDateToWasiTimeStamp(ZStat.cTime);
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
constructor TWASIZenFS.create;
|
||||||
|
begin
|
||||||
|
FDirMap:=TJSMap.new;
|
||||||
|
end;
|
||||||
|
|
||||||
function TWASIZenFS.StatAt(FD: Integer; const aPath: String;
|
function TWASIZenFS.StatAt(FD: Integer; const aPath: String;
|
||||||
var stat: TWasiFileStat): NativeInt;
|
var stat: TWasiFileStat): NativeInt;
|
||||||
|
|
||||||
@ -231,8 +269,15 @@ end;
|
|||||||
|
|
||||||
function TWASIZenFS.Close(FD : Integer): NativeInt;
|
function TWASIZenFS.Close(FD : Integer): NativeInt;
|
||||||
|
|
||||||
|
|
||||||
begin
|
begin
|
||||||
try
|
try
|
||||||
|
if IsDirEnt(FD)<>Nil then
|
||||||
|
begin
|
||||||
|
RemoveDirent(FD);
|
||||||
|
Result:=WASI_ESUCCESS;
|
||||||
|
end
|
||||||
|
else
|
||||||
ZenFS.closeSync(fd);
|
ZenFS.closeSync(fd);
|
||||||
Result:=resOK;
|
Result:=resOK;
|
||||||
except
|
except
|
||||||
@ -344,6 +389,38 @@ begin
|
|||||||
end;
|
end;
|
||||||
end;
|
end;
|
||||||
|
|
||||||
|
function TWASIZenFS.ReadDir(FD: Integer; Cookie : NativeInt; out DirEnt: TWasiFSDirent): NativeInt;
|
||||||
|
|
||||||
|
var
|
||||||
|
DirEnts : TZenFSDirentArray;
|
||||||
|
ZDirEntry : TZenFSDirent;
|
||||||
|
|
||||||
|
begin
|
||||||
|
DirEnts:=IsDirEnt(FD);
|
||||||
|
if Not Assigned(DirEnts) then
|
||||||
|
Exit(WASI_EBADF);
|
||||||
|
if (Cookie<0) or (Cookie>=Length(Dirents)) then
|
||||||
|
Exit(WASI_ENOENT);
|
||||||
|
ZDirEntry:=Dirents[Cookie];
|
||||||
|
DirEnt.name:=ZDirEntry.path;
|
||||||
|
if ZDirEntry.isFile() then
|
||||||
|
Dirent.EntryType:=dtFile
|
||||||
|
else if ZDirEntry.isDirectory() then
|
||||||
|
Dirent.EntryType:=dtDirectory
|
||||||
|
else if ZDirEntry.isSymbolicLink() then
|
||||||
|
Dirent.EntryType:=dtSymlink
|
||||||
|
else if ZDirEntry.isFIFO() then
|
||||||
|
Dirent.EntryType:=dtFIFO
|
||||||
|
else if ZDirEntry.isBlockDevice() then
|
||||||
|
Dirent.EntryType:=dtBlockDevice
|
||||||
|
else if ZDirEntry.isCharacterDevice() then
|
||||||
|
Dirent.EntryType:=dtCharacterDevice
|
||||||
|
else if ZDirEntry.isSocket() then
|
||||||
|
Dirent.EntryType:=dtSocket;
|
||||||
|
Dirent.Next:=Cookie+1;
|
||||||
|
Result:=ResOK;
|
||||||
|
end;
|
||||||
|
|
||||||
function TWASIZenFS.GetPrestat(FD: Integer): String;
|
function TWASIZenFS.GetPrestat(FD: Integer): String;
|
||||||
begin
|
begin
|
||||||
if (FD=3) then
|
if (FD=3) then
|
||||||
@ -376,6 +453,8 @@ var
|
|||||||
lFlags : String;
|
lFlags : String;
|
||||||
Rights : NativeInt;
|
Rights : NativeInt;
|
||||||
Reading,Writing : Boolean;
|
Reading,Writing : Boolean;
|
||||||
|
Dir : TZenFSDirentArray;
|
||||||
|
Opts : TZenFSReadDirOptions;
|
||||||
|
|
||||||
Function HasFlag(aFlag : Integer) : Boolean;
|
Function HasFlag(aFlag : Integer) : Boolean;
|
||||||
begin
|
begin
|
||||||
@ -397,6 +476,8 @@ var
|
|||||||
begin
|
begin
|
||||||
if (fdFlags<>0) and (fsFlags<>0) then ;
|
if (fdFlags<>0) and (fsFlags<>0) then ;
|
||||||
lPath:=PrependFD(FD,aPath);
|
lPath:=PrependFD(FD,aPath);
|
||||||
|
if Not HasFlag(__WASI_OFLAGS_DIRECTORY) then
|
||||||
|
begin
|
||||||
Rights:=AsIntNumber(fsRightsBase);
|
Rights:=AsIntNumber(fsRightsBase);
|
||||||
Writing:=HasFlag(__WASI_OFLAGS_CREAT) or HasRight(__WASI_RIGHTS_FD_WRITE);
|
Writing:=HasFlag(__WASI_OFLAGS_CREAT) or HasRight(__WASI_RIGHTS_FD_WRITE);
|
||||||
Reading:=HasRight(__WASI_RIGHTS_FD_READ);
|
Reading:=HasRight(__WASI_RIGHTS_FD_READ);
|
||||||
@ -415,7 +496,16 @@ begin
|
|||||||
begin
|
begin
|
||||||
lFlags:='r';
|
lFlags:='r';
|
||||||
end;
|
end;
|
||||||
|
end;
|
||||||
try
|
try
|
||||||
|
if HasFlag(__WASI_OFLAGS_DIRECTORY) then
|
||||||
|
begin
|
||||||
|
Opts:=TZenFSReadDirOptions.New;
|
||||||
|
Opts.withFileTypes:=True;
|
||||||
|
Dir:=ZenFS.readdirSyncDirent(lpath,Opts);
|
||||||
|
OpenFD:=AllocateDirFD(Dir);
|
||||||
|
end
|
||||||
|
else
|
||||||
OpenFD:=ZenFS.openSync(lPath,lFlags);
|
OpenFD:=ZenFS.openSync(lPath,lFlags);
|
||||||
Result:=resOK;
|
Result:=resOK;
|
||||||
except
|
except
|
||||||
|
@ -162,6 +162,7 @@ Type
|
|||||||
function isSocket() : Boolean;
|
function isSocket() : Boolean;
|
||||||
property path : string read FPath;
|
property path : string read FPath;
|
||||||
end;
|
end;
|
||||||
|
TZenFSDirentArray = Array of TZenFSDirent;
|
||||||
|
|
||||||
TJSDirentCallback = reference to procedure(aDirent : TZenFSDirent);
|
TJSDirentCallback = reference to procedure(aDirent : TZenFSDirent);
|
||||||
TJSDirCloseCallback = reference to procedure;
|
TJSDirCloseCallback = reference to procedure;
|
||||||
@ -741,6 +742,8 @@ Type
|
|||||||
|
|
||||||
Function readdirSync(path : String; options : TZenFSReadDirOptions): TStringDynArray; overload;
|
Function readdirSync(path : String; options : TZenFSReadDirOptions): TStringDynArray; overload;
|
||||||
Function readdirSync(path : String): TStringDynArray; overload;
|
Function readdirSync(path : String): TStringDynArray; overload;
|
||||||
|
Function readdirSyncDirent(path : String; options : TZenFSReadDirOptions): TZenFSDirentArray; external name 'readdirSync';
|
||||||
|
|
||||||
|
|
||||||
Procedure readlink(path : String; options : String; callback : TStringCallBack); overload;
|
Procedure readlink(path : String; options : String; callback : TStringCallBack); overload;
|
||||||
Procedure readlink(path : String; callback : TStringCallBack); overload;
|
Procedure readlink(path : String; callback : TStringCallBack); overload;
|
||||||
|
Loading…
Reference in New Issue
Block a user