-
Notifications
You must be signed in to change notification settings - Fork 215
Addition of shortcuts for bases that are powers of two and for base 10 to mp_radix_size #371
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
bn_s_mp_radix_size_radix_10.c
Outdated
| const uint64_t inv_log_2_10 = {0x4d104d427de7fbccULL}; | ||
| when MP_8BIT got the boot. | ||
| */ | ||
| const uint16_t inv_log_2_10[4] = {0x4d10u, 0x4d42u, 0x7de7u, 0xfbccu}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
how about
const uint8_t inv_log_2_10[] = {0x4du, 0x10u, 0x4du, 0x42u, 0x7du, 0xe7u, 0xfbu, 0xccu};
mp_int bi_bit_count, bi_k, t;
int i, bit_count;
if ((err = mp_init_multi(&bi_bit_count, &bi_k, &t, NULL)) != MP_OKAY) {
return err;
}
if ((err = mp_from_ubin(&bi_k, inv_log_2_10, sizeof(inv_log_2_10))) != MP_OKAY) {
return err;
}
...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, that would be simpler (and most likely even faster) but I didn't want to add a dependency on a function that you might not use elsewhere and once MP_8BIT is gone it is down to just two mp_get_u32, one big-shift and and one big-add.
But if you like it more with mp_from_ubin: drop me a note and I'll change it, no problem.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would prefer from_ubin which is the canonical importer for large integers from binary data. Alternatively you statically initialize the const mp_int, but then you have to recompute the array for each supported digit size.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Added a branch for MP_16BIT which is the only one left, since MP_8BIT got the boot, to need that part. Every other size must support 64 bit integers to function, which allow for a simple mp_set_u64 for that rest.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ok, but please unroll the loop. set, mul, set, add.
|
👍 |
|
Can we discuss this later for 2.0 and concentrate on finishing 1.2 now? |
fine by me, can you please put milestones on the open issues that you think should still go into 1.2? |
|
Ok, I will do. If nothing remains will you create a separate branch and we start on 2.0 in develop? |
eae202a to
5968fcc
Compare
|
@sjaeckel Yes, I must admit, I like this one most, too.
Don't worry, we're still threadsafe.
I hope you're talking to @sjaeckel here? ;-) |
ae47fef to
393bf3d
Compare
b7a420e to
bbdd25c
Compare
|
@czurnieden alternatively to #368 use this, which optimizes the function for base 10 only? And then don't provide mp_radix_overestimate? |
|
What do you prefer? |
This one has the extra functions for base 10 and powers-of-two and does the rest with
The original The second version, #368 , is a really rough one (but can be tamed down with an additional small table) and is, in my opinion, not really an alternative, even with the extra table.
I prefer this one: O(1) for base 10 and powers-of-two and the the rest with And there was the discussion that we restrict LTM to these bases which can be done with this PR quite quickly: just add a test for the bases given and replace the call to Yes, I really like this one. And now back to rebaseing *sigh* ;-) |
|
I don't want to restrict ltm to only a few bases. But we could offer optimized versions for base 10 for sure. Is the following a correct summary?
If we choose 2. or 3. we wouldn't need the overestimate function? This would make the API nicer. And we could still have the slower log fallback available via conditional MP_HAS compilation of that is preferred. Edit: so it is either 2 or 3. |
|
I think I agree with you then - we should take this version. |
bbdd25c to
ae492e0
Compare
|
|
||
| #define LTM_RADIX_SIZE_SCALE 64 | ||
| #define LTM_RADIX_SIZE_CONST_SHIFT 32 | ||
| int s_mp_radix_size_radix_10(const mp_int *a, size_t *size) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@czurnieden why don't you add a function s_mp_log10 which is called from mp_log and used indirectly bymp_radix_size?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I was, and still am, a bit torn between calling that optimization in mp_log or in mp_radix_size.
Calling it in mp_radix_size allows for easy reduction to the restricted radix-set 2,4,8,10,16,32,64 and would also getting rid of the dependency mp_log which isn't a very small function.
Calling it in mp_log is cleaner if we want to keep the full radix-set.
Mmh…
*strokes sesquipedalian beard*
I don't know.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Well, but you can strip down mp_log by disabling s_mp_log and only enabling the power of two and base 10 versions. We had that discussion in #389. I think it should go to mp_log since it is more general.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If you strip down 'mp_log' you don't have a general log-function anymore.
If you strip down 'mp_radix_size' you still have a radix-size function, just not for the small range of radices 2-64, only for the smaller range of powers-of-two and base 10.
You expect of a log-function that it works over the whole range, with no holes in it.
You expect from a radix-size function to work over a very small range, it might even have holes in it. Restricting the string out/input to only a handfull of bases, sometimes down to only two (10 and 16) won't get many complains (vid. e.g.: printf).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, but we don't get an optimized log function if we add the base10 optimization only to radix_size. We already have other functions with holes in it if configured as such.
Yepp, exactly. |
bn_mp_log_u32.c
Outdated
| /* SPDX-License-Identifier: Unlicense */ | ||
|
|
||
| /* Compute log_{base}(a) */ | ||
| static mp_word s_pow(mp_word base, mp_word exponent) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This file is called mp_log_u32.c in develop
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ah, great, knew that this large renaming would get me at some point! ;-)
|
I think I'll put this to rest, too and bury it beside #401 |
|
@czurnieden so shall we consider adding mp_radix_size_overestimate again? |
Back to where we started? Ok.
(You may add one to the upper limit for the sign to skip testing for the sign) Using the full tables makes only sense when we have a fast number conversion for all bases. I hacked something together to give @MasterDuke17 an example of how he might be able to extend his On the other side: the So: shall all bases belong to us, or shall we restrict versions ≥2.0.0 to the small set |
|
We shall not restrict the bases but we can provide faster to_radix/to_radix_overestimate for 10, 2^n. This is what I would like :) |
Both shortcuts are implemented as the internal functions
s_mp_radix_size_radix_10ands_mp_log_power_of_twoso it would be easy to make a functionmp_radix_sizerestricted to the bases{2,4,8,10,16,32,64}if that is wanted for version 2.0.0.