Coverage Report

Created: 2026-08-15 06:21

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/wolfssl-sp-math-all-8bit/wolfcrypt/src/arc4.c
Line
Count
Source
1
/* arc4.c
2
 *
3
 * Copyright (C) 2006-2026 wolfSSL Inc.
4
 *
5
 * This file is part of wolfSSL.
6
 *
7
 * wolfSSL is free software; you can redistribute it and/or modify
8
 * it under the terms of the GNU General Public License as published by
9
 * the Free Software Foundation; either version 3 of the License, or
10
 * (at your option) any later version.
11
 *
12
 * wolfSSL is distributed in the hope that it will be useful,
13
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15
 * GNU General Public License for more details.
16
 *
17
 * You should have received a copy of the GNU General Public License
18
 * along with this program; if not, write to the Free Software
19
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA
20
 */
21
22
#include <wolfssl/wolfcrypt/libwolfssl_sources.h>
23
24
#ifndef NO_RC4
25
26
#include <wolfssl/wolfcrypt/arc4.h>
27
28
#ifdef NO_INLINE
29
    #include <wolfssl/wolfcrypt/misc.h>
30
#else
31
    #define WOLFSSL_MISC_INCLUDED
32
    #include <wolfcrypt/src/misc.c>
33
#endif
34
35
36
int wc_Arc4SetKey(Arc4* arc4, const byte* key, word32 length)
37
11
{
38
11
    int ret = 0;
39
11
    word32 i;
40
11
    word32 keyIndex = 0, stateIndex = 0;
41
42
11
    if (arc4 == NULL || key == NULL || length == 0) {
43
0
        return BAD_FUNC_ARG;
44
0
    }
45
46
#if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_ARC4) && \
47
        defined(HAVE_CAVIUM) && !defined(HAVE_CAVIUM_V)
48
    if (arc4->asyncDev.marker == WOLFSSL_ASYNC_MARKER_ARC4) {
49
        return NitroxArc4SetKey(arc4, key, length);
50
    }
51
#endif
52
53
11
    arc4->x = 1;
54
11
    arc4->y = 0;
55
56
2.82k
    for (i = 0; i < ARC4_STATE_SIZE; i++)
57
2.81k
        arc4->state[i] = (byte)i;
58
59
2.82k
    for (i = 0; i < ARC4_STATE_SIZE; i++) {
60
2.81k
        word32 a = arc4->state[i];
61
2.81k
        stateIndex += key[keyIndex] + a;
62
2.81k
        stateIndex &= 0xFF;
63
2.81k
        arc4->state[i] = arc4->state[stateIndex];
64
2.81k
        arc4->state[stateIndex] = (byte)a;
65
66
2.81k
        if (++keyIndex >= length)
67
176
            keyIndex = 0;
68
2.81k
    }
69
70
11
    arc4->keySet = 1;
71
72
11
    return ret;
73
11
}
74
75
76
static WC_INLINE byte MakeByte(word32* x, word32* y, byte* s)
77
6.81k
{
78
6.81k
    word32 a = s[*x], b;
79
6.81k
    *y = (*y+a) & 0xff;
80
81
6.81k
    b = s[*y];
82
6.81k
    s[*x] = (byte)b;
83
6.81k
    s[*y] = (byte)a;
84
6.81k
    *x = (*x+1) & 0xff;
85
86
6.81k
    return s[(a+b) & 0xff];
87
6.81k
}
88
89
90
int wc_Arc4Process(Arc4* arc4, byte* out, const byte* in, word32 length)
91
14
{
92
14
    int ret = 0;
93
14
    word32 x;
94
14
    word32 y;
95
96
14
    if (arc4 == NULL || out == NULL || in == NULL) {
97
0
        return BAD_FUNC_ARG;
98
0
    }
99
100
#if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_ARC4) && \
101
        defined(HAVE_CAVIUM) && !defined(HAVE_CAVIUM_V)
102
    if (arc4->asyncDev.marker == WOLFSSL_ASYNC_MARKER_ARC4) {
103
        return NitroxArc4Process(arc4, out, in, length);
104
    }
105
#endif
106
107
14
    if (!arc4->keySet) {
108
0
        return MISSING_KEY;
109
0
    }
110
111
14
    x = arc4->x;
112
14
    y = arc4->y;
113
114
6.83k
    while(length--)
115
6.81k
        *out++ = *in++ ^ MakeByte(&x, &y, arc4->state);
116
117
14
    arc4->x = (byte)x;
118
14
    arc4->y = (byte)y;
119
120
14
    return ret;
121
14
}
122
123
/* Initialize Arc4 for use with async device */
124
int wc_Arc4Init(Arc4* arc4, void* heap, int devId)
125
6
{
126
6
    int ret = 0;
127
128
6
    if (arc4 == NULL)
129
0
        return BAD_FUNC_ARG;
130
131
6
    arc4->heap = heap;
132
6
    arc4->keySet = 0;
133
134
#if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_ARC4)
135
    ret = wolfAsync_DevCtxInit(&arc4->asyncDev, WOLFSSL_ASYNC_MARKER_ARC4,
136
        arc4->heap, devId);
137
#else
138
6
    (void)devId;
139
6
#endif /* WOLFSSL_ASYNC_CRYPT */
140
141
6
    return ret;
142
6
}
143
144
145
/* Free Arc4 from use with async device */
146
void wc_Arc4Free(Arc4* arc4)
147
171k
{
148
171k
    if (arc4 == NULL)
149
171k
        return;
150
151
#if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_ARC4)
152
    wolfAsync_DevCtxFree(&arc4->asyncDev, WOLFSSL_ASYNC_MARKER_ARC4);
153
#endif /* WOLFSSL_ASYNC_CRYPT */
154
155
6
    ForceZero(arc4->state, sizeof(arc4->state));
156
6
    arc4->x = 0;
157
6
    arc4->y = 0;
158
6
    arc4->keySet = 0;
159
6
}
160
161
#endif /* NO_RC4 */
162