1 /****************************************************************************/
2 /*                          APQ DATABASE BINDINGS                           */
3 /*                                                                          */
4 /*                            A P Q - POSTGRESQL			    */
5 /*                                                                          */
6 /*		                  S p e c                                   */
7 /*                                                                          */
8 /*         Copyright (C) 2002-2007, Warren W. Gay VE3WWG                    */
9 /*         Copyright (C) 2007-2009, Ada Works Project                       */
10 /*                                                                          */
11 /*                                                                          */
12 /* APQ is free software;  you can  redistribute it  and/or modify it under  */
13 /* terms of the  GNU General Public License as published  by the Free Soft- */
14 /* ware  Foundation;  either version 2,  or (at your option) any later ver- */
15 /* sion.  APQ is distributed in the hope that it will be useful, but WITH-  */
16 /* OUT ANY WARRANTY;  without even the  implied warranty of MERCHANTABILITY */
17 /* or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License */
18 /* for  more details.  You should have  received  a copy of the GNU General */
19 /* Public License  distributed with APQ;  see file COPYING.  If not, write  */
20 /* to  the Free Software Foundation,  59 Temple Place - Suite 330,  Boston, */
21 /* MA 02111-1307, USA.                                                      */
22 /*                                                                          */
23 /* As a special exception,  if other files  instantiate  generics from this */
24 /* unit, or you link  this unit with other files  to produce an executable, */
25 /* this  unit  does not  by itself cause  the resulting  executable  to  be */
26 /* covered  by the  GNU  General  Public  License.  This exception does not */
27 /* however invalidate  any other reasons why  the executable file  might be */
28 /* covered by the  GNU Public License.                                      */
29 /****************************************************************************/
30 
31 
32 #ifndef _PG_NUMERIC_H_
33 #define _PG_NUMERIC_H_
34 
35 /* ----------
36  * The hardcoded limits and defaults of the numeric data type
37  * ----------
38  */
39 #define NUMERIC_MAX_PRECISION		1000
40 #define NUMERIC_DEFAULT_PRECISION	30
41 #define NUMERIC_DEFAULT_SCALE		6
42 
43 
44 /* ----------
45  * Internal limits on the scales chosen for calculation results
46  * ----------
47  */
48 #define NUMERIC_MAX_DISPLAY_SCALE	NUMERIC_MAX_PRECISION
49 #define NUMERIC_MIN_DISPLAY_SCALE	(NUMERIC_DEFAULT_SCALE + 4)
50 
51 #define NUMERIC_MAX_RESULT_SCALE	(NUMERIC_MAX_PRECISION * 2)
52 #define NUMERIC_MIN_RESULT_SCALE	(NUMERIC_DEFAULT_PRECISION + 4)
53 
54 /* ----------
55  * Sign values and macros to deal with packing/unpacking n_sign_dscale
56  * ----------
57  */
58 #define NUMERIC_SIGN_MASK	0xC000
59 #define NUMERIC_POS			0x0000
60 #define NUMERIC_NEG			0x4000
61 #define NUMERIC_NAN			0xC000
62 #define NUMERIC_DSCALE_MASK 0x3FFF
63 #define NUMERIC_SIGN(n)		((n)->n_sign_dscale & NUMERIC_SIGN_MASK)
64 #define NUMERIC_DSCALE(n)	((n)->n_sign_dscale & NUMERIC_DSCALE_MASK)
65 #define NUMERIC_IS_NAN(n)	(NUMERIC_SIGN(n) != NUMERIC_POS &&			\
66 								NUMERIC_SIGN(n) != NUMERIC_NEG)
67 
68 /* ----------
69  * The Numeric data type stored in the database
70  *
71  * NOTE: by convention, values in the packed form have been stripped of
72  * all leading and trailing zeroes (except there will be a trailing zero
73  * in the last byte, if the number of digits is odd).  In particular,
74  * if the value is zero, there will be no digits at all!  The weight is
75  * arbitrary in that case, but we normally set it to zero.
76  * ----------
77  */
78 typedef struct NumericData
79 {
80 	int32		varlen;			/* Variable size		*/
81 	int16		n_weight;		/* Weight of 1st digit	*/
82 	uint16		n_rscale;		/* Result scale			*/
83 	uint16		n_sign_dscale;	/* Sign + display scale */
84 	unsigned char n_data[1];	/* Digit data (2 decimal digits/byte) */
85 } NumericData;
86 typedef NumericData *Numeric;
87 
88 #define NUMERIC_HDRSZ	(sizeof(int32) + sizeof(uint16) * 3)
89 
90 #endif   /* _PG_NUMERIC_H_ */
91