NetBSD-Bugs archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

lib/54053: humanize_number(HN_AUTOSCALE) with big buffer doesn't work.



>Number:         54053
>Category:       lib
>Synopsis:       humanize_number(HN_AUTOSCALE) with big buffer doesn't work.
>Confidential:   no
>Severity:       non-critical
>Priority:       low
>Responsible:    lib-bug-people
>State:          open
>Class:          sw-bug
>Submitter-Id:   net
>Arrival-Date:   Mon Mar 11 06:25:00 +0000 2019
>Originator:     msaitoh%execsw.org@localhost
>Release:        Any?
>Organization:
>Environment:
>Description:
	It seems using humanize_number(HN_AUTOSCALE) with big buffer doesn't work as expected.

------------------ test program ---------------
#include <assert.h>
#include <inttypes.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#ifdef __FreeBSD__
#include <libutil.h>
#endif

/*
 * bufsize	bps		result
 *
 *	40	1000000000	0 Ebps
 *	39	1000000000	1000000000 bps
 */
int
main(int argc, char *argv[])
{

	char buf[40];
	int64_t bps = 1000000000;
	int rv;
	
	rv = humanize_number(buf, sizeof(buf), bps, "bps",
	     HN_AUTOSCALE, HN_DIVISOR_1000);
	printf("\tbaudrate %s\n", buf);

	return rv;
}
-----------------------------------------

	1000000000 with buffer size 39 works:

		1000000000 bps

	1000000000 with buffer size 40 doesn't work:

		0 Ebps

	I added debug printf into humanize_number.c like below:

-------------------------------------
	/* Check if enough room for `x y' + suffix + `\0' */
	if (len < baselen + 1)
		return (-1);
#if 1
	printf("divisor = %ld\n", divisor);
	printf("    len = %ld\n", len);
	printf("baselen = %ld\n", baselen);
	printf("bytes = %ld\n", bytes);
#endif
	if (scale & (HN_AUTOSCALE | HN_GETSCALE)) {
		/* See if there is additional columns can be used. */
		for (max = 100, i = len - baselen; i-- > 0;) {
			printf("i = %zu, max   = %ld\n", i, max);
			max *= 10;
		}
-------------------------------------

	The output was:

./humanize_number
divisor = 1000
    len = 40
baselen = 6
bytes = 100000000000
i = 33, max   = 100
i = 32, max   = 1000
i = 31, max   = 10000
i = 30, max   = 100000
i = 29, max   = 1000000
i = 28, max   = 10000000
i = 27, max   = 100000000
i = 26, max   = 1000000000
i = 25, max   = 10000000000
i = 24, max   = 100000000000
i = 23, max   = 1000000000000
i = 22, max   = 10000000000000
i = 21, max   = 100000000000000
i = 20, max   = 1000000000000000
i = 19, max   = 10000000000000000
i = 18, max   = 100000000000000000
i = 17, max   = 1000000000000000000
i = 16, max   = -8446744073709551616
i = 15, max   = 7766279631452241920
i = 14, max   = 3875820019684212736
i = 13, max   = 1864712049423024128
i = 12, max   = 200376420520689664
i = 11, max   = 2003764205206896640
i = 10, max   = 1590897978359414784
i = 9, max   = -2537764290115403776
i = 8, max   = -6930898827444486144
i = 7, max   = 4477988020393345024
i = 6, max   = 7886392056514347008
i = 5, max   = 5076944270305263616
i = 4, max   = -4570789518076018688
i = 3, max   = -8814407033341083648
i = 2, max   = 4089650035136921600
i = 1, max   = 4003012203950112768
i = 0, max   = 3136633892082024448
        baudrate 0 Ebps

	Overflow?

>How-To-Repeat:
	See above.
>Fix:
	I don't know.



Home | Main Index | Thread Index | Old Index