/src/mosquitto/lib/alias_mosq.c
Line | Count | Source |
1 | | /* |
2 | | Copyright (c) 2019-2021 Roger Light <roger@atchoo.org> |
3 | | |
4 | | All rights reserved. This program and the accompanying materials |
5 | | are made available under the terms of the Eclipse Public License 2.0 |
6 | | and Eclipse Distribution License v1.0 which accompany this distribution. |
7 | | |
8 | | The Eclipse Public License is available at |
9 | | https://www.eclipse.org/legal/epl-2.0/ |
10 | | and the Eclipse Distribution License is available at |
11 | | http://www.eclipse.org/org/documents/edl-v10.php. |
12 | | |
13 | | SPDX-License-Identifier: EPL-2.0 OR BSD-3-Clause |
14 | | |
15 | | Contributors: |
16 | | Roger Light - initial implementation and documentation. |
17 | | */ |
18 | | |
19 | | #include "config.h" |
20 | | |
21 | | #include <string.h> |
22 | | |
23 | | #include "mosquitto.h" |
24 | | #include "alias_mosq.h" |
25 | | |
26 | | static void alias__free_r2l(struct mosquitto *mosq); |
27 | | static void alias__free_l2r(struct mosquitto *mosq); |
28 | | |
29 | | |
30 | | int alias__add_l2r(struct mosquitto *mosq, const char *topic, uint16_t *alias) |
31 | 0 | { |
32 | 0 | struct mosquitto__alias *aliases_new; |
33 | |
|
34 | 0 | if(mosq->alias_count_l2r < mosq->alias_max_l2r){ |
35 | 0 | aliases_new = mosquitto_realloc(mosq->aliases_l2r, sizeof(struct mosquitto__alias)*(size_t)(mosq->alias_count_l2r+1)); |
36 | 0 | if(!aliases_new){ |
37 | 0 | return MOSQ_ERR_NOMEM; |
38 | 0 | } |
39 | | |
40 | 0 | mosq->aliases_l2r = aliases_new; |
41 | 0 | mosq->alias_count_l2r++; |
42 | 0 | *alias = mosq->alias_count_l2r; |
43 | |
|
44 | 0 | mosq->aliases_l2r[mosq->alias_count_l2r-1].alias = *alias; |
45 | 0 | mosq->aliases_l2r[mosq->alias_count_l2r-1].topic = mosquitto_strdup(topic); |
46 | 0 | if(!mosq->aliases_l2r[mosq->alias_count_l2r-1].topic){ |
47 | 0 | *alias = 0; |
48 | 0 | return MOSQ_ERR_NOMEM; |
49 | 0 | } |
50 | 0 | return MOSQ_ERR_SUCCESS; |
51 | 0 | } |
52 | | |
53 | 0 | *alias = 0; |
54 | 0 | return MOSQ_ERR_INVAL; |
55 | 0 | } |
56 | | |
57 | | |
58 | | int alias__add_r2l(struct mosquitto *mosq, const char *topic, uint16_t alias) |
59 | 0 | { |
60 | 0 | int i; |
61 | 0 | struct mosquitto__alias *aliases_new; |
62 | |
|
63 | 0 | for(i=0; i<mosq->alias_count_r2l; i++){ |
64 | 0 | if(mosq->aliases_r2l[i].alias == alias){ |
65 | 0 | mosquitto_FREE(mosq->aliases_r2l[i].topic); |
66 | 0 | mosq->aliases_r2l[i].topic = mosquitto_strdup(topic); |
67 | 0 | if(mosq->aliases_r2l[i].topic){ |
68 | 0 | return MOSQ_ERR_SUCCESS; |
69 | 0 | }else{ |
70 | 0 | return MOSQ_ERR_NOMEM; |
71 | 0 | } |
72 | 0 | } |
73 | 0 | } |
74 | | |
75 | | /* New alias */ |
76 | 0 | aliases_new = mosquitto_realloc(mosq->aliases_r2l, sizeof(struct mosquitto__alias)*(size_t)(mosq->alias_count_r2l+1)); |
77 | 0 | if(!aliases_new){ |
78 | 0 | return MOSQ_ERR_NOMEM; |
79 | 0 | } |
80 | | |
81 | 0 | mosq->aliases_r2l = aliases_new; |
82 | 0 | mosq->alias_count_r2l++; |
83 | |
|
84 | 0 | mosq->aliases_r2l[mosq->alias_count_r2l-1].alias = alias; |
85 | 0 | mosq->aliases_r2l[mosq->alias_count_r2l-1].topic = mosquitto_strdup(topic); |
86 | 0 | if(!mosq->aliases_r2l[mosq->alias_count_r2l-1].topic){ |
87 | 0 | return MOSQ_ERR_NOMEM; |
88 | 0 | } |
89 | | |
90 | 0 | return MOSQ_ERR_SUCCESS; |
91 | 0 | } |
92 | | |
93 | | |
94 | | int alias__find_by_alias(struct mosquitto *mosq, int direction, uint16_t alias, char **topic) |
95 | 0 | { |
96 | 0 | int i; |
97 | 0 | struct mosquitto__alias *aliases; |
98 | 0 | int alias_count; |
99 | |
|
100 | 0 | if(direction == ALIAS_DIR_R2L){ |
101 | 0 | aliases = mosq->aliases_r2l; |
102 | 0 | alias_count = mosq->alias_count_r2l; |
103 | 0 | }else{ |
104 | 0 | aliases = mosq->aliases_l2r; |
105 | 0 | alias_count = mosq->alias_count_l2r; |
106 | 0 | } |
107 | |
|
108 | 0 | for(i=0; i<alias_count; i++){ |
109 | 0 | if(aliases[i].alias == alias){ |
110 | 0 | *topic = mosquitto_strdup(aliases[i].topic); |
111 | 0 | if(*topic){ |
112 | 0 | return MOSQ_ERR_SUCCESS; |
113 | 0 | }else{ |
114 | 0 | return MOSQ_ERR_NOMEM; |
115 | 0 | } |
116 | 0 | } |
117 | 0 | } |
118 | 0 | return MOSQ_ERR_INVAL; |
119 | 0 | } |
120 | | |
121 | | |
122 | | int alias__find_by_topic(struct mosquitto *mosq, int direction, const char *topic, uint16_t *alias) |
123 | 0 | { |
124 | 0 | int i; |
125 | 0 | struct mosquitto__alias *aliases; |
126 | 0 | int alias_count; |
127 | |
|
128 | 0 | if(direction == ALIAS_DIR_R2L){ |
129 | 0 | aliases = mosq->aliases_r2l; |
130 | 0 | alias_count = mosq->alias_count_r2l; |
131 | 0 | }else{ |
132 | 0 | aliases = mosq->aliases_l2r; |
133 | 0 | alias_count = mosq->alias_count_l2r; |
134 | 0 | } |
135 | |
|
136 | 0 | for(i=0; i<alias_count; i++){ |
137 | 0 | if(aliases[i].topic && !strcmp(aliases[i].topic, topic)){ |
138 | 0 | *alias = aliases[i].alias; |
139 | 0 | return MOSQ_ERR_SUCCESS; |
140 | 0 | } |
141 | 0 | } |
142 | 0 | return MOSQ_ERR_INVAL; |
143 | 0 | } |
144 | | |
145 | | |
146 | | static void alias__free_r2l(struct mosquitto *mosq) |
147 | 0 | { |
148 | 0 | int i; |
149 | |
|
150 | 0 | for(i=0; i<mosq->alias_count_r2l; i++){ |
151 | 0 | mosquitto_FREE(mosq->aliases_r2l[i].topic); |
152 | 0 | } |
153 | 0 | mosquitto_FREE(mosq->aliases_r2l); |
154 | 0 | mosq->alias_count_r2l = 0; |
155 | 0 | } |
156 | | |
157 | | |
158 | | static void alias__free_l2r(struct mosquitto *mosq) |
159 | 0 | { |
160 | 0 | int i; |
161 | |
|
162 | 0 | for(i=0; i<mosq->alias_count_l2r; i++){ |
163 | 0 | mosquitto_FREE(mosq->aliases_l2r[i].topic); |
164 | 0 | } |
165 | 0 | mosquitto_FREE(mosq->aliases_l2r); |
166 | 0 | mosq->alias_count_l2r = 0; |
167 | 0 | } |
168 | | |
169 | | |
170 | | void alias__free_all(struct mosquitto *mosq) |
171 | 0 | { |
172 | 0 | alias__free_r2l(mosq); |
173 | 0 | alias__free_l2r(mosq); |
174 | 0 | } |