takashi kadono / Mbed OS Nucleo_446

Dependencies:   ssd1331

Committer:
kadonotakashi
Date:
Wed Oct 10 00:33:53 2018 +0000
Revision:
0:8fdf9a60065b
how to make mbed librry

Who changed what in which revision?

UserRevisionLine numberNew contents of line
kadonotakashi 0:8fdf9a60065b 1 /*
kadonotakashi 0:8fdf9a60065b 2 * Platform-specific and custom entropy polling functions
kadonotakashi 0:8fdf9a60065b 3 *
kadonotakashi 0:8fdf9a60065b 4 * Copyright (C) 2006-2016, ARM Limited, All Rights Reserved
kadonotakashi 0:8fdf9a60065b 5 * SPDX-License-Identifier: Apache-2.0
kadonotakashi 0:8fdf9a60065b 6 *
kadonotakashi 0:8fdf9a60065b 7 * Licensed under the Apache License, Version 2.0 (the "License"); you may
kadonotakashi 0:8fdf9a60065b 8 * not use this file except in compliance with the License.
kadonotakashi 0:8fdf9a60065b 9 * You may obtain a copy of the License at
kadonotakashi 0:8fdf9a60065b 10 *
kadonotakashi 0:8fdf9a60065b 11 * http://www.apache.org/licenses/LICENSE-2.0
kadonotakashi 0:8fdf9a60065b 12 *
kadonotakashi 0:8fdf9a60065b 13 * Unless required by applicable law or agreed to in writing, software
kadonotakashi 0:8fdf9a60065b 14 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
kadonotakashi 0:8fdf9a60065b 15 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
kadonotakashi 0:8fdf9a60065b 16 * See the License for the specific language governing permissions and
kadonotakashi 0:8fdf9a60065b 17 * limitations under the License.
kadonotakashi 0:8fdf9a60065b 18 *
kadonotakashi 0:8fdf9a60065b 19 * This file is part of mbed TLS (https://tls.mbed.org)
kadonotakashi 0:8fdf9a60065b 20 */
kadonotakashi 0:8fdf9a60065b 21
kadonotakashi 0:8fdf9a60065b 22 #if defined(__linux__)
kadonotakashi 0:8fdf9a60065b 23 /* Ensure that syscall() is available even when compiling with -std=c99 */
kadonotakashi 0:8fdf9a60065b 24 #define _GNU_SOURCE
kadonotakashi 0:8fdf9a60065b 25 #endif
kadonotakashi 0:8fdf9a60065b 26
kadonotakashi 0:8fdf9a60065b 27 #if !defined(MBEDTLS_CONFIG_FILE)
kadonotakashi 0:8fdf9a60065b 28 #include "mbedtls/config.h"
kadonotakashi 0:8fdf9a60065b 29 #else
kadonotakashi 0:8fdf9a60065b 30 #include MBEDTLS_CONFIG_FILE
kadonotakashi 0:8fdf9a60065b 31 #endif
kadonotakashi 0:8fdf9a60065b 32
kadonotakashi 0:8fdf9a60065b 33 #include <string.h>
kadonotakashi 0:8fdf9a60065b 34
kadonotakashi 0:8fdf9a60065b 35 #if defined(MBEDTLS_ENTROPY_C)
kadonotakashi 0:8fdf9a60065b 36
kadonotakashi 0:8fdf9a60065b 37 #include "mbedtls/entropy.h"
kadonotakashi 0:8fdf9a60065b 38 #include "mbedtls/entropy_poll.h"
kadonotakashi 0:8fdf9a60065b 39
kadonotakashi 0:8fdf9a60065b 40 #if defined(MBEDTLS_TIMING_C)
kadonotakashi 0:8fdf9a60065b 41 #include "mbedtls/timing.h"
kadonotakashi 0:8fdf9a60065b 42 #endif
kadonotakashi 0:8fdf9a60065b 43 #if defined(MBEDTLS_HAVEGE_C)
kadonotakashi 0:8fdf9a60065b 44 #include "mbedtls/havege.h"
kadonotakashi 0:8fdf9a60065b 45 #endif
kadonotakashi 0:8fdf9a60065b 46 #if defined(MBEDTLS_ENTROPY_NV_SEED)
kadonotakashi 0:8fdf9a60065b 47 #include "mbedtls/platform.h"
kadonotakashi 0:8fdf9a60065b 48 #endif
kadonotakashi 0:8fdf9a60065b 49
kadonotakashi 0:8fdf9a60065b 50 #if !defined(MBEDTLS_NO_PLATFORM_ENTROPY)
kadonotakashi 0:8fdf9a60065b 51
kadonotakashi 0:8fdf9a60065b 52 #if !defined(unix) && !defined(__unix__) && !defined(__unix) && \
kadonotakashi 0:8fdf9a60065b 53 !defined(__APPLE__) && !defined(_WIN32) && !defined(__QNXNTO__) && \
kadonotakashi 0:8fdf9a60065b 54 !defined(__HAIKU__)
kadonotakashi 0:8fdf9a60065b 55 #error "Platform entropy sources only work on Unix and Windows, see MBEDTLS_NO_PLATFORM_ENTROPY in config.h"
kadonotakashi 0:8fdf9a60065b 56 #endif
kadonotakashi 0:8fdf9a60065b 57
kadonotakashi 0:8fdf9a60065b 58 #if defined(_WIN32) && !defined(EFIX64) && !defined(EFI32)
kadonotakashi 0:8fdf9a60065b 59
kadonotakashi 0:8fdf9a60065b 60 #if !defined(_WIN32_WINNT)
kadonotakashi 0:8fdf9a60065b 61 #define _WIN32_WINNT 0x0400
kadonotakashi 0:8fdf9a60065b 62 #endif
kadonotakashi 0:8fdf9a60065b 63 #include <windows.h>
kadonotakashi 0:8fdf9a60065b 64 #include <wincrypt.h>
kadonotakashi 0:8fdf9a60065b 65
kadonotakashi 0:8fdf9a60065b 66 int mbedtls_platform_entropy_poll( void *data, unsigned char *output, size_t len,
kadonotakashi 0:8fdf9a60065b 67 size_t *olen )
kadonotakashi 0:8fdf9a60065b 68 {
kadonotakashi 0:8fdf9a60065b 69 HCRYPTPROV provider;
kadonotakashi 0:8fdf9a60065b 70 ((void) data);
kadonotakashi 0:8fdf9a60065b 71 *olen = 0;
kadonotakashi 0:8fdf9a60065b 72
kadonotakashi 0:8fdf9a60065b 73 if( CryptAcquireContext( &provider, NULL, NULL,
kadonotakashi 0:8fdf9a60065b 74 PROV_RSA_FULL, CRYPT_VERIFYCONTEXT ) == FALSE )
kadonotakashi 0:8fdf9a60065b 75 {
kadonotakashi 0:8fdf9a60065b 76 return( MBEDTLS_ERR_ENTROPY_SOURCE_FAILED );
kadonotakashi 0:8fdf9a60065b 77 }
kadonotakashi 0:8fdf9a60065b 78
kadonotakashi 0:8fdf9a60065b 79 if( CryptGenRandom( provider, (DWORD) len, output ) == FALSE )
kadonotakashi 0:8fdf9a60065b 80 {
kadonotakashi 0:8fdf9a60065b 81 CryptReleaseContext( provider, 0 );
kadonotakashi 0:8fdf9a60065b 82 return( MBEDTLS_ERR_ENTROPY_SOURCE_FAILED );
kadonotakashi 0:8fdf9a60065b 83 }
kadonotakashi 0:8fdf9a60065b 84
kadonotakashi 0:8fdf9a60065b 85 CryptReleaseContext( provider, 0 );
kadonotakashi 0:8fdf9a60065b 86 *olen = len;
kadonotakashi 0:8fdf9a60065b 87
kadonotakashi 0:8fdf9a60065b 88 return( 0 );
kadonotakashi 0:8fdf9a60065b 89 }
kadonotakashi 0:8fdf9a60065b 90 #else /* _WIN32 && !EFIX64 && !EFI32 */
kadonotakashi 0:8fdf9a60065b 91
kadonotakashi 0:8fdf9a60065b 92 /*
kadonotakashi 0:8fdf9a60065b 93 * Test for Linux getrandom() support.
kadonotakashi 0:8fdf9a60065b 94 * Since there is no wrapper in the libc yet, use the generic syscall wrapper
kadonotakashi 0:8fdf9a60065b 95 * available in GNU libc and compatible libc's (eg uClibc).
kadonotakashi 0:8fdf9a60065b 96 */
kadonotakashi 0:8fdf9a60065b 97 #if defined(__linux__) && defined(__GLIBC__)
kadonotakashi 0:8fdf9a60065b 98 #include <unistd.h>
kadonotakashi 0:8fdf9a60065b 99 #include <sys/syscall.h>
kadonotakashi 0:8fdf9a60065b 100 #if defined(SYS_getrandom)
kadonotakashi 0:8fdf9a60065b 101 #define HAVE_GETRANDOM
kadonotakashi 0:8fdf9a60065b 102
kadonotakashi 0:8fdf9a60065b 103 static int getrandom_wrapper( void *buf, size_t buflen, unsigned int flags )
kadonotakashi 0:8fdf9a60065b 104 {
kadonotakashi 0:8fdf9a60065b 105 /* MemSan cannot understand that the syscall writes to the buffer */
kadonotakashi 0:8fdf9a60065b 106 #if defined(__has_feature)
kadonotakashi 0:8fdf9a60065b 107 #if __has_feature(memory_sanitizer)
kadonotakashi 0:8fdf9a60065b 108 memset( buf, 0, buflen );
kadonotakashi 0:8fdf9a60065b 109 #endif
kadonotakashi 0:8fdf9a60065b 110 #endif
kadonotakashi 0:8fdf9a60065b 111
kadonotakashi 0:8fdf9a60065b 112 return( syscall( SYS_getrandom, buf, buflen, flags ) );
kadonotakashi 0:8fdf9a60065b 113 }
kadonotakashi 0:8fdf9a60065b 114
kadonotakashi 0:8fdf9a60065b 115 #include <sys/utsname.h>
kadonotakashi 0:8fdf9a60065b 116 /* Check if version is at least 3.17.0 */
kadonotakashi 0:8fdf9a60065b 117 static int check_version_3_17_plus( void )
kadonotakashi 0:8fdf9a60065b 118 {
kadonotakashi 0:8fdf9a60065b 119 int minor;
kadonotakashi 0:8fdf9a60065b 120 struct utsname un;
kadonotakashi 0:8fdf9a60065b 121 const char *ver;
kadonotakashi 0:8fdf9a60065b 122
kadonotakashi 0:8fdf9a60065b 123 /* Get version information */
kadonotakashi 0:8fdf9a60065b 124 uname(&un);
kadonotakashi 0:8fdf9a60065b 125 ver = un.release;
kadonotakashi 0:8fdf9a60065b 126
kadonotakashi 0:8fdf9a60065b 127 /* Check major version; assume a single digit */
kadonotakashi 0:8fdf9a60065b 128 if( ver[0] < '3' || ver[0] > '9' || ver [1] != '.' )
kadonotakashi 0:8fdf9a60065b 129 return( -1 );
kadonotakashi 0:8fdf9a60065b 130
kadonotakashi 0:8fdf9a60065b 131 if( ver[0] - '0' > 3 )
kadonotakashi 0:8fdf9a60065b 132 return( 0 );
kadonotakashi 0:8fdf9a60065b 133
kadonotakashi 0:8fdf9a60065b 134 /* Ok, so now we know major == 3, check minor.
kadonotakashi 0:8fdf9a60065b 135 * Assume 1 or 2 digits. */
kadonotakashi 0:8fdf9a60065b 136 if( ver[2] < '0' || ver[2] > '9' )
kadonotakashi 0:8fdf9a60065b 137 return( -1 );
kadonotakashi 0:8fdf9a60065b 138
kadonotakashi 0:8fdf9a60065b 139 minor = ver[2] - '0';
kadonotakashi 0:8fdf9a60065b 140
kadonotakashi 0:8fdf9a60065b 141 if( ver[3] >= '0' && ver[3] <= '9' )
kadonotakashi 0:8fdf9a60065b 142 minor = 10 * minor + ver[3] - '0';
kadonotakashi 0:8fdf9a60065b 143 else if( ver [3] != '.' )
kadonotakashi 0:8fdf9a60065b 144 return( -1 );
kadonotakashi 0:8fdf9a60065b 145
kadonotakashi 0:8fdf9a60065b 146 if( minor < 17 )
kadonotakashi 0:8fdf9a60065b 147 return( -1 );
kadonotakashi 0:8fdf9a60065b 148
kadonotakashi 0:8fdf9a60065b 149 return( 0 );
kadonotakashi 0:8fdf9a60065b 150 }
kadonotakashi 0:8fdf9a60065b 151 static int has_getrandom = -1;
kadonotakashi 0:8fdf9a60065b 152 #endif /* SYS_getrandom */
kadonotakashi 0:8fdf9a60065b 153 #endif /* __linux__ */
kadonotakashi 0:8fdf9a60065b 154
kadonotakashi 0:8fdf9a60065b 155 #include <stdio.h>
kadonotakashi 0:8fdf9a60065b 156
kadonotakashi 0:8fdf9a60065b 157 int mbedtls_platform_entropy_poll( void *data,
kadonotakashi 0:8fdf9a60065b 158 unsigned char *output, size_t len, size_t *olen )
kadonotakashi 0:8fdf9a60065b 159 {
kadonotakashi 0:8fdf9a60065b 160 FILE *file;
kadonotakashi 0:8fdf9a60065b 161 size_t read_len;
kadonotakashi 0:8fdf9a60065b 162 ((void) data);
kadonotakashi 0:8fdf9a60065b 163
kadonotakashi 0:8fdf9a60065b 164 #if defined(HAVE_GETRANDOM)
kadonotakashi 0:8fdf9a60065b 165 if( has_getrandom == -1 )
kadonotakashi 0:8fdf9a60065b 166 has_getrandom = ( check_version_3_17_plus() == 0 );
kadonotakashi 0:8fdf9a60065b 167
kadonotakashi 0:8fdf9a60065b 168 if( has_getrandom )
kadonotakashi 0:8fdf9a60065b 169 {
kadonotakashi 0:8fdf9a60065b 170 int ret;
kadonotakashi 0:8fdf9a60065b 171
kadonotakashi 0:8fdf9a60065b 172 if( ( ret = getrandom_wrapper( output, len, 0 ) ) < 0 )
kadonotakashi 0:8fdf9a60065b 173 return( MBEDTLS_ERR_ENTROPY_SOURCE_FAILED );
kadonotakashi 0:8fdf9a60065b 174
kadonotakashi 0:8fdf9a60065b 175 *olen = ret;
kadonotakashi 0:8fdf9a60065b 176 return( 0 );
kadonotakashi 0:8fdf9a60065b 177 }
kadonotakashi 0:8fdf9a60065b 178 #endif /* HAVE_GETRANDOM */
kadonotakashi 0:8fdf9a60065b 179
kadonotakashi 0:8fdf9a60065b 180 *olen = 0;
kadonotakashi 0:8fdf9a60065b 181
kadonotakashi 0:8fdf9a60065b 182 file = fopen( "/dev/urandom", "rb" );
kadonotakashi 0:8fdf9a60065b 183 if( file == NULL )
kadonotakashi 0:8fdf9a60065b 184 return( MBEDTLS_ERR_ENTROPY_SOURCE_FAILED );
kadonotakashi 0:8fdf9a60065b 185
kadonotakashi 0:8fdf9a60065b 186 read_len = fread( output, 1, len, file );
kadonotakashi 0:8fdf9a60065b 187 if( read_len != len )
kadonotakashi 0:8fdf9a60065b 188 {
kadonotakashi 0:8fdf9a60065b 189 fclose( file );
kadonotakashi 0:8fdf9a60065b 190 return( MBEDTLS_ERR_ENTROPY_SOURCE_FAILED );
kadonotakashi 0:8fdf9a60065b 191 }
kadonotakashi 0:8fdf9a60065b 192
kadonotakashi 0:8fdf9a60065b 193 fclose( file );
kadonotakashi 0:8fdf9a60065b 194 *olen = len;
kadonotakashi 0:8fdf9a60065b 195
kadonotakashi 0:8fdf9a60065b 196 return( 0 );
kadonotakashi 0:8fdf9a60065b 197 }
kadonotakashi 0:8fdf9a60065b 198 #endif /* _WIN32 && !EFIX64 && !EFI32 */
kadonotakashi 0:8fdf9a60065b 199 #endif /* !MBEDTLS_NO_PLATFORM_ENTROPY */
kadonotakashi 0:8fdf9a60065b 200
kadonotakashi 0:8fdf9a60065b 201 #if defined(MBEDTLS_TEST_NULL_ENTROPY)
kadonotakashi 0:8fdf9a60065b 202 int mbedtls_null_entropy_poll( void *data,
kadonotakashi 0:8fdf9a60065b 203 unsigned char *output, size_t len, size_t *olen )
kadonotakashi 0:8fdf9a60065b 204 {
kadonotakashi 0:8fdf9a60065b 205 ((void) data);
kadonotakashi 0:8fdf9a60065b 206 ((void) output);
kadonotakashi 0:8fdf9a60065b 207 *olen = 0;
kadonotakashi 0:8fdf9a60065b 208
kadonotakashi 0:8fdf9a60065b 209 if( len < sizeof(unsigned char) )
kadonotakashi 0:8fdf9a60065b 210 return( 0 );
kadonotakashi 0:8fdf9a60065b 211
kadonotakashi 0:8fdf9a60065b 212 *olen = sizeof(unsigned char);
kadonotakashi 0:8fdf9a60065b 213
kadonotakashi 0:8fdf9a60065b 214 return( 0 );
kadonotakashi 0:8fdf9a60065b 215 }
kadonotakashi 0:8fdf9a60065b 216 #endif
kadonotakashi 0:8fdf9a60065b 217
kadonotakashi 0:8fdf9a60065b 218 #if defined(MBEDTLS_TIMING_C)
kadonotakashi 0:8fdf9a60065b 219 int mbedtls_hardclock_poll( void *data,
kadonotakashi 0:8fdf9a60065b 220 unsigned char *output, size_t len, size_t *olen )
kadonotakashi 0:8fdf9a60065b 221 {
kadonotakashi 0:8fdf9a60065b 222 unsigned long timer = mbedtls_timing_hardclock();
kadonotakashi 0:8fdf9a60065b 223 ((void) data);
kadonotakashi 0:8fdf9a60065b 224 *olen = 0;
kadonotakashi 0:8fdf9a60065b 225
kadonotakashi 0:8fdf9a60065b 226 if( len < sizeof(unsigned long) )
kadonotakashi 0:8fdf9a60065b 227 return( 0 );
kadonotakashi 0:8fdf9a60065b 228
kadonotakashi 0:8fdf9a60065b 229 memcpy( output, &timer, sizeof(unsigned long) );
kadonotakashi 0:8fdf9a60065b 230 *olen = sizeof(unsigned long);
kadonotakashi 0:8fdf9a60065b 231
kadonotakashi 0:8fdf9a60065b 232 return( 0 );
kadonotakashi 0:8fdf9a60065b 233 }
kadonotakashi 0:8fdf9a60065b 234 #endif /* MBEDTLS_TIMING_C */
kadonotakashi 0:8fdf9a60065b 235
kadonotakashi 0:8fdf9a60065b 236 #if defined(MBEDTLS_HAVEGE_C)
kadonotakashi 0:8fdf9a60065b 237 int mbedtls_havege_poll( void *data,
kadonotakashi 0:8fdf9a60065b 238 unsigned char *output, size_t len, size_t *olen )
kadonotakashi 0:8fdf9a60065b 239 {
kadonotakashi 0:8fdf9a60065b 240 mbedtls_havege_state *hs = (mbedtls_havege_state *) data;
kadonotakashi 0:8fdf9a60065b 241 *olen = 0;
kadonotakashi 0:8fdf9a60065b 242
kadonotakashi 0:8fdf9a60065b 243 if( mbedtls_havege_random( hs, output, len ) != 0 )
kadonotakashi 0:8fdf9a60065b 244 return( MBEDTLS_ERR_ENTROPY_SOURCE_FAILED );
kadonotakashi 0:8fdf9a60065b 245
kadonotakashi 0:8fdf9a60065b 246 *olen = len;
kadonotakashi 0:8fdf9a60065b 247
kadonotakashi 0:8fdf9a60065b 248 return( 0 );
kadonotakashi 0:8fdf9a60065b 249 }
kadonotakashi 0:8fdf9a60065b 250 #endif /* MBEDTLS_HAVEGE_C */
kadonotakashi 0:8fdf9a60065b 251
kadonotakashi 0:8fdf9a60065b 252 #if defined(MBEDTLS_ENTROPY_NV_SEED)
kadonotakashi 0:8fdf9a60065b 253 int mbedtls_nv_seed_poll( void *data,
kadonotakashi 0:8fdf9a60065b 254 unsigned char *output, size_t len, size_t *olen )
kadonotakashi 0:8fdf9a60065b 255 {
kadonotakashi 0:8fdf9a60065b 256 unsigned char buf[MBEDTLS_ENTROPY_BLOCK_SIZE];
kadonotakashi 0:8fdf9a60065b 257 size_t use_len = MBEDTLS_ENTROPY_BLOCK_SIZE;
kadonotakashi 0:8fdf9a60065b 258 ((void) data);
kadonotakashi 0:8fdf9a60065b 259
kadonotakashi 0:8fdf9a60065b 260 memset( buf, 0, MBEDTLS_ENTROPY_BLOCK_SIZE );
kadonotakashi 0:8fdf9a60065b 261
kadonotakashi 0:8fdf9a60065b 262 if( mbedtls_nv_seed_read( buf, MBEDTLS_ENTROPY_BLOCK_SIZE ) < 0 )
kadonotakashi 0:8fdf9a60065b 263 return( MBEDTLS_ERR_ENTROPY_SOURCE_FAILED );
kadonotakashi 0:8fdf9a60065b 264
kadonotakashi 0:8fdf9a60065b 265 if( len < use_len )
kadonotakashi 0:8fdf9a60065b 266 use_len = len;
kadonotakashi 0:8fdf9a60065b 267
kadonotakashi 0:8fdf9a60065b 268 memcpy( output, buf, use_len );
kadonotakashi 0:8fdf9a60065b 269 *olen = use_len;
kadonotakashi 0:8fdf9a60065b 270
kadonotakashi 0:8fdf9a60065b 271 return( 0 );
kadonotakashi 0:8fdf9a60065b 272 }
kadonotakashi 0:8fdf9a60065b 273 #endif /* MBEDTLS_ENTROPY_NV_SEED */
kadonotakashi 0:8fdf9a60065b 274
kadonotakashi 0:8fdf9a60065b 275 #endif /* MBEDTLS_ENTROPY_C */