Skip to content

Commit

Permalink
Merge branch 'mr/jicquel/14.copy_symbolic_link' into 'master'
Browse files Browse the repository at this point in the history
Implement Copy_Symbolic_Link

See merge request eng/toolchain/gnatcoll-core!54
  • Loading branch information
Jicquel committed Jan 9, 2024
2 parents ab2c15a + 196b3e2 commit b748b85
Show file tree
Hide file tree
Showing 3 changed files with 72 additions and 1 deletion.
20 changes: 20 additions & 0 deletions src/os/gnatcoll-os-fsutil.adb
Original file line number Diff line number Diff line change
Expand Up @@ -348,4 +348,24 @@ package body GNATCOLL.OS.FSUtil is
return True;
end Symbolic_Link_Is_Internal;

------------------------
-- Copy_Symbolic_Link --
------------------------

function Copy_Symbolic_Link
(Src_Path : UTF8.UTF_8_String; Dst_Path : UTF8.UTF_8_String)
return Boolean
is
Target_Path : Unbounded_String;
begin

if not Read_Symbolic_Link (Src_Path, Target_Path) then
return False;
end if;

return Create_Symbolic_Link
(Link_Path => Dst_Path,
Target_Path => To_String (Target_Path));
end Copy_Symbolic_Link;

end GNATCOLL.OS.FSUtil;
5 changes: 5 additions & 0 deletions src/os/gnatcoll-os-fsutil.ads
Original file line number Diff line number Diff line change
Expand Up @@ -119,6 +119,11 @@ package GNATCOLL.OS.FSUtil is
return Boolean;
-- Return the symbolic link target path. Return True on success.

function Copy_Symbolic_Link
(Src_Path : UTF8.UTF_8_String; Dst_Path : UTF8.UTF_8_String)
return Boolean;
-- Copy a symbolic link. Return True on success.

function Symbolic_Link_Is_Internal
(Top_Dir_Path : UTF8.UTF_8_String; Link_Path : UTF8.UTF_8_String)
return Boolean;
Expand Down
48 changes: 47 additions & 1 deletion testsuite/tests/os/fsutil/symlink/test.adb
Original file line number Diff line number Diff line change
Expand Up @@ -347,9 +347,55 @@ begin
end;
Dir.Close (DH);
end;
end;

-- Test symbolic link copy
declare
Target_Name : constant String := "file";
Link_Name : constant String := "file_link";
Link_Copy_Name : constant String := "file_link_copy";
FA : Stat.File_Attributes;
begin

FD := Open (Target_Name, Mode => Write_Mode);
Write (FD, "Input content");
Close (FD);

A.Assert (Check_File_Content (Target_Name, "Input content"));

A.Assert (Create_Symbolic_Link (Link_Name, Target_Name));
A.Assert (Check_File_Content (Link_Name, "Input content"));
FA := Stat.Stat (Link_Name, Follow_Symlinks => False);
A.Assert (Stat.Is_Symbolic_Link (FA));
FA := Stat.Stat (Link_Name, Follow_Symlinks => True);
A.Assert (Stat.Is_File (FA));
A.Assert (not Create_Symbolic_Link (Link_Name, Target_Name));

A.Assert (Copy_Symbolic_Link (Link_Name, Link_Copy_Name));
A.Assert (Check_File_Content (Link_Copy_Name, "Input content"));
FA := Stat.Stat (Link_Copy_Name, Follow_Symlinks => False);
A.Assert (Stat.Is_Symbolic_Link (FA));
FA := Stat.Stat (Link_Copy_Name, Follow_Symlinks => True);
A.Assert (Stat.Is_File (FA));

declare
Target_Path : Unbounded_String;
Target_Path_Copy : Unbounded_String;
begin
A.Assert (Read_Symbolic_Link (Link_Name, Target_Path));
A.Assert (Read_Symbolic_Link (Link_Copy_Name, Target_Path_Copy));
A.Assert (To_String (Target_Path) = Target_Name);
A.Assert (To_String (Target_Path_Copy) = Target_Name);
end;

return A.Report;
A.Assert (Remove_File (Link_Name));
A.Assert (Remove_File (Link_Copy_Name));

-- Ensure that we do not erase the target when removing the link
A.Assert (Check_File_Content (Target_Name, "Input content"));
A.Assert (Remove_File (Target_Name));
end;

return A.Report;

end Test;

0 comments on commit b748b85

Please sign in to comment.