runtime: IndexOutOfRangeException in NumberFormatInfo

From @bmpcon on Friday, 17 August 2018 08:49:05

Hello,

when deploying a vanilla ASP.NET Core (2.1.1) WebApi application to our enterprise server (Windows 2016) we get the following exception when doing a request from localhost:

Application started. Press Ctrl+C to shut down.
fail: Microsoft.AspNetCore.Server.Kestrel[13]
      Connection id "0HLG41UURV0D2", Request id "0HLG41UURV0D2:00000001": An unhandled exception was thrown by the application.
System.IndexOutOfRangeException: Index was outside the bounds of the array.
   at System.Globalization.CultureData.GetNFIValues(NumberFormatInfo nfi)
   at System.Globalization.NumberFormatInfo..ctor(CultureData cultureData)
   at System.Globalization.CultureInfo.get_NumberFormat()
   at System.Globalization.NumberFormatInfo.get_CurrentInfo()
   at System.Int32.TryParse(String s, Int32& result)
   at Microsoft.AspNetCore.HttpOverrides.Internal.IPEndPointParser.TryParse(String addressWithPort, IPEndPoint& endpoint)
   at Microsoft.AspNetCore.HttpOverrides.ForwardedHeadersMiddleware.ApplyForwarders(HttpContext context)
   at Microsoft.AspNetCore.HttpOverrides.ForwardedHeadersMiddleware.Invoke(HttpContext context)
  at Microsoft.AspNetCore.HostFiltering.HostFilteringMiddleware.Invoke(HttpContext context)
   at Microsoft.AspNetCore.Hosting.Internal.RequestServicesContainerMiddleware.Invoke(HttpContext httpContext)
   at Microsoft.AspNetCore.Hosting.Internal.HostingApplication.ProcessRequestAsync(Context context)
   at Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http.HttpProtocol.ProcessRequests[TContext](IHttpApplication`1 application)

As a workaround we were able to solve the problem with changing the thread culture to en-us:

private static void SetCultureToUs()
{
    var cultureInfo = new CultureInfo("en-US");
    CultureInfo.DefaultThreadCurrentCulture = cultureInfo;
    CultureInfo.DefaultThreadCurrentUICulture = cultureInfo;
}

Copied from original issue: aspnet/BasicMiddleware#356

About this issue

  • Original URL
  • State: closed
  • Created 6 years ago
  • Comments: 22 (20 by maintainers)

Most upvoted comments

It would be a good idea if you can collect the registry contents on the failing machine of the following registry paths:

HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Nls
HKEY_CURRENT_USER\Control Panel\International

Maybe this can give any clue.

Do you have any custom culture data installed for the sv-SE culture?

From a cursory inspection of the method, it would seem this could only come from: https://github.com/dotnet/coreclr/blob/e0d680101a93797c9e1a049bf582a874e2cb4113/src/System.Private.CoreLib/shared/System/Globalization/CultureData.cs#L2364 which assumes we’ll get back exactly ten characters from the call to Windows (one for each digit 0 to 9).

Could you try running this and sharing the output:

using System;
using System.Runtime.InteropServices;

unsafe class Program
{
    static void Main()
    {
        string withOverride = GetDigits("sv-SE", true);
        string withoutOverride = GetDigits("sv-SE", false);
        Console.WriteLine("With:    " + withOverride);
        Console.WriteLine("Without: " + withoutOverride);
    }

    private static string GetDigits(string localeName, bool useUserOverride)
    {
        uint lctype = 0x00000013; // DIGITS
        if (!useUserOverride) lctype |= 0x80000000; // NOUSEROVERRIDE

        const int BUFFER_SIZE = 1024;
        char* pBuffer = stackalloc char[BUFFER_SIZE];
        int resultCode = GetLocaleInfoEx(localeName, lctype, pBuffer, BUFFER_SIZE);
        return resultCode > 0 ? new string(pBuffer) : null;
    }

    [DllImport("kernel32.dll", CharSet = CharSet.Unicode)]
    internal static extern int GetLocaleInfoEx(string lpLocaleName, uint LCType, void* lpLCData, int cchData);
}

?