mirror of
https://github.com/intrepidcs/libicsneo.git
synced 2026-08-05 01:18:36 +02:00
Move examples into tree
See history at https://github.com/intrepidcs/libicsneo-examples/tree/v0.2.0-dev
This commit is contained in:
@@ -0,0 +1,16 @@
|
||||
cmake_minimum_required(VERSION 3.2)
|
||||
project(libicsneoc-interactive-example VERSION 0.2.0)
|
||||
|
||||
include(GNUInstallDirs)
|
||||
|
||||
# Include libicsneo's include directory
|
||||
include_directories(${CMAKE_CURRENT_SOURCE_DIR}/../../../include)
|
||||
|
||||
if(UNIX)
|
||||
set(CMAKE_SHARED_LIBRARY_LINK_C_FLAGS)
|
||||
endif()
|
||||
|
||||
add_executable(libicsneoc-interactive-example src/main.c)
|
||||
if(UNIX)
|
||||
target_link_libraries(libicsneoc-interactive-example ${CMAKE_DL_LIBS})
|
||||
endif()
|
||||
@@ -0,0 +1,80 @@
|
||||
# libicsneo C Example
|
||||
|
||||
This is an example console application that uses the icsneoc library to control an Intrepid Control Systems hardware device.
|
||||
|
||||
## Cloning
|
||||
|
||||
This will create a copy of the repository on your local machine.
|
||||
|
||||
Run:
|
||||
|
||||
```shell
|
||||
git clone https://github.com/intrepidcs/libicsneo-examples -b v0.2.0-dev --recursive
|
||||
```
|
||||
|
||||
Alternatively, if you cloned without the `--recursive` flag, you must enter the `libicsneo-examples` folder and run the following:
|
||||
|
||||
```shell
|
||||
git submodule update --recursive --init
|
||||
```
|
||||
|
||||
If you haven't done this, `third-party/libicsneo` will be empty and you won't be able to build!
|
||||
|
||||
## Windows using Visual Studio 2017+
|
||||
|
||||
### Building the DLL
|
||||
|
||||
First, we are going to build the icsneoc library into a .dll file that we can later use in order to access the library functions.
|
||||
|
||||
1. Launch Visual Studio and open the `libicsneo-examples` folder.
|
||||
2. Choose `File->Open->Cmake...`
|
||||
3. Navigate to `third-party/libicsneo` and select the `CMakeLists.txt` there.
|
||||
4. Visual Studio will process the CMake project.
|
||||
5. Select `Build->Rebuild All`
|
||||
6. Visual Studio will generate the `icsneoc.dll` file, which can then be found by selecting `Project->Cmake Cache (x64-Debug Only)->Open in Explorer`. If the file cannot be found, search in `libicsneo-examples/third-party/libicsneo/out/build/x64-Debug` and double-check that the build succeeded in step 5.
|
||||
7. Move the `icsneoc.dll` file to the `/C/Windows/System32` folder. This will allow it to be found by icsneo_init(), which loads all the library functions.
|
||||
* Alternatively, the `icsneoc.dll` file can be placed in the same directory as `libicsneoc-example.exe`, which is typically `libicsneo-examples/libicsneoc-example/out/build/x64-Debug`, although this is not recommended. For more information, refer to [the Microsoft documentation](https://docs.microsoft.com/en-us/windows/desktop/dlls/dynamic-link-library-search-order).
|
||||
|
||||
### Building the example program
|
||||
|
||||
Although the example program will build without successfully completing the steps above, it will exit immediately upon running due to a failure to load any library functions.
|
||||
|
||||
1. Choose `File->Open->Cmake...`
|
||||
2. Navigate to `libicsneo-examples/libicsneoc-example` and select the `CMakeLists.txt` there.
|
||||
3. Visual Studio will process the CMake project.
|
||||
4. Select `Build->Rebuild All`
|
||||
5. Click on the dropdown arrow attached to the green play button (labelled "Select Startup Item") and select `libicsneoc-example.exe`
|
||||
6. Click on the green play button to run the example.
|
||||
|
||||
## Ubuntu 18.04 LTS
|
||||
|
||||
### Building the .so
|
||||
|
||||
First, we are going to build the icsneoc library into a .so file that we can later use in order to access the library functions.
|
||||
|
||||
1. Install dependencies with `sudo apt update` then `sudo apt install build-essential cmake libusb-1.0-0-dev libpcap0.8-dev`
|
||||
2. Change directories to `libicsneo-examples/third-party/libicsneo` and create a build directory by running `mkdir -p build`
|
||||
3. Enter the build directory with `cd build`
|
||||
4. Run `cmake ..` to generate your Makefile.
|
||||
* Hint! Running `cmake -DCMAKE_BUILD_TYPE=Debug ..` will generate the proper scripts to build debug, and `cmake -DCMAKE_BUILD_TYPE=Release ..` will generate the proper scripts to build with all optimizations on.
|
||||
5. Run `make` to build the library.
|
||||
* Hint! Speed up your build by using multiple processors! Use `make -j#` where `#` is the number of cores/threads your system has plus one. For instance, on a standard 8 thread Intel i7, you might use `-j9` for an ~8x speedup.
|
||||
6. Run `sudo cp libicsneoc.so /usr/lib` so that it can be found via the default ubuntu .so search path. For more information, see the [ld.so.8 man page](http://man7.org/linux/man-pages/man8/ld.so.8.html).
|
||||
|
||||
### Building the example program
|
||||
|
||||
Although the example program will build without successfully completing the steps above, it will exit immediately upon running due to a failure to load any library functions.
|
||||
|
||||
1. Change directories to `libicsneo-examples/libicsneoc-example`
|
||||
2. Create a build directory by running `mkdir -p build`
|
||||
3. Enter the build directory with `cd build`
|
||||
4. Run `cmake ..` to generate your Makefile.
|
||||
* Hint! Running `cmake -DCMAKE_BUILD_TYPE=Debug ..` will generate the proper scripts to build debug, and `cmake -DCMAKE_BUILD_TYPE=Release ..` will generate the proper scripts to build with all optimizations on.
|
||||
5. Run `make` to build the library.
|
||||
* Hint! Speed up your build by using multiple processors! Use `make -j#` where `#` is the number of cores/threads your system has plus one. For instance, on a standard 8 thread Intel i7, you might use `-j9` for an ~8x speedup.
|
||||
6. Run `sudo ./libicsneoc-example` to run the example.
|
||||
* Hint! In order to run without sudo, you will need to set up the udev rules. Copy `libicsneo-examples/third-party/libicsneo/99-intrepidcs.rules` to `/etc/udev/rules.d`, then run `udevadm control --reload-rules && udevadm trigger` afterwards. While the program will still run without setting up these rules, it will fail to open any devices.
|
||||
|
||||
## macOS
|
||||
|
||||
Instructions coming soon™
|
||||
@@ -0,0 +1,610 @@
|
||||
// Signal to dynamically load the library
|
||||
#define ICSNEOC_DYNAMICLOAD
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <stdarg.h>
|
||||
#include <ctype.h>
|
||||
|
||||
// Get the PRIu64 macro for timestamps
|
||||
#define __STDC_FORMAT_MACROS
|
||||
#include <inttypes.h>
|
||||
|
||||
// Include icsneo/icsneoc.h to access library functions
|
||||
#include "icsneo/icsneoc.h"
|
||||
|
||||
size_t msgLimit = 50000;
|
||||
size_t numDevices = 0;
|
||||
neodevice_t devices[99];
|
||||
const neodevice_t* selectedDevice = NULL;
|
||||
|
||||
/**
|
||||
* \brief Prints all current known devices to output in the following format:
|
||||
* [num] DeviceType SerialNum Connected: Yes/No Online: Yes/No Msg Polling: On/Off
|
||||
*
|
||||
* If any devices could not be described due to an error, they will appear in the following format:
|
||||
* Description for device num not available!
|
||||
*/
|
||||
void printAllDevices() {
|
||||
if(numDevices == 0) {
|
||||
printf("No devices found! Please scan for new devices.\n");
|
||||
}
|
||||
for(int i = 0; i < numDevices; i++) {
|
||||
char productDescription[ICSNEO_DEVICETYPE_LONGEST_DESCRIPTION];
|
||||
size_t descriptionLength = ICSNEO_DEVICETYPE_LONGEST_DESCRIPTION;
|
||||
|
||||
// Updates productDescription and descriptionLength for each device
|
||||
if(icsneo_describeDevice(devices + i, productDescription, &descriptionLength)) {
|
||||
printf("[%d] %s\tConnected: ", i + 1, productDescription);
|
||||
if(icsneo_isOpen(devices + i)) {
|
||||
printf("Yes\t");
|
||||
} else printf("No\t");
|
||||
|
||||
printf("Online: ");
|
||||
if(icsneo_isOnline(devices + i)) {
|
||||
printf("Yes\t");
|
||||
} else printf("No\t");
|
||||
|
||||
printf("Msg Polling: ");
|
||||
if(icsneo_isMessagePollingEnabled(devices + i)) {
|
||||
printf("On\n");
|
||||
} else printf("Off\n");
|
||||
|
||||
} else {
|
||||
printf("Description for device %d not available!\n", i + 1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief Scans for any new devices, adding them to devices and updating numDevices accordingly
|
||||
* A total of 99 devices may be stored at once
|
||||
*/
|
||||
size_t scanNewDevices() {
|
||||
neodevice_t newDevices[99];
|
||||
size_t numNewDevices = 99;
|
||||
icsneo_findAllDevices(newDevices, &numNewDevices);
|
||||
|
||||
for(int i = 0; i < numNewDevices; ++i) {
|
||||
devices[numDevices + i] = newDevices[i];
|
||||
}
|
||||
numDevices += numNewDevices;
|
||||
return numNewDevices;
|
||||
}
|
||||
|
||||
// Prints the main menu options to output
|
||||
void printMainMenu() {
|
||||
printf("Press the letter next to the function you want to use:\n");
|
||||
printf("A - List all devices\n");
|
||||
printf("B - Scan for new devices\n");
|
||||
printf("C - Open/close\n");
|
||||
printf("D - Go online/offline\n");
|
||||
printf("E - Enable/disable message polling\n");
|
||||
printf("F - Get messages\n");
|
||||
printf("G - Send message\n");
|
||||
printf("H - Get events\n");
|
||||
printf("I - Set HS CAN to 250K\n");
|
||||
printf("J - Set HS CAN to 500K\n");
|
||||
printf("X - Exit\n");
|
||||
}
|
||||
|
||||
void printLastError() {
|
||||
neoevent_t error;
|
||||
if(icsneo_getLastError(&error))
|
||||
printf("Error 0x%u: %s\n", error.eventNumber, error.description);
|
||||
else
|
||||
printf("No errors found!\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief Gets all current API events and prints them to output
|
||||
* Flushes the API event cache, meaning future calls (barring any new events) will not detect any further API events
|
||||
*/
|
||||
void printAPIEvents() {
|
||||
neoevent_t events[99];
|
||||
size_t eventCount = 99;
|
||||
if(icsneo_getEvents(events, &eventCount)) {
|
||||
if(eventCount == 1) {
|
||||
printf("1 API event found!\n");
|
||||
printf("Event 0x%u: %s\n", events[0].eventNumber, events[0].description);
|
||||
} else {
|
||||
printf("%d API events found!\n", (int) eventCount);
|
||||
for(int i = 0; i < eventCount; ++i) {
|
||||
printf("Event 0x%u: %s\n", events[i].eventNumber, events[i].description);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
printf("Failed to get API events!\n");
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief Gets all current device events and prints them to output. If no device events were found, printAPIEvents() is called
|
||||
* Flushes the device event cache, meaning future calls (barring any new events) will not detect any further device events for this device
|
||||
*/
|
||||
void printDeviceEvents(neodevice_t* device) {
|
||||
neoevent_t events[99];
|
||||
size_t eventCount = 99;
|
||||
if(icsneo_getDeviceEvents(selectedDevice, events, &eventCount)) {
|
||||
if(eventCount == 1) {
|
||||
printf("1 device event found!\n");
|
||||
printf("Event 0x%x: %s\n", events[0].eventNumber, events[0].description);
|
||||
} else {
|
||||
printf("%d device events found!\n", (int) eventCount);
|
||||
for(int i = 0; i < eventCount; ++i) {
|
||||
printf("Event 0x%x: %s\n", events[i].eventNumber, events[i].description);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief Used to check character inputs for correctness (if they are found in an expected list)
|
||||
* \param[in] numArgs the number of possible options for the expected character
|
||||
* \param[in] ... the possible options for the expected character
|
||||
* \returns the entered character
|
||||
*
|
||||
* This function repeatedly prompts the user for input until a matching input is entered
|
||||
* Example usage: char input = getCharInput(5, 'F', 'u', 'b', 'a', 'r');
|
||||
*/
|
||||
char getCharInput(int numArgs, ...) {
|
||||
// 99 chars shold be more than enough to catch any typos
|
||||
char input[99];
|
||||
bool found = false;
|
||||
|
||||
va_list vaList;
|
||||
va_start(vaList, numArgs);
|
||||
|
||||
char* list = (char*) calloc(numArgs, sizeof(char));
|
||||
for(int i = 0; i < numArgs; ++i) {
|
||||
*(list + i) = va_arg(vaList, int);
|
||||
}
|
||||
|
||||
va_end(vaList);
|
||||
|
||||
while(!found) {
|
||||
fgets(input, 99, stdin);
|
||||
if(strlen(input) == 2) {
|
||||
for(int i = 0; i < numArgs; ++i) {
|
||||
if(input[0] == *(list + i)) {
|
||||
found = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if(!found) {
|
||||
printf("Input did not match expected options. Please try again.\n");
|
||||
}
|
||||
}
|
||||
|
||||
free(list);
|
||||
|
||||
return input[0];
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief Prompts the user to select a device from the list of currently known devices
|
||||
* \returns a pointer to the device in devices[] selected by the user
|
||||
* Requires an input from 1-9, so a maximum of 9 devices are supported
|
||||
*/
|
||||
const neodevice_t* selectDevice() {
|
||||
printf("Please select a device:\n");
|
||||
printAllDevices();
|
||||
printf("\n");
|
||||
|
||||
int selectedDeviceNum = 10;
|
||||
|
||||
while(selectedDeviceNum > numDevices) {
|
||||
char deviceSelection = getCharInput(9, '1', '2', '3', '4', '5', '6', '7', '8', '9');
|
||||
selectedDeviceNum = deviceSelection - '0';
|
||||
if(selectedDeviceNum > numDevices) {
|
||||
printf("Selected device out of range!\n");
|
||||
}
|
||||
}
|
||||
|
||||
printf("\n");
|
||||
|
||||
return devices + selectedDeviceNum - 1;
|
||||
}
|
||||
|
||||
int main() {
|
||||
|
||||
// Attempt to initialize the library and access its functions
|
||||
// This call searches for icsneoc.dll according to the standard dynamic-link library search order
|
||||
int ret = icsneo_init();
|
||||
if(ret == 1) {
|
||||
printf("The library was already initialized!\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
if(ret == 2) {
|
||||
printf("The library could not be found!\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
if(ret == 3) {
|
||||
printf("The library is missing functions!\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
neoversion_t ver = icsneo_getVersion();
|
||||
printf("ICS icsneoc.dll version %u.%u.%u\n\n", ver.major, ver.minor, ver.patch);
|
||||
|
||||
while(true) {
|
||||
printMainMenu();
|
||||
printf("\n");
|
||||
char input = getCharInput(22, 'A', 'a', 'B', 'b', 'C', 'c', 'D', 'd', 'E', 'e', 'F', 'f', 'G', 'g', 'H', 'h', 'I', 'i', 'J', 'j', 'X', 'x');
|
||||
printf("\n");
|
||||
switch(input) {
|
||||
// List current devices
|
||||
case 'A':
|
||||
case 'a':
|
||||
printAllDevices();
|
||||
printf("\n");
|
||||
break;
|
||||
// Scan for new devices
|
||||
case 'B':
|
||||
case 'b':
|
||||
{
|
||||
size_t numNewDevices = scanNewDevices();
|
||||
if(numNewDevices == 1) {
|
||||
printf("1 new device found!\n");
|
||||
} else {
|
||||
printf("%d new devices found!\n", (int) numNewDevices);
|
||||
}
|
||||
printAllDevices();
|
||||
printf("\n");
|
||||
break;
|
||||
}
|
||||
// Open/close a device
|
||||
case 'C':
|
||||
case 'c':
|
||||
{
|
||||
// Select a device and get its description
|
||||
if(numDevices == 0) {
|
||||
printf("No devices found! Please scan for new devices.\n\n");
|
||||
break;
|
||||
}
|
||||
selectedDevice = selectDevice();
|
||||
|
||||
// Get the product description for the device
|
||||
char productDescription[ICSNEO_DEVICETYPE_LONGEST_DESCRIPTION];
|
||||
size_t descriptionLength = ICSNEO_DEVICETYPE_LONGEST_DESCRIPTION;
|
||||
icsneo_describeDevice(selectedDevice, productDescription, &descriptionLength);
|
||||
|
||||
printf("Would you like to open or close %s?\n", productDescription);
|
||||
printf("[1] Open\n[2] Close\n[3] Cancel\n\n");
|
||||
|
||||
char input = getCharInput(3, '1', '2', '3');
|
||||
printf("\n");
|
||||
|
||||
switch(input) {
|
||||
case '1':
|
||||
// Attempt to open the selected device
|
||||
if(icsneo_openDevice(selectedDevice)) {
|
||||
printf("%s successfully opened!\n\n", productDescription);
|
||||
} else {
|
||||
printf("%s failed to open!\n\n", productDescription);
|
||||
printLastError();
|
||||
printf("\n");
|
||||
}
|
||||
break;
|
||||
case '2':
|
||||
// Attempt to close the device
|
||||
if(icsneo_closeDevice(selectedDevice)) {
|
||||
numDevices--;
|
||||
printf("Successfully closed %s!\n\n", productDescription);
|
||||
|
||||
// Shifts everything after the removed device 1 index to the left
|
||||
bool startResizing = false;
|
||||
for(int i = 0; i < numDevices; ++i) {
|
||||
if(selectedDevice == devices + i)
|
||||
startResizing = true;
|
||||
if(startResizing)
|
||||
devices[i] = devices[i + 1];
|
||||
}
|
||||
|
||||
selectedDevice = NULL;
|
||||
} else {
|
||||
printf("Failed to close %s!\n\n", productDescription);
|
||||
printLastError();
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
break;
|
||||
default:
|
||||
printf("Canceling!\n\n");
|
||||
}
|
||||
}
|
||||
break;
|
||||
// Go online/offline
|
||||
case 'D':
|
||||
case 'd':
|
||||
{
|
||||
// Select a device and get its description
|
||||
if(numDevices == 0) {
|
||||
printf("No devices found! Please scan for new devices.\n\n");
|
||||
break;
|
||||
}
|
||||
selectedDevice = selectDevice();
|
||||
|
||||
// Get the product description for the device
|
||||
char productDescription[ICSNEO_DEVICETYPE_LONGEST_DESCRIPTION];
|
||||
size_t descriptionLength = ICSNEO_DEVICETYPE_LONGEST_DESCRIPTION;
|
||||
icsneo_describeDevice(selectedDevice, productDescription, &descriptionLength);
|
||||
|
||||
printf("Would you like to have %s go online or offline?\n", productDescription);
|
||||
printf("[1] Online\n[2] Offline\n[3] Cancel\n\n");
|
||||
|
||||
char input = getCharInput(3, '1', '2', '3');
|
||||
printf("\n");
|
||||
|
||||
switch(input) {
|
||||
case '1':
|
||||
// Attempt to go online
|
||||
if(icsneo_goOnline(selectedDevice)) {
|
||||
printf("%s successfully went online!\n\n", productDescription);
|
||||
} else {
|
||||
printf("%s failed to go online!\n\n", productDescription);
|
||||
printLastError();
|
||||
printf("\n");
|
||||
}
|
||||
break;
|
||||
case '2':
|
||||
// Attempt to go offline
|
||||
if(icsneo_goOffline(selectedDevice)) {
|
||||
printf("%s successfully went offline!\n\n", productDescription);
|
||||
} else {
|
||||
printf("%s failed to go offline!\n\n", productDescription);
|
||||
printLastError();
|
||||
printf("\n");
|
||||
}
|
||||
break;
|
||||
default:
|
||||
printf("Canceling!\n\n");
|
||||
}
|
||||
}
|
||||
break;
|
||||
// Enable/disable message polling
|
||||
case 'E':
|
||||
case 'e':
|
||||
{
|
||||
// Select a device and get its description
|
||||
if(numDevices == 0) {
|
||||
printf("No devices found! Please scan for new devices.\n\n");
|
||||
break;
|
||||
}
|
||||
selectedDevice = selectDevice();
|
||||
|
||||
// Get the product description for the device
|
||||
char productDescription[ICSNEO_DEVICETYPE_LONGEST_DESCRIPTION];
|
||||
size_t descriptionLength = ICSNEO_DEVICETYPE_LONGEST_DESCRIPTION;
|
||||
icsneo_describeDevice(selectedDevice, productDescription, &descriptionLength);
|
||||
|
||||
printf("Would you like to enable or disable message polling for %s?\n", productDescription);
|
||||
printf("[1] Enable\n[2] Disable\n[3] Cancel\n\n");
|
||||
|
||||
char input = getCharInput(3, '1', '2', '3');
|
||||
printf("\n");
|
||||
|
||||
switch(input) {
|
||||
case '1':
|
||||
// Attempt to enable message polling
|
||||
if(icsneo_enableMessagePolling(selectedDevice)) {
|
||||
printf("Successfully enabled message polling for %s!\n\n", productDescription);
|
||||
} else {
|
||||
printf("Failed to enable message polling for %s!\n\n", productDescription);
|
||||
printLastError();
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
// Manually setting the polling message limit as done below is optional
|
||||
// It will default to 20k if not set
|
||||
// Attempt to set the polling message limit
|
||||
if(icsneo_setPollingMessageLimit(selectedDevice, msgLimit)) {
|
||||
printf("Successfully set message polling limit for %s!\n\n", productDescription);
|
||||
} else {
|
||||
printf("Failed to set polling message limit for %s!\n\n", productDescription);
|
||||
printLastError();
|
||||
printf("\n");
|
||||
}
|
||||
break;
|
||||
case '2':
|
||||
// Attempt to disable message polling
|
||||
if(icsneo_disableMessagePolling(selectedDevice)) {
|
||||
printf("Successfully disabled message polling for %s!\n\n", productDescription);
|
||||
} else {
|
||||
printf("Failed to disable message polling limit for %s!\n\n", productDescription);
|
||||
printLastError();
|
||||
printf("\n");
|
||||
}
|
||||
break;
|
||||
default:
|
||||
printf("Canceling!\n\n");
|
||||
}
|
||||
}
|
||||
break;
|
||||
// Get messages
|
||||
case 'F':
|
||||
case 'f':
|
||||
{
|
||||
// Select a device and get its description
|
||||
if(numDevices == 0) {
|
||||
printf("No devices found! Please scan for new devices.\n\n");
|
||||
break;
|
||||
}
|
||||
selectedDevice = selectDevice();
|
||||
|
||||
// Get the product description for the device
|
||||
char productDescription[ICSNEO_DEVICETYPE_LONGEST_DESCRIPTION];
|
||||
size_t descriptionLength = ICSNEO_DEVICETYPE_LONGEST_DESCRIPTION;
|
||||
icsneo_describeDevice(selectedDevice, productDescription, &descriptionLength);
|
||||
|
||||
// Prepare the array of neomessage_t ptrs for reading in the messages
|
||||
neomessage_t* msgs = (neomessage_t*) malloc(msgLimit * sizeof(neomessage_t*));
|
||||
|
||||
// Get messages
|
||||
size_t msgCount = msgLimit;
|
||||
|
||||
// Attempt to get messages
|
||||
if(!icsneo_getMessages(selectedDevice, msgs, &msgCount, (uint64_t) 0)) {
|
||||
printf("Failed to get messages for %s!\n\n", productDescription);
|
||||
printLastError();
|
||||
free(msgs);
|
||||
printf("\n");
|
||||
break;
|
||||
}
|
||||
|
||||
if(msgCount == 1) {
|
||||
printf("1 message received from %s!\n", productDescription);
|
||||
} else {
|
||||
printf("%d messages received from %s!\n", (int) msgCount, productDescription);
|
||||
}
|
||||
|
||||
// Print out the received messages
|
||||
for(size_t i = 0; i < msgCount; i++) {
|
||||
neomessage_t* msg = &msgs[i];
|
||||
switch(msg->type) {
|
||||
case ICSNEO_NETWORK_TYPE_CAN: // CAN
|
||||
{
|
||||
neomessage_can_t* canMsg = (neomessage_can_t*) msg;
|
||||
printf("\t0x%03x [%zu] ", canMsg->arbid, canMsg->length);
|
||||
for(size_t i = 0; i < canMsg->length; i++) {
|
||||
printf("%02x ", canMsg->data[i]);
|
||||
}
|
||||
printf("(%"PRIu64")\n", canMsg->timestamp);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
if(msg->netid != 0)
|
||||
printf("\tMessage on netid %d with length %zu\n", msg->netid, msg->length);
|
||||
break;
|
||||
}
|
||||
}
|
||||
printf("\n");
|
||||
|
||||
free(msgs);
|
||||
}
|
||||
|
||||
break;
|
||||
// Send message
|
||||
case 'G':
|
||||
case 'g':
|
||||
{
|
||||
// Select a device and get its description
|
||||
if(numDevices == 0) {
|
||||
printf("No devices found! Please scan for new devices.\n\n");
|
||||
break;
|
||||
}
|
||||
selectedDevice = selectDevice();
|
||||
|
||||
// Get the product description for the device
|
||||
char productDescription[ICSNEO_DEVICETYPE_LONGEST_DESCRIPTION];
|
||||
size_t descriptionLength = ICSNEO_DEVICETYPE_LONGEST_DESCRIPTION;
|
||||
icsneo_describeDevice(selectedDevice, productDescription, &descriptionLength);
|
||||
|
||||
// Start generating sample msg
|
||||
uint8_t sendMessageData[6];
|
||||
sendMessageData[0] = 0xaa;
|
||||
sendMessageData[1] = 0xbb;
|
||||
sendMessageData[2] = 0xcc;
|
||||
sendMessageData[3] = 0xdd;
|
||||
sendMessageData[4] = 0xee;
|
||||
sendMessageData[5] = 0xff;
|
||||
|
||||
neomessage_can_t msg = {0};
|
||||
msg.arbid = 0x120;
|
||||
msg.length = 6;
|
||||
msg.netid = ICSNEO_NETID_HSCAN;
|
||||
msg.data = sendMessageData;
|
||||
msg.status.canfdFDF = false;
|
||||
msg.status.extendedFrame = false;
|
||||
msg.status.canfdBRS = false;
|
||||
// End generating sample msg
|
||||
|
||||
// Attempt to transmit the sample msg
|
||||
if(icsneo_transmit(selectedDevice, (const neomessage_t*) &msg)) {
|
||||
printf("Message transmit successful!\n\n");
|
||||
} else {
|
||||
printf("Failed to transmit message to %s!\n\n", productDescription);
|
||||
printLastError();
|
||||
printf("\n");
|
||||
}
|
||||
}
|
||||
break;
|
||||
// Get events
|
||||
case 'H':
|
||||
case 'h':
|
||||
{
|
||||
// All API events
|
||||
printAPIEvents();
|
||||
printf("\n");
|
||||
}
|
||||
break;
|
||||
// Set HS CAN to 250k
|
||||
case 'I':
|
||||
case 'i':
|
||||
{
|
||||
// Select a device and get its description
|
||||
if(numDevices == 0) {
|
||||
printf("No devices found! Please scan for new devices.\n\n");
|
||||
break;
|
||||
}
|
||||
selectedDevice = selectDevice();
|
||||
|
||||
// Get the product description for the device
|
||||
char productDescription[ICSNEO_DEVICETYPE_LONGEST_DESCRIPTION];
|
||||
size_t descriptionLength = ICSNEO_DEVICETYPE_LONGEST_DESCRIPTION;
|
||||
icsneo_describeDevice(selectedDevice, productDescription, &descriptionLength);
|
||||
|
||||
// Attempt to set baudrate and apply settings
|
||||
if(icsneo_setBaudrate(selectedDevice, ICSNEO_NETID_HSCAN, 250000) && icsneo_settingsApply(selectedDevice)) {
|
||||
printf("Successfully set HS CAN baudrate for %s to 250k!\n\n", productDescription);
|
||||
} else {
|
||||
printf("Failed to set HS CAN for %s to 250k!\n\n", productDescription);
|
||||
printLastError();
|
||||
printf("\n");
|
||||
}
|
||||
}
|
||||
break;
|
||||
// Set HS CAN to 500k
|
||||
case 'J':
|
||||
case 'j':
|
||||
{
|
||||
// Select a device and get its description
|
||||
if(numDevices == 0) {
|
||||
printf("No devices found! Please scan for new devices.\n\n");
|
||||
break;
|
||||
}
|
||||
selectedDevice = selectDevice();
|
||||
|
||||
// Get the product description for the device
|
||||
char productDescription[ICSNEO_DEVICETYPE_LONGEST_DESCRIPTION];
|
||||
size_t descriptionLength = ICSNEO_DEVICETYPE_LONGEST_DESCRIPTION;
|
||||
icsneo_describeDevice(selectedDevice, productDescription, &descriptionLength);
|
||||
|
||||
// Attempt to set baudrate and apply settings
|
||||
if(icsneo_setBaudrate(selectedDevice, ICSNEO_NETID_HSCAN, 500000) && icsneo_settingsApply(selectedDevice)) {
|
||||
printf("Successfully set HS CAN baudrate for %s to 500k!\n\n", productDescription);
|
||||
} else {
|
||||
printf("Failed to set HS CAN for %s to 500k!\n\n", productDescription);
|
||||
printLastError();
|
||||
printf("\n");
|
||||
}
|
||||
}
|
||||
break;
|
||||
// Exit
|
||||
case 'X':
|
||||
case 'x':
|
||||
printf("Exiting program\n");
|
||||
return !icsneo_close();
|
||||
default:
|
||||
printf("Unexpected input, exiting!\n");
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
Reference in New Issue
Block a user