X-Git-Url: http://sigrok.org/gitweb/?a=blobdiff_plain;f=src%2Fstrutil.c;h=050f37bf7090532cc67282e07c10ce2867a985b6;hb=HEAD;hp=63cd2fdfc62baf8e2ea65b88f9a0378ceee3a23e;hpb=227913f26433bb09b353c2339c1ecc339692df61;p=libsigrok.git diff --git a/src/strutil.c b/src/strutil.c index 63cd2fdf..2136bd49 100644 --- a/src/strutil.c +++ b/src/strutil.c @@ -1819,4 +1819,57 @@ SR_API char *sr_text_next_word(char *s, char **next) return word; } +/** + * Get the number of necessary bits to hold a given value. Also gets + * the next power-of-two value at or above the caller provided value. + * + * @param[in] value The value that must get stored. + * @param[out] bits The required number of bits. + * @param[out] power The corresponding power-of-two. + * + * @return SR_OK upon success, SR_ERR* otherwise. + * + * TODO Move this routine to a more appropriate location, it is not + * strictly string related. + * + * @since 0.6.0 + */ +SR_API int sr_next_power_of_two(size_t value, size_t *bits, size_t *power) +{ + size_t need_bits; + size_t check_mask; + + if (bits) + *bits = 0; + if (power) + *power = 0; + + /* + * Handle the special case of input value 0 (needs 1 bit + * and results in "power of two" value 1) here. It is not + * covered by the generic logic below. + */ + if (!value) { + if (bits) + *bits = 1; + if (power) + *power = 1; + return SR_OK; + } + + need_bits = 0; + check_mask = 0; + do { + need_bits++; + check_mask <<= 1; + check_mask |= 1UL << 0; + } while (value & ~check_mask); + + if (bits) + *bits = need_bits; + if (power) + *power = ++check_mask; + return SR_OK; +} + /** @} */