1/*
2 *  RSA simple data encryption program
3 *
4 *  Copyright The Mbed TLS Contributors
5 *  SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later
6 */
7
8#include "mbedtls/build_info.h"
9
10#include "mbedtls/platform.h"
11
12#if defined(MBEDTLS_BIGNUM_C) && defined(MBEDTLS_PK_PARSE_C) && \
13    defined(MBEDTLS_ENTROPY_C) && defined(MBEDTLS_FS_IO) && \
14    defined(MBEDTLS_CTR_DRBG_C)
15#include "mbedtls/error.h"
16#include "mbedtls/pk.h"
17#include "mbedtls/entropy.h"
18#include "mbedtls/ctr_drbg.h"
19
20#include <stdio.h>
21#include <string.h>
22#endif
23
24#if !defined(MBEDTLS_BIGNUM_C) || !defined(MBEDTLS_PK_PARSE_C) ||  \
25    !defined(MBEDTLS_ENTROPY_C) || !defined(MBEDTLS_FS_IO) || \
26    !defined(MBEDTLS_CTR_DRBG_C)
27int main(void)
28{
29    mbedtls_printf("MBEDTLS_BIGNUM_C and/or MBEDTLS_PK_PARSE_C and/or "
30                   "MBEDTLS_ENTROPY_C and/or MBEDTLS_FS_IO and/or "
31                   "MBEDTLS_CTR_DRBG_C not defined.\n");
32    mbedtls_exit(0);
33}
34#else
35
36
37int main(int argc, char *argv[])
38{
39    FILE *f;
40    int ret = 1;
41    int exit_code = MBEDTLS_EXIT_FAILURE;
42    size_t i, olen = 0;
43    mbedtls_pk_context pk;
44    mbedtls_entropy_context entropy;
45    mbedtls_ctr_drbg_context ctr_drbg;
46    unsigned char input[1024];
47    unsigned char buf[512];
48    const char *pers = "mbedtls_pk_encrypt";
49
50    mbedtls_ctr_drbg_init(&ctr_drbg);
51    mbedtls_entropy_init(&entropy);
52    mbedtls_pk_init(&pk);
53
54#if defined(MBEDTLS_USE_PSA_CRYPTO)
55    psa_status_t status = psa_crypto_init();
56    if (status != PSA_SUCCESS) {
57        mbedtls_fprintf(stderr, "Failed to initialize PSA Crypto implementation: %d\n",
58                        (int) status);
59        goto exit;
60    }
61#endif /* MBEDTLS_USE_PSA_CRYPTO */
62
63    if (argc != 3) {
64        mbedtls_printf("usage: mbedtls_pk_encrypt <key_file> <string of max 100 characters>\n");
65
66#if defined(_WIN32)
67        mbedtls_printf("\n");
68#endif
69
70        goto exit;
71    }
72
73    mbedtls_printf("\n  . Seeding the random number generator...");
74    fflush(stdout);
75
76    if ((ret = mbedtls_ctr_drbg_seed(&ctr_drbg, mbedtls_entropy_func,
77                                     &entropy, (const unsigned char *) pers,
78                                     strlen(pers))) != 0) {
79        mbedtls_printf(" failed\n  ! mbedtls_ctr_drbg_seed returned -0x%04x\n",
80                       (unsigned int) -ret);
81        goto exit;
82    }
83
84    mbedtls_printf("\n  . Reading public key from '%s'", argv[1]);
85    fflush(stdout);
86
87    if ((ret = mbedtls_pk_parse_public_keyfile(&pk, argv[1])) != 0) {
88        mbedtls_printf(" failed\n  ! mbedtls_pk_parse_public_keyfile returned -0x%04x\n",
89                       (unsigned int) -ret);
90        goto exit;
91    }
92
93    if (strlen(argv[2]) > 100) {
94        mbedtls_printf(" Input data larger than 100 characters.\n\n");
95        goto exit;
96    }
97
98    memcpy(input, argv[2], strlen(argv[2]));
99
100    /*
101     * Calculate the RSA encryption of the hash.
102     */
103    mbedtls_printf("\n  . Generating the encrypted value");
104    fflush(stdout);
105
106    if ((ret = mbedtls_pk_encrypt(&pk, input, strlen(argv[2]),
107                                  buf, &olen, sizeof(buf),
108                                  mbedtls_ctr_drbg_random, &ctr_drbg)) != 0) {
109        mbedtls_printf(" failed\n  ! mbedtls_pk_encrypt returned -0x%04x\n",
110                       (unsigned int) -ret);
111        goto exit;
112    }
113
114    /*
115     * Write the signature into result-enc.txt
116     */
117    if ((f = fopen("result-enc.txt", "wb+")) == NULL) {
118        mbedtls_printf(" failed\n  ! Could not create %s\n\n",
119                       "result-enc.txt");
120        ret = 1;
121        goto exit;
122    }
123
124    for (i = 0; i < olen; i++) {
125        mbedtls_fprintf(f, "%02X%s", buf[i],
126                        (i + 1) % 16 == 0 ? "\r\n" : " ");
127    }
128
129    fclose(f);
130
131    mbedtls_printf("\n  . Done (created \"%s\")\n\n", "result-enc.txt");
132
133    exit_code = MBEDTLS_EXIT_SUCCESS;
134
135exit:
136
137    mbedtls_pk_free(&pk);
138    mbedtls_entropy_free(&entropy);
139    mbedtls_ctr_drbg_free(&ctr_drbg);
140#if defined(MBEDTLS_USE_PSA_CRYPTO)
141    mbedtls_psa_crypto_free();
142#endif /* MBEDTLS_USE_PSA_CRYPTO */
143
144#if defined(MBEDTLS_ERROR_C)
145    if (exit_code != MBEDTLS_EXIT_SUCCESS) {
146        mbedtls_strerror(ret, (char *) buf, sizeof(buf));
147        mbedtls_printf("  !  Last error was: %s\n", buf);
148    }
149#endif
150
151    mbedtls_exit(exit_code);
152}
153#endif /* MBEDTLS_BIGNUM_C && MBEDTLS_PK_PARSE_C && MBEDTLS_ENTROPY_C &&
154          MBEDTLS_FS_IO && MBEDTLS_CTR_DRBG_C */
155