⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 rfile.c

📁 UNIX环境下命令行FTP/SFTP工具源代码
💻 C
📖 第 1 页 / 共 2 页
字号:
/* $Id: rfile.c,v 1.13 2005/10/05 19:32:47 splicednetworks Exp $ * * rfile.c -- representation of a remote file * * Yet Another FTP Client * Copyright (C) 1998-2001, Martin Hedenfalk <mhe@stacken.kth.se> * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. See COPYING for more details. */#include "syshdr.h"#include "ftp.h"#include "strq.h"rfile *rfile_create(void){    rfile *f;    f = (rfile *)xmalloc(sizeof(rfile));    return f;}rfile *rfile_clone(const rfile *f){    rfile *nf = rfile_create();    nf->perm = xstrdup(f->perm);    nf->owner = xstrdup(f->owner);    nf->group = xstrdup(f->group);    nf->color = xstrdup(f->color);    nf->date = xstrdup(f->date);    nf->link = xstrdup(f->link);    nf->path = xstrdup(f->path);    nf->size = f->size;    nf->nhl = f->nhl;    nf->mtime = f->mtime;    return nf;}void rfile_clear(rfile *f){    free(f->perm);    free(f->owner);    free(f->group);    free(f->color);    free(f->date);    free(f->link);    free(f->path);    f->perm = f->owner = f->group = f->color = 0;    f->date = f->link = f->path = 0;    f->nhl = 0;    f->size = 0L;    f->mtime = (time_t)0;}void rfile_destroy(rfile *f){    if(!f)        return;    rfile_clear(f);    free(f);}bool risdir(const rfile *f){    return (f->perm[0] == 'd');}bool risdotdir(const rfile *f){    return (risdir(f)            && ((strcmp(base_name_ptr(f->path), ".") == 0                 || strcmp(base_name_ptr(f->path), "..") == 0)));}bool risreg(const rfile *f){    return !(risdir(f) || rispipe(f) || rischardev(f) || risblockdev(f));}bool rispipe(const rfile *f){    return (f->perm[0] == 'p');}bool risexec(const rfile *f){    return (strchr(f->perm, 'x') != 0);}bool rissock(const rfile *f){    return (f->perm[0] == 's');}bool rischardev(const rfile *f){    return (f->perm[0] == 'c');}bool risblockdev(const rfile *f){    return (f->perm[0] == 'b');}bool rislink(const rfile *f){    return (f->perm[0] == 'l');}void rfile_fake(rfile *f, const char *path){    ftp_trace("faking file '%s'\n", path);    free(f->perm);    f->perm = xstrdup("-rw-r-r-");    free(f->owner);    f->owner = xstrdup("owner");    free(f->group);    f->group = xstrdup("group");    free(f->link);    f->link = 0;    free(f->path);    f->path = xstrdup(path);    free(f->date);    f->date = xstrdup("Jan  0  1900");    f->mtime = 0;    f->nhl = 0;    f->size = (unsigned long long)-1;    rfile_parse_colors(f);}char rfile_classchar(const rfile *f){    if(risdir(f)) return '/';    if(rislink(f)) return '@';    if(rissock(f)) return '=';    if(rispipe(f)) return '|';    if(risexec(f)) return '*';    return 0;}mode_t str2mode_t(const char *p){    mode_t m = 0;    p++;    if(*p++=='r') m|=S_IRUSR;    if(*p++=='w') m|=S_IWUSR;    if(*p=='x') m|=S_IXUSR;    else if(*p=='S') m|=S_ISUID;    else if(*p=='s') m|=(S_ISUID|S_IXUSR);    p++;    if(*p++=='r') m|=S_IRGRP;    if(*p++=='w') m|=S_IWGRP;    if(*p=='x') m|=S_IXGRP;    else if(*p=='S') m|=S_ISGID;    else if(*p=='s') m|=(S_ISGID|S_IXGRP);    p++;    if(*p++=='r') m|=S_IROTH;    if(*p++=='w') m|=S_IWOTH;    if(*p=='x') m|=S_IXOTH;    else if(*p=='T') m|=S_ISVTX;    else if(*p=='t') m|=(S_ISVTX|S_IXOTH);    return m;}mode_t rfile_getmode(const rfile *f){    if(!f || !f->perm)        return (mode_t)-1;    return str2mode_t(f->perm);}static const char *month_name[] = {    "Jan", "Feb", "Mar", "Apr", "May", "Jun",    "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"};/* returns month number if STR is a month abbreviation * else -1 */int month_number(const char *str){    int i;    for(i=0; i<12; i++) {        if(strcasecmp(str, month_name[i]) == 0)            return i;    }    return -1;}void rfile_parse_time(rfile *f, const char *m, const char *d, const char *y){    time_t now;    struct tm *tm_now;    struct tm mt;    int u;    f->mtime = (time_t)-1;    if(!m || !d || !y)        return;    mt.tm_sec = 0;    mt.tm_mday = atoi(d);    mt.tm_mon = month_number(m);    if(mt.tm_mon == -1)        return;    time(&now);    tm_now = localtime(&now);    mt.tm_isdst = tm_now->tm_isdst;    if(strchr(y, ':') != 0) {        /* date on form "MMM DD HH:MM" */        time_t tmp;        char *eh, *em;        u = strtoul(y, &eh, 10);        if(eh == y)            return;        mt.tm_hour = u;        u = strtoul(eh+1, &em, 10);        if(em == eh+1)            return;        mt.tm_min = u;        mt.tm_year = tm_now->tm_year;        /* might be wrong year, +- 1         * filetime is not older than 6 months         * or newer than 1 hour         */        tmp = mktime(&mt);        if(tmp > now + 60L*60L)            mt.tm_year--;        if(tmp < now - 6L*30L*24L*60L*60L)            mt.tm_year++;    } else {        /* date on form "MMM DD YYYY" */        char *ey;        u = strtoul(y, &ey, 10);        if(ey == y)            return;        mt.tm_year = u - 1900;        mt.tm_hour = 0;        mt.tm_min = 0;    }    f->mtime = mktime(&mt);}#define NEXT_FIELD \e = strqsep(&cf, ' '); \if(!e || !*e) { \    return -1; \}#define NEXT_FIELD2 \e = strqsep(&cf, ' '); \if(!e || !*e) { \    free(m); \    free(d); \    free(y); \    return -1; \}char *time_to_string(time_t t){    char *ret;    time_t now;    char *fmt;    now = time(0);    if(now > t + 6L * 30L * 24L * 60L * 60L  /* Old. */       || now < t - 60L * 60L)   /* In the future. */        {            /* The file is fairly old or in the future.               POSIX says the cutoff is 6 months old;               approximate this by 6*30 days.               Allow a 1 hour slop factor for what is considered "the future",               to allow for NFS server/client clock disagreement.               Show the year instead of the time of day.  */            fmt = "%b %e  %Y";        }    else        fmt = "%b %e %H:%M";    ret = (char *)xmalloc(42);    strftime(ret, 42, fmt, localtime(&t));    return ret;}static int rfile_parse_eplf(rfile *f, char *str, const char *dirpath){    char *e;    if(!str || str[0] != '+')        return -1;    str++;    f->perm = xstrdup("-rw-r--r--");    f->size = 0L;    f->mtime = 0;    f->link = 0;    f->nhl = 0;    f->owner = xstrdup("owner");    f->group = xstrdup("group");    f->date = xstrdup("Jan  0  1900");    f->path = 0;    while((e = strqsep(&str, ',')) != 0) {        switch(*e) {        case '/':            f->perm[0] = 'd';            break;        case 'm':            f->mtime = strtoul(e+1, 0, 10);            free(f->date);            f->date = time_to_string(f->mtime);            break;        case 's':            f->size = strtoull(e+1, 0, 10);            break;        case '\t':            asprintf(&f->path, "%s/%s",                     strcmp(dirpath, "/") ? dirpath : "", e+1);            break;        }    }    if(f->path == 0)        return -1;    rfile_parse_colors(f);    return 0;}/* This is a total mess! */static int rfile_parse_unix(rfile *f, char *str, const char *dirpath){    char *cf;    char *e;    char *m=0, *d=0, *y=0;    char *saved_field[5];    bool time_parsed = false;    /* real unix ls listing:     *     * saved_field[0] == nhl     * saved_field[1] == owner     * saved_field[2] == group     * saved_field[3] == size     * saved_field[4] == month     *     *     * unix w/o group listing:     *     * saved_field[0] == nhl     * saved_field[1] == owner     * saved_field[2] == size     * saved_field[3] == month     * saved_field[4] == date     *     *     * strange MacOS WebStar thingy:     *     * saved_field[0] == size or "folder"     * saved_field[1] == zero or date if [0]=="folder"     * saved_field[2] == size (again!?) or month     * saved_field[3] == month or date     * saved_field[4] == date or time (or year?)     *     *     * Linux netkit FTP server with LANG=sv_SE (ISO date&time format):     * (-rw-------    1 mhe      mhe          1422 2002-09-24 22:30 asdf.txt)     *     * saved_field[0] == nhl     * saved_field[1] == owner     * saved_field[2] == group     * saved_field[3] == size     * saved_field[4] == YYYY-MM-DD     *     */    if(strncmp(str, "total ", 6) == 0)        return 1;    cf = str;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -