Logo Search packages:      
Sourcecode: make version File versions

dirent.c

#include <sys/types.h>
#include <sys/stat.h>
#include <errno.h>
#include <string.h>
#include <stdlib.h>
#include "dirent.h"


DIR*
opendir(const char* pDirName)
{
      struct stat sb;
      DIR*  pDir;
      char* pEndDirName;
      int   nBufferLen;

      /* sanity checks */
      if (!pDirName) {
            errno = EINVAL;
            return NULL;
      }
      if (stat(pDirName, &sb) != 0) {
            errno = ENOENT;
            return NULL;
      }
      if ((sb.st_mode & S_IFMT) != S_IFDIR) {
            errno = ENOTDIR;
            return NULL;
      }

      /* allocate a DIR structure to return */
      pDir = (DIR *) malloc(sizeof (DIR));

      if (!pDir)
            return NULL;

      /* input directory name length */
      nBufferLen = strlen(pDirName);

      /* copy input directory name to DIR buffer */
      strcpy(pDir->dir_pDirectoryName, pDirName);

      /* point to end of the copied directory name */
      pEndDirName = &pDir->dir_pDirectoryName[nBufferLen - 1];

      /* if directory name did not end in '/' or '\', add '/' */
      if ((*pEndDirName != '/') && (*pEndDirName != '\\')) {
            pEndDirName++;
            *pEndDirName = '/';
      }

      /* now append the wildcard character to the buffer */
      pEndDirName++;
      *pEndDirName = '*';
      pEndDirName++;
      *pEndDirName = '\0';

      /* other values defaulted */
      pDir->dir_nNumFiles = 0;
      pDir->dir_hDirHandle = INVALID_HANDLE_VALUE;    
      pDir->dir_ulCookie = __DIRENT_COOKIE;

      return pDir;
}

void
closedir(DIR *pDir)
{
      /* got a valid pointer? */
      if (!pDir) {
            errno = EINVAL;
            return;
      }

      /* sanity check that this is a DIR pointer */
      if (pDir->dir_ulCookie != __DIRENT_COOKIE) {
            errno = EINVAL;
            return;
      }

      /* close the WINDOWS32 directory handle */
      if (pDir->dir_hDirHandle != INVALID_HANDLE_VALUE)
            FindClose(pDir->dir_hDirHandle);

      free(pDir);

      return;
}

struct dirent *
readdir(DIR* pDir)
{
      WIN32_FIND_DATA wfdFindData;

      if (!pDir) {
            errno = EINVAL;
            return NULL;
      }

      /* sanity check that this is a DIR pointer */
      if (pDir->dir_ulCookie != __DIRENT_COOKIE) {
            errno = EINVAL;
            return NULL;
      }

      if (pDir->dir_nNumFiles == 0) {
            pDir->dir_hDirHandle = FindFirstFile(pDir->dir_pDirectoryName, &wfdFindData);
            if (pDir->dir_hDirHandle == INVALID_HANDLE_VALUE)
                  return NULL;
      } else if (!FindNextFile(pDir->dir_hDirHandle, &wfdFindData))
                  return NULL;

      /* bump count for next call to readdir() or telldir() */
      pDir->dir_nNumFiles++;

      /* fill in struct dirent values */
      pDir->dir_sdReturn.d_ino = -1;
      strcpy(pDir->dir_sdReturn.d_name, wfdFindData.cFileName);

      return &pDir->dir_sdReturn;
}

void
rewinddir(DIR* pDir)
{
      if (!pDir) {
            errno = EINVAL;
            return;
      }

      /* sanity check that this is a DIR pointer */
      if (pDir->dir_ulCookie != __DIRENT_COOKIE) {
            errno = EINVAL;
            return;
      }

      /* close the WINDOWS32 directory handle */
      if (pDir->dir_hDirHandle != INVALID_HANDLE_VALUE)
            if (!FindClose(pDir->dir_hDirHandle))
                  errno = EBADF;

      /* reset members which control readdir() */
      pDir->dir_hDirHandle = INVALID_HANDLE_VALUE;
      pDir->dir_nNumFiles = 0;

      return;
}

int
telldir(DIR* pDir)
{
      if (!pDir) {
            errno = EINVAL;
            return -1;
      }

      /* sanity check that this is a DIR pointer */
      if (pDir->dir_ulCookie != __DIRENT_COOKIE) {
            errno = EINVAL;
            return -1;
      }

      /* return number of times readdir() called */
      return pDir->dir_nNumFiles;
}

void
seekdir(DIR* pDir, long nPosition)
{
      if (!pDir)
            return;

      /* sanity check that this is a DIR pointer */
      if (pDir->dir_ulCookie != __DIRENT_COOKIE)
            return;

      /* go back to beginning of directory */
      rewinddir(pDir);

      /* loop until we have found position we care about */
      for (--nPosition; nPosition && readdir(pDir); nPosition--);

      /* flag invalid nPosition value */
      if (nPosition)
            errno = EINVAL;

      return;
}

Generated by  Doxygen 1.6.0   Back to index