mirror of
https://gitlab.isc.org/isc-projects/bind9
synced 2025-09-01 23:25:38 +00:00
add isc_random_t, and all the isc_random_*() function to use it. Right now it is
a pretty empty type, but it would be good to flesh it out so each random state will be separated from one another. Right now they all just lock around rand(), which isn't perfect, but good enough for what I need today.
This commit is contained in:
@@ -47,7 +47,7 @@ OBJS = @ISC_EXTRA_OBJS@ \
|
|||||||
assertions.@O@ base64.@O@ bitstring.@O@ buffer.@O@ \
|
assertions.@O@ base64.@O@ bitstring.@O@ buffer.@O@ \
|
||||||
bufferlist.@O@ commandline.@O@ error.@O@ event.@O@ heap.@O@ \
|
bufferlist.@O@ commandline.@O@ error.@O@ event.@O@ heap.@O@ \
|
||||||
lex.@O@ lib.@O@ log.@O@ \
|
lex.@O@ lib.@O@ log.@O@ \
|
||||||
mem.@O@ mutexblock.@O@ result.@O@ rwlock.@O@ \
|
mem.@O@ mutexblock.@O@ random.@O@ result.@O@ rwlock.@O@ \
|
||||||
serial.@O@ sockaddr.@O@ str.@O@ symtab.@O@ task.@O@ timer.@O@ \
|
serial.@O@ sockaddr.@O@ str.@O@ symtab.@O@ task.@O@ timer.@O@ \
|
||||||
version.@O@ \
|
version.@O@ \
|
||||||
${UNIXOBJS} ${NLSOBJS} ${PTHREADOBJS}
|
${UNIXOBJS} ${NLSOBJS} ${PTHREADOBJS}
|
||||||
@@ -57,7 +57,7 @@ SRCS = @ISC_EXTRA_SRCS@ \
|
|||||||
assertions.c base64.c bitstring.c buffer.c \
|
assertions.c base64.c bitstring.c buffer.c \
|
||||||
bufferlist.c commandline.c error.c event.c heap.c \
|
bufferlist.c commandline.c error.c event.c heap.c \
|
||||||
lex.c lib.c log.c \
|
lex.c lib.c log.c \
|
||||||
mem.c mutexblock.c result.c rwlock.c \
|
mem.c mutexblock.c random.c result.c rwlock.c \
|
||||||
serial.c sockaddr.c str.c symtab.c task.c timer.c \
|
serial.c sockaddr.c str.c symtab.c task.c timer.c \
|
||||||
version.c
|
version.c
|
||||||
|
|
||||||
|
69
lib/isc/include/isc/random.h
Normal file
69
lib/isc/include/isc/random.h
Normal file
@@ -0,0 +1,69 @@
|
|||||||
|
#ifndef ISC_RANDOM_H
|
||||||
|
#define ISC_RANDOM_H 1
|
||||||
|
|
||||||
|
#include <isc/lang.h>
|
||||||
|
#include <isc/int.h>
|
||||||
|
#include <isc/mutex.h>
|
||||||
|
#include <isc/result.h>
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Implements a random state pool which will let the caller return a
|
||||||
|
* series of possibly non-reproducable random values. Note that the
|
||||||
|
* strength of these numbers is not all that high, and should not be
|
||||||
|
* used in cryptography functions.
|
||||||
|
*/
|
||||||
|
|
||||||
|
ISC_LANG_BEGINDECLS
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
unsigned int magic;
|
||||||
|
#if 0
|
||||||
|
isc_mutex_t lock;
|
||||||
|
#endif
|
||||||
|
} isc_random_t;
|
||||||
|
#define ISC_RANDOM_MAGIC 0x52416e64 /* RAnd. */
|
||||||
|
#define ISC_RANDOM_VALID(x) ((x) != NULL && (x->magic) == ISC_RANDOM_MAGIC)
|
||||||
|
|
||||||
|
isc_result_t isc_random_init(isc_random_t *r);
|
||||||
|
/*
|
||||||
|
* Initialize a random state.
|
||||||
|
*
|
||||||
|
* This function must be called before using any of the following functions.
|
||||||
|
*
|
||||||
|
* Requires:
|
||||||
|
* r != NULL.
|
||||||
|
*/
|
||||||
|
|
||||||
|
isc_result_t isc_random_invalidate(isc_random_t *r);
|
||||||
|
/*
|
||||||
|
* Invalidate a random state. This will wipe any information contained in
|
||||||
|
* the state and make it unusable.
|
||||||
|
*
|
||||||
|
* Requires:
|
||||||
|
* r be a valid pool.
|
||||||
|
*/
|
||||||
|
|
||||||
|
void isc_random_seed(isc_random_t *r, isc_uint32_t seed);
|
||||||
|
/*
|
||||||
|
* Set the initial seed of the random state. Note that on some systems
|
||||||
|
* the private state isn't all that private, and setting the seed may
|
||||||
|
* alter numbers returned to other state pools.
|
||||||
|
*
|
||||||
|
* Requires:
|
||||||
|
* r be a valid pool.
|
||||||
|
*/
|
||||||
|
|
||||||
|
void isc_random_get(isc_random_t *r, isc_uint32_t *val);
|
||||||
|
/*
|
||||||
|
* Get a random value. Note that on some systems the private state isn't
|
||||||
|
* all that private, and getting a value may alter what other state pools
|
||||||
|
* would have returned.
|
||||||
|
*
|
||||||
|
* Requires:
|
||||||
|
* r be a valid pool.
|
||||||
|
* val != NULL.
|
||||||
|
*/
|
||||||
|
|
||||||
|
ISC_LANG_ENDDECLS
|
||||||
|
|
||||||
|
#endif /* ISC_RANDOM_H */
|
97
lib/isc/random.c
Normal file
97
lib/isc/random.c
Normal file
@@ -0,0 +1,97 @@
|
|||||||
|
/*
|
||||||
|
* Wrapper around the ANSI rand() function.
|
||||||
|
*/
|
||||||
|
#include <config.h>
|
||||||
|
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#include <isc/assertions.h>
|
||||||
|
#include <isc/mutex.h>
|
||||||
|
#include <isc/once.h>
|
||||||
|
#include <isc/random.h>
|
||||||
|
|
||||||
|
#include "util.h"
|
||||||
|
|
||||||
|
static isc_once_t once = ISC_ONCE_INIT;
|
||||||
|
static isc_mutex_t rand_lock;
|
||||||
|
|
||||||
|
static void
|
||||||
|
initialize_rand(void)
|
||||||
|
{
|
||||||
|
RUNTIME_CHECK(isc_mutex_init(&rand_lock) == ISC_R_SUCCESS);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
initialize(void)
|
||||||
|
{
|
||||||
|
RUNTIME_CHECK(isc_once_do(&once, initialize_rand) == ISC_R_SUCCESS);
|
||||||
|
}
|
||||||
|
|
||||||
|
isc_result_t
|
||||||
|
isc_random_init(isc_random_t *r)
|
||||||
|
{
|
||||||
|
REQUIRE(r != NULL);
|
||||||
|
|
||||||
|
r->magic = ISC_RANDOM_MAGIC;
|
||||||
|
#if 0
|
||||||
|
return (isc_mutex_init(&r->lock));
|
||||||
|
#else
|
||||||
|
return (ISC_R_SUCCESS);
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
isc_result_t
|
||||||
|
isc_random_invalidate(isc_random_t *r)
|
||||||
|
{
|
||||||
|
isc_result_t result;
|
||||||
|
|
||||||
|
REQUIRE(ISC_RANDOM_VALID(r));
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
result = isc_mutex_destroy(&r->lock);
|
||||||
|
#else
|
||||||
|
result = ISC_R_SUCCESS;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
memset(r, 0, sizeof(isc_random_t));
|
||||||
|
|
||||||
|
return (result);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
isc_random_seed(isc_random_t *r, isc_uint32_t seed)
|
||||||
|
{
|
||||||
|
REQUIRE(ISC_RANDOM_VALID(r));
|
||||||
|
|
||||||
|
initialize();
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
LOCK(&r->lock);
|
||||||
|
#endif
|
||||||
|
LOCK(&rand_lock);
|
||||||
|
srand(seed);
|
||||||
|
UNLOCK(&rand_lock);
|
||||||
|
#if 0
|
||||||
|
UNLOCK(&r->lock);
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
isc_random_get(isc_random_t *r, isc_uint32_t *val)
|
||||||
|
{
|
||||||
|
REQUIRE(ISC_RANDOM_VALID(r));
|
||||||
|
REQUIRE(val != NULL);
|
||||||
|
|
||||||
|
initialize();
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
LOCK(&r->lock);
|
||||||
|
#endif
|
||||||
|
LOCK(&rand_lock);
|
||||||
|
*val = rand();
|
||||||
|
UNLOCK(&rand_lock);
|
||||||
|
#if 0
|
||||||
|
UNLOCK(&r->lock);
|
||||||
|
#endif
|
||||||
|
}
|
Reference in New Issue
Block a user