kdriveExpress SDK 22.1.1
kdrive_express_services.c
//
// Copyright (c) 2002-2022 WEINZIERL ENGINEERING GmbH
// All rights reserved.
//
// 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, TITLE AND NON-INFRINGEMENT. IN NO EVENT
// SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY DAMAGES OR OTHER LIABILITY,
// WHETHER IN CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE
//
#include <stdio.h>
#include <stdlib.h>
#include <kdrive_express.h>
#define SERIAL_NUMBER_LENGTH (6)
#define ERROR_MESSAGE_LEN (128)
#define MAX_IND_ADDR (5)
#define MAX_ITEMS (5)
/*******************************
** Private Functions
********************************/
static int32_t open_access_port();
static void set_rf_domain_address(int32_t ap);
static void prop_value_read(int32_t sp);
static void prop_value_write(int32_t sp);
static void switch_prog_mode(int32_t sp, bool_t enable);
static void read_prog_mode(int32_t sp);
static void memory_read(int32_t sp);
static void memory_write(int32_t sp);
static void ind_addr_prog_mode_read(int32_t sp);
static void ind_addr_prog_mode_write(int32_t sp);
static void ind_addr_sn_read(int32_t sp);
static void ind_addr_sn_write(int32_t sp);
static void domain_addr_prog_mode_read(int32_t sp);
static void domain_addr_prog_mode_write(int32_t sp);
static void domain_addr_sn_read(int32_t sp);
static void domain_addr_sn_write(int32_t sp);
static void error_callback(error_t e, void* user_data);
/*******************************
** Private Variables
********************************/
/*
For Twisted Pair:
Set to 0
For RF:
Set to 1
*/
static bool_t is_rf = 0;
/*
For Twisted Pair:
Set to 1 to use connection-oriented
Set to 0 for connection-less
For RF:
Set to 0 for connection-less
*/
static bool_t connection_oriented = 1;
static uint16_t address = 0x5102;
/*******************************
** Main
********************************/
int main(int argc, char* argv[])
{
/* create a access and service port */
/* Configure the logging level and console logger */
/*
We register an error callback as a convenience logger function to
print out the error message when an error occurs.
*/
kdrive_register_error_callback(&error_callback, NULL);
/*
We create a Access Port descriptor. This descriptor is then used for
all calls to that specific access port.
*/
ap = open_access_port();
/*
We check that we were able to allocate a new descriptor
This should always happen, unless a bad_alloc exception is internally thrown
which means the memory couldn't be allocated.
*/
{
kdrive_logger(KDRIVE_LOGGER_FATAL, "Unable to create access port. This is a terminal failure");
while (1)
{
;
}
}
/*
KNX USB Local Device Management
Set the RF Domain Address
This will only work for interfaces that support RF
(i.e. KNX TP USB interfaces will raise an error here, we ignore it)
*/
if (is_rf)
{
set_rf_domain_address(ap);
}
/*
We create a Service Port descriptor. This descriptor is then used for
all calls to that specific service port. The service port requires
an access port
*/
sp = kdrive_sp_create(ap);
/*
We check that we were able to allocate a new descriptor
This should always happen, unless a bad_alloc exception is internally thrown
which means the memory couldn't be allocated.
*/
{
kdrive_logger(KDRIVE_LOGGER_FATAL, "Unable to create service port. This is a terminal failure");
while (1)
{
;
}
}
/*
Set the device services to connection-oriented or
connection-less (depending on the value of connection_oriented)
*/
kdrive_sp_set_co(sp, connection_oriented);
prop_value_read(sp); /* read property value : serial number */
prop_value_write(sp); /* write property value : programming mode */
if (is_rf)
{
domain_addr_sn_read(sp); /* read the domain address via serial number */
domain_addr_sn_write(sp); /* write the domain address via serial number */
}
ind_addr_sn_read(sp); /* read the individual address via serial number */
ind_addr_sn_write(sp); /* write the individual address via serial number */
switch_prog_mode(sp, 1); /* switch the programming mode on */
read_prog_mode(sp); /* read the programming mode */
if (is_rf)
{
domain_addr_prog_mode_read(sp); /* read the domain address of devices which are in programming mode */
domain_addr_prog_mode_write(sp); /* write the domain address of devices which are in programming mode */
}
ind_addr_prog_mode_read(sp); /* read the individual address of devices which are in programming mode */
ind_addr_prog_mode_write(sp); /* write the individual address of devices which are in programming mode */
switch_prog_mode(sp, 0); /* switch the programming mode off */
read_prog_mode(sp); /* read the programming mode */
memory_read(sp); /* read memory: programming mode */
memory_write(sp); /* write memory: programming mode */
/* Release the service port */
/* Close the access port */
return 0;
}
/*******************************
** Private Functions
********************************/
static int32_t open_access_port()
{
{
if ((kdrive_ap_enum_usb(ap) == 0) ||
{
}
}
return ap;
}
void set_rf_domain_address(int32_t ap)
{
uint8_t da[KDRIVE_DA_LEN] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
}
void prop_value_read(int32_t sp)
{
uint8_t data[SERIAL_NUMBER_LENGTH];
uint32_t data_length = SERIAL_NUMBER_LENGTH;
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "Property Value Read");
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "===================");
if (kdrive_sp_prop_value_read(sp, address, 0, 11, 1, 1, data, &data_length) == KDRIVE_ERROR_NONE)
{
kdrive_logger_dump(KDRIVE_LOGGER_INFORMATION, "Read Serial Number: ", data, data_length);
}
}
void prop_value_write(int32_t sp)
{
uint8_t data = 0;
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "Property Value Write");
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "====================");
kdrive_sp_prop_value_write(sp, address, 0, 54, 1, 1, &data, 1);
}
void switch_prog_mode(int32_t sp, bool_t enable)
{
kdrive_sp_switch_prog_mode(sp, address, enable);
}
void read_prog_mode(int32_t sp)
{
bool_t enabled = 0;
if (kdrive_sp_read_prog_mode(sp, address, &enabled) == KDRIVE_ERROR_NONE)
{
kdrive_logger_ex(KDRIVE_LOGGER_INFORMATION, "Programming Mode: %s", enabled ? "on" : "off");
}
}
void memory_read(int32_t sp)
{
uint8_t data;
uint32_t data_length = 1;
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "===================");
if (kdrive_sp_memory_read(sp, address, 0x0060, 1, &data, &data_length) == KDRIVE_ERROR_NONE)
{
kdrive_logger_dump(KDRIVE_LOGGER_INFORMATION, "Read Prog mode: ", &data, data_length);
}
}
void memory_write(int32_t sp)
{
uint8_t data = 0;
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "====================");
kdrive_sp_memory_write(sp, address, 0x0060, &data, 1);
}
void ind_addr_prog_mode_read(int32_t sp)
{
uint32_t index = 0;
uint16_t data[MAX_IND_ADDR];
uint32_t data_length = MAX_IND_ADDR;
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "Individual Address Prog Mode Read");
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "=================================");
if (kdrive_sp_ind_addr_prog_mode_read(sp, 500, data, &data_length) == KDRIVE_ERROR_NONE)
{
kdrive_logger_ex(KDRIVE_LOGGER_INFORMATION, "Read %d Individual Address(es):", data_length);
for (index = 0; index < data_length; ++index)
{
}
}
}
void ind_addr_prog_mode_write(int32_t sp)
{
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "Individual Address Prog Mode Write");
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "==================================");
ind_addr_prog_mode_read(sp);
ind_addr_prog_mode_read(sp);
}
void ind_addr_sn_read(int32_t sp)
{
uint8_t sn[KDRIVE_SN_LEN] = { 0x00, 0xC5, 0x00, 0x00, 0x00, 0xFA };
uint16_t ind_addr = 0;
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "Individual Address Serial Number Read");
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "=====================================");
if (kdrive_sp_ind_addr_sn_read(sp, sn, &ind_addr) == KDRIVE_ERROR_NONE)
{
kdrive_logger_ex(KDRIVE_LOGGER_INFORMATION, "Read Individual Address: %d", ind_addr);
}
}
void ind_addr_sn_write(int32_t sp)
{
uint8_t sn[KDRIVE_SN_LEN] = { 0x00, 0xC5, 0x00, 0x00, 0x00, 0xFA };
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "Individual Address Serial Number Write");
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "======================================");
kdrive_sp_ind_addr_sn_write(sp, sn, 0x05F1);
ind_addr_sn_read(sp);
kdrive_sp_ind_addr_sn_write(sp, sn, address);
ind_addr_sn_read(sp);
}
void domain_addr_prog_mode_read(int32_t sp)
{
uint32_t index = 0;
domain_addr_prog_mode_read_t items[MAX_ITEMS];
uint32_t items_length = MAX_ITEMS;
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "Domain Address Prog Mode Read");
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "=============================");
if (kdrive_sp_domain_addr_prog_mode_read(sp, 500, items, &items_length) == KDRIVE_ERROR_NONE)
{
kdrive_logger_ex(KDRIVE_LOGGER_INFORMATION, "Read %d item(s):", items_length);
for (index = 0; index < items_length; ++index)
{
kdrive_logger_ex(KDRIVE_LOGGER_INFORMATION, "Individual Address : %04X", items[index].ind_addr);
kdrive_logger_dump(KDRIVE_LOGGER_INFORMATION, "Serial Number :", items[index].serial_number, KDRIVE_SN_LEN);
kdrive_logger_dump(KDRIVE_LOGGER_INFORMATION, "Domain Address :", items[index].domain_address, KDRIVE_DA_LEN);
}
}
}
void domain_addr_prog_mode_write(int32_t sp)
{
uint8_t da1[KDRIVE_DA_LEN] = { 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA };
uint8_t da2[KDRIVE_DA_LEN] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "Domain Address Prog Mode Write");
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "==============================");
domain_addr_prog_mode_read(sp);
domain_addr_prog_mode_read(sp);
}
void domain_addr_sn_read(int32_t sp)
{
uint8_t sn[KDRIVE_SN_LEN] = { 0x00, 0xC5, 0x00, 0x00, 0x00, 0xFA };
uint16_t ind_addr = 0;
uint8_t da[KDRIVE_DA_LEN] = { 0 };
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "Domain Address Serial Number Read");
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "=================================");
if (kdrive_sp_domain_addr_sn_read(sp, sn, &ind_addr, da) == KDRIVE_ERROR_NONE)
{
kdrive_logger_ex(KDRIVE_LOGGER_INFORMATION, "Individual Address : %04X", ind_addr);
}
}
void domain_addr_sn_write(int32_t sp)
{
uint8_t sn[KDRIVE_SN_LEN] = { 0x00, 0xC5, 0x00, 0x00, 0x00, 0xFA };
uint8_t da1[KDRIVE_DA_LEN] = { 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA };
uint8_t da2[KDRIVE_DA_LEN] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "Domain Address Serial Number Write");
kdrive_logger(KDRIVE_LOGGER_INFORMATION, "==================================");
domain_addr_sn_read(sp);
domain_addr_sn_read(sp);
}
void error_callback(error_t e, void* user_data)
{
{
static char error_message[ERROR_MESSAGE_LEN];
kdrive_get_error_message(e, error_message, ERROR_MESSAGE_LEN);
kdrive_logger_ex(KDRIVE_LOGGER_ERROR, "kdrive error: %s", error_message);
}
}
kdriveExpress_API error_t kdrive_ap_set_rf_domain_addr(int32_t ap, const uint8_t da[KDRIVE_DA_LEN])
Sets the Domain Address of the Local Device (KNX Interface Device)
kdriveExpress_API uint32_t kdrive_ap_enum_usb(int32_t ap)
Scan for all KNX USB Interface devices.
kdriveExpress_API bool_t kdrive_ap_release(int32_t ap)
Releases the AccessPort interface.
kdriveExpress_API int32_t kdrive_ap_create(void)
Creates an internal AccessPort interface This should be the first function called when working with t...
kdriveExpress_API error_t kdrive_ap_close(int32_t ap)
Closes the access port If the access port is not open nothing happens.
kdriveExpress_API error_t kdrive_ap_open_usb(int32_t ap, uint32_t iface_index)
Opens a connection to a KNX USB Interface device iface_index should be in the range 0....
kdriveExpress_API void kdrive_logger(uint8_t level, const char *message)
Writes to the kdrive express logger.
kdriveExpress_API void kdrive_logger_dump(uint8_t level, const char *message, const void *buffer, uint32_t buffer_len)
Logs the given message, followed by the data in buffer.
kdriveExpress_API void kdrive_logger_console(void)
Sets the logger to write to the console.
kdriveExpress_API void kdrive_logger_ex(uint8_t level, const char *fmt,...)
Writes to the kdrive express logger.
kdriveExpress_API void kdrive_logger_set_level(uint8_t level)
Sets the root logger level This is once of:
kdriveExpress_API error_t kdrive_sp_switch_prog_mode(int32_t sp, uint16_t ind_addr, bool_t enable)
Enable / Disable the programming mode (switches the learn LED).
kdriveExpress_API error_t kdrive_sp_domain_addr_prog_mode_read(int32_t sp, uint32_t wait_time, domain_addr_prog_mode_read_t items[], uint32_t *items_length)
Reads the Domain Addresses of devices in Programming Mode (i.e.
kdriveExpress_API error_t kdrive_sp_ind_addr_sn_read(int32_t sp, const uint8_t sn[KDRIVE_SN_LEN], uint16_t *ind_addr)
Reads the individual address of a device that matches the specified Serial Number.
kdriveExpress_API error_t kdrive_sp_ind_addr_sn_write(int32_t sp, const uint8_t sn[KDRIVE_SN_LEN], uint16_t new_ind_addr)
Writes the individual address of a device that matches the specified Serial Number.
kdriveExpress_API error_t kdrive_sp_ind_addr_prog_mode_write(int32_t sp, uint16_t new_ind_addr)
Writes the specified individual address to a device in Programming Mode (i.e.
kdriveExpress_API error_t kdrive_sp_domain_addr_sn_write(int32_t sp, const uint8_t sn[KDRIVE_SN_LEN], const uint8_t da[KDRIVE_DA_LEN])
Writes the Domain Address of a device This function validates that the domain address was successfull...
kdriveExpress_API error_t kdrive_sp_read_prog_mode(int32_t sp, uint16_t ind_addr, bool_t *enabled)
Reads the current programming mode.
kdriveExpress_API error_t kdrive_sp_prop_value_write(int32_t sp, uint16_t ind_addr, uint8_t object_index, uint8_t prop_id, uint8_t nr_of_elems, uint16_t start_index, const uint8_t data[], uint32_t data_length)
Writes the value of a property to a device.
kdriveExpress_API error_t kdrive_sp_prop_value_read(int32_t sp, uint16_t ind_addr, uint8_t object_index, uint8_t prop_id, uint8_t nr_of_elems, uint16_t start_index, uint8_t data[], uint32_t *data_length)
Reads a property value from a device The data buffer must exist (should be pre-allocated by the user)...
kdriveExpress_API error_t kdrive_sp_ind_addr_prog_mode_read(int32_t sp, uint32_t wait_time, uint16_t data[], uint32_t *data_length)
Reads the individual addresses of devices in Programming Mode (i.e.
kdriveExpress_API error_t kdrive_sp_domain_addr_sn_read(int32_t sp, const uint8_t sn[KDRIVE_SN_LEN], uint16_t *ind_addr, uint8_t da[KDRIVE_DA_LEN])
Reads the Domain Address of a device that matches the specified Serial Number.
kdriveExpress_API error_t kdrive_sp_memory_read(int32_t sp, uint16_t ind_addr, uint16_t memory_addr, uint8_t number, uint8_t data[], uint32_t *data_length)
Reads data via DMA.
kdriveExpress_API error_t kdrive_sp_domain_addr_prog_mode_write(int32_t sp, const uint8_t da[KDRIVE_DA_LEN])
Writes the Domain Address to a device in Programming Mode (i.e.
kdriveExpress_API bool_t kdrive_sp_release(int32_t sp)
Releases the ServicePort interface.
kdriveExpress_API error_t kdrive_sp_set_co(int32_t sp, bool_t connection_oriented)
Sets whether the device services are run as connection-oriented or connection-less.
kdriveExpress_API error_t kdrive_sp_memory_write(int32_t sp, uint16_t ind_addr, uint16_t memory_addr, const uint8_t data[], uint32_t data_length)
Writes data via DMA.
kdriveExpress_API int32_t kdrive_sp_create(int32_t ap)
Creates an internal ServicePort interface This should be the first function called when working with ...
unsigned short uint16_t
16 bit unsigned char
Definition: kdrive_express_config.h:30
int int32_t
32 bit signed int
Definition: kdrive_express_config.h:34
unsigned int uint32_t
32 bit unsigned char
Definition: kdrive_express_config.h:31
int32_t error_t
Definition: kdrive_express_config.h:46
int32_t bool_t
Definition: kdrive_express_config.h:57
unsigned char uint8_t
8 bit unsigned char
Definition: kdrive_express_config.h:29
#define KDRIVE_DA_LEN
The Length of a KNX Domain Address.
Definition: kdrive_express_defs.h:35
#define KDRIVE_SN_LEN
The Length of a KNX Serial Number.
Definition: kdrive_express_defs.h:34
#define KDRIVE_INVALID_DESCRIPTOR
Indicates an invalid descriptor.
Definition: kdrive_express_defs.h:39
kdriveExpress_API void kdrive_register_error_callback(kdrive_error_callback c, void *user_data)
Registers the error callback function.
#define KDRIVE_TIMEOUT_ERROR
Timeout.
Definition: kdrive_express_error.h:26
#define KDRIVE_ERROR_NONE
No Error, Everything OK.
Definition: kdrive_express_error.h:22
kdriveExpress_API void kdrive_get_error_message(error_t e, char *str, uint32_t str_len)
Gets the error message.
#define KDRIVE_LOGGER_FATAL
A fatal error.
Definition: kdrive_express_logger.h:26
#define KDRIVE_LOGGER_ERROR
An error.
Definition: kdrive_express_logger.h:28
#define KDRIVE_LOGGER_INFORMATION
An informational message, usually denoting the successful completion of an operation.
Definition: kdrive_express_logger.h:31
Structure holding individual address, serial number, domain address for the DomainAddressProgModeRead...
Definition: kdrive_express_services.h:1366