/* Test locale support in C++ functions.

Copyright 2001-2003, 2007 Free Software Foundation, Inc.

This file is part of the GNU MP Library test suite.

The GNU MP Library test suite is free software; you can redistribute it
and/or modify it under the terms of the GNU General Public License as
published by the Free Software Foundation; either version 3 of the License,
or (at your option) any later version.

The GNU MP Library test suite is distributed in the hope that it will be
useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General
Public License for more details.

You should have received a copy of the GNU General Public License along with
the GNU MP Library test suite.  If not, see https://www.gnu.org/licenses/.  */

#include <clocale>
#include <iostream>
#include <cstdlib>

#include "gmp-impl.h"
#include "tests.h"

using namespace std;


extern "C" {
  char point_string[2];
}

#if HAVE_STD__LOCALE
// Like std::numpunct, but with decimal_point coming from point_string[].
class my_numpunct : public numpunct<char> {
 public:
  explicit my_numpunct (size_t r = 0) : numpunct<char>(r) { }
 protected:
  char do_decimal_point() const { return point_string[0]; }
};
#endif

void
set_point (char c)
{
  point_string[0] = c;

#if HAVE_STD__LOCALE
  locale loc (locale::classic(), new my_numpunct ());
  locale::global (loc);
#endif
}


void
check_input (void)
{
  static const struct {
    const char  *str1;
    const char  *str2;
    double      want;
  } data[] = {

    { "1","",   1.0 },
    { "1","0",  1.0 },
    { "1","00", 1.0 },

    { "","5",    0.5 },
    { "0","5",   0.5 },
    { "00","5",  0.5 },
    { "00","50", 0.5 },

    { "1","5",    1.5 },
    { "1","5e1", 15.0 },
  };

  static char point[] = {
    '.', ',', 'x', '\xFF'
  };

  mpf_t  got;
  mpf_init (got);

  for (size_t i = 0; i < numberof (point); i++)
    {
      set_point (point[i]);

      for (int neg = 0; neg <= 1; neg++)
        {
          for (size_t j = 0; j < numberof (data); j++)
            {
              string str = string(data[j].str1)+point[i]+string(data[j].str2);
              if (neg)
                str = "-" + str;

              istringstream is (str.c_str());

              mpf_set_ui (got, 123);   // dummy initial value

              if (! (is >> got))
                {
                  cout << "istream mpf_t operator>> error\n";
                  cout << "  point " << point[i] << "\n";
                  cout << "  str   \"" << str << "\"\n";
                  cout << "  localeconv point \""
                       << GMP_DECIMAL_POINT << "\"\n";
                  abort ();
                }

              double want = data[j].want;
              if (neg)
                want = -want;
              if (mpf_cmp_d (got, want) != 0)
                {
                  cout << "istream mpf_t operator>> wrong\n";
                  cout << "  point " << point[i] << "\n";
                  cout << "  str   \"" << str << "\"\n";
                  cout << "  got   " << got << "\n";
                  cout << "  want  " << want << "\n";
                  cout << "  localeconv point \""
                       << GMP_DECIMAL_POINT << "\"\n";
                  abort ();
                }
            }
        }
    }

  mpf_clear (got);
}

void
check_output (void)
{
  static char point[] = {
    '.', ',', 'x', '\xFF'
  };

  for (size_t i = 0; i < numberof (point); i++)
    {
      set_point (point[i]);
      ostringstream  got;

      mpf_t  f;
      mpf_init (f);
      mpf_set_d (f, 1.5);
      got << f;
      mpf_clear (f);

      string  want = string("1") + point[i] + string("5");

      if (want.compare (got.str()) != 0)
        {
          cout << "ostream mpf_t operator<< doesn't respect locale\n";
          cout << "  point " << point[i] << "\n";
          cout << "  got   \"" << got.str() << "\"\n";
          cout << "  want  \"" << want      << "\"\n";
          abort ();
        }
    }
}

int
replacement_works (void)
{
  set_point ('x');
  mpf_t  f;
  mpf_init (f);
  mpf_set_d (f, 1.5);
  ostringstream s;
  s << f;
  mpf_clear (f);

  return (s.str().compare("1x5") == 0);
}

int
main (void)
{
  tests_start ();

  if (replacement_works())
    {
      check_input ();
      check_output ();
    }
  else
    {
      cout << "Replacing decimal point didn't work, tests skipped\n";
    }

  tests_end ();
  return 0;
}
