cwd =  getcwd (NULL, 0);
cwd =  __getcwd (NULL, 0);
ftw_startup (const char *dir, int is_nftw, void *func, int descriptors,	     int flags){  struct ftw_data data;  struct STAT st;  int result = 0;  int save_err;  char *cwd = NULL;  char *cp;  /* First make sure the parameters are reasonable.  */  if (dir[0] == '\0')    {      __set_errno (ENOTDIR);      return -1;    }  data.maxdir = descriptors < 1 ? 1 : descriptors;  data.actdir = 0;  data.dirstreams = (struct dir_data **) alloca (data.maxdir						 * sizeof (struct dir_data *));  memset (data.dirstreams, '\0', data.maxdir * sizeof (struct dir_data *));#ifdef PATH_MAX  data.dirbufsize = MAX (2 * strlen (dir), PATH_MAX);#else  data.dirbufsize = 2 * strlen (dir);#endif  data.dirbuf = (char *) malloc (data.dirbufsize);  if (data.dirbuf == NULL)    return -1;  cp = __stpcpy (data.dirbuf, dir);  /* Strip trailing slashes.  */  while (cp > data.dirbuf + 1 && cp[-1] == '/')    --cp;  *cp = '\0';  data.ftw.level = 0;  /* Find basename.  */  while (cp > data.dirbuf && cp[-1] != '/')    --cp;  data.ftw.base = cp - data.dirbuf;  data.flags = flags;  /* This assignment might seem to be strange but it is what we want.     The trick is that the first three arguments to the `ftw' and     `nftw' callback functions are equal.  Therefore we can call in     every case the callback using the format of the `nftw' version     and get the correct result since the stack layout for a function     call in C allows this.  */  data.func = (NFTW_FUNC_T) func;  /* Since we internally use the complete set of FTW_* values we need     to reduce the value range before calling a `ftw' callback.  */  data.cvt_arr = is_nftw ? nftw_arr : ftw_arr;  /* No object known so far.  */  data.known_objects = NULL;  /* Now go to the directory containing the initial file/directory.  */  if ((flags & FTW_CHDIR) && data.ftw.base > 0)    {      /* GNU extension ahead.  */      cwd =  getcwd (NULL, 0);      if (cwd == NULL)	result = -1;      else	{	  /* Change to the directory the file is in.  In data.dirbuf	     we have a writable copy of the file name.  Just NUL	     terminate it for now and change the directory.  */	  if (data.ftw.base == 1)	    /* I.e., the file is in the root directory.  */	    result = chdir ("/");	  else	    {	      char ch = data.dirbuf[data.ftw.base - 1];	      data.dirbuf[data.ftw.base - 1] = '\0';	      result = chdir (data.dirbuf);	      data.dirbuf[data.ftw.base - 1] = ch;	    }	}    }  /* Get stat info for start directory.  */  if (result == 0)    if (((flags & FTW_PHYS)	 ? LXSTAT (_STAT_VER, data.dirbuf, &st)	 : XSTAT (_STAT_VER, data.dirbuf, &st)) < 0)      {	if (errno == EACCES)	  result = (*data.func) (data.dirbuf, &st, FTW_NS, &data.ftw);	else if (!(flags & FTW_PHYS)		 && errno == ENOENT		 && LXSTAT (_STAT_VER, dir, &st) == 0		 && S_ISLNK (st.st_mode))	  result = (*data.func) (data.dirbuf, &st, data.cvt_arr[FTW_SLN],				 &data.ftw);	else	  /* No need to call the callback since we cannot say anything	     about the object.  */	  result = -1;      }    else      {	if (S_ISDIR (st.st_mode))	  {	    /* Remember the device of the initial directory in case	       FTW_MOUNT is given.  */	    data.dev = st.st_dev;	    /* We know this directory now.  */	    if (!(flags & FTW_PHYS))	      result = add_object (&data, &st);	    if (result == 0)	      result = ftw_dir (&data, &st);	  }	else	  {	    int flag = S_ISLNK (st.st_mode) ? FTW_SL : FTW_F;	    result = (*data.func) (data.dirbuf, &st, data.cvt_arr[flag],				   &data.ftw);	  }      }  /* Return to the start directory (if necessary).  */  if (cwd != NULL)    {      int save_err = errno;      chdir (cwd);      free (cwd);      __set_errno (save_err);    }  /* Free all memory.  */  save_err = errno;  __tdestroy (data.known_objects, free);  free (data.dirbuf);  __set_errno (save_err);  return result;}