Jump to content
Chester Wilson

DeleteFile Compilation Message

Recommended Posts

Can anyone please tell me why one of the two occurrences of DeleteFile in a programme produces the message "In line function 'DeleteFile' has not been expanded because unit 'Posix.Unistd' is not specified in USES list"?

And does it matter?

 

Share this post


Link to post
Posted (edited)

It means the function in question has been marked with the 'inline' specifier, but the function uses code from the Posix.Unistd unit, and that unit is not in a 'uses' clause in scope of the code that is calling the function, so the function can't be inlined at the call site.

 

You posted this in a VCL forum, but the VCL's version of DeleteFile() does not use any Posix units, so you must be using FMX's version of DeleteFile() instead.

Edited by Remy Lebeau

Share this post


Link to post

It is.

C:\Program Files (x86)\Embarcadero\Studio\20.0\source\rtl\sys\System.SysUtils.pas(1638): function DeleteFile(const FileName: string): Boolean; {$IFDEF POSIX}inline;{$ENDIF}

 

Share this post


Link to post

Or... add Posix.Unistd to the uses clause in the file where you use DeleteFile.

 

 

Share this post


Link to post
Posted (edited)
20 hours ago, David Heffernan said:

Curious, but why would here be VCL and FMX versions of Delete File? Isn't it an RTL function? 

Yes, it is an RTL function, but it has different implementations for different platforms, and they want the POSIX implementation to be inlined, as it is just a 1-line call to the POSIX unlink() function, so ideal for inlining:

function DeleteFile(const FileName: string): Boolean;
...
{$IFDEF POSIX}
var
  M: TMarshaller;
begin
  Result := unlink(M.AsAnsi(FileName, CP_UTF8).ToPointer) <> -1;
end;
{$ENDIF POSIX}

The Windows implementation used to be a 1-line call as well, to the Win32 DeleteFile() function, and thus was inlined, too:

function DeleteFile(const FileName: string): Boolean;
{$IFDEF MSWINDOWS}
begin
  Result := Winapi.Windows.DeleteFile(PChar(FileName));
end;
{$ENDIF MSWINDOWS}

But, it is no longer inlined.  In XE, new logic was added to make SysUtils.DeleteFile() call the Win32 GetFileAttributes() and RemoveDirectory() functions when deleting a symbolic link to a directory (why that was added, I did not know):

function DeleteFile(const FileName: string): Boolean;
{$IFDEF MSWINDOWS}
var
  Flags, LastError: Cardinal;
begin
  Result := Winapi.Windows.DeleteFile(PChar(FileName));

  if not Result then
  begin
    LastError := GetLastError;
    Flags := GetFileAttributes(PChar(FileName));

    if (Flags <> INVALID_FILE_ATTRIBUTES) and (faSymLink and Flags <> 0) and
      (faDirectory and Flags <> 0) then
    begin
      Result := RemoveDirectory(PChar(FileName));
      Exit;
    end;

    SetLastError(LastError);
  end;
end;
{$ENDIF MSWINDOWS}

As such, the inline keyword for that implementation was removed in XE2.

Edited by Remy Lebeau

Share this post


Link to post

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

×