fltk  1.3.5-source
About: FLTK (Fast Light Tool Kit) is a cross-platform C++ GUI toolkit for UNIX/Linux (X11), Microsoft Windows, and MacOS X.
  Fossies Dox: fltk-1.3.5-source.tar.bz2  ("inofficial" and yet experimental doxygen-generated source code documentation)  

scandir_win32.c
Go to the documentation of this file.
1 /*
2  * "$Id$"
3  *
4  * WIN32 scandir function for the Fast Light Tool Kit (FLTK).
5  *
6  * Copyright 1998-2010 by Bill Spitzak and others.
7  *
8  * This library is free software. Distribution and use rights are outlined in
9  * the file "COPYING" which should have been included with this file. If this
10  * file is missing or damaged, see the license at:
11  *
12  * http://www.fltk.org/COPYING.php
13  *
14  * Please report all bugs and problems on the following page:
15  *
16  * http://www.fltk.org/str.php
17  */
18 
19 #ifndef __CYGWIN__
20 /* Emulation of posix scandir() call */
21 #include <FL/fl_utf8.h>
22 #include <FL/filename.H>
23 #include "flstring.h"
24 #include <windows.h>
25 #include <stdlib.h>
26 
27 int fl_scandir(const char *dirname, struct dirent ***namelist,
28  int (*select)(struct dirent *),
29  int (*compar)(struct dirent **, struct dirent **)) {
30  int len;
31  char *findIn, *d, is_dir = 0;
32  WIN32_FIND_DATAW findw;
33  HANDLE h;
34  int nDir = 0, NDir = 0;
35  struct dirent **dir = 0, *selectDir;
36  unsigned long ret;
37 
38  len = (int) strlen(dirname);
39  findIn = (char *)malloc((size_t)(len+10));
40  if (!findIn) return -1;
41  strcpy(findIn, dirname);
42 
43  /* #if defined(__GNUC__) */
44  /* #warning FIXME This probably needs to be MORE UTF8 aware now */
45  /* #endif */
46  for (d = findIn; *d; d++) if (*d=='/') *d='\\';
47  if (len==0) { strcpy(findIn, ".\\*"); }
48  if ((len==2)&&findIn[1]==':'&&isalpha(findIn[0])) { *d++ = '\\'; *d = 0; }
49  if ((len==1)&& (d[-1]=='.')) { strcpy(findIn, ".\\*"); is_dir = 1; }
50  if ((len>0) && (d[-1]=='\\')) { *d++ = '*'; *d = 0; is_dir = 1; }
51  if ((len>1) && (d[-1]=='.') && (d[-2]=='\\')) { d[-1] = '*'; is_dir = 1; }
52  if (!is_dir) { /* this file may still be a directory that we need to list */
53  DWORD attr = GetFileAttributes(findIn);
54  if (attr&FILE_ATTRIBUTE_DIRECTORY)
55  strcpy(d, "\\*");
56  }
57  { /* Create a block to limit the scope while we find the initial "wide" filename */
58  /* unsigned short * wbuf = (unsigned short*)malloc(sizeof(short) *(len + 10)); */
59  /* wbuf[fl_utf2unicode(findIn, strlen(findIn), wbuf)] = 0; */
60  unsigned short *wbuf = NULL;
61  unsigned wlen = fl_utf8toUtf16(findIn, (unsigned) strlen(findIn), NULL, 0); /* Pass NULL to query length */
62  wlen++; /* add a little extra for termination etc. */
63  wbuf = (unsigned short*)malloc(sizeof(unsigned short)*wlen);
64  wlen = fl_utf8toUtf16(findIn, (unsigned) strlen(findIn), wbuf, wlen); /* actually convert the filename */
65  wbuf[wlen] = 0; /* NULL terminate the resultant string */
66  h = FindFirstFileW(wbuf, &findw); /* get a handle to the first filename in the search */
67  free(wbuf); /* release the "wide" buffer before the pointer goes out of scope */
68  }
69  if (h==INVALID_HANDLE_VALUE) {
70  free(findIn);
71  ret = GetLastError();
72  if (ret != ERROR_NO_MORE_FILES) {
73  nDir = -1;
74  }
75  *namelist = dir;
76  return nDir;
77  }
78  do {
79  int l = (int) wcslen(findw.cFileName);
80  int dstlen = l * 5 + 1;
81  selectDir=(struct dirent*)malloc(sizeof(struct dirent)+dstlen);
82 
83  /* l = fl_unicode2utf(findw.cFileName, l, selectDir->d_name); */
84  l = fl_utf8fromwc(selectDir->d_name, dstlen, findw.cFileName, l);
85 
86  selectDir->d_name[l] = 0;
87  if (findw.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) {
88  /* Append a trailing slash to directory names... */
89  strcat(selectDir->d_name, "/");
90  }
91  if (!select || (*select)(selectDir)) {
92  if (nDir==NDir) {
93  struct dirent **tempDir = (struct dirent **)calloc(sizeof(struct dirent*), (size_t)(NDir+33));
94  if (NDir) memcpy(tempDir, dir, sizeof(struct dirent*)*NDir);
95  if (dir) free(dir);
96  dir = tempDir;
97  NDir += 32;
98  }
99  dir[nDir] = selectDir;
100  nDir++;
101  dir[nDir] = 0;
102  } else {
103  free(selectDir);
104  }
105  } while (FindNextFileW(h, &findw));
106  ret = GetLastError();
107  if (ret != ERROR_NO_MORE_FILES) {
108  /* don't return an error code, because the dir list may still be valid
109  up to this point */
110  }
111  FindClose(h);
112 
113  free (findIn);
114 
115  if (compar) qsort(dir, (size_t)nDir, sizeof(*dir),
116  (int(*)(const void*, const void*))compar);
117 
118  *namelist = dir;
119  return nDir;
120 }
121 
122 #endif
123 
124 /*
125  * End of "$Id$".
126  */
fl_scandir
int fl_scandir(const char *dirname, struct dirent ***namelist, int(*select)(struct dirent *), int(*compar)(struct dirent **, struct dirent **))
Definition: scandir_win32.c:27
fl_utf8toUtf16
unsigned fl_utf8toUtf16(const char *src, unsigned srclen, unsigned short *dst, unsigned dstlen)
Definition: fl_utf.c:432
filename.H
free
void free()
NULL
#define NULL
Definition: forms.H:34
fl_utf8fromwc
unsigned fl_utf8fromwc(char *dst, unsigned dstlen, const wchar_t *src, unsigned srclen)
Definition: fl_utf.c:617
is_dir
static int is_dir(const char *dirname)
Definition: ExternalCodeEditor_UNIX.cxx:38
dir
static int dir
Definition: fl_draw_image.cxx:67
fl_utf8.h
header for Unicode and UTF-8 character handling
select
void select(Fl_Type *, int)
Definition: Fl_Type.cxx:240
calloc
voidp calloc()
malloc
voidp malloc()
flstring.h
dirent
#define dirent
Definition: numericsort.c:31