dir_linux.odin 1.3 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970
  1. package os
  2. import "core:strings"
  3. import "core:mem"
  4. read_dir :: proc(fd: Handle, n: int, allocator := context.allocator) -> (fi: []File_Info, err: Errno) {
  5. dirp: Dir;
  6. dirp, err = _fdopendir(fd);
  7. if err != ERROR_NONE {
  8. return;
  9. }
  10. defer _closedir(dirp);
  11. dirpath: string;
  12. dirpath, err = absolute_path_from_handle(fd);
  13. if err != ERROR_NONE {
  14. return;
  15. }
  16. defer delete(dirpath);
  17. n := n;
  18. size := n;
  19. if n <= 0 {
  20. n = -1;
  21. size = 100;
  22. }
  23. dfi := make([dynamic]File_Info, 0, size, allocator);
  24. for {
  25. entry: Dirent;
  26. end_of_stream: bool;
  27. entry, err, end_of_stream = _readdir(dirp);
  28. if err != ERROR_NONE {
  29. for fi_ in dfi {
  30. file_info_delete(fi_, allocator);
  31. }
  32. delete(dfi);
  33. return;
  34. } else if end_of_stream {
  35. break;
  36. }
  37. fi_: File_Info;
  38. filename := cast(string)(transmute(cstring)mem.Raw_Cstring{ data = &entry.name[0] });
  39. if filename == "." || filename == ".." {
  40. continue;
  41. }
  42. fullpath := strings.join( []string{ dirpath, filename }, "/", context.temp_allocator);
  43. defer delete(fullpath, context.temp_allocator);
  44. fi_, err = stat(fullpath, allocator);
  45. if err != ERROR_NONE {
  46. for fi__ in dfi {
  47. file_info_delete(fi__, allocator);
  48. }
  49. delete(dfi);
  50. return;
  51. }
  52. append(&dfi, fi_);
  53. }
  54. return dfi[:], ERROR_NONE;
  55. }