162306a36Sopenharmony_ci// SPDX-License-Identifier: GPL-2.0 262306a36Sopenharmony_ci/* 362306a36Sopenharmony_ci * Copyright (C) 2015-2019 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved. 462306a36Sopenharmony_ci */ 562306a36Sopenharmony_ci 662306a36Sopenharmony_ci#ifdef DEBUG 762306a36Sopenharmony_cibool __init wg_packet_counter_selftest(void) 862306a36Sopenharmony_ci{ 962306a36Sopenharmony_ci struct noise_replay_counter *counter; 1062306a36Sopenharmony_ci unsigned int test_num = 0, i; 1162306a36Sopenharmony_ci bool success = true; 1262306a36Sopenharmony_ci 1362306a36Sopenharmony_ci counter = kmalloc(sizeof(*counter), GFP_KERNEL); 1462306a36Sopenharmony_ci if (unlikely(!counter)) { 1562306a36Sopenharmony_ci pr_err("nonce counter self-test malloc: FAIL\n"); 1662306a36Sopenharmony_ci return false; 1762306a36Sopenharmony_ci } 1862306a36Sopenharmony_ci 1962306a36Sopenharmony_ci#define T_INIT do { \ 2062306a36Sopenharmony_ci memset(counter, 0, sizeof(*counter)); \ 2162306a36Sopenharmony_ci spin_lock_init(&counter->lock); \ 2262306a36Sopenharmony_ci } while (0) 2362306a36Sopenharmony_ci#define T_LIM (COUNTER_WINDOW_SIZE + 1) 2462306a36Sopenharmony_ci#define T(n, v) do { \ 2562306a36Sopenharmony_ci ++test_num; \ 2662306a36Sopenharmony_ci if (counter_validate(counter, n) != (v)) { \ 2762306a36Sopenharmony_ci pr_err("nonce counter self-test %u: FAIL\n", \ 2862306a36Sopenharmony_ci test_num); \ 2962306a36Sopenharmony_ci success = false; \ 3062306a36Sopenharmony_ci } \ 3162306a36Sopenharmony_ci } while (0) 3262306a36Sopenharmony_ci 3362306a36Sopenharmony_ci T_INIT; 3462306a36Sopenharmony_ci /* 1 */ T(0, true); 3562306a36Sopenharmony_ci /* 2 */ T(1, true); 3662306a36Sopenharmony_ci /* 3 */ T(1, false); 3762306a36Sopenharmony_ci /* 4 */ T(9, true); 3862306a36Sopenharmony_ci /* 5 */ T(8, true); 3962306a36Sopenharmony_ci /* 6 */ T(7, true); 4062306a36Sopenharmony_ci /* 7 */ T(7, false); 4162306a36Sopenharmony_ci /* 8 */ T(T_LIM, true); 4262306a36Sopenharmony_ci /* 9 */ T(T_LIM - 1, true); 4362306a36Sopenharmony_ci /* 10 */ T(T_LIM - 1, false); 4462306a36Sopenharmony_ci /* 11 */ T(T_LIM - 2, true); 4562306a36Sopenharmony_ci /* 12 */ T(2, true); 4662306a36Sopenharmony_ci /* 13 */ T(2, false); 4762306a36Sopenharmony_ci /* 14 */ T(T_LIM + 16, true); 4862306a36Sopenharmony_ci /* 15 */ T(3, false); 4962306a36Sopenharmony_ci /* 16 */ T(T_LIM + 16, false); 5062306a36Sopenharmony_ci /* 17 */ T(T_LIM * 4, true); 5162306a36Sopenharmony_ci /* 18 */ T(T_LIM * 4 - (T_LIM - 1), true); 5262306a36Sopenharmony_ci /* 19 */ T(10, false); 5362306a36Sopenharmony_ci /* 20 */ T(T_LIM * 4 - T_LIM, false); 5462306a36Sopenharmony_ci /* 21 */ T(T_LIM * 4 - (T_LIM + 1), false); 5562306a36Sopenharmony_ci /* 22 */ T(T_LIM * 4 - (T_LIM - 2), true); 5662306a36Sopenharmony_ci /* 23 */ T(T_LIM * 4 + 1 - T_LIM, false); 5762306a36Sopenharmony_ci /* 24 */ T(0, false); 5862306a36Sopenharmony_ci /* 25 */ T(REJECT_AFTER_MESSAGES, false); 5962306a36Sopenharmony_ci /* 26 */ T(REJECT_AFTER_MESSAGES - 1, true); 6062306a36Sopenharmony_ci /* 27 */ T(REJECT_AFTER_MESSAGES, false); 6162306a36Sopenharmony_ci /* 28 */ T(REJECT_AFTER_MESSAGES - 1, false); 6262306a36Sopenharmony_ci /* 29 */ T(REJECT_AFTER_MESSAGES - 2, true); 6362306a36Sopenharmony_ci /* 30 */ T(REJECT_AFTER_MESSAGES + 1, false); 6462306a36Sopenharmony_ci /* 31 */ T(REJECT_AFTER_MESSAGES + 2, false); 6562306a36Sopenharmony_ci /* 32 */ T(REJECT_AFTER_MESSAGES - 2, false); 6662306a36Sopenharmony_ci /* 33 */ T(REJECT_AFTER_MESSAGES - 3, true); 6762306a36Sopenharmony_ci /* 34 */ T(0, false); 6862306a36Sopenharmony_ci 6962306a36Sopenharmony_ci T_INIT; 7062306a36Sopenharmony_ci for (i = 1; i <= COUNTER_WINDOW_SIZE; ++i) 7162306a36Sopenharmony_ci T(i, true); 7262306a36Sopenharmony_ci T(0, true); 7362306a36Sopenharmony_ci T(0, false); 7462306a36Sopenharmony_ci 7562306a36Sopenharmony_ci T_INIT; 7662306a36Sopenharmony_ci for (i = 2; i <= COUNTER_WINDOW_SIZE + 1; ++i) 7762306a36Sopenharmony_ci T(i, true); 7862306a36Sopenharmony_ci T(1, true); 7962306a36Sopenharmony_ci T(0, false); 8062306a36Sopenharmony_ci 8162306a36Sopenharmony_ci T_INIT; 8262306a36Sopenharmony_ci for (i = COUNTER_WINDOW_SIZE + 1; i-- > 0;) 8362306a36Sopenharmony_ci T(i, true); 8462306a36Sopenharmony_ci 8562306a36Sopenharmony_ci T_INIT; 8662306a36Sopenharmony_ci for (i = COUNTER_WINDOW_SIZE + 2; i-- > 1;) 8762306a36Sopenharmony_ci T(i, true); 8862306a36Sopenharmony_ci T(0, false); 8962306a36Sopenharmony_ci 9062306a36Sopenharmony_ci T_INIT; 9162306a36Sopenharmony_ci for (i = COUNTER_WINDOW_SIZE + 1; i-- > 1;) 9262306a36Sopenharmony_ci T(i, true); 9362306a36Sopenharmony_ci T(COUNTER_WINDOW_SIZE + 1, true); 9462306a36Sopenharmony_ci T(0, false); 9562306a36Sopenharmony_ci 9662306a36Sopenharmony_ci T_INIT; 9762306a36Sopenharmony_ci for (i = COUNTER_WINDOW_SIZE + 1; i-- > 1;) 9862306a36Sopenharmony_ci T(i, true); 9962306a36Sopenharmony_ci T(0, true); 10062306a36Sopenharmony_ci T(COUNTER_WINDOW_SIZE + 1, true); 10162306a36Sopenharmony_ci 10262306a36Sopenharmony_ci#undef T 10362306a36Sopenharmony_ci#undef T_LIM 10462306a36Sopenharmony_ci#undef T_INIT 10562306a36Sopenharmony_ci 10662306a36Sopenharmony_ci if (success) 10762306a36Sopenharmony_ci pr_info("nonce counter self-tests: pass\n"); 10862306a36Sopenharmony_ci kfree(counter); 10962306a36Sopenharmony_ci return success; 11062306a36Sopenharmony_ci} 11162306a36Sopenharmony_ci#endif 112