17cbd73c887e1d5a9656431c5b7465b7f98b9c2a
[physik/nlsop.git] / random.c
1 /*
2  * random functions
3  *
4  * author: hackbard@hackdaworld.dyndns.org
5  *
6  */
7
8 #include <sys/types.h>
9 #include <sys/stat.h>
10 #include <fcntl.h>
11 #include <unistd.h>
12
13 #include "random.h"
14
15 static int rand_fd;
16 static u32 *c_ptr,*b_ptr;
17
18 int rand_init(char *rf)
19 {
20  if(rf==NULL)
21  {
22   if((rand_fd=open("/dev/urandom",O_RDONLY))<0)
23   {
24    puts("cannot open /dev/urandom");
25    return -1;
26   }
27  } else
28  {
29   if((rand_fd=open(rf,O_RDONLY))<0)
30   {
31    printf("cannot open %s\n",rf);
32    return -1;
33   }
34  }
35  if((b_ptr=(u32 *)(malloc(BUFSIZE*sizeof(u32))))==NULL)
36  {
37   puts("failed allocating random buffer");
38   return -1;
39  }
40  c_ptr=b_ptr+BUFSIZE;
41  
42  return 1;
43 }
44
45 int rand_close(void)
46 {
47  close(rand_fd);
48  
49  return 1;
50 }
51
52 u32 get_rand(u32 max)
53 {
54  if(c_ptr>=b_ptr+BUFSIZE)
55  {
56   if(read(rand_fd,b_ptr,BUFSIZE*sizeof(u32))<BUFSIZE*sizeof(u32))
57   {
58    /* -> assume random file, end reached */
59    puts("warning, will read random file from beginning ...");
60    lseek(rand_fd,0,SEEK_SET);
61    read(rand_fd,b_ptr,BUFSIZE*sizeof(u32));
62   }
63   c_ptr=b_ptr;
64  }
65  
66  return((u32)(*(c_ptr++)*(max*1.0/((long long unsigned int)URAND_MAX+1))));
67 }
68
69 u32 get_rand_lgp(u32 max,double a,double b)
70 {
71  return((u32)(1.0*max*(-1.0*b+sqrt(b*b+2*a*((b+a/2)*get_rand(URAND_MAX)/((long long unsigned int)URAND_MAX+1))))/a));
72 }
73