Cloud Interface Feature base on CoAP over TCP in CA Layer
[platform/upstream/iotivity.git] / resource / csdk / connectivity / src / caconnectivitymanager.c
1 /******************************************************************
2  *
3  * Copyright 2014 Samsung Electronics All Rights Reserved.
4  *
5  *
6  *
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  *      http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  *
19  ******************************************************************/
20
21 #include <stdio.h>
22 #include <stdlib.h>
23 #include <stdint.h>
24 #include <stdbool.h>
25
26 #include "cainterface.h"
27 #include "caremotehandler.h"
28 #include "camessagehandler.h"
29 #include "caprotocolmessage.h"
30 #include "canetworkconfigurator.h"
31 #include "cainterfacecontroller.h"
32 #include "logger.h"
33 #ifdef __WITH_DTLS__
34 #include "caadapternetdtls.h"
35 #endif
36
37 #ifdef TCP_ADAPTER
38 #include "catcpadapter.h"
39 #endif
40
41 CAGlobals_t caglobals = { 0 };
42
43 #define TAG "CA_CONN_MGR"
44
45 static bool g_isInitialized = false;
46
47 #ifdef __WITH_DTLS__
48 // CAAdapterNetDTLS will register the callback.
49 // Taking callback all the way through adapters not the right approach, hence calling here.
50 extern void CADTLSSetCredentialsCallback(CAGetDTLSCredentialsHandler credCallback);
51 #endif
52
53 CAResult_t CAInitialize()
54 {
55     OIC_LOG(DEBUG, TAG, "CAInitialize");
56
57     if (!g_isInitialized)
58     {
59         CAResult_t res = CAInitializeMessageHandler();
60         if (res != CA_STATUS_OK)
61         {
62             OIC_LOG(ERROR, TAG, "CAInitialize has failed");
63             return res;
64         }
65         g_isInitialized = true;
66     }
67     return CA_STATUS_OK;
68 }
69
70 void CATerminate()
71 {
72     OIC_LOG(DEBUG, TAG, "CATerminate");
73
74     if (g_isInitialized)
75     {
76         CATerminateMessageHandler();
77         CATerminateNetworkType();
78
79         g_isInitialized = false;
80     }
81 }
82
83 CAResult_t CAStartListeningServer()
84 {
85     OIC_LOG(DEBUG, TAG, "CAStartListeningServer");
86
87     if(!g_isInitialized)
88     {
89         return CA_STATUS_NOT_INITIALIZED;
90     }
91
92     return CAStartListeningServerAdapters();
93 }
94
95 CAResult_t CAStartDiscoveryServer()
96 {
97     OIC_LOG(DEBUG, TAG, "CAStartDiscoveryServer");
98
99     if(!g_isInitialized)
100     {
101         return CA_STATUS_NOT_INITIALIZED;
102     }
103
104     return CAStartDiscoveryServerAdapters();
105 }
106
107 void CARegisterHandler(CARequestCallback ReqHandler, CAResponseCallback RespHandler,
108                        CAErrorCallback ErrorHandler)
109 {
110     OIC_LOG(DEBUG, TAG, "CARegisterHandler");
111
112     if(!g_isInitialized)
113     {
114         OIC_LOG(DEBUG, TAG, "CA is not initialized");
115         return;
116     }
117
118     CASetInterfaceCallbacks(ReqHandler, RespHandler, ErrorHandler);
119 }
120
121 #ifdef __WITH_DTLS__
122 CAResult_t CARegisterDTLSCredentialsHandler(CAGetDTLSCredentialsHandler GetDTLSCredentialsHandler)
123 {
124     OIC_LOG(DEBUG, TAG, "CARegisterDTLSCredentialsHandler");
125
126     if(!g_isInitialized)
127     {
128         return CA_STATUS_NOT_INITIALIZED;
129     }
130
131     CADTLSSetCredentialsCallback(GetDTLSCredentialsHandler);
132     return CA_STATUS_OK;
133 }
134 #endif //__WITH_DTLS__
135
136 CAResult_t CACreateEndpoint(CATransportFlags_t flags,
137                             CATransportAdapter_t adapter,
138                             const char *addr,
139                             uint16_t port,
140                             CAEndpoint_t **object)
141 {
142     if (!object)
143     {
144         OIC_LOG(ERROR, TAG, "Invalid Parameter");
145         return CA_STATUS_INVALID_PARAM;
146     }
147
148     CAEndpoint_t *endpoint = CACreateEndpointObject(flags, adapter, addr, port);
149     if (!endpoint)
150     {
151         return CA_STATUS_FAILED;
152     }
153     *object = endpoint;
154     return CA_STATUS_OK;
155 }
156
157 void CADestroyEndpoint(CAEndpoint_t *rep)
158 {
159     OIC_LOG(DEBUG, TAG, "CADestroyEndpoint");
160
161     CAFreeEndpoint(rep);
162 }
163
164 CAResult_t CAGenerateToken(CAToken_t *token, uint8_t tokenLength)
165 {
166     OIC_LOG(DEBUG, TAG, "CAGenerateToken");
167
168     return CAGenerateTokenInternal(token, tokenLength);
169 }
170
171 void CADestroyToken(CAToken_t token)
172 {
173     OIC_LOG(DEBUG, TAG, "CADestroyToken");
174
175     CADestroyTokenInternal(token);
176
177     OIC_LOG(DEBUG, TAG, "OUT");
178 }
179
180 CAResult_t CAGetNetworkInformation(CAEndpoint_t **info, uint32_t *size)
181 {
182     OIC_LOG(DEBUG, TAG, "CAGetNetworkInformation");
183
184     if(!g_isInitialized)
185     {
186         return CA_STATUS_NOT_INITIALIZED;
187     }
188
189     return CAGetNetworkInformationInternal(info, size);
190 }
191
192 CAResult_t CASendRequest(const CAEndpoint_t *object,const CARequestInfo_t *requestInfo)
193 {
194     OIC_LOG(DEBUG, TAG, "CASendGetRequest");
195
196     if(!g_isInitialized)
197     {
198         return CA_STATUS_NOT_INITIALIZED;
199     }
200
201     return CADetachRequestMessage(object, requestInfo);
202 }
203
204 CAResult_t CASendNotification(const CAEndpoint_t *object, const CAResponseInfo_t *responseInfo)
205 {
206     OIC_LOG(DEBUG, TAG, "CASendNotification");
207
208     if(!g_isInitialized)
209     {
210         return CA_STATUS_NOT_INITIALIZED;
211     }
212
213     return CADetachResponseMessage(object, responseInfo);
214 }
215
216 CAResult_t CASendResponse(const CAEndpoint_t *object, const CAResponseInfo_t *responseInfo)
217 {
218     OIC_LOG(DEBUG, TAG, "CASendResponse");
219
220     if(!g_isInitialized)
221     {
222         return CA_STATUS_NOT_INITIALIZED;
223     }
224
225     return CADetachResponseMessage(object, responseInfo);
226 }
227
228 CAResult_t CASelectNetwork(CATransportAdapter_t interestedNetwork)
229 {
230     OIC_LOG_V(DEBUG, TAG, "Selected network : %d", interestedNetwork);
231
232     if(!g_isInitialized)
233     {
234         return CA_STATUS_NOT_INITIALIZED;
235     }
236
237     CAResult_t res = CA_STATUS_OK;
238
239     if (interestedNetwork & CA_ADAPTER_IP)
240     {
241         res = CAAddNetworkType(CA_ADAPTER_IP);
242         OIC_LOG_V(DEBUG, TAG, "CAAddNetworkType(CA_IP_ADAPTER) function returns result: %d", res);
243     }
244     else if (interestedNetwork & CA_ADAPTER_RFCOMM_BTEDR)
245     {
246         res = CAAddNetworkType(CA_ADAPTER_RFCOMM_BTEDR);
247         OIC_LOG_V(DEBUG, TAG, "CAAddNetworkType(CA_RFCOMM_ADAPTER) function returns result : %d", res);
248     }
249     else if (interestedNetwork & CA_ADAPTER_GATT_BTLE)
250     {
251         res = CAAddNetworkType(CA_ADAPTER_GATT_BTLE);
252         OIC_LOG_V(DEBUG, TAG, "CAAddNetworkType(CA_GATT_ADAPTER) function returns result : %d", res);
253     }
254
255 #ifdef RA_ADAPTER
256     else if (interestedNetwork & CA_ADAPTER_REMOTE_ACCESS)
257     {
258         res = CAAddNetworkType(CA_ADAPTER_REMOTE_ACCESS);
259         OIC_LOG_V(DEBUG, TAG,
260                   "CAAddNetworkType(CA_ADAPTER_REMOTE_ACCESS) function returns result : %d", res);
261     }
262 #endif
263
264 #ifdef TCP_ADAPTER
265     else if (interestedNetwork & CA_ADAPTER_TCP)
266     {
267         res = CAAddNetworkType(CA_ADAPTER_TCP);
268         OIC_LOG_V(DEBUG, TAG,
269                   "CAAddNetworkType(CA_ADAPTER_TCP) function returns result : %d", res);
270     }
271 #endif
272
273     else
274     {
275         res = CA_NOT_SUPPORTED;
276     }
277     return res;
278 }
279
280 CAResult_t CAUnSelectNetwork(CATransportAdapter_t nonInterestedNetwork)
281 {
282     OIC_LOG_V(DEBUG, TAG, "unselected network : %d", nonInterestedNetwork);
283
284     if(!g_isInitialized)
285     {
286         return CA_STATUS_NOT_INITIALIZED;
287     }
288
289     CAResult_t res = CA_STATUS_OK;
290
291     if (nonInterestedNetwork & CA_ADAPTER_IP)
292     {
293         res = CARemoveNetworkType(CA_ADAPTER_IP);
294         OIC_LOG_V(DEBUG, TAG, "CARemoveNetworkType(CA_IP_ADAPTER) function returns result : %d", res);
295     }
296     else if (nonInterestedNetwork & CA_ADAPTER_RFCOMM_BTEDR)
297     {
298         res = CARemoveNetworkType(CA_ADAPTER_RFCOMM_BTEDR);
299         OIC_LOG_V(DEBUG, TAG, "CARemoveNetworkType(CA_RFCOMM_ADAPTER) function returns result : %d", res);
300     }
301     else if (nonInterestedNetwork & CA_ADAPTER_GATT_BTLE)
302     {
303         res = CARemoveNetworkType(CA_ADAPTER_GATT_BTLE);
304         OIC_LOG_V(DEBUG, TAG, "CARemoveNetworkType(CA_GATT_ADAPTER) function returns result : %d", res);
305     }
306 #ifdef RA_ADAPTER
307     else if (nonInterestedNetwork & CA_ADAPTER_REMOTE_ACCESS)
308     {
309         res = CARemoveNetworkType(CA_ADAPTER_REMOTE_ACCESS);
310         OIC_LOG_V(DEBUG, TAG, "CARemoveNetworkType(CA_ADAPTER_REMOTE_ACCESS) function returns result : %d",
311                   res);
312     }
313 #endif
314
315
316 #ifdef TCP_ADAPTER
317     else if (nonInterestedNetwork & CA_ADAPTER_TCP)
318     {
319         res = CARemoveNetworkType(CA_ADAPTER_TCP);
320         OIC_LOG_V(DEBUG, TAG, "CARemoveNetworkType(CA_ADAPTER_TCP) function returns result : %d",
321                   res);
322     }
323 #endif
324
325     else
326     {
327         res = CA_STATUS_FAILED;
328     }
329     return res;
330 }
331
332 CAResult_t CAHandleRequestResponse()
333 {
334     if (!g_isInitialized)
335     {
336         OIC_LOG(ERROR, TAG, "not initialized");
337         return CA_STATUS_NOT_INITIALIZED;
338     }
339
340     CAHandleRequestResponseCallbacks();
341
342     return CA_STATUS_OK;
343 }
344
345 #ifdef __WITH_DTLS__
346
347 CAResult_t CASelectCipherSuite(const uint16_t cipher)
348 {
349     OIC_LOG_V(DEBUG, TAG, "CASelectCipherSuite");
350
351     return CADtlsSelectCipherSuite(cipher);
352 }
353
354 CAResult_t CAEnableAnonECDHCipherSuite(const bool enable)
355 {
356     OIC_LOG_V(DEBUG, TAG, "CAEnableAnonECDHCipherSuite");
357
358     return CADtlsEnableAnonECDHCipherSuite(enable);
359 }
360
361 CAResult_t CAGenerateOwnerPSK(const CAEndpoint_t* endpoint,
362                     const uint8_t* label, const size_t labelLen,
363                     const uint8_t* rsrcServerDeviceID, const size_t rsrcServerDeviceIDLen,
364                     const uint8_t* provServerDeviceID, const size_t provServerDeviceIDLen,
365                     uint8_t* ownerPSK, const size_t ownerPSKSize)
366 {
367     OIC_LOG_V(DEBUG, TAG, "IN : CAGenerateOwnerPSK");
368
369     CAResult_t res = CA_STATUS_OK;
370
371     //newOwnerLabel and prevOwnerLabe can be NULL
372     if (!endpoint || !label || 0 == labelLen || !ownerPSK || 0 == ownerPSKSize)
373     {
374         return CA_STATUS_INVALID_PARAM;
375     }
376
377     res = CADtlsGenerateOwnerPSK(endpoint, label, labelLen,
378                                   rsrcServerDeviceID, rsrcServerDeviceIDLen,
379                                   provServerDeviceID, provServerDeviceIDLen,
380                                   ownerPSK, ownerPSKSize);
381     if (CA_STATUS_OK != res)
382     {
383         OIC_LOG_V(ERROR, TAG, "Failed to CAGenerateOwnerPSK : %d", res);
384     }
385
386     OIC_LOG_V(DEBUG, TAG, "OUT : CAGenerateOwnerPSK");
387
388     return res;
389 }
390
391 CAResult_t CAInitiateHandshake(const CAEndpoint_t *endpoint)
392 {
393     OIC_LOG_V(DEBUG, TAG, "IN : CAInitiateHandshake");
394     CAResult_t res = CA_STATUS_OK;
395
396     if (!endpoint)
397     {
398         return CA_STATUS_INVALID_PARAM;
399     }
400
401     res = CADtlsInitiateHandshake(endpoint);
402     if (CA_STATUS_OK != res)
403     {
404         OIC_LOG_V(ERROR, TAG, "Failed to CADtlsInitiateHandshake : %d", res);
405     }
406
407     OIC_LOG_V(DEBUG, TAG, "OUT : CAInitiateHandshake");
408
409     return res;
410 }
411
412 CAResult_t CACloseDtlsSession(const CAEndpoint_t *endpoint)
413 {
414     OIC_LOG_V(DEBUG, TAG, "IN : CACloseDtlsSession");
415     CAResult_t res = CA_STATUS_OK;
416
417     if (!endpoint)
418     {
419         return CA_STATUS_INVALID_PARAM;
420     }
421
422     res = CADtlsClose(endpoint);
423     if (CA_STATUS_OK != res)
424     {
425         OIC_LOG_V(ERROR, TAG, "Failed to CADtlsClose : %d", res);
426     }
427
428     OIC_LOG_V(DEBUG, TAG, "OUT : CACloseDtlsSession");
429
430     return res;
431 }
432
433 #endif /* __WITH_DTLS__ */