Adding initial code jy.oak@samsung.com
[ric-app/kpimon.git] / asn1c_defs / all-defs / asn_random_fill.c
1 /*\r
2  * Copyright (c) 2017 Lev Walkin <vlm@lionet.info>.\r
3  * All rights reserved.\r
4  * Redistribution and modifications are permitted subject to BSD license.\r
5  */\r
6 #include <asn_internal.h>\r
7 #include <asn_random_fill.h>\r
8 #include <constr_TYPE.h>\r
9 \r
10 int\r
11 asn_random_fill(const struct asn_TYPE_descriptor_s *td, void **struct_ptr,\r
12                 size_t length) {\r
13 \r
14     if(td && td->op->random_fill) {\r
15         asn_random_fill_result_t res =\r
16             td->op->random_fill(td, struct_ptr, 0, length);\r
17         return (res.code == ARFILL_OK) ? 0 : -1;\r
18     } else {\r
19         return -1;\r
20     }\r
21 }\r
22 \r
23 static uintmax_t\r
24 asn__intmax_range(intmax_t lb, intmax_t ub) {\r
25     assert(lb <= ub);\r
26     if((ub < 0) == (lb < 0)) {\r
27         return ub - lb;\r
28     } else if(lb < 0) {\r
29         return 1 + ((uintmax_t)ub + (uintmax_t)-(lb + 1));\r
30     } else {\r
31         assert(!"Unreachable");\r
32         return 0;\r
33     }\r
34 }\r
35 \r
36 intmax_t\r
37 asn_random_between(intmax_t lb, intmax_t rb) {\r
38     if(lb == rb) {\r
39         return lb;\r
40     } else {\r
41         const uintmax_t intmax_max = ((~(uintmax_t)0) >> 1);\r
42         uintmax_t range = asn__intmax_range(lb, rb);\r
43         uintmax_t value = 0;\r
44         uintmax_t got_entropy = 0;\r
45 \r
46         assert(RAND_MAX > 0xffffff);    /* Seen 7ffffffd! */\r
47         assert(range < intmax_max);\r
48 \r
49         for(; got_entropy < range;) {\r
50             got_entropy = (got_entropy << 24) | 0xffffff;\r
51             value = (value << 24) | (random() % 0xffffff);\r
52         }\r
53 \r
54         return lb + (intmax_t)(value % (range + 1));\r
55     }\r
56 }\r