]> git.ipfire.org Git - thirdparty/openssl.git/blob - apps/apps_ui.c
Updated test command line parsing to support commmon commands
[thirdparty/openssl.git] / apps / apps_ui.c
1 /*
2 * Copyright 1995-2018 The OpenSSL Project Authors. All Rights Reserved.
3 *
4 * Licensed under the OpenSSL license (the "License"). You may not use
5 * this file except in compliance with the License. You can obtain a copy
6 * in the file LICENSE in the source distribution or at
7 * https://www.openssl.org/source/license.html
8 */
9
10 #include <string.h>
11 #include <openssl/err.h>
12 #include <openssl/ui.h>
13 #include "apps_ui.h"
14
15 static UI_METHOD *ui_method = NULL;
16 static const UI_METHOD *ui_fallback_method = NULL;
17
18
19 static int ui_open(UI *ui)
20 {
21 int (*opener)(UI *ui) = UI_method_get_opener(ui_fallback_method);
22
23 if (opener)
24 return opener(ui);
25 return 1;
26 }
27
28 static int ui_read(UI *ui, UI_STRING *uis)
29 {
30 int (*reader)(UI *ui, UI_STRING *uis) = NULL;
31
32 if (UI_get_input_flags(uis) & UI_INPUT_FLAG_DEFAULT_PWD
33 && UI_get0_user_data(ui)) {
34 switch (UI_get_string_type(uis)) {
35 case UIT_PROMPT:
36 case UIT_VERIFY:
37 {
38 const char *password =
39 ((PW_CB_DATA *)UI_get0_user_data(ui))->password;
40 if (password && password[0] != '\0') {
41 UI_set_result(ui, uis, password);
42 return 1;
43 }
44 }
45 break;
46 case UIT_NONE:
47 case UIT_BOOLEAN:
48 case UIT_INFO:
49 case UIT_ERROR:
50 break;
51 }
52 }
53
54 reader = UI_method_get_reader(ui_fallback_method);
55 if (reader)
56 return reader(ui, uis);
57 return 1;
58 }
59
60 static int ui_write(UI *ui, UI_STRING *uis)
61 {
62 int (*writer)(UI *ui, UI_STRING *uis) = NULL;
63
64 if (UI_get_input_flags(uis) & UI_INPUT_FLAG_DEFAULT_PWD
65 && UI_get0_user_data(ui)) {
66 switch (UI_get_string_type(uis)) {
67 case UIT_PROMPT:
68 case UIT_VERIFY:
69 {
70 const char *password =
71 ((PW_CB_DATA *)UI_get0_user_data(ui))->password;
72 if (password && password[0] != '\0')
73 return 1;
74 }
75 break;
76 case UIT_NONE:
77 case UIT_BOOLEAN:
78 case UIT_INFO:
79 case UIT_ERROR:
80 break;
81 }
82 }
83
84 writer = UI_method_get_writer(ui_fallback_method);
85 if (writer)
86 return writer(ui, uis);
87 return 1;
88 }
89
90 static int ui_close(UI *ui)
91 {
92 int (*closer)(UI *ui) = UI_method_get_closer(ui_fallback_method);
93
94 if (closer)
95 return closer(ui);
96 return 1;
97 }
98
99 int setup_ui_method(void)
100 {
101 ui_fallback_method = UI_null();
102 #ifndef OPENSSL_NO_UI_CONSOLE
103 ui_fallback_method = UI_OpenSSL();
104 #endif
105 ui_method = UI_create_method("OpenSSL application user interface");
106 UI_method_set_opener(ui_method, ui_open);
107 UI_method_set_reader(ui_method, ui_read);
108 UI_method_set_writer(ui_method, ui_write);
109 UI_method_set_closer(ui_method, ui_close);
110 return 0;
111 }
112
113 void destroy_ui_method(void)
114 {
115 if (ui_method) {
116 UI_destroy_method(ui_method);
117 ui_method = NULL;
118 }
119 }
120
121 const UI_METHOD *get_ui_method(void)
122 {
123 return ui_method;
124 }
125
126 static void *ui_malloc(int sz, const char *what)
127 {
128 void *vp = OPENSSL_malloc(sz);
129
130 if (vp == NULL) {
131 BIO_printf(bio_err, "Could not allocate %d bytes for %s\n", sz, what);
132 ERR_print_errors(bio_err);
133 exit(1);
134 }
135 return vp;
136 }
137
138 int password_callback(char *buf, int bufsiz, int verify, PW_CB_DATA *cb_data)
139 {
140 int res = 0;
141 UI *ui;
142 int ok = 0;
143 char *buff = NULL;
144 int ui_flags = 0;
145 const char *prompt_info = NULL;
146 char *prompt;
147
148 if ((ui = UI_new_method(ui_method)) == NULL)
149 return 0;
150
151 if (cb_data != NULL && cb_data->prompt_info != NULL)
152 prompt_info = cb_data->prompt_info;
153 prompt = UI_construct_prompt(ui, "pass phrase", prompt_info);
154 if (prompt == NULL) {
155 BIO_printf(bio_err, "Out of memory\n");
156 UI_free(ui);
157 return 0;
158 }
159
160 ui_flags |= UI_INPUT_FLAG_DEFAULT_PWD;
161 UI_ctrl(ui, UI_CTRL_PRINT_ERRORS, 1, 0, 0);
162
163 /* We know that there is no previous user data to return to us */
164 (void)UI_add_user_data(ui, cb_data);
165
166 ok = UI_add_input_string(ui, prompt, ui_flags, buf,
167 PW_MIN_LENGTH, bufsiz - 1);
168
169 if (ok >= 0 && verify) {
170 buff = ui_malloc(bufsiz, "password buffer");
171 ok = UI_add_verify_string(ui, prompt, ui_flags, buff,
172 PW_MIN_LENGTH, bufsiz - 1, buf);
173 }
174 if (ok >= 0)
175 do {
176 ok = UI_process(ui);
177 } while (ok < 0 && UI_ctrl(ui, UI_CTRL_IS_REDOABLE, 0, 0, 0));
178
179 OPENSSL_clear_free(buff, (unsigned int)bufsiz);
180
181 if (ok >= 0)
182 res = strlen(buf);
183 if (ok == -1) {
184 BIO_printf(bio_err, "User interface error\n");
185 ERR_print_errors(bio_err);
186 OPENSSL_cleanse(buf, (unsigned int)bufsiz);
187 res = 0;
188 }
189 if (ok == -2) {
190 BIO_printf(bio_err, "aborted!\n");
191 OPENSSL_cleanse(buf, (unsigned int)bufsiz);
192 res = 0;
193 }
194 UI_free(ui);
195 OPENSSL_free(prompt);
196 return res;
197 }