1 /* $NetBSD: hntest.c,v 1.4 2007/03/12 03:38:21 enami Exp $ */
13 const char *ho_suffix
;
16 int ho_retval
; /* expected return value */
17 const char *ho_retstr
; /* expected string in buffer */
20 * Rev. 1.6 produces "10.0".
22 { 5, 10737418236ULL * 1024, "",
23 HN_AUTOSCALE
, HN_B
| HN_NOSPACE
| HN_DECIMAL
, 3, "10T" },
26 HN_AUTOSCALE
, HN_B
| HN_NOSPACE
| HN_DECIMAL
, 3, "10M" },
27 { 5, 10500000, "", /* just for reference */
28 HN_AUTOSCALE
, HN_B
| HN_NOSPACE
| HN_DECIMAL
, 3, "10M" },
31 * Trailing space. Rev. 1.7 produces "1 ".
33 { 5, 1, "", 0, HN_NOSPACE
, 1, "1" },
35 { 5, 1, "", 0, 0, 2, "1 " }, /* just for reference */
36 { 5, 1, "", 0, HN_B
, 3, "1 B" }, /* and more ... */
37 { 5, 1, "", 0, HN_DECIMAL
, 2, "1 " },
38 { 5, 1, "", 0, HN_NOSPACE
| HN_B
, 2, "1B" },
39 { 5, 1, "", 0, HN_B
| HN_DECIMAL
, 3, "1 B" },
40 { 5, 1, "", 0, HN_NOSPACE
| HN_B
| HN_DECIMAL
, 2, "1B" },
43 * Space and HN_B. Rev. 1.7 produces "1B".
45 { 5, 1, "", HN_AUTOSCALE
, HN_B
, 3, "1 B" },
46 { 5, 1000, "", /* just for reference */
47 HN_AUTOSCALE
, HN_B
, 3, "1 K" },
50 * Truncated output. Rev. 1.7 produces "1.0 K".
52 { 6, 1000, "A", HN_AUTOSCALE
, HN_DECIMAL
, -1, "" },
55 * Failure case reported by Greg Troxel <gdt@NetBSD.org>.
56 * Rev. 1.11 incorrectly returns 5 with filling the buffer
60 HN_AUTOSCALE
, HN_B
| HN_NOSPACE
| HN_DECIMAL
, 4, "1.0G" },
61 /* Similar case it prints 1000 where it shouldn't */
63 HN_AUTOSCALE
, HN_B
| HN_NOSPACE
| HN_DECIMAL
, 4, "1.0M" },
65 HN_AUTOSCALE
, HN_B
| HN_NOSPACE
| HN_DECIMAL
, 4, "1.0M" },
73 const struct hnflags scale_flags
[] = {
74 { HN_GETSCALE
, "HN_GETSCALE" },
75 { HN_AUTOSCALE
, "HN_AUTOSCALE" },
77 const struct hnflags normal_flags
[] = {
78 { HN_DECIMAL
, "HN_DECIMAL" },
79 { HN_NOSPACE
, "HN_NOSPACE" },
81 { HN_DIVISOR_1000
, "HN_DIVISOR_1000" },
85 formatflags(char *, size_t, const struct hnflags
*, size_t, int);
87 void w_printf(const char *, ...);
88 int main(int, char *[]);
91 formatflags(char *buf
, size_t buflen
, const struct hnflags
*hfs
,
92 size_t hfslen
, int flags
)
94 const struct hnflags
*hf
;
100 snprintf(buf
, buflen
, "0");
103 for (i
= found
= 0; i
< hfslen
&& flags
& ~found
; i
++) {
105 if (flags
& hf
->hf_flags
) {
106 found
|= hf
->hf_flags
;
107 n
= snprintf(p
, len
, "|%s", hf
->hf_name
);
111 /* Print `flags' as number */
121 snprintf(p
, len
, "|0x%x", flags
);
122 return (*buf
== '|' ? buf
+ 1 : buf
);
125 static int col
, bol
= 1;
130 fprintf(stderr
, "\n");
136 w_printf(const char *fmt
, ...)
144 n
= vsnprintf(buf
, sizeof(buf
), fmt
, ap
);
145 if (n
>= sizeof(buf
)) {
153 fprintf(stderr
, "\n "), col
= 4;
155 fprintf(stderr
, " "), col
++;
157 fprintf(stderr
, "%s", buf
);
162 vfprintf(stderr
, fmt
, ap
);
169 main(int argc
, char *argv
[])
172 const struct hnopts
*ho
;
175 int i
, rv
, error
= 0;
177 for (i
= 0; i
< sizeof(hnopts
) / sizeof(hnopts
[0]); i
++) {
179 if (buflen
< ho
->ho_len
) {
181 buf
= realloc(buf
, buflen
);
183 err(1, "realloc(..., %d)", buflen
);
186 rv
= humanize_number(buf
, ho
->ho_len
, ho
->ho_num
,
187 ho
->ho_suffix
, ho
->ho_scale
, ho
->ho_flags
);
189 if (rv
== ho
->ho_retval
&&
190 (rv
== -1 || strcmp(buf
, ho
->ho_retstr
) == 0))
193 w_printf("humanize_number(\"%s\", %d, %" PRId64
",",
194 ho
->ho_retstr
, ho
->ho_len
, ho
->ho_num
);
195 w_printf("\"%s\",", ho
->ho_suffix
);
196 w_printf("%s,", formatflags(fbuf
, sizeof(fbuf
), scale_flags
,
197 sizeof(scale_flags
) / sizeof(scale_flags
[0]),
199 w_printf("%s)", formatflags(fbuf
, sizeof(fbuf
), normal_flags
,
200 sizeof(normal_flags
) / sizeof(normal_flags
[0]),
202 w_printf("= %d,", ho
->ho_retval
);
204 w_printf("%d/[%s]", rv
, rv
== -1 ? "" : buf
);
208 exit(error
? EXIT_FAILURE
: EXIT_SUCCESS
);