]>
Commit | Line | Data |
---|---|---|
7ba3f707 JH |
1 | /** |
2 | * @file configuration_attribute.c | |
3 | * | |
4 | * @brief Implementation of configuration_attribute_t. | |
5 | * | |
6 | */ | |
7 | ||
8 | /* | |
9 | * Copyright (C) 2005 Jan Hutter, Martin Willi | |
10 | * Hochschule fuer Technik Rapperswil | |
11 | * | |
12 | * This program is free software; you can redistribute it and/or modify it | |
13 | * under the terms of the GNU General Public License as published by the | |
14 | * Free Software Foundation; either version 2 of the License, or (at your | |
15 | * option) any later version. See <http://www.fsf.org/copyleft/gpl.txt>. | |
16 | * | |
17 | * This program is distributed in the hope that it will be useful, but | |
18 | * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY | |
19 | * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | |
20 | * for more details. | |
21 | */ | |
5113680f | 22 | |
7ba3f707 JH |
23 | #include <stddef.h> |
24 | ||
25 | #include "configuration_attribute.h" | |
26 | ||
27 | #include <encoding/payloads/encodings.h> | |
28 | #include <types.h> | |
7ba3f707 JH |
29 | |
30 | ||
31 | typedef struct private_configuration_attribute_t private_configuration_attribute_t; | |
32 | ||
33 | /** | |
34 | * Private data of an configuration_attribute_t object. | |
35 | * | |
36 | */ | |
37 | struct private_configuration_attribute_t { | |
38 | /** | |
39 | * Public configuration_attribute_t interface. | |
40 | */ | |
41 | configuration_attribute_t public; | |
42 | ||
43 | /** | |
44 | * Type of the attribute. | |
45 | */ | |
46 | u_int16_t attribute_type; | |
47 | ||
48 | /** | |
49 | * Length of the attribute. | |
50 | */ | |
51 | u_int16_t attribute_length; | |
52 | ||
53 | ||
54 | /** | |
55 | * Attribute value as chunk. | |
56 | */ | |
57 | chunk_t attribute_value; | |
58 | }; | |
59 | ||
60 | /** | |
61 | * String mappings for configuration_attribute_type_t. | |
62 | */ | |
63 | mapping_t configuration_attribute_type_m[] = { | |
64 | {INTERNAL_IP4_ADDRESS, "INTERNAL_IP4_ADDRESS"}, | |
65 | {INTERNAL_IP4_NETMASK, "INTERNAL_IP4_NETMASK"}, | |
66 | {INTERNAL_IP4_DNS, "INTERNAL_IP4_DNS"}, | |
67 | {INTERNAL_IP4_NBNS, "INTERNAL_IP4_NBNS"}, | |
68 | {INTERNAL_ADDRESS_EXPIRY, "INTERNAL_ADDRESS_EXPIRY"}, | |
69 | {INTERNAL_IP4_DHCP, "INTERNAL_IP4_DHCP"}, | |
70 | {APPLICATION_VERSION, "APPLICATION_VERSION"}, | |
71 | {INTERNAL_IP6_ADDRESS, "INTERNAL_IP6_ADDRESS"}, | |
72 | {INTERNAL_IP6_DNS, "INTERNAL_IP6_DNS"}, | |
73 | {INTERNAL_IP6_NBNS, "INTERNAL_IP6_NBNS"}, | |
74 | {INTERNAL_IP6_DHCP, "INTERNAL_IP6_DHCP"}, | |
75 | {INTERNAL_IP4_SUBNET, "INTERNAL_IP4_SUBNET"}, | |
76 | {SUPPORTED_ATTRIBUTES, "SUPPORTED_ATTRIBUTES"}, | |
77 | {INTERNAL_IP6_SUBNET, "INTERNAL_IP6_SUBNET"}, | |
78 | {MAPPING_END, NULL} | |
79 | }; | |
80 | ||
81 | ||
82 | /** | |
83 | * Encoding rules to parse or generate a configuration attribute. | |
84 | * | |
85 | * The defined offsets are the positions in a object of type | |
86 | * private_configuration_attribute_t. | |
87 | * | |
88 | */ | |
89 | encoding_rule_t configuration_attribute_encodings[] = { | |
90 | ||
91 | { RESERVED_BIT, 0 }, | |
92 | /* type of the attribute as 15 bit unsigned integer */ | |
93 | { ATTRIBUTE_TYPE, offsetof(private_configuration_attribute_t, attribute_type) }, | |
94 | /* Length of attribute value */ | |
95 | { CONFIGURATION_ATTRIBUTE_LENGTH, offsetof(private_configuration_attribute_t, attribute_length)}, | |
96 | /* Value of attribute if attribute format flag is zero */ | |
97 | { CONFIGURATION_ATTRIBUTE_VALUE, offsetof(private_configuration_attribute_t, attribute_value)} | |
98 | }; | |
99 | ||
100 | /* | |
101 | 1 2 3 | |
102 | 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 | |
103 | +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | |
104 | !R| Attribute Type ! Length | | |
105 | +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | |
106 | | | | |
107 | ~ Value ~ | |
108 | | | | |
109 | +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | |
110 | */ | |
111 | ||
112 | /** | |
113 | * Implementation of payload_t.verify. | |
114 | */ | |
115 | static status_t verify(private_configuration_attribute_t *this) | |
116 | { | |
117 | switch (this->attribute_type) | |
118 | { | |
119 | case INTERNAL_IP4_ADDRESS: | |
120 | case INTERNAL_IP4_NETMASK: | |
121 | case INTERNAL_IP4_DNS: | |
122 | case INTERNAL_IP4_NBNS: | |
123 | case INTERNAL_ADDRESS_EXPIRY: | |
124 | case INTERNAL_IP4_DHCP: | |
125 | case APPLICATION_VERSION: | |
126 | case INTERNAL_IP6_ADDRESS: | |
127 | case INTERNAL_IP6_DNS: | |
128 | case INTERNAL_IP6_NBNS: | |
129 | case INTERNAL_IP6_DHCP: | |
130 | case INTERNAL_IP4_SUBNET: | |
131 | case SUPPORTED_ATTRIBUTES: | |
132 | case INTERNAL_IP6_SUBNET: | |
133 | { | |
134 | /* Attribute types are not checked in here */ | |
135 | break; | |
136 | } | |
137 | default: | |
138 | return FAILED; | |
139 | } | |
140 | ||
141 | if (this->attribute_length != this->attribute_value.len) | |
142 | { | |
143 | return FAILED; | |
144 | } | |
145 | ||
146 | return SUCCESS; | |
147 | } | |
148 | ||
149 | /** | |
150 | * Implementation of payload_t.get_encoding_rules. | |
151 | */ | |
152 | static void get_encoding_rules(private_configuration_attribute_t *this, encoding_rule_t **rules, size_t *rule_count) | |
153 | { | |
154 | *rules = configuration_attribute_encodings; | |
155 | *rule_count = sizeof(configuration_attribute_encodings) / sizeof(encoding_rule_t); | |
156 | } | |
157 | ||
158 | /** | |
159 | * Implementation of payload_t.get_type. | |
160 | */ | |
161 | static payload_type_t get_type(private_configuration_attribute_t *this) | |
162 | { | |
163 | return CONFIGURATION_ATTRIBUTE; | |
164 | } | |
165 | ||
166 | /** | |
167 | * Implementation of payload_t.get_next_type. | |
168 | */ | |
169 | static payload_type_t get_next_type(private_configuration_attribute_t *this) | |
170 | { | |
171 | return (NO_PAYLOAD); | |
172 | } | |
173 | ||
174 | /** | |
175 | * Implementation of payload_t.set_next_type. | |
176 | */ | |
177 | static void set_next_type(private_configuration_attribute_t *this,payload_type_t type) | |
178 | { | |
179 | } | |
180 | ||
181 | /** | |
182 | * Implementation of configuration_attribute_t.get_length. | |
183 | */ | |
184 | static size_t get_length(private_configuration_attribute_t *this) | |
185 | { | |
186 | return (this->attribute_value.len + CONFIGURATION_ATTRIBUTE_HEADER_LENGTH); | |
187 | } | |
188 | ||
189 | /** | |
190 | * Implementation of configuration_attribute_t.set_value. | |
191 | */ | |
192 | static void set_value(private_configuration_attribute_t *this, chunk_t value) | |
193 | { | |
194 | if (this->attribute_value.ptr != NULL) | |
195 | { | |
196 | /* free existing value */ | |
5113680f | 197 | chunk_free(&(this->attribute_value)); |
7ba3f707 JH |
198 | } |
199 | ||
5113680f | 200 | this->attribute_value.ptr = clalloc(value.ptr,value.len); |
7ba3f707 JH |
201 | this->attribute_value.len = value.len; |
202 | ||
203 | this->attribute_length = this->attribute_value.len; | |
204 | } | |
205 | ||
206 | /** | |
207 | * Implementation of configuration_attribute_t.get_value. | |
208 | */ | |
209 | static chunk_t get_value (private_configuration_attribute_t *this) | |
210 | { | |
211 | return this->attribute_value; | |
212 | } | |
213 | ||
214 | ||
215 | /** | |
216 | * Implementation of configuration_attribute_t.set_attribute_type. | |
217 | */ | |
218 | static void set_attribute_type (private_configuration_attribute_t *this, u_int16_t type) | |
219 | { | |
220 | this->attribute_type = type & 0x7FFF; | |
221 | } | |
222 | ||
223 | /** | |
224 | * Implementation of configuration_attribute_t.get_attribute_type. | |
225 | */ | |
226 | static u_int16_t get_attribute_type (private_configuration_attribute_t *this) | |
227 | { | |
228 | return this->attribute_type; | |
229 | } | |
230 | ||
231 | /** | |
232 | * Implementation of configuration_attribute_t.get_attribute_length. | |
233 | */ | |
234 | static u_int16_t get_attribute_length (private_configuration_attribute_t *this) | |
235 | { | |
236 | return this->attribute_length; | |
237 | } | |
238 | ||
239 | ||
240 | /** | |
241 | * Implementation of configuration_attribute_t.destroy and payload_t.destroy. | |
242 | */ | |
243 | static void destroy(private_configuration_attribute_t *this) | |
244 | { | |
245 | if (this->attribute_value.ptr != NULL) | |
246 | { | |
5113680f | 247 | free(this->attribute_value.ptr); |
7ba3f707 | 248 | } |
5113680f | 249 | free(this); |
7ba3f707 JH |
250 | } |
251 | ||
252 | /* | |
253 | * Described in header. | |
254 | */ | |
255 | configuration_attribute_t *configuration_attribute_create() | |
256 | { | |
5113680f | 257 | private_configuration_attribute_t *this = malloc_thing(private_configuration_attribute_t); |
7ba3f707 JH |
258 | |
259 | /* payload interface */ | |
260 | this->public.payload_interface.verify = (status_t (*) (payload_t *))verify; | |
261 | this->public.payload_interface.get_encoding_rules = (void (*) (payload_t *, encoding_rule_t **, size_t *) ) get_encoding_rules; | |
262 | this->public.payload_interface.get_length = (size_t (*) (payload_t *)) get_length; | |
263 | this->public.payload_interface.get_next_type = (payload_type_t (*) (payload_t *)) get_next_type; | |
264 | this->public.payload_interface.set_next_type = (void (*) (payload_t *,payload_type_t)) set_next_type; | |
265 | this->public.payload_interface.get_type = (payload_type_t (*) (payload_t *)) get_type; | |
266 | this->public.payload_interface.destroy = (void (*) (payload_t *))destroy; | |
267 | ||
268 | /* public functions */ | |
269 | this->public.set_value = (void (*) (configuration_attribute_t *,chunk_t)) set_value; | |
270 | this->public.get_value = (chunk_t (*) (configuration_attribute_t *)) get_value; | |
271 | this->public.set_attribute_type = (void (*) (configuration_attribute_t *,u_int16_t type)) set_attribute_type; | |
272 | this->public.get_attribute_type = (u_int16_t (*) (configuration_attribute_t *)) get_attribute_type; | |
273 | this->public.get_attribute_length = (u_int16_t (*) (configuration_attribute_t *)) get_attribute_length; | |
274 | this->public.destroy = (void (*) (configuration_attribute_t *)) destroy; | |
275 | ||
276 | /* set default values of the fields */ | |
277 | this->attribute_type = 0; | |
278 | this->attribute_value = CHUNK_INITIALIZER; | |
279 | this->attribute_length = 0; | |
280 | ||
281 | return (&(this->public)); | |
282 | } |