It provides the service library and an sample application using the library.
Arduino Mega board and WiFi shield are used for functionlity test.
Change-Id: Iadb19361db8a777b84437ad978887dedeb2e6e63
Signed-off-by: Jihun Ha <jihun.ha@samsung.com>
Reviewed-on: https://gerrit.iotivity.org/gerrit/1189
Reviewed-by: Madan Lanka <lanka.madan@samsung.com>
Tested-by: Madan Lanka <lanka.madan@samsung.com>
env.SConscript('./src/SConscript')
-if build_sample == 'ON':
- if target_os in ['linux', 'arduino', 'android']:
- env.SConscript('./samples/' + target_os + '/SConscript')
+#if build_sample == 'ON':
+# if target_os in ['linux', 'arduino', 'android']:
+# env.SConscript('./samples/' + target_os + '/SConscript')
target_os = env.get('TARGET_OS')
-if target_os not in ['arduino','darwin','ios']:
+if target_os not in ['arduino','darwin']:
# Build things manager project
SConscript('things-manager/SConscript')
# Build protocol plugin project
# protocol-plugin use 'inotify', this feature isn't support by MAC OSX
- if target_os not in ['darwin', 'ios']:
+ if target_os not in ['darwin', 'ios', 'android']:
SConscript('protocol-plugin/SConscript')
# Build notification manager project
#else:
# SConscript('notification-manager/SampleApp/arduino/SConscript')
+if target_os == 'arduino':
+ SConscript('easy-setup/SConscript')
\ No newline at end of file
--- /dev/null
+#******************************************************************
+#
+# Copyright 2014 Samsung Electronics All Rights Reserved.
+#
+#-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+#
+#-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+
+##
+# easy-setup project build script
+##
+import os
+Import('env')
+
+# Add third party libraries
+lib_env = env.Clone()
+#SConscript(env.get('SRC_DIR') + '/service/third_party_libs.scons', exports = 'lib_env')
+
+easy_setup_env = lib_env.Clone()
+target_os = env.get('TARGET_OS')
+######################################################################
+# Build flags
+######################################################################
+easy_setup_env.AppendUnique(CPPPATH = ['sdk/inc', 'sdk/src'])
+
+if target_os not in ['windows', 'winrt']:
+ easy_setup_env.AppendUnique(CXXFLAGS = ['-std=c++0x', '-Wall'])
+ if target_os not in ['android', 'arduino']:
+ easy_setup_env.AppendUnique(CXXFLAGS = ['-pthread'])
+
+if target_os == 'android':
+ easy_setup_env.AppendUnique(CXXFLAGS = ['-frtti', '-fexceptions'])
+ easy_setup_env.PrependUnique(LIBS = ['oc', 'octbstack', 'gnustl_shared'])
+
+if target_os == 'arduino':
+ easy_setup_env.AppendUnique(CPPPATH = [
+ '../../resource/oc_logger/include',
+ '../../resource/csdk/logger/include',
+ '../../resource/csdk/stack/include',
+ '../../extlibs/cjson',
+ 'sdk/arduino/wifi/inc',
+ 'sdk/arduino/wifi/src' ])
+
+######################################################################
+# Source files and Targets
+######################################################################
+
+#if target_os == 'arduino':
+ es_src = env.Glob('sdk/src/*.cpp')
+ es_src += env.Glob('sdk/arduino/wifi/src/*.cpp')
+ es_sdk_static = easy_setup_env.StaticLibrary('ESSDKLibrary', es_src)
+ easy_setup_env.InstallTarget(es_sdk_static, 'libESSDK')
+
+if target_os == 'android':
+ es_src = env.Glob('sdk/src/*.cpp')
+ es_src += env.Glob('sdk/android/wifi/src/*.cpp')
+ es_sdk_static = easy_setup_env.StaticLibrary('ESLib', es_src)
+ es_sdk_shared = easy_setup_env.SharedLibrary('ESLib', es_src)
+ easy_setup_env.InstallTarget([es_sdk_static, es_sdk_shared], 'libESSDK')
+
+# Build JNI layer
+#if target_os == 'android':
+# SConscript(os.path.join('sdk', 'java', 'jni', 'SConscript'))
+
+#Go to build sample apps
+SConscript('sampleapp/SConscript')
+
+
--- /dev/null
+#******************************************************************
+#
+# Copyright 2014 Samsung Electronics All Rights Reserved.
+#
+#-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+#
+#-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+
+##
+# sampleapp build script
+##
+
+Import('env')
+
+# Add third party libraries
+lib_env = env.Clone()
+#SConscript(env.get('SRC_DIR') + '/service/third_party_libs.scons', 'lib_env')
+sample_env = lib_env.Clone()
+target_os = env.get('TARGET_OS')
+
+######################################################################
+# Build flags
+######################################################################
+
+######################################################################
+# Source files and Targets
+######################################################################
+if target_os == 'arduino' :
+ # Build linux sample app
+ SConscript('arduino/thinserver/SConscript')
+
--- /dev/null
+#******************************************************************
+#
+# Copyright 2014 Intel Mobile Communications GmbH All Rights Reserved.
+#
+#-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+#
+#-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+
+Import('env')
+
+thinserver_env = env.Clone()
+######################################################################
+# Build flags
+######################################################################
+thinserver_env.PrependUnique(CPPPATH = [
+ '../../../../../resource/oc_logger/include',
+ '../../../../../resource/csdk/logger/include',
+ '../../../../../resource/csdk/stack/include',
+ '../../../../../extlibs/cjson',
+ '../../../sdk/inc',
+ '../../../sdk/arduino/wifi/inc'
+ ])
+
+thinserver_env.AppendUnique(LIBPATH = [env.get('BUILD_DIR')])
+thinserver_env.AppendUnique(CPPDEFINES = ['TB_LOG', 'ARDUINOWIFI'])
+
+thinserver_env.PrependUnique(LIBS = ['octbstack', 'connectivity_abstraction','coap', 'ESSDKLibrary'])
+
+thinserver = thinserver_env.Program('thinserver', 'thinserver.cpp')
+env.CreateBin('thinserver')
+
+i_thinserver = thinserver_env.Install(env.get('BUILD_DIR'), thinserver)
+
+Alias('thinserver', i_thinserver)
+env.AppendTarget('thinserver')
+
+if(thinserver_env['UPLOAD'] == True):
+ from sys import platform as _platform
+ if _platform == "linux" or _platform == "linux2":
+ thinserver_env.Upload(env.get('BUILD_DIR') + '/service/easy-setup/sampleapp/arduino/thinserver/thinserver.hex')
+ else:
+ print 'Please use appropriate install method for your developing machine. Linux is the only supported platform right now.'
--- /dev/null
+//******************************************************************
+//
+// Copyright 2014 Samsung Electronics All Rights Reserved.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+
+// Do not remove the include below
+#include "Arduino.h"
+
+#include "logger.h"
+#include "ocstack.h"
+#include <string.h>
+
+#ifdef ARDUINOWIFI
+// Arduino WiFi Shield
+#include <SPI.h>
+#include <WiFi.h>
+#include <WiFiUdp.h>
+#else
+// Arduino Ethernet Shield
+#include <EthernetServer.h>
+#include <Ethernet.h>
+#include <Dns.h>
+#include <EthernetClient.h>
+#include <util.h>
+#include <EthernetUdp.h>
+#include <Dhcp.h>
+#endif
+
+#include "easysetup.h"
+
+const char *getResult(OCStackResult result);
+
+PROGMEM const char TAG[] = "ArduinoServer";
+
+void EventCallbackInApp(ES_RESULT eventFlag)
+{
+ Serial.println("callback!!! in app");
+}
+
+// On Arduino Atmel boards with Harvard memory architecture, the stack grows
+// downwards from the top and the heap grows upwards. This method will print
+// the distance(in terms of bytes) between those two.
+// See here for more details :
+// http://www.atmel.com/webdoc/AVRLibcReferenceManual/malloc_1malloc_intro.html
+void PrintArduinoMemoryStats()
+{
+#ifdef ARDUINO_AVR_MEGA2560
+ //This var is declared in avr-libc/stdlib/malloc.c
+ //It keeps the largest address not allocated for heap
+ extern char *__brkval;
+ //address of tmp gives us the current stack boundry
+ int tmp;
+ OC_LOG_V(INFO, TAG, "Stack: %u Heap: %u", (unsigned int)&tmp, (unsigned int)__brkval);
+ OC_LOG_V(INFO, TAG, "Unallocated Memory between heap and stack: %u",
+ ((unsigned int)&tmp - (unsigned int)__brkval));
+#endif
+}
+//The setup function is called once at startup of the sketch
+void setup()
+{
+ // Add your initialization code here
+ // Note : This will initialize Serial port on Arduino at 115200 bauds
+ OC_LOG_INIT();
+ OC_LOG(DEBUG, TAG, PCF("OCServer is starting..."));
+
+ WaitingForOnboarding(ES_WIFI, EventCallbackInApp);
+
+ // Initialize the OC Stack in Server mode
+ if (OCInit(NULL, 0, OC_SERVER) != OC_STACK_OK)
+ {
+ OC_LOG(ERROR, TAG, PCF("OCStack init error"));
+ return;
+ }
+
+ PrepareToProvisioning(EventCallbackInApp);
+
+ if (OCStartPresence(0) != OC_STACK_OK)
+ {
+ OC_LOG(ERROR, TAG, PCF("Start Presence init error"));
+ return;
+ }
+}
+
+// The loop function is called in an endless loop
+void loop()
+{
+ // This artificial delay is kept here to avoid endless spinning
+ // of Arduino microcontroller. Modify it as per specific application needs.
+ delay(2000);
+
+ // This call displays the amount of free SRAM available on Arduino
+ PrintArduinoMemoryStats();
+
+ // Give CPU cycles to OCStack to perform send/recv and other OCStack stuff
+ if (OCProcess() != OC_STACK_OK)
+ {
+ OC_LOG(ERROR, TAG, PCF("OCStack process error"));
+ return;
+ }
+ //ChangeLightRepresentation(NULL);
+}
--- /dev/null
+//******************************************************************
+//
+// Copyright 2014 Samsung Electronics All Rights Reserved.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+
+// Do not remove the include below
+#include "Arduino.h"
+
+#include "logger.h"
+#include "ocstack.h"
+#include <string.h>
+
+#ifdef ARDUINOWIFI
+// Arduino WiFi Shield
+#include <SPI.h>
+#include <WiFi.h>
+#include <WiFiUdp.h>
+#else
+// Arduino Ethernet Shield
+#include <EthernetServer.h>
+#include <Ethernet.h>
+#include <Dns.h>
+#include <EthernetClient.h>
+#include <util.h>
+#include <EthernetUdp.h>
+#include <Dhcp.h>
+#endif
+
+#include "common.h"
+
+#ifndef ES_NETWORK_HANDLER_H_
+#define ES_NETWORK_HANDLER_H_
+
+#define MAXSSIDLEN 33
+#define MAXNETCREDLEN 20
+#define MAXNUMTYPE 5
+#define MAXADDRLEN 15
+
+typedef void (*NetworkEventCallback)(ES_RESULT);
+
+enum NetworkType
+{
+ ES_WIFI = 1, ES_BT = 2, ES_BLE = 3, ES_ZIGBEE = 4, ES_ETH = 5
+};
+
+typedef struct NETWORKINFO
+{
+ NetworkType type;
+
+ // for WiFI
+ IPAddress ipaddr;
+ char ssid[MAXSSIDLEN];
+
+ // for BT, BLE
+ byte mac[6];
+} NetworkInfo;
+
+ES_RESULT ConnectToWiFiNetworkForOnboarding(char *ssid, char *pass, NetworkEventCallback);
+int getCurrentNetworkInfo(NetworkType targetType, NetworkInfo *info);
+
+#endif
--- /dev/null
+//******************************************************************
+//
+// Copyright 2014 Samsung Electronics All Rights Reserved.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+
+#include "networkHandler.h"
+
+PROGMEM const char TAG[] = "ArduinoServer";
+
+int findNetwork(char *ssid);
+int ConnectToNetwork(char *ssid, char *pass);
+void printEncryptionType(int thisType);
+
+// Arduino WiFi Shield
+// Note : Arduino WiFi Shield currently does NOT support multicast and therefore
+// this server will NOT be listening on 224.0.1.187 multicast address.
+
+static const char ARDUINO_WIFI_SHIELD_UDP_FW_VER[] = "1.1.0";
+
+IPAddress myIP;
+
+ES_RESULT ConnectToWiFiNetworkForOnboarding(char *ssid, char *pass, NetworkEventCallback cb)
+{
+ char *fwVersion;
+ int status = WL_IDLE_STATUS;
+ int res;
+
+ // check for the presence of the shield:
+ if (WiFi.status() == WL_NO_SHIELD)
+ {
+ OC_LOG(ERROR, TAG, PCF("WiFi shield not present"));
+ return ES_ERROR;
+ }
+
+ // Verify that WiFi Shield is running the firmware with all UDP fixes
+ fwVersion = WiFi.firmwareVersion();
+ OC_LOG_V(INFO, TAG, "WiFi Shield Firmware version %s", fwVersion);
+ if (strncmp(fwVersion, ARDUINO_WIFI_SHIELD_UDP_FW_VER, sizeof(ARDUINO_WIFI_SHIELD_UDP_FW_VER))
+ != 0)
+ {
+ OC_LOG(DEBUG, TAG, PCF("!!!!! Upgrade WiFi Shield Firmware version !!!!!!"));
+ return ES_ERROR;
+ }
+
+ while (findNetwork(ssid) == 0) // found
+ {
+ delay(2000);
+ }
+
+ if (cb != NULL)
+ {
+ cb(ES_NETWORKFOUND);
+ }
+
+ if (WiFi.status() == WL_CONNECTED)
+ WiFi.disconnect();
+
+ res = ConnectToNetwork(ssid, pass);
+
+ if (res == 0)
+ {
+ return ES_NETWORKCONNECTED;
+ }
+ else
+ {
+ return ES_NETWORKNOTCONNECTED;
+ }
+}
+
+int findNetwork(char *ssid)
+{
+ int res = 0;
+ // scan for nearby networks:
+ Serial.println("** Scan Networks **");
+ int numSsid = WiFi.scanNetworks();
+ if (numSsid == -1)
+ {
+ Serial.println("Couldn't get a wifi connection");
+
+ return res;
+ }
+
+ // print the list of networks seen:
+ Serial.print("number of available networks:");
+ Serial.println(numSsid);
+
+ // print the network number and name for each network found:
+ for (int thisNet = 0; thisNet < numSsid; thisNet++)
+ {
+ Serial.print(thisNet);
+ Serial.print(") ");
+ Serial.print(WiFi.SSID(thisNet));
+ Serial.print("\tEncryption: ");
+ printEncryptionType(WiFi.encryptionType(thisNet));
+
+ if (strcmp(WiFi.SSID(thisNet), ssid) == 0)
+ {
+ res = 1;
+ }
+ }
+
+ return res;
+}
+
+int ConnectToNetwork(char *ssid, char *pass)
+{
+ int status = WL_IDLE_STATUS;
+ //IPAddress desiredIP(192, 168, 43, 2);
+ //IPAddress desiredIP(192, 168, 0, 115);
+
+ //WiFi.config(desiredIP);
+
+ // attempt to connect to Wifi network:
+ while (status != WL_CONNECTED)
+ {
+ OC_LOG_V(INFO, TAG, "Attempting to connect to SSID: %s", ssid);
+
+ status = WiFi.begin(ssid, pass);
+
+ // wait 10 seconds for connection:
+ delay(10000);
+ }
+ OC_LOG(DEBUG, TAG, PCF("Connected to wifi"));
+
+ myIP = WiFi.localIP();
+ OC_LOG_V(INFO, TAG, "IP Address: %d.%d.%d.%d", myIP[0], myIP[1], myIP[2], myIP[3]);
+
+ char buf[50];
+ sprintf(buf, "IP Address: %d.%d.%d.%d", myIP[0], myIP[1], myIP[2], myIP[3]);
+ Serial.println(buf);
+
+ return 0;
+}
+
+int getCurrentNetworkInfo(NetworkType targetType, NetworkInfo *info)
+{
+ if (targetType == ES_WIFI && WiFi.status() == WL_CONNECTED)
+ {
+ info->type = ES_WIFI;
+ info->ipaddr = WiFi.localIP();
+ strcpy(info->ssid, WiFi.SSID());
+
+ return 0;
+ }
+
+ return -1;
+}
+
+void printEncryptionType(int thisType)
+{
+ // read the encryption type and print out the name:
+ switch (thisType)
+ {
+ case ENC_TYPE_WEP:
+ Serial.println("WEP");
+ break;
+ case ENC_TYPE_TKIP:
+ Serial.println("WPA");
+ break;
+ case ENC_TYPE_CCMP:
+ Serial.println("WPA2");
+ break;
+ case ENC_TYPE_NONE:
+ Serial.println("None");
+ break;
+ case ENC_TYPE_AUTO:
+ Serial.println("Auto");
+ break;
+ }
+}
--- /dev/null
+//******************************************************************
+//
+// Copyright 2014 Samsung Electronics All Rights Reserved.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+
+#ifndef ES_COMMON_H_
+#define ES_COMMON_H_
+
+typedef enum
+{
+ ES_ERROR = -1,
+ ES_OK = 0,
+ ES_NETWORKFOUND = 1,
+ ES_NETWORKCONNECTED,
+ ES_NETWORKNOTCONNECTED,
+ ES_RESOURCECREATED = 11,
+ ES_RECVREQOFPROVRES = 21,
+ ES_RECVREQOFNETRES,
+ ES_RECVUPDATEOFPROVRES,
+ ES_RECVTRIGGEROFPROVRES,
+} ES_RESULT;
+
+#endif
--- /dev/null
+//******************************************************************
+//
+// Copyright 2014 Samsung Electronics All Rights Reserved.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+
+// Do not remove the include below
+#include "Arduino.h"
+
+#include "logger.h"
+#include "ocstack.h"
+#include <string.h>
+
+#ifdef ARDUINOWIFI
+// Arduino WiFi Shield
+#include <SPI.h>
+#include <WiFi.h>
+#include <WiFiUdp.h>
+#else
+// Arduino Ethernet Shield
+#include <EthernetServer.h>
+#include <Ethernet.h>
+#include <Dns.h>
+#include <EthernetClient.h>
+#include <util.h>
+#include <EthernetUdp.h>
+#include <Dhcp.h>
+#endif
+
+#include "common.h"
+#include "networkHandler.h"
+#include "resourceHandler.h"
+
+typedef void (*EventCallback)(ES_RESULT);
+
+OCStackResult Init();
+
+ES_RESULT WaitingForOnboarding(NetworkType networkType, EventCallback);
+//OCStackResult WaitingForOnboarding(NetworkType networkType, char *name);
+//OCStackResult WaitingForOnboarding(NetworkType networkType, char *name, char *pass);
+
+ES_RESULT PrepareToProvisioning(EventCallback);
--- /dev/null
+//******************************************************************
+//
+// Copyright 2014 Samsung Electronics All Rights Reserved.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+
+// Do not remove the include below
+#include "Arduino.h"
+
+#include "logger.h"
+#include "ocstack.h"
+#include <string.h>
+
+#ifdef ARDUINOWIFI
+// Arduino WiFi Shield
+#include <SPI.h>
+#include <WiFi.h>
+#include <WiFiUdp.h>
+#else
+// Arduino Ethernet Shield
+#include <EthernetServer.h>
+#include <Ethernet.h>
+#include <Dns.h>
+#include <EthernetClient.h>
+#include <util.h>
+#include <EthernetUdp.h>
+#include <Dhcp.h>
+#endif
+
+#include "common.h"
+#include "networkHandler.h"
+#include "octypes.h"
+
+#ifndef ES_RESOURCE_HANDLER_H_
+#define ES_RESOURCE_HANDLER_H_
+
+typedef void (*ResourceEventCallback)(ES_RESULT);
+
+/* Structure to represent a Light resource */
+typedef struct PROVRESOURCE
+{
+ OCResourceHandle handle;
+ int ps; // provisiong status, 1 : need to provisioning, 2 : Connected to Internet
+ int tnt; // target network type, 1: WLAN, 2: BT, 3: BLE, 4: Zigbee, ...
+ char tnn[MAXSSIDLEN]; // target network name, i.e. SSID for WLAN, MAC address for BT
+ char cd[MAXNETCREDLEN]; // credential information
+} ProvResource;
+
+/* Structure to represent a Light resource */
+typedef struct NETRESOURCE
+{
+ OCResourceHandle handle;
+ int cnt; // current network type, 1: WLAN, 2: BT, 3: BLE, 4: Zigbee, ...
+ int ant[MAXNUMTYPE]; // available network type, 1: WLAN, 2: BT, 3: BLE, 4: Zigbee, ...
+ char ipaddr[MAXADDRLEN]; // ip address
+ char cnn[MAXSSIDLEN]; // current network name
+} NetResource;
+
+OCStackResult createProvisioningResource();
+OCStackResult createNetworkResource();
+void getTargetNetworkInfoFromProvResource(char *, char *);
+void RegisterResourceEventCallBack(ResourceEventCallback);
+
+#endif
--- /dev/null
+//******************************************************************
+//
+// Copyright 2014 Samsung Electronics All Rights Reserved.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+
+#include "easysetup.h"
+
+PROGMEM const char TAG[] = "ArduinoServer";
+
+/// WiFi network info and credentials
+char defaultSsid[] = "EasyConnect";
+char defaultPass[] = "EasyConnect";
+
+int g_eventflag = 0;
+int g_cnt = 0;
+char *targetSsid;
+char *targetPass;
+
+EventCallback g_cbForProvisioning = NULL;
+EventCallback g_cbForOnboarding = NULL;
+
+void EventCallbackInOnboarding(ES_RESULT event);
+void EventCallbackInProvisioning(ES_RESULT event);
+void EventCallbackAfterProvisioning(ES_RESULT event);
+
+void EventCallbackInOnboarding(ES_RESULT event)
+{
+ Serial.println("[Callback] in onboarding process");
+
+ if (event == ES_NETWORKFOUND || event == ES_NETWORKCONNECTED)
+ {
+ if (g_cbForOnboarding != NULL)
+ {
+ g_cbForOnboarding(event);
+ }
+ }
+}
+
+void EventCallbackInProvisioning(ES_RESULT event)
+{
+ ES_RESULT res = ES_OK;
+
+ Serial.println("[Callback] in provisioning process");
+
+ if (event == ES_RECVTRIGGEROFPROVRES)
+ {
+ targetSsid = (char *) malloc(MAXSSIDLEN);
+ targetPass = (char *) malloc(MAXNETCREDLEN);
+
+ getTargetNetworkInfoFromProvResource(targetSsid, targetPass);
+
+ res = ConnectToWiFiNetworkForOnboarding(targetSsid, targetPass,
+ EventCallbackAfterProvisioning);
+
+ if (g_cbForProvisioning != NULL)
+ {
+ g_cbForProvisioning(res);
+ }
+ }
+}
+
+void EventCallbackAfterProvisioning(ES_RESULT event)
+{
+ Serial.println("[Callback] after provisioning process");
+
+ if (event == ES_NETWORKFOUND || event == ES_NETWORKCONNECTED)
+ {
+ if (g_cbForProvisioning != NULL)
+ {
+ g_cbForProvisioning(event);
+ }
+ }
+}
+
+ES_RESULT WaitingForOnboarding(NetworkType networkType, EventCallback cb)
+{
+ if (networkType == ES_WIFI)
+ {
+ if (g_cbForOnboarding == NULL)
+ {
+ g_cbForOnboarding = cb;
+ }
+
+ return ConnectToWiFiNetworkForOnboarding(defaultSsid, defaultPass,
+ EventCallbackInOnboarding);
+ }
+}
+
+ES_RESULT PrepareToProvisioning(EventCallback cb)
+{
+ if (cb == NULL)
+ {
+ return ES_ERROR;
+ }
+ else
+ {
+ g_cbForProvisioning = cb;
+ }
+
+ if (createProvisioningResource() != OC_STACK_OK)
+ {
+ return ES_ERROR;
+ }
+
+ if (createNetworkResource() != OC_STACK_OK)
+ {
+ return ES_ERROR;
+ }
+
+ RegisterResourceEventCallBack(EventCallbackInProvisioning);
+
+ return ES_RESOURCECREATED;
+}
+
--- /dev/null
+//******************************************************************
+//
+// Copyright 2014 Samsung Electronics All Rights Reserved.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+//-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
+
+#include "resourceHandler.h"
+#include "cJSON.h"
+
+PROGMEM const char TAG[] = "ArduinoServer";
+
+ProvResource g_prov;
+NetResource g_net;
+
+OCEntityHandlerResult OCEntityHandlerCb(OCEntityHandlerFlag, OCEntityHandlerRequest *);
+const char *getResult(OCStackResult result);
+
+OCEntityHandlerResult ProcessGetRequest(OCEntityHandlerRequest *ehRequest, char *payload,
+ uint16_t maxPayloadSize);
+OCEntityHandlerResult ProcessPutRequest(OCEntityHandlerRequest *ehRequest, char *payload,
+ uint16_t maxPayloadSize);
+OCEntityHandlerResult ProcessPostRequest(OCEntityHandlerRequest *ehRequest, char *payload,
+ uint16_t maxPayloadSize);
+char* constructJsonResponse(OCEntityHandlerRequest *ehRequest);
+
+int g_flag = 0;
+
+ResourceEventCallback g_cbForResEvent = NULL;
+
+void RegisterResourceEventCallBack(ResourceEventCallback cb)
+{
+ g_cbForResEvent = cb;
+}
+
+void getTargetNetworkInfoFromProvResource(char *name, char *pass)
+{
+ if (name != NULL && pass != NULL)
+ {
+ sprintf(name, "%s", g_prov.tnn);
+ sprintf(pass, "%s", g_prov.cd);
+ }
+}
+
+OCStackResult createProvisioningResource()
+{
+ g_prov.ps = 1; // need to provisioning
+ g_prov.tnt = ES_WIFI;
+ sprintf(g_prov.tnn, "Unknown");
+ sprintf(g_prov.cd, "Unknown");
+
+ OCStackResult res = OCCreateResource(&g_prov.handle, "oic.prov", OC_RSRVD_INTERFACE_DEFAULT,
+ "/oic/prov", OCEntityHandlerCb, OC_DISCOVERABLE | OC_OBSERVABLE);
+
+ OC_LOG_V(INFO, TAG, "Created Prov resource with result: %s", getResult(res));
+
+ return res;
+}
+
+OCStackResult createNetworkResource()
+{
+ NetworkInfo netInfo;
+
+ if (getCurrentNetworkInfo(ES_WIFI, &netInfo) != 0)
+ {
+ return OC_STACK_ERROR;
+ }
+
+ if (netInfo.type != ES_WIFI)
+ {
+ return OC_STACK_ERROR;
+ }
+
+ g_net.cnt = (int) netInfo.type;
+ g_net.ant[0] = (int) ES_WIFI;
+ sprintf(g_net.ipaddr, "%d.%d.%d.%d", netInfo.ipaddr[0], netInfo.ipaddr[1], netInfo.ipaddr[2],
+ netInfo.ipaddr[3]);
+ sprintf(g_net.cnn, "%s", netInfo.ssid);
+
+ OC_LOG_V(INFO, TAG, "SSID: %s", g_net.cnn);
+ OC_LOG_V(INFO, TAG, "IP Address: %s", g_net.ipaddr);
+
+ OCStackResult res = OCCreateResource(&g_net.handle, "oic.net", OC_RSRVD_INTERFACE_DEFAULT,
+ "/oic/net", OCEntityHandlerCb, OC_DISCOVERABLE | OC_OBSERVABLE);
+ OC_LOG_V(INFO, TAG, "Created Net resource with result: %s", getResult(res));
+
+ return res;
+}
+
+OCEntityHandlerResult ProcessGetRequest(OCEntityHandlerRequest *ehRequest, char *payload,
+ uint16_t maxPayloadSize)
+{
+ OCEntityHandlerResult ehResult = OC_EH_ERROR;
+
+ char *getResp = constructJsonResponse(ehRequest);
+
+ if (!getResp)
+ {
+ OC_LOG(ERROR, TAG, "constructJsonResponse failed");
+ return OC_EH_ERROR;
+ }
+
+ if (MAX_RESPONSE_LENGTH > strlen(getResp))
+ {
+ strncpy(payload, getResp, strlen(getResp));
+ ehResult = OC_EH_OK;
+ }
+ else
+ {
+ OC_LOG_V(INFO, TAG, "Response buffer: %d bytes is too small", maxPayloadSize);
+ ehResult = OC_EH_ERROR;
+ }
+
+ free(getResp);
+
+ return ehResult;
+}
+
+OCEntityHandlerResult ProcessPutRequest(OCEntityHandlerRequest *ehRequest, char *payload,
+ uint16_t maxPayloadSize)
+{
+ OCEntityHandlerResult ehResult = OC_EH_ERROR;
+
+ OC_LOG_V(INFO, TAG, "PUT Request Payload: %s", ehRequest->reqJSONPayload);
+
+ // Get cJSON pointer to query
+ cJSON *putJson = cJSON_Parse(ehRequest->reqJSONPayload);
+ if (!putJson)
+ {
+ OC_LOG_V(ERROR, TAG, "Failed to parse JSON: %s", ehRequest->reqJSONPayload);
+ return ehResult;
+ }
+
+ // Get root of JSON payload, then the 1st resource.
+ cJSON* carrier = cJSON_GetObjectItem(putJson, "oic");
+ if (!carrier)
+ {
+ OC_LOG_V(ERROR, TAG, "Failed to parse JSON: %s", ehRequest->reqJSONPayload);
+ return ehResult;
+ }
+ carrier = cJSON_GetArrayItem(carrier, 0);
+ carrier = cJSON_GetObjectItem(carrier, "rep");
+ if (!carrier)
+ {
+ OC_LOG_V(ERROR, TAG, "Failed to parse JSON: %s", ehRequest->reqJSONPayload);
+ return ehResult;
+ }
+
+ cJSON* prop = cJSON_GetObjectItem(carrier, "tnn");
+ if (prop)
+ {
+ sprintf(g_prov.tnn, "%s", prop->valuestring);
+ }
+
+ prop = cJSON_GetObjectItem(carrier, "cd");
+ if (prop)
+ {
+ sprintf(g_prov.cd, "%s", prop->valuestring);
+ }
+
+ cJSON_Delete(putJson);
+
+ // TODO: Now once receiving PUT request, the enrollee start to connect to enroller.
+ g_flag = 1;
+
+ char *getResp = constructJsonResponse(ehRequest);
+
+ if (!getResp)
+ {
+ OC_LOG(ERROR, TAG, "constructJsonResponse failed");
+ return OC_EH_ERROR;
+ }
+
+ if (MAX_RESPONSE_LENGTH > strlen(getResp))
+ {
+ strncpy(payload, getResp, strlen(getResp));
+ ehResult = OC_EH_OK;
+ }
+ else
+ {
+ OC_LOG_V(INFO, TAG, "Response buffer: %d bytes is too small", maxPayloadSize);
+ ehResult = OC_EH_ERROR;
+ }
+
+ free(getResp);
+ return ehResult;
+}
+
+OCEntityHandlerResult ProcessPostRequest(OCEntityHandlerRequest *ehRequest, char *payload,
+ uint16_t maxPayloadSize)
+{
+ OCEntityHandlerResult ehResult = OC_EH_ERROR;
+ OC_LOG_V(INFO, TAG, "PUT Request Payload: %s", ehRequest->reqJSONPayload);
+
+ // Get cJSON pointer to query
+ cJSON *putJson = cJSON_Parse(ehRequest->reqJSONPayload);
+
+ if (!putJson)
+ {
+ OC_LOG_V(ERROR, TAG, "Failed to parse JSON: %s", ehRequest->reqJSONPayload);
+ return ehResult;
+ }
+
+ // Get root of JSON payload, then the 1st resource.
+ cJSON* carrier = cJSON_GetObjectItem(putJson, "oic");
+ if (!carrier)
+ {
+ OC_LOG_V(ERROR, TAG, "Failed to parse JSON: %s", ehRequest->reqJSONPayload);
+ return ehResult;
+ }
+ carrier = cJSON_GetArrayItem(carrier, 0);
+ carrier = cJSON_GetObjectItem(carrier, "rep");
+ if (!carrier)
+ {
+ OC_LOG_V(ERROR, TAG, "Failed to parse JSON: %s", ehRequest->reqJSONPayload);
+ return ehResult;
+ }
+
+ cJSON* prop = cJSON_GetObjectItem(carrier, "tr");
+ if (prop)
+ {
+ // Triggering
+ ehResult = OC_EH_OK;
+ }
+
+ cJSON_Delete(putJson);
+
+ g_flag = 1;
+
+ return ehResult;
+}
+
+char* constructJsonResponse(OCEntityHandlerRequest *ehRequest)
+{
+ cJSON *json = cJSON_CreateObject();
+ cJSON *format;
+ char *jsonResponse;
+ char *JsonResp;
+ char temp_resp[256];
+
+ if (g_prov.handle != NULL && ehRequest->resource == g_prov.handle)
+ {
+ char *uri = (char *) "/oic/prov";
+
+ cJSON_AddStringToObject(json, "href", uri);
+ cJSON_AddItemToObject(json, "rep", format = cJSON_CreateObject());
+ cJSON_AddNumberToObject(format, "ps", g_prov.ps);
+ cJSON_AddNumberToObject(format, "tnt", g_prov.tnt);
+ cJSON_AddStringToObject(format, "tnn", g_prov.tnn);
+ cJSON_AddStringToObject(format, "cd", g_prov.cd);
+
+ jsonResponse = cJSON_Print(json);
+ cJSON_Delete(json);
+ }
+ else if (g_net.handle != NULL && ehRequest->requestHandle == g_net.handle)
+ {
+ char *uri = (char *) "/oic/net";
+
+ cJSON_AddStringToObject(json, "href", uri);
+ cJSON_AddItemToObject(json, "rep", format = cJSON_CreateObject());
+ cJSON_AddNumberToObject(format, "ant", g_net.ant[0]);
+
+ jsonResponse = cJSON_Print(json);
+ cJSON_Delete(json);
+ }
+ else
+ {
+ return jsonResponse;
+ }
+
+ OC_LOG_V(INFO, TAG, "Constructed Response: %s", jsonResponse);
+
+ Serial.print("Constructed Response: ");
+ Serial.println(jsonResponse);
+
+ return jsonResponse;
+}
+
+// This is the entity handler for the registered resource.
+// This is invoked by OCStack whenever it recevies a request for this resource.
+
+OCEntityHandlerResult OCEntityHandlerCb(OCEntityHandlerFlag flag,
+ OCEntityHandlerRequest* entityHandlerRequest)
+{
+ OCEntityHandlerResult ehRet = OC_EH_OK;
+ OCEntityHandlerResponse response =
+ { 0 };
+ char payload[MAX_RESPONSE_LENGTH] =
+ { 0 };
+
+ if (entityHandlerRequest && (flag & OC_REQUEST_FLAG))
+ {
+ if (OC_REST_GET == entityHandlerRequest->method)
+ {
+ OC_LOG_V(INFO, TAG, "Received GET request");
+ ehRet = ProcessGetRequest(entityHandlerRequest, payload, sizeof(payload) - 1);
+ }
+ else if (OC_REST_PUT == entityHandlerRequest->method)
+ {
+ OC_LOG_V(INFO, TAG, "Received PUT request");
+
+ if (g_prov.handle != NULL && entityHandlerRequest->resource == g_prov.handle)
+ {
+ ehRet = ProcessPutRequest(entityHandlerRequest, payload, sizeof(payload) - 1);
+ }
+ else
+ {
+ ehRet = OC_EH_ERROR;
+ }
+ }
+ else if (OC_REST_POST == entityHandlerRequest->method)
+ {
+ // TODO: As of now, POST request will be not received.
+ OC_LOG(INFO, TAG, "Received OC_REST_POST from client");
+ //ehRet = ProcessPostRequest (entityHandlerRequest, payload, sizeof(payload) - 1);
+ }
+
+ if (ehRet == OC_EH_OK)
+ {
+ // Format the response. Note this requires some info about the request
+ response.requestHandle = entityHandlerRequest->requestHandle;
+ response.resourceHandle = entityHandlerRequest->resource;
+ response.ehResult = ehRet;
+ response.payload = payload;
+ response.payloadSize = strlen(payload);
+ response.numSendVendorSpecificHeaderOptions = 0;
+ memset(response.sendVendorSpecificHeaderOptions, 0,
+ sizeof response.sendVendorSpecificHeaderOptions);
+ memset(response.resourceUri, 0, sizeof response.resourceUri);
+ // Indicate that response is NOT in a persistent buffer
+ response.persistentBufferFlag = 0;
+
+ // Send the response
+ if (OCDoResponse(&response) != OC_STACK_OK)
+ {
+ OC_LOG(ERROR, TAG, "Error sending response");
+ ehRet = OC_EH_ERROR;
+ }
+ }
+ }
+
+ if (g_flag == 1)
+ {
+ g_cbForResEvent(ES_RECVTRIGGEROFPROVRES);
+ g_flag = 0;
+ }
+
+ return ehRet;
+}
+
+const char *getResult(OCStackResult result)
+{
+ switch (result)
+ {
+ case OC_STACK_OK:
+ return "OC_STACK_OK";
+ case OC_STACK_INVALID_URI:
+ return "OC_STACK_INVALID_URI";
+ case OC_STACK_INVALID_QUERY:
+ return "OC_STACK_INVALID_QUERY";
+ case OC_STACK_INVALID_IP:
+ return "OC_STACK_INVALID_IP";
+ case OC_STACK_INVALID_PORT:
+ return "OC_STACK_INVALID_PORT";
+ case OC_STACK_INVALID_CALLBACK:
+ return "OC_STACK_INVALID_CALLBACK";
+ case OC_STACK_INVALID_METHOD:
+ return "OC_STACK_INVALID_METHOD";
+ case OC_STACK_NO_MEMORY:
+ return "OC_STACK_NO_MEMORY";
+ case OC_STACK_COMM_ERROR:
+ return "OC_STACK_COMM_ERROR";
+ case OC_STACK_INVALID_PARAM:
+ return "OC_STACK_INVALID_PARAM";
+ case OC_STACK_NOTIMPL:
+ return "OC_STACK_NOTIMPL";
+ case OC_STACK_NO_RESOURCE:
+ return "OC_STACK_NO_RESOURCE";
+ case OC_STACK_RESOURCE_ERROR:
+ return "OC_STACK_RESOURCE_ERROR";
+ case OC_STACK_SLOW_RESOURCE:
+ return "OC_STACK_SLOW_RESOURCE";
+ case OC_STACK_NO_OBSERVERS:
+ return "OC_STACK_NO_OBSERVERS";
+ case OC_STACK_ERROR:
+ return "OC_STACK_ERROR";
+ default:
+ return "UNKNOWN";
+ }
+}
+