LCOV - code coverage report
Current view: directory - src/shared/platform/osx - nacl_host_dir.c (source / functions) Found Hit Coverage
Test: coverage.lcov Lines: 55 46 83.6 %
Date: 2012-02-16 Functions: 0 0 -

       1                 : /*
       2                 :  * Copyright 2008 The Native Client Authors. All rights reserved.
       3                 :  * Use of this source code is governed by a BSD-style license that can
       4                 :  * be found in the LICENSE file.
       5                 :  */
       6                 : 
       7                 : /*
       8                 :  * NaCl Service Runtime.  Directory descriptor / Handle abstraction.
       9                 :  *
      10                 :  * Note that we avoid using the thread-specific data / thread local
      11                 :  * storage access to the "errno" variable, and instead use the raw
      12                 :  * system call return interface of small negative numbers as errors.
      13                 :  */
      14                 : 
      15                 : #include <stddef.h>
      16                 : #include <stdint.h>
      17                 : #include <string.h>
      18                 : #include <sys/types.h>
      19                 : #include <sys/stat.h>
      20                 : #include <fcntl.h>
      21                 : #include <errno.h>
      22                 : #include <sys/mman.h>
      23                 : #include <unistd.h>
      24                 : #include <dirent.h>
      25                 : 
      26                 : #include "native_client/src/include/nacl_platform.h"
      27                 : 
      28                 : #include "native_client/src/shared/platform/nacl_host_desc.h"
      29                 : #include "native_client/src/shared/platform/nacl_host_dir.h"
      30                 : #include "native_client/src/shared/platform/nacl_log.h"
      31                 : #include "native_client/src/shared/platform/nacl_sync.h"
      32                 : #include "native_client/src/shared/platform/nacl_sync_checked.h"
      33                 : 
      34                 : #include "native_client/src/trusted/service_runtime/include/sys/dirent.h"
      35                 : #include "native_client/src/trusted/service_runtime/include/sys/errno.h"
      36                 : #include "native_client/src/trusted/service_runtime/include/sys/fcntl.h"
      37                 : #include "native_client/src/trusted/service_runtime/include/sys/mman.h"
      38                 : #include "native_client/src/trusted/service_runtime/include/sys/stat.h"
      39                 : 
      40                 : 
      41                 : #ifndef SSIZE_T_MAX
      42                 : # define SSIZE_T_MAX ((ssize_t) ((~(size_t) 0) >> 1))
      43                 : #endif
      44                 : 
      45                 : 
      46                 : int NaClHostDirOpen(struct NaClHostDir  *d,
      47               3 :                     char                *path) {
      48                 :   DIR  *dirp;
      49                 : 
      50               3 :   NaClLog(3, "NaClHostDirOpen(0x%08"NACL_PRIxPTR", %s)\n", (uintptr_t) d, path);
      51               3 :   if (NULL == d) {
      52               0 :     NaClLog(LOG_FATAL, "NaClHostDirOpen: 'this' is NULL\n");
      53                 :   }
      54                 : 
      55               3 :   if (!NaClMutexCtor(&d->mu)) {
      56               0 :     NaClLog(LOG_ERROR,
      57                 :             "NaClHostDirOpen: could not initialize mutex\n");
      58               0 :     return -NACL_ABI_ENOMEM;
      59                 :   }
      60                 : 
      61               3 :   NaClLog(3, "NaClHostDirOpen: invoking POSIX opendir(%s)\n", path);
      62               3 :   dirp = opendir(path);
      63               3 :   NaClLog(3, "NaClHostDirOpen: got DIR* 0x%08"NACL_PRIxPTR"\n",
      64                 :           (uintptr_t) dirp);
      65               3 :   if (NULL == dirp) {
      66               0 :     NaClLog(LOG_ERROR,
      67                 :             "NaClHostDirOpen: open returned NULL, errno %d\n", errno);
      68               0 :     return -NaClXlateErrno(errno);
      69                 :   }
      70               3 :   d->dirp = dirp;
      71               3 :   d->dp = readdir(d->dirp);
      72               3 :   d->off = 0;
      73               3 :   NaClLog(3, "NaClHostDirOpen: success.\n");
      74               3 :   return 0;
      75                 : }
      76                 : 
      77                 : ssize_t NaClHostDirGetdents(struct NaClHostDir  *d,
      78                 :                             void                *buf,
      79              14 :                             size_t              len) {
      80                 :   struct nacl_abi_dirent *p;
      81                 :   int                    rec_length;
      82                 :   ssize_t                i;
      83                 : 
      84              14 :   if (NULL == d) {
      85               0 :     NaClLog(LOG_FATAL, "NaClHostDirGetdents: 'this' is NULL\n");
      86                 :   }
      87              14 :   NaClLog(3, "NaClHostDirGetdents(0x%08"NACL_PRIxPTR", %"NACL_PRIuS"):\n",
      88                 :           (uintptr_t) buf, len);
      89                 : 
      90              14 :   NaClXMutexLock(&d->mu);
      91                 : 
      92              14 :   i = 0;
      93              37 :   while ((size_t) i < len) {
      94              17 :     if (NULL == d->dp) {
      95               2 :       goto done;
      96                 :     }
      97              15 :     if (i > SSIZE_T_MAX - d->dp->d_reclen) {
      98               0 :       NaClLog(LOG_FATAL, "NaClHostDirGetdents: buffer impossibly large\n");
      99                 :     }
     100              15 :     if ((size_t) i + d->dp->d_reclen > len) {
     101               6 :       if (0 == i) {
     102               5 :         i = (size_t) -NACL_ABI_EINVAL;
     103                 :       }
     104               6 :       goto done;
     105                 :     }
     106               9 :     p = (struct nacl_abi_dirent *) (((char *) buf) + i);
     107               9 :     p->nacl_abi_d_ino = 0x6c43614e;
     108               9 :     p->nacl_abi_d_off = ++d->off;
     109               9 :     memcpy(p->nacl_abi_d_name,
     110                 :            d->dp->d_name,
     111                 :            d->dp->d_namlen + 1);
     112                 :     /*
     113                 :      * Newlib expects entries to start on 0mod4 boundaries.
     114                 :      * Round reclen to the next multiple of four.
     115                 :      */
     116               9 :     rec_length = (offsetof(struct nacl_abi_dirent, nacl_abi_d_name) +
     117                 :                   (d->dp->d_namlen + 1 + 3)) & ~3;
     118                 :     /*
     119                 :      * We cast to a volatile pointer so that the compiler won't ever
     120                 :      * pick up the rec_length value from that user-accessible memory
     121                 :      * location, rather than actually using the value in a register or
     122                 :      * in the local frame.
     123                 :      */
     124               9 :     ((volatile struct nacl_abi_dirent *) p)->nacl_abi_d_reclen = rec_length;
     125               9 :     if ((size_t) i > SIZE_T_MAX - rec_length) {
     126               0 :       NaClLog(LOG_FATAL, "NaClHostDirGetdents: buffer offset overflow\n");
     127                 :     }
     128               9 :     i += rec_length;
     129               9 :     d->dp = readdir(d->dirp);
     130                 :   }
     131              14 :  done:
     132              14 :   NaClXMutexUnlock(&d->mu);
     133              14 :   return (ssize_t) i;
     134                 : }
     135                 : 
     136               2 : int NaClHostDirClose(struct NaClHostDir *d) {
     137                 :   int retval;
     138                 : 
     139               2 :   if (NULL == d) {
     140               0 :     NaClLog(LOG_FATAL, "NaClHostDirClose: 'this' is NULL\n");
     141                 :   }
     142               2 :   NaClLog(3, "NaClHostDirClose(0x%08"NACL_PRIxPTR")\n", (uintptr_t) d->dirp);
     143               2 :   retval = closedir(d->dirp);
     144               2 :   if (-1 != retval) {
     145               2 :     d->dirp = NULL;
     146                 :   }
     147               2 :   NaClMutexDtor(&d->mu);
     148               2 :   return (-1 == retval) ? -NaClXlateErrno(errno) : retval;
     149                 : }

Generated by: LCOV version 1.7