Gene Cumm
2010-Mar-18 00:30 UTC
[syslinux] [MODULE] COM32 module to time null-dumping a file
From: Gene Cumm <gene.cumm at gmail.com> COM32/samples/cptime.c: A module for coarse null-dumping speed comparisons. Accepts multiple files and an option of -s (as the first option) to provide a simple output. Also computes/displays +/- 1 tick to show coarseness. Signed-off-by: Gene Cumm <gene.cumm at gmail.com> --- I'd recommend using a file that takes around 100 ticks to get a reasonable idea but you'd probably need closer to 1000+ if you want more precise numbers. I haven't checked that this is OK against scripts/checkpatch.pl as I'm having difficulty running it (been around a year since I last used it) but things should be pretty close. Long term, I should break it out to also having a .h to clean up the #ifdef. I also need to go back and review the indentation styling per current standards. I designed this (as I've done before) to compile for both Linux and Syslinux COM32 with very similar functionality. I've tested different sizes for the buffer/fetch block but haven't determined the "optimal" size yet (which might vary by environment... I'm not sure.). diff --git a/com32/samples/cptime.c b/com32/samples/cptime.c new file mode 100644 index 0000000..73266ec --- /dev/null +++ b/com32/samples/cptime.c @@ -0,0 +1,138 @@ +/* ----------------------------------------------------------------------- * + * + * Copyright 2010 Gene Cumm - All Rights Reserved + * + * 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, Inc., 53 Temple Place Ste 330, + * Boston MA 02111-1307, USA; either version 2 of the License, or + * (at your option) any later version; incorporated herein by reference. + * + * ----------------------------------------------------------------------- */ + +/* + * cptime.c + * + * Timed copy; read entire file then output total time, bytes transferred, + * and compute transfer rate. + * + * cptime [-s] _FILE_.... + * -s Change to simple output mode without computing transfer rate + * _FILE_..... Space delimited list of files to dump + */ + +/* + * ToDos: + * Refine timing to be more precise. + */ + +#include <stdio.h> +#include <stdlib.h> +#include <errno.h> +#include <fcntl.h> +#include <unistd.h> +#include <sys/times.h> +#include <consoles.h> +#include <minmax.h> + + +#ifdef __COM32__ +#define BUFSZ 2048 +/* What's optimal? Under 4k? + * layout.inc: xfer_buf_seg equ 1000h + */ + +float get_tps(){ return 18.2; } + +#else /* __COM32__ */ + +#define BUFSZ 16384 +/* Need to check what might be a "best" buffer/fetch block size here */ + +float get_tps(){ return (float)sysconf(_SC_CLK_TCK); } +void print_cp_result2(char *fn, int bcnt, clock_t bc, clock_t ec) +{ + float et, dr; + et = ((float)(ec - bc)) / (float)sysconf(_SC_CLK_TCK); + dr = ((float)bcnt) / et; + printf(" %dB in %.3fs from '%s'\n", bcnt, et, fn); + printf(" %.0f B/s; %.0f KiB/s; %.0f MiB/s\n", dr, dr/1024, dr/1048576); +} /* void print_cp_result2(char *fn, int bcnt, clock_t bc, clock_t ec) */ +#endif /* __COM32__ */ + +void print_cp_result_tick(int bcnt, clock_t et, float tps, int offs) +{ + int dr; + dr = bcnt * tps / max(1,(et + offs)); // prevent divide by 0 + printf(" %+d %d B/s; %d KiB/s; %d MiB/s\n", offs, dr, dr/1024, dr/1048576); +} /* void print_cp_result_tick(int bcnt, clock_t et, float tps, int offs) */ + +void print_cp_result(char *fn, int bcnt, clock_t bc, clock_t ec) +{ + float tps; + tps = get_tps(); + printf(" %dB in %d ticks from '%s'\n", bcnt, (int)(ec - bc), fn); + printf(" ~%d ticks per second; %d\n", (int)tps, (BUFSZ)); + print_cp_result_tick(bcnt, (ec - bc), tps, 0); + print_cp_result_tick(bcnt, (ec - bc), tps, 1); + print_cp_result_tick(bcnt, (ec - bc), tps, -1); +} /* void print_cp_result(char *fn, int bcnt, clock_t bc, clock_t ec) */ + +void print_cp_result_simple(char *fn, int bcnt, clock_t bc, clock_t ec) +{ + printf(" %dB %dt %dx '%s'\n", bcnt, (int)(ec - bc), (BUFSZ), fn); +} /* void print_cp_result_simple(char *fn, int bcnt, clock_t bc, clock_t ec) */ + +int time_copy(char *fn, char do_simple) +{ + int fd, rv = 0; + int bcnt; + int numrd; + struct tms tm; + clock_t bc, ec; + char buf[BUFSZ + 1]; + buf[0] = 0; + fd = open(fn, O_RDONLY); + if (fd == -1) { + switch (errno){ + case ENOENT : + printf("File '%s' does not exist\n", fn); + break; + default : + printf("Error '%d' opening file '%s'\n", errno, fn); + } + rv = 1; + } else { + bc = times(&tm); + numrd = read(fd, buf, BUFSZ); + bcnt = numrd; + while(numrd > 0){ + numrd = read(fd, buf, BUFSZ); + bcnt = bcnt + numrd; + } + ec = times(&tm); + close(fd); + if (do_simple) + print_cp_result_simple(fn, bcnt, bc, ec); + else + print_cp_result(fn, bcnt, bc, ec); + } + return rv; +} /* int time_copy(char *fn, char do_simple) */ + +int main(int argc, char *argv[]) +{ + int i, st_arg = 1; + char do_simple = 0; + console_ansi_std(); + if (argc == 1) + printf("%s: Please specify a file\n", argv[0]); + if ((argc > 2) && (argv[1][0] == '-') && (argv[1][1] == 's') & (argv[1][2] == 0) ) + { + do_simple = 1; + st_arg = 2; + } + for (i=st_arg;i<argc;i++) + time_copy(argv[i], do_simple); + return 0; +} /* int main(int argc, char *argv[]) */