scandir.c 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165
  1. /*
  2. * Copyright (c) 1983-2013 Martin Atkins, Richard Dobson and Composers Desktop Project Ltd
  3. * http://people.bath.ac.uk/masrwd
  4. * http://www.composersdesktop.com
  5. *
  6. This file is part of the CDP System.
  7. The CDP System is free software; you can redistribute it
  8. and/or modify it under the terms of the GNU Lesser General Public
  9. License as published by the Free Software Foundation; either
  10. version 2.1 of the License, or (at your option) any later version.
  11. The CDP System is distributed in the hope that it will be useful,
  12. but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  14. GNU Lesser General Public License for more details.
  15. You should have received a copy of the GNU Lesser General Public
  16. License along with the CDP System; if not, write to the Free Software
  17. Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
  18. 02111-1307 USA
  19. *
  20. */
  21. /*
  22. * portable sfsys - NT version of scandir
  23. */
  24. static char *rcsid = "$Id: scandir.c%v 1.2 1994/10/31 15:56:04 martin Exp $";
  25. /*
  26. * $Log: scandir.c%v $
  27. * Revision 1.2 1994/10/31 15:56:04 martin
  28. * Fix local copy of rcsid string
  29. *
  30. * Revision 1.1 1994/10/31 15:46:36 martin
  31. * Initial revision
  32. *
  33. */
  34. #include <stdlib.h>
  35. #include <string.h>
  36. #ifdef _WIN32
  37. #include <windows.h>
  38. #endif
  39. #include "scandir.h"
  40. static char *scandir_h_rcsid = SCANDIR_H_RCSID;
  41. #define ARRAY_INCR (10)
  42. #ifdef _WIN32
  43. int
  44. scandir(const char *dir,
  45. struct dirent ***namelist,
  46. int (*selfn)(const struct dirent *d),
  47. int (*srtfn)(const struct dirent * const *d1,
  48. const struct dirent * const *d2))
  49. {
  50. struct dirent **names = (struct dirent **)malloc(1);
  51. int names_size = 0;
  52. int names_seen = 0;
  53. HANDLE shndl;
  54. struct dirent f;
  55. WIN32_FIND_DATA filedata;
  56. char pattern[_MAX_PATH];
  57. if(names == 0)
  58. return -1;
  59. strcpy(pattern, dir);
  60. strcat(pattern, "\\*.*");
  61. if((shndl = FindFirstFile(pattern, &filedata)) == INVALID_HANDLE_VALUE) {
  62. if(GetLastError() == ERROR_FILE_NOT_FOUND)
  63. return 0;
  64. return -1;
  65. }
  66. for(;;) {
  67. strcpy(f.d_name, filedata.cFileName);
  68. if(selfn(&f)) {
  69. if(names_seen >= names_size) {
  70. names_size += ARRAY_INCR;
  71. if((names = (struct dirent **) realloc(names, names_size*sizeof(struct dirent *))) == 0) {
  72. FindClose(shndl);
  73. return -1;
  74. }
  75. }
  76. if((names[names_seen] = (struct dirent *)malloc(sizeof(struct dirent))) == 0) {
  77. FindClose(shndl);
  78. return -1;
  79. }
  80. *names[names_seen++] = f;
  81. }
  82. if(!FindNextFile(shndl, &filedata)) {
  83. if(GetLastError() != ERROR_NO_MORE_FILES) {
  84. FindClose(shndl);
  85. return -1;
  86. }
  87. break;
  88. }
  89. }
  90. FindClose(shndl);
  91. qsort(names, names_seen, sizeof(struct dirent *),
  92. (int (*)(const void *, const void *))srtfn);
  93. *namelist = names;
  94. return names_seen;
  95. }
  96. #endif
  97. #ifdef unix
  98. int
  99. scandir(const char *dir,
  100. struct dirent ***namelist,
  101. int (*selfn)(const struct dirent *d),
  102. int (*srtfn)(const struct dirent * const *d1,
  103. const struct dirent * const *d2))
  104. {
  105. DIR *dirfd;
  106. struct dirent *f;
  107. struct dirent **names = (struct dirent **)malloc(1);
  108. int names_size = 0;
  109. int names_seen = 0;
  110. if(names == 0)
  111. return -1;
  112. if((dirfd = opendir(".")) == NULL)
  113. return -1;
  114. while((f = readdir(dirfd)) != NULL) {
  115. if(!selfn(f))
  116. continue;
  117. if(names_seen >= names_size) {
  118. names_size += ARRAY_INCR;
  119. if((names = realloc(names, names_size*sizeof(struct dirent *))) == 0) {
  120. closedir(dirfd);
  121. return -1;
  122. }
  123. }
  124. if((names[names_seen] = (struct dirent *)malloc(sizeof(struct dirent))) == 0) {
  125. closedir(dirfd);
  126. return -1;
  127. }
  128. *names[names_seen++] = *f;
  129. }
  130. closedir(dirfd);
  131. qsort(names, names_seen, sizeof(struct dirent *),
  132. (int (*)(const void *, const void *))srtfn);
  133. *namelist = names;
  134. return names_seen;
  135. }
  136. #endif
  137. int
  138. alphasort(const struct dirent * const *d1,
  139. const struct dirent * const *d2)
  140. {
  141. return strcmp((*d1)->d_name, (*d2)->d_name);
  142. }