Right padding a string with interpolated strings throw a System.FormatException
Code to reproduce:
using System;
namespace tmp5
{
class Program
{
static void Main(string[] args)
{
var st = "1";
var st2 = $"{st,100}"; // Ok
var st3 = $"{st,-100}"; // FormatException here
}
}
}
Bug reproduced with net5.0 and netcore3.0 build target.
dotnet --info
.NET SDK (reflecting any global.json):
Version: 5.0.100
Commit: 5044b93829
Runtime Environment:
OS Name: ubuntu
OS Version: 18.04
OS Platform: Linux
RID: ubuntu.18.04-x64
Base Path: /usr/share/dotnet/sdk/5.0.100/
Host (useful for support):
Version: 5.0.0
Commit: cf258a14b7
.NET SDKs installed:
3.1.404 [/usr/share/dotnet/sdk]
5.0.100 [/usr/share/dotnet/sdk]
.NET runtimes installed:
Microsoft.AspNetCore.App 3.1.10 [/usr/share/dotnet/shared/Microsoft.AspNetCore.App]
Microsoft.AspNetCore.App 5.0.0 [/usr/share/dotnet/shared/Microsoft.AspNetCore.App]
Microsoft.NETCore.App 3.1.10 [/usr/share/dotnet/shared/Microsoft.NETCore.App]
Microsoft.NETCore.App 5.0.0 [/usr/share/dotnet/shared/Microsoft.NETCore.App]
Operating System: Feren OS 2020.07
KDE Plasma Version: 5.19.4
KDE Frameworks Version: 5.72.0
Qt Version: 5.14.2
Kernel Version: 5.4.0-56-generic
OS Type: 64-bit
Processors: 16 × AMD Ryzen 7 3700X 8-Core Processor
Memory: 31,4 GiB of RAM
Graphics Processor: AMD Radeon RX 5700
Found this when porting a project from .net framework 4.6.
I have found no workarounds.
I couldn't figure out the best area label to add to this issue. If you have write-permissions please help me learn by adding exactly one area label.
I tried this on both .NET Core 3.1 and .NET 5, on both Windows and Ubuntu, and I could not repro a FormatException.
It is 100% reproducible for me. I don't what more info I can add.
Exception has occurred: CLR/System.FormatException
Exception thrown: 'System.FormatException' in System.Private.CoreLib.dll: 'Input string was not in a correct format.'
at System.Text.ValueStringBuilder.ThrowFormatError()
at System.Text.ValueStringBuilder.AppendFormatHelper(IFormatProvider provider, String format, ParamsArray args)
at System.String.FormatHelper(IFormatProvider provider, String format, ParamsArray args)
at System.String.Format(String format, Object arg0)
at tmp5.Program.Main(String[] args) in tmp5/Program.cs:line 11
What is your CultureInfo.CurrentCulture?
Console.WriteLine( System.Globalization.CultureInfo.CurrentCulture );
sv-SE
LANG="en_US.UTF-8" LANGUAGE=en LC_CTYPE="en_US.UTF-8" dotnet ./bin/Debug/net5.0/tmp5.dll
Same result. Still FormatException. This still reported CultureInfo.CurrentCulture sv-SE though.
With
LANG="en_US.UTF-8" LANGUAGE="en" LC_CTYPE="en_US.UTF-8" LC_ALL="en_US.UTF-8" dotnet ./bin/Debug/net5.0/tmp5.dll
CultureInfo.CurrentCulture is en-US. I still get the FormatException.
I'm guessing this is due to the CLDR defining the minus sign as − rather than - for sv-SE:
https://github.com/dotnet/runtime/issues/44678#issuecomment-727261177
I couldn't figure out the best area label to add to this issue. If you have write-permissions please help me learn by adding exactly one area label.
Tagging subscribers to this area: @tarekgh, @safern, @krwq
See info in area-owners.md if you want to be subscribed.
Issue Details
Right padding a string with interpolated strings throw a System.FormatException
Code to reproduce:
using System;
namespace tmp5
{
class Program
{
static void Main(string[] args)
{
var st = "1";
var st2 = $"{st,100}"; // Ok
var st3 = $"{st,-100}"; // FormatException here
}
}
}
Bug reproduced with net5.0 and netcore3.0 build target.
dotnet --info
.NET SDK (reflecting any global.json):
Version: 5.0.100
Commit: 5044b93829
Runtime Environment:
OS Name: ubuntu
OS Version: 18.04
OS Platform: Linux
RID: ubuntu.18.04-x64
Base Path: /usr/share/dotnet/sdk/5.0.100/
Host (useful for support):
Version: 5.0.0
Commit: cf258a14b7
.NET SDKs installed:
3.1.404 [/usr/share/dotnet/sdk]
5.0.100 [/usr/share/dotnet/sdk]
.NET runtimes installed:
Microsoft.AspNetCore.App 3.1.10 [/usr/share/dotnet/shared/Microsoft.AspNetCore.App]
Microsoft.AspNetCore.App 5.0.0 [/usr/share/dotnet/shared/Microsoft.AspNetCore.App]
Microsoft.NETCore.App 3.1.10 [/usr/share/dotnet/shared/Microsoft.NETCore.App]
Microsoft.NETCore.App 5.0.0 [/usr/share/dotnet/shared/Microsoft.NETCore.App]
Operating System: Feren OS 2020.07
KDE Plasma Version: 5.19.4
KDE Frameworks Version: 5.72.0
Qt Version: 5.14.2
Kernel Version: 5.4.0-56-generic
OS Type: 64-bit
Processors: 16 × AMD Ryzen 7 3700X 8-Core Processor
Memory: 31,4 GiB of RAM
Graphics Processor: AMD Radeon RX 5700
Found this when porting a project from .net framework 4.6.
I have found no workarounds.
| Author: | PeterZander |
|---|---|
| Assignees: | - |
| Labels: | `area-System.Globalization` |
| Milestone: | - |
@stephentoub
I'm guessing this is due to the CLDR defining the minus sign as − rather than - for sv-SE:
I don't think this is the case. Looking at AppendFormatHelper which throw this exception, it doesn't throw the exception because of any related reason.
@PeterZander
I ran the same code on Windows and Ubuntu 18.04 and I couldn't reproduce the issue. the only possible reason I can think of that can cause this issue is the line
```C#
var st3 = $"{st,-100}";
contains characters that not really what we think it is. like `-` could be not the real the hyphen. could you please try to run the following code in the exact string you used to reproduce the issue and send the output? just ensure you copy and paste the string text and not retyping it.
```C#
var st3 = "{st,-100}";
foreach (char c in st3)
{
Console.Write("{0:x}", (int)c);
}
Result (copy and pasting the code above):
7b73742c2d3130307d
Using the original string in my code (removing the initial "$" to not make it interpolated):
7b73742c2d3130307d
Interesting, the string looks fine and shouldn't cause this issue. is it possible you can debug it on your environment as we cannot reproduce it?
How do I do that? Is there any guide?
You may try Visual Studio Code first https://code.visualstudio.com/docs/editor/debugging with installing the Omnisharp extensionhttps://marketplace.visualstudio.com/items?itemName=ms-dotnettools.csharp. and ensure your debugging configuration something like the following:
{
// Use IntelliSense to find out which attributes exist for C# debugging
// Use hover for the description of the existing attributes
// For further information visit https://github.com/OmniSharp/omnisharp-vscode/blob/master/debugger-launchjson.md
"version": "0.2.0",
"configurations": [
{
"name": ".NET Core Launch (console)",
"type": "coreclr",
"request": "launch",
"preLaunchTask": "build",
// If you have changed target frameworks, make sure to update the program path.
"program": "${workspaceFolder}/bin/Debug/netcoreapp3.1/NetCoreApp.dll",
"args": [],
"cwd": "${workspaceFolder}",
// For more information about the 'console' field, see https://aka.ms/VSCode-CS-LaunchJson-Console
"console": "internalConsole",
"justMyCode": false,
"suppressJITOptimizations": false,
"stopAtEntry": true
},
{
"name": ".NET Core Attach",
"type": "coreclr",
"request": "attach",
"processId": "${command:pickProcess}"
}
]
}
I don't get more info, just:
Exception has occurred: CLR/System.FormatException
An unhandled exception of type 'System.FormatException' occurred in System.Private.CoreLib.dll: 'Input string was not in a correct format.'
at System.Text.ValueStringBuilder.ThrowFormatError()
at System.Text.ValueStringBuilder.AppendFormatHelper(IFormatProvider provider, String format, ParamsArray args)
at System.String.FormatHelper(IFormatProvider provider, String format, ParamsArray args)
at System.String.Format(String format, Object arg0)
at tmp5.Program.Main(String[] args) in /home/peter/src/tmp5/Program.cs:line 12
I don't think I got these lines in the debug output before though:
Loaded '/usr/share/dotnet/shared/Microsoft.NETCore.App/5.0.0/System.Private.CoreLib.dll'. Cannot find or open the PDB file.
Couldn't reproduce the exception with sv-SE on Ubuntu 18.04 running .NET 5.0.0: https://dotnetfiddle.net/apDcdb.
@PeterZander in the debugger configuration file launch.json, please ensure you have the following properties:
"justMyCode": false,
"symbolOptions": {
"searchPaths": [],
"searchMicrosoftSymbolServer": true,
"searchNuGetOrgSymbolServer": true
},
I believe this will help downloading the needed symbols when you start the debugging.
That worked.
It looks like it is the compiler.
Setting a break point at:
var st4 = $"{st,-100}"; // FormatException here
and stepping into String.Manipulation.cs
public static string Format(string format, object? arg0)
{
return FormatHelper(null, format, new ParamsArray(arg0));
}
format is "{0,−100}"
and the minus is not detected on line 196 in ValueStringBuilder.AppendFormat.cs
// Is there a minus sign?
ch = format[pos];
if (ch == '-') // Line 196
{
Could it be line 84 in file src/Compilers/CSharp/Portable/Lowering/LocalRewriter/LocalRewriter_StringInterpolation.cs
(roslyn) that is causing this by localizing the int64?
84 stringBuilder.Append(',').Append(fillin.Alignment.ConstantValue.Int64Value);
That does appear to be the culprit (potentially there are other places, too); nice job tracking it down. It also explains why it was so hard to repro. Upon first compilation, the compiler spins up a compilation server that's used for subsequent compilations, and it picks up whatever locale was set at the time it was spun up; even if the locale was changed subsequently, additional compilations would still end up using the original locale. Killing the server after each operation makes it easier to repro.
Most helpful comment
Could it be line 84 in file src/Compilers/CSharp/Portable/Lowering/LocalRewriter/LocalRewriter_StringInterpolation.cs
(roslyn) that is causing this by localizing the int64?