Browse Source

Merge upstream version 1.2.5

Christoph Biedl 3 years ago
parent
commit
4474189192
63 changed files with 8452 additions and 803 deletions
  1. 10 6
      .gitignore
  2. 27 0
      .vscode/launch.json
  3. 2494 0
      Doxyfile
  4. 10 18
      LICENSE.md
  5. 34 13
      Makefile
  6. 34 0
      Makefile_tests
  7. 42 0
      Makefile_win32
  8. 40 0
      Makefile_win32_cross
  9. 42 0
      Makefile_win64
  10. 39 0
      Makefile_win64_cross
  11. 29 94
      README.md
  12. 0 0
      bin/placeholder
  13. 3 22
      build.sh
  14. 118 0
      doc/general_help.txt
  15. 14 0
      doc/reference-manual-ykushcmd/INDEX_reference-manual-ykushcmd.json
  16. 16 0
      doc/reference-manual-ykushcmd/METADATA_ykushcmd-reference-ykush.json
  17. 16 0
      doc/reference-manual-ykushcmd/METADATA_ykushcmd-reference-ykush3.json
  18. 16 0
      doc/reference-manual-ykushcmd/METADATA_ykushcmd-reference-ykushxs.json
  19. 31 0
      doc/reference-manual-ykushcmd/crud_cmd_example.txt
  20. 435 0
      doc/reference-manual-ykushcmd/ykushcmd-reference-manual-ykush3.html
  21. 173 0
      doc/reference-manual-ykushcmd/ykushcmd-reference-ykush.html
  22. 243 0
      doc/reference-manual-ykushcmd/ykushcmd-reference-ykush3.html
  23. 145 0
      doc/reference-manual-ykushcmd/ykushcmd-reference-ykushxs.html
  24. 136 0
      doc/ykush3_help.txt
  25. 49 0
      doc/ykushxs_help.txt
  26. 0 5
      install.sh
  27. 435 0
      learn/html/ykushcmd-reference-manual-ykush3.html
  28. 116 0
      src/commandParser.cpp
  29. 0 0
      ykushcmd/commandParser.h
  30. 160 0
      src/help/ykush_help.cpp
  31. 49 0
      src/help/ykush_help.h
  32. 0 0
      ykushcmd/objs/placeholder
  33. 0 0
      ykushcmd/platformdefs.h
  34. 0 0
      ykushcmd/stdafx.cpp
  35. 0 0
      ykushcmd/stdafx.h
  36. 0 0
      ykushcmd/targetver.h
  37. 67 0
      src/tests/test_usbhid.cpp
  38. 407 0
      src/usbhid/usbhid.cpp
  39. 156 0
      src/usbhid/usbhid.h
  40. 147 0
      src/utils/command_parser.cpp
  41. 82 0
      src/utils/command_parser.h
  42. 101 0
      src/utils/string2val.cpp
  43. 31 0
      src/utils/string2val.h
  44. 0 0
      src/windows/placeholder
  45. 204 0
      src/yk_usb_device.cpp
  46. 115 0
      src/yk_usb_device.h
  47. 14 0
      src/yktrl.cpp
  48. 283 0
      src/ykush/ykush.cpp
  49. 104 0
      src/ykush/ykush.h
  50. 417 0
      src/ykush2/ykush2.cpp
  51. 70 0
      src/ykush2/ykush2.h
  52. 857 0
      src/ykush3/ykush3.cpp
  53. 128 0
      src/ykush3/ykush3.h
  54. 18 10
      ykushcmd/ykushcmd.vcxproj
  55. 20 2
      ykushcmd/ykushcmd.vcxproj.filters
  56. 6 0
      src/ykushcmd.vcxproj.user
  57. 191 0
      src/ykushxs/ykushxs.cpp
  58. 78 0
      src/ykushxs/ykushxs.h
  59. 0 0
      ykush.sln
  60. 0 268
      ykushcmd/commandParser.cpp
  61. 0 338
      ykushcmd/usbcom.cpp
  62. 0 15
      ykushcmd/usbcom.h
  63. 0 12
      ykushcmd/ykushcmd.cpp

+ 10 - 6
.gitignore

@@ -1,10 +1,14 @@
-hidapi/
-Release/
-Debug/
-release/
-debug/
 *.swp
 *.bak
 *.o
 .directory
-bin/ykushcmd
+bin/ykushcmd*
+.vs/
+*.exe
+*.so
+*.exp
+nbproject
+doc/ykushcmd-doxygen/*
+.vscode
+dev/
+

+ 27 - 0
.vscode/launch.json

@@ -0,0 +1,27 @@
+{
+    // Use IntelliSense to learn about possible attributes.
+    // Hover to view descriptions of existing attributes.
+    // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
+    "version": "0.2.0",
+    "configurations": [
+        {
+            "name": "(gdb) Launch",
+            "type": "cppdbg",
+            "request": "launch",
+            "program": "enter program name, for example ${workspaceFolder}/a.out",
+            "args": [],
+            "stopAtEntry": false,
+            "cwd": "${workspaceFolder}",
+            "environment": [],
+            "externalConsole": true,
+            "MIMode": "gdb",
+            "setupCommands": [
+                {
+                    "description": "Enable pretty-printing for gdb",
+                    "text": "-enable-pretty-printing",
+                    "ignoreFailures": true
+                }
+            ]
+        }
+    ]
+}

File diff suppressed because it is too large
+ 2494 - 0
Doxyfile


+ 10 - 18
LICENSE.md

@@ -1,21 +1,13 @@
- Copyright (c) 2016 Yepkit Lda
+Copyright (c) 2017 Yepkit Lda
 
- Permission is hereby granted, free of charge, to any person obtaining a copy
- of this software and associated documentation files (the "Software"), to deal
- in the Software without restriction, including without limitation the rights
- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
- copies of the Software, and to permit persons to whom the Software is
- furnished to do so, subject to the following conditions:
-
- The above copyright notice and this permission notice shall be included in
- all copies or substantial portions of the Software.
-
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
- THE SOFTWARE.
+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.

+ 34 - 13
Makefile

@@ -1,23 +1,44 @@
+PROG_SOURCE = yktrl.cpp
+SOURCE += commandParser.cpp
+SOURCE += ykushxs/ykushxs.cpp
+SOURCE += ykush/ykush.cpp
+SOURCE += ykush2/ykush2.cpp
+SOURCE += ykush3/ykush3.cpp
+SOURCE += yk_usb_device.cpp
+SOURCE += help/ykush_help.cpp
+SOURCE += utils/command_parser.cpp
+SOURCE += utils/string2val.cpp
+SOURCE += usbhid/usbhid.cpp
+
+
+SOURCE_FULL = $(addprefix src/, $(SOURCE))
+PROG_SOURCE_FULL = $(addprefix src/, $(PROG_SOURCE))
+OBJS = $(SOURCE_FULL:.cpp=.o)
+PROG_OBJ = $(PROG_SOURCE_FULL:.cpp=.o)
+
+DEFINES += _LINUX_
+DEFINES += _LIBUSB_
+
+COMPILE_FLAGS += $(addprefix -D, $(DEFINES))
+
 CUR_PATH = $(shell echo $(PWD))
-OBJS = $(addprefix ykushcmd/objs/,ykushcmd.o commandParser.o usbcom.o)
-LIBS = -lhidapi-libusb -lusb-1.0 -ludev
-LOADPATHS = -L$(CUR_PATH)/ykushcmd/linux
-PREPROCESSOR_DEFS = -DLINUX
+INCLUDEPATHS = $(addprefix -I$(CUR_PATH)/, $(dir $(SOURCE_FULL)) libusb )
+LOADPATHS = 
+LIBS = -lusb-1.0
 CPP = g++
+ 
 
-ykushcmd : $(OBJS)
-	$(CPP) $(LOADPATHS) -o bin/ykushcmd $(OBJS) $(LIBS)
 
+ykushcmd : $(PROG_OBJ) $(OBJS)
+	$(CPP) -o bin/$@ $(PROG_OBJ) $(OBJS) $(LIBS)
 
-ykushcmd/objs/ykushcmd.o : ykushcmd/ykushcmd.cpp ykushcmd/commandParser.h
-	$(CPP) $(PREPROCESSOR_DEFS) -c ykushcmd/ykushcmd.cpp -o ykushcmd/objs/ykushcmd.o
+$(PROG_OBJ) :  %.o : %.cpp
+	$(CPP) $(COMPILE_FLAGS) $(INCLUDEPATHS) -c $< -o $@
 
-ykushcmd/objs/commandParser.o : ykushcmd/commandParser.cpp ykushcmd/commandParser.h ykushcmd/usbcom.h 
-	$(CPP) $(PREPROCESSOR_DEFS) -c ykushcmd/commandParser.cpp -o ykushcmd/objs/commandParser.o
+$(OBJS) : %.o : %.cpp %.h
+	$(CPP) $(COMPILE_FLAGS) $(INCLUDEPATHS) -c $< -o $@
 
-ykushcmd/objs/usbcom.o : ykushcmd/usbcom.cpp ykushcmd/linux/hidapi.h ykushcmd/usbcom.h
-	$(CPP) $(PREPROCESSOR_DEFS) -c ykushcmd/usbcom.cpp -o ykushcmd/objs/usbcom.o
 
 clean :
-	rm -f bin/ykushcmd $(OBJS)
+	rm -f bin/yktrl $(OBJS) $(PROG_OBJ)
 

+ 34 - 0
Makefile_tests

@@ -0,0 +1,34 @@
+PROG_SOURCE = tests/test_usbhid.cpp
+SOURCE += usbhid/usbhid.cpp
+
+
+SOURCE_FULL = $(addprefix src/, $(SOURCE))
+PROG_SOURCE_FULL = $(addprefix src/, $(PROG_SOURCE))
+OBJS = $(SOURCE_FULL:.cpp=.o)
+PROG_OBJ = $(PROG_SOURCE_FULL:.cpp=.o)
+
+CUR_PATH = $(shell echo $(PWD))
+INCLUDEPATHS = $(addprefix -I$(CUR_PATH)/, $(dir $(SOURCE_FULL)))
+LOADPATHS =
+LIBS = -lusb-1.0
+CPP = g++
+
+
+
+#OBJS = $(addprefix src/objs/, ykushcmd.o commandParser.o ykushxs.o yk_usb_device.o ykush.o ykush_help.o ykush2.o ykush3.o command_parser.o string2val.o)
+#LOADPATHS = -L$(CUR_PATH)/src/linux
+#INCLUDEPATHS= -I$(CUR_PATH)/src/linux -I$(CUR_PATH)/src/ykushxs -I$(CUR_PATH)/src/ykush -I$(CUR_PATH)/src -I$(CUR_PATH)/src/help -I$(CUR_PATH)/src/ykush2 -I$(CUR_PATH)/src/ykush3 -I$(CUR_PATH)/src/utils
+
+
+ykushcmd : $(PROG_OBJ) $(OBJS)
+	$(CPP) $(LOADPATHS) -o bin/$@ $(PROG_OBJ) $(OBJS) $(LIBS)
+
+$(PROG_OBJ) :  %.o : %.cpp
+	$(CPP) $(PREPROCESSOR_DEFS) $(INCLUDEPATHS) -c $< -o $@
+
+$(OBJS) : %.o : %.cpp %.h
+	$(CPP) $(PREPROCESSOR_DEFS) $(INCLUDEPATHS) -c $< -o $@
+
+clean :
+	rm -f bin/ykushcmd $(OBJS) $(PROG_OBJ)
+

+ 42 - 0
Makefile_win32

@@ -0,0 +1,42 @@
+PROG_SOURCE = yktrl.cpp
+SOURCE += commandParser.cpp
+SOURCE += ykushxs/ykushxs.cpp
+SOURCE += ykush/ykush.cpp
+SOURCE += ykush2/ykush2.cpp
+SOURCE += ykush3/ykush3.cpp
+SOURCE += yk_usb_device.cpp
+SOURCE += help/ykush_help.cpp
+SOURCE += utils/command_parser.cpp
+SOURCE += utils/string2val.cpp
+
+
+SOURCE_FULL = $(addprefix src/, $(SOURCE))
+PROG_SOURCE_FULL = $(addprefix src/, $(PROG_SOURCE))
+OBJS = $(SOURCE_FULL:.cpp=.o)
+PROG_OBJ = $(PROG_SOURCE_FULL:.cpp=.o)
+
+CUR_PATH = $(CURDIR)
+INCLUDEPATHS = $(addprefix -I$(CUR_PATH)/, $(dir $(SOURCE_FULL)) hidapi )
+LOADPATHS = -L$(CUR_PATH)/hidapi/mingw32
+LIBS = -lhidapi
+FLAGS = -static-libgcc -static-libstdc++
+
+#Change MinGW exec name to match version instaled in your system
+CPP = i686-w64-mingw32-g++
+#CPP_WIN32 =  i686-w64-mingw32-g++ 
+#CPP_WIN64 =  x86_64-w64-mingw32-g++ 
+
+
+ykushcmd_win32.exe : $(PROG_OBJ) $(OBJS)
+	$(CPP) $(FLAGS) $(LOADPATHS) -o bin/Win32/$@ $(PROG_OBJ) $(OBJS) $(LIBS)
+
+$(PROG_OBJ) :  %.o : %.cpp
+	$(CPP) $(FLAGS) $(PREPROCESSOR_DEFS) $(INCLUDEPATHS) -c $< -o $@
+
+$(OBJS) : %.o : %.cpp %.h
+	$(CPP) $(FLAGS) $(PREPROCESSOR_DEFS) $(INCLUDEPATHS) -c $< -o $@
+
+
+clean :
+	rm -f bin/Win32/yktrl_win32.exe $(OBJS) $(PROG_OBJ)
+

+ 40 - 0
Makefile_win32_cross

@@ -0,0 +1,40 @@
+PROG_SOURCE = yktrl.cpp
+SOURCE += commandParser.cpp
+SOURCE += ykushxs/ykushxs.cpp
+SOURCE += ykush/ykush.cpp
+SOURCE += ykush2/ykush2.cpp
+SOURCE += ykush3/ykush3.cpp
+SOURCE += yk_usb_device.cpp
+SOURCE += help/ykush_help.cpp
+SOURCE += utils/command_parser.cpp
+SOURCE += utils/string2val.cpp
+
+
+SOURCE_FULL = $(addprefix src/, $(SOURCE))
+PROG_SOURCE_FULL = $(addprefix src/, $(PROG_SOURCE))
+OBJS = $(SOURCE_FULL:.cpp=.o)
+PROG_OBJ = $(PROG_SOURCE_FULL:.cpp=.o)
+
+CUR_PATH = $(shell echo $(PWD))
+INCLUDEPATHS = $(addprefix -I$(CUR_PATH)/, $(dir $(SOURCE_FULL)) hidapi )
+LOADPATHS = -L$(CUR_PATH)/hidapi/mingw32
+LIBS = -lhidapi
+FLAGS = -static-libgcc -static-libstdc++
+CPP = i686-w64-mingw32-g++
+#CPP_WIN32 =  i686-w64-mingw32-g++ 
+#CPP_WIN64 =  x86_64-w64-mingw32-g++ 
+
+
+ykushcmd_win32.exe : $(PROG_OBJ) $(OBJS)
+	$(CPP) $(FLAGS) $(LOADPATHS) -o bin/Win32/$@ $(PROG_OBJ) $(OBJS) $(LIBS)
+
+$(PROG_OBJ) :  %.o : %.cpp
+	$(CPP) $(FLAGS) $(PREPROCESSOR_DEFS) $(INCLUDEPATHS) -c $< -o $@
+
+$(OBJS) : %.o : %.cpp %.h
+	$(CPP) $(FLAGS) $(PREPROCESSOR_DEFS) $(INCLUDEPATHS) -c $< -o $@
+
+
+clean :
+	rm -f bin/Win32/yktrl_win32.exe $(OBJS) $(PROG_OBJ)
+

+ 42 - 0
Makefile_win64

@@ -0,0 +1,42 @@
+PROG_SOURCE = yktrl.cpp
+SOURCE += commandParser.cpp
+SOURCE += ykushxs/ykushxs.cpp
+SOURCE += ykush/ykush.cpp
+SOURCE += ykush2/ykush2.cpp
+SOURCE += ykush3/ykush3.cpp
+SOURCE += yk_usb_device.cpp
+SOURCE += help/ykush_help.cpp
+SOURCE += utils/command_parser.cpp
+SOURCE += utils/string2val.cpp
+
+
+SOURCE_FULL = $(addprefix src/, $(SOURCE))
+PROG_SOURCE_FULL = $(addprefix src/, $(PROG_SOURCE))
+OBJS = $(SOURCE_FULL:.cpp=.o)
+PROG_OBJ = $(PROG_SOURCE_FULL:.cpp=.o)
+
+CUR_PATH = $(CURDIR)
+INCLUDEPATHS = $(addprefix -I$(CUR_PATH)/, $(dir $(SOURCE_FULL)) hidapi )
+LOADPATHS = -L$(CUR_PATH)/hidapi/mingw32
+LIBS = -lhidapi
+FLAGS = -static-libgcc -static-libstdc++
+
+#Change MinGW exec name to match version instaled in your system
+CPP = x86_64-w64-mingw32-g++
+#CPP_WIN32 =  i686-w64-mingw32-g++ 
+#CPP_WIN64 =  x86_64-w64-mingw32-g++ 
+
+
+ykushcmd_win64.exe : $(PROG_OBJ) $(OBJS)
+	$(CPP) $(FLAGS) $(LOADPATHS) -o bin/Win32/$@ $(PROG_OBJ) $(OBJS) $(LIBS)
+
+$(PROG_OBJ) :  %.o : %.cpp
+	$(CPP) $(FLAGS) $(PREPROCESSOR_DEFS) $(INCLUDEPATHS) -c $< -o $@
+
+$(OBJS) : %.o : %.cpp %.h
+	$(CPP) $(FLAGS) $(PREPROCESSOR_DEFS) $(INCLUDEPATHS) -c $< -o $@
+
+
+clean :
+	rm -f bin/Win64/yktrl_win32.exe $(OBJS) $(PROG_OBJ)
+

+ 39 - 0
Makefile_win64_cross

@@ -0,0 +1,39 @@
+PROG_SOURCE = yktrl.cpp
+SOURCE += commandParser.cpp
+SOURCE += ykushxs/ykushxs.cpp
+SOURCE += ykush/ykush.cpp
+SOURCE += ykush2/ykush2.cpp
+SOURCE += ykush3/ykush3.cpp
+SOURCE += yk_usb_device.cpp
+SOURCE += help/ykush_help.cpp
+SOURCE += utils/command_parser.cpp
+SOURCE += utils/string2val.cpp
+
+
+SOURCE_FULL = $(addprefix src/, $(SOURCE))
+PROG_SOURCE_FULL = $(addprefix src/, $(PROG_SOURCE))
+OBJS = $(SOURCE_FULL:.cpp=.o)
+PROG_OBJ = $(PROG_SOURCE_FULL:.cpp=.o)
+
+CUR_PATH = $(shell echo $(PWD))
+INCLUDEPATHS = $(addprefix -I$(CUR_PATH)/, $(dir $(SOURCE_FULL)) hidapi )
+LOADPATHS = -L$(CUR_PATH)/hidapi/mingw64
+LIBS = -lhidapi
+FLAGS = -static-libgcc -static-libstdc++
+CPP = x86_64-w64-mingw32-g++
+#CPP_WIN32 =  i686-w64-mingw32-g++ 
+#CPP_WIN64 =  x86_64-w64-mingw32-g++ 
+
+
+ykushcmd_win64.exe : $(PROG_OBJ) $(OBJS)
+	$(CPP) $(FLAGS) $(LOADPATHS) -o bin/Win64/$@ $(PROG_OBJ) $(OBJS) $(LIBS)
+
+$(PROG_OBJ) :  %.o : %.cpp
+	$(CPP) $(FLAGS) $(PREPROCESSOR_DEFS) $(INCLUDEPATHS) -c $< -o $@
+
+$(OBJS) : %.o : %.cpp %.h
+	$(CPP) $(FLAGS) $(PREPROCESSOR_DEFS) $(INCLUDEPATHS) -c $< -o $@
+
+clean :
+	rm -f bin/Win64/yktrl_win64.exe $(OBJS) $(PROG_OBJ)
+

+ 29 - 94
README.md

@@ -1,151 +1,86 @@
 # YKUSH Command Application
 
 
-Control application for Yepkit YKUSH Switchable USB Hub board.
+Control application for Yepkit YKUSH Switchable USB Hub boards.
 
 
 Description
 ===========
 
-Console application developed to illustrate the programmatic control of YKUSH capabilities.
+Console application developed to illustrate the programmatic control of YKUSH family boards capabilities.
 It executes one command per run, being appropriate to be executed as a console command.
 But it can be easily adapted to execute a work-flow with multiple commands and we encourage you to alter it to best fit your needs.
 
-The core of the application is consolidated in two source code files, the *commandParser.cpp* and the *usbcom.cpp*.
-The first contains the work-flow control and the second the communication functions.
+The implementation makes use of libusb for Linux builds and hidapi for Windows.
+For Linux we include a build and installation script, `build.sh` and `install.sh` respectively, for building and installing the application. 
 
-The implementation makes use of hidapi open-source library which is portable across several operating systems.
-We include a Visual Studio solution file for building on Windows. For Linux we include a build and installation script, `build.sh` and `install.sh` respectively, for building and installing the application. 
 
-Note that hidapi is not included in the source code package and has to be obtained beforehand. For Linux, if the
-`build.sh` script is used, to build the application, it will take care of downloading and building the hidapi library for you. In Windows this step has to
-be manually performed by the user.
+Boards Supported
+================
+- [YKUSH](https://www.yepkit.com/products/ykush)
+- [YKUSHXS](https://www.yepkit.com/product/300115/YKUSHXS)
+- [YKUSH3](https://www.yepkit.com/product/300110/YKUSH3)
 
 
 Licensing
 =========
 
-The source code is licensed under MIT license. 
+The source code is licensed Apache License, Version 2.0. 
 Refer to [LICENSE](LICENSE.md) file.
 
 
 Building
 ========
 
-The steps for building on Windows and Linux are detailed bellow.
-
-Windows
--------
-
-Before building the application from source on Windows you need to get the [hidapi library](http://www.signal11.us/oss/hidapi/) and build it.
-Follow the instructions in the hidapi documentation for building the library in the several systems. 
-
-After building the hidapi library you need to include the relevant hidapi files to *ykushcmd* project. 
-
-Copy to `ykush\ykushcmd\windows\` the following hidapi library files:
-- hidapi.dll
-- hidapi.exp
-- hidapi.lib
-
-
-Open the `ykush\ykush.sln` with Microsoft Visual Studio and build the solution.
-After a successful build process the executable file will be created in the`ykush\bin\` folder.
-
-The next step is to make the dynamically linked library accessible to executable.
-We can install the `hidapi.dll` in the system or ensure that a copy of the file is in the same folder than the `ykush.exe`.
+The steps for building on Linux and Windows are detailed bellow.
 
 
 Linux
 -----
 
-The easiest way to build the application on Linux is to use the `build.sh` script which is in the `ykush/` folder.
-Nonetheless the application can be built running make and using the provided Makefile directly, but it will require
-some prior manual configuration detailed ahead. 
-
-To build the application using the scripts run the following inside the `ykush/` folder.
+For Linux `libusb-1.0` must be installed. For Debian based systems run the following.
 ```
-./build.sh
+sudo apt-get install libusb-1.0-0 libusb-1.0-0-dev
 ```
-Note that the script requires Internet connectivity to fetch the latest version of hidapi library.
-
-Some dependencies may not have been satisfied and some additional systems components and utilities may be required.
-If that was the case please install them and re-run the script. 
-
-After a successful build process you can install the ykush command in the system. To do so, in `ykush/` folder run:
+With these dependencies installed, build the application the running the following script.
 ```
-sudo ./install.sh
+./build.sh
 ```
 
-After install, the `ykush` command is ready for use.
-
-
-On the other hand, if you want to build running make directly with the provided Makefile do the following.
-
-First get the [hidapi library](http://www.signal11.us/oss/hidapi/) and build it.
-Please follow the instructions in the hidapi documentation for building the library in the several systems. 
-
-After building the hidapi library include the relevant hidapi files to *ykushcmd* project. 
-
-Copy to `ykush/ykushcmd/linux/` the `libhidapi-hidraw.so` and the `libhidapi-libusb.so` files from hidapi library you
-just built.
-
-Now add the following lines to the `platformdefs.h` file which is in the `ykush/ykushcmd/` folder.
+After a successful build process you can install the ykush command in the system. To do so, run:
 ```
-#ifndef PLATFORMDEFS_H
-#define PLATFORMDEFS_H
-#define LINUX
-#endif
+sudo ./install.sh
 ```
 
+After install, the `ykushcmd` command is ready for use.
 
-Next, in the `ykush/` folder run `make` to build the application.
-If the build process is successful the ykush executable will be created in the `ykush/bin/` folder.
-
-The next step is to make the shared library accessible to the executable.
-Do this by installing the *libhidapi-hidraw.so* or the *libhidapi-libusb.so*, depending if the hidraw or the libusb back-end is to be used (in doubt install both), in a system folder (e.g., /usr/lib/) or set the environment variable *LD_LIBRARY_PATH* with the path to the library files. 
-Alternatively you can run the script `install.sh` which is located in the `ykush/` folder.
 
 
-Using it
-========
-
 Windows
 -------
-Navigate to the `ykush\bin\` folder and run `ykush.exe -h` to print all the available command options a syntax.
 
-Let's look at some command examples.
+To build using MinGW run the following command.
 
-Assuming that just one YKUSH board is connected to our host, if we wanted to turn **OFF** the downstream port 1 we would issue the following command.
+For 32bit:
 ```
-ykushcmd.exe -d 1
+make -f Makefile_win32
 ```
 
-Similarly, if we wanted to turn the downstream 1 back **ON** we would issue the following command.
+For 64bit:
 ```
-ykushcmd.exe -u 1
+make -f Makefile_win64
 ```
 
-Assuming that two YKUSH boards are connected to our host and we wanted to turn **OFF** the downstream port 1 of one specific board. 
-To accomplish this we need to address the command by the YKUSH board **serial number**. 
-To find out the boards serial number we can issue the following command.
-```
-ykushcmd.exe -l
-```
-This will print the serial number of all YKUSH boards attached to the host.
-Assuming the our board had the serial number YK1234567, we would issue the following command.
-```
-ykushcmd.exe -s YK1234567 -d 1
-```
-This would turn **OFF** the downstream port 1 of the board with the serial number YK12345.
+After a successful build process the executable file will be created in the `bin\Win32` or `bin\Win64` folder depending if it was the 32 or 64 bit build.
 
 
-Linux
------
-For Linux the command options and syntax are the same with the slight difference that the executable file does not have the `.exe` extension.
-Also depending of your user permissions you may need to precede the command with the *sudo* directive (e.g, `sudo ykushcmd -d 1`).
+
+Using it
+========
+
+For details on using YKUSHCMD please refer to the [YKUSHCMD Reference Manual](https://www.learn.yepkit.com/reference/ykushcmd-reference-ykush/1/2).
 
 
-For more information and resources for the YKUSH board please visit the [yepkit website ykush page](https://www.yepkit.com/products/ykush).
 
 
 

+ 0 - 0
bin/placeholder


+ 3 - 22
build.sh

@@ -2,28 +2,9 @@
 #
 # YKUSH command application build script
 
-rm -rf hidapi
+make clean
 
-echo "Checking for git..."
-command -v git >/dev/null 2>&1 || { echo >&2 "Git is required and is not installed. Aborting."; exit 1; }
-
-echo "Fetching latest version of hidapi..."
-git clone git://github.com/signal11/hidapi.git
-
-echo "Building hidapi..."
-make --directory=hidapi/linux -f Makefile-manual
-cp -fv hidapi/linux/libhidapi-hidraw.so ykushcmd/linux/
-
-make --directory=hidapi/libusb -f Makefile-manual
-cp -fv hidapi/libusb/libhidapi-libusb.so ykushcmd/linux/
-
-echo "Configuring ykush app files..."
-
-echo "#ifndef PLATFORMDEFS_H" > ykushcmd/platformdefs.h
-echo "#define PLATFORMDEFS_H" >> ykushcmd/platformdefs.h
-echo "#define LINUX" >> ykushcmd/platformdefs.h
-echo "#endif" >> ykushcmd/platformdefs.h
-
-echo "Building ykush command..."
+echo "Building YKUSHCMD..."
 make
 
+

+ 118 - 0
doc/general_help.txt

@@ -0,0 +1,118 @@
+--------------------------------------------------------------------------
+
+        YKUSH Boards Command Application Help
+        
+--------------------------------------------------------------------------
+
+
+Command Structure:
+-------------------
+
+ykushcmd <board_prefix> [<options>]
+
+board_prefix            Indexes the scopeboard being commanded. 
+                        Prefixes/board scope mapping:
+                        
+                        -------------------------
+                        | Board     | Prefix    |
+                        -------------------------
+                        | YKUSH     | No prefix |
+                        -------------------------
+                        | YKUSH XS  | ykushxs   |
+                        -------------------------
+                        | YKUSH 2   | ykush2    |
+                        -------------------------
+                        | YKUSH 3   | ykush3    |
+                        -------------------------
+                        
+
+ options                Options specific to each board scope as detailed
+                        bellow.                      
+                        
+
+                        
+1. Available Commands For YKUSH Boards:
+------------------------------------------
+
+ykushcmd -d dn_number                       Turns DOWN the downstream port
+                                            with the number dn_number
+                                            
+
+ykushcmd -u dn_number                       Turns UP the downstream port 
+                                            with the number dn_number
+                                            
+
+ykushcmd -g dn_number                       Obtains the switching status 
+                                            of port with the number dn_number
+                                            
+
+ykushcmd -l                                 Lists all currently attached 
+                                            YKUSH boards
+                                            
+
+ykushcmd -s serial_number -d dn_number      Turns DOWN the downstream port 
+                                            with the number dn_number for
+                                            the board with the specified
+                                            serial number
+                                            
+
+ykushcmd -s serial_number -u dn_number      Turns UP the downstream port
+                                            with the number dn_number for
+                                            the board with the specified
+                                            serial number
+
+
+
+ykushcmd -s serial_number -g dn_number      Obtains the switching status
+                                            of port with the number
+                                            dn_number for the board with
+                                            the specified serial number
+
+
+
+                                            
+NOTE: For Windows operating systems add the .exe extension when calling the ykushcmd command. For example for disconnecting the downstream port 1 the command is as follows.
+
+ykushcmd.exe -d 1                                            
+                                            
+                   
+                   
+
+
+2. Available Commands For YKUSH XS Boards:
+------------------------------------------
+
+ykushcmd ykushxs -d                     Turns DOWN the downstream port
+
+
+ykushcmd ykushxs -u                     Turns UP the downstream port
+
+
+ykushcmd ykushxs -g                     Obtains the switching status of
+                                        the downstream port
+                                        
+
+ykushcmd ykushxs -l                     Lists all currently attached
+                                        YKUSH XS boards
+                                        
+
+ykushcmd ykushxs -s serial_number -d    Turns DOWN the downstream port for
+                                        the board with the specified
+                                        serial number
+                                        
+
+ykushcmd ykushxs -s serial_number -u    Turns UP the downstream port for
+                                        the board with the specified
+                                        serial number
+                                        
+
+ykushcmd ykushxs -s serial_number -g    Obtains the switching status of
+                                        port for the board with the
+                                        specified serial number
+
+                                        
+NOTE: For Windows operating systems add the .exe extension when calling the ykushcmd command. For example for disconnecting the downstream port the command is as follows.
+
+ykushcmd.exe ykushxs -d
+
+

+ 14 - 0
doc/reference-manual-ykushcmd/INDEX_reference-manual-ykushcmd.json

@@ -0,0 +1,14 @@
+{
+    "reference_uid" : "reference-manual-ykushcmd",
+    "reference_title" : "YKUSHCMD Reference Manual",
+    "version" : {
+                    "major" : 1,
+                    "minor" : 2
+            },
+    "pages" : [
+            { "page_uid" : "ykushcmd-reference-ykush", "page_title" : "YKUSH"},
+            { "page_uid" : "ykushcmd-reference-ykushxs", "page_title" : "YKUSHXS"},
+            { "page_uid" : "ykushcmd-reference-ykush3", "page_title" : "YKUSH3"}
+    ],
+    "root_page_uid" : "ykushcmd-reference-ykush"
+}

+ 16 - 0
doc/reference-manual-ykushcmd/METADATA_ykushcmd-reference-ykush.json

@@ -0,0 +1,16 @@
+{
+        "page_uid": "ykushcmd-reference-ykush",
+        "page_title" : "YKUSH with YKUSHCMD",
+        "reference_uid" :"reference-manual-ykushcmd",
+        "reference_title" : "YKUSHCMD Reference Manual",
+        "version" : {
+                "major" : 1,
+                "minor" :  2
+        },
+        "status": "published",
+        "content": {
+                "tags": ["YKUSHCMD","YKUSH","User Manual","Switched Hub","USB Hub", "Yepkit"],
+                "title": "Controlling YKUSH with YKUSHCMD",
+                "subtitle": "Command options and examples"
+        }
+}

+ 16 - 0
doc/reference-manual-ykushcmd/METADATA_ykushcmd-reference-ykush3.json

@@ -0,0 +1,16 @@
+{
+        "page_uid": "ykushcmd-reference-ykush3",
+        "page_title" : "YKUSH3 with YKUSHCMD",
+        "reference_uid" :"reference-manual-ykushcmd",
+        "reference_title" : "YKUSHCMD Reference Manual",
+        "version" : {
+                "major" : 1,
+                "minor" :  2
+        },
+        "status": "published",
+        "content": {
+                "tags": ["YKUSHCMD","YKUSH3","User Manual","Switched Hub","USB Hub", "Yepkit", "USB 3.1"],
+                "title": "Controlling YKUSH3 with YKUSHCMD",
+                "subtitle": "Command options and examples"
+        }
+}

+ 16 - 0
doc/reference-manual-ykushcmd/METADATA_ykushcmd-reference-ykushxs.json

@@ -0,0 +1,16 @@
+{
+        "page_uid": "ykushcmd-reference-ykushxs",
+        "page_title" : "YKUSHXS with YKUSHCMD",
+        "reference_uid" :"reference-manual-ykushcmd",
+        "reference_title" : "YKUSHCMD Reference Manual",
+        "version" : {
+                "major" : 1,
+                "minor" :  2
+        },
+        "status": "published",
+        "content": {
+                "tags": ["YKUSHCMD","YKUSHXS","User Manual","Switched Hub","USB Hub", "Yepkit"],
+                "title": "Controlling YKUSHXS with YKUSHCMD",
+                "subtitle": "Command options and examples"
+        }
+}

+ 31 - 0
doc/reference-manual-ykushcmd/crud_cmd_example.txt

@@ -0,0 +1,31 @@
+node reference_index_create_replace.js /home/paulo/development/software/ykushcmd/doc/reference-manual-ykushcmd/INDEX_reference-manual-ykushcmd.json
+
+#YKUSH
+node reference_page_create_replace.js /home/paulo/development/software/ykushcmd/doc/reference-manual-ykushcmd/METADATA_ykushcmd-reference-ykush.json /home/paulo/development/software/ykushcmd/doc/reference-manual-ykushcmd/ykushcmd-reference-ykush.html
+
+
+#YKUSHXS
+node reference_page_create_replace.js /home/paulo/development/software/ykushcmd/doc/reference-manual-ykushcmd/METADATA_ykushcmd-reference-ykushxs.json /home/paulo/development/software/ykushcmd/doc/reference-manual-ykushcmd/ykushcmd-reference-ykushxs.html
+
+#YKUSH3
+node reference_page_create_replace.js /home/paulo/development/software/ykushcmd/doc/reference-manual-ykushcmd/METADATA_ykushcmd-reference-ykush3.json /home/paulo/development/software/ykushcmd/doc/reference-manual-ykushcmd/ykushcmd-reference-ykush3.html
+
+
+
+
+
+#
+#AWS
+#
+
+node reference_index_create_replace.js /home/yepkit/web/nodejs/apps/learn.yepkit.com/htmls/reference/ykushcmd/INDEX_reference-manual-ykushcmd.json
+
+#YKUSH
+node reference_page_create_replace.js /home/yepkit/web/nodejs/apps/learn.yepkit.com/htmls/reference/ykushcmd/METADATA_ykushcmd-reference-ykush.json /home/yepkit/web/nodejs/apps/learn.yepkit.com/htmls/reference/ykushcmd/ykushcmd-reference-ykush.html
+
+
+#YKUSHXS
+node reference_page_create_replace.js /home/yepkit/web/nodejs/apps/learn.yepkit.com/htmls/reference/ykushcmd/METADATA_ykushcmd-reference-ykushxs.json /home/yepkit/web/nodejs/apps/learn.yepkit.com/htmls/reference/ykushcmd/ykushcmd-reference-ykushxs.html
+
+#YKUSH3
+node reference_page_create_replace.js /home/yepkit/web/nodejs/apps/learn.yepkit.com/htmls/reference/ykushcmd/METADATA_ykushcmd-reference-ykush3.json /home/yepkit/web/nodejs/apps/learn.yepkit.com/htmls/reference/ykushcmd/ykushcmd-reference-ykush3.html

+ 435 - 0
doc/reference-manual-ykushcmd/ykushcmd-reference-manual-ykush3.html

@@ -0,0 +1,435 @@
+<div class="reference_software_manual_version">
+	This manual page refers to software version <b>v1.2.0</b>.
+</div>
+
+<div class="reference_software_manual_index">
+	<ul>
+		<li><a href="#command_list">Command list</a></li>
+		<li><a href="#ykush3_man_important_links">Important links</a></li>
+		
+	</ul>
+</div>
+
+<div class="reference_software_manual_body">
+
+	<!-- 
+		COMMAND LIST 
+	-->
+	<h1 id="command_list">Command list</h1>
+	<div>
+		<ul>
+			<li><a href="#downstream_port_commands">Downstream port commands</a></li>
+			<li><a href="#5V_output_port_commands">5V output switched port control commands</a></li>
+			<li><a href="#gpio_ctrl_config_commands">GPIO control configuration commands</a></li>
+			<li><a href="#gpio_read_write_commands">GPIO Read/Write commands</a></li>
+			<li><a href="#ykush3_downstream_port_config_commands">Downstream ports configuration commands</a></li>
+			<li><a href="#ykush3_i2c_commands">I2C interface commands</a></li>
+			<li><a href="#ykush3_uart_commands">UART interface commands</a></li>
+			<li><a href="#ykush3_reset_commands">Reset command</a></li>
+			<li><a href="#ykush3_versioning_commands">Versioning commands</a></li>
+		</ul>
+	</div>
+	<div>
+		<p>Legend:</p>
+		<p>
+			&lt;&gt; Variable<br> 
+			[] Optional parameter<br>
+			&gt;  Command line
+		</p>
+	</div>
+	<div>
+		<!-- 1. Downstream port commands -->
+		<h2 id="downstream_port_commands">Downstream port commands</h2>
+		
+		<p>The structure of the downstream port commands is as follows.</p>
+
+		<p class="command_line">ykushcmd ykush3 [-s &lt;serial_number&gt;] -&lt;action&gt; &lt;port&gt;</p>
+
+		<p>Where:</p>
+		<table>
+			<tr>
+				<td>serial_number</td>
+				<td>Serial number of a board. This is an optional parameter useful for when multiple boards are attached to the same host.</td>
+			</tr>
+			<tr>
+				<td>action</td>
+				<td>
+					u &rarr; Turn ON/UP the downstream<br>
+					d &rarr; Turn OFF/DOWN the downstream<br>
+					g &rarr; Get downstream port status<br>
+					l &rarr; List boards attached<br>
+				</td>
+			</tr>
+			<tr>
+				<td>port</td>
+				<td>1, 2 or 3.</td>
+			</tr>
+		</table>
+
+
+		<p>Some examples:</p>
+
+		<p>Turn OFF the downstream port 1 (if only one YKUSH3 board is attached).</p>
+
+		<p class="command_line">ykushcmd ykush3 -d 1<p>
+
+		<p>Turn OFF the downstream port 1 of the board with serial number YKB00001.</p>
+
+		<p class="command_line">ykushcmd ykush3 -s YKB00001 -d 1</p>
+
+		<p>Get status of downstream port 2</p>
+
+		<p class="command_line">ykushcmd ykush3 -g 2<p>
+
+		<p>List attached YKUSH3 boards</p>
+
+		<p class="command_line">ykushcmd ykush3 -l</p>
+		
+		
+		
+		<!-- 2. 5V output switched port control commands -->
+		<h2 id="5V_output_port_commands">5V output switched port control commands</h2>
+
+		<p>The structure of commands:</p>
+
+		<p class="command_line">ykushcmd ykush3 [-s &lt;serial_number&gt;] -&lt;action&gt;</p>
+
+		<p>Where:</p>
+		<table>
+			<tr>
+				<td>serial_number</td>
+				<td>
+					Serial number of a board. 
+					This is an optional parameter useful for when multiple boards are attached to the same host.
+				</td>
+			</tr>
+			<tr>
+				<td>action</td>
+				<td>
+					on &rarr; Turn ON.<br>
+					off &rarr; Turn OFF.
+				</td>
+			</tr>
+		</table>
+
+		<p>Some examples:</p>
+
+		<p>Turn OFF the 5V Out port (if only one YKUSH3 board is attached).</p>
+
+		<p class="command_line">ykushcmd ykush3 -off</p>
+
+		<p>Turn ON the 5V Out port of the board with serial number YKB00001.</p>
+
+		<p class="command_line">ykushcmd ykush3 -s YKB00001 -on</p>
+
+		
+		
+
+		<!-- GPIO control configuration commands -->
+		<h2 id="gpio_ctrl_config_commands">GPIO control configuration commands</h2>
+		<p>
+			Commands to enable/disable the ability to control the downstream ports using the inputs of the board GPIO pins.
+		</p>
+
+		<p>Structure of commands:</p>
+		<p class="command_line">ykushcmd ykush3 [-s &lt;serial_number&gt;] --gpio &lt;action&gt;</p>
+
+		<p>Where:</p>
+		<table>
+			<tr>
+				<td>serial_number</td>
+				<td>
+					Serial number of a board. This is an optional parameter
+					useful for when multiple boards are attached to the 
+					same host.
+				</td>
+			</tr>
+			<tr>
+				<td>action</td>
+				<td>
+					enable &rarr; Enable the GPIO control of the downstream ports.<br>
+					disable &rarr; Disable the GPIO control of the downstream ports.
+				</td>
+			</tr>			
+		</table>
+
+		
+		
+		
+		
+		
+		<!-- GPIO Read/Write commands -->
+		<h2 id="gpio_read_write_commands">GPIO Read/Write commands</h2>
+		<p>
+			Commands to read/write the logical value of the GPIO pins.
+		</p>
+		<p>Structure of commands:</p>
+		<p class="command_line">ykushcmd ykush3 [-s &lt;serial_number&gt;] -&lt;action&gt; &lt;gpio&gt; &lt;value&gt;</p>
+
+		<p>Where:</p>
+		<table>
+			<tr>
+				<td>serial_number</td>
+				<td>
+					Serial number of a board. This is an optional parameter
+					useful for when multiple boards are attached to the 
+					same host.
+				</td>
+			</tr>
+			<tr>
+				<td>action</td>
+				<td>
+					w &rarr; Write to GPIO.<br>
+					r &rarr; Read from GPIO.
+				</td>
+			</tr>
+			<tr>
+				<td>gpio</td>
+				<td>
+					1 &rarr; GPIO 1.<br>
+					2 &rarr; GPIO 2.<br>
+					3 &rarr; GPIO 3.<br>
+				</td>
+			</tr>
+			<tr>
+				<td>value</td>
+				<td>
+					1 &rarr; Set GPIO to High.<br>
+					0 &rarr; Set GPIO to Low.
+				</td>
+			</tr>
+		</table>
+		
+		<p>Some examples:</p>
+
+		<p>Set GPIO 2 to high (1).</p>
+
+		<p class="command_line">ykushcmd ykush3 -w 2 1<p>
+
+		<p>Read the GPIO 2.<p>
+
+		<p class="command_line">ykushcmd ykush3 -r 2<p>
+                      
+		<p>NOTE: For Windows operating systems add the .exe extension when calling the ykushcmd command.</p>
+		
+		
+		
+		
+		
+		<!-- 4. Downstream ports configuration commands -->
+		<h2 id="ykush3_downstream_port_config_commands">Downstream ports configuration commands</h2>
+		<p>
+			Sets the default state of the downstream ports on power-on.
+		</p>
+		<p>Structure of commands:</p>
+		<p class="command_line">ykushcmd ykush3 [-s &lt;serial_number&gt;] -c &lt;port&gt; &lt;value&gt;</p>
+		<p>Where:</p>
+		<table>
+			<tr>
+				<td>serial_number</td>
+				<td>
+					Serial number of a board. This is an optional parameter
+					useful for when multiple boards are attached to the 
+					same host.
+				</td>
+			</tr>
+			<tr>
+				<td>port</td>
+				<td>1, 2 or 3.</td>
+			</tr>
+			<tr>
+				<td>value</td>
+				<td>
+					1 &rarr; ON state.
+					0 &rarr; OFF state.
+				</td>
+			</tr>
+		</table>
+		
+		<p>Some examples:</p>
+
+		<p>Set default state of downstream port 2 at power-on to ON.</p>
+		<p class="command_line">ykushcmd ykush3 -c 2 1<p>
+
+		<p>Set default state of downstream port 2 at power-on to OFF.</p>
+		<p class="command_line">ykushcmd ykush3 -c 2 0<p>
+
+		
+		
+		
+		
+		<!-- I2C control interface commands -->
+		<h2 id="ykush3_i2c_commands">I2C interface commands</h2>
+		<p>
+			YKUSH3 boards have an I2C interface alowing them to be connected to a
+			I2C bus and communicate to other devices in that bus.
+			The board can be configured in I2C slave mode, for other I2C devices to be
+			able to control the switching of the downstream ports, or in master mode
+			to be able to control other I2C devices.
+		</p>
+		<p>
+			To configure the board to operate I2C in slave mode and be controlable
+			by a master I2C device the user must enable the 
+			<i>i2C control interface</i> feature.
+		</p>
+		<p>
+			When the board is configure with I2C in master mode it provides a
+			USB to I2C gateway funcionality.
+			With this USB to I2C gateway functionality a user can communicate with
+			a slave I2C device, connected in the same I2C bus than YKUSH3 board,
+			from the command line of the PC using <i>ykushcmd</i> application.
+		</p>
+
+		<h3>Command usage</h3>
+		<p class="command_line">
+			ykushcmd ykush3 [OPTION]... 
+		</p>
+		<p>The following options are available:</p>
+		<table>
+			<tr>
+				<td>--i2c-enable-control</td>
+				<td>
+					Enables I2C as a control interface.
+					This will configure I2C in slave mode.
+				</td>
+			</tr>
+			<tr>
+				<td>--i2c-disable-control</td>
+				<td>
+					Disables I2C as a control interface.
+				</td>
+			</tr>
+			<tr>
+				<td>--i2c-enable-gateway</td>
+				<td>
+					Enables USB to I2C gateway functionality.
+					This will configure I2C in master mode.
+				</td>
+			</tr>
+			<tr>
+				<td>--i2c-disable-gateway</td>
+				<td>
+					Disables USB to I2C gateway functionality.
+				</td>
+			</tr>
+			<tr>
+				<td>--i2c-set-address &lt;address&gt;</td>
+				<td>
+					Set the board I2C address. 
+					The <i>address</i> should be in hexadecimal representation
+					with a <b>0x</b> prefix.
+					Example: 0x1F for 7-bit address 0011111.
+					This address is only used when the board is configured
+					with I2C in slave mode.
+				</td>
+			</tr>
+			<tr>
+				<td>--i2c-write &lt;dev_address&gt; &lt;num_bytes&gt; &lt;byte1&gt;...</td>
+				<td>
+					Writes <i>num_bytes</i> (byte1...) to the I2C
+					slave device with address <i>dev_address</i>.
+					<i>dev_address</i> is in hexadecimal representation 
+					with a <b>0x</b> prefix.
+					<i>num_bytes</i> is in decimal representation.
+					<i>byte1...byteN</i> is in hexadecimal representation 
+					with a <b>0x</b> prefix. 
+				</td>
+			</tr>
+			<tr>
+				<td>--i2c-read &lt;dev_address&gt; &lt;num_bytes&gt;</td>
+				<td>
+					Reads <i>num_bytes</i>from the I2C
+					slave device with address <i>dev_address</i>.  
+				</td>
+			</tr>
+			<tr>
+				<td>--i2c-usb-serial &lt;serial_number&gt;</td>
+				<td>
+					Serial number of the YKUSH3 board. 
+					This is an optional parameter useful for when multiple 
+					YKUSH3 boards are attached to the same host. 
+				</td>
+			</tr>
+		</table>
+
+		
+		<h3>Examples</h3>
+
+		<p>Enable I2C control interface:</p>
+		<p class="command_line">ykushcmd ykush3 --i2c-enable-control<p>
+
+		<p>Set the board I2C address to 0x1A:</p>
+		<p class="command_line">ykushcmd ykush3 --i2c-set-address 0x1A<p>
+		
+		<p>Write bytes 0x12 0xAA 0x2F to I2C device with address 0x07:</p>
+		<p class="command_line">ykushcmd ykush3 --i2c-write 0x07 3 0x12 0xAA 0x2F<p>
+		
+		
+		
+		
+		<!-- Reset command -->
+		<h2 id="ykush3_reset_commands">Reset command</h2>
+		<p>
+			Triggers a reset of the board.
+		</p>
+		<p>Structure of command:</p>
+		<p class="command_line">ykushcmd ykush3 [-s &lt;serial_number&gt;] --reset</p>
+		
+		<p>Examples:</p>
+
+		<p>Reset the attached board.</p>
+		<p class="command_line">ykushcmd ykush3 --reset<p>
+		
+		<p>Reset the attached board with serial number YK00001.</p>
+		<p class="command_line">ykushcmd ykush3 -s YK00001 --reset<p>
+		
+		
+		
+		
+		<!-- Versioning commands -->
+		<h2 id="ykush3_versioning_commands">Versioning commands</h2>
+		<p>
+			Get version of the firmware loaded in the board.
+		</p>
+		<h3>Command usage</h3>
+		<p class="command_line">
+			ykushcmd ykush3 [OPTION]
+		</p>
+		<p>The following options are available:</p>
+		<table>
+			<tr>
+				<td>--version-bootloader</td>
+				<td>Get bootloader version from board.</td>
+			</tr>
+			<tr>
+				<td>--version-firmware</td>
+				<td>Get firmware version from board.</td>
+			</tr>
+		</table>
+
+		<h3>Examples</h3>
+
+		<p>Get bootloader version:</p>
+		<p class="command_line">ykushcmd ykush3 --version-bootloader<p>
+		
+		<p>Get firmware version:</p>
+		<p class="command_line">ykushcmd ykush3 --version-firmware<p>
+
+	</div>
+	
+	
+	<!--
+		#ykush3_man_important_links
+	-->
+	<h1 id="ykush3_man_important_links">Important links</h1>
+	<div>
+		<ul>
+			<li><a class="inlineLink" href="https://www.yepkit.com/product/300110/YKUSH3" target="_blank">YKUSH3 product page</a></li>
+			<li><a class="inlineLink" href="https://www.yepkit.com/learn/tutorial/setup_guide/ykush3-i2c-control-interface" target="_blank">How to control the YKUSH3 boards using the I2C interface</a></li>
+		</ul>
+	</div>
+	
+	
+	
+</div>
+

+ 173 - 0
doc/reference-manual-ykushcmd/ykushcmd-reference-ykush.html

@@ -0,0 +1,173 @@
+<h1>YKUSH Board Commands</h1>
+
+<div class="reference_page_toc">
+        <ul>
+                <li><a href="#command_overview">Command overview</a></li>
+                <li><a href="#list_attached_example">List attached boards</a></li>
+                <li><a href="#switch_command_example">Downstream port On/Off switching</a></li>
+                <li><a href="#switch_state_command_example">Port switching state</a></li>      
+        </ul>
+</div>
+
+
+
+
+<h2 id="command_overview">Command overview</h2>
+<p>YKUSH board commands have the following structure.</p>
+<p class="command_line">ykushcmd ykush [-s serial_number] [OPTION]</p>
+<p>Where:</p>
+<table cellpadding="10">
+        <tr>
+                <td width="30%" valign="top">-s serial_number</td>
+                <td>
+                        Board serial number to which the command is addressed.
+                        When multiple YKUSH boards are connected to a host, this option should be used
+                        to specify the board. If more than one board is connected and this option is not
+                        provided the command will be sent to the first board in the USB enumeration list.
+                </td>
+        </tr>
+        <tr>
+                <td valign="top">-l</td>
+                <td>
+                        List attached YKUSH boards.
+                        The serial number of each board attached to the host will be displayed.
+                </td>
+        </tr>
+        <tr>
+                <td valign="top">-d 1|2|3|a</td>
+                <td>
+                        Power Down/Off downstream port with the number provided.
+                        If <i>a</i> is provided as the port number then all ports will be switched.
+                </td>
+        </tr>
+        <tr>
+                <td valign="top">-u 1|2|3|a</td>
+                <td>
+                        Power Up/On downstream port with the number provided.
+                        If <i>a</i> is provided as the port number then all ports will be switched.
+                </td>
+        </tr>
+        <tr>
+                <td>-g 1|2|3</td>
+                <td>
+                        Get state of downstream port.
+                </td>
+        </tr>
+</table>
+
+
+
+<h2 id="list_attached_example">List attached boards</h2>
+<p>
+        The <b>[-l]</b> option is used to list all attached YKUSH boards.
+        All YKUSH board have unique serial numbers which are displayed when this option is used.
+</p>
+<pre>
+<code class="language-bash">
+#list the serial number for each of the attached YKUSH boards
+$ ykushcmd ykush -l
+
+Attached YKUSH Boards:
+1. Board found with serial number: YK17125
+2. Board found with serial number: YK21493
+</code>
+</pre>
+                
+
+
+<h2 id="switch_command_example">Downstream port On/Off switching</h2>
+<p>
+        When only one YKUSH board is attached to the host the <b>[-s serial_number]</b> option is not required.
+        Bellow are some examples.
+</p>
+<pre>
+<code class="language-bash">
+#power-down downstream port 1
+$ ykushcmd ykush -d 1
+
+#power-down downstream port 2
+$ ykushcmd ykush -d 2
+
+#power down downstream port 3
+$ ykushcmd ykush -d 3
+
+#power-down all three downstream ports
+$ ykushcmd ykush -d a
+
+#power-up downstream port 1
+$ ykushcmd ykush -u 1
+
+#power-up downstream port 2
+$ ykushcmd ykush -u 2
+
+#power-up downstream port 3
+$ ykushcmd ykush -u 3
+
+#power-up all three downstream ports
+$ ykushcmd ykush -u a
+</code>
+</pre>
+
+<p>
+        If more than one YKUSH board is attached to the host the <b>[-s serial_number]</b> option should be used.
+        Bellow are some examples.
+</p>
+<pre>
+<code class="language-bash">
+#list the serial number for each of the attached YKUSH boards
+$ ykushcmd ykush -l
+
+Attached YKUSH Boards:
+1. Board found with serial number: YK17125
+2. Board found with serial number: YK21493
+
+#power-down downstream port 1 of the board with serial number YK17125
+$ ykushcmd ykush -s YK17125 -d 1
+
+#power-down downstream port 1 of the board with serial number YK21493
+$ ykushcmd ykush -s YK21493 -d 1
+
+#power-down downstream port 3
+$ ykushcmd ykush -d 3
+
+#power-down all three downstream ports of the board with serial number YK21493
+$ ykushcmd ykush -s YK21493 -d a
+</code>
+</pre>
+
+
+<h2 id="switch_state_command_example">Port switching state</h2>
+<p>
+        The current switching state of each downstream port can be fetched from the YKUSH board using the <b>[-g 1|2|3]</b> option.
+</p>
+<pre>
+<code class="language-bash">
+#State of downstream port 1
+$ ykushcmd ykush -g 1
+
+Downstream port 1 is ON
+
+#power-down downstream port 1
+$ ykushcmd ykush -d 1
+
+#State of downstream port 1
+$ ykushcmd ykush -g 1
+
+Downstream port 1 is OFF
+
+#list the serial number for each of the attached YKUSH boards
+$ ykushcmd ykush -l
+
+Attached YKUSH Boards:
+1. Board found with serial number: YK17125
+2. Board found with serial number: YK21493
+
+#State of downstream port 1 of the board with serial number YK17125
+$ ykushcmd ykush -s YK17125 -g 1
+
+Downstream port 1 is OFF
+
+#power-up downstream port 1 of the board with serial number YK17125
+$ ykushcmd ykush -s YK17125 -u 1
+</code>
+</pre>

+ 243 - 0
doc/reference-manual-ykushcmd/ykushcmd-reference-ykush3.html

@@ -0,0 +1,243 @@
+<h1>YKUSH3 Board Commands</h1>
+
+<div class="reference_page_toc">
+        <ul>
+                <li><a href="#command_overview">Command overview</a></li>
+                <li><a href="#list_attached_example">List attached boards</a></li>
+                <li><a href="#switch_command_example">Downstream port On/Off switching</a></li>
+                <li><a href="#switch_state_command_example">Port switching state</a></li>  
+                <li><a href="#gpio_read_write_command_example">GPIO read/write</a></li>
+                <li><a href="#reset_command_example">Reset/reboot board</a></li>    
+        </ul>
+</div>
+
+
+
+<h2 id="command_overview">Command overview</h2>
+<p>YKUSH3 board commands have the following structure.</p>
+<p class="command_line">ykushcmd ykush3 [-s serial_number] [OPTION]</p>
+<p>Where:</p>
+<table cellpadding="10">
+        <tr>
+                <td width="30%" valign="top">-s serial_number</td>
+                <td>
+                        Board serial number to which the command is addressed.
+                        When multiple YKUSH boards are connected to a host, this option should be used
+                        to specify the board. If more than one board is connected and this option is not
+                        provided the command will be sent to the first board in the USB enumeration list.
+                </td>
+        </tr>
+        <tr>
+                <td valign="top">-l</td>
+                <td>
+                        List attached YKUSH3 boards.
+                        The serial number of each board attached to the host will be displayed.
+                </td>
+        </tr>
+        <tr>
+                <td valign="top">-d 1|2|3|a</td>
+                <td>
+                        Power Down/Off downstream port with the number provided.
+                        If <i>a</i> is provided as the port number then all ports will be switched.
+                </td>
+        </tr>
+        <tr>
+                <td valign="top">-u 1|2|3|a</td>
+                <td>
+                        Power Up/On downstream port with the number provided.
+                        If <i>a</i> is provided as the port number then all ports will be switched.
+                </td>
+        </tr>
+        <tr>
+                <td>-g 1|2|3</td>
+                <td>
+                        Get port state.
+                </td>
+        </tr>
+        <tr>
+                <td valign="top">-on</td>
+                <td>
+                        Switch On the 5V output power port.
+                </td>
+        </tr>
+        <tr>
+                <td valign="top">-off</td>
+                <td>
+                        Switch Off the 5V output power port.
+                </td>
+        </tr>
+        <tr>
+                <td valign="top">-r 1|2|3</td>
+                <td>
+                        Read GPIO with the number provided (1, 2 or 3).
+                </td>
+        </tr>
+        <tr>
+                <td valign="top">-w 1|2|3 0|1</td>
+                <td>
+                        Write to the GPIO with the number provided (1, 2 or 3).
+                        Writing a value of <b>1</b> or <b>0</b> will drive the GPIO to logical <b>high</b> or <b>low</b>, respectively.
+                </td>
+        </tr>
+        <tr>
+                <td valign="top">--reset</td>
+                <td>
+                        Resets (reboot) the YKUSH3 board.
+                </td>
+        </tr>
+</table>
+
+
+
+<h2 id="list_attached_example">List attached boards</h2>
+<p>
+        The <b>[-l]</b> option is used to list all attached YKUSH3 boards.
+        All YKUSH board have unique serial numbers which are displayed when this option is used.
+</p>
+<pre>
+<code class="language-bash">
+#list the serial number for each of the attached YKUSH3 boards
+$ ykushcmd ykush3 -l
+
+Attached YKUSH3 Boards:
+1. Board found with serial number: YK17125
+2. Board found with serial number: YK21493
+</code>
+</pre>
+                
+
+
+<h2 id="switch_command_example">Downstream port On/Off switching</h2>
+<p>
+        When only one YKUSH3 board is attached to the host the <b>[-s serial_number]</b> option is not required.
+        Bellow are some examples.
+</p>
+<pre>
+<code class="language-bash">
+#power-down downstream port 1
+$ ykushcmd ykush3 -d 1
+
+#power-down downstream port 2
+$ ykushcmd ykush3 -d 2
+
+#power down downstream port 3
+$ ykushcmd ykush3 -d 3
+
+#power-down all three downstream ports
+$ ykushcmd ykush3 -d a
+
+#power-up downstream port 1
+$ ykushcmd ykush3 -u 1
+
+#power-up downstream port 2
+$ ykushcmd ykush3 -u 2
+
+#power-up downstream port 3
+$ ykushcmd ykush3 -u 3
+
+#power-up all three downstream ports
+$ ykushcmd ykush3 -u a
+</code>
+</pre>
+
+<p>
+        If more than one YKUSH3 board is attached to the host the <b>[-s serial_number]</b> option should be used.
+        Bellow are some examples.
+</p>
+<pre>
+<code class="language-bash">
+#list the serial number for each of the attached YKUSH3 boards
+$ ykushcmd ykush3 -l
+
+Attached YKUSH3 Boards:
+1. Board found with serial number: YK17125
+2. Board found with serial number: YK21493
+
+#power-down downstream port 1 of the board with serial number YK17125
+$ ykushcmd ykush3 -s YK17125 -d 1
+
+#power-down downstream port 1 of the board with serial number YK21493
+$ ykushcmd ykush3 -s YK21493 -d 1
+
+#power-down downstream port 3
+$ ykushcmd ykush3 -d 3
+
+#power-down all three downstream ports of the board with serial number YK21493
+$ ykushcmd ykush3 -s YK21493 -d a
+</code>
+</pre>
+
+
+<h2 id="switch_state_command_example">Port switching state</h2>
+<p>
+        The current switching state of each downstream port can be fetched from the YKUSH3 board using the <b>[-g 1|2|3]</b> option.
+</p>
+<pre>
+<code class="language-bash">
+#State of downstream port 1
+$ ykushcmd ykush3 -g 1
+
+Downstream port 1 is ON
+
+#power-down downstream port 1
+$ ykushcmd ykush3 -d 1
+
+#State of downstream port 1
+$ ykushcmd ykush3 -g 1
+
+Downstream port 1 is OFF
+
+#list the serial number for each of the attached YKUSH boards
+$ ykushcmd ykush3 -l
+
+Attached YKUSH Boards:
+1. Board found with serial number: YK17125
+2. Board found with serial number: YK21493
+
+#State of downstream port 1 of the board with serial number YK17125
+$ ykushcmd ykush3 -s YK17125 -g 1
+
+Downstream port 1 is OFF
+
+#power-up downstream port 1 of the board with serial number YK17125
+$ ykushcmd ykush3 -s YK17125 -u 1
+</code>
+</pre>
+
+
+
+<h2 id="gpio_read_write_command_example">GPIO read/write</h2>
+<p>
+        The <b>[-r|-w]</b> option is used to read from or write to a GPIO.
+</p>
+<pre>
+<code class="language-bash">
+#Writing a 0 to a GPIO will drive it to logical low (0V).
+#Example of writing value 0 to GPIO 1
+$ ykushcmd ykush3 -w 1 0
+
+#Writing a 1 to a GPIO will drive it to logical high (3.3V).
+#Example of writing value 1 to GPIO 1
+$ ykushcmd ykush3 -w 1 1
+
+#Example of writing value 1 to GPIO 2
+$ ykushcmd ykush3 -w 2 1
+
+#Reading from a GPIO will get the digital value of that pin,
+#0 if Low and 1 if High.
+#Example of reading from GPIO 3
+$ ykushcmd ykush3 -r 3
+</code>
+</pre>
+
+
+<h2 id="reset_command_example">Reset/reboot board</h2>
+<p>
+        The <b>[--reset]</b> option is used to reset (reboot) the board.
+</p>
+<pre>
+<code class="language-bash">
+#Example of resetting YKUSH3
+$ ykushcmd ykush3 --reset
+</code>
+</pre>

+ 145 - 0
doc/reference-manual-ykushcmd/ykushcmd-reference-ykushxs.html

@@ -0,0 +1,145 @@
+<h1>YKUSHXS Board Commands</h1>
+
+<div class="reference_page_toc">
+        <ul>
+                <li><a href="#command_overview">Command overview</a></li>
+                <li><a href="#list_attached_example">List attached boards</a></li>
+                <li><a href="#switch_command_example">Downstream port On/Off switching</a></li>
+                <li><a href="#switch_state_command_example">Port switching state</a></li>      
+        </ul>
+</div>
+
+
+
+
+<h2 id="command_overview">Command overview</h2>
+<p>YKUSHXS board commands have the following structure.</p>
+<p class="command_line">ykushcmd ykushxs [-s serial_number] [OPTION]</p>
+<p>Where:</p>
+<table cellpadding="10">
+        <tr>
+                <td width="30%" valign="top">-s serial_number</td>
+                <td>
+                        Board serial number to which the command is addressed.
+                        When multiple YKUSH boards are connected to a host, this option should be used
+                        to specify the board. If more than one board is connected and this option is not
+                        provided the command will be sent to the first board in the USB enumeration list.
+                </td>
+        </tr>
+
+        <tr>
+                <td valign="top">-l</td>
+                <td>
+                        List attached YKUSHXS boards.
+                        The serial number of each board attached to the host will be displayed.
+                </td>
+        </tr>
+        <tr>
+                <td>-d</td>
+                <td>
+                        Power Down/Off the downstream port.
+                </td>
+        </tr>
+        <tr>
+                <td>-u</td>
+                <td>
+                        Power Up/On the downstream port.
+                </td>
+        </tr>
+        <tr>
+                <td>-g</td>
+                <td>
+                        Get downstream port state.
+                </td>
+        </tr>
+</table>
+
+
+
+<h2 id="list_attached_example">List attached boards</h2>
+<p>
+        The <b>[-l]</b> option is used to list all attached YKUSHXS boards.
+        All YKUSH board have unique serial numbers which are displayed when this option is used.
+</p>
+<pre>
+<code class="language-bash">
+#list the serial number for each of the attached YKUSHXS boards
+$ ykushcmd ykushxs -l
+
+Attached YKUSHXS Boards:
+1. Board found with serial number: YK17125
+2. Board found with serial number: YK21493
+</code>
+</pre>
+                
+
+
+<h2 id="switch_command_example">Downstream port On/Off switching</h2>
+<p>
+        When only one YKUSHXS board is attached to the host the <b>[-s serial_number]</b> option is not required.
+        Bellow are some examples.
+</p>
+<pre>
+<code class="language-bash">
+#power-down the downstream port
+$ ykushcmd ykushxs -d
+
+#power-up the downstream port 
+$ ykushcmd ykushxs -u
+</code>
+</pre>
+
+<p>
+        If more than one YKUSHXS board is attached to the host the <b>[-s serial_number]</b> option should be used.
+        Bellow are some examples.
+</p>
+<pre>
+<code class="language-bash">
+#list the serial number for each of the attached YKUSHXS boards
+$ ykushcmd ykushxs -l
+
+Attached YKUSHXS Boards:
+1. Board found with serial number: YK17125
+2. Board found with serial number: YK21493
+
+#power-down the downstream port of the board with serial number YK17125
+$ ykushcmd ykushxs -s YK17125 -d
+</code>
+</pre>
+
+
+<h2 id="switch_state_command_example">Port switching state</h2>
+<p>
+        The current switching state of each downstream port can be fetched from the YKUSH board using the <b>[-g 1|2|3]</b> option.
+</p>
+<pre>
+<code class="language-bash">
+#State of the downstream port
+$ ykushcmd ykushxs -g
+
+Downstream port is ON
+
+#power-down the downstream port
+$ ykushcmd ykushxs -d
+
+#State of downstream port
+$ ykushcmd ykushxs -g
+
+Downstream port is OFF
+
+#list the serial number for each of the attached YKUSHXS boards
+$ ykushcmd ykushxs -l
+
+Attached YKUSHXS Boards:
+1. Board found with serial number: YK17125
+2. Board found with serial number: YK21493
+
+#State of the downstream port for the board with serial number YK17125
+$ ykushcmd ykushxs -s YK17125 -g
+
+Downstream port is OFF
+
+#power-up the downstream port of the board with serial number YK17125
+$ ykushcmd ykushxs -s YK17125 -u
+</code>
+</pre>

+ 136 - 0
doc/ykush3_help.txt

@@ -0,0 +1,136 @@
+--------------------------------------------------------------------------
+
+            YKUSH 3 Command Appplication Help
+
+--------------------------------------------------------------------------
+
+Legend:
+<> Variable 
+[] Optional parameter
+>  Command line
+
+
+
+
+1. Downstream port commands
+---------------------------
+
+The structure of the downstream port commands is as follows.
+
+ykushcmd ykush3 [-s <serial_number>] -<action> <port>
+
+Where:
+
+serial_number               Serial number of a board. This is an optional parameter
+                            useful for when multiple boards are attached to the 
+                            same host.
+                            
+action                      u -> Turn ON/UP the downstream.
+                            d -> Turn OFF/DOWN the downstream.
+                            g -> Get downstream port status.
+                            l -> List boards attached.
+                            
+port                        1, 2 or 3.
+
+
+
+Some examples:
+
+Turn OFF the downstream port 1 (if only one YKUSH3 board is attached).
+
+> ykushcmd ykush3 -d 1
+
+Turn OFF the downstream port 1 of the board with serial number YKB00001.
+
+> ykushcmd ykush3 -s YKB00001 -d 1
+
+Get status of downstream port 2
+
+> ykushcmd ykush3 -g 2
+
+List attached YKUSH3 boards
+
+> ykushcmd ykush3 -l
+
+
+
+
+
+2. 5V output switched port control commands
+-------------------------------------------
+
+The structure of commands.
+
+ykushcmd ykush3 [-s <serial_number>] -<action>
+
+Where:
+
+serial_number               Serial number of a board. This is an optional parameter
+                            useful for when multiple boards are attached to the 
+                            same host.
+                            
+action                      on -> Turn ON.
+                            off -> Turn OFF.
+                            
+
+
+Some examples:
+
+Turn OFF the 5V Out port (if only one YKUSH3 board is attached).
+
+> ykushcmd ykush3 -off
+
+Turn ON the 5V Out port of the board with serial number YKB00001.
+
+> ykushcmd ykush3 -s YKB00001 -on
+
+
+
+
+3. IO control commands
+----------------------
+
+Structure of commands.
+
+ykushcmd ykush3 [-s <serial_numer>] -<action> <port> [<value>]
+
+Where:
+
+serial_number               Serial number of a board. This is an optional parameter
+                            useful for when multiple boards are attached to the 
+                            same host.
+                            
+action                      w -> Write.
+                            r -> Turn OFF. When Read action the command will return
+                            the read value (1/0). Also in this option, the
+                            <value> parameter is not required.
+            
+port                        1, 2 or 3.
+                            
+value                       1 -> Set the I/O to digital High Level
+                            0 -> Set the I/O to digital Low Level
+                            
+
+
+Some examples:
+
+Set GPIO 2 to high (1).
+
+> ykushcmd ykush3 -w 2 1
+
+Read the GPIO 2.
+
+> ykushcmd ykush3 -r 2
+
+
+                                        
+NOTE: For Windows operating systems add the .exe extension when calling the ykushcmd command.
+
+
+
+
+
+
+
+
+

+ 49 - 0
doc/ykushxs_help.txt

@@ -0,0 +1,49 @@
+--------------------------------------------------------------------------
+
+            YKUSH XS Command Appplication Help
+
+--------------------------------------------------------------------------
+
+
+Available Commands:
+-------------------
+
+ykushcmd ykushxs -d                     Turns DOWN the downstream port
+
+
+ykushcmd ykushxs -u                     Turns UP the downstream port
+
+
+ykushcmd ykushxs -g                     Obtains the switching status of
+                                        the downstream port
+                                        
+
+ykushcmd ykushxs -l                     Lists all currently attached
+                                        YKUSH XS boards
+                                        
+
+ykushcmd ykushxs -s serial_number -d    Turns DOWN the downstream port for
+                                        the board with the specified
+                                        serial number
+                                        
+
+ykushcmd ykushxs -s serial_number -u    Turns UP the downstream port for
+                                        the board with the specified
+                                        serial number
+                                        
+
+ykushcmd ykushxs -s serial_number -g    Obtains the switching status of
+                                        port for the board with the
+                                        specified serial number
+
+                                        
+NOTE: For Windows operating systems add the .exe extension when calling the ykushcmd command. For example for disconnecting the downstream port the command is as follows.
+
+ykushcmd.exe ykushxs -d
+
+
+
+
+
+
+

+ 0 - 5
install.sh

@@ -3,10 +3,5 @@
 echo installing ykush command...
 sudo cp -f bin/ykushcmd /usr/bin
 
-echo installing shared libraries...
-sudo cp -f ykushcmd/linux/libhidapi-hidraw.so /usr/lib/libhidapi-hidraw.so
-sudo cp -f ykushcmd/linux/libhidapi-hidraw.so /usr/lib/libhidapi-hidraw.so.0
 
-sudo cp -f ykushcmd/linux/libhidapi-libusb.so /usr/lib/libhidapi-libusb.so
-sudo cp -f ykushcmd/linux/libhidapi-libusb.so /usr/lib/libhidapi-libusb.so.0
 

+ 435 - 0
learn/html/ykushcmd-reference-manual-ykush3.html

@@ -0,0 +1,435 @@
+<div class="reference_software_manual_version">
+	This manual page refers to software version <b>v1.2.0</b>.
+</div>
+
+<div class="reference_software_manual_index">
+	<ul>
+		<li><a href="#command_list">Command list</a></li>
+		<li><a href="#ykush3_man_important_links">Important links</a></li>
+		
+	</ul>
+</div>
+
+<div class="reference_software_manual_body">
+
+	<!-- 
+		COMMAND LIST 
+	-->
+	<h1 id="command_list">Command list</h1>
+	<div>
+		<ul>
+			<li><a href="#downstream_port_commands">Downstream port commands</a></li>
+			<li><a href="#5V_output_port_commands">5V output switched port control commands</a></li>
+			<li><a href="#gpio_ctrl_config_commands">GPIO control configuration commands</a></li>
+			<li><a href="#gpio_read_write_commands">GPIO Read/Write commands</a></li>
+			<li><a href="#ykush3_downstream_port_config_commands">Downstream ports configuration commands</a></li>
+			<li><a href="#ykush3_i2c_commands">I2C interface commands</a></li>
+			<li><a href="#ykush3_uart_commands">UART interface commands</a></li>
+			<li><a href="#ykush3_reset_commands">Reset command</a></li>
+			<li><a href="#ykush3_versioning_commands">Versioning commands</a></li>
+		</ul>
+	</div>
+	<div>
+		<p>Legend:</p>
+		<p>
+			&lt;&gt; Variable<br> 
+			[] Optional parameter<br>
+			&gt;  Command line
+		</p>
+	</div>
+	<div>
+		<!-- 1. Downstream port commands -->
+		<h2 id="downstream_port_commands">Downstream port commands</h2>
+		
+		<p>The structure of the downstream port commands is as follows.</p>
+
+		<p class="command_line">ykushcmd ykush3 [-s &lt;serial_number&gt;] -&lt;action&gt; &lt;port&gt;</p>
+
+		<p>Where:</p>
+		<table>
+			<tr>
+				<td>serial_number</td>
+				<td>Serial number of a board. This is an optional parameter useful for when multiple boards are attached to the same host.</td>
+			</tr>
+			<tr>
+				<td>action</td>
+				<td>
+					u &rarr; Turn ON/UP the downstream<br>
+					d &rarr; Turn OFF/DOWN the downstream<br>
+					g &rarr; Get downstream port status<br>
+					l &rarr; List boards attached<br>
+				</td>
+			</tr>
+			<tr>
+				<td>port</td>
+				<td>1, 2 or 3.</td>
+			</tr>
+		</table>
+
+
+		<p>Some examples:</p>
+
+		<p>Turn OFF the downstream port 1 (if only one YKUSH3 board is attached).</p>
+
+		<p class="command_line">ykushcmd ykush3 -d 1<p>
+
+		<p>Turn OFF the downstream port 1 of the board with serial number YKB00001.</p>
+
+		<p class="command_line">ykushcmd ykush3 -s YKB00001 -d 1</p>
+
+		<p>Get status of downstream port 2</p>
+
+		<p class="command_line">ykushcmd ykush3 -g 2<p>
+
+		<p>List attached YKUSH3 boards</p>
+
+		<p class="command_line">ykushcmd ykush3 -l</p>
+		
+		
+		
+		<!-- 2. 5V output switched port control commands -->
+		<h2 id="5V_output_port_commands">5V output switched port control commands</h2>
+
+		<p>The structure of commands:</p>
+
+		<p class="command_line">ykushcmd ykush3 [-s &lt;serial_number&gt;] -&lt;action&gt;</p>
+
+		<p>Where:</p>
+		<table>
+			<tr>
+				<td>serial_number</td>
+				<td>
+					Serial number of a board. 
+					This is an optional parameter useful for when multiple boards are attached to the same host.
+				</td>
+			</tr>
+			<tr>
+				<td>action</td>
+				<td>
+					on &rarr; Turn ON.<br>
+					off &rarr; Turn OFF.
+				</td>
+			</tr>
+		</table>
+
+		<p>Some examples:</p>
+
+		<p>Turn OFF the 5V Out port (if only one YKUSH3 board is attached).</p>
+
+		<p class="command_line">ykushcmd ykush3 -off</p>
+
+		<p>Turn ON the 5V Out port of the board with serial number YKB00001.</p>
+
+		<p class="command_line">ykushcmd ykush3 -s YKB00001 -on</p>
+
+		
+		
+
+		<!-- GPIO control configuration commands -->
+		<h2 id="gpio_ctrl_config_commands">GPIO control configuration commands</h2>
+		<p>
+			Commands to enable/disable the ability to control the downstream ports using the inputs of the board GPIO pins.
+		</p>
+
+		<p>Structure of commands:</p>
+		<p class="command_line">ykushcmd ykush3 [-s &lt;serial_number&gt;] --gpio &lt;action&gt;</p>
+
+		<p>Where:</p>
+		<table>
+			<tr>
+				<td>serial_number</td>
+				<td>
+					Serial number of a board. This is an optional parameter
+					useful for when multiple boards are attached to the 
+					same host.
+				</td>
+			</tr>
+			<tr>
+				<td>action</td>
+				<td>
+					enable &rarr; Enable the GPIO control of the downstream ports.<br>
+					disable &rarr; Disable the GPIO control of the downstream ports.
+				</td>
+			</tr>			
+		</table>
+
+		
+		
+		
+		
+		
+		<!-- GPIO Read/Write commands -->
+		<h2 id="gpio_read_write_commands">GPIO Read/Write commands</h2>
+		<p>
+			Commands to read/write the logical value of the GPIO pins.
+		</p>
+		<p>Structure of commands:</p>
+		<p class="command_line">ykushcmd ykush3 [-s &lt;serial_number&gt;] -&lt;action&gt; &lt;gpio&gt; &lt;value&gt;</p>
+
+		<p>Where:</p>
+		<table>
+			<tr>
+				<td>serial_number</td>
+				<td>
+					Serial number of a board. This is an optional parameter
+					useful for when multiple boards are attached to the 
+					same host.
+				</td>
+			</tr>
+			<tr>
+				<td>action</td>
+				<td>
+					w &rarr; Write to GPIO.<br>
+					r &rarr; Read from GPIO.
+				</td>
+			</tr>
+			<tr>
+				<td>gpio</td>
+				<td>
+					1 &rarr; GPIO 1.<br>
+					2 &rarr; GPIO 2.<br>
+					3 &rarr; GPIO 3.<br>
+				</td>
+			</tr>
+			<tr>
+				<td>value</td>
+				<td>
+					1 &rarr; Set GPIO to High.<br>
+					0 &rarr; Set GPIO to Low.
+				</td>
+			</tr>
+		</table>
+		
+		<p>Some examples:</p>
+
+		<p>Set GPIO 2 to high (1).</p>
+
+		<p class="command_line">ykushcmd ykush3 -w 2 1<p>
+
+		<p>Read the GPIO 2.<p>
+
+		<p class="command_line">ykushcmd ykush3 -r 2<p>
+                      
+		<p>NOTE: For Windows operating systems add the .exe extension when calling the ykushcmd command.</p>
+		
+		
+		
+		
+		
+		<!-- 4. Downstream ports configuration commands -->
+		<h2 id="ykush3_downstream_port_config_commands">Downstream ports configuration commands</h2>
+		<p>
+			Sets the default state of the downstream ports on power-on.
+		</p>
+		<p>Structure of commands:</p>
+		<p class="command_line">ykushcmd ykush3 [-s &lt;serial_number&gt;] -c &lt;port&gt; &lt;value&gt;</p>
+		<p>Where:</p>
+		<table>
+			<tr>
+				<td>serial_number</td>
+				<td>
+					Serial number of a board. This is an optional parameter
+					useful for when multiple boards are attached to the 
+					same host.
+				</td>
+			</tr>
+			<tr>
+				<td>port</td>
+				<td>1, 2 or 3.</td>
+			</tr>
+			<tr>
+				<td>value</td>
+				<td>
+					1 &rarr; ON state.
+					0 &rarr; OFF state.
+				</td>
+			</tr>
+		</table>
+		
+		<p>Some examples:</p>
+
+		<p>Set default state of downstream port 2 at power-on to ON.</p>
+		<p class="command_line">ykushcmd ykush3 -c 2 1<p>
+
+		<p>Set default state of downstream port 2 at power-on to OFF.</p>
+		<p class="command_line">ykushcmd ykush3 -c 2 0<p>
+
+		
+		
+		
+		
+		<!-- I2C control interface commands -->
+		<h2 id="ykush3_i2c_commands">I2C interface commands</h2>
+		<p>
+			YKUSH3 boards have an I2C interface alowing them to be connected to a
+			I2C bus and communicate to other devices in that bus.
+			The board can be configured in I2C slave mode, for other I2C devices to be
+			able to control the switching of the downstream ports, or in master mode
+			to be able to control other I2C devices.
+		</p>
+		<p>
+			To configure the board to operate I2C in slave mode and be controlable
+			by a master I2C device the user must enable the 
+			<i>i2C control interface</i> feature.
+		</p>
+		<p>
+			When the board is configure with I2C in master mode it provides a
+			USB to I2C gateway funcionality.
+			With this USB to I2C gateway functionality a user can communicate with
+			a slave I2C device, connected in the same I2C bus than YKUSH3 board,
+			from the command line of the PC using <i>ykushcmd</i> application.
+		</p>
+
+		<h3>Command usage</h3>
+		<p class="command_line">
+			ykushcmd ykush3 [OPTION]... 
+		</p>
+		<p>The following options are available:</p>
+		<table>
+			<tr>
+				<td>--i2c-enable-control</td>
+				<td>
+					Enables I2C as a control interface.
+					This will configure I2C in slave mode.
+				</td>
+			</tr>
+			<tr>
+				<td>--i2c-disable-control</td>
+				<td>
+					Disables I2C as a control interface.
+				</td>
+			</tr>
+			<tr>
+				<td>--i2c-enable-gateway</td>
+				<td>
+					Enables USB to I2C gateway functionality.
+					This will configure I2C in master mode.
+				</td>
+			</tr>
+			<tr>
+				<td>--i2c-disable-gateway</td>
+				<td>
+					Disables USB to I2C gateway functionality.
+				</td>
+			</tr>
+			<tr>
+				<td>--i2c-set-address &lt;address&gt;</td>
+				<td>
+					Set the board I2C address. 
+					The <i>address</i> should be in hexadecimal representation
+					with a <b>0x</b> prefix.
+					Example: 0x1F for 7-bit address 0011111.
+					This address is only used when the board is configured
+					with I2C in slave mode.
+				</td>
+			</tr>
+			<tr>
+				<td>--i2c-write &lt;dev_address&gt; &lt;num_bytes&gt; &lt;byte1&gt;...</td>
+				<td>
+					Writes <i>num_bytes</i> (byte1...) to the I2C
+					slave device with address <i>dev_address</i>.
+					<i>dev_address</i> is in hexadecimal representation 
+					with a <b>0x</b> prefix.
+					<i>num_bytes</i> is in decimal representation.
+					<i>byte1...byteN</i> is in hexadecimal representation 
+					with a <b>0x</b> prefix. 
+				</td>
+			</tr>
+			<tr>
+				<td>--i2c-read &lt;dev_address&gt; &lt;num_bytes&gt;</td>
+				<td>
+					Reads <i>num_bytes</i>from the I2C
+					slave device with address <i>dev_address</i>.  
+				</td>
+			</tr>
+			<tr>
+				<td>--i2c-usb-serial &lt;serial_number&gt;</td>
+				<td>
+					Serial number of the YKUSH3 board. 
+					This is an optional parameter useful for when multiple 
+					YKUSH3 boards are attached to the same host. 
+				</td>
+			</tr>
+		</table>
+
+		
+		<h3>Examples</h3>
+
+		<p>Enable I2C control interface:</p>
+		<p class="command_line">ykushcmd ykush3 --i2c-enable-control<p>
+
+		<p>Set the board I2C address to 0x1A:</p>
+		<p class="command_line">ykushcmd ykush3 --i2c-set-address 0x1A<p>
+		
+		<p>Write bytes 0x12 0xAA 0x2F to I2C device with address 0x07:</p>
+		<p class="command_line">ykushcmd ykush3 --i2c-write 0x07 3 0x12 0xAA 0x2F<p>
+		
+		
+		
+		
+		<!-- Reset command -->
+		<h2 id="ykush3_reset_commands">Reset command</h2>
+		<p>
+			Triggers a reset of the board.
+		</p>
+		<p>Structure of command:</p>
+		<p class="command_line">ykushcmd ykush3 [-s &lt;serial_number&gt;] --reset</p>
+		
+		<p>Examples:</p>
+
+		<p>Reset the attached board.</p>
+		<p class="command_line">ykushcmd ykush3 --reset<p>
+		
+		<p>Reset the attached board with serial number YK00001.</p>
+		<p class="command_line">ykushcmd ykush3 -s YK00001 --reset<p>
+		
+		
+		
+		
+		<!-- Versioning commands -->
+		<h2 id="ykush3_versioning_commands">Versioning commands</h2>
+		<p>
+			Get version of the firmware loaded in the board.
+		</p>
+		<h3>Command usage</h3>
+		<p class="command_line">
+			ykushcmd ykush3 [OPTION]
+		</p>
+		<p>The following options are available:</p>
+		<table>
+			<tr>
+				<td>--version-bootloader</td>
+				<td>Get bootloader version from board.</td>
+			</tr>
+			<tr>
+				<td>--version-firmware</td>
+				<td>Get firmware version from board.</td>
+			</tr>
+		</table>
+
+		<h3>Examples</h3>
+
+		<p>Get bootloader version:</p>
+		<p class="command_line">ykushcmd ykush3 --version-bootloader<p>
+		
+		<p>Get firmware version:</p>
+		<p class="command_line">ykushcmd ykush3 --version-firmware<p>
+
+	</div>
+	
+	
+	<!--
+		#ykush3_man_important_links
+	-->
+	<h1 id="ykush3_man_important_links">Important links</h1>
+	<div>
+		<ul>
+			<li><a class="inlineLink" href="https://www.yepkit.com/product/300110/YKUSH3" target="_blank">YKUSH3 product page</a></li>
+			<li><a class="inlineLink" href="https://www.yepkit.com/learn/tutorial/setup_guide/ykush3-i2c-control-interface" target="_blank">How to control the YKUSH3 boards using the I2C interface</a></li>
+		</ul>
+	</div>
+	
+	
+	
+</div>
+

+ 116 - 0
src/commandParser.cpp

@@ -0,0 +1,116 @@
+/****************************************************************************
+ FileName:      commandParser.cpp
+ Dependencies:  See INCLUDES section
+ Compiler:      Visual Studio Community 2015
+ Company:       Yepkit, Lda.
+
+ Software License Agreement:
+
+ Copyright (c) 2015 Yepkit Lda
+
+ Permission is hereby granted, free of charge, to any person obtaining a copy
+ of this software and associated documentation files (the "Software"), to deal
+ in the Software without restriction, including without limitation the rights
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ copies of the Software, and to permit persons to whom the Software is
+ furnished to do so, subject to the following conditions:
+
+ The above copyright notice and this permission notice shall be included in
+ all copies or substantial portions of the Software.
+
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ THE SOFTWARE.
+
+*****************************************************************************
+ File Description:
+
+    Change History:
+        Rev     Date            Description
+        ----    -----------     -----------------------------------------
+        1.0     2015-09-11      First Release
+
+
+ ****************************************************************************
+ *  Summary:
+ *      Main program function
+ *
+ *
+ *
+*****************************************************************************/
+
+
+// INCLUDES ---------------------------------------------------------------
+
+#include <cstdlib>
+#include <iostream>
+#include <stdio.h>
+
+#include "stdafx.h"
+#include "commandParser.h"
+#include <ykush.h>
+#include <ykushxs.h>
+#include <ykush_help.h>
+#include <ykush2.h>
+#include <ykush3.h>
+#include <string>
+
+
+extern unsigned int PRODUCT_ID;
+
+enum Board {
+	YKUSH,
+	YKUSHXS,
+	YKUSH2,
+	YKUSH3,
+};
+
+
+int commandParser(int argc, char** argv) 
+{	
+    	Help help(argv[0]);
+	std::string str_ykush ("ykush");
+	std::string str_ykush3 ("ykush3");
+	std::string str_ykush2 ("ykush2");
+	std::string str_ykushxs ("ykushxs");
+
+  	if ( argc <= 1) {
+        	help.print_all();
+		return 0;
+    	}
+
+	//Parse input options and define action
+	if( argc >= 2) {
+		if ( str_ykushxs.compare( argv[1]) == 0 ) {
+			//YKUSHXS
+			return ykushxs_cmd_parser(argc, argv);
+		} else if ( str_ykush2.compare( argv[1]) == 0 ) {
+			//YKUSH2
+			ykush2_cmd_parser(argc, argv);	//Not active yet.
+			return 0;
+		} else if ( str_ykush3.compare( argv[1]) == 0) {
+			//YKUSH3
+			return ykush3_cmd_parser(argc, argv);
+		} else if ( str_ykush.compare( argv[1]) == 0 ) {
+			//YKUSH
+			if ( argc >= 3 )
+				return ykush_cmd_parser(argc - 1 , &argv[1]);
+			else
+				help.print_all();
+			
+			return -1;
+		} else {
+			//YKUSH
+			return ykush_cmd_parser(argc, argv);
+		}
+	}
+	
+	return 0;
+}
+
+
+

+ 0 - 0
ykushcmd/commandParser.h


+ 160 - 0
src/help/ykush_help.cpp

@@ -0,0 +1,160 @@
+/*******************************************************************************
+Copyright 2019 Yepkit Lda (www.yepkit.com)
+
+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 "ykush_help.h"
+#include <iostream>
+
+#include <stdio.h>
+
+
+Help::Help(char *exec_name)
+{
+	app_name = exec_name;
+}
+
+void Help::print_version(void) 
+{
+	std::cout << "YKUSHCMD Version 1.2.5\n";
+}
+
+void Help::print_usage(void)
+{
+        std::cout << "Usage:\t" << app_name << " [board_name] [-s serial_number] [OPTION]...\n";
+	std::cout << "Control Yepkit YKUSH family boards.\n";
+}
+
+void Help::print_board_names(void)
+{
+	std::cout << "\nThe board_name specifies the board model being addressed.";
+	std::cout << "If no board_name is provided the board is assumed to be a YKUSH board (board_name = ykush).\n";
+	std::cout << "Board names:\n";
+	std::cout << " ykush\t\tYKUSH board.\n";
+	std::cout << " ykush3\t\tYKUSH3 board.\n";
+	std::cout << " ykushxs\tYKUSHXS board.\n";
+	std::cout << "The [board_name] must be provided for commands addressed for a specific board.\n";
+	std::cout << "For general or common commands, applicable to all board models, the [board_name] is to ommited from the command.\n";
+}
+
+void Help::print_common_options(void)
+{
+
+
+
+}
+
+void Help::print_ykush(void)
+{
+	std::cout << "\nYKUSH board options:\n";
+
+	std::cout << "-d 1|2|3|a                Power Down/Off downstream port with the number privided.\n";
+	std::cout << "                          If [a] is provided as the port number then all ports will be switched.\n";
+
+	std::cout << "-u 1|2|3|a                Power Up/On downstream port number downstream_number\n";
+
+	std::cout << "-s serial_number          Board serial number to wich the command is addressed.\n";
+	std::cout << "                          When multiple YKUSH boards are connected to a host, this option should be used\n";
+	std::cout << "                          to specify the board. If more than one board is connected and this option is not\n";
+	std::cout << "                          provided the command will be sent to the first board in the USB enumeration list.\n";
+
+	std::cout << "-l                        Lists the serial numbers of the YKUSH boards attached to the host.\n";
+
+	std::cout << "-g 1|2|3                  Switching state of a downstream port.\n";
+
+	std::cout << "-h                        Display help for YKUSH board specific commands.\n";
+}
+
+void Help::print_ykush2(void)
+{
+
+}
+
+void Help::print_ykush3(void)
+{
+	std::cout << "\nYKUSH3 board options:\n";
+
+	std::cout << "-d 1|2|3|a                Power Down/Off downstream port with the number privided.\n";
+	std::cout << "                          If [a] is provided as the port number then all ports will be switched.\n";
+
+	std::cout << "-u 1|2|3|a                Power Up/On downstream port number downstream_number\n";
+
+	std::cout << "-s serial_number          Board serial number to wich the command is addressed.\n";
+	std::cout << "                          When multiple YKUSH boards are connected to a host, this option should be used\n";
+	std::cout << "                          to specify the board. If more than one board is connected and this option is not\n";
+	std::cout << "                          provided the command will be sent to the first board in the USB enumeration list.\n";
+
+	std::cout << "-l                        Lists the serial numbers of the YKUSH boards attached to the host.\n";
+
+        std::cout << "-g 1|2|3                  Switching state of a downstream port.\n";
+        
+        std::cout << "-c <port-number> <config-value>       Configure the default state of a downstream port\n";
+        std::cout << "                                      (port-number=1|2|3|e) at power-on. The port number <e> refers to exteranl 5V port.\n";
+        std::cout << "                                      The default states are off (config-value=0), on (config-value=1)\n";
+        std::cout << "                                      and persistent (config-value=2).\n";
+
+	std::cout << "-on                       Switch On the 5V output power port.\n";
+	std::cout << "-off                      Switch Off the 5V output power port.\n";
+
+	std::cout << "-r 1|2|3                  Read GPIO with the number provided (1, 2 or 3).\n";
+	std::cout << "-w 1|2|3 0|1              Write to the GPIO with the number provided (1, 2 or 3).\n";
+	std::cout << "                          Writing a value of 1 or 0 will drive the GPIO to logical high or low, respectively.\n";
+
+        std::cout << "--gpio enable|disable     Enable / Disable GPIO control interface. Will become active on next reset/power-on.\n\n";
+
+	std::cout << "--reset                   Resets (reboot) the YKUSH3 board.\n";
+
+	std::cout << "-h                        Display help for YKUSH board specific commands.\n";
+
+        std::cout << "--bootloader-version      Board bootloader version.\n";
+        std::cout << "--firmware-version        Board firmware version.\n";
+        
+	std::cout << "--boot                    Enter bootloader mode for firmware update.\n";
+}
+
+void Help::print_ykushxs(void)
+{
+	std::cout << "\nYKUSHXS board options:\n";
+
+	std::cout << "-d                        Power Down/Off the downstream port.\n";
+
+	std::cout << "-u                        Power Up/On the downstream port\n";
+
+	std::cout << "-s serial_number          Board serial number to wich the command is addressed.\n";
+	std::cout << "                          When multiple YKUSHXS boards are connected to a host, this option should be used\n";
+	std::cout << "                          to specify the board. If more than one board is connected and this option is not\n";
+	std::cout << "                          provided the command will be sent to the first board in the USB enumeration list.\n";
+
+	std::cout << "-l                        Lists the serial numbers of the YKUSHXS boards attached to the host.\n";
+
+	std::cout << "-g                        Switching state of a downstream port.\n";
+
+	std::cout << "-h                        Display help for YKUSHXS board specific commands.\n";
+}
+
+
+void Help::print_all(void)
+{
+	print_version();
+	print_usage();
+	print_board_names();
+	print_ykush();
+	print_ykush2();
+	print_ykush3();
+	print_ykushxs();
+}
+
+
+
+

+ 49 - 0
src/help/ykush_help.h

@@ -0,0 +1,49 @@
+/*******************************************************************************
+Copyright 2017 Yepkit Lda (www.yepkit.com)
+
+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 _YKUSHCMD_HELP_H_
+#define _YKUSHCMD_HELP_H_
+
+
+class Help
+{
+	public:
+
+		Help(char *exec_name);
+
+		void print_version(void);
+		void print_usage(void);
+		void print_board_names(void);
+		void print_common_options(void);
+		void print_ykush(void);
+		void print_ykush2(void);
+		void print_ykush3(void);
+		void print_ykushxs(void);
+		void print_all(void);
+
+	private:
+
+		char *app_name;
+};
+
+
+
+
+
+
+#endif

+ 0 - 0
ykushcmd/objs/placeholder


+ 0 - 0
ykushcmd/platformdefs.h


+ 0 - 0
ykushcmd/stdafx.cpp


+ 0 - 0
ykushcmd/stdafx.h


+ 0 - 0
ykushcmd/targetver.h


+ 67 - 0
src/tests/test_usbhid.cpp

@@ -0,0 +1,67 @@
+#include <usbhid.h>
+#include <iostream>
+#include <string>
+
+int main(int argc, char* argv[])
+{
+        UsbHid *usbhid = new UsbHid();
+        unsigned int pid = 0xF2F7;
+        unsigned int vid = 0x04D8;
+        libusb_device_handle *handle;
+        int i = 0;
+        std::string str2 = "YK21493";
+        unsigned char hid_report_out[65];
+        unsigned char hid_report_in[65];
+        char serialInput[] = "YK21493";
+        int res;
+    	
+        struct hid_device_info *devs, *cur_dev;
+		
+        std::cout << "Get attach devices serial numbers test...\n";
+	devs = usbhid->enumerate(vid, pid);
+	if (devs == NULL) 
+	{
+		if (handle == NULL)
+		{
+		// No HID devices found
+		return 0;
+		}
+	}
+
+	cur_dev = devs;
+	while (cur_dev) 
+	{
+                std::cout << cur_dev->serial_number_ascii << "\n";
+
+                std::string str1;
+                str1 = cur_dev->serial_number_ascii;
+                if ( str1.compare(str2) == 0 ) {
+                        std::cout << "MATCH\n";
+                }
+		//printf("\n%ls\n", cur_dev->serial_number);
+		cur_dev = cur_dev->next;
+		i++;
+	}
+
+        usbhid->free_enumeration(devs);
+
+
+
+        std::cout << "Send command test...\n";
+        //abrir device
+        res = usbhid->open(vid, pid, serialInput);
+        if (res < 0) {
+                 std::cout << "Unable to open device";
+                 return 0;
+        }
+
+        hid_report_out[0] = 0x01;       //port 1 off
+        std::cout << "usbhid->write : " << usbhid->write(hid_report_out, 64) << "\n";
+        std::cout << "usbhid->read : " << usbhid->read(hid_report_in, 64) << "\n";
+        usbhid->close();
+        for (i=0; i < 64; i++)
+                std::cout << " " << std::hex << (int)hid_report_in[i];
+        std::cout << std::endl;
+
+    	return 0;
+}

+ 407 - 0
src/usbhid/usbhid.cpp

@@ -0,0 +1,407 @@
+/*******************************************************************************
+Copyright 2019 Yepkit Lda (www.yepkit.com)
+
+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 "usbhid.h"
+#include <libusb.h>
+#include <cstdlib>
+#include <string.h>
+#include <string>
+#include <iostream>
+
+
+UsbHid::UsbHid()
+{
+        usb_context = NULL;
+}
+
+
+struct hid_device_info *UsbHid::enumerate(unsigned int vendor_id, unsigned int product_id) 
+{
+        libusb_device **devs;
+	libusb_device *dev;
+	libusb_device_handle *handle;
+	ssize_t num_devs;
+        int i = 0;
+
+        struct hid_device_info *root = NULL;            // Return object. The first device found.
+        struct hid_device_info *cur_dev = NULL;
+
+        if(init() < 0)
+                return NULL;
+
+        num_devs = libusb_get_device_list(usb_context, &devs);
+	if (num_devs < 0)
+                return NULL;
+
+        while ((dev = devs[i++]) != NULL) {
+                struct libusb_device_descriptor desc;
+
+                int res = libusb_get_device_descriptor(dev, &desc);
+                if ((desc.idVendor == vendor_id) && (desc.idProduct == product_id)) {
+                        struct hid_device_info *tmp;
+
+                        // VID/PID match. Create the record.
+                        tmp = (struct hid_device_info*) std::calloc(1, sizeof(struct hid_device_info));
+                        if (cur_dev)
+                                cur_dev->next = tmp;
+                        else
+                                root = tmp;
+                        cur_dev = tmp;
+                        
+                        // Fill out the record.
+                        cur_dev->next = NULL;
+
+                        res = libusb_open(dev, &handle);
+                        if (res >= 0) {
+                                /* Serial Number */
+                                if (desc.iSerialNumber > 0)
+                                        cur_dev->serial_number_ascii = get_usb_string_ascii(handle, desc.iSerialNumber);
+
+                                /* Manufacturer and Product strings */
+                                if (desc.iManufacturer > 0)
+                                        cur_dev->manufacturer_string_ascii = get_usb_string_ascii(handle, desc.iManufacturer);
+                                if (desc.iProduct > 0)
+                                        cur_dev->product_string_ascii = get_usb_string_ascii(handle, desc.iProduct);
+
+                        }
+                        libusb_close(handle);
+                } 
+        }
+
+        libusb_free_device_list(devs, 1);
+        return root;
+}
+
+
+void UsbHid::free_enumeration(struct hid_device_info *devs)
+{
+        struct hid_device_info *d = devs;
+	while (d) {
+		struct hid_device_info *next = d->next;
+		//free(d->path);
+		free(d->serial_number_ascii);
+		free(d->manufacturer_string_ascii);
+		free(d->product_string_ascii);
+		free(d);
+		d = next;
+        }
+}
+
+
+int UsbHid::init()
+{
+        if (!usb_context) {
+		// Init Libusb
+		if (libusb_init(&usb_context))
+			return -1;
+	}
+
+        return 0;
+}
+
+
+ char *UsbHid::get_usb_string_ascii(libusb_device_handle *dev, uint8_t idx)
+ {
+        unsigned char buf[512];
+	int len;
+        wchar_t *str = NULL;
+
+        // Get the string from libusb.
+	//len = libusb_get_string_descriptor(dev, idx, 0x0409, (unsigned char*)buf, sizeof(buf));
+        len = libusb_get_string_descriptor_ascii(dev, idx, (unsigned char*)buf, sizeof(buf));	
+	if (len < 0)
+                return NULL;
+        return (char *)strdup((const char *)buf);
+ }
+
+
+int UsbHid::open(unsigned int vendor_id, unsigned int product_id, char *serial)
+ {
+        libusb_device **devs;
+	libusb_device *dev;
+	libusb_device_handle *handle;
+	ssize_t num_devs;
+        int i = 0;
+
+        std::string str1, str2;
+
+        if (serial != NULL)
+                str1 = serial;
+
+        if(init() < 0)
+                return -1;
+        num_devs = libusb_get_device_list(usb_context, &devs);
+	if (num_devs < 0)
+                return -1;
+        //std::cout << "num_devs = " << num_devs << "\n";
+        while ((dev = devs[i++]) != NULL) {
+                struct libusb_device_descriptor desc;
+
+                int res = libusb_get_device_descriptor(dev, &desc);
+                if ((desc.idVendor == vendor_id) && (desc.idProduct == product_id)) {
+
+                        res = libusb_open(dev, &open_device.handle);
+                        //std::cout << "res = libusb_open = " << res << "\n";
+                        if (res >= 0) {
+                                if (serial == NULL) {   // Without serial number
+                                        struct libusb_device_descriptor desc;
+                                        struct libusb_config_descriptor *conf_desc = NULL;
+                                        int f,j,k;
+
+                                        libusb_get_device_descriptor(dev, &desc);
+                                        if (libusb_get_active_config_descriptor(dev, &conf_desc) < 0) {
+                                                std::cout << "cannot get active descriptor\n";
+                                                libusb_free_device_list(devs, 1);
+                                                libusb_close(open_device.handle);
+                                                return -1; 
+                                        }
+                                        //std::cout << "conf_desc->bNumInterfaces = " << (unsigned int)conf_desc->bNumInterfaces << "\n";
+                                        for (j = 0; j < conf_desc->bNumInterfaces; j++) {
+                                                const struct libusb_interface *intf = &conf_desc->interface[j];
+                                                for (k = 0; k < intf->num_altsetting; k++) {
+                                                        const struct libusb_interface_descriptor *intf_desc;
+                                                        intf_desc = &intf->altsetting[k];
+                                                        if (intf_desc->bInterfaceClass == LIBUSB_CLASS_HID) {
+                                                                //std::cout << "intf_desc->bInterfaceNumber = " << (unsigned int)intf_desc->bInterfaceNumber << "\n";
+                                                                open_device.interface = intf_desc->bInterfaceNumber;
+                                                                //std::cout << "intf_desc->bNumEndpoints = " << (unsigned int)intf_desc->bNumEndpoints << "\n";
+                                                                // Find the INPUT and OUTPUT endpoints. An OUTPUT endpoint is not required. 
+                                                                for (f = 0; f < intf_desc->bNumEndpoints; f++) {
+                                                                        //std::cout << "f = " << f << "\n";
+                                                                        const struct libusb_endpoint_descriptor *ep = &intf_desc->endpoint[f];
+
+                                                                        /* Determine the type and direction of this
+                                                                        endpoint. */
+                                                                        int is_interrupt =
+                                                                                (ep->bmAttributes & LIBUSB_TRANSFER_TYPE_MASK)
+                                                                        == LIBUSB_TRANSFER_TYPE_INTERRUPT;
+                                                                        int is_output =
+                                                                                (ep->bEndpointAddress & LIBUSB_ENDPOINT_DIR_MASK)
+                                                                        == LIBUSB_ENDPOINT_OUT;
+                                                                        int is_input =
+                                                                                (ep->bEndpointAddress & LIBUSB_ENDPOINT_DIR_MASK)
+                                                                        == LIBUSB_ENDPOINT_IN;
+
+                                                                        /* Decide whether to use it for input or output. */
+                                                                        if (open_device.input_endpoint == 0 &&
+                                                                        is_interrupt && is_input) {
+                                                                                /* Use this endpoint for INPUT */
+                                                                                open_device.input_endpoint = ep->bEndpointAddress;
+                                                                                open_device.input_ep_max_packet_size = ep->wMaxPacketSize;
+                                                                        }
+                                                                        if (open_device.output_endpoint == 0 &&
+                                                                        is_interrupt && is_output) {
+                                                                                /* Use this endpoint for OUTPUT */
+                                                                                open_device.output_endpoint = ep->bEndpointAddress;
+                                                                        }
+                                                                }
+                                                        }
+                                                }
+                                        }
+
+ 
+
+                                        res = libusb_claim_interface(open_device.handle, open_device.interface);
+                                        if (res < 0) {
+                                                //try detach kernel driver
+                                                int detached = 0;
+                                                res = libusb_kernel_driver_active(open_device.handle, open_device.interface);
+                                                if (res == 1) {
+                                                        res = libusb_detach_kernel_driver(open_device.handle, open_device.interface);
+                                                        if (res < 0)
+                                                                std::cout << "Couldn't detach kernel driver, even though a kernel driver was attached.\n";
+                                                        else
+                                                                detached = 1;
+                                                }
+                                                res = libusb_claim_interface(open_device.handle, open_device.interface);
+                                                
+                                                if (res < 0) {
+                                                        std::cout << "cannot claim interface\n";
+                                                        libusb_free_device_list(devs, 1);
+                                                        libusb_free_config_descriptor(conf_desc);
+                                                        libusb_close(open_device.handle);
+                                                        return -1;
+                                                }      
+                                        }
+                                        //std::cout << "debug claim interface: " << res << "\n";
+
+                                        /* Store off the string descriptor indexes */
+                                        open_device.manufacturer_index = desc.iManufacturer;
+                                        open_device.product_index      = desc.iProduct;
+                                        open_device.serial_index       = desc.iSerialNumber;
+
+                                        libusb_free_device_list(devs, 1);
+                                        libusb_free_config_descriptor(conf_desc);
+                                        return 0;       //Success
+                                } else if (desc.iSerialNumber > 0) {    // With serial number
+                                        str2 = get_usb_string_ascii(open_device.handle, desc.iSerialNumber);
+                                        if ( str1.compare(str2) == 0 ) {
+                                                //std::cout << "Serial found\n";
+                                                struct libusb_device_descriptor desc;
+                                                struct libusb_config_descriptor *conf_desc = NULL;
+                                                int f,j,k;
+
+                                                libusb_get_device_descriptor(dev, &desc);
+                                                if (libusb_get_active_config_descriptor(dev, &conf_desc) < 0) {
+                                                        std::cout << "cannot get active descriptor\n";
+                                                        libusb_free_device_list(devs, 1);
+							libusb_close(open_device.handle);
+							return -1; 
+                                                }
+                                                //std::cout << "conf_desc->bNumInterfaces = " << (unsigned int)conf_desc->bNumInterfaces << "\n";
+                                                for (j = 0; j < conf_desc->bNumInterfaces; j++) {
+                                                        const struct libusb_interface *intf = &conf_desc->interface[j];
+                                                        for (k = 0; k < intf->num_altsetting; k++) {
+                                                                const struct libusb_interface_descriptor *intf_desc;
+                                                                intf_desc = &intf->altsetting[k];
+                                                                if (intf_desc->bInterfaceClass == LIBUSB_CLASS_HID) {
+                                                                        //std::cout << "intf_desc->bInterfaceNumber = " << (unsigned int)intf_desc->bInterfaceNumber << "\n";
+                                                                        open_device.interface = intf_desc->bInterfaceNumber;
+                                                                        //std::cout << "intf_desc->bNumEndpoints = " << (unsigned int)intf_desc->bNumEndpoints << "\n";
+                                                                        // Find the INPUT and OUTPUT endpoints. An OUTPUT endpoint is not required. 
+                                                                        for (f = 0; f < intf_desc->bNumEndpoints; f++) {
+                                                                                //std::cout << "f = " << f << "\n";
+                                                                                const struct libusb_endpoint_descriptor *ep = &intf_desc->endpoint[f];
+
+                                                                                /* Determine the type and direction of this
+                                                                                endpoint. */
+                                                                                int is_interrupt =
+                                                                                        (ep->bmAttributes & LIBUSB_TRANSFER_TYPE_MASK)
+                                                                                == LIBUSB_TRANSFER_TYPE_INTERRUPT;
+                                                                                int is_output =
+                                                                                        (ep->bEndpointAddress & LIBUSB_ENDPOINT_DIR_MASK)
+                                                                                == LIBUSB_ENDPOINT_OUT;
+                                                                                int is_input =
+                                                                                        (ep->bEndpointAddress & LIBUSB_ENDPOINT_DIR_MASK)
+                                                                                == LIBUSB_ENDPOINT_IN;
+
+                                                                                /* Decide whether to use it for input or output. */
+                                                                                if (open_device.input_endpoint == 0 &&
+                                                                                is_interrupt && is_input) {
+                                                                                        /* Use this endpoint for INPUT */
+                                                                                        open_device.input_endpoint = ep->bEndpointAddress;
+                                                                                        open_device.input_ep_max_packet_size = ep->wMaxPacketSize;
+                                                                                }
+                                                                                if (open_device.output_endpoint == 0 &&
+                                                                                is_interrupt && is_output) {
+                                                                                        /* Use this endpoint for OUTPUT */
+                                                                                        open_device.output_endpoint = ep->bEndpointAddress;
+                                                                                }
+                                                                        }
+                                                                }
+                                                        }
+                                                }
+
+                                                /* 
+                                                int detached = 0;
+                                                res = libusb_kernel_driver_active(open_device.handle, open_device.interface);
+                                                if (res == 1) {
+                                                        res = libusb_detach_kernel_driver(open_device.handle, open_device.interface);
+                                                        if (res < 0)
+                                                                std::cout << "Couldn't detach kernel driver, even though a kernel driver was attached.\n";
+                                                        else
+                                                                detached = 1;
+                                                }
+                                                */
+
+                                                res = libusb_claim_interface(open_device.handle, open_device.interface);
+						if (res < 0) {
+							//try detach kernel driver
+                                                        int detached = 0;
+                                                        res = libusb_kernel_driver_active(open_device.handle, open_device.interface);
+                                                        if (res == 1) {
+                                                                res = libusb_detach_kernel_driver(open_device.handle, open_device.interface);
+                                                                if (res < 0)
+                                                                        std::cout << "Couldn't detach kernel driver, even though a kernel driver was attached.\n";
+                                                                else
+                                                                        detached = 1;
+                                                        }
+                                                        res = libusb_claim_interface(open_device.handle, open_device.interface);
+                                                        
+                                                        if (res < 0) {
+                                                                std::cout << "cannot claim interface\n";
+                                                                libusb_free_device_list(devs, 1);
+                                                                libusb_free_config_descriptor(conf_desc);
+                                                                libusb_close(open_device.handle);
+                                                                return -1;
+                                                        }
+                                                }
+                                                //std::cout << "debug claim interface: " << res << "\n";
+
+                                                /* Store off the string descriptor indexes */
+						open_device.manufacturer_index = desc.iManufacturer;
+						open_device.product_index      = desc.iProduct;
+						open_device.serial_index       = desc.iSerialNumber;
+                                                
+                                                libusb_free_device_list(devs, 1);
+                                                libusb_free_config_descriptor(conf_desc);
+                                                return 0;       //Success
+                                        }
+                                }
+                        }
+                        libusb_close(open_device.handle);
+                } 
+        }
+
+        libusb_free_device_list(devs, 1);
+
+        return -1;
+ }
+
+
+void UsbHid::close() {
+        libusb_close(open_device.handle);
+}
+
+
+int UsbHid::write(unsigned char *data, size_t length)
+{
+        int res;
+
+        /* Use the interrupt out endpoint */
+        int actual_length;
+        res = libusb_interrupt_transfer(open_device.handle,
+                open_device.output_endpoint,
+                (unsigned char*)data,
+                length,
+                &actual_length, 1000);
+        //std::cout << "Interrupt transfer used\n";
+        if (res < 0)
+                return -1;
+
+
+        return actual_length;
+}
+
+int UsbHid::read(unsigned char *data, int length)
+{
+        int res;
+	int report_number = data[0];
+	int skipped_report_id = 0;
+
+        int actual_length;
+        res = libusb_interrupt_transfer(open_device.handle,
+                open_device.input_endpoint,
+                data,
+                length,
+                &actual_length, 5000);
+        
+        //std::cout << "read res = " << res << "\n";
+
+        if (res < 0)
+                return -1;
+
+	return actual_length;
+}

+ 156 - 0
src/usbhid/usbhid.h

@@ -0,0 +1,156 @@
+/*******************************************************************************
+Copyright 2019 Yepkit Lda (www.yepkit.com)
+
+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 _USBHID_H_
+#define _USBHID_H_
+
+#include <libusb.h>
+
+
+/** hidapi info structure */
+struct hid_device_info {
+        /** Platform-specific device path */
+        char *path;
+        /** Device Vendor ID */
+        unsigned short vendor_id;
+        /** Device Product ID */
+        unsigned short product_id;
+        /** Serial Number */
+        wchar_t *serial_number;
+        char *serial_number_ascii;
+        /** Device Release Number in binary-coded decimal,
+                 also known as Device Version Number */
+        unsigned short release_number;
+        /** Manufacturer String */
+        wchar_t *manufacturer_string;
+        char *manufacturer_string_ascii;
+        /** Product string */
+        wchar_t *product_string;
+        /** Usage Page for this Device/Interface
+                 (Windows/Mac only). */
+        char *product_string_ascii;
+        unsigned short usage_page;
+        /** Usage for this Device/Interface
+                 (Windows/Mac only).*/
+        unsigned short usage;
+        /** The USB interface which this logical device
+                 represents.
+                * Valid on both Linux implementations in all cases.
+                * Valid on the Windows implementation only if the device
+                        contains more than one interface.
+                * Valid on the Mac implementation if and only if the device
+                        is a USB HID device. */
+        int interface_number;
+
+        /** Pointer to the next device */
+        struct hid_device_info *next;
+};
+
+struct input_report {
+	uint8_t *data;
+	size_t len;
+	struct input_report *next;
+};
+
+typedef struct hid_device {
+	/* Handle to the actual device. */
+	libusb_device_handle *handle;
+
+	/* Endpoint information */
+	int input_endpoint;
+	int output_endpoint;
+	int input_ep_max_packet_size;
+
+	/* The interface number of the HID */
+	int interface;
+
+	/* Indexes of Strings */
+	int manufacturer_index;
+	int product_index;
+	int serial_index;
+
+	/* Whether blocking reads are used */
+	int blocking; /* boolean */
+
+	int cancelled;
+	struct libusb_transfer *transfer;
+
+	/* List of received input reports. */
+	struct input_report *input_reports;
+} HidDevice;
+
+class UsbHid {
+        public:
+                /**
+                 * \brief UsbHid class constructor.
+                 */
+                UsbHid();
+
+                /**
+                 * \brief Enumerates the USB devices with the provided VID and PID.
+                 * 
+                 * This method will alloc memory for device structure that must be free when not needed.
+                 * Call free_enumeration() method to free the device structure.
+                 * 
+                 * \return List of USB devices currently attached to the system with the provided VID and PID. 
+                 */
+                struct hid_device_info *enumerate(unsigned int vendor_id, unsigned int product_id);
+
+                void free_enumeration(struct hid_device_info *devs);
+
+                /**
+                 * \brief Opens the device and sets the open_device property
+                 * 
+                 * \retval 0 Success
+                 * \retval -1 Error
+                 */
+                int open(unsigned int vendor_id, unsigned int product_id, char *serial);
+
+                /**
+                 * \brief Closes de open_device
+                 */
+                void close(void);
+
+                /**
+                 * \brief Writes to the open_device
+                 * 
+                 * \retval 0 Success
+                 * \retval -1 Error
+                 */
+                int write(unsigned char *data, size_t length);
+
+                int read(unsigned char *data, int length);
+        
+        private:
+                libusb_context *usb_context;
+
+                int init();
+
+                wchar_t *get_usb_string(libusb_device_handle *dev, uint8_t idx);
+
+                char *get_usb_string_ascii(libusb_device_handle *dev, uint8_t idx);
+
+                HidDevice open_device;
+
+
+                
+
+
+};
+
+
+#endif
+
+

+ 147 - 0
src/utils/command_parser.cpp

@@ -0,0 +1,147 @@
+/*******************************************************************************
+Copyright 2019 Yepkit Lda (www.yepkit.com)
+
+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 <command_parser.h>
+#include <string>
+#include <cstring>
+#include <ykush_help.h>
+#include <cstdlib>
+
+
+
+/**
+ * CommandLine class constructor
+ * 
+ */
+
+CommandLine::CommandLine() 
+{
+
+}
+
+CommandLine::~CommandLine()
+{
+	//free command line structures
+	struct command_option *cur_opt = command.options;
+	while (cur_opt) {
+		struct command_option *next_opt = cur_opt->next;
+		free(cur_opt->name);
+		struct command_parameter *cur_param = cur_opt->parameters;
+		while ( cur_param ) {
+			struct command_parameter *next_param = cur_param->next;
+			free( cur_param->name );
+			free( cur_param );
+			cur_param = next_param;
+		}
+		free( cur_opt );
+		cur_opt = next_opt;
+	}
+}
+
+
+int CommandLine::parse(int argc, char **argv)
+{
+	command.app_name = argv[0];
+	
+	if ( argc < 2 ) 
+		return -1;
+	
+	
+	int i = 1;
+	struct command_option *cur_opt = NULL;
+	struct command_option *root_opt = NULL;
+	
+	bool exit_while;
+	while ( i < ( argc - 1 ) ) {
+
+		exit_while = false;
+
+		if ( std::strlen(argv[i]) > 1 ) {
+			if ( argv[i][0] == '-') { //is an option
+				//add new option to command.options
+				struct command_option *tmp_opt;
+				tmp_opt = (struct command_option *) std::calloc(1, sizeof(struct command_option));
+				if (cur_opt)
+					cur_opt->next = tmp_opt;
+				else
+					root_opt = tmp_opt;
+				cur_opt = tmp_opt;
+				cur_opt->next = NULL;
+
+				std::memcpy( cur_opt->name, argv[i], std::strlen( argv[i] ) + 1 );	//copy string allocating memory for destination
+
+				i++;
+				//get option parameters, if they exist
+				struct command_parameter *cur_param = NULL;
+				struct command_parameter *root_param = NULL;
+				while ( ( i < ( argc - 1 ) ) && !exit_while ) {
+					if ( argv[i][0] == '-' ) { //is another option
+						i--;
+						exit_while = true;
+					} else { //is a parameter
+						//add parameter to option
+						struct command_parameter *tmp_param;
+						tmp_param = (struct command_parameter *) std::calloc(1, sizeof(struct command_parameter));
+						if (cur_param)
+							cur_param->next = tmp_param;
+						else
+							root_param = tmp_param;
+						cur_param = tmp_param;
+						cur_param->next = NULL;
+						std::memcpy( cur_param->name, argv[i], std::strlen( argv[i] ) + 1 );	//copy string allocating memory for destination
+
+						i++;
+					}
+				}
+				cur_opt->parameters = root_param;
+			}
+		}
+	}
+
+	command.options = root_opt;
+
+	return 0;
+}
+
+
+int CommandLine::is_board(char *board_name) 
+{
+	int i = 0;
+	std::string str1 ("-b");
+	std::string str2 ("--board");
+	std::string str3 (board_name);
+	//look for -b or --board option
+	struct command_option *cur_opt;
+	struct command_parameter *cur_param;
+
+	cur_opt = command.options;
+	while ( cur_opt ) {
+		if ( (str1.compare( cur_opt->name ) == 0) || (str2.compare( cur_opt->name ) == 0) ) {
+			//board option was found.
+			//Now let's check if the board name parameter matches the board_name
+			cur_param = cur_opt->parameters;
+			while ( cur_param ) {
+				if ( str3.compare(cur_param->name) )
+					return 0;			//board match
+				cur_param = cur_param->next;
+			}	
+		}
+		cur_opt = cur_opt->next;
+	}
+	return -1;
+}
+
+

+ 82 - 0
src/utils/command_parser.h

@@ -0,0 +1,82 @@
+/*******************************************************************************
+Copyright 2019 Yepkit Lda (www.yepkit.com)
+
+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 _COMMAND_PARSER_H_
+#define _COMMAND_PARSER_H_
+
+
+struct command_parameter {
+	char *name;
+	struct command_parameter *next;
+};
+
+struct command_option {
+	char *name;
+	struct command_parameter *parameters;
+	struct command_option *next;
+};
+
+struct command_line {
+	char *app_name;
+	struct command_option *options;
+};
+
+/**
+ * \defgroup command_line Command line
+ */
+
+/**
+ * \ingroup command_line
+ * \brief Parses the command line and sets the command object.
+ * 
+ */
+class CommandLine {
+
+	public:
+		CommandLine();
+		~CommandLine();
+
+		/**
+		 * \brief Processes the command line and sets the command property.
+		 */
+		int parse(int argc, char **argv);
+
+		/**
+		 * \brief Iterates through the command_line object and looks for a board option.
+		 * 
+		 * \param board_name board name.
+		 * 
+		 * \retval 0 board is in options.
+		 * \retval -1 board is not in option.
+		 * 
+		 */
+		int is_board(char *board_name);
+
+
+		
+	protected:
+		
+		
+
+	private:
+		struct command_line command;
+
+};
+
+
+#endif
+

+ 101 - 0
src/utils/string2val.cpp

@@ -0,0 +1,101 @@
+/*******************************************************************************
+Copyright 2017 Yepkit Lda (www.yepkit.com)
+
+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 "string2val.h"
+#include <stdlib.h>
+#include <stdio.h>
+
+
+
+/*****************************************************************
+ * Function:
+ *
+ * Description:
+ *
+ * Inputs:
+ *
+ * Outputs:
+ *
+ * Precedences:
+ *
+ *****************************************************************/
+int char2int(char input)
+{
+	if(input >= '0' && input <= '9')
+	return input - '0';
+	if(input >= 'A' && input <= 'F')
+	return input - 'A' + 10;
+	if(input >= 'a' && input <= 'f')
+	return input - 'a' + 10;
+	//throw std::invalid_argument("Invalid input string");
+	return 0;
+}
+
+
+
+
+
+/*****************************************************************
+ * Function:
+ *
+ * Description:
+ *
+ * Inputs:
+ *
+ * Outputs:
+ *
+ * Precedences:
+ *
+ *****************************************************************/
+// This function assumes src to be a zero terminated sanitized string with
+// an even number of [0-9a-f] characters, and target to be sufficiently large
+int hex2bin(char* src, unsigned char* output, int size)
+{
+	//unsigned char *out = (unsigned char*)malloc(size/2);
+	unsigned char out;
+	int i;
+
+	for(i=0; i<size; i=i+2) {
+		*(output++) = char2int(src[0])*16 + char2int(src[1]);
+		src += 2; 
+	}
+
+	//printf("\nout = 0x%x\n", *out);
+
+	return 0;
+}
+
+
+int dec2bin(char* src, unsigned char* output, int size)
+{
+	//unsigned char *out = (unsigned char*)malloc(size/2);
+	unsigned char out;
+	int base;
+	for(int i = 0; i < size; i++) {
+		base = 1;
+		for (int j = 1; j < (size - i); j++) {
+			base = base * 10;
+		}
+		*(output++) = char2int(src[0]) * base;
+		src++; 
+	}
+
+	//printf("\nout = 0x%x\n", *out);
+
+	return 0;
+}
+

+ 31 - 0
src/utils/string2val.h

@@ -0,0 +1,31 @@
+/*******************************************************************************
+Copyright 2017 Yepkit Lda (www.yepkit.com)
+
+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 _STRING2VAL_H_
+#define _STRING2VAL_H_
+
+
+int char2int(char input);
+
+int hex2bin(char* src, unsigned char* output, int size);
+
+int dec2bin(char* src, unsigned char* output, int size);
+
+#endif
+
+
+
+

+ 0 - 0
src/windows/placeholder


+ 204 - 0
src/yk_usb_device.cpp

@@ -0,0 +1,204 @@
+/*******************************************************************************
+Copyright 2019 Yepkit Lda (www.yepkit.com)
+
+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 "yk_usb_device.h"
+
+#ifdef _LIBUSB_
+#include <usbhid.h>
+#else
+#include <hidapi.h>
+#include <string.h>
+#endif
+
+#include <iostream>
+#include <string>
+#include <stdlib.h>
+
+#ifdef _LIBUSB_
+// Uses libusb directly
+int UsbDevice::listConnected() 
+{
+	UsbHid *usbhid = new UsbHid();
+	struct hid_device_info *devs, *cur_dev;
+	int i = 1;
+
+	devs = usbhid->enumerate(vid, pid);
+	if (devs == NULL)
+		return 0;
+
+	cur_dev = devs;
+	while (cur_dev) {
+                std::cout << i << ". Board found with serial number: " << cur_dev->serial_number_ascii << "\n";
+		cur_dev = cur_dev->next;
+		i++;
+	}
+
+        usbhid->free_enumeration(devs);
+
+	return i;
+}
+#else
+// Uses hidapi
+int UsbDevice::listConnected() 
+{
+	int i=0;
+
+	struct hid_device_info *devs, *cur_dev;
+		
+	devs = hid_enumerate(vid, pid);
+	if (devs == NULL)
+		return 0;
+
+	cur_dev = devs;
+	while (cur_dev) {
+		i++;
+		printf("%d. Board found with serial number: %ls\n", i, cur_dev->serial_number); 
+		cur_dev = cur_dev->next;
+	}
+	
+	hid_free_enumeration(devs);
+
+	return i;
+}
+#endif
+
+UsbDevice::UsbDevice(unsigned int vendor_id, unsigned int product_id) {
+	pid = product_id;
+	vid = vendor_id;
+}
+
+
+/**
+ * Sends HID report with the data provided in the input buffer "msg". 
+ *
+ * \param [in] serial Pointer to a char array containing the serial number.
+ * \param [in] msg Pointer to buffer containing the HID report message to be sent to USB device.
+ * \param [out] resp_msg Pointer to buffer to which the HID report message replied by the device.
+ * 
+ * \retval 0 No error.
+ * \retval -1 Unable to open USB device.
+ * \retval -2 Unable to write HID report to USB device.
+ * \retval -3 Unable to read HID report from USB device.
+ *
+ *
+ *  In the case of error, a message is printed into the standard
+ *  output.
+ *
+ *
+ * Precedences: 
+ *
+ *  Requires that VENDOR_ID and PRODUCT_ID constants are defined.
+ *
+ *
+ *****************************************************************/
+#ifdef _LIBUSB_
+int UsbDevice::sendHidReport(char *serial, unsigned char *msg, unsigned char *resp_msg, int report_size) 
+{
+	UsbHid *usbhid = new UsbHid();
+	int res;	
+
+	res = usbhid->open(vid, pid, serial);
+        if (res < 0) {
+		std::cout << "Unable to open device\n";
+		return -1;
+        }
+
+	res = usbhid->write(msg, report_size);
+	if (res < 0) {
+		std::cout << "Unable to write to device\n";
+		return -2;
+        }
+
+	res = usbhid->read(resp_msg, report_size);
+	if (res < 0) {
+		std::cout << "Unable to read from device\n";
+		return -3;
+        }
+
+	usbhid->close();
+
+	return 0;
+}
+#else
+int UsbDevice::sendHidReport(char *serial, unsigned char *msg, unsigned char *resp_msg, int report_size) 
+{	
+	const size_t newsize = 100;
+	wchar_t cserial[newsize];
+	int res, i;
+	unsigned char out_buf[65];
+	unsigned char in_buf[65];
+
+	if (report_size <= 64) {
+		out_buf[0] = 0;
+		for (i = 0; i < report_size; i++) {
+			out_buf[i+1] = msg[i]; 
+		}
+	} else {
+		std::cout << "Invalid report size\n";
+		return -1;
+	}
+	
+	if (serial) {
+			// Convert to a wchar_t*
+			size_t origsize = strlen(serial) + 1;
+			size_t convertedChars = 0;
+
+			mbstowcs_s(&convertedChars, cserial, origsize, serial, _TRUNCATE);
+
+		}
+
+	// Open the USB device 
+	handle = hid_open(vid, pid, serial ? cserial : NULL);
+	
+	if (handle == NULL) {
+		//printf("\n\nERROR: Unable to open USB device\n");
+		return -1;
+	}
+
+	// Set the hid_read() function to be blocking (wait for response from the device).
+	hid_set_nonblocking(handle, USB_CMD_BLOCKING);
+
+	//send HID report
+	res = hid_write(handle, out_buf, report_size++);
+	if (res < 0) {
+		std::cout << "Unable to write HID report to USB device\n";
+		return -1;
+	}
+
+	//read HID report
+	res = hid_read(handle, in_buf, report_size++);
+	if (res < 0) {
+		std::cout << "Unable to read HID report from USB device\n";
+		return -1;
+	}
+	for (i = 0; i < report_size; i++) {
+		resp_msg[i] = in_buf[i];
+	}
+
+	return 0; 
+}
+
+
+#endif
+
+
+
+
+
+
+
+
+

+ 115 - 0
src/yk_usb_device.h

@@ -0,0 +1,115 @@
+/*******************************************************************************
+Copyright 2017 Yepkit Lda (www.yepkit.com)
+
+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 _YK_USB_DEVICE_H_
+#define _YK_USB_DEVICE_H_
+
+#ifdef _LIBUSB_
+#include <usbhid.h>
+#else
+#include <hidapi.h>
+#endif
+#include <stdlib.h>
+
+/**
+ * \defgroup yepkit_usb_device_handler Yepkit USB device handling
+ */
+
+#ifndef _LIBUSB_
+#define USB_CMD_NON_BLOCKING	1	//1 -> Set the USB device handle to be non-blocking
+#define USB_CMD_BLOCKING	0	//0 -> Set the USB device handle to be blocking and wait for response
+#endif
+
+/**
+ * \ingroup yepkit_usb_device_handler
+ * 
+ * \brief Handles the USB HID for a given PID and VID.
+ */
+class UsbDevice {
+
+	public:
+
+		UsbDevice(unsigned int vendor_id, unsigned int product_id);
+		int sendHidReport(char *serial, unsigned char *msg, unsigned char *resp_msg, int report_size);
+
+                /**
+		 * Prints to standard output the list of connected devices with PID a VID provided in the class constructor.
+		 * 
+		 * \return Number of attached devices.
+		 */
+		int listConnected(void);    //List connected devices
+
+	private:
+
+		unsigned short vid;       
+		unsigned short pid; 
+#ifndef _LIBUSB_
+		hid_device *handle;
+#endif
+
+	protected:
+
+		unsigned char hid_report_out[64];
+		unsigned char hid_report_in[64];
+		char *usb_serial = NULL;
+
+};
+
+/*****************************************************************
+ * Function: 
+ *
+ *  send_usb_msg
+ *
+ *
+ * Description:
+ *
+ *  Sends HID report with the data provided in the input buffer
+ *  "msg". 
+ *
+ *
+ * Inputs:
+ *
+ *      serial      -   target usb device serial number string
+ *
+ *      msg         -   message (HID report) to be sent
+ *
+ *      resp_msg    -   response message (HID report) received
+ *
+ *
+ * Outputs:
+ *
+ *  The function returns the following value.
+ *      0   -   No error
+ *      -1  -   Error
+ *
+ *  In the case of error, a message is printed into the standard
+ *  output.
+ *
+ *
+ * Precedences: 
+ *
+ *  Requires that VENDOR_ID and PRODUCT_ID constants are defined.
+ *
+ *
+ *****************************************************************/
+int send_usb_msg(char *serial, char *msg, char *resp_msg); 
+char commands(char *cmd, char *resp, int num);
+char command(char cmd);
+char commandsBySerial(char *iSerial, char *cmd, char *resp, int num);
+char commandBySerial(char *iSerial, char cmd);
+int listDevices();
+
+
+#endif // USBCOM_H

+ 14 - 0
src/yktrl.cpp

@@ -0,0 +1,14 @@
+// Program entry point
+#include "commandParser.h"
+
+
+unsigned int PRODUCT_ID = 0;
+char *app_exc_name;
+
+int main(int argc, char* argv[])
+{
+	app_exc_name = argv[0];
+    	
+    	return commandParser(argc, argv);
+}
+

+ 283 - 0
src/ykush/ykush.cpp

@@ -0,0 +1,283 @@
+/*******************************************************************************
+Copyright 2017 Yepkit Lda (www.yepkit.com)
+
+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 "ykush.h"
+#include <stdio.h>
+#include <ykush_help.h>
+#include <command_parser.h>
+#include <iostream>
+
+
+
+int ykush_cmd_parser(int argc, char** argv)
+{
+	char bySerialFlag = 0;
+	enum ykushAction action = YKUSH_HELP;
+	Ykush ykush( 0xF2F7 );
+	Ykush ykushLegacy( 0x0042 );
+	char port;
+	char status_response = 0;
+
+	
+	if((argv[1][0]=='-') && (argv[1][1]=='s')) {
+		if(argc < 5) {
+			ykush.print_help(argv[0]);
+			return -1;
+		}
+		bySerialFlag = 1;
+		if(argv[3][0]=='-' && argv[3][1]=='u') {
+			action = YKUSH_PORT_UP;
+			port = argv[4][0];
+		} else if(argv[3][0]=='-' && argv[3][1]=='d') {
+			action = YKUSH_PORT_DOWN;
+			port = argv[4][0];
+		} else if(argv[3][0]=='-' && argv[3][1]=='l') {
+			action = YKUSH_LIST_BOARDS;
+		} else if(argv[3][0]=='-' && argv[3][1]=='g') {
+			action = YKUSH_GET_STATUS;
+			port = argv[4][0];
+		} else {
+			ykush.print_help(argv[0]);
+			return -1;
+		}
+
+	} else if((argv[1][0]=='-') && (argv[1][1]=='u')) {
+		if(argc < 3) {
+			ykush.print_help(argv[0]);
+			return -1;
+		}
+		action = YKUSH_PORT_UP;
+		port = argv[2][0];
+	} else if((argv[1][0]=='-') && (argv[1][1]=='d')) {
+		if(argc < 3) {
+			ykush.print_help(argv[0]);
+			return -1;
+		}
+		action = YKUSH_PORT_DOWN;
+		port = argv[2][0];
+	} else if((argv[1][0]=='-') && (argv[1][1]=='l')) {
+		action = YKUSH_LIST_BOARDS;
+	} else if((argv[1][0]=='-') && (argv[1][1]=='g')) {
+		if(argc < 3) {
+			ykush.print_help(argv[0]);
+			return -1;
+		}
+		action = YKUSH_GET_STATUS;
+		port = argv[2][0];
+	} else {
+		ykush.print_help(argv[0]);
+		return -1;
+	}
+
+	switch (action) {
+
+	case YKUSH_PORT_UP:
+		if(bySerialFlag) {
+			if(ykush.port_up(argv[2], port) == -1) {
+				ykushLegacy.port_up(argv[2], port);
+			}
+		} else {
+			if(ykush.port_up(NULL, port) == -1) {
+				ykushLegacy.port_up(NULL, port);
+			}
+		}
+		break;
+
+	case YKUSH_PORT_DOWN:
+		if ( bySerialFlag ) {
+			if ( ykush.port_down(argv[2], port) < 0 ) {
+				return ykushLegacy.port_down(argv[2], port);
+			}
+		} else {
+			if ( ykush.port_down(NULL, port) < 0 ) {
+				return ykushLegacy.port_down(NULL, port);
+			}
+		}
+		break;
+
+	case YKUSH_LIST_BOARDS:
+			return ykush_list_attached(); 
+		break;
+
+	case YKUSH_GET_STATUS:
+		if ( bySerialFlag ) {
+			status_response = ykush.get_port_status(argv[2], port);
+			if ( status_response >> 4 ) {
+				printf("\n\nDownstream port %d is ON\n\n", status_response & 0x0F );
+			} else {
+				printf("\n\nDownstream port %d is OFF\n\n", status_response & 0x0F);
+			}
+		} else {
+			status_response = ykush.get_port_status(NULL, port);
+			if ( status_response >> 4 ) {
+				printf("\n\nDownstream port %d is ON\n\n", status_response & 0x0F);
+			} else {
+				printf("\n\nDownstream port %d is OFF\n\n", status_response & 0x0F);
+			}
+		}   
+		break;
+
+	default:
+		ykush.print_help(argv[0]);
+		return -1;
+		break;
+	}
+	return 0;
+}
+
+
+int Ykush::port_up(char *serial, char port)
+{  
+	switch(port) {
+	case '1':
+		hid_report_out[0] = 0x11;
+		break;
+	case '2':     
+		hid_report_out[0] = 0x12;
+		break;
+	case '3':     
+		hid_report_out[0] = 0x13;
+		break;
+	case 'a':     
+		hid_report_out[0] = 0x1a;
+		break;
+	default:
+		return -1;
+		break;
+
+	}
+
+	int res;
+	if(is_legacy)
+		res = sendHidReport(serial, hid_report_out, hid_report_in, 6);
+	else
+		res = sendHidReport(serial, hid_report_out, hid_report_in, 64);
+
+	if ( res < 1 )
+		return res;
+	
+	if ( hid_report_in[0] == 0x01 )
+		return 0;
+	return -1;
+}
+
+
+
+int Ykush::port_down(char *serial, char port)
+{
+	switch(port){
+	case '1':
+		hid_report_out[0] = 0x01;
+		break;
+	case '2':     
+		hid_report_out[0] = 0x02;
+		break;
+	case '3':     
+		hid_report_out[0] = 0x03;
+		break;
+	case 'a':     
+		hid_report_out[0] = 0x0a;
+		break;
+	default:
+		return -1;
+		break;
+
+	}
+	
+	int res;
+	if(is_legacy)
+		res = sendHidReport(serial, hid_report_out, hid_report_in, 6);
+	else
+		res = sendHidReport(serial, hid_report_out, hid_report_in, 64);
+
+	if ( res < 1 )
+		return res;
+	
+	if ( hid_report_in[0] == 0x01 )
+		return 0;
+	return -1;
+}
+
+
+
+int Ykush::get_port_status(char *serial, char port)
+{
+	switch(port) {
+	case '1':
+		hid_report_out[0] = 0x21;
+		break;
+	case '2':     
+		hid_report_out[0] = 0x22;
+		break;
+	case '3':     
+		hid_report_out[0] = 0x23;
+		break;
+	default:
+		return -1;
+		break;
+	}
+	
+	int res;
+	if(is_legacy)
+		res = sendHidReport(serial, hid_report_out, hid_report_in, 6);
+	else
+		res = sendHidReport(serial, hid_report_out, hid_report_in, 64);
+
+	if ( res < 0 )
+		return res;
+
+	if ( hid_report_in[0] == 0x01 )
+		return hid_report_in[1];
+	return -1;
+}
+
+
+
+int ykush_list_attached()
+{
+	Ykush ykush( 0xF2F7 );
+	Ykush ykushLegacy( 0x0042 );
+
+	printf("\nAttached YKUSH Boards:\n");        
+	if( ykush.listConnected() == 0 ) {
+		if( ykushLegacy.listConnected() == 0 ) {
+			printf("\nNo YKUSH boards found.");
+		}
+	} else {
+		ykushLegacy.listConnected();
+	}
+
+	printf("\n");
+	return 0;
+}
+
+
+
+void Ykush::print_help(char *exec_name)
+{
+	Help help( exec_name );
+
+	help.print_version();
+	help.print_usage();
+	help.print_ykush();
+
+}
+
+
+
+
+
+

+ 104 - 0
src/ykush/ykush.h

@@ -0,0 +1,104 @@
+/*******************************************************************************
+Copyright 2017 Yepkit Lda (www.yepkit.com)
+
+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 _YKUSH_H_
+#define _YKUSH_H_
+
+#include <yk_usb_device.h>
+#include <command_parser.h>
+
+/**
+ * \defgroup ykush YKUSH boards
+ */
+
+/**
+ * \ingroup ykush
+ * \brief Available options for YKUSH boards.
+ */
+enum ykushAction {
+	YKUSH_PORT_UP,
+	YKUSH_PORT_DOWN,
+	YKUSH_PORT_STATUS,
+	YKUSH_LIST_BOARDS,
+	YKUSH_GET_STATUS,
+	YKUSH_HELP
+};
+
+/**
+ * \ingroup ykush
+ * \brief Handles the YKUSH device.
+ */
+class Ykush : public UsbDevice  
+{
+	public:
+
+		Ykush(unsigned int pid)
+		: UsbDevice(0x04D8, pid)
+		{     
+			if( pid == 0x0042 ) {
+				is_legacy = true;
+			} else {
+				is_legacy = false;
+			}
+			non_blocking_usb_comm = false;
+		}
+
+		int get_port_status(char *serial, char port);     //get downstream port status
+
+		/**
+		 * \brief Switch ON YKUSH downstream(s).
+		 * 
+		 */
+		int port_up(char *serial, char port);
+
+		int port_down(char *serial, char port);
+
+		void print_help(char *exec_name);
+
+	private:
+
+		bool is_legacy;
+		bool non_blocking_usb_comm;
+    
+};
+
+
+
+
+
+//---------------------------------
+//FUNCTIONS
+//---------------------------------
+
+int ykush_cmd_parser(int argc, char** argv);
+
+
+void ykush_help(char * execName);
+
+
+void ykush_up(char * iserial);
+
+
+void ykush_down(char * iserial);
+
+
+int ykush_list_attached(void); 
+
+
+
+#endif
+
+

+ 417 - 0
src/ykush2/ykush2.cpp

@@ -0,0 +1,417 @@
+/*******************************************************************************
+Copyright 2017 Yepkit Lda (www.yepkit.com)
+
+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 "stdafx.h"
+#include "ykush2.h"
+#include <stdio.h>
+#include <ykush_help.h>
+
+
+
+enum ykush2Action
+{
+    PORT_UP,
+    PORT_DOWN,
+    PORT_STATUS,
+    LIST_BOARDS,
+    GET_STATUS,
+    HELP
+};
+
+
+
+
+/*********************************************************
+ *  Function: ykushxs_cmd_parser
+ *
+ *  Description:
+ *
+ *  Does the parsing of the user command and call the
+ *  action to be undertaken.
+ *
+ *
+ *
+ *
+ *
+ *
+ *
+ *********************************************************/
+void ykush2_cmd_parser(int argc, char** argv)
+{
+    char bySerialFlag = 0;
+    enum ykush2Action action = HELP;
+    Ykush2 *ykush = new Ykush2(0xEFED);
+    char port;
+    char status_response = 0;
+    Help *help = new Help(argv[0]);
+
+
+
+    if((argv[2][0]=='-') && (argv[2][1]=='s'))
+    {
+        if(argc < 6)
+        {
+            //ykush_help(argv[0]);
+            help->print_ykush2();
+            return;
+        }
+        bySerialFlag = 1;
+        if(argv[4][0]=='-' && argv[4][1]=='u') 
+        {
+            action = PORT_UP;
+            port = argv[5][0];
+
+        } else if(argv[4][0]=='-' && argv[4][1]=='d') 
+        {
+            action = PORT_DOWN;
+            port = argv[5][0];
+        } else if(argv[4][0]=='-' && argv[4][1]=='l') 
+        {
+            action = LIST_BOARDS;
+        } else if(argv[4][0]=='-' && argv[4][1]=='g') 
+        {
+            action = GET_STATUS;
+            port = argv[5][0];
+        } else 
+        {
+            //ykush_help(argv[0]);
+            help->print_ykush2();
+            return;
+        }
+
+    } 
+    else if((argv[2][0]=='-') && (argv[2][1]=='u'))
+    {
+        if(argc < 4)
+        {
+            help->print_ykush2();
+            return;
+        }
+
+        action = PORT_UP;
+        port = argv[3][0];
+    }
+    else if((argv[2][0]=='-') && (argv[2][1]=='d'))
+    {
+        if(argc < 4)
+        {
+            help->print_ykush2();
+            return;
+        }
+        action = PORT_DOWN;
+        port = argv[3][0];
+    }
+    else if((argv[2][0]=='-') && (argv[2][1]=='l'))
+    {
+        action = LIST_BOARDS;
+
+    }
+    else if((argv[2][0]=='-') && (argv[2][1]=='g'))
+    {
+        if(argc < 4)
+        {
+            help->print_ykush2();
+            return;
+        }
+        action = GET_STATUS;
+        port = argv[3][0];
+    }
+    else
+    {
+        //ykush_help(argv[0]);
+        help->print_ykush2();
+        return;
+    }
+
+
+
+
+    switch (action)
+    {
+        case PORT_UP:
+            if(bySerialFlag)
+            {
+               ykush->port_up(argv[3], port); 
+            }
+            else
+            {
+                ykush->port_up(NULL, port); 
+            }
+            break;
+
+        case PORT_DOWN:
+            if(bySerialFlag)
+            {
+                ykush->port_down(argv[3], port); 
+            }
+            else
+            {
+                ykush->port_down(NULL, port); 
+            }
+            break;
+
+        case LIST_BOARDS:
+            ykush2_list_attached(); 
+            break;
+
+        case GET_STATUS:
+            if(bySerialFlag)
+            {
+                status_response = ykush->get_port_status(argv[3], port);
+                if (status_response >> 4)
+                {
+                    printf("\n\nDownstream port %d is ON\n\n", status_response & 0x0F );
+                } 
+                else 
+                {
+                    printf("\n\nDownstream port %d is OFF\n\n", status_response & 0x0F);
+                }
+            }
+            else
+            {
+                status_response = ykush->get_port_status(NULL, port);
+                if (status_response >> 4)
+                {
+                    printf("\n\nDownstream port %d is ON\n\n", status_response & 0x0F);
+                } 
+                else 
+                {
+                    printf("\n\nDownstream port %d is OFF\n\n", status_response & 0x0F);
+                }
+            }   
+            break;
+
+        default:
+            //ykush_help(argv[0]);
+            help->print_ykush2();
+            break;
+
+    }
+
+}
+
+
+
+
+
+/********************************************************
+ ********************************************************
+ *
+ *  Ykush Class Implementation
+ *
+ ********************************************************
+ ********************************************************/
+
+
+
+
+/*********************************************************
+ * Method: port_up
+ *
+ * Description:
+ *
+ * Commands the YKUSH XS board to turn ON the downstream
+ * port.
+ *
+ *
+ *
+ *
+ *********************************************************/
+int Ykush2::port_up(char *serial, char port)
+{  
+    switch(port)
+    {
+        case '1':
+            hid_report_out[0] = 0x11;
+            break;
+
+        case '2':     
+            hid_report_out[0] = 0x12;
+            break;
+        
+        case '3':     
+            hid_report_out[0] = 0x13;
+            break;
+
+        case 'a':     
+            hid_report_out[0] = 0x1a;
+            break;
+
+        default:
+            return 0;
+            break;
+
+    }
+    
+    
+    //send HID report to board
+    if(is_legacy)
+    {
+        return sendHidReport(serial, hid_report_out, hid_report_in, 6);
+    }
+    else
+    {
+        return sendHidReport(serial, hid_report_out, hid_report_in, 65);
+    }
+
+}
+
+
+/*********************************************************
+ * Method: port_down
+ *
+ * Description:
+ *
+ * Commands the YKUSH XS board to turn OFF the downstream
+ * port.
+ *
+ *
+ *
+ *
+ *********************************************************/
+int Ykush2::port_down(char *serial, char port)
+{
+    switch(port)
+    {
+        case '1':
+            hid_report_out[0] = 0x01;
+            break;
+
+        case '2':     
+            hid_report_out[0] = 0x02;
+            break;
+        
+        case '3':     
+            hid_report_out[0] = 0x03;
+            break;
+
+        case 'a':     
+            hid_report_out[0] = 0x0a;
+            break;
+
+        default:
+            return 0;
+            break;
+
+    }
+  
+    //send HID report to board
+    if(is_legacy)
+    {
+        return sendHidReport(serial, hid_report_out, hid_report_in, 6);
+    }
+    else
+    {
+        return sendHidReport(serial, hid_report_out, hid_report_in, 64);
+    }
+
+}
+
+
+
+/*********************************************************
+ * Method: get_port_status
+ *
+ * Description:
+ *
+ * Commands the YKUSH XS to respond with the port status.
+ *
+ *  1 -> Port is ON/UP
+ *  0 -> PORT is OFF/DOWN
+ *
+ *
+ *
+ *
+ *********************************************************/
+int Ykush2::get_port_status(char *serial, char port)
+{
+    int status;
+
+    switch(port)
+    {
+        case '1':
+            hid_report_out[0] = 0x21;
+            break;
+
+        case '2':     
+            hid_report_out[0] = 0x22;
+            break;
+        
+        case '3':     
+            hid_report_out[0] = 0x23;
+            break;
+
+        default:
+            return 0;
+            break;
+
+    }
+  
+    //send HID report to board
+    if(is_legacy)
+    {
+        sendHidReport(serial, hid_report_out, hid_report_in, 6);
+    }
+    else
+    {
+        sendHidReport(serial, hid_report_out, hid_report_in, 64);
+    }
+
+    //handle board response HID report
+    status = hid_report_in[1];
+
+    return status;
+}
+
+
+
+/****************************************************
+ *
+ *
+ *
+ *
+ ****************************************************/ 
+void ykush2_list_attached()
+{
+    Ykush2 *ykush = new Ykush2(0xEFED);
+    Ykush2 *ykushLegacy = new Ykush2(0x0042);
+
+    printf("\n\nAttached YKUSH Boards:\n");        
+    if(ykush->listConnected()==0)
+    {
+        //try legacy
+        if(ykushLegacy->listConnected()==0)
+        {
+            printf("\n\nNo YKUSH boards found.");
+        }
+    } 
+    else
+    {
+        //list legacy boards if attached 
+        ykushLegacy->listConnected();
+    }
+
+    printf("\n\n");
+
+}
+
+
+
+
+
+
+
+

+ 70 - 0
src/ykush2/ykush2.h

@@ -0,0 +1,70 @@
+/*******************************************************************************
+Copyright 2017 Yepkit Lda (www.yepkit.com)
+
+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 _YKUSH2_H_
+#define _YKUSH2_H_
+
+
+#include <yk_usb_device.h>
+
+
+
+
+
+//------------------------------------
+//CLASSES
+//------------------------------------
+
+class Ykush2 : public UsbDevice  
+{
+    public:
+
+        Ykush2(unsigned int pid)
+            : UsbDevice(0x04D8, pid)
+        {     
+        }
+
+        int get_port_status(char *serial, char port);     //get downstream port status
+
+        int port_up(char *serial, char port);
+
+        int port_down(char *serial, char port);
+
+    private:
+
+        bool is_legacy;
+    
+};
+
+
+
+
+
+//---------------------------------
+//FUNCTIONS
+//---------------------------------
+
+void ykush2_cmd_parser(int argc, char** argv);
+
+
+void ykush2_list_attached(void); 
+
+
+
+#endif
+
+

+ 857 - 0
src/ykush3/ykush3.cpp

@@ -0,0 +1,857 @@
+/*******************************************************************************
+Copyright 2017 Yepkit Lda (www.yepkit.com)
+
+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 <ykush3.h>
+#include <stdio.h>
+#include <ykush_help.h>
+#include <command_parser.h>
+#include <iostream>
+#include <string>
+#include <string2val.h>
+#include <cstring>
+
+
+extern char *app_exc_name;
+
+
+int 
+ykush3_cmd_parser (int argc, char** argv)
+  {
+    char bySerialFlag = 0;
+    enum ykush3Action action = YKUSH3_HELP;
+    Ykush3 ykush3;
+    char port;
+    char value;
+    char status_response = 0;
+    bool action_taken = false;
+    
+    if (argc < 3)
+      {
+        ykush3.print_help ();
+        return -1;
+      }
+
+    std::string str = argv[2];
+
+    if (str.compare ("-s") == 0) 
+      {	
+        //BY SERIAL
+        if (argc < 5) 
+          {
+            ykush3.print_help ();
+            return -1;
+          }
+        // set serial in object
+        ykush3.set_usb_serial(argv[3]);
+
+        str = argv[4];
+        bySerialFlag = 1;
+        if (str.compare ("-u") == 0 ) 
+          {
+            action = YKUSH3_PORT_UP;
+            port = argv[5][0];
+          }
+        else if (str.compare ("-d") == 0 ) 
+          {  
+            action = YKUSH3_PORT_DOWN;
+            port = argv[5][0];
+          }
+        else if (str.compare ("-g") == 0 )
+          {
+            action = YKUSH3_GET_STATUS;
+            port = argv[5][0];
+          }
+        else if (str.compare ("-on") == 0 )
+          {
+            action = YKUSH3_EXT_CTRL_ON;
+          }
+        else if (str.compare ("-off") == 0 )
+          {
+            action = YKUSH3_EXT_CTRL_OFF;
+          } 
+        else if (str.compare ("-w") == 0 )
+          {
+            if (argc < 7) 
+              {
+                ykush3.print_help ();
+                return -1;
+              }
+            action = YKUSH3_WRITE_IO;
+            port = argv[5][0];
+            value = argv[6][0]; 
+          } 
+        else if (str.compare ("-r") == 0) 
+          { 
+            action = YKUSH3_READ_IO;
+            port = argv[5][0];
+          } 
+        else if (str.compare ("-c") == 0)
+          { 
+            action = YKUSH3_CONFIG;
+            port = argv[5][0];
+            value = argv[6][0];
+          } 
+        else if (str.compare("--reset") == 0) 
+          { 
+            action = YKUSH3_RESET;
+          }
+        else if (str.compare ("--gpio") == 0) 
+          {
+            std::string str2 = argv[5];
+            if (str2.compare ("enable") == 0) 
+              {
+                action = YKUSH3_GPIO_EN;
+              }
+            else if (str2.compare ("disable") == 0 ) 
+              {
+                action = YKUSH3_GPIO_DIS;
+              } 
+            else 
+              {
+                ykush3.print_help ();
+                return -1;
+              }
+          } 
+        else if (str.compare ("--boot") == 0) 
+          { 
+            action = YKUSH3_ENTER_BOOTLOADER;		
+          }
+        else if (str.compare ("--firmware-version") == 0)
+          {
+            action = YKUSH3_FIRMWARE_VERSION;
+          }
+        else if (str.compare ("--bootloader-version") == 0)
+          {
+            action = YKUSH3_BOOTLOADER_VERSION;
+          }
+        else
+          {
+            ykush3.print_help ();
+            return -1;
+          }
+      }
+    // Without serial prefix
+    else if (str.compare ("-u") == 0) 
+      {
+        if (argc < 3)
+          {
+            ykush3.print_help ();
+            return -1;
+          }
+        action = YKUSH3_PORT_UP;
+        port = argv[3][0];
+      }
+    else if (str.compare ("-d") == 0)
+      {
+        if (argc < 4) 
+          {
+            ykush3.print_help ();
+            return -1;
+          }
+        action = YKUSH3_PORT_DOWN;
+        port = argv[3][0];
+      }
+    else if (str.compare ("-l") == 0)
+      {
+        action = YKUSH3_LIST_BOARDS;
+      } 
+    else if (str.compare ("-g") == 0)
+      {
+        if (argc < 4)
+          {
+            ykush3.print_help ();
+            return -1;
+          }
+        action = YKUSH3_GET_STATUS;
+        port = argv[3][0];
+      }
+    else if (str.compare ("-on") == 0)
+      {
+        action = YKUSH3_EXT_CTRL_ON;
+      }
+    else if (str.compare ("-off") == 0)
+      {
+        action = YKUSH3_EXT_CTRL_OFF;
+      } 
+    else if (str.compare ("-w") == 0)
+      {
+        if (argc < 5)
+          {
+            ykush3.print_help ();
+            return -1;
+          }
+        action = YKUSH3_WRITE_IO;
+        port = argv[3][0];
+        value = argv[4][0];
+      }
+    else if (str.compare ("-r") == 0)
+      { 
+        action = YKUSH3_READ_IO;
+        port = argv[3][0];
+      } 
+    else if (str.compare ("-c") == 0)
+      {
+        if (argc < 5)
+          {
+            ykush3.print_help ();
+            return -1;
+          }
+        action = YKUSH3_CONFIG;
+        port = argv[3][0];
+        value = argv[4][0];
+      }
+    else if (str.compare ("--reset") == 0)
+      {
+        action = YKUSH3_RESET;
+      }
+    else if (str.compare ("--boot") == 0)
+      { 
+          action = YKUSH3_ENTER_BOOTLOADER;
+      }
+    else if (str.compare ("--gpio") == 0)
+      {
+          std::string str2 = argv[3];
+          if (str2.compare ("enable") == 0)
+            {
+              action = YKUSH3_GPIO_EN;
+            }
+          else if (str2.compare ("disable") == 0)
+            {
+              action = YKUSH3_GPIO_DIS;
+            }
+          else
+            {
+              ykush3.print_help ();
+              return -1;
+            }
+      }
+    else if (str.compare ("--firmware-version") == 0)
+      {
+        action = YKUSH3_FIRMWARE_VERSION;
+      }
+    else if (str.compare ("--bootloader-version") == 0)
+      {
+        action = YKUSH3_BOOTLOADER_VERSION;
+      }
+    else
+      {
+        ykush3.print_help ();
+        return -1;
+      }
+
+    switch (action)
+      {
+      case YKUSH3_PORT_UP:
+        if (bySerialFlag) 
+          return ykush3.port_up (argv[3], port); 
+        else
+          return ykush3.port_up (NULL, port); 
+        break;
+
+      case YKUSH3_PORT_DOWN:
+        if (bySerialFlag)
+          return ykush3.port_down (argv[3], port); 
+        else
+          return ykush3.port_down (NULL, port); 
+        break;
+
+      case YKUSH3_LIST_BOARDS:
+        ykush3_list_attached (); 
+        break;
+
+      case YKUSH3_GET_STATUS:
+        if (bySerialFlag)
+          {
+            status_response = ykush3.get_port_status (argv[3], port);
+            if (status_response < 0)
+              return status_response;
+            if (status_response >> 4)
+              printf ("\n\nDownstream port %d is ON\n\n", status_response & 0x0F);
+            else 
+              printf ("\n\nDownstream port %d is OFF\n\n", status_response & 0x0F);
+            return 0;
+          } 
+        else
+          {
+            status_response = ykush3.get_port_status (NULL, port);
+            if (status_response < 0)
+              return status_response;
+            if (status_response >> 4)
+                 printf ("\n\nDownstream port %d is ON\n\n", status_response & 0x0F);
+            else 
+                 printf ("\n\nDownstream port %d is OFF\n\n", status_response & 0x0F);
+            return 0;
+          }   
+        break;
+
+      case YKUSH3_EXT_CTRL_ON:
+        if (bySerialFlag)
+          return ykush3.port_up (argv[3], '4'); 
+        else
+          return ykush3.port_up (NULL, '4'); 
+        break;
+
+      case YKUSH3_EXT_CTRL_OFF:
+        if (bySerialFlag)
+          return ykush3.port_down (argv[3], '4'); 
+        else
+          return ykush3.port_down (NULL, '4'); 
+        break;
+
+      case YKUSH3_WRITE_IO:
+        if (bySerialFlag)
+          return ykush3.write_io (argv[3], port, value); 
+        else
+          return ykush3.write_io (NULL, port, value); 
+        return 0;
+        break;
+
+      case YKUSH3_READ_IO:
+        if (bySerialFlag)
+          printf ("\n%d\n", ykush3.read_io(argv[3], port)); 
+        else
+          printf ("\n%d\n", ykush3.read_io(NULL, port)); 
+        return 0;
+        break;
+
+      case YKUSH3_CONFIG:
+        if (bySerialFlag)
+              return ykush3.config_port (argv[3], port, value); 
+        else
+              return ykush3.config_port (NULL, port, value); 
+        break;
+
+      case YKUSH3_RESET:
+        if (bySerialFlag)
+          return ykush3.reset (argv[3]); 
+        else
+          return ykush3.reset (NULL); 
+        break;
+
+      case YKUSH3_GPIO_EN:
+        if (bySerialFlag)
+          return ykush3.gpio_ctrl_enable (argv[3]); 
+        else
+          return ykush3.gpio_ctrl_enable (NULL); 
+        break;
+
+      case YKUSH3_GPIO_DIS:
+        if (bySerialFlag)
+          return ykush3.gpio_ctrl_disable (argv[3]); 
+        else
+          return ykush3.gpio_ctrl_disable (NULL); 
+        break;
+
+      case YKUSH3_ENTER_BOOTLOADER:
+        if (bySerialFlag)
+          return ykush3.enter_bootloader (argv[3]); 
+        else
+          return ykush3.enter_bootloader (NULL);
+        break;
+
+      case YKUSH3_FIRMWARE_VERSION:
+        return ykush3.display_version_firmware ();
+        break;
+      
+      case YKUSH3_BOOTLOADER_VERSION:
+        return ykush3.display_version_bootloader ();
+        break;
+
+      default:
+        ykush3.print_help ();
+        return -1;
+        break;
+
+      }
+
+    return 0;
+  }
+
+
+
+
+int Ykush3::port_up(char *serial, char port)
+{  
+	switch(port) {
+	case '1':
+		hid_report_out[0] = 0x11;
+		break;
+
+	case '2':     
+		hid_report_out[0] = 0x12;
+		break;
+		
+	case '3':     
+		hid_report_out[0] = 0x13;
+		break;
+
+	case 'a':     
+		hid_report_out[0] = 0x1a;
+		break;
+
+	case '4':     
+		hid_report_out[0] = 0x14;
+		break;
+
+	default:
+		return -1;
+		break;
+
+	}
+    
+    
+    //send HID report to board
+    return sendHidReport(serial, hid_report_out, hid_report_in, 64);
+
+}
+
+
+
+int Ykush3::port_down(char *serial, char port)
+{
+    switch(port)
+    {
+        case '1':
+            hid_report_out[0] = 0x01;
+            break;
+
+        case '2':     
+            hid_report_out[0] = 0x02;
+            break;
+        
+        case '3':     
+            hid_report_out[0] = 0x03;
+            break;
+
+        case 'a':     
+            hid_report_out[0] = 0x0a;
+            break;
+        
+        case '4':
+            hid_report_out[0] = 0x04;
+            break;
+
+        default:
+            return 0;
+            break;
+
+    }
+  
+    //send HID report to board
+    return sendHidReport(serial, hid_report_out, hid_report_in, 64);
+   
+
+}
+
+
+
+int Ykush3::get_port_status(char *serial, char port)
+{
+    int status;      
+
+    switch(port)
+    {
+        case '1':
+            hid_report_out[0] = 0x21;
+            break;
+
+        case '2':     
+            hid_report_out[0] = 0x22;
+            break;
+        
+        case '3':     
+            hid_report_out[0] = 0x23;
+            break;
+
+        case '4':     
+            hid_report_out[0] = 0x24;
+            break;
+
+        default:
+            return 0;
+            break;
+
+    }
+  
+    //send HID report to board 
+    sendHidReport(serial, hid_report_out, hid_report_in, 64);
+
+    //handle board response HID report
+    status = hid_report_in[1];
+
+    return status;
+}
+
+
+
+int Ykush3::write_io(char *serial, char port, char value)
+{
+
+    hid_report_out[0] = 0x31;
+    if(value=='0'){
+        hid_report_out[2] = 0; 
+    } else {
+        hid_report_out[2] = 1; 
+    }
+
+
+    switch(port)
+    {
+        case '1':
+            hid_report_out[1] = 0x01;
+            break;
+
+        case '2':     
+            hid_report_out[1] = 0x02;
+            break;
+        
+        case '3':     
+            hid_report_out[1] = 0x03;
+            break;
+ 
+        default:
+            return 0;
+            break;
+
+    }
+    
+    //send HID report to board
+    return sendHidReport(serial, hid_report_out, hid_report_in, 64);
+
+}
+
+
+
+int Ykush3::read_io(char *serial, char port)
+{
+    
+    hid_report_out[0] = 0x30;
+
+    switch(port)
+    {
+        case '1':
+            hid_report_out[1] = 0x01;
+            break;
+
+        case '2':     
+            hid_report_out[1] = 0x02;
+            break;
+        
+        case '3':     
+            hid_report_out[1] = 0x03;
+            break;
+ 
+        default:
+            return 0;
+            break;
+
+    }
+    
+    
+    //send HID report to board
+    sendHidReport(serial, hid_report_out, hid_report_in, 64);
+    
+    //process response
+    return hid_report_in[3];
+
+}
+
+ 
+int Ykush3::config_port(char *serial, char port, char value)
+{
+	hid_report_out[0] = 0x41;
+	if ( value == '0' )
+		hid_report_out[2] = 0; 
+	else if ( value == '1' )
+		hid_report_out[2] = 1; 
+	else
+		hid_report_out[2] = 2;	//Persist mode
+	
+
+
+	switch ( port ) {
+	case '1':
+		hid_report_out[1] = 0x01;
+		break;
+	case '2':     
+		hid_report_out[1] = 0x02;
+		break;
+	case '3':     
+		hid_report_out[1] = 0x03;
+		break;
+	case 'e':     
+		hid_report_out[1] = 0x04;
+		break;
+	default:
+		return 0;
+		break;
+	}
+
+	//send HID report to board
+	return sendHidReport(serial, hid_report_out, hid_report_in, 64);
+
+}
+
+
+int Ykush3::reset(char *serial)
+{
+	hid_report_out[0] = 0x55;        
+	
+	//send HID report to board
+	sendHidReport(serial, hid_report_out, hid_report_in, 64);
+	return 0;
+}
+
+
+
+int
+Ykush3::gpio_ctrl_enable (char *serial)
+  {
+    hid_report_out[0] = 0x32;
+    hid_report_out[1] = 0x01;
+    
+    //send HID report to board
+    sendHidReport (serial, hid_report_out, hid_report_in, 64);
+    return 0;
+  }
+
+
+
+int
+Ykush3::gpio_ctrl_disable (char *serial)
+  {
+    hid_report_out[0] = 0x32;
+    hid_report_out[1] = 0x00;
+    
+    //send HID report to board
+    sendHidReport (serial, hid_report_out, hid_report_in, 64);
+    return 0;
+  }
+
+
+
+int 
+Ykush3::enter_bootloader (char *serial)
+  {
+    hid_report_out[0] = 0x42;
+    
+    //send HID report to board
+    sendHidReport (serial, hid_report_out, hid_report_in, 64);
+    return 0;
+  }
+
+
+
+int Ykush3::i2c_enable_disable_control(bool enable_flag) 
+{
+	hid_report_out[0] = 0x51;
+	hid_report_out[1] = 0x01;
+	
+	if ( enable_flag )
+		hid_report_out[2] = 0x01;
+	else 
+		hid_report_out[2] = 0x00;
+
+	sendHidReport(usb_serial, hid_report_out, hid_report_in, 64);
+
+	if ( (hid_report_in[0] == 0x01) && (hid_report_in[1] == 0x51) ) {
+		//command executed with success
+		return 0;
+	} 
+
+	return 1;
+}
+
+
+int Ykush3::i2c_enable_disable_gateway(bool enable_flag)
+{
+	hid_report_out[0] = 0x51;
+	hid_report_out[1] = 0x02;
+
+	if ( enable_flag )
+		hid_report_out[2] = 0x01;
+	else 
+		hid_report_out[2] = 0x00;
+
+	sendHidReport(usb_serial, hid_report_out, hid_report_in, 64);
+
+	if ( (hid_report_in[0] == 0x01) && (hid_report_in[1] == 0x51) ) {
+		//command executed with success
+		return 0;
+	} 
+
+	return 1;
+}
+
+
+int Ykush3::i2c_set_address(char *i2c_address)
+{
+	std::cout << "i2c_set_address com address: " << i2c_address << std::endl;
+
+	hid_report_out[0] = 0x51;
+	hid_report_out[1] = 0x03;
+
+	hex2bin(i2c_address + 2, &hid_report_out[2], 2);
+	sendHidReport(usb_serial, hid_report_out, hid_report_in, 64);
+
+	if ( (hid_report_in[0] == 0x01) && (hid_report_in[1] == 0x51) ) {
+		//command executed with success
+		return 0;
+	}
+
+	return 1;
+}
+
+
+int Ykush3::i2c_write(char *i2c_address_ASCII, char *num_bytes_ASCII, char **data_to_write_ASCII)
+{
+	hid_report_out[0] = 0x52;
+	hid_report_out[1] = 0x01;
+
+	//convert i2c_address_ASCII to binary
+	hex2bin(i2c_address_ASCII + 2, &hid_report_out[2], 2);
+
+	//convert num_bytes_ASCII to binary
+	int size = strlen(num_bytes_ASCII);
+	if ( size <= 0 )
+		return 1;
+	dec2bin(num_bytes_ASCII, &hid_report_out[3], size);
+	if ( hid_report_out[3] > 60 ) 
+		return 2;
+
+	//convert data_to_write_ASCII to binary
+	for ( int i = 0; i < hid_report_out[3]; i++ ) {
+		hex2bin(num_bytes_ASCII + 2, &hid_report_out[i + 4], 2);
+	}
+
+	sendHidReport(usb_serial, hid_report_out, hid_report_in, 64);
+
+	if ( (hid_report_in[0] == 0x01) && (hid_report_in[1] == 0x52) ) {
+		//command executed with success
+		return 0;
+	}
+	return 0;
+}
+
+
+int Ykush3::i2c_read(char *i2c_address_ASCII, char *num_bytes_ASCII, unsigned char *data_buffer, int *bytes_read)
+{
+	hid_report_out[0] = 0x52;
+	hid_report_out[1] = 0x02;
+
+	//convert i2c_address_ASCII to binary
+	hex2bin(i2c_address_ASCII + 2, &hid_report_out[2], 2);
+
+	//convert num_bytes_ASCII to binary
+	int size = strlen(num_bytes_ASCII);
+	if ( size <= 0 )
+		return 1;
+	dec2bin(num_bytes_ASCII, &hid_report_out[3], size);
+
+	sendHidReport(usb_serial, hid_report_out, hid_report_in, 64);
+
+	//handle response message
+	if ((hid_report_in[0] == 0x01) && (hid_report_in[1] == 0x52)) {
+		//get num_bytes
+		if (hid_report_in[2] < 0)
+			return 1;
+		int i;
+		for (i = 0; (i < hid_report_in[2]) && (i < 60); i++) {
+			data_buffer[i] = hid_report_in[i + 4];
+		}
+		*bytes_read = i; 
+	} else {
+		return 1;
+	}
+
+	return 0;
+}
+
+
+int 
+Ykush3::display_version_bootloader (void)
+  {
+    int major, minor, patch;
+    hid_report_out[0] = 0x61;
+    hid_report_out[1] = 0x01;
+    if (sendHidReport (usb_serial, hid_report_out, hid_report_in, 64) != 0 ) 
+      {
+        std::cout << "Unable to get bootloader version \n";
+        return 1; 
+      }
+    //print response
+    if ((hid_report_in[0] != 0x01) && (hid_report_in[0] != 0x61)) 
+      {
+        std::cout << "Bootloader version-0.10.0\n";
+        return 0; 
+      }
+
+    std::cout << "Bootloader version-" << (int) hid_report_in[2] << "." << (int) hid_report_in[3] << "." << (int) hid_report_in[4] << std::endl;
+    return 0;
+  }
+		
+
+int
+Ykush3::display_version_firmware (void)
+  {
+    hid_report_out[0] = 0x61;
+    hid_report_out[1] = 0x02;
+    sendHidReport(usb_serial, hid_report_out, hid_report_in, 64);
+    //print response
+    if (( hid_report_in[0] != 0x01) && (hid_report_in[0] != 0x61))
+      {
+        std::cout << "Firmware version-1.0.0\n";
+        return 0; 
+      }
+    std::cout << "Firmware version-" << (int) hid_report_in[2] << "." << (int) hid_report_in[3] << "." << (int) hid_report_in[4] << std::endl;
+    return 0;
+  }
+
+
+
+int Ykush3::set_usb_serial(char *serial) 
+{
+	usb_serial = serial;
+	return 0;
+}
+
+
+ 
+int ykush3_list_attached()
+{
+	Ykush3 ykush3;
+	printf("\n\nAttached YKUSH 3 Boards:\n");        
+	if( ykush3.listConnected() == 0 )
+		printf("\n\nNo YKUSH 3 boards found.");
+	printf("\n\n");
+	return 0;
+}
+
+
+void Ykush3::print_help(void) 
+{
+	Help help(app_exc_name);
+
+	help.print_version();
+	help.print_usage();
+	help.print_ykush3();
+}
+
+
+
+
+
+

+ 128 - 0
src/ykush3/ykush3.h

@@ -0,0 +1,128 @@
+/*******************************************************************************
+Copyright 2017 Yepkit Lda (www.yepkit.com)
+
+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 _YKUSH3_H_
+#define _YKUSH3_H_
+
+
+#include <yk_usb_device.h>
+#include <command_parser.h>
+
+enum ykush3Action {
+	YKUSH3_PORT_UP,
+	YKUSH3_PORT_DOWN,
+	YKUSH3_PORT_STATUS,
+	YKUSH3_LIST_BOARDS,
+	YKUSH3_GET_STATUS,
+	YKUSH3_EXT_CTRL_ON,
+	YKUSH3_EXT_CTRL_OFF,
+	YKUSH3_READ_IO,
+	YKUSH3_WRITE_IO,
+	YKUSH3_CONFIG,
+	YKUSH3_RESET,
+	YKUSH3_GPIO_EN,
+	YKUSH3_GPIO_DIS,
+	YKUSH3_ENTER_BOOTLOADER,
+	//I2C
+	YKUSH3_I2C_CONTROL_ENABLE,
+	YKUSH3_YKUSH3_I2C_CONTROL_DISABLE,
+	YKUSH3_I2C_GATEWAY_ENABLE,
+	YKUSH3_I2C_GATEWAY_DISABLE,
+	YKUSH3_I2C_SET_ADRRESS,
+	YKUSH3_I2C_WRITE,
+	YKUSH3_I2C_READ,
+  YKUSH3_FIRMWARE_VERSION,
+  YKUSH3_BOOTLOADER_VERSION,
+	YKUSH3_HELP
+};
+
+
+class Ykush3 : public UsbDevice  
+{
+    	public:
+
+		Ykush3()
+		: UsbDevice(0x04D8, 0xF11B)
+		{  
+      usb_serial = NULL;
+		}
+
+		//Downstream ports and 5V EXT port control 
+		int get_port_status(char *serial, char port);     //get downstream port status
+
+		int port_up(char *serial, char port);
+
+		int port_down(char *serial, char port);
+
+
+		//GPIO control
+		int write_io(char *serial, char port, char value);
+
+		int read_io(char *serial, char port);
+		
+		int gpio_ctrl_enable(char *serial);
+		
+		int gpio_ctrl_disable(char *serial);
+		
+		int enter_bootloader(char *serial);
+
+
+		//Configurations control
+		int config_port(char *serial, char port, char value);
+
+		//Reset
+		int reset(char *serial);
+		
+		//Help
+		void print_help(void);
+
+		//I2C
+		int i2c_enable_disable_control(bool enable_flag);		//ToDo
+		int i2c_enable_disable_gateway(bool enable_flag);		//ToDo
+		int i2c_set_address(char *i2c_address);			//ToDo
+		int i2c_write(char *i2c_address_ASCII, char *num_bytes_ASCII, char **data_to_write_ASCII);	//ToDo
+		int i2c_read(char *i2c_address_ASCII, char *num_bytes_ASCII, unsigned char *data_buffer, int *bytes_read);	//ToDo
+
+		//Versioning
+		int display_version_bootloader (void);
+		int display_version_firmware (void);
+
+		int set_usb_serial(char *serial);
+	
+	private:
+
+		char *usb_serial;
+};
+
+
+
+
+
+//---------------------------------
+//FUNCTIONS
+//---------------------------------
+
+int ykush3_cmd_parser(int argc, char** argv);
+
+
+int ykush3_list_attached(void); 
+
+
+
+#endif
+
+

+ 18 - 10
ykushcmd/ykushcmd.vcxproj

@@ -1,5 +1,5 @@
 <?xml version="1.0" encoding="utf-8"?>
-<Project DefaultTargets="Build" ToolsVersion="14.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+<Project DefaultTargets="Build" ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
   <ItemGroup Label="ProjectConfigurations">
     <ProjectConfiguration Include="Debug|Win32">
       <Configuration>Debug</Configuration>
@@ -22,32 +22,32 @@
     <ProjectGuid>{C8815452-C975-41CE-8E08-E12E7E488901}</ProjectGuid>
     <Keyword>Win32Proj</Keyword>
     <RootNamespace>ykushcmd</RootNamespace>
-    <WindowsTargetPlatformVersion>8.1</WindowsTargetPlatformVersion>
+    <WindowsTargetPlatformVersion>10.0.15063.0</WindowsTargetPlatformVersion>
   </PropertyGroup>
   <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
   <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
     <ConfigurationType>Application</ConfigurationType>
     <UseDebugLibraries>true</UseDebugLibraries>
-    <PlatformToolset>v140</PlatformToolset>
+    <PlatformToolset>v141</PlatformToolset>
     <CharacterSet>Unicode</CharacterSet>
   </PropertyGroup>
   <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
     <ConfigurationType>Application</ConfigurationType>
     <UseDebugLibraries>false</UseDebugLibraries>
-    <PlatformToolset>v140</PlatformToolset>
+    <PlatformToolset>v141_xp</PlatformToolset>
     <WholeProgramOptimization>true</WholeProgramOptimization>
     <CharacterSet>Unicode</CharacterSet>
   </PropertyGroup>
   <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
     <ConfigurationType>Application</ConfigurationType>
     <UseDebugLibraries>true</UseDebugLibraries>
-    <PlatformToolset>v140</PlatformToolset>
+    <PlatformToolset>v141</PlatformToolset>
     <CharacterSet>Unicode</CharacterSet>
   </PropertyGroup>
   <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
     <ConfigurationType>Application</ConfigurationType>
     <UseDebugLibraries>false</UseDebugLibraries>
-    <PlatformToolset>v140</PlatformToolset>
+    <PlatformToolset>v141</PlatformToolset>
     <WholeProgramOptimization>true</WholeProgramOptimization>
     <CharacterSet>Unicode</CharacterSet>
   </PropertyGroup>
@@ -116,14 +116,14 @@
       <IntrinsicFunctions>true</IntrinsicFunctions>
       <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
       <SDLCheck>true</SDLCheck>
-      <AdditionalIncludeDirectories>C:\yk\ykush\ykushcmd\windows;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
+      <AdditionalIncludeDirectories>$(ProjectDir);$(ProjectDir)\windows;$(ProjectDir)\help;$(ProjectDir)\ykush;$(ProjectDir)\ykushxs;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
     </ClCompile>
     <Link>
       <SubSystem>Console</SubSystem>
       <GenerateDebugInformation>true</GenerateDebugInformation>
       <EnableCOMDATFolding>true</EnableCOMDATFolding>
       <OptimizeReferences>true</OptimizeReferences>
-      <AdditionalLibraryDirectories>C:\yk\ykush\ykushcmd\windows;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
+      <AdditionalLibraryDirectories>$(ProjectDir)\windows;%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
       <AdditionalDependencies>hidapi.lib;%(AdditionalDependencies)</AdditionalDependencies>
     </Link>
   </ItemDefinitionGroup>
@@ -149,21 +149,29 @@
   </ItemGroup>
   <ItemGroup>
     <ClInclude Include="commandParser.h" />
+    <ClInclude Include="help\ykush_help.h" />
     <ClInclude Include="platformdefs.h" />
     <ClInclude Include="stdafx.h" />
     <ClInclude Include="targetver.h" />
-    <ClInclude Include="usbcom.h" />
+    <ClInclude Include="ykushxs\ykushxs.h" />
+    <ClInclude Include="ykush\ykush.h" />
+    <ClInclude Include="yk_usb_device.h" />
   </ItemGroup>
   <ItemGroup>
     <ClCompile Include="commandParser.cpp" />
+    <ClCompile Include="help\ykush_help.cpp">
+      <PreprocessorDefinitions Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">%(PreprocessorDefinitions)</PreprocessorDefinitions>
+    </ClCompile>
     <ClCompile Include="stdafx.cpp">
       <PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Create</PrecompiledHeader>
       <PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">Create</PrecompiledHeader>
       <PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">Create</PrecompiledHeader>
       <PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Release|x64'">Create</PrecompiledHeader>
     </ClCompile>
-    <ClCompile Include="usbcom.cpp" />
     <ClCompile Include="ykushcmd.cpp" />
+    <ClCompile Include="ykushxs\ykushxs.cpp" />
+    <ClCompile Include="ykush\ykush.cpp" />
+    <ClCompile Include="yk_usb_device.cpp" />
   </ItemGroup>
   <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
   <ImportGroup Label="ExtensionTargets">

+ 20 - 2
ykushcmd/ykushcmd.vcxproj.filters

@@ -30,7 +30,16 @@
     <ClInclude Include="commandParser.h">
       <Filter>Header Files</Filter>
     </ClInclude>
-    <ClInclude Include="usbcom.h">
+    <ClInclude Include="ykushxs\ykushxs.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="yk_usb_device.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="ykush\ykush.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="help\ykush_help.h">
       <Filter>Header Files</Filter>
     </ClInclude>
   </ItemGroup>
@@ -44,7 +53,16 @@
     <ClCompile Include="commandParser.cpp">
       <Filter>Source Files</Filter>
     </ClCompile>
-    <ClCompile Include="usbcom.cpp">
+    <ClCompile Include="ykushxs\ykushxs.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+    <ClCompile Include="yk_usb_device.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+    <ClCompile Include="help\ykush_help.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+    <ClCompile Include="ykush\ykush.cpp">
       <Filter>Source Files</Filter>
     </ClCompile>
   </ItemGroup>

+ 6 - 0
src/ykushcmd.vcxproj.user

@@ -0,0 +1,6 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <PropertyGroup>
+    <ShowAllFiles>false</ShowAllFiles>
+  </PropertyGroup>
+</Project>

+ 191 - 0
src/ykushxs/ykushxs.cpp

@@ -0,0 +1,191 @@
+/*******************************************************************************
+Copyright 2019 Yepkit Lda (www.yepkit.com)
+
+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 "ykushxs.h"
+#include <stdio.h>
+#include <ykush_help.h>
+
+
+enum ykushxsAction
+{
+	YKUSHXS_PORT_UP,
+	YKUSHXS_PORT_DOWN,
+	YKUSHXS_PORT_STATUS,
+	YKUSHXS_LIST_BOARDS,
+	YKUSHXS_GET_STATUS,
+	YKUSHXS_HELP
+};
+
+
+int ykushxs_cmd_parser(int argc, char** argv)
+{
+	char bySerialFlag = 0;
+	enum ykushxsAction action = YKUSHXS_HELP;
+	YkushXs ykushxs;
+	
+	if ( argc < 3 ) {
+		ykushxs.ykushxs_help(argv[0]);
+		return -1;
+	}
+
+	if ( ( argv[2][0] == '-' ) && ( argv[2][1] == 's' ) ) {
+		bySerialFlag = 1;
+		if ( (argv[4][0] == '-') && (argv[4][1] == 'u') ) {
+			action = YKUSHXS_PORT_UP;
+		} else if ( (argv[4][0] == '-') && (argv[4][1] == 'd') ) {
+			action = YKUSHXS_PORT_DOWN;
+		} else if ( (argv[4][0] == '-') && (argv[4][1] == 'l') ) {
+			action = YKUSHXS_LIST_BOARDS;
+		} else if ( (argv[4][0] == '-') && (argv[4][1] == 'g') ) {
+			action = YKUSHXS_GET_STATUS;
+		} else {
+			ykushxs.ykushxs_help(argv[0]);
+			return -1;
+		}
+	} else if ( (argv[2][0] == '-') && (argv[2][1] == 'u') ) {
+		action = YKUSHXS_PORT_UP;
+	} else if ( (argv[2][0] == '-') && (argv[2][1]=='d') ) {
+		action = YKUSHXS_PORT_DOWN;
+	} else if ( (argv[2][0] == '-') && (argv[2][1] == 'l') ) {
+		action = YKUSHXS_LIST_BOARDS;
+	} else if ( (argv[2][0] == '-') && (argv[2][1] == 'g') ) {
+		action = YKUSHXS_GET_STATUS;
+	} else {
+		ykushxs.ykushxs_help(argv[0]);
+		return -1;
+	}
+
+	switch ( action ) {
+	case YKUSHXS_PORT_UP:
+		if ( bySerialFlag ) {
+			return ykushxs.port_up( argv[3] );
+		} else {
+			return ykushxs.port_up(NULL);
+		}
+		break;
+	case YKUSHXS_PORT_DOWN:
+		if ( bySerialFlag ) {
+			return ykushxs.port_down(argv[3]);
+		} else {
+			return ykushxs.port_down(NULL);
+		}
+		break;
+	case YKUSHXS_LIST_BOARDS:
+		return ykushxs_list_attached(); 
+		break;
+	case YKUSHXS_GET_STATUS:
+		if ( bySerialFlag ){
+			if( ykushxs.get_port_status(argv[3]) == 0x11 ) {
+				printf("\n\nDownstream port is ON\n\n");
+			} else {
+				printf("\n\nDownstream port is OFF\n\n");
+			}
+		} else {
+			if ( ykushxs.get_port_status(NULL) == 0x11 ) {
+				printf("\n\nDownstream port is ON\n\n");
+			} else {
+				printf("\n\nDownstream port is OFF\n\n");
+			}
+		}   
+		break;
+	default:
+		ykushxs.ykushxs_help(argv[0]); 
+		return -1;
+		break;
+
+	}
+
+}
+
+
+int YkushXs::port_up(char *serial) {
+
+	hid_report_out[0] = 0x11;   //port up
+	
+	int res = sendHidReport(serial, hid_report_out, hid_report_in, 64);
+
+	if ( res < 0 )
+		return res;
+
+	if ( hid_report_in[0] == 0x01 )
+		return 0;
+	else
+		return -1;
+}
+
+
+int YkushXs::port_down(char *serial)
+{
+	hid_report_out[0] = 0x01;   //port down
+
+	int res = sendHidReport(serial, hid_report_out, hid_report_in, 64);
+
+	if ( res < 0 )
+		return res;
+
+	if ( hid_report_in[0] == 0x01 )
+		return 0;
+	else
+		return -1;
+}
+
+
+int YkushXs::get_port_status(char *serial)
+{
+	int status;
+
+	hid_report_out[0] = 0x21;   //get status
+
+	int res = sendHidReport(serial, hid_report_out, hid_report_in, 64);
+
+	if ( res < 0 )
+		return res;
+
+	if ( hid_report_in[0] == 0x01 )
+		return hid_report_in[1];
+	else
+		return -1;
+}
+
+
+int ykushxs_list_attached()
+{
+	YkushXs ykushxs;
+
+	printf("\n\nAttached YKUSH XS Boards:\n");        
+	if ( ykushxs.listConnected() == 0 ) {
+		printf("\nNo YKUSH XS boards found.");
+	}
+	printf("\n\n");
+	return 0;
+}
+
+
+
+void YkushXs::ykushxs_help(char * execName)
+{
+	Help help( execName );
+
+	help.print_version();
+	help.print_usage();
+	help.print_ykushxs();
+}
+
+
+
+
+
+

+ 78 - 0
src/ykushxs/ykushxs.h

@@ -0,0 +1,78 @@
+/*******************************************************************************
+Copyright 2017 Yepkit Lda (www.yepkit.com)
+
+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 _YKUSHXS_H_
+#define _YKUSHXS_H_
+
+
+#include <yk_usb_device.h>
+
+
+
+
+
+//------------------------------------
+//CLASSES
+//------------------------------------
+
+class YkushXs : public UsbDevice  
+{
+        public:
+
+            YkushXs()
+                : UsbDevice(0x04D8, 0xF0CD)
+            {            
+            }
+
+            int get_port_status(char *serial);     //get downstream port status
+
+            int port_up(char *serial);
+
+            int port_down(char *serial);
+
+            void ykushxs_help(char * execName);
+
+    
+};
+
+
+
+
+
+//---------------------------------
+//FUNCTIONS
+//---------------------------------
+
+int ykushxs_cmd_parser(int argc, char** argv);
+
+
+void ykushxs_help(char * execName);
+
+
+void ykushxs_up(char * iserial);
+
+
+void ykushxs_down(char * iserial);
+
+
+int ykushxs_list_attached(void); 
+
+
+
+#endif
+
+

+ 0 - 0
ykush.sln


+ 0 - 268
ykushcmd/commandParser.cpp

@@ -1,268 +0,0 @@
-/****************************************************************************
- FileName:      commandParser.cpp
- Dependencies:  See INCLUDES section
- Compiler:      Visual Studio Community 2015
- Company:       Yepkit, Lda.
-
- Software License Agreement:
-
- Copyright (c) 2015 Yepkit Lda
-
- Permission is hereby granted, free of charge, to any person obtaining a copy
- of this software and associated documentation files (the "Software"), to deal
- in the Software without restriction, including without limitation the rights
- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
- copies of the Software, and to permit persons to whom the Software is
- furnished to do so, subject to the following conditions:
-
- The above copyright notice and this permission notice shall be included in
- all copies or substantial portions of the Software.
-
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
- THE SOFTWARE.
-
-*****************************************************************************
- File Description:
-
-    Change History:
-        Rev     Date            Description
-        ----    -----------     -----------------------------------------
-        1.0     2015-09-11      First Release
-
-
- ****************************************************************************
- *  Summary:
- *      Main program function
- *
- *
- *
-*****************************************************************************/
-
-
-// INCLUDES ---------------------------------------------------------------
-
-#include <cstdlib>
-#include <iostream>
-#include <stdio.h>
-
-#include "stdafx.h"
-#include "commandParser.h"
-#include "usbcom.h"
-
-using namespace std;
-
-
-
-enum cmdAction {
-    PORT_UP,
-    PORT_DOWN,
-    LIST_DEVICES,
-    DISPLAY_SERIAL_NUMBER,
-    GET_PORT_STATUS,
-    PRINT_HELP,
-};
-
-bool bySerial = false;
-
-
-
-int commandParser(int argc, char** argv) {
-
-  	char choice;
-  	char cmd = 0x00;
-	enum cmdAction action = PRINT_HELP;
-	char *iSerial=NULL;
-    char response;
-    char port = 0;
-
-  	if ( argc <= 1){
-		printUsage(argv[0]);
-		return 0;
-    	}
-
-	
-  	//Parse input options and define action
-	switch (argc) {
-		case 2:
-			if ((argv[1][0]=='-') && (argv[1][1]=='l')) {
-				action = LIST_DEVICES;
-			} else {
-				action = PRINT_HELP;
-			}
-			break;
-		case 3:
-			// Single Option
-			if ((argv[1][0] == '-') && (argv[1][1]=='d')) {
-				action = PORT_DOWN;
-				port = argv[2][0];
-			} else if ((argv[1][0] == '-') && (argv[1][1]=='u')) {
-				action = PORT_UP;
-				port = argv[2][0];
-			} else if ((argv[1][0] == '-') && (argv[1][1]=='g')) {
-				action = GET_PORT_STATUS;
-				port = argv[2][0];
-			} else {
-				action = PRINT_HELP;
-			} 	
-			break;
-
-		case 5:
-			// Two Options
-			if ((argv[1][0] == '-') && (argv[1][1]=='s')) {
-				bySerial = true;
-				iSerial = argv[2];	
-			}
-			if ((argv[3][0] == '-') && (argv[3][1]=='d')) {
-				action = PORT_DOWN;
-				port = argv[4][0];
-			} else if ((argv[3][0] == '-') && (argv[3][1]=='u')) {
-				action = PORT_UP;
-				port = argv[4][0];
-			} else if ((argv[3][0] == '-') && (argv[3][1]=='g')) {
-				action = GET_PORT_STATUS;
-				port = argv[4][0];
-			} else {
-				action = PRINT_HELP;
-			}
-			break;
-
-		default:
-			printUsage(argv[0]);
-			break;
-	}
-
-
-
-	//Get options values and execute action
-	
-	if ( action == PORT_DOWN || action == PORT_UP ) {
-		switch(port) {
-			case '1':
-				// Downstream 1 down
-				cmd = 0x01;
-				break;
-
-			case '2':
-				// Downstream 2 down
-				cmd = 0x02;
-				break;
-
-			case '3':
-				// Downstream 3 down
-				cmd = 0x03;
-				break;
-
-			case 'a':
-				// All downstreams down
-				cmd = 0x0a;
-				break;
-
-			default:
-				printUsage(argv[0]);
-				return -1;
-				break;
-		}
-
-		// PORT_UP has 0x11 - 0x1a, while PORT_DOWN has 0x01 - 0x0a
-		if ( action == PORT_UP )
-			cmd += 0x10;
-
-		if (bySerial)
-			commandBySerial(iSerial, cmd);
-		else
-			command(cmd);
-	}
-
-	if (action == GET_PORT_STATUS && port == 'a') {
-		char cmds[3] = { 0x21, 0x22, 0x23 };
-		char resps[3];
-		int i;
-
-		if (bySerial)
-			commandsBySerial(iSerial, cmds, resps, 3);
-		else
-			commands(cmds, resps, 3);
-
-		for (i = 0; i < 3; i++) {
-			response = resps[i] + 0x20 - cmds[i];
-			if (response == 0x10 + cmd) {
-				printf("Downstream port %d is: UP\n", i+1);
-			} else if (response == cmd) {
-				printf("Downstream port %d is: DOWN\n", i+1);
-			} else {
-				printf("Downstream port %d is: UNKNOWN\n", i+1);
-			}
-		}
-	} else if (action == GET_PORT_STATUS) {
-		switch (port) {
-			case '1':
-				//downstream 1 status
-				cmd = 0x1;
-				break;
-			case '2':
-				//downstream 2 status
-				cmd = 0x2;
-				break;
-			case '3':
-				//downstream 3 status
-				cmd = 0x3;
-				break;
-			default:
-				printUsage(argv[0]);
-				return -1;
-				break;
-		}
-
-		if (bySerial) //target board specified by serial number
-			response = commandBySerial(iSerial,cmd + 0x20);
-		else
-			response = command(cmd + 0x20);
-
-		if (response == 0x10 + cmd) {
-			printf("\nDownstream port %c is: UP\n", port);
-		} else if (response == cmd) {
-			printf("\nDownstream port %c is: DOWN\n", port);
-		} else {
-			printf("\nUnable to get port status for port %c\n", port);
-		}
-	}
-
-
-	
-	if ( action == LIST_DEVICES ) {
-		printf("\nAttached YKUSH Boards\n");
-        	printf("\n---------------------\n");
-        	listDevices();
-	}
-
-
-	if ( action == PRINT_HELP ) {
-		printUsage(argv[0]);
-	}
-
-
-    return 0;
-}
-
-
-
-int printUsage(char* execName){
-
-    printf("\n-------------------");
-    printf("\n\tUsage:\n");
-    printf("-------------------\n");
-    printf("\n%s -d downstream_number \t\tTurns DOWN the downstream port with the number downstream_number\n", execName);
-    printf("\n%s -u downstream_number \t\tTurns UP the downstream port with the number downstream_number\n", execName);
-    printf("\n%s -g downstream_number \t\tObtains the switching status of port with the number downstream_number\n", execName);
-    printf("\n%s -l \t\t\t\tLists all currently attached YKUSH boards\n", execName);
-    printf("\n%s -s serial_number -d downstream_number \tTurns DOWN the downstream port with the number downstream_number for the board with the specified serial number\n", execName);
-    printf("\n%s -s serial_number -u downstream_number \tTurns UP the downstream port with the number downstream_number for the board with the specified serial number\n\n\n", execName);
-    printf("\n%s -s serial_number -g downstream_number \tObtains the switching status of port with the number downstream_number for the board with the specified serial number\n\n\n", execName);
-
-    return 0;
-}

+ 0 - 338
ykushcmd/usbcom.cpp

@@ -1,338 +0,0 @@
-/****************************************************************************
- FileName:      usbcom.cpp
- Dependencies:  See INCLUDES section
- Compiler:      Visual Studio Community 2015
- Company:       Yepkit, Lda.
-
- Software License Agreement:
-
- Copyright (c) 2015 Yepkit Lda
-
- Permission is hereby granted, free of charge, to any person obtaining a copy
- of this software and associated documentation files (the "Software"), to deal
- in the Software without restriction, including without limitation the rights
- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
- copies of the Software, and to permit persons to whom the Software is
- furnished to do so, subject to the following conditions:
-
- The above copyright notice and this permission notice shall be included in
- all copies or substantial portions of the Software.
-
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
- THE SOFTWARE.
-
-*****************************************************************************
- File Description:
-
-    Change History:
-        Rev     Date            Description
-        ----    -----------     -----------------------------------------
-        1.0     2015-09-11      First Release
-
-
- ****************************************************************************
- *  Summary:
- *
- *  Functions that communicate with the YKUSH board and/or provide
- *  status information.
- *
-*****************************************************************************/
-
-
-
-//-------------------------------------------------------------------------
-// INCLUDES
-//-------------------------------------------------------------------------
-#include <errno.h>
-#include <string.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <iostream>
-
-#include "stdafx.h"
-
-#ifndef LINUX
-	#include "windows\hidapi.h"
-#else
-	#include "linux/hidapi.h"
-#endif
-
-#include "usbcom.h"
-
-
-using namespace std;
-
-
-//-------------------------------------------------------------------------
-// DEFINES
-//-------------------------------------------------------------------------
-#define VERSION "0.1.0"
-#define VENDOR_ID 0x04D8
-#define PRODUCT_ID 0xF2F7
-#define OLD_PRODUCT_ID 0x0042
-
-
-
-
-/**************************************************************************
- * listDevices() - List YKUSH Devices Serial Number
- *-------------------------------------------------------------------------
- *
- * This function prints the iSerial of the
- * attached YKUSH devices.
- *
- **************************************************************************/
-int listDevices() {
-
-    	// Enumerate and print the YKUSH devices on the system
-        
-        hid_device *handle;
-    	struct hid_device_info *devs, *cur_dev;
-
-    	devs = hid_enumerate(0x0, 0x0);
-    	if (devs == NULL) {
-            //APAGAR
-            // Limited Legaccy firmware support (does not work in all systems)
-            //handle = hid_open(VENDOR_ID, OLD_PRODUCT_ID, NULL);
-            //FIM APAGAR
-            if (handle == NULL){
-                // No HID devices found
-                printf("\nNo HID USB devices connected to this Host\n");
-            }
-
-    	}
-
-    	cur_dev = devs;
-    	while (cur_dev) {
-        	if ((cur_dev->vendor_id == VENDOR_ID) && (cur_dev->product_id == PRODUCT_ID)) {
-            		printf("YKUSH device found with Serial Number: %ls", cur_dev->serial_number);
-            		printf("\n");
-            		printf("  Manufacturer: %ls\n", cur_dev->manufacturer_string);
-            		printf("  Product:      %ls\n", cur_dev->product_string);
-            		printf("\n");
-        	} else if ((cur_dev->vendor_id == VENDOR_ID) && (cur_dev->product_id == OLD_PRODUCT_ID)) {
-                    printf("YKUSH device found with Serial Number: %ls", cur_dev->serial_number);
-            		printf("\n");
-            		printf("  Manufacturer: %ls\n", cur_dev->manufacturer_string);
-            		printf("  Product:      %ls\n", cur_dev->product_string);
-                    printf("  NOTE: This is an old version of the firmware. If you have access to a PIC programmer contact Yepkit to get the latest version of the firmware.");
-            		printf("\n");
-            }
-
-        	cur_dev = cur_dev->next;
-    	}
-    	hid_free_enumeration(devs);
-    
-	return 0;
-}
-
-
-
-/*******************************************************************************
- * commandsBySerial(char* iSerial, char *cmd, char* resp, int num) - Sends commands to YKUSH board
- * -----------------------------------------------------------------------------
- *
- * Description:
- *
- * 	All commands in the cmd array are send to the YKUSH board and the
- * 	response bytes are stored in the matching resp entry. If more than
- * 	one YKUSH board is connected to the host it will send the command
- * 	just to the first one that appears in the enumerated list.
- *
- * 	If there are more than one YKUSH board connected to the same host
- * 	the commandBySerial function should be used instead.
- *
- * Inputs:
- *
- *	iSerial	-	Serial number of the YKUSH board to issue the command.
- *	cmds	-	Command bytes to be sent to YKUSH.
- *	resp	-	Array for storing response bytes
- *	num	-	Number of entries in cmds and resp
- *
- * Outputs:
- *
- * 	The function will return the response byte or zero.
- *
- ********************************************************************************/
-char commandsBySerial(char *iSerial, char *cmd, char *resp, int num)
-{
-
-	int res;
-    unsigned char buf[65];
-    unsigned char buf6[6];
-    bool isLegacy = false;
-    #define MAX_STR 255
-    wchar_t wstr[MAX_STR];
-    hid_device *handle;
-    int i;
-	const size_t newsize = 100;
-	wchar_t serial[newsize];
-	
-     
-	if (iSerial) {
-		// Convert to a wchar_t*
-		size_t origsize = strlen(iSerial) + 1;
-		size_t convertedChars = 0;
-
-#ifndef LINUX
-		mbstowcs_s(&convertedChars, serial, origsize, iSerial, _TRUNCATE);
-#else
-		mbstowcs(serial, iSerial, newsize);
-#endif
-	}
-
-     	// Open the YKUSH device 
-        handle = hid_open(VENDOR_ID, PRODUCT_ID, iSerial ? serial : NULL);
-
-    
-        if (handle == NULL) {
-
-            // Limited Legaccy firmware support (does not work in all systems)
-            handle = hid_open(VENDOR_ID, OLD_PRODUCT_ID, NULL);
-
-            if (handle == NULL){
-                return 0;
-            }
-
-            isLegacy = true;
-
-        }
-
-     	// Set the hid_read() function to be blocking (wait for response from YKUSH).
-    	hid_set_nonblocking(handle, 0);
-
-	for (i = 0; i < num; i++) {
-		// Send an Output report with the desired command
-		if (isLegacy) {
-			buf6[0] = 0; 	// First byte is report number
-			buf6[1] = cmd[i];	// Command byte
-			buf6[2] = cmd[i];	// Command confirm byte
-			res = hid_write(handle, buf6, 6);
-		} else {
-			buf[0] = 0; 	// First byte is report number
-			buf[1] = cmd[i];	// Command byte
-			buf[2] = cmd[i];	// Command confirm byte
-			res = hid_write(handle, buf, 65);
-		}
-
-		// Read response
-		if (isLegacy) {
-			res = hid_read(handle, buf, 6);
-		} else {
-			res = hid_read(handle, buf, 65);
-		}
-
-		if (res < 0) {
-			printf("Unable to read YKUSH command response\n");
-		}
-
-		if (res >= 1) {
-			resp[i] = buf[1];
-		}
-	}
-
-    	return 0;
- }
-
-/*******************************************************************************
- * commands(char *cmd, char* resp, int num) - Sends commands to YKUSH board
- * -----------------------------------------------------------------------------
- *
- * Description:
- *
- * 	All commands in the cmd array are send to the YKUSH board and the
- * 	response bytes are stored in the matching resp entry. If more than
- * 	one YKUSH board is connected to the host it will send the command
- * 	just to the first one that appears in the enumerated list.
- *
- * 	If there are more than one YKUSH board connected to the same host
- * 	the commandBySerial function should be used instead.
- *
- * Inputs:
- *
- *	cmds	-	Command bytes to be sent to YKUSH.
- *	resp	-	Array for storing response bytes
- *	num	-	Number of entries in cmds and resp
- *
- * Outputs:
- *
- * 	The function will return the response byte or zero.
- *
- ********************************************************************************/
-char commands(char *cmd, char *resp, int num)
-{
-	return commandsBySerial(NULL, cmd, resp, num);
-}
-
-/*******************************************************************************
- * commandBySerial(char *iSerial, char cmd) - Sends the command to YKUSH board
- * -----------------------------------------------------------------------------
- *
- * Description:
- *
- * 	The command in the variable cmd is sent to YKUSH board. If more than
- * 	one YKUSH board is connected to the host it will send the command
- * 	just to the first one that appears in the enumerated list.
- *
- * 	If there are more than one YKUSH board connected to the same host
- * 	the commandBySerial function should be used instead.
- *
- * Inputs:
- *
- *	iSerial	-	Serial number of the YKUSH board to issue the command.
- *	cmd	-	Command byte to be sent to YKUSH.
- *
- * Outputs:
- *
- * 	The function will return the response byte or zero.
- *
- ********************************************************************************/
-char commandBySerial(char *iSerial, char cmd)
-{
-	char resp;
-
-	commandsBySerial(iSerial, &cmd, &resp, 1);
-
-	return resp;
-}
-
-/*******************************************************************************
- * command(char cmd) - Sends the command to YKUSH board
- * -----------------------------------------------------------------------------
- *
- * Description:
- *
- * 	The command in the variable cmd is sent to YKUSH board. If more than
- * 	one YKUSH board is connected to the host it will send the command
- * 	just to the first one that appears in the enumerated list.
- *
- * 	If there are more than one YKUSH board connected to the same host
- * 	the commandBySerial function should be used instead.
- *
- * Inputs:
- *
- * 	cmd	-	Command byte to be sent to YKUSH.
- *
- * Outputs:
- *
- * 	The function will return the response byte.
- *
- ********************************************************************************/
-char command(char cmd)
-{
-	return commandBySerial(NULL, cmd);
-}
-
-
-
-
-
-
-
-
-

+ 0 - 15
ykushcmd/usbcom.h

@@ -1,15 +0,0 @@
-#ifndef USBCOM_H
-#define USBCOM_H
-
-static int sendCommand(unsigned char *toSendBuffer, unsigned char *receivedBuffer);
-
-char commands(char *cmd, char *resp, int num);
-char command(char cmd);
-
-char commandsBySerial(char *iSerial, char *cmd, char *resp, int num);
-char commandBySerial(char *iSerial, char cmd);
-
-int listDevices();
-
-
-#endif // USBCOM_H

+ 0 - 12
ykushcmd/ykushcmd.cpp

@@ -1,12 +0,0 @@
-// Program entry point
-
-#include "stdafx.h"
-#include "commandParser.h"
-
-
-int main(int argc, char* argv[])
-{
-    	commandParser(argc, argv);
-    	return 0;
-}
-