Merge branch 'master' into notification-service
[platform/upstream/iotivity.git] / resource / csdk / connectivity / src / cainterfacecontroller.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 <string.h>
24 #include <inttypes.h>
25
26 #include "logger.h"
27 #include "oic_malloc.h"
28 #include "caadapterutils.h"
29 #include "canetworkconfigurator.h"
30 #include "cainterfacecontroller.h"
31 #include "caedradapter.h"
32 #include "caleadapter.h"
33 #include "canfcadapter.h"
34 #include "caremotehandler.h"
35 #include "cathreadpool.h"
36 #include "caipadapter.h"
37 #include "cainterface.h"
38
39 #ifdef RA_ADAPTER
40 #include "caraadapter.h"
41 #endif
42
43 #ifdef TCP_ADAPTER
44 #include "catcpadapter.h"
45 #endif
46
47 #define TAG "OIC_CA_INF_CTR"
48
49 #define CA_MEMORY_ALLOC_CHECK(arg) {if (arg == NULL) \
50     {OIC_LOG(ERROR, TAG, "memory error");goto memory_error_exit;} }
51
52 static CAConnectivityHandler_t *g_adapterHandler = NULL;
53
54 static uint32_t g_numberOfAdapters = 0;
55
56 static CANetworkPacketReceivedCallback g_networkPacketReceivedCallback = NULL;
57
58 static CAAdapterStateChangedCB g_adapterChangeCallback = NULL;
59
60 static CAConnectionStateChangedCB g_connChangeCallback = NULL;
61
62 static CAErrorHandleCallback g_errorHandleCallback = NULL;
63
64 static int CAGetAdapterIndex(CATransportAdapter_t cType)
65 {
66     for (uint32_t index=0 ; index < g_numberOfAdapters ; index++)
67     {
68         if (cType == g_adapterHandler[index].cType )
69          {
70              return index;
71          }
72     }
73     return -1;
74 }
75
76 static void CARegisterCallback(CAConnectivityHandler_t handler)
77 {
78     if (handler.startAdapter == NULL ||
79         handler.startListenServer == NULL ||
80         handler.stopListenServer == NULL ||
81         handler.startDiscoveryServer == NULL ||
82         handler.sendData == NULL ||
83         handler.sendDataToAll == NULL ||
84         handler.GetnetInfo == NULL ||
85         handler.readData == NULL ||
86         handler.stopAdapter == NULL ||
87         handler.terminate == NULL)
88     {
89         OIC_LOG(ERROR, TAG, "connectivity handler is not enough to be used!");
90         return;
91     }
92     uint32_t numberofAdapters = g_numberOfAdapters + 1;
93     CAConnectivityHandler_t *adapterHandler = OICRealloc(g_adapterHandler,
94                                    (numberofAdapters) * sizeof(*adapterHandler));
95     if (NULL == adapterHandler)
96     {
97         OIC_LOG(ERROR, TAG, "Memory allocation failed during registration");
98         return;
99     }
100     g_adapterHandler = adapterHandler;
101     g_numberOfAdapters = numberofAdapters;
102     g_adapterHandler[g_numberOfAdapters-1] = handler;
103
104     OIC_LOG_V(DEBUG, TAG, "%d type adapter, register complete!", handler.cType);
105 }
106
107 #ifdef RA_ADAPTER
108 CAResult_t CASetAdapterRAInfo(const CARAInfo_t *caraInfo)
109 {
110     return CASetRAInfo(caraInfo);
111 }
112 #endif
113
114 static void CAReceivedPacketCallback(const CASecureEndpoint_t *sep,
115                                      const void *data, uint32_t dataLen)
116 {
117     if (g_networkPacketReceivedCallback != NULL)
118     {
119         g_networkPacketReceivedCallback(sep, data, dataLen);
120     }
121     else
122     {
123         OIC_LOG(ERROR, TAG, "network packet received callback is NULL!");
124     }
125 }
126
127 static void CAAdapterChangedCallback(CATransportAdapter_t adapter, CANetworkStatus_t status)
128 {
129     // Call the callback.
130     if (g_adapterChangeCallback != NULL)
131     {
132         if (CA_INTERFACE_UP == status)
133         {
134             g_adapterChangeCallback(adapter, true);
135         }
136         else if (CA_INTERFACE_DOWN == status)
137         {
138             g_adapterChangeCallback(adapter, false);
139         }
140     }
141     OIC_LOG_V(DEBUG, TAG, "[%d]adapter status is changed to [%d]", adapter, status);
142 }
143
144 #if defined(TCP_ADAPTER) || defined(EDR_ADAPTER) || defined(LE_ADAPTER)
145 static void CAConnectionChangedCallback(const CAEndpoint_t *info, bool isConnected)
146 {
147     // Call the callback.
148     if (g_connChangeCallback != NULL)
149     {
150         g_connChangeCallback(info, isConnected);
151     }
152     OIC_LOG_V(DEBUG, TAG, "[%s] connection status is changed to [%d]", info->addr, isConnected);
153 }
154 #endif
155
156 static void CAAdapterErrorHandleCallback(const CAEndpoint_t *endpoint,
157                                          const void *data, uint32_t dataLen,
158                                          CAResult_t result)
159 {
160     OIC_LOG(DEBUG, TAG, "received error from adapter in interfacecontroller");
161
162     // Call the callback.
163     if (g_errorHandleCallback != NULL)
164     {
165         g_errorHandleCallback(endpoint, data, dataLen, result);
166     }
167 }
168
169 void CAInitializeAdapters(ca_thread_pool_t handle)
170 {
171     OIC_LOG(DEBUG, TAG, "initialize adapters..");
172
173     // Initialize adapters and register callback.
174 #ifdef IP_ADAPTER
175     CAInitializeIP(CARegisterCallback, CAReceivedPacketCallback, CAAdapterChangedCallback,
176                    CAAdapterErrorHandleCallback, handle);
177 #endif /* IP_ADAPTER */
178
179 #ifdef EDR_ADAPTER
180     CAInitializeEDR(CARegisterCallback, CAReceivedPacketCallback, CAAdapterChangedCallback,
181                     CAConnectionChangedCallback, CAAdapterErrorHandleCallback, handle);
182 #endif /* EDR_ADAPTER */
183
184 #ifdef LE_ADAPTER
185     CAInitializeLE(CARegisterCallback, CAReceivedPacketCallback, CAAdapterChangedCallback,
186                    CAConnectionChangedCallback, CAAdapterErrorHandleCallback, handle);
187 #endif /* LE_ADAPTER */
188
189 #ifdef RA_ADAPTER
190     CAInitializeRA(CARegisterCallback, CAReceivedPacketCallback, CAAdapterChangedCallback,
191                    handle);
192 #endif /* RA_ADAPTER */
193
194 #ifdef TCP_ADAPTER
195     CAInitializeTCP(CARegisterCallback, CAReceivedPacketCallback, CAAdapterChangedCallback,
196                     CAConnectionChangedCallback, CAAdapterErrorHandleCallback, handle);
197 #endif /* TCP_ADAPTER */
198
199 #ifdef NFC_ADAPTER
200     CAInitializeNFC(CARegisterCallback, CAReceivedPacketCallback, CAAdapterChangedCallback,
201                     CAAdapterErrorHandleCallback, handle);
202 #endif /* NFC_ADAPTER */
203 }
204
205 void CASetPacketReceivedCallback(CANetworkPacketReceivedCallback callback)
206 {
207     OIC_LOG(DEBUG, TAG, "Set Receiver handle callback");
208
209     g_networkPacketReceivedCallback = callback;
210 }
211
212 void CASetNetworkMonitorCallbacks(CAAdapterStateChangedCB adapterCB,
213                                   CAConnectionStateChangedCB connCB)
214 {
215     OIC_LOG(DEBUG, TAG, "Set network monitoring callback");
216
217     g_adapterChangeCallback = adapterCB;
218     g_connChangeCallback = connCB;
219 }
220
221 void CASetErrorHandleCallback(CAErrorHandleCallback errorCallback)
222 {
223     OIC_LOG(DEBUG, TAG, "Set error handle callback");
224     g_errorHandleCallback = errorCallback;
225 }
226
227 CAResult_t CAStartAdapter(CATransportAdapter_t transportType)
228 {
229     OIC_LOG_V(DEBUG, TAG, "Start the adapter of CAConnectivityType[%d]", transportType);
230
231     int index = CAGetAdapterIndex(transportType);
232     if (0 > index)
233     {
234         OIC_LOG(ERROR, TAG, "unknown connectivity type!");
235         return CA_STATUS_FAILED;
236     }
237
238     CAResult_t res = CA_STATUS_FAILED;
239     if (g_adapterHandler[index].startAdapter != NULL)
240     {
241         res = g_adapterHandler[index].startAdapter();
242     }
243
244     return res;
245 }
246
247 void CAStopAdapter(CATransportAdapter_t transportType)
248 {
249     OIC_LOG_V(DEBUG, TAG, "Stop the adapter of CATransportType[%d]", transportType);
250
251     int index = CAGetAdapterIndex(transportType);
252     if (0 > index)
253     {
254         OIC_LOG(ERROR, TAG, "unknown transport type!");
255         return;
256     }
257
258     if (g_adapterHandler[index].stopAdapter != NULL)
259     {
260         g_adapterHandler[index].stopAdapter();
261     }
262 }
263
264 CAResult_t CAGetNetworkInfo(CAEndpoint_t **info, uint32_t *size)
265 {
266     if (info == NULL || size == NULL)
267     {
268         return CA_STATUS_INVALID_PARAM;
269     }
270
271     CAEndpoint_t **tempInfo = (CAEndpoint_t**) OICCalloc(g_numberOfAdapters, sizeof(*tempInfo));
272     if (!tempInfo)
273     {
274         OIC_LOG(ERROR, TAG, "Out of memory!");
275         return CA_MEMORY_ALLOC_FAILED;
276     }
277     uint32_t *tempSize =(uint32_t*) OICCalloc(g_numberOfAdapters, sizeof(*tempSize));
278     if (!tempSize)
279     {
280         OIC_LOG(ERROR, TAG, "Out of memory!");
281         OICFree(tempInfo);
282         return CA_MEMORY_ALLOC_FAILED;
283     }
284
285     CAResult_t res = CA_STATUS_FAILED;
286     size_t resSize = 0;
287     for (uint32_t index = 0; index < g_numberOfAdapters; index++)
288     {
289         if (g_adapterHandler[index].GetnetInfo != NULL)
290         {
291             // #1. get information for each adapter
292             res = g_adapterHandler[index].GetnetInfo(&tempInfo[index],
293                                                      &tempSize[index]);
294
295             // #2. total size
296             if (res == CA_STATUS_OK)
297             {
298                 resSize += tempSize[index];
299             }
300
301             OIC_LOG_V(DEBUG,
302                       TAG,
303                       "%" PRIu32 " adapter network info size is %" PRIu32 " res:%d",
304                       index,
305                       tempSize[index],
306                       res);
307         }
308     }
309
310     OIC_LOG_V(DEBUG, TAG, "network info total size is %zu!", resSize);
311
312     if (resSize == 0)
313     {
314         OICFree(tempInfo);
315         OICFree(tempSize);
316         if (res == CA_ADAPTER_NOT_ENABLED || res == CA_NOT_SUPPORTED)
317         {
318             return res;
319         }
320         else
321         {
322             return CA_STATUS_FAILED;
323         }
324     }
325
326     // #3. add data into result
327     // memory allocation
328     CAEndpoint_t *resInfo = (CAEndpoint_t *) OICCalloc(resSize, sizeof (*resInfo));
329     CA_MEMORY_ALLOC_CHECK(resInfo);
330
331     // #4. save data
332     *info = resInfo;
333     *size = resSize;
334
335     for (uint32_t index = 0; index < g_numberOfAdapters; index++)
336     {
337         // check information
338         if (tempSize[index] == 0)
339         {
340             continue;
341         }
342
343         memcpy(resInfo,
344                tempInfo[index],
345                sizeof(*resInfo) * tempSize[index]);
346
347         resInfo += tempSize[index];
348
349         // free adapter data
350         OICFree(tempInfo[index]);
351         tempInfo[index] = NULL;
352     }
353     OICFree(tempInfo);
354     OICFree(tempSize);
355
356     OIC_LOG(DEBUG, TAG, "each network info save success!");
357     return CA_STATUS_OK;
358
359     // memory error label.
360 memory_error_exit:
361
362     for (uint32_t index = 0; index < g_numberOfAdapters; index++)
363     {
364         OICFree(tempInfo[index]);
365         tempInfo[index] = NULL;
366     }
367     OICFree(tempInfo);
368     OICFree(tempSize);
369
370     return CA_MEMORY_ALLOC_FAILED;
371 }
372
373 CAResult_t CASendUnicastData(const CAEndpoint_t *endpoint, const void *data, uint32_t length,
374                              CADataType_t dataType)
375 {
376     if (endpoint == NULL)
377     {
378         OIC_LOG(DEBUG, TAG, "Invalid endpoint");
379         return CA_STATUS_INVALID_PARAM;
380     }
381
382
383     u_arraylist_t *list = CAGetSelectedNetworkList();
384     if (!list)
385     {
386         OIC_LOG(ERROR, TAG, "No selected network");
387         return CA_SEND_FAILED;
388     }
389     CATransportAdapter_t requestedAdapter = endpoint->adapter ? endpoint->adapter : CA_ALL_ADAPTERS;
390
391     for (uint32_t i = 0; i < u_arraylist_length(list); i++)
392     {
393         void* ptrType = u_arraylist_get(list, i);
394
395         if (NULL == ptrType)
396         {
397             continue;
398         }
399
400         CATransportAdapter_t connType = *(CATransportAdapter_t *)ptrType;
401         if (0 == (connType & requestedAdapter))
402         {
403             continue;
404         }
405
406         int index = CAGetAdapterIndex(connType);
407
408         if (-1 == index)
409         {
410             OIC_LOG(ERROR, TAG, "unknown transport type!");
411             return CA_STATUS_INVALID_PARAM;
412         }
413
414         int32_t sentDataLen = 0;
415
416         if (NULL != g_adapterHandler[index].sendData)
417         {
418             OIC_LOG(DEBUG, TAG, "unicast message to adapter");
419             sentDataLen = g_adapterHandler[index].sendData(endpoint, data, length, dataType);
420         }
421
422         if (sentDataLen != (int32_t)length)
423         {
424             OIC_LOG(ERROR, TAG, "error in sending data. Error will be reported in adapter");
425 #ifdef SINGLE_THREAD
426             //in case of single thread, no error handler. Report error immediately
427             return CA_SEND_FAILED;
428 #endif
429         }
430
431     }
432
433     return CA_STATUS_OK;
434 }
435
436 CAResult_t CASendMulticastData(const CAEndpoint_t *endpoint, const void *data, uint32_t length,
437                                CADataType_t dataType)
438 {
439     u_arraylist_t *list = CAGetSelectedNetworkList();
440     if (!list)
441     {
442         OIC_LOG(DEBUG, TAG, "No selected network");
443         return CA_SEND_FAILED;
444     }
445
446     CATransportAdapter_t requestedAdapter = endpoint->adapter ? endpoint->adapter : CA_ALL_ADAPTERS;
447     size_t selectedLength = u_arraylist_length(list);
448     for (size_t i = 0; i < selectedLength; i++)
449     {
450         void* ptrType = u_arraylist_get(list, i);
451
452         if (NULL == ptrType)
453         {
454             continue;
455         }
456
457         CATransportAdapter_t connType = *(CATransportAdapter_t *)ptrType;
458         if (0 == (connType & requestedAdapter))
459         {
460             continue;
461         }
462
463         int index = CAGetAdapterIndex(connType);
464         if (0 > index)
465         {
466             OIC_LOG(ERROR, TAG, "unknown connectivity type!");
467             continue;
468         }
469
470         uint32_t sentDataLen = 0;
471
472         if (NULL != g_adapterHandler[index].sendDataToAll)
473         {
474             void *payload = (void *) OICMalloc(length);
475             if (!payload)
476             {
477                 OIC_LOG(ERROR, TAG, "Out of memory!");
478                 return CA_MEMORY_ALLOC_FAILED;
479             }
480             memcpy(payload, data, length);
481             sentDataLen = g_adapterHandler[index].sendDataToAll(endpoint, payload, length, dataType);
482             OICFree(payload);
483         }
484
485         if (sentDataLen != length)
486         {
487             OIC_LOG(ERROR, TAG, "sendDataToAll failed! Error will be reported from adapter");
488 #ifdef SINGLE_THREAD
489             //in case of single thread, no error handler. Report error immediately
490             return CA_SEND_FAILED;
491 #endif
492         }
493     }
494
495     return CA_STATUS_OK;
496 }
497
498 CAResult_t CAStartListeningServerAdapters()
499 {
500     CAResult_t result = CA_STATUS_FAILED;
501
502     u_arraylist_t *list = CAGetSelectedNetworkList();
503     if (!list)
504     {
505         OIC_LOG(ERROR, TAG, "No selected network");
506         return result;
507     }
508
509     size_t length = u_arraylist_length(list);
510     for (size_t i = 0; i < length; i++)
511     {
512         void* ptrType = u_arraylist_get(list, i);
513
514         if(ptrType == NULL)
515         {
516             continue;
517         }
518
519         CATransportAdapter_t connType = *(CATransportAdapter_t *)ptrType;
520
521         int index = CAGetAdapterIndex(connType);
522         if (0 > index)
523         {
524             OIC_LOG(ERROR, TAG, "unknown connectivity type!");
525             continue;
526         }
527
528         if (g_adapterHandler[index].startListenServer != NULL)
529         {
530             const CAResult_t tmp =
531                 g_adapterHandler[index].startListenServer();
532
533             // Successful listen if at least one adapter started.
534             if (CA_STATUS_OK == tmp)
535             {
536                 result = tmp;
537             }
538         }
539     }
540
541     return result;
542 }
543
544 CAResult_t CAStopListeningServerAdapters()
545 {
546     u_arraylist_t *list = CAGetSelectedNetworkList();
547     if (!list)
548     {
549         OIC_LOG(ERROR, TAG, "No selected network");
550         return CA_STATUS_FAILED;
551     }
552
553     size_t length = u_arraylist_length(list);
554     for (size_t i = 0; i < length; i++)
555     {
556         void* ptrType = u_arraylist_get(list, i);
557         if(ptrType == NULL)
558         {
559             continue;
560         }
561
562         CATransportAdapter_t connType = *(CATransportAdapter_t *)ptrType;
563
564         int index = CAGetAdapterIndex(connType);
565         if (0 > index)
566         {
567             OIC_LOG(ERROR, TAG, "unknown connectivity type!");
568             continue;
569         }
570
571         if (g_adapterHandler[index].stopListenServer != NULL)
572         {
573             g_adapterHandler[index].stopListenServer();
574         }
575     }
576
577     return CA_STATUS_OK;
578 }
579
580 CAResult_t CAStartDiscoveryServerAdapters()
581 {
582     CAResult_t result = CA_STATUS_FAILED;
583
584     u_arraylist_t *list = CAGetSelectedNetworkList();
585
586     if (!list)
587     {
588         OIC_LOG(ERROR, TAG, "No selected network");
589         return result;
590     }
591
592     size_t length = u_arraylist_length(list);
593     for (size_t i = 0; i < length; i++)
594     {
595         void* ptrType = u_arraylist_get(list, i);
596
597         if(ptrType == NULL)
598         {
599             continue;
600         }
601
602         CATransportAdapter_t connType = *(CATransportAdapter_t *)ptrType;
603
604         int index = CAGetAdapterIndex(connType);
605         if (0 > index)
606         {
607             OIC_LOG(DEBUG, TAG, "unknown connectivity type!");
608             continue;
609         }
610
611         if (g_adapterHandler[index].startDiscoveryServer != NULL)
612         {
613             const CAResult_t tmp =
614                 g_adapterHandler[index].startDiscoveryServer();
615
616             // Successful discovery if at least one adapter started.
617             if (CA_STATUS_OK == tmp)
618             {
619                 result = tmp;
620             }
621         }
622     }
623
624     return result;
625 }
626
627 void CATerminateAdapters()
628 {
629     for (uint32_t index = 0; index < g_numberOfAdapters; index++)
630     {
631         if (g_adapterHandler[index].terminate != NULL)
632         {
633             g_adapterHandler[index].terminate();
634         }
635     }
636
637     OICFree(g_adapterHandler);
638     g_adapterHandler = NULL;
639     g_numberOfAdapters = 0;
640 }
641
642 #ifdef SINGLE_THREAD
643 CAResult_t CAReadData()
644 {
645     u_arraylist_t *list = CAGetSelectedNetworkList();
646
647     if (!list)
648     {
649         return CA_STATUS_FAILED;
650     }
651
652     uint8_t i = 0;
653     for (i = 0; i < u_arraylist_length(list); i++)
654     {
655         void *ptrType = u_arraylist_get(list, i);
656         if (NULL == ptrType)
657         {
658             OIC_LOG(ERROR, TAG, "get list fail");
659             return CA_STATUS_FAILED;
660         }
661
662         CATransportAdapter_t connType = *(CATransportAdapter_t *) ptrType;
663
664         int index = CAGetAdapterIndex(connType);
665         if (0 > index)
666         {
667             OIC_LOG(DEBUG, TAG, "unknown connectivity type!");
668             continue;
669         }
670
671         if (g_adapterHandler[index].readData != NULL)
672         {
673             g_adapterHandler[index].readData();
674         }
675     }
676
677     return CA_STATUS_OK;
678 }
679 #endif
680