annotate toys/posix/wc.c @ 1775:57f2a26fa92c draft toast

To ensure that toybox can be installed alongside busybox without confusing update-alternatives, the paths of the links installed by toybox should match those installed by busybox. This is accomplished by changing the flags of a few tools within toybox.
author Paul Barker <paul@paulbarker.me.uk>
date Sat, 04 Apr 2015 11:58:06 -0500
parents 3b85d2ce34aa
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
694
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
1 /* wc.c - Word count
386
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
2 *
387
67b0ded3c56c Add dirname, and typo fixes to wc header.
Rob Landley <rob@landley.net>
parents: 386
diff changeset
3 * Copyright 2011 Rob Landley <rob@landley.net>
386
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
4 *
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
5 * See http://opengroup.org/onlinepubs/9699919799/utilities/wc.html
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
6
1342
3b85d2ce34aa When locale is enabled, sprintf("%.123s", str) is counting characters, not bytes, so we can't globally enable locale without opening stack/heap smashing vulnerabilities. Make commands individually request setlocale() using TOYFLAGS instead.
Rob Landley <rob@landley.net>
parents: 780
diff changeset
7 USE_WC(NEWTOY(wc, USE_TOYBOX_I18N("m")"cwl", TOYFLAG_USR|TOYFLAG_BIN|TOYFLAG_LOCALE))
386
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
8
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
9 config WC
694
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
10 bool "wc"
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
11 default y
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
12 help
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
13 usage: wc -lwcm [FILE...]
386
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
14
694
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
15 Count lines, words, and characters in input.
386
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
16
694
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
17 -l show lines
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
18 -w show words
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
19 -c show bytes
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
20 -m show characters
386
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
21
694
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
22 By default outputs lines, words, bytes, and filename for each
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
23 argument (or from stdin if none). Displays only either bytes
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
24 or characters.
386
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
25 */
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
26
674
7e846e281e38 New build infrastructure to generate FLAG_ macros and TT alias, #define FOR_commandname before #including toys.h to trigger it. Rename DEFINE_GLOBALS() to just GLOBALS() (because I could never remember if it was DECLARE_GLOBALS). Convert existing commands to use new infrastructure, and replace optflag constants with FLAG_ macros where appropriate.
Rob Landley <rob@landley.net>
parents: 662
diff changeset
27 #define FOR_wc
386
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
28 #include "toys.h"
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
29
674
7e846e281e38 New build infrastructure to generate FLAG_ macros and TT alias, #define FOR_commandname before #including toys.h to trigger it. Rename DEFINE_GLOBALS() to just GLOBALS() (because I could never remember if it was DECLARE_GLOBALS). Convert existing commands to use new infrastructure, and replace optflag constants with FLAG_ macros where appropriate.
Rob Landley <rob@landley.net>
parents: 662
diff changeset
30 GLOBALS(
694
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
31 unsigned long totals[3];
662
5cb41d56f9d3 Posix compliance: wc shouldn't have trailing spaces (breaks aboriginal's mkinitr
Rob Landley <rob@landley.net>
parents: 653
diff changeset
32 )
5cb41d56f9d3 Posix compliance: wc shouldn't have trailing spaces (breaks aboriginal's mkinitr
Rob Landley <rob@landley.net>
parents: 653
diff changeset
33
5cb41d56f9d3 Posix compliance: wc shouldn't have trailing spaces (breaks aboriginal's mkinitr
Rob Landley <rob@landley.net>
parents: 653
diff changeset
34 static void show_lengths(unsigned long *lengths, char *name)
5cb41d56f9d3 Posix compliance: wc shouldn't have trailing spaces (breaks aboriginal's mkinitr
Rob Landley <rob@landley.net>
parents: 653
diff changeset
35 {
694
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
36 int i, nospace = 1;
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
37 for (i=0; i<3; i++) {
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
38 if (!toys.optflags || (toys.optflags&(1<<i))) {
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
39 xprintf(" %ld"+nospace, lengths[i]);
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
40 nospace = 0;
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
41 }
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
42 TT.totals[i] += lengths[i];
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
43 }
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
44 if (*toys.optargs) xprintf(" %s", name);
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
45 xputc('\n');
662
5cb41d56f9d3 Posix compliance: wc shouldn't have trailing spaces (breaks aboriginal's mkinitr
Rob Landley <rob@landley.net>
parents: 653
diff changeset
46 }
5cb41d56f9d3 Posix compliance: wc shouldn't have trailing spaces (breaks aboriginal's mkinitr
Rob Landley <rob@landley.net>
parents: 653
diff changeset
47
386
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
48 static void do_wc(int fd, char *name)
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
49 {
694
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
50 int i, len, clen=1, space;
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
51 unsigned long word=0, lengths[]={0,0,0};
386
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
52
694
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
53 for (;;) {
724
9499e4cf830f Felix Janda pointed out that the r in mbrtowc() stands for "restartable" so it's already buffering the partial data we feed it, so rolling back most of the last commit to wc.
Rob Landley <rob@landley.net>
parents: 719
diff changeset
54 len = read(fd, toybuf, sizeof(toybuf));
780
6cc69be43c42 Have error_msg() and friends set TT.exitval to 1 if it's still 0, clean out other places that were setting it that no longer need to.
Rob Landley <rob@landley.net>
parents: 726
diff changeset
55 if (len<0) perror_msg("%s", name);
724
9499e4cf830f Felix Janda pointed out that the r in mbrtowc() stands for "restartable" so it's already buffering the partial data we feed it, so rolling back most of the last commit to wc.
Rob Landley <rob@landley.net>
parents: 719
diff changeset
56 if (len<1) break;
694
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
57 for (i=0; i<len; i+=clen) {
724
9499e4cf830f Felix Janda pointed out that the r in mbrtowc() stands for "restartable" so it's already buffering the partial data we feed it, so rolling back most of the last commit to wc.
Rob Landley <rob@landley.net>
parents: 719
diff changeset
58 wchar_t wchar;
9499e4cf830f Felix Janda pointed out that the r in mbrtowc() stands for "restartable" so it's already buffering the partial data we feed it, so rolling back most of the last commit to wc.
Rob Landley <rob@landley.net>
parents: 719
diff changeset
59
712
a950dd960593 Cleanup i18n support (#ifdefectomy, move global init to process launch). Teach make.sh to emit "#define FLAG_x 0" for options inside disabled USE macros so we can unconditionally refer to them.
Rob Landley <rob@landley.net>
parents: 710
diff changeset
60 if (CFG_TOYBOX_I18N && (toys.optflags&FLAG_m)) {
694
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
61 clen = mbrtowc(&wchar, toybuf+i, len-i, 0);
724
9499e4cf830f Felix Janda pointed out that the r in mbrtowc() stands for "restartable" so it's already buffering the partial data we feed it, so rolling back most of the last commit to wc.
Rob Landley <rob@landley.net>
parents: 719
diff changeset
62 if (clen == -1) {
726
6617899e55f8 Minor cleanup: unify two codepaths that do the same thing.
Rob Landley <rob@landley.net>
parents: 724
diff changeset
63 clen = 1;
6617899e55f8 Minor cleanup: unify two codepaths that do the same thing.
Rob Landley <rob@landley.net>
parents: 724
diff changeset
64 continue;
694
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
65 }
724
9499e4cf830f Felix Janda pointed out that the r in mbrtowc() stands for "restartable" so it's already buffering the partial data we feed it, so rolling back most of the last commit to wc.
Rob Landley <rob@landley.net>
parents: 719
diff changeset
66 if (clen == -2) break;
9499e4cf830f Felix Janda pointed out that the r in mbrtowc() stands for "restartable" so it's already buffering the partial data we feed it, so rolling back most of the last commit to wc.
Rob Landley <rob@landley.net>
parents: 719
diff changeset
67 if (clen == 0) clen=1;
694
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
68 space = iswspace(wchar);
712
a950dd960593 Cleanup i18n support (#ifdefectomy, move global init to process launch). Teach make.sh to emit "#define FLAG_x 0" for options inside disabled USE macros so we can unconditionally refer to them.
Rob Landley <rob@landley.net>
parents: 710
diff changeset
69 } else space = isspace(toybuf[i]);
686
9414be56b1db wc -m only cares about counting characters. Attached is a try on implementing it and some test cases for it. The test cases are only for UTF-8 locales.
Felix Janda <felix.janda@posteo.de>
parents: 674
diff changeset
70
694
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
71 if (toybuf[i]==10) lengths[0]++;
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
72 if (space) word=0;
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
73 else {
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
74 if (!word) lengths[1]++;
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
75 word=1;
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
76 }
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
77 lengths[2]++;
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
78 }
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
79 }
662
5cb41d56f9d3 Posix compliance: wc shouldn't have trailing spaces (breaks aboriginal's mkinitr
Rob Landley <rob@landley.net>
parents: 653
diff changeset
80
694
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
81 show_lengths(lengths, name);
386
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
82 }
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
83
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
84 void wc_main(void)
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
85 {
694
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
86 toys.optflags |= (toys.optflags&8)>>1;
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
87 loopfiles(toys.optargs, do_wc);
786841fdb1e0 Reindent to two spaces per level. Remove vi: directives that haven't worked right in years (ubuntu broke its' vim implementation). Remove trailing spaces. Add/remove blank lines. Re-wordwrap in places. Update documentation with new coding style.
Rob Landley <rob@landley.net>
parents: 686
diff changeset
88 if (toys.optc>1) show_lengths(TT.totals, "total");
386
03bf7c545b6f Add wc.
Rob Landley <rob@landley.net>
parents:
diff changeset
89 }