Example #1
0
rdirectory *ssh_read_directory(const char *path)
{
  char *p = ftp_path_absolute(path);
  stripslash(p);

  sftp_dir dir = sftp_opendir(ftp->sftp_session, p);
  if (!dir)
  {
    free(p);
    return 0;
  }

  ftp_trace("*** start parsing directory listing ***\n");
  rdirectory* rdir = rdir_create();
  sftp_attributes attrib = NULL;
  while ((attrib = sftp_readdir(ftp->sftp_session, dir)) != NULL)
  {
    ftp_trace("%s\n", attrib->longname);

    rfile* rf = rfile_create();
    rf->perm = perm2string(attrib->permissions);

    rf->nhl = 0; // atoi(e);
    if (attrib->owner)
      rf->owner = xstrdup(attrib->owner);
    if (attrib->group)
      rf->group = xstrdup(attrib->group);

    if (asprintf(&rf->path, "%s/%s", p, attrib->name) == -1)
    {
      ftp_err(_("Failed to allocate memory.\n"));
      sftp_closedir(dir);
      free(p);
      rdir_destroy(rdir);
      rfile_destroy(rf);
    }
    rf->mtime = attrib->mtime;
    rf->date = time_to_string(rf->mtime);
    rf->size = attrib->size;
    rfile_parse_colors(rf);

    rf->link = NULL;
    if (rislink(rf) && ftp->ssh_version > 2)
      rf->link = sftp_readlink(ftp->sftp_session, rf->path);

    list_additem(rdir->files, (void *)rf);
    sftp_attributes_free(attrib);
  }
  ftp_trace("*** end parsing directory listing ***\n");

  if (!sftp_dir_eof(dir))
  {
    ftp_err(_("Couldn't list directory: %s\n"), ssh_get_error(ftp->session));
    sftp_closedir(dir);
    free(p);
    rdir_destroy(rdir);
    return NULL;
  }

  sftp_closedir(dir);
  rdir->path = p;
  ftp_trace("added directory '%s' to cache\n", p);
  list_additem(ftp->cache, rdir);

  return rdir;
}
Example #2
0
rdirectory *ftp_read_directory(const char *path)
{
    FILE *fp = 0;
    rdirectory *rdir;
    bool is_curdir = false;
    bool _failed = false;
    char *dir;
    bool is_mlsd = false;

#ifdef HAVE_LIBSSH
    if(ftp->session)
        return ssh_read_directory(path);
#endif

    dir = ftp_path_absolute(path);
    stripslash(dir);

    is_curdir = (strcmp(dir, ftp->curdir) == 0);

    if((fp = tmpfile()) == NULL) {	/* can't create a tmpfile */
	    ftp_err("Unable to create temp file: %s\n", strerror(errno));
            free(dir);
            return 0;
    }

    /* we do a "CWD" before the listing, because: we want a listing of
     *  the directory contents, not the directory itself, and some
     *  servers misunderstand this. If the target is a link to a
     *  directory, we have to do this.
     */
    if(!is_curdir) {
        ftp_cmd("CWD %s", dir);
        if(ftp->code != ctComplete)
            goto failed;
    }

    if(ftp->has_mlsd_command) {
        is_mlsd = true;
#if 0
        /* PureFTPd (1.0.11) doesn't recognize directory arguments
         * with spaces, not even quoted, it just chops the argument
         * string after the first space, duh... so we have to CWD to
         * the directory...
         */
        char *asdf;
        asprintf(&asdf, "%s/", dir);
        /* Hack to get around issue in PureFTPd (up to version 0.98.2):
         * doing a 'MLSD link-to-dir' on PureFTPd closes the control
         * connection, however, 'MLSD link-to-dir/' works fine.
         */
        _failed = (ftp_list("MLSD", asdf, fp) != 0);
        free(asdf);
#else
        _failed = (ftp_list("MLSD", 0, fp) != 0);
#endif
        if(_failed && ftp->code == ctError)
            ftp->has_mlsd_command = false;
    }
    if(!ftp->has_mlsd_command) {
        _failed = (ftp_list("LIST", 0, fp) != 0);
        is_mlsd = false;
    }

    if(!is_curdir)
        ftp_cmd("CWD %s", ftp->curdir);

    if(_failed)
        goto failed;

    rewind(fp);

    rdir = rdir_create();
    if(rdir_parse(rdir, fp, dir, is_mlsd) != 0) {
        rdir_destroy(rdir);
        goto failed;
    }

    fclose(fp);
    ftp_trace("added directory '%s' to cache\n", dir);
    list_additem(ftp->cache, rdir);
    free(dir);
    return rdir;

  failed: /* forgive me father, for I have goto'ed */
    if (fp)
	    fclose(fp);
    free(dir);
    return 0;
}
Example #3
0
rdirectory *ssh_read_directory(const char *path)
{
	rdirectory *rdir;
	int i;
	SFTP_DIRENT **dir;
	char *p = ftp_path_absolute(path);
	stripslash(p);

	if(ssh_readdir(p, &dir) != 0) {
		free(p);
		return 0;
	}

	rdir = rdir_create();

	ftp_trace("*** start parsing directory listing ***\n");

	for(i = 0; dir[i]; i++) {
		rfile *rf;
		char *e, *cf = dir[i]->longname;

		ftp_trace("%s\n", dir[i]->longname);

		rf = rfile_create();

		rf->perm = perm2string(dir[i]->a.perm);

		e = strqsep(&cf, ' ');  /* skip permissions */
		e = strqsep(&cf, ' ');  /* nhl? */
/*		if(ftp->ssh_version > 2) {*/
			rf->nhl = atoi(e);
/*		} else*/
/*			rf->nhl = 0;*/
#if 1
		e = strqsep(&cf, ' ');
		rf->owner = xstrdup(e);
		e = strqsep(&cf, ' ');
		rf->group = xstrdup(e);
#else
		asprintf(&rf->owner, "%d", dir[i]->a.uid);
		asprintf(&rf->group, "%d", dir[i]->a.gid);
#endif

		asprintf(&rf->path, "%s/%s", p, dir[i]->filename);
		rf->mtime = dir[i]->a.mtime;
		if(rf->mtime == 0) {
			char *m, *d, *y;
			while(e && month_number(e) == -1)
				e = strqsep(&cf, ' ');
			if(e) {
				m = e;
				d = strqsep(&cf, ' ');
				y = strqsep(&cf, ' ');
				ftp_trace("parsing time: m:%s d:%s y:%s\n", m, d, y);
				rfile_parse_time(rf, m, d, y);
			}
		}
		rf->date = time_to_string(rf->mtime);
		rf->size = dir[i]->a.size;
		rfile_parse_colors(rf);

		rf->link = 0;
		if(rislink(rf) && ftp->ssh_version > 2)
			rf->link = ssh_readlink(rf->path);

		list_additem(rdir->files, (void *)rf);
	}
	ftp_trace("*** end parsing directory listing ***\n");

	ssh_free_dirents(dir);

	rdir->path = p;

	ftp_trace("added directory '%s' to cache\n", p);
	list_additem(ftp->cache, rdir);

	return rdir;
}