Imported Upstream version 0.9.1
[platform/upstream/iotivity.git] / resource / csdk / connectivity / src / ip_adapter / arduino / caipclient_eth.cpp
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 #include "caipinterface_singlethread.h"
21
22 #include <Arduino.h>
23 #include <Ethernet.h>
24 #include <socket.h>
25 #include <w5100.h>
26 #include <EthernetUdp.h>
27 #include <IPAddress.h>
28
29 #include "logger.h"
30 #include "cacommon.h"
31 #include "caadapterinterface.h"
32 #include "caipadapter_singlethread.h"
33 #include "caipadapterutils_eth.h"
34 #include "caadapterutils.h"
35 #include "oic_malloc.h"
36
37 #define TAG "IPC"
38
39 static int g_sockID = 0;
40
41 /**
42  * @var g_unicastPort
43  * @brief Unicast Port
44  */
45 static uint16_t g_unicastPort = 0;
46
47 void CAIPSetUnicastSocket(int socketID)
48 {
49     OIC_LOG(DEBUG, TAG, "IN");
50     if (0 < socketID)
51     {
52         g_sockID = socketID;
53     }
54     else
55     {
56         OIC_LOG(ERROR, TAG, "sock err");
57     }
58
59     OIC_LOG(DEBUG, TAG, "OUT");
60     return;
61 }
62
63 void CAIPSetUnicastPort(uint16_t port)
64 {
65     OIC_LOG(DEBUG, TAG, "IN");
66     g_unicastPort = port;
67     OIC_LOG(DEBUG, TAG, "OUT");
68     return;
69 }
70
71 uint32_t CAIPSendData(const char *remoteAddress, uint16_t port,
72                       const char *buf, uint32_t bufLen, bool isMulticast)
73 {
74     if (!isMulticast && 0 == g_unicastPort)
75     {
76         OIC_LOG(ERROR, TAG, "port 0");
77         return 0;
78     }
79
80     VERIFY_NON_NULL(buf, TAG, "buf");
81     VERIFY_NON_NULL(remoteAddress, TAG, "address");
82
83     int socketID = 0;
84     if (isMulticast)
85     {
86         if (CAArduinoInitMulticastUdpSocket(remoteAddress, port, g_unicastPort, &socketID)
87             != CA_STATUS_OK)
88         {
89             OIC_LOG(ERROR, TAG, "init mcast err");
90             return 0;
91         }
92         OIC_LOG_V(DEBUG, TAG, "MPORT:%d", port);
93         OIC_LOG_V(DEBUG, TAG, "LPORT:%d", g_unicastPort);
94         OIC_LOG_V(DEBUG, TAG, "SOCKET ID:%d", socketID);
95     }
96     else
97     {
98         if (0 == g_sockID)
99         {
100             if (CAArduinoInitUdpSocket(&port, &socketID) != CA_STATUS_OK)
101             {
102                 OIC_LOG(ERROR, TAG, "init ucast err");
103                 return 0;
104             }
105         }
106         else
107         {
108             socketID = g_sockID;
109         }
110     }
111
112     uint32_t ret;
113     uint8_t ipAddr[4] = { 0 };
114     uint16_t parsedPort = 0;
115     if (CAParseIPv4AddressInternal(remoteAddress, ipAddr, sizeof(ipAddr),
116                                    &parsedPort) != CA_STATUS_OK)
117     {
118         OIC_LOG(ERROR, TAG, "parse fail");
119         return 0;
120     }
121
122     if (bufLen > 65535) // Max value for uint16_t
123     {
124         // This will never happen as max buffer size we are dealing with is COAP_MAX_PDU_SIZE
125         OIC_LOG(ERROR, TAG, "Size exceeded");
126         return 0;
127     }
128
129     ret = sendto(socketID, (const uint8_t *)buf, (uint16_t)bufLen, ipAddr, port);
130     if (g_sockID != socketID)
131     {
132         close(socketID);
133     }
134
135     OIC_LOG(DEBUG, TAG, "OUT");
136     return ret;
137 }
138