Annotation of OpenXM_contrib/gmp/mpn/tests/tst-addsub.c, Revision 1.1.1.2
1.1.1.2 ! maekawa 1: /*
! 2: Copyright (C) 1996 Free Software Foundation, Inc.
! 3:
! 4: This file is part of the GNU MP Library.
! 5:
! 6: The GNU MP Library is free software; you can redistribute it and/or modify
! 7: it under the terms of the GNU Lesser General Public License as published by
! 8: the Free Software Foundation; either version 2.1 of the License, or (at your
! 9: option) any later version.
! 10:
! 11: The GNU MP Library is distributed in the hope that it will be useful, but
! 12: WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
! 13: or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
! 14: License for more details.
! 15:
! 16: You should have received a copy of the GNU Lesser General Public License
! 17: along with the GNU MP Library; see the file COPYING.LIB. If not, write to
! 18: the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
! 19: MA 02111-1307, USA.
! 20: */
! 21:
1.1 maekawa 22: #include <stdio.h>
23: #include <stdlib.h>
24: #include "gmp.h"
25: #include "gmp-impl.h"
26:
27: #define ADD 1
28: #define SUB 2
29:
30: #ifndef METHOD
31: #define METHOD ADD
32: #endif
33:
34: #if METHOD == ADD
35: #define REFCALL refmpn_add_n
36: #define TESTCALL mpn_add_n
37: #endif
38:
39: #if METHOD == SUB
40: #define REFCALL refmpn_sub_n
41: #define TESTCALL mpn_sub_n
42: #endif
43:
44: mp_limb_t refmpn_add_n ();
45: mp_limb_t refmpn_sub_n ();
46:
47: #define SIZE 100
48:
49: main (argc, argv)
50: int argc;
51: char **argv;
52: {
53: mp_size_t alloc_size, max_size, size, i, cumul_size;
54: mp_ptr s1, s2, dx, dy;
55: int s1_align, s2_align, d_align;
56: long pass, n_passes;
57: mp_limb_t cx, cy;
58:
59: max_size = SIZE;
60: n_passes = 1000000;
61:
62: argc--; argv++;
63: if (argc)
64: {
65: max_size = atol (*argv);
66: argc--; argv++;
67: }
68:
69: alloc_size = max_size + 32;
70: s1 = malloc (alloc_size * BYTES_PER_MP_LIMB);
71: s2 = malloc (alloc_size * BYTES_PER_MP_LIMB);
72: dx = malloc (alloc_size * BYTES_PER_MP_LIMB);
73: dy = malloc (alloc_size * BYTES_PER_MP_LIMB);
74:
75: cumul_size = 0;
76: for (pass = 0; pass < n_passes; pass++)
77: {
78: cumul_size += size;
79: if (cumul_size >= 1000000)
80: {
81: cumul_size -= 1000000;
82: printf ("%d ", pass); fflush (stdout);
83: }
84: s1_align = random () % 32;
85: s2_align = random () % 32;
86: d_align = random () % 32;
87:
88: size = random () % max_size + 1;
89:
90: mpn_random2 (s1 + s1_align, size);
91: mpn_random2 (s2 + s2_align, size);
92:
93: for (i = 0; i < alloc_size; i++)
94: dx[i] = dy[i] = i + 0x9876500;
95:
96: cx = TESTCALL (dx + d_align, s1 + s1_align, s2 + s2_align, size);
97: cy = REFCALL (dy + d_align, s1 + s1_align, s2 + s2_align, size);
98:
99: if (cx != cy || mpn_cmp (dx, dy, alloc_size) != 0)
100: abort ();
101: }
102:
103: printf ("%d passes OK\n", n_passes);
104: exit (0);
105: }
106:
107: mp_limb_t
108: #if __STDC__
109: refmpn_add_n (mp_ptr res_ptr,
110: mp_srcptr s1_ptr, mp_srcptr s2_ptr, mp_size_t size)
111: #else
112: refmpn_add_n (res_ptr, s1_ptr, s2_ptr, size)
113: register mp_ptr res_ptr;
114: register mp_srcptr s1_ptr;
115: register mp_srcptr s2_ptr;
116: mp_size_t size;
117: #endif
118: {
119: register mp_limb_t x, y, cy;
120: register mp_size_t j;
121:
122: /* The loop counter and index J goes from -SIZE to -1. This way
123: the loop becomes faster. */
124: j = -size;
125:
126: /* Offset the base pointers to compensate for the negative indices. */
127: s1_ptr -= j;
128: s2_ptr -= j;
129: res_ptr -= j;
130:
131: cy = 0;
132: do
133: {
134: y = s2_ptr[j];
135: x = s1_ptr[j];
136: y += cy; /* add previous carry to one addend */
137: cy = (y < cy); /* get out carry from that addition */
138: y = x + y; /* add other addend */
139: cy = (y < x) + cy; /* get out carry from that add, combine */
140: res_ptr[j] = y;
141: }
142: while (++j != 0);
143:
144: return cy;
145: }
146:
147: mp_limb_t
148: #if __STDC__
149: refmpn_sub_n (mp_ptr res_ptr,
150: mp_srcptr s1_ptr, mp_srcptr s2_ptr, mp_size_t size)
151: #else
152: refmpn_sub_n (res_ptr, s1_ptr, s2_ptr, size)
153: register mp_ptr res_ptr;
154: register mp_srcptr s1_ptr;
155: register mp_srcptr s2_ptr;
156: mp_size_t size;
157: #endif
158: {
159: register mp_limb_t x, y, cy;
160: register mp_size_t j;
161:
162: /* The loop counter and index J goes from -SIZE to -1. This way
163: the loop becomes faster. */
164: j = -size;
165:
166: /* Offset the base pointers to compensate for the negative indices. */
167: s1_ptr -= j;
168: s2_ptr -= j;
169: res_ptr -= j;
170:
171: cy = 0;
172: do
173: {
174: y = s2_ptr[j];
175: x = s1_ptr[j];
176: y += cy; /* add previous carry to subtrahend */
177: cy = (y < cy); /* get out carry from that addition */
178: y = x - y; /* main subtract */
179: cy = (y > x) + cy; /* get out carry from the subtract, combine */
180: res_ptr[j] = y;
181: }
182: while (++j != 0);
183:
184: return cy;
185: }
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>