ForNeVeR / ForNeVeR/Cesium

On locales and locale-specific behavior of formatting functions

Open
#560 5 comments 0 reactions 0 assignees View on GitHub
area:cil-interop area:infrastructure area:standard-support kind:feature status:help-wanted
Dominant language
C#
Stars
451
Forks
49
Avg merge
13h 59m
Merged PRs (30d)
6

Description

My general idea on locales in Cesium was the following:
1. C's "locale" stuff should be tied to .NET's `CultureInfo`.
2. We are okay to use the default .NET behavior (unwanted in most other programs, but not here) across the standard library, and rely on the global culture info being set up properly.

**Note** that I would really like to just drop this all into the trash bin and use the invariant culture universally. However, keeping in mind the C standard and programs written for alternative C implementations, I think that the best decision for the Cesium users is to make this user-controllable. That is, give the users the C API for locales.

@BadRyuner comments on the current behavior in #559: there are problems in our own tests that now implicitly rely on this locale stuff, and the locale treatment varies between implementations. In particular, Microsoft's C implementation doesn't seem to agree with… uhm, the Microsoft's .NET implementation on what decimal separator to use?

It's more or less easy to fix the tests by setting `DOTNET_SYSTEM_GLOBALIZATION_INVARIANT=true` when running them, but I no longer believe that the current's Cesium behavior is acceptable.

First of all, let me quote paragraph 2 from section **7.1.1 Definition of terms** of the C standard we use:
> The _decimal-point character_ is the character used by functions that convert floating-point numbers to or from character sequences to denote the beginning of the fractional part of such character sequences. It is represented in the text and examples by a period, but may be changed by the `setlocale` function.

So, we are right in that `printf` should consult to locale.

But then, let's also go to **7.11.1.1 The `setlocale` function** and read paragraph 4:
> At program startup, the equivalent of
> ```c
> setlocale(LC_ALL, "C");
> ```
> is executed.

This means that every Cesium program that adheres the C standard should have an equivalent of the default "C" locale set on by default. I believe that one is most commonly associated with the culture-invariant environment in other C implementations; for now I didn't look it up in the standard, but that's the common practice, so let's stick with that for now.

So, should we just do something like `CultureInfo.CurrentCulture = InvariantCulture` in the `main` function by default? I think we should.

See also: https://github.com/ForNeVeR/Cesium/pull/770 (here we've set up the proposed default for some functions).

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.