/* Copyright (C) 2007-2018 Free Software Foundation, Inc.

This file is part of GCC.

GCC 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, or (at your option) any later
version.

GCC 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.

Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.

You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
<http://www.gnu.org/licenses/>.  */

#define decimal32FromString __dpd32FromString
#define decimal32ToString __dpd32ToString
#define decimal32ToEngString __dpd32ToEngString
#define decimal32FromNumber __dpd32FromNumber
#define decimal32ToNumber __dpd32ToNumber

#include "dpd/decimal32.c"

#undef decimal32FromString
#undef decimal32ToString
#undef decimal32ToEngString
#undef decimal32FromNumber
#undef decimal32ToNumber

#include "bid-dpd.h"

#ifdef IN_LIBGCC2
#define decimal32FromString __decimal32FromString
#define decimal32ToString __decimal32ToString
#define decimal32ToEngString __decimal32ToEngString
#define decimal32FromNumber __decimal32FromNumber
#define decimal32ToNumber __decimal32ToNumber
#endif

decimal32 *decimal32FromString (decimal32 *, const char *, decContext *);
char *decimal32ToString (const decimal32 *, char *);
char *decimal32ToEngString (const decimal32 *, char *);
decimal32 *decimal32FromNumber (decimal32 *, const decNumber *, decContext *);
decNumber *decimal32ToNumber (const decimal32 *, decNumber *);

void __host_to_ieee_32 (_Decimal32 in, decimal32 *out);
void __ieee_to_host_32 (decimal32 in, _Decimal32 *out);

decimal32 *
decimal32FromNumber (decimal32 *d32, const decNumber *dn,
		      decContext *set)
{
  /* decimal32 and _Decimal32 are different types.  */
  union
    {
      _Decimal32 _Dec;
      decimal32 dec;
    } u;

  __dpd32FromNumber (d32, dn, set);

  /* __dpd32FromNumber returns in big endian. But _dpd_to_bid32 takes
     host endian. */
  __ieee_to_host_32 (*d32, &u._Dec);

  /* Convert DPD to BID.  */
  _dpd_to_bid32 (&u._Dec, &u._Dec);

  /* dfp.c is in bid endian. */
  __host_to_ieee_32 (u._Dec, &u.dec);

  /* d32 is returned as a pointer to _Decimal32 here.  */
  *d32 = u.dec;

  return d32;
}

decNumber *
decimal32ToNumber (const decimal32 *bid32, decNumber *dn)
{
  /* decimal32 and _Decimal32 are different types.  */
  union
    {
      _Decimal32 _Dec;
      decimal32 dec;
    } u;

  /* bid32 is a pointer to _Decimal32 in bid endian. But _bid_to_dpd32
     takes host endian.  */
  __ieee_to_host_32 (*bid32, &u._Dec);

  /* Convert BID to DPD.  */
  _bid_to_dpd32 (&u._Dec, &u._Dec);

  /* __dpd32ToNumber is in bid endian.  */
  __host_to_ieee_32 (u._Dec, &u.dec);

  return __dpd32ToNumber (&u.dec, dn);
}

char *
decimal32ToString (const decimal32 *d32, char *string)
{
  decNumber dn;			/* work */
  decimal32ToNumber (d32, &dn);
  decNumberToString (&dn, string);
  return string;
}

char *
decimal32ToEngString (const decimal32 *d32, char *string)
{
  decNumber dn;			/* work */
  decimal32ToNumber (d32, &dn);
  decNumberToEngString (&dn, string);
  return string;
}

decimal32 *
decimal32FromString (decimal32 *result, const char *string,
		      decContext *set)
{
  decContext dc;		/* work */
  decNumber dn;			/* .. */

  decContextDefault (&dc, DEC_INIT_DECIMAL32);	/* no traps, please */
  dc.round = set->round;	/* use supplied rounding */

  decNumberFromString (&dn, string, &dc);	/* will round if needed */
  decimal32FromNumber (result, &dn, &dc);
  if (dc.status != 0)
    {				/* something happened */
      decContextSetStatus (set, dc.status);	/* .. pass it on */
    }
  return result;
}
