1 /*************************************************************************
3 * Open Dynamics Engine, Copyright (C) 2001,2002 Russell L. Smith. *
4 * All rights reserved. Email: russ@q12.org Web: www.q12.org *
6 * This library is free software; you can redistribute it and/or *
7 * modify it under the terms of EITHER: *
8 * (1) The GNU Lesser General Public License as published by the Free *
9 * Software Foundation; either version 2.1 of the License, or (at *
10 * your option) any later version. The text of the GNU Lesser *
11 * General Public License is included with this library in the *
13 * (2) The BSD-style license that is included with this library in *
14 * the file LICENSE-BSD.TXT. *
16 * This library is distributed in the hope that it will be useful, *
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the files *
19 * LICENSE.TXT and LICENSE-BSD.TXT for more details. *
21 *************************************************************************/
23 #include <ode/odeconfig.h>
30 //****************************************************************************
33 static volatile duint32 seed
= 0;
37 duint32 origSeed
, newSeed
;
38 #if !dTHREADING_INTF_DISABLED
42 newSeed
= ((duint32
)1664525 * origSeed
+ (duint32
)1013904223) & (duint32
)0xffffffff;
43 #if dTHREADING_INTF_DISABLED
46 } while (!AtomicCompareExchange((volatile atomicord32
*)&seed
, origSeed
, newSeed
));
52 unsigned long dRandGetSeed()
58 void dRandSetSeed (unsigned long s
)
66 unsigned long oldseed
= seed
;
69 if (dRand() != 0x3c6ef35f || dRand() != 0x47502932 ||
70 dRand() != 0xd1ccf6e9 || dRand() != 0xaaf95334 ||
71 dRand() != 0x6252e503) ret
= 0;
77 // adam's all-int straightforward(?) dRandInt (0..n-1)
81 // Since there is no memory barrier macro in ODE assign via volatile variable
82 // to prevent compiler reusing seed as value of `r'
83 volatile unsigned long raw_r
= dRand();
84 duint32 r
= (duint32
)raw_r
;
87 dIASSERT(sizeof(n
) == sizeof(un
));
89 // note: probably more aggressive than it needs to be -- might be
90 // able to get away without one or two of the innermost branches.
91 // if (un <= 0x00010000UL) {
93 // if (un <= 0x00000100UL) {
95 // if (un <= 0x00000010UL) {
97 // if (un <= 0x00000004UL) {
99 // if (un <= 0x00000002UL) {
106 // Optimized version of above
107 if (un
<= (duint32
)0x00000010) {
111 if (un
<= (duint32
)0x00000002) {
114 result
= (r
/* & (duint32)0x01*/) & (un
>> 1);
116 if (un
<= (duint32
)0x00000004) {
118 result
= ((r
& (duint32
)0x03) * un
) >> 2;
120 result
= ((r
& (duint32
)0x0F) * un
) >> 4;
124 if (un
<= (duint32
)0x00000100) {
127 result
= ((r
& (duint32
)0xFF) * un
) >> 8;
129 if (un
<= (duint32
)0x00010000) {
131 result
= ((r
& (duint32
)0xFFFF) * un
) >> 16;
133 result
= (int)(((duint64
)r
* un
) >> 32);
144 return (dReal
)(((double) dRand()) / ((double) 0xffffffff));
147 //****************************************************************************
148 // matrix utility stuff
150 void dPrintMatrix (const dReal
*A
, int n
, int m
, const char *fmt
, FILE *f
)
153 const dReal
*Arow
= A
;
154 for (int i
=0; i
<n
; Arow
+=skip
, ++i
) {
155 for (int j
=0; j
<m
; ++j
) fprintf (f
,fmt
,Arow
[j
]);
161 void dMakeRandomVector (dReal
*A
, int n
, dReal range
)
164 for (i
=0; i
<n
; i
++) A
[i
] = (dRandReal()*REAL(2.0)-REAL(1.0))*range
;
168 void dMakeRandomMatrix (dReal
*A
, int n
, int m
, dReal range
)
171 // dSetZero (A,n*skip);
173 for (int i
=0; i
<n
; Arow
+=skip
, ++i
) {
174 for (int j
=0; j
<m
; ++j
) Arow
[j
] = (dRandReal()*REAL(2.0)-REAL(1.0))*range
;
179 void dClearUpperTriangle (dReal
*A
, int n
)
183 for (int i
=0; i
<n
; Arow
+=skip
, ++i
) {
184 for (int j
=i
+1; j
<n
; ++j
) Arow
[j
] = 0;
189 dReal
dMaxDifference (const dReal
*A
, const dReal
*B
, int n
, int m
)
192 dReal max
= REAL(0.0);
193 const dReal
*Arow
= A
, *Brow
= B
;
194 for (int i
=0; i
<n
; Arow
+=skip
, Brow
+=skip
, ++i
) {
195 for (int j
=0; j
<m
; ++j
) {
196 dReal diff
= dFabs(Arow
[j
] - Brow
[j
]);
197 if (diff
> max
) max
= diff
;
204 dReal
dMaxDifferenceLowerTriangle (const dReal
*A
, const dReal
*B
, int n
)
207 dReal max
= REAL(0.0);
208 const dReal
*Arow
= A
, *Brow
= B
;
209 for (int i
=0; i
<n
; Arow
+=skip
, Brow
+=skip
, ++i
) {
210 for (int j
=0; j
<=i
; ++j
) {
211 dReal diff
= dFabs(Arow
[j
] - Brow
[j
]);
212 if (diff
> max
) max
= diff
;