Complete 64-bit division support.

* grub-core/kern/misc.c (grub_divmod64): Rename to ...
	(grub_divmod64_full): ... this. Support 64-bit divisor and reminder.
	* include/grub/misc.h (grub_divmod64): Rename to ...
	(grub_divmod64_full): ... this.
	(grub_divmod64): New inline function.
This commit is contained in:
Vladimir 'phcoder' Serbinenko 2011-04-18 23:03:52 +02:00
parent a5102d9433
commit 93a777e388
3 changed files with 31 additions and 9 deletions

View File

@ -1,3 +1,13 @@
2011-04-18 Vladimir Serbinenko <phcoder@gmail.com>
Complete 64-bit division support.
* grub-core/kern/misc.c (grub_divmod64): Rename to ...
(grub_divmod64_full): ... this. Support 64-bit divisor and reminder.
* include/grub/misc.h (grub_divmod64): Rename to ...
(grub_divmod64_full): ... this.
(grub_divmod64): New inline function.
2011-04-18 Vladimir Serbinenko <phcoder@gmail.com>
* util/grub-mkimage.c (generate_image): Add forgotten comma.

View File

@ -597,23 +597,23 @@ grub_reverse (char *str)
/* Divide N by D, return the quotient, and store the remainder in *R. */
grub_uint64_t
grub_divmod64 (grub_uint64_t n, grub_uint32_t d, grub_uint32_t *r)
grub_divmod64_full (grub_uint64_t n, grub_uint64_t d, grub_uint64_t *r)
{
/* This algorithm is typically implemented by hardware. The idea
is to get the highest bit in N, 64 times, by keeping
upper(N * 2^i) = upper((Q * 10 + M) * 2^i), where upper
upper(N * 2^i) = (Q * D + M), where upper
represents the high 64 bits in 128-bits space. */
unsigned bits = 64;
unsigned long long q = 0;
unsigned m = 0;
grub_uint64_t q = 0;
grub_uint64_t m = 0;
/* Skip the slow computation if 32-bit arithmetic is possible. */
if (n < 0xffffffff)
if (n < 0xffffffff && d < 0xffffffff)
{
if (r)
*r = ((grub_uint32_t) n) % d;
*r = ((grub_uint32_t) n) % (grub_uint32_t) d;
return ((grub_uint32_t) n) / d;
return ((grub_uint32_t) n) / (grub_uint32_t) d;
}
while (bits--)

View File

@ -287,8 +287,20 @@ char *EXPORT_FUNC(grub_xasprintf) (const char *fmt, ...)
char *EXPORT_FUNC(grub_xvasprintf) (const char *fmt, va_list args) __attribute__ ((warn_unused_result));
void EXPORT_FUNC(grub_exit) (void) __attribute__ ((noreturn));
void EXPORT_FUNC(grub_abort) (void) __attribute__ ((noreturn));
grub_uint64_t EXPORT_FUNC(grub_divmod64) (grub_uint64_t n,
grub_uint32_t d, grub_uint32_t *r);
grub_uint64_t EXPORT_FUNC(grub_divmod64_full) (grub_uint64_t n,
grub_uint64_t d,
grub_uint64_t *r);
static inline grub_uint64_t grub_divmod64 (grub_uint64_t n,
grub_uint32_t d,
grub_uint32_t *r)
{
grub_uint64_t ret, rr;
ret = grub_divmod64_full (n, d, &rr);
if (r)
*r = rr;
return ret;
}
#if NEED_ENABLE_EXECUTE_STACK && !defined(GRUB_UTIL)
void EXPORT_FUNC(__enable_execute_stack) (void *addr);