fixed head

This commit is contained in:
Your Name 2013-01-18 09:27:24 +00:00
parent 87abbeffa3
commit a3270dd18a
2 changed files with 75 additions and 15 deletions

1
TODO
View File

@ -50,6 +50,5 @@ BUGS:
FIX: FIX:
ps ps
head
echo (escape) echo (escape)
que (unicode) que (unicode)

View File

@ -10,46 +10,102 @@
char v_flag; char v_flag;
char c_flag; char c_flag;
char n_flag;
long parse_long(const char *str) { long parse_long(const char *str) {
char *ptr; char *ptr;
long ret = strtol(str, &ptr, 0); long ret = strtol(str, &ptr, 0);
if (*ptr) { if (*ptr) {
fprintf(stderr, "head: %s invalid number\n", ptr); fprintf(stderr, "head: invalid number %s\n", ptr);
exit(1); exit(1);
} }
return ret; return ret;
} }
void print(const char *file, FILE *fp, long lines, long bytes) { int print(const char *file, FILE *fp, long lines, long bytes) {
if (v_flag) if (v_flag)
printf(HEAD_FMT, file); printf(HEAD_FMT, file);
long lcount = 0; long lcount = 0;
long bcount = 0; long bcount = 0;
while (1) { /* If lines or bytes < 0 */
int c = getc(fp); if (lines < 0 || bytes < 0) {
bcount++; long lmax = 0;
if (c == '\n') long bmax = 0;
lcount++;
if (c == EOF || lcount == lines || (c_flag && bcount == bytes)) size_t buf_size = 0;
break; char *buf = malloc(1);
if (buf == NULL) {
fprintf(stderr, "head: malloc: %s\n", strerror(errno));
return 1;
}
putchar(c); while (1) {
int c = getc(fp);
if (c == EOF)
break;
char *tmp = realloc(buf, buf_size + 2);
if (tmp == NULL) {
fprintf(stderr, "head: realloc: %s\n", strerror(errno));
free(buf);
return 1;
}
buf = tmp;
buf[buf_size] = c;
if (c == '\n')
lmax++;
bmax++;
buf_size++;
}
buf[buf_size] = '\0';
for (size_t i = 0; i < buf_size; i++) {
if (buf[i] == '\n')
lcount++;
bcount++;
putchar(buf[i]);
if ((n_flag && lcount == lmax + lines) || (c_flag && bcount == bmax + bytes))
break;
}
free(buf);
} }
else {
while (1) {
int c = getc(fp);
if (c == EOF)
break;
if (c == '\n')
lcount++;
bcount++;
putchar(c);
if ((n_flag && lcount == lines) || (c_flag && bcount == bytes))
break;
}
}
return 0;
} }
int main(int argc, char **argv) { int main(int argc, char **argv) {
long lines = 10; long lines = 0;
long bytes = 0; long bytes = 0;
int opt; int opt;
while ((opt = getopt(argc, argv, "n:c:v")) != -1) { while ((opt = getopt(argc, argv, "n:c:v")) != -1) {
switch (opt) { switch (opt) {
case 'n': case 'n':
n_flag = 1;
lines = parse_long(optarg); lines = parse_long(optarg);
break; break;
@ -63,7 +119,7 @@ int main(int argc, char **argv) {
break; break;
default: default:
printf("head [ncv] [file1 file2...]\n\t-n Print N lines\n\t-c Print N bytes\n\t-v Print headers\n"); printf("head [ncv] [file1 file2...]\n\t-n Print [-]N lines\n\t-c Print [-]N bytes\n\t-v Print headers\n");
return 0; return 0;
} }
} }
@ -74,6 +130,7 @@ int main(int argc, char **argv) {
if (argc == 0) if (argc == 0)
print("-", stdin, lines, bytes); print("-", stdin, lines, bytes);
int ret = 0;
for (int i = 0; i < argc; i++) { for (int i = 0; i < argc; i++) {
FILE *fp = NULL; FILE *fp = NULL;
if (argv[i][0] == '-') if (argv[i][0] == '-')
@ -84,10 +141,14 @@ int main(int argc, char **argv) {
if (fp == NULL) { if (fp == NULL) {
fprintf(stderr, "head: %s: %s\n", argv[i], strerror(errno)); fprintf(stderr, "head: %s: %s\n", argv[i], strerror(errno));
return 1;
ret = 1;
continue;
} }
print(argv[i], fp, lines, bytes); if (print(argv[i], fp, lines, bytes))
ret = 1;
fclose(fp); fclose(fp);
} }