xref: /titanic_44/usr/src/lib/libast/common/uwin/rand48.c (revision 986fd29a0dc13f7608ef7f508f6e700bd7bc2720)
1 /***********************************************************************
2 *                                                                      *
3 *               This software is part of the ast package               *
4 *           Copyright (c) 1985-2007 AT&T Knowledge Ventures            *
5 *                      and is licensed under the                       *
6 *                  Common Public License, Version 1.0                  *
7 *                      by AT&T Knowledge Ventures                      *
8 *                                                                      *
9 *                A copy of the License is available at                 *
10 *            http://www.opensource.org/licenses/cpl1.0.txt             *
11 *         (with md5 checksum 059e8cd6165cb4c31e351f2b69388fd9)         *
12 *                                                                      *
13 *              Information and Software Systems Research               *
14 *                            AT&T Research                             *
15 *                           Florham Park NJ                            *
16 *                                                                      *
17 *                 Glenn Fowler <gsf@research.att.com>                  *
18 *                  David Korn <dgk@research.att.com>                   *
19 *                   Phong Vo <kpv@research.att.com>                    *
20 *                                                                      *
21 ***********************************************************************/
22 #include "FEATURE/uwin"
23 
24 #if !_UWIN || _lib_srand48
25 
26 void _STUB_srand48(){}
27 
28 #else
29 
30 #define drand48	______drand48
31 #define erand48	______erand48
32 #define jrand48	______jrand48
33 #define lcong48	______lcong48
34 #define lrand48	______lrand48
35 #define mrand48	______mrand48
36 #define nrand48	______nrand48
37 #define seed48	______seed48
38 #define srand48	______srand48
39 
40 #include	<stdlib.h>
41 
42 #undef	drand48
43 #undef	erand48
44 #undef	jrand48
45 #undef	lcong48
46 #undef	lrand48
47 #undef	mrand48
48 #undef	nrand48
49 #undef	seed48
50 #undef	srand48
51 
52 #if defined(__EXPORT__)
53 #define extern		__EXPORT__
54 #endif
55 
56 #define A	0x5DEECE66D
57 #define A0	0X5
58 #define A1	0xDEEC
59 #define A2	0xE66D
60 #define C	0xB
61 #define XINIT	0x330E
62 #define SCALE	3.55271e-15
63 
64 static unsigned short oldval[3];
65 static unsigned short X[3] = { 0, 0, XINIT};
66 static unsigned short a[3] = { A0, A1, A2};
67 static unsigned short c = C;
68 
69 static void multadd(unsigned short x[3], unsigned short a[3], unsigned short c)
70 {
71 	register unsigned long r = c;
72 	unsigned short x2 = x[2];
73 	unsigned short x1 = x[1];
74 	r += a[2]*x2;
75 	x[2] = (unsigned short)r;
76 	r >>= 16;
77 	r += a[1]*x2;
78 	r += a[2]*x1;
79 	x[1] = (unsigned short)r;
80 	r >>= 16;
81 	r += a[2]*x[0];
82 	r += a[1]*x1;
83 	r += a[0]*x2;
84 	x[0] = (unsigned short)r;
85 }
86 
87 extern double drand48(void)
88 {
89 	double d;
90 	unsigned long u;
91 	multadd(X,a,c);
92 	u = (X[0]<<16) + X[1];
93 	d = (u*65536.) + X[2];
94 	return(d*SCALE);
95 }
96 
97 extern double erand48(unsigned short xsubi[3])
98 {
99 	double d;
100 	unsigned long u;
101 	multadd(xsubi,a,c);
102 	u = (xsubi[0]<<16) + xsubi[1];
103 	d = (u*65536.) + xsubi[2];
104 	return(d*SCALE);
105 }
106 
107 extern long jrand48(unsigned short xsubi[3])
108 {
109 	long u;
110 	multadd(xsubi,a,c);
111 	u = (xsubi[0]<<16) | xsubi[1];
112 	return((long)u);
113 }
114 
115 extern void lcong48(unsigned short param[7])
116 {
117 	X[0] = param[0];
118 	X[1] = param[1];
119 	X[2] = param[2];
120 	a[0] = param[3];
121 	a[1] = param[4];
122 	a[2] = param[5];
123 	c = param[6];
124 }
125 
126 extern long lrand48(void)
127 {
128 	long l;
129 	multadd(X,a,c);
130 	l = (X[0]<<15)|(X[1]>>1);
131 	return(l);
132 }
133 
134 extern long mrand48(void)
135 {
136 	unsigned long u;
137 	multadd(X,a,c);
138 	u = (X[0]<<16) | X[1];
139 	return((long)u);
140 }
141 
142 extern long nrand48(unsigned short xsubi[3])
143 {
144 	long l;
145 	multadd(xsubi,a,c);
146 	l = (xsubi[0]<<15)|(xsubi[1]>>1);
147 	return(l);
148 }
149 
150 extern unsigned short *seed48(unsigned short seed[3])
151 {
152 	unsigned short *sp = (unsigned short*)&X;
153 	a[0] = A0;
154 	a[1] = A1;
155 	a[2] = A2;
156 	c = C;
157 	oldval[0] = X[2];
158 	oldval[1] = X[1];
159 	oldval[2] = X[0];
160 	X[0] = seed[2];
161 	X[1] = seed[1];
162 	X[2] = seed[0];
163 	return(oldval);
164 }
165 
166 extern void srand48(long seedval)
167 {
168 	a[0] = A0;
169 	a[1] = A1;
170 	a[2] = A2;
171 	c = C;
172 	X[0] = (unsigned short)(((unsigned long)seedval) >> 16);
173 	X[1] = (unsigned short)seedval;
174 	X[2] = XINIT;
175 }
176 
177 #endif
178