Fix up path generation to use OPENSSL_MODULES
[openssl.git] / ssl / d1_srtp.c
1 /*
2  * Copyright 2011-2024 The OpenSSL Project Authors. All Rights Reserved.
3  *
4  * Licensed under the Apache License 2.0 (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 /*
11  * DTLS code by Eric Rescorla <ekr@rtfm.com>
12  *
13  * Copyright (C) 2006, Network Resonance, Inc. Copyright (C) 2011, RTFM, Inc.
14  */
15
16 #include <stdio.h>
17 #include <openssl/objects.h>
18 #include "ssl_local.h"
19 #include "quic/quic_local.h"
20
21 #ifndef OPENSSL_NO_SRTP
22
23 static const SRTP_PROTECTION_PROFILE srtp_known_profiles[] = {
24     {
25      "SRTP_AES128_CM_SHA1_80",
26      SRTP_AES128_CM_SHA1_80,
27      },
28     {
29      "SRTP_AES128_CM_SHA1_32",
30      SRTP_AES128_CM_SHA1_32,
31      },
32     {
33      "SRTP_AEAD_AES_128_GCM",
34      SRTP_AEAD_AES_128_GCM,
35      },
36     {
37      "SRTP_AEAD_AES_256_GCM",
38      SRTP_AEAD_AES_256_GCM,
39      },
40     {
41      "SRTP_DOUBLE_AEAD_AES_128_GCM_AEAD_AES_128_GCM",
42      SRTP_DOUBLE_AEAD_AES_128_GCM_AEAD_AES_128_GCM,
43      },
44     {
45      "SRTP_DOUBLE_AEAD_AES_256_GCM_AEAD_AES_256_GCM",
46      SRTP_DOUBLE_AEAD_AES_256_GCM_AEAD_AES_256_GCM,
47      },
48     {
49      "SRTP_ARIA_128_CTR_HMAC_SHA1_80",
50      SRTP_ARIA_128_CTR_HMAC_SHA1_80,
51      },
52     {
53      "SRTP_ARIA_128_CTR_HMAC_SHA1_32",
54      SRTP_ARIA_128_CTR_HMAC_SHA1_32,
55      },
56     {
57      "SRTP_ARIA_256_CTR_HMAC_SHA1_80",
58      SRTP_ARIA_256_CTR_HMAC_SHA1_80,
59      },
60     {
61      "SRTP_ARIA_256_CTR_HMAC_SHA1_32",
62      SRTP_ARIA_256_CTR_HMAC_SHA1_32,
63      },
64     {
65      "SRTP_AEAD_ARIA_128_GCM",
66      SRTP_AEAD_ARIA_128_GCM,
67      },
68     {
69      "SRTP_AEAD_ARIA_256_GCM",
70      SRTP_AEAD_ARIA_256_GCM,
71      },
72     {0}
73 };
74
75 static int find_profile_by_name(char *profile_name,
76                                 const SRTP_PROTECTION_PROFILE **pptr, size_t len)
77 {
78     const SRTP_PROTECTION_PROFILE *p;
79
80     p = srtp_known_profiles;
81     while (p->name) {
82         if ((len == strlen(p->name))
83             && strncmp(p->name, profile_name, len) == 0) {
84             *pptr = p;
85             return 0;
86         }
87
88         p++;
89     }
90
91     return 1;
92 }
93
94 static int ssl_ctx_make_profiles(const char *profiles_string,
95                                  STACK_OF(SRTP_PROTECTION_PROFILE) **out)
96 {
97     STACK_OF(SRTP_PROTECTION_PROFILE) *profiles;
98
99     char *col;
100     char *ptr = (char *)profiles_string;
101     const SRTP_PROTECTION_PROFILE *p;
102
103     if ((profiles = sk_SRTP_PROTECTION_PROFILE_new_null()) == NULL) {
104         ERR_raise(ERR_LIB_SSL, SSL_R_SRTP_COULD_NOT_ALLOCATE_PROFILES);
105         return 1;
106     }
107
108     do {
109         col = strchr(ptr, ':');
110
111         if (!find_profile_by_name(ptr, &p, col ? (size_t)(col - ptr)
112                                                : strlen(ptr))) {
113             if (sk_SRTP_PROTECTION_PROFILE_find(profiles,
114                                                 (SRTP_PROTECTION_PROFILE *)p) >= 0) {
115                 ERR_raise(ERR_LIB_SSL, SSL_R_BAD_SRTP_PROTECTION_PROFILE_LIST);
116                 goto err;
117             }
118
119             if (!sk_SRTP_PROTECTION_PROFILE_push(profiles,
120                                                  (SRTP_PROTECTION_PROFILE *)p)) {
121                 ERR_raise(ERR_LIB_SSL, SSL_R_SRTP_COULD_NOT_ALLOCATE_PROFILES);
122                 goto err;
123             }
124         } else {
125             ERR_raise(ERR_LIB_SSL, SSL_R_SRTP_UNKNOWN_PROTECTION_PROFILE);
126             goto err;
127         }
128
129         if (col)
130             ptr = col + 1;
131     } while (col);
132
133     sk_SRTP_PROTECTION_PROFILE_free(*out);
134
135     *out = profiles;
136
137     return 0;
138  err:
139     sk_SRTP_PROTECTION_PROFILE_free(profiles);
140     return 1;
141 }
142
143 int SSL_CTX_set_tlsext_use_srtp(SSL_CTX *ctx, const char *profiles)
144 {
145     if (IS_QUIC_METHOD(ctx->method))
146         return 1;
147
148     return ssl_ctx_make_profiles(profiles, &ctx->srtp_profiles);
149 }
150
151 int SSL_set_tlsext_use_srtp(SSL *s, const char *profiles)
152 {
153     SSL_CONNECTION *sc = SSL_CONNECTION_FROM_SSL_ONLY(s);
154
155     if (sc == NULL)
156         return 1;
157
158     return ssl_ctx_make_profiles(profiles, &sc->srtp_profiles);
159 }
160
161 STACK_OF(SRTP_PROTECTION_PROFILE) *SSL_get_srtp_profiles(SSL *s)
162 {
163     SSL_CONNECTION *sc = SSL_CONNECTION_FROM_SSL_ONLY(s);
164
165     if (sc != NULL) {
166         if (sc->srtp_profiles != NULL) {
167             return sc->srtp_profiles;
168         } else if ((s->ctx != NULL) && (s->ctx->srtp_profiles != NULL)) {
169             return s->ctx->srtp_profiles;
170         }
171     }
172
173     return NULL;
174 }
175
176 SRTP_PROTECTION_PROFILE *SSL_get_selected_srtp_profile(SSL *s)
177 {
178     SSL_CONNECTION *sc = SSL_CONNECTION_FROM_SSL_ONLY(s);
179
180     if (sc == NULL)
181         return 0;
182
183     return sc->srtp_profile;
184 }
185 #endif