The Ada.Directories directory search function is changed so the contents of the directory is now read in Start_Search instead of in Get_Next_Entry. Start_Search now stores the result of the directory search in the search object, with Get_Next_Entry returning results from the search object. This differs from the prior implementation where Get_Next_Entry would query the directory directly for the next item using the POSIX readdir function.
The problem with building Get_Next_Entry around the readdir function is POSIX does not specify the behavior of readdir when files are added or removed from the directory being read. For example: on most systems, deleting files from the folder being read does not impact readdir. However, some systems, like RTEMS and HFS+ volumes on macOS, will return NULL instead of the next item in the directory if the current item returned by readdir is deleted. To avoid this issue, the contents of the directory is read in Start_Search and the user is given a copy of these results. Consequently, any subsequent modification to the directory does not affect the ability to iterate through the results. This approach is the same taken by the popular fts C functions. Tested on x86_64-pc-linux-gnu, committed on trunk gcc/ada/ * libgnat/a-direct.adb (Search_Data): Remove type. (Directory_Vectors): New package instantiation. (Search_State): New type. (Fetch_Next_Entry): Remove. (Close): Remove. (Finalize): Rewritten. (Full_Name): Ditto. (Get_Next_Entry): Return next entry from Search results vector rather than querying the directory directly using readdir. (Kind): Rewritten. (Modification_Time): Rewritten. (More_Entries): Use Search state cursor to determine if more entries are available for users to read. (Simple_Name): Rewritten. (Size): Rewritten. (Start_Search_Internal): Rewritten to load the contents of the directory that matches the pattern and filter into the search object. * libgnat/a-direct.ads (Search_Type): New type. (Search_Ptr): Ditto. (Directory_Entry_Type): Rewritten to support new Start_Search procedure. * libgnat/s-filatt.ads (File_Length_Attr): New function.
patch.diff.gz
Description: application/gzip