Bug in ConvertOverflow_S ?

Hi,

I have a strange error with currency.
Below are my settings for silver and gold -> 1 gold equals 10 silver
currency_data_bug_gold.jpg
currency_data_bug_silver.jpg

I set the price for item to 500 silver. However, as the result I get 9 silver and 2147483647 gold. I tried to debug the problem and it looks like a source is in:

C#:
public static ListSlice<CurrencyAmount> ConvertOverflow_S(Currency currency, double amount, ref CurrencyAmount[] result)
        {
            var index = 0;

            var nextCurrency = currency;

            amount = Math.Truncate(amount);// ToIntSafe(amount);

            while (nextCurrency != null && amount > 0) {

                var mod = amount % (currency.MaxAmount + 1);

                var intMod = (int)mod;
                if (intMod > 0) {
                    TypeUtility.ResizeIfNecessary(ref result, index + 1);
                    result[index] = (intMod, nextCurrency);
                    index++;
                }

                if (amount - intMod <= 0d) { break; }

                if (nextCurrency.OverflowCurrency == null ||
                    !nextCurrency.TryGetExchangeRateTo(nextCurrency.OverflowCurrency, out var rate)) {
                    return MaxedOutAmount_S(nextCurrency, ref result);
                }

                amount -= mod;
                amount *= rate;
                nextCurrency = nextCurrency.OverflowCurrency;
            }

            return (result, 0, index);
        }

The amount is calculated but it is not save to the result structure. Or I missed something?

When I set the amount to 50 silver then everything works correctly.
Asset version 1.2.2
 
Well that is a very odd one, I have 100s of unit tests for testing CurrencyCollections. I don't know how that slipped through all the tests.
I added a unit test for your use case.

The issue is on this line
Code:
var mod = amount % (currency.MaxAmount + 1);
if should be
Code:
var mod = amount % (nextCurrency.MaxAmount + 1);

But one thing that is very particular with your setup is that you have int.Max as the max amount of gold.
So it now does int.Max + 1. That somehow still works because it becomes int.Min (thanks to 2's complement) and we are doing a modulus which doesn't car if the value is negative. So I'll leave it as is an not make an exemption.

Thank you for bringing this to my attention It'll be fixed in the next update, you can do the change manually in the meantime.
 
Top