0002-mbedtls-support.patch 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715
  1. From 68352e0cb94fe08b220d4befec828171ec871154 Mon Sep 17 00:00:00 2001
  2. From: =?UTF-8?q?Timo=20Ter=C3=A4s?= <[email protected]>
  3. Date: Fri, 5 Apr 2024 12:06:56 +0300
  4. Subject: [PATCH 1/2] add alternate url wget implementation
  5. ---
  6. meson.build | 6 +-
  7. meson_options.txt | 1 +
  8. src/io_url_wget.c | 137 ++++++++++++++++++++++++++++++++++++++++++++++
  9. src/meson.build | 8 ++-
  10. 4 files changed, 150 insertions(+), 2 deletions(-)
  11. create mode 100644 src/io_url_wget.c
  12. diff --git a/meson.build b/meson.build
  13. index 1a44c11f..9a14cac0 100644
  14. --- a/meson.build
  15. +++ b/meson.build
  16. @@ -33,6 +33,10 @@ subproject = meson.is_subproject()
  17. subdir('doc')
  18. subdir('portability')
  19. -subdir('libfetch')
  20. +if get_option('url_backend') == 'libfetch'
  21. + subdir('libfetch')
  22. +else
  23. + libfetch_dep = dependency('', required: false)
  24. +endif
  25. subdir('src')
  26. subdir('tests')
  27. diff --git a/meson_options.txt b/meson_options.txt
  28. index 693f46ec..44b88b32 100644
  29. --- a/meson_options.txt
  30. +++ b/meson_options.txt
  31. @@ -5,5 +5,6 @@ option('help', description: 'Build help into apk binaries, needs lua', type: 'fe
  32. option('lua', description: 'Build luaapk (lua bindings)', type: 'feature', value: 'auto')
  33. option('lua_version', description: 'Lua version to build against', type: 'string', value: '5.3')
  34. option('static_apk', description: 'Also build apk.static', type: 'boolean', value: false)
  35. +option('url_backend', description: 'URL backend', type: 'string', value: 'libfetch')
  36. option('uvol_db_target', description: 'Default target for uvol database layer', type: 'string')
  37. option('zstd', description: 'Build with zstd support', type: 'boolean', value: true)
  38. diff --git a/src/io_url_wget.c b/src/io_url_wget.c
  39. new file mode 100644
  40. index 00000000..d8885a4f
  41. --- /dev/null
  42. +++ b/src/io_url_wget.c
  43. @@ -0,0 +1,137 @@
  44. +/* io_url_wget.c - Alpine Package Keeper (APK)
  45. + *
  46. + * Copyright (C) 2005-2008 Natanael Copa <[email protected]>
  47. + * Copyright (C) 2008-2011 Timo Teräs <[email protected]>
  48. + * All rights reserved.
  49. + *
  50. + * SPDX-License-Identifier: GPL-2.0-only
  51. + */
  52. +
  53. +#include <spawn.h>
  54. +#include <unistd.h>
  55. +#include <sys/wait.h>
  56. +#include "apk_io.h"
  57. +
  58. +static int wget_translate_status(int status)
  59. +{
  60. + if (!WIFEXITED(status)) return -EFAULT;
  61. + switch (WEXITSTATUS(status)) {
  62. + case 0: return 0;
  63. + case 3: return -EIO;
  64. + case 4: return -ENETUNREACH;
  65. + case 5: return -EACCES;
  66. + case 6: return -EACCES;
  67. + case 7: return -EPROTO;
  68. + default: return -APKE_REMOTE_IO;
  69. + }
  70. +}
  71. +
  72. +struct apk_wget_istream {
  73. + struct apk_istream is;
  74. + int fd;
  75. + pid_t pid;
  76. +};
  77. +
  78. +static int wget_spawn(const char *url, pid_t *pid, int *fd)
  79. +{
  80. + int r, pipefds[2];
  81. + posix_spawn_file_actions_t act;
  82. + char *argv[] = {
  83. + (char*)"wget", "-q", (char*) url, "-O", "-", 0
  84. + };
  85. +
  86. + if (pipe2(pipefds, O_CLOEXEC) != 0) return -errno;
  87. +
  88. + posix_spawn_file_actions_init(&act);
  89. + posix_spawn_file_actions_adddup2(&act, pipefds[1], STDOUT_FILENO);
  90. + r = posix_spawnp(pid, "wget", &act, 0, argv, environ);
  91. + posix_spawn_file_actions_destroy(&act);
  92. + if (r != 0) return -r;
  93. + close(pipefds[1]);
  94. + *fd = pipefds[0];
  95. + return 0;
  96. +}
  97. +
  98. +static int wget_check_exit(struct apk_wget_istream *wis)
  99. +{
  100. + int status;
  101. +
  102. + if (wis->pid == 0) return apk_istream_error(&wis->is, 0);
  103. + if (waitpid(wis->pid, &status, 0) == wis->pid) {
  104. + wis->pid = 0;
  105. + return apk_istream_error(&wis->is, wget_translate_status(status));
  106. + }
  107. + return 0;
  108. +}
  109. +
  110. +static void wget_get_meta(struct apk_istream *is, struct apk_file_meta *meta)
  111. +{
  112. +}
  113. +
  114. +static ssize_t wget_read(struct apk_istream *is, void *ptr, size_t size)
  115. +{
  116. + struct apk_wget_istream *wis = container_of(is, struct apk_wget_istream, is);
  117. + ssize_t r;
  118. +
  119. + r = read(wis->fd, ptr, size);
  120. + if (r < 0) return -errno;
  121. + if (r == 0) return wget_check_exit(wis);
  122. + return r;
  123. +}
  124. +
  125. +static int wget_close(struct apk_istream *is)
  126. +{
  127. + int r = is->err;
  128. + struct apk_wget_istream *wis = container_of(is, struct apk_wget_istream, is);
  129. +
  130. + while (wis->pid != 0)
  131. + wget_check_exit(wis);
  132. +
  133. + close(wis->fd);
  134. + free(wis);
  135. + return r < 0 ? r : 0;
  136. +}
  137. +
  138. +static const struct apk_istream_ops wget_istream_ops = {
  139. + .get_meta = wget_get_meta,
  140. + .read = wget_read,
  141. + .close = wget_close,
  142. +};
  143. +
  144. +struct apk_istream *apk_io_url_istream(const char *url, time_t since)
  145. +{
  146. + struct apk_wget_istream *wis;
  147. + int r;
  148. +
  149. + wis = malloc(sizeof(*wis) + apk_io_bufsize);
  150. + if (wis == NULL) return ERR_PTR(-ENOMEM);
  151. +
  152. + *wis = (struct apk_wget_istream) {
  153. + .is.ops = &wget_istream_ops,
  154. + .is.buf = (uint8_t *)(wis + 1),
  155. + .is.buf_size = apk_io_bufsize,
  156. + };
  157. + r = wget_spawn(url, &wis->pid, &wis->fd);
  158. + if (r != 0) {
  159. + free(wis);
  160. + return ERR_PTR(r);
  161. + }
  162. +
  163. + return &wis->is;
  164. +}
  165. +
  166. +void apk_io_url_no_check_certificate(void)
  167. +{
  168. +}
  169. +
  170. +void apk_io_url_set_timeout(int timeout)
  171. +{
  172. +}
  173. +
  174. +void apk_io_url_set_redirect_callback(void (*cb)(int, const char *))
  175. +{
  176. +}
  177. +
  178. +void apk_io_url_init(void)
  179. +{
  180. +}
  181. diff --git a/src/meson.build b/src/meson.build
  182. index c1aae550..28bfce7e 100644
  183. --- a/src/meson.build
  184. +++ b/src/meson.build
  185. @@ -22,7 +22,6 @@ libapk_src = [
  186. 'fs_uvol.c',
  187. 'hash.c',
  188. 'io.c',
  189. - 'io_url_libfetch.c',
  190. 'io_gunzip.c',
  191. 'package.c',
  192. 'pathbuilder.c',
  193. @@ -87,6 +86,13 @@ apk_src = [
  194. 'applet.c',
  195. ]
  196. +url_backend = get_option('url_backend')
  197. +if url_backend == 'libfetch'
  198. + libapk_src += [ 'io_url_libfetch.c' ]
  199. +elif url_backend == 'wget'
  200. + libapk_src += [ 'io_url_wget.c' ]
  201. +endif
  202. +
  203. if lua_bin.found()
  204. genhelp_script = files('genhelp.lua')
  205. genhelp_args = [lua_bin, genhelp_script, '@INPUT@']
  206. --
  207. GitLab
  208. From dc7ff789a45522eb847118a29b60b896de55d083 Mon Sep 17 00:00:00 2001
  209. From: Jonas Jelonek <[email protected]>
  210. Date: Sun, 14 Apr 2024 00:20:14 +0200
  211. Subject: [PATCH 2/2] crypto: add support for mbedtls as backend
  212. backend is selected at compile-time with crypto_backend option
  213. Co-developed-by: Christian Marangi <[email protected]>
  214. Signed-off-by: Christian Marangi <[email protected]>
  215. Signed-off-by: Jonas Jelonek <[email protected]>
  216. ---
  217. libfetch/meson.build | 2 +-
  218. meson.build | 14 +-
  219. meson_options.txt | 1 +
  220. src/apk_crypto.h | 5 +
  221. src/apk_crypto_mbedtls.h | 26 ++++
  222. src/crypto_mbedtls.c | 305 +++++++++++++++++++++++++++++++++++++++
  223. src/meson.build | 23 ++-
  224. 7 files changed, 364 insertions(+), 12 deletions(-)
  225. create mode 100644 src/apk_crypto_mbedtls.h
  226. create mode 100644 src/crypto_mbedtls.c
  227. diff --git a/libfetch/meson.build b/libfetch/meson.build
  228. index 431ba197..e24f95eb 100644
  229. --- a/libfetch/meson.build
  230. +++ b/libfetch/meson.build
  231. @@ -40,7 +40,7 @@ libfetch = static_library(
  232. c_args: libfetch_cargs,
  233. dependencies: [
  234. libportability_dep.partial_dependency(compile_args: true, includes: true),
  235. - openssl_dep.partial_dependency(compile_args: true, includes: true)
  236. + crypto_dep.partial_dependency(compile_args: true, includes: true)
  237. ],
  238. )
  239. diff --git a/meson.build b/meson.build
  240. index 9a14cac0..3a83f4e1 100644
  241. --- a/meson.build
  242. +++ b/meson.build
  243. @@ -13,15 +13,21 @@ apk_libdir = get_option('libdir')
  244. lua_bin = find_program('lua' + get_option('lua_version'), required: get_option('help'))
  245. lua_dep = dependency('lua' + get_option('lua_version'), required: get_option('lua'))
  246. scdoc_dep = dependency('scdoc', version: '>=1.10', required: get_option('docs'))
  247. -openssl_dep = dependency('openssl')
  248. -openssl_static_dep = dependency('openssl', static: true)
  249. zlib_dep = dependency('zlib')
  250. zlib_static_dep = dependency('zlib', static: true)
  251. libzstd_dep = dependency('libzstd', required: get_option('zstd'))
  252. libzstd_static_dep = dependency('libzstd', required: get_option('zstd'), static: true)
  253. -shared_deps = [ openssl_dep, zlib_dep, libzstd_dep ]
  254. -static_deps = [ openssl_static_dep, zlib_static_dep, libzstd_static_dep ]
  255. +if get_option('crypto_backend') == 'openssl'
  256. + crypto_dep = dependency('openssl')
  257. + crypto_static_dep = dependency('openssl', static: true)
  258. +elif get_option('crypto_backend') == 'mbedtls'
  259. + crypto_dep = [ dependency('mbedtls'), dependency('mbedcrypto') ]
  260. + crypto_static_dep = [ dependency('mbedtls', static: true), dependency('mbedcrypto', static: true) ]
  261. +endif
  262. +
  263. +shared_deps = [ crypto_dep, zlib_dep, libzstd_dep ]
  264. +static_deps = [ crypto_static_dep, zlib_static_dep, libzstd_static_dep ]
  265. add_project_arguments('-D_GNU_SOURCE', language: 'c')
  266. diff --git a/meson_options.txt b/meson_options.txt
  267. index 44b88b32..2b1d24ce 100644
  268. --- a/meson_options.txt
  269. +++ b/meson_options.txt
  270. @@ -5,6 +5,7 @@ option('help', description: 'Build help into apk binaries, needs lua', type: 'fe
  271. option('lua', description: 'Build luaapk (lua bindings)', type: 'feature', value: 'auto')
  272. option('lua_version', description: 'Lua version to build against', type: 'string', value: '5.3')
  273. option('static_apk', description: 'Also build apk.static', type: 'boolean', value: false)
  274. +option('crypto_backend', description: 'SSL backend', type: 'string', value: 'openssl')
  275. option('url_backend', description: 'URL backend', type: 'string', value: 'libfetch')
  276. option('uvol_db_target', description: 'Default target for uvol database layer', type: 'string')
  277. option('zstd', description: 'Build with zstd support', type: 'boolean', value: true)
  278. diff --git a/src/apk_crypto.h b/src/apk_crypto.h
  279. index 7de88dfc..5cae3bfe 100644
  280. --- a/src/apk_crypto.h
  281. +++ b/src/apk_crypto.h
  282. @@ -12,7 +12,12 @@
  283. #include <string.h>
  284. #include "apk_defines.h"
  285. #include "apk_blob.h"
  286. +
  287. +#if defined(CRYPTO_USE_OPENSSL)
  288. #include "apk_crypto_openssl.h"
  289. +#elif defined(CRYPTO_USE_MBEDTLS)
  290. +#include "apk_crypto_mbedtls.h"
  291. +#endif
  292. // Digest
  293. diff --git a/src/apk_crypto_mbedtls.h b/src/apk_crypto_mbedtls.h
  294. new file mode 100644
  295. index 00000000..e379535b
  296. --- /dev/null
  297. +++ b/src/apk_crypto_mbedtls.h
  298. @@ -0,0 +1,26 @@
  299. +/* apk_crypto_mbedtls.h - Alpine Package Keeper (APK)
  300. + *
  301. + * Copyright (C) 2024
  302. + * All rights reserved.
  303. + *
  304. + * SPDX-License-Identifier: GPL-2.0-only
  305. + */
  306. +
  307. +#ifndef APK_CRYPTO_MBEDTLS_H
  308. +#define APK_CRYPTO_MBEDTLS_H
  309. +
  310. +#include <mbedtls/md.h>
  311. +#include <mbedtls/pk.h>
  312. +
  313. +struct apk_pkey {
  314. + uint8_t id[16];
  315. + mbedtls_pk_context *key;
  316. +};
  317. +
  318. +struct apk_digest_ctx {
  319. + mbedtls_md_context_t *mdctx;
  320. + struct apk_pkey *sigver_key;
  321. + uint8_t alg;
  322. +};
  323. +
  324. +#endif
  325. diff --git a/src/crypto_mbedtls.c b/src/crypto_mbedtls.c
  326. new file mode 100644
  327. index 00000000..9ce148b5
  328. --- /dev/null
  329. +++ b/src/crypto_mbedtls.c
  330. @@ -0,0 +1,305 @@
  331. +#include <errno.h>
  332. +#include <stdio.h>
  333. +#include <stdlib.h>
  334. +#include <fcntl.h>
  335. +#include <sys/random.h>
  336. +
  337. +#include <mbedtls/platform.h>
  338. +#include <mbedtls/md.h>
  339. +#include <mbedtls/pk.h>
  340. +#include <mbedtls/entropy.h>
  341. +#include <psa/crypto.h>
  342. +
  343. +#include "apk_crypto.h"
  344. +
  345. +static inline const mbedtls_md_type_t apk_digest_alg_to_mbedtls_type(uint8_t alg) {
  346. + switch (alg) {
  347. + case APK_DIGEST_NONE: return MBEDTLS_MD_NONE;
  348. + case APK_DIGEST_MD5: return MBEDTLS_MD_MD5;
  349. + case APK_DIGEST_SHA1: return MBEDTLS_MD_SHA1;
  350. + case APK_DIGEST_SHA256_160:
  351. + case APK_DIGEST_SHA256: return MBEDTLS_MD_SHA256;
  352. + case APK_DIGEST_SHA512: return MBEDTLS_MD_SHA512;
  353. + default:
  354. + assert(alg);
  355. + return MBEDTLS_MD_NONE;
  356. + }
  357. +}
  358. +
  359. +static inline const mbedtls_md_info_t *apk_digest_alg_to_mdinfo(uint8_t alg)
  360. +{
  361. + return mbedtls_md_info_from_type(
  362. + apk_digest_alg_to_mbedtls_type(alg)
  363. + );
  364. +}
  365. +
  366. +int apk_digest_calc(struct apk_digest *d, uint8_t alg, const void *ptr, size_t sz)
  367. +{
  368. + if (mbedtls_md(apk_digest_alg_to_mdinfo(alg), ptr, sz, d->data))
  369. + return -APKE_CRYPTO_ERROR;
  370. +
  371. + apk_digest_set(d, alg);
  372. + return 0;
  373. +}
  374. +
  375. +int apk_digest_ctx_init(struct apk_digest_ctx *dctx, uint8_t alg)
  376. +{
  377. + dctx->alg = alg;
  378. + dctx->mdctx = malloc(sizeof(mbedtls_md_context_t));
  379. +
  380. + if (!dctx->mdctx) return -ENOMEM;
  381. +
  382. + mbedtls_md_init(dctx->mdctx);
  383. + if (alg == APK_DIGEST_NONE) return 0;
  384. + if (mbedtls_md_setup(dctx->mdctx, apk_digest_alg_to_mdinfo(alg), 0) ||
  385. + mbedtls_md_starts(dctx->mdctx))
  386. + return -APKE_CRYPTO_ERROR;
  387. +
  388. + return 0;
  389. +}
  390. +
  391. +int apk_digest_ctx_reset(struct apk_digest_ctx *dctx)
  392. +{
  393. + if (dctx->alg == APK_DIGEST_NONE) return 0;
  394. + if (mbedtls_md_starts(dctx->mdctx)) return -APKE_CRYPTO_ERROR;
  395. + return 0;
  396. +}
  397. +
  398. +int apk_digest_ctx_reset_alg(struct apk_digest_ctx *dctx, uint8_t alg)
  399. +{
  400. + mbedtls_md_free(dctx->mdctx);
  401. +
  402. + dctx->alg = alg;
  403. + if (alg == APK_DIGEST_NONE) return 0;
  404. + if (mbedtls_md_setup(dctx->mdctx, apk_digest_alg_to_mdinfo(alg), 0) ||
  405. + mbedtls_md_starts(dctx->mdctx))
  406. + return -APKE_CRYPTO_ERROR;
  407. +
  408. + return 0;
  409. +}
  410. +
  411. +void apk_digest_ctx_free(struct apk_digest_ctx *dctx)
  412. +{
  413. + free(dctx->mdctx);
  414. + dctx->mdctx = 0;
  415. +}
  416. +
  417. +int apk_digest_ctx_update(struct apk_digest_ctx *dctx, const void *ptr, size_t sz)
  418. +{
  419. + if (dctx->alg == APK_DIGEST_NONE) return 0;
  420. + return mbedtls_md_update(dctx->mdctx, ptr, sz) == 0 ? 0 : -APKE_CRYPTO_ERROR;
  421. +}
  422. +
  423. +int apk_digest_ctx_final(struct apk_digest_ctx *dctx, struct apk_digest *d)
  424. +{
  425. + if (mbedtls_md_finish(dctx->mdctx, d->data)) {
  426. + apk_digest_reset(d);
  427. + return -APKE_CRYPTO_ERROR;
  428. + }
  429. +
  430. + mbedtls_md_free(dctx->mdctx);
  431. +
  432. + d->alg = dctx->alg;
  433. + d->len = apk_digest_alg_len(d->alg);
  434. + return 0;
  435. +}
  436. +
  437. +// Entropy function adopted from ustream-ssl to avoid using the bloated mbedtls'
  438. +// mbedtls_entropy_context and mbedtls_ctr_drbg_context.
  439. +static int _apk_random(void *ctx, unsigned char *out, size_t len)
  440. +{
  441. + static FILE *f;
  442. +
  443. + if (!f)
  444. + f = fopen("/dev/urandom", "r");
  445. + if (fread(out, len, 1, f) != 1)
  446. + return MBEDTLS_ERR_ENTROPY_SOURCE_FAILED;
  447. +
  448. + return 0;
  449. +}
  450. +
  451. +// adopted from mbedtls_pk_load_file
  452. +static int apk_load_file_fd(int fd, unsigned char **buf, size_t *n)
  453. +{
  454. + FILE *f;
  455. + long size;
  456. +
  457. + if ((f = fdopen(fd, "rb")) == NULL) {
  458. + return MBEDTLS_ERR_PK_FILE_IO_ERROR;
  459. + }
  460. +
  461. +#if (MBEDTLS_VERSION_NUMBER >= 0x03000000)
  462. + /* Ensure no stdio buffering of secrets, as such buffers cannot be wiped. */
  463. + mbedtls_setbuf(f, NULL);
  464. +#endif
  465. +
  466. + fseek(f, 0, SEEK_END);
  467. + if ((size = ftell(f)) == -1) {
  468. + fclose(f);
  469. + return MBEDTLS_ERR_PK_FILE_IO_ERROR;
  470. + }
  471. + fseek(f, 0, SEEK_SET);
  472. +
  473. + *n = (size_t) size;
  474. +
  475. + if (*n + 1 == 0 ||
  476. + (*buf = mbedtls_calloc(1, *n + 1)) == NULL) {
  477. + fclose(f);
  478. + return MBEDTLS_ERR_PK_ALLOC_FAILED;
  479. + }
  480. +
  481. + if (fread(*buf, 1, *n, f) != *n) {
  482. + fclose(f);
  483. +
  484. + mbedtls_platform_zeroize(*buf, *n);
  485. + mbedtls_free(*buf);
  486. +
  487. + return MBEDTLS_ERR_PK_FILE_IO_ERROR;
  488. + }
  489. +
  490. + fclose(f);
  491. +
  492. + (*buf)[*n] = '\0';
  493. +
  494. + if (strstr((const char *) *buf, "-----BEGIN ") != NULL) {
  495. + ++*n;
  496. + }
  497. +
  498. + return 0;
  499. +}
  500. +
  501. +static int apk_pkey_init(struct apk_pkey *pkey, mbedtls_pk_context *key)
  502. +{
  503. + unsigned char dig[APK_DIGEST_MAX_LENGTH], *pub = NULL;
  504. + unsigned char *c;
  505. + int len, publen, r = -APKE_CRYPTO_ERROR;
  506. +
  507. + // Assume byte len is always * 2 + NULL terminated
  508. + publen = mbedtls_pk_get_len(key) * 2 + 1;
  509. + pub = malloc(publen);
  510. + if (!pub)
  511. + return -ENOMEM;
  512. + c = pub + publen;
  513. +
  514. + if ((len = mbedtls_pk_write_pubkey(&c, pub, key)) < 0) return -APKE_CRYPTO_ERROR;
  515. + if (!mbedtls_md(apk_digest_alg_to_mdinfo(APK_DIGEST_SHA512), pub, len, dig)) {
  516. + memcpy(pkey->id, dig, sizeof pkey->id);
  517. + r = 0;
  518. + }
  519. +
  520. + free(pub);
  521. + pkey->key = key;
  522. +
  523. + return r;
  524. +}
  525. +
  526. +void apk_pkey_free(struct apk_pkey *pkey)
  527. +{
  528. + mbedtls_pk_free(pkey->key);
  529. +}
  530. +
  531. +int apk_pkey_load(struct apk_pkey *pkey, int dirfd, const char *fn)
  532. +{
  533. + mbedtls_pk_context *key;
  534. + unsigned char *buf;
  535. + size_t blen;
  536. + int ret, fd;
  537. +
  538. + fd = openat(dirfd, fn, O_RDONLY|O_CLOEXEC);
  539. + if (fd < 0)
  540. + return -errno;
  541. +
  542. + key = malloc(sizeof *key);
  543. + if (!key)
  544. + return -ENOMEM;
  545. +
  546. + mbedtls_pk_init(key);
  547. + if (apk_load_file_fd(fd, &buf, &blen))
  548. + return -APKE_CRYPTO_ERROR;
  549. +
  550. + if ((ret = mbedtls_pk_parse_public_key(key, buf, blen)) != 0) {
  551. +#if (MBEDTLS_VERSION_NUMBER >= 0x03000000)
  552. + ret = mbedtls_pk_parse_key(key, buf, blen, NULL, 0, _apk_random, NULL);
  553. +#else
  554. + ret = mbedtls_pk_parse_key(key, buf, blen, NULL, 0);
  555. +#endif
  556. + }
  557. + mbedtls_platform_zeroize(buf, blen);
  558. + mbedtls_free(buf);
  559. + if (ret != 0)
  560. + return -APKE_CRYPTO_KEY_FORMAT;
  561. +
  562. + return apk_pkey_init(pkey, key);
  563. +}
  564. +
  565. +int apk_sign_start(struct apk_digest_ctx *dctx, uint8_t alg, struct apk_pkey *pkey)
  566. +{
  567. + if (apk_digest_ctx_reset_alg(dctx, alg))
  568. + return -APKE_CRYPTO_ERROR;
  569. +
  570. + dctx->sigver_key = pkey;
  571. +
  572. + return 0;
  573. +}
  574. +
  575. +int apk_sign(struct apk_digest_ctx *dctx, void *sig, size_t *len)
  576. +{
  577. + struct apk_digest dig;
  578. + int r = 0;
  579. +
  580. + if (apk_digest_ctx_final(dctx, &dig))
  581. + return -APKE_SIGNATURE_GEN_FAILURE;
  582. +#if (MBEDTLS_VERSION_NUMBER >= 0x03000000)
  583. + if (mbedtls_pk_sign(dctx->sigver_key->key, apk_digest_alg_to_mbedtls_type(dctx->alg),
  584. + &dig.data, dig.len, sig, sizeof *sig, len, _apk_random, NULL))
  585. +#else
  586. + if (mbedtls_pk_sign(dctx->sigver_key->key, apk_digest_alg_to_mbedtls_type(dctx->alg),
  587. + &dig.data, dig.len, sig, len, _apk_random, NULL))
  588. +#endif
  589. + r = -APKE_SIGNATURE_GEN_FAILURE;
  590. +
  591. +
  592. + dctx->sigver_key = NULL;
  593. + return r;
  594. +}
  595. +
  596. +int apk_verify_start(struct apk_digest_ctx *dctx, uint8_t alg, struct apk_pkey *pkey)
  597. +{
  598. + if (apk_digest_ctx_reset_alg(dctx, alg))
  599. + return -APKE_CRYPTO_ERROR;
  600. +
  601. + dctx->sigver_key = pkey;
  602. +
  603. + return 0;
  604. +}
  605. +
  606. +int apk_verify(struct apk_digest_ctx *dctx, void *sig, size_t len)
  607. +{
  608. + struct apk_digest dig;
  609. + int r = 0;
  610. +
  611. + if (apk_digest_ctx_final(dctx, &dig))
  612. + return -APKE_SIGNATURE_GEN_FAILURE;
  613. +
  614. + if (mbedtls_pk_verify(dctx->sigver_key->key, apk_digest_alg_to_mbedtls_type(dctx->alg), &dig.data, dig.len, sig, len))
  615. + r = -APKE_SIGNATURE_INVALID;
  616. +
  617. + dctx->sigver_key = NULL;
  618. + return r;
  619. +}
  620. +
  621. +static void apk_crypto_cleanup(void)
  622. +{
  623. +#ifdef MBEDTLS_PSA_CRYPTO_C
  624. + mbedtls_psa_crypto_free();
  625. +#endif
  626. +}
  627. +
  628. +void apk_crypto_init(void)
  629. +{
  630. + atexit(apk_crypto_cleanup);
  631. +
  632. +#ifdef MBEDTLS_PSA_CRYPTO_C
  633. + psa_crypto_init();
  634. +#endif
  635. +}
  636. diff --git a/src/meson.build b/src/meson.build
  637. index 28bfce7e..4eab6e0d 100644
  638. --- a/src/meson.build
  639. +++ b/src/meson.build
  640. @@ -13,7 +13,6 @@ libapk_src = [
  641. 'common.c',
  642. 'context.c',
  643. 'crypto.c',
  644. - 'crypto_openssl.c',
  645. 'ctype.c',
  646. 'database.c',
  647. 'extract_v2.c',
  648. @@ -37,7 +36,6 @@ libapk_headers = [
  649. 'apk_atom.h',
  650. 'apk_blob.h',
  651. 'apk_crypto.h',
  652. - 'apk_crypto_openssl.h',
  653. 'apk_ctype.h',
  654. 'apk_database.h',
  655. 'apk_defines.h',
  656. @@ -86,6 +84,11 @@ apk_src = [
  657. 'applet.c',
  658. ]
  659. +apk_cargs = [
  660. + '-DAPK_VERSION="' + meson.project_version() + '"',
  661. + '-D_ATFILE_SOURCE',
  662. +]
  663. +
  664. url_backend = get_option('url_backend')
  665. if url_backend == 'libfetch'
  666. libapk_src += [ 'io_url_libfetch.c' ]
  667. @@ -93,6 +96,17 @@ elif url_backend == 'wget'
  668. libapk_src += [ 'io_url_wget.c' ]
  669. endif
  670. +crypto_backend = get_option('crypto_backend')
  671. +if crypto_backend == 'openssl'
  672. + apk_cargs += [ '-DCRYPTO_USE_OPENSSL' ]
  673. + libapk_src += [ 'crypto_openssl.c' ]
  674. + libapk_headers += [ 'apk_crypto_openssl.h' ]
  675. +elif crypto_backend == 'mbedtls'
  676. + apk_cargs += [ '-DCRYPTO_USE_MBEDTLS' ]
  677. + libapk_src += [ 'crypto_mbedtls.c' ]
  678. + libapk_headers += [ 'apk_crypto_mbedtls.h' ]
  679. +endif
  680. +
  681. if lua_bin.found()
  682. genhelp_script = files('genhelp.lua')
  683. genhelp_args = [lua_bin, genhelp_script, '@INPUT@']
  684. @@ -119,11 +133,6 @@ endif
  685. apk_src += [ generated_help ]
  686. -apk_cargs = [
  687. - '-DAPK_VERSION="' + meson.project_version() + '"',
  688. - '-D_ATFILE_SOURCE',
  689. -]
  690. -
  691. apk_arch_prefix = get_option('arch_prefix')
  692. if apk_arch_prefix != ''
  693. apk_cargs += ['-DAPK_ARCH_PREFIX="@0@"'.format(apk_arch_prefix)]
  694. --
  695. GitLab