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

📄 pure-ftpwho.c

📁 功能强大的ftp服务器源代码
💻 C
📖 第 1 页 / 共 2 页
字号:
    if (current_size > (off_t) 0) {        unsigned long bandwidth;        long double pct;        int pcti;                        if (xfer_since > 0UL && current_size > restartat) {            bandwidth = (unsigned long) ((current_size - restartat) / xfer_since);        } else {            bandwidth = 0UL;        }                if ((long double) total_size > 0.0L) {            pct = ((long double) current_size * 100.0L) / (long double) total_size;            pcti = (int) (pct + 0.5L);            if (pcti > 100) {                pcti = 100;           /* should never happen */            }            printf(" resume=\"%llu\"", (unsigned long long) restartat);            printf(" current_size=\"%llu\"", (unsigned long long) current_size);            printf(" total_size=\"%llu\"", (unsigned long long) total_size);            printf(" percentage=\"%d\"", pcti);            printf(" bandwidth=\"%lu\"", bandwidth);        } else {            printf(" resume=\"%llu\"", (unsigned long long) restartat);            printf(" current_size=\"%llu\"", (unsigned long long) current_size);            printf(" bandwidth=\"%lu\"", bandwidth);                    }    }    puts(" />");}static void xml_output_footer(void){    puts("</status>");}/* Shell output */static const char *shell_escaped(const char * const s_){    register const unsigned char *s = (const unsigned char *) s_;            static char buf[MAXPATHLEN + 32U];    const char * const bufend = &buf[sizeof buf - (size_t) 1U];    register char *bufpnt = buf;            while (*s != 0U) {        if (ISCTRLCODE(*s)) {            *bufpnt = '_';        } else if (*s == '|' || *s == '\\') {            if (bufpnt == bufend) {                break;            }            *bufpnt++ = '\\';            if (bufpnt == bufend) {                bufpnt--;                break;            }            *bufpnt = (char) *s;        } else {            *bufpnt = (char) *s;        }        if (bufpnt == bufend) {            break;        }        bufpnt++;        s++;    }    *bufpnt = 0;        return buf;}static void shell_output_header(void){}static void shell_output_line(const pid_t pid, const char * const account,                              const unsigned long since,                              const unsigned long xfer_since,                              const char * const state,                              const char * const filename,                              const char * const hbuf,                              const char * const local_hbuf,                              const char * const local_port,                              const off_t restartat,                              const off_t total_size,                              const off_t current_size){    unsigned long bandwidth = 0UL;    long double pct;    int pcti = 0;                if (current_size > (off_t) 0) {                if (xfer_since > 0UL && current_size > restartat) {            bandwidth = (unsigned long) ((current_size - restartat) /                                         (xfer_since * 1024UL));        }                 if ((long double) total_size > 0.0L) {            pct = ((long double) current_size * 100.0L) / (long double) total_size;            pcti = (int) (pct + 0.5L);            if (pcti > 100) {                pcti = 100;           /* should never happen */            }        }    }             printf("%lu|", (unsigned long) pid);    printf("%s|", shell_escaped(account));    printf("%lu|", since);    printf("%s|", shell_escaped(state));    printf("%s|", shell_escaped(filename));    printf("%s|", shell_escaped(hbuf));    printf("%s|", shell_escaped(local_hbuf));    printf("%s|", shell_escaped(local_port));    printf("%llu|", (unsigned long long) (current_size / 1024));    printf("%llu|", (unsigned long long) (total_size / 1024));    printf("%d|", pcti);    printf("%lu\n", bandwidth);}static void shell_output_footer(void){}/* function pointers */static void (*output_header)(void) = text_output_header;static void (*output_line)(const pid_t pid, const char * const account,                           const unsigned long since,                            const unsigned long xfer_since,                           const char * const state,                           const char * const filename,                           const char * const hbuf,                           const char * const local_hbuf,                           const char * const local_port,                           const off_t restartat,                                                      const off_t total_size,                           const off_t current_size) = text_output_line;static void (*output_footer)(void) = text_output_footer;/* Back to life */static void help(void){    puts("\nUsage :\n\n"         "-c : this program is called by a web server (CGI mode)\n"         "-h : help\n"         "-H : don't resolve host names, only show IP addresses\n"         "-n : synonym for -H\n"         "-s : easily parsable output for shell scripts\n"         "     format is :\n"         "     pid|acct|time|state|file|peer|local|port|current|total|%|bandwidth\n"         "-v : output verbose ASCII\n"                  "-w : output HTML page (web mode)\n"         "-W : output HTML page without header/footer (embedded mode)\n"         "-x : output XML data\n");    exit(EXIT_SUCCESS);}static int closedesc_but1(void){    int fodder;        (void) close(0);    if ((fodder = open("/dev/null", O_RDONLY)) == -1) {        return -1;    }    (void) dup2(fodder, 0);    if (fodder > 0) {        (void) close(fodder);    }    if (fcntl(1, F_GETFD) == -1) {        return -1;    }    if (fcntl(2, F_GETFD) != -1) {        if ((fodder = open("/dev/null", O_WRONLY)) == -1) {            return -1;        }        (void) dup2(fodder, 2);        if (fodder > 2) {            (void) close(fodder);        }    }    return 0;}int main(int argc, char *argv[]){    DIR *dir;    struct dirent *entry;    struct stat st;    FTPWhoEntry *scanned_entry;    int locked;    int delete_file;    const char *state;    time_t now;    int fodder;#ifndef NON_ROOT_FTP    if (geteuid() != (uid_t) 0) {        puts("You must be root to run this. Sorry.");        return 1;    }#endif    if (argc < 0) {        return -1;    }    if (closedesc_but1() < 0) {        return -2;    }#ifdef HAVE_SETLOCALE# ifdef LC_MESSAGES    (void) setlocale(LC_MESSAGES, "");# endif# ifdef LC_CTYPE    (void) setlocale(LC_CTYPE, "");# endif# ifdef LC_COLLATE    (void) setlocale(LC_COLLATE, "");# endif#endif            fixlimits();# ifdef SIGFPE    signal(SIGFPE, sigfpe);# endif# ifdef SIGSEGV    signal(SIGSEGV, sigsegv);# endif        if (getenv("GATEWAY_INTERFACE") != NULL) {        html_cgi = 1;        output_header = html_output_header;        output_line = html_output_line;                    output_footer = html_output_footer;            }    while ((fodder = getopt(argc, argv, "CchHnsvwWx")) != -1) {        switch(fodder) {        case 'h' :            help();            /* doesn't return */        case 'n' :        case 'H' :            dont_resolve_ip++;            break;        case 'C' :        case 'c' :            html_cgi++;        case 'W' :            html_raw++;        case 'w' :            output_header = html_output_header;            output_line = html_output_line;                        output_footer = html_output_footer;            break;        case 's' :            output_header = shell_output_header;            output_line = shell_output_line;                        output_footer = shell_output_footer;            break;                    case 'x' :            output_header = xml_output_header;            output_line = xml_output_line;                        output_footer = xml_output_footer;            break;                    case 'v' :            verbose++;            break;        case '?' :            help();        }    }        now = time(NULL);    if (chdir(SCOREBOARD_PATH) != 0 ||        (dir = opendir(".")) == NULL) {        fprintf(stderr, "Unable to open the ftpwho scoreboard.\n"                "Make sure that the [" SCOREBOARD_PATH "/] directory exists,\n"                "Or wait until a client connects, so that it gets\n"                "automatically created. This message doesn't mean that your\n"                "server didn't start properly. It probably just means that\n"                "you are running it with ftpwho for the first time.\n");        return -1;    }    lock.l_whence = SEEK_SET;    lock.l_start = (off_t) 0;    lock.l_len = (off_t) 0;    lock.l_pid = getpid();        output_header();    while ((entry = readdir(dir)) != NULL) {        mmap_fd = -1;        locked = 0;        delete_file = 0;        scanned_entry = NULL;        if (strncmp(entry->d_name, SCOREBOARD_PREFIX,                    sizeof SCOREBOARD_PREFIX - 1U) != 0) {            goto nextone;        }        if ((mmap_fd = open(entry->d_name, O_RDWR | O_NOFOLLOW)) == -1) {            goto nextone;        }        if (fstat(mmap_fd, &st) != 0 || !S_ISREG(st.st_mode) ||            (st.st_mode & 0600) != 0600 ||             st.st_size != (off_t) sizeof (FTPWhoEntry) ||#ifdef NON_ROOT_FTP            st.st_uid != geteuid()#else            st.st_uid != (uid_t) 0#endif            ) {            goto nextone;        }        ftpwho_lock();        locked++;        if ((scanned_entry = (FTPWhoEntry *) mmap(NULL, sizeof (FTPWhoEntry),                                                  PROT_READ,                                                   MAP_SHARED | MAP_FILE,                                                   mmap_fd, (off_t) 0)) == NULL) {            goto nextone;        }        if (checkproc(scanned_entry->pid) == 0) {            /* still in the scoreboard, but no more process */            delete_file++;            goto nextone;        }                if (scanned_entry->state != FTPWHO_STATE_FREE) {            unsigned long since;            unsigned long xfer_since;            char local_port[NI_MAXSERV];            char local_hbuf[NI_MAXHOST];                        char hbuf[NI_MAXHOST];            switch (scanned_entry->state) {            case FTPWHO_STATE_IDLE :                state = "IDLE";                break;            case FTPWHO_STATE_DOWNLOAD :                state = " DL ";                break;            case FTPWHO_STATE_UPLOAD :                state = " UL ";                break;            default :                state = "ERR!";            }            if (scanned_entry->date < now) {                since = (unsigned long) (now - scanned_entry->date);            } else {                since = 0UL;            }            if (scanned_entry->xfer_date > (time_t) 0 &&                scanned_entry->xfer_date < now) {                xfer_since = (unsigned long) (now - scanned_entry->xfer_date);            } else {                xfer_since = 0UL;            }            for (;;) {                int eai;                                                if ((eai = getnameinfo                     ((struct sockaddr *) &scanned_entry->addr,                      STORAGE_LEN(scanned_entry->addr),                      hbuf, sizeof hbuf, NULL, (size_t) 0U,                      dont_resolve_ip != 0 ? NI_NUMERICHOST : 0)) == 0) {                    break;                }#ifdef EAI_NONAME                if (eai == EAI_NONAME && dont_resolve_ip == 0 &&                    getnameinfo                    ((struct sockaddr *) &scanned_entry->addr,                     STORAGE_LEN(scanned_entry->addr),                     hbuf, sizeof hbuf, NULL, (size_t) 0U,                     NI_NUMERICHOST) == 0) {                    break;                }                #endif                goto nextone;            }            for (;;) {                int eai;                                if ((eai = getnameinfo                     ((struct sockaddr *) &scanned_entry->local_addr,                      STORAGE_LEN(scanned_entry->addr),                      local_hbuf, sizeof local_hbuf,                      local_port, sizeof local_port,                      dont_resolve_ip != 0 ? (NI_NUMERICHOST | NI_NUMERICSERV) :                      NI_NUMERICSERV)) == 0) {                    break;                }#ifdef EAI_NONAME                                if (eai == EAI_NONAME && dont_resolve_ip == 0 &&                    getnameinfo                    ((struct sockaddr *) &scanned_entry->local_addr,                     STORAGE_LEN(scanned_entry->addr),                     local_hbuf, sizeof local_hbuf,                     local_port, sizeof local_port,                     NI_NUMERICHOST | NI_NUMERICSERV) == 0) {                    break;                }#endif                goto nextone;            }            output_line(scanned_entry->pid, scanned_entry->account,                        since, xfer_since, state, scanned_entry->filename,                         hbuf, local_hbuf, local_port,                        (scanned_entry->restartat <=                          scanned_entry->download_current_size) ?                        scanned_entry->restartat : (off_t) 0,                        (scanned_entry->state == FTPWHO_STATE_DOWNLOAD) ?                        scanned_entry->download_total_size : (off_t) 0,                        (scanned_entry->state == FTPWHO_STATE_DOWNLOAD ||                         scanned_entry->state == FTPWHO_STATE_UPLOAD) ?                        scanned_entry->download_current_size : (off_t) 0);        }        nextone:        if (locked != 0 && mmap_fd != -1) {            ftpwho_unlock();        }        if (scanned_entry != NULL) {            (void) munmap((void *) scanned_entry, sizeof (FTPWhoEntry));        }        if (mmap_fd != -1) {            close(mmap_fd);        }        if (delete_file != 0) {            unlink(entry->d_name);        }    }        output_footer();        return 0;}#endif

⌨️ 快捷键说明

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