This commit is contained in:
etrinh 2020-06-15 14:36:49 +02:00
commit 21264dd4b3
27 changed files with 395 additions and 39 deletions

6
.gitignore vendored
View File

@ -270,3 +270,9 @@ __pycache__/
**/CodeDB
**/VisualGDBCache
doc/build
.pio
.vscode/.browse.c_cpp.db*
.vscode/c_cpp_properties.json
.vscode/launch.json
.vscode/ipch

View File

@ -13,8 +13,6 @@
- MATRIX_EVAL="CC=gcc-7 && CXX=g++-7"
cache:
directories:
- ~/arduino_ide
- ~/.arduino15/packages/
git:
depth: false
quiet: true
@ -36,6 +34,7 @@
- language: cpp
os: linux
env:
- ARDUINO_IDE_VERSION="1.8.11"
cache:
directories:
- ~/arduino_ide
@ -52,13 +51,15 @@
- sed -i 's#compiler.warning_level=all#compiler.warning_level=default#' ~/.arduino15/preferences.txt
# changes for bsec lib
# samd
- sed -ri 's#(recipe.c.combine.pattern=[^$]*\{archive_file\}")( -Wl,--end-group)#\1 {compiler.libraries.ldflags}\2#' ~/.arduino15/packages/arduino/hardware/samd/1.8.4/platform.txt
- sed -i 's#compiler.elf2hex.extra_flags=#compiler.elf2hex.extra_flags=\ncompiler.libraries.ldflags=#' ~/.arduino15/packages/arduino/hardware/samd/1.8.4/platform.txt
- ls -l ~/.arduino15/packages/arduino/hardware/samd
- sed -ri 's#(recipe.c.combine.pattern=[^$]*\{archive_file\}")( -Wl,--end-group)#\1 {compiler.libraries.ldflags}\2#' ~/.arduino15/packages/arduino/hardware/samd/1.8.6/platform.txt
- sed -i 's#compiler.elf2hex.extra_flags=#compiler.elf2hex.extra_flags=\ncompiler.libraries.ldflags=#' ~/.arduino15/packages/arduino/hardware/samd/1.8.6/platform.txt
# esp8266
- sed -ri 's#(recipe.c.combine.pattern=[^$]*\{compiler.c.elf.libs\})( -Wl,--end-group "-L\{build.path\}")#\1 {compiler.libraries.ldflags}\2#' ~/.arduino15/packages/esp8266/hardware/esp8266/2.6.3/platform.txt
- sed -i 's#compiler.elf2hex.extra_flags=#compiler.elf2hex.extra_flags=\ncompiler.libraries.ldflags=#' ~/.arduino15/packages/esp8266/hardware/esp8266/2.6.3/platform.txt
- sed -i '/^.*libalgobsec.*$/d' ~/.arduino15/packages/esp8266/hardware/esp8266/2.6.3/tools/sdk/ld/eagle.app.v6.common.ld.h
- sed -ri 's#(\*libwps\.a:\(\.literal\.\* \.text\.\*\))#\1\n *libalgobsec.a:(.literal.* .text.*)#' ~/.arduino15/packages/esp8266/hardware/esp8266/2.6.3/tools/sdk/ld/eagle.app.v6.common.ld.h
- ls -l ~/.arduino15/packages/esp8266/hardware/esp8266
- sed -ri 's#(recipe.c.combine.pattern=[^$]*\{compiler.c.elf.libs\})( -Wl,--end-group "-L\{build.path\}")#\1 {compiler.libraries.ldflags}\2#' ~/.arduino15/packages/esp8266/hardware/esp8266/2.7.1/platform.txt
- sed -i 's#compiler.elf2hex.extra_flags=#compiler.elf2hex.extra_flags=\ncompiler.libraries.ldflags=#' ~/.arduino15/packages/esp8266/hardware/esp8266/2.7.1/platform.txt
- sed -i '/^.*libalgobsec.*$/d' ~/.arduino15/packages/esp8266/hardware/esp8266/2.7.1/tools/sdk/ld/eagle.app.v6.common.ld.h
- sed -ri 's#(\*libwps\.a:\(\.literal\.\* \.text\.\*\))#\1\n *libalgobsec.a:(.literal.* .text.*)#' ~/.arduino15/packages/esp8266/hardware/esp8266/2.7.1/tools/sdk/ld/eagle.app.v6.common.ld.h
# the HDC100X lib is not properly set up in githup so move things around a bit
- rm -rf $HOME/arduino_ide/libraries/HDC100X_Arduino_Library-master
@ -74,12 +75,12 @@
# - buildExampleSketch knx-bme680
# - buildExampleSketch knx-hdc1008
- build_platform zero
- build_platform esp8266
# - build_platform esp8266
# Test build for PlatformIO based projects
- language: python
python:
- "2.7"
- "3.8"
cache:
directories:
- "~/.platformio"

7
.vscode/extensions.json vendored Normal file
View File

@ -0,0 +1,7 @@
{
// See http://go.microsoft.com/fwlink/?LinkId=827846
// for the documentation about the extensions.json format
"recommendations": [
"platformio.platformio-ide"
]
}

View File

@ -28,7 +28,10 @@ add_executable(knx-linux
../../src/knx/cemi_frame.cpp
../../src/knx/cemi_frame.h
../../src/knx/cemi_server.cpp
../../src/knx/cemi_server.h
../../src/knx/cemi_server_object.cpp
../../src/knx/cemi_server_object.h
../../src/knx/config.h
../../src/knx/data_link_layer.cpp
../../src/knx/data_link_layer.h
../../src/knx/data_property.cpp
@ -50,13 +53,22 @@ add_executable(knx-linux
../../src/knx/ip_parameter_object.cpp
../../src/knx/ip_parameter_object.h
../../src/knx/knx_ip_device_information_dib.cpp
../../src/knx/knx_ip_device_information_dib.h
../../src/knx/knx_ip_dib.cpp
../../src/knx/knx_ip_dib.h
../../src/knx/knx_ip_frame.cpp
../../src/knx/knx_ip_frame.h
../../src/knx/knx_ip_routing_indication.cpp
../../src/knx/knx_ip_routing_indication.h
../../src/knx/knx_ip_search_request.cpp
../../src/knx/knx_ip_search_request.h
../../src/knx/knx_ip_search_response.cpp
../../src/knx/knx_ip_search_response.h
../../src/knx/knx_ip_supported_service_dib.cpp
../../src/knx/knx_ip_supported_service_dib.h
../../src/knx/ip_host_protocol_address_information.cpp
../../src/knx/ip_host_protocol_address_information.h
../../src/knx/knx_types.h
../../src/knx/knx_value.cpp
../../src/knx/knx_value.h
../../src/knx/memory.cpp
@ -75,6 +87,7 @@ add_executable(knx-linux
../../src/knx/rf_medium_object.h
../../src/knx/rf_physical_layer.cpp
../../src/knx/rf_physical_layer.h
../../src/knx/save_restore.h
../../src/knx/table_object.cpp
../../src/knx/table_object.h
../../src/knx/tpdu.cpp
@ -84,6 +97,7 @@ add_executable(knx-linux
../../src/knx/transport_layer.cpp
../../src/knx/transport_layer.h
../../src/knx/usb_tunnel_interface.cpp
../../src/knx/usb_tunnel_interface.h
../../src/knx_facade.cpp
../../src/knx_facade.h
../../src/linux_platform.cpp

View File

@ -19,7 +19,7 @@ board_build.usb_product="KNX RF - USB Interface"
lib_deps =
SPI
Adafruit TinyUSB Library
Adafruit TinyUSB Library@0.7.1
https://github.com/thelsing/FlashStorage.git
knx

27
platformio.ini Normal file
View File

@ -0,0 +1,27 @@
; PlatformIO Project Configuration File
;
; Build options: build flags, source filter
; Upload options: custom upload port, speed and extra flags
; Library options: dependencies, extra library storages
; Advanced options: extra scripting
;
; Please visit documentation for the other options and examples
; https://docs.platformio.org/page/projectconf.html
[platformio]
src_dir = examples/knx-demo
[env]
platform = atmelsam
board = zeroUSB
framework = arduino
build_type = debug
monitor_speed = 115200
lib_ldf_mode = deep+
lib_extra_dirs =
${sysenv.USERPROFILE}/Documents/PlatformIO/Projects
build_flags =
-Wno-unknown-pragmas
[env:build]

View File

@ -118,8 +118,15 @@ void ApplicationLayer::dataBroadcastIndication(HopCountType hopType, Priority pr
break;
}
default:
#if (MEDIUM_TYPE == 5)||(MEDIUM_TYPE == 0)
// Make sure we also check if it is a service normally available only on SystemBroadcast on open media
dataSystemBroadcastIndication(hopType, priority, source, apdu);
#else
print("Broadcast-indication: unhandled APDU-Type: ");
println(apdu.type());
#endif
break;
}
}
@ -159,8 +166,15 @@ void ApplicationLayer::dataBroadcastConfirm(AckType ack, HopCountType hopType, P
break;
}
default:
#if (MEDIUM_TYPE == 5)||(MEDIUM_TYPE == 0)
// Make sure we also check if it is a service normally available only on SystemBroadcast on open media
dataSystemBroadcastConfirm(hopType, priority, apdu, status);
#else
print("Broadcast-confirm: unhandled APDU-Type: ");
println(apdu.type());
#endif
break;
}
}
@ -198,13 +212,58 @@ void ApplicationLayer::dataSystemBroadcastIndication(HopCountType hopType, Prior
break;
}
default:
#if (MEDIUM_TYPE == 5)||(MEDIUM_TYPE == 0)
print("Broadcast-indication: unhandled APDU-Type: ");
#else
print("SystemBroadcast-indication: unhandled APDU-Type: ");
#endif
println(apdu.type());
break;
}
}
void ApplicationLayer::dataSystemBroadcastConfirm(HopCountType hopType, Priority priority, APDU& apdu, bool status)
{
const uint8_t* data = apdu.data();
switch (apdu.type())
{
// TODO: testInfo could be of any length
case SystemNetworkParameterRead:
{
uint16_t objectType;
uint16_t propertyId;
uint8_t testInfo[2];
popWord(objectType, data + 1);
popWord(propertyId, data + 3);
popByte(testInfo[0], data + 4);
popByte(testInfo[1], data + 5);
propertyId = (propertyId >> 4) & 0x0FFF;;
testInfo[0] &= 0x0F;
_bau.systemNetworkParameterReadLocalConfirm(priority, hopType, objectType, propertyId, testInfo, sizeof(testInfo), status);
break;
}
case DomainAddressSerialNumberWrite:
{
const uint8_t* knxSerialNumber = &data[1];
const uint8_t* domainAddress = &data[7];
_bau.domainAddressSerialNumberWriteLocalConfirm(priority, hopType, domainAddress, knxSerialNumber, status);
break;
}
case DomainAddressSerialNumberRead:
{
const uint8_t* knxSerialNumber = &data[1];
_bau.domainAddressSerialNumberReadLocalConfirm(priority, hopType, knxSerialNumber, status);
break;
}
default:
#if (MEDIUM_TYPE == 5)||(MEDIUM_TYPE == 0)
print("Broadcast-confirm: unhandled APDU-Type: ");
#else
print("SystemBroadcast-confirm: unhandled APDU-Type: ");
#endif
println(apdu.type());
break;
}
}
void ApplicationLayer::dataIndividualIndication(HopCountType hopType, Priority priority, uint16_t tsap, APDU& apdu)
@ -494,6 +553,25 @@ void ApplicationLayer::propertyValueWriteRequest(AckType ack, Priority priority,
startIndex, data, length);
}
void ApplicationLayer::functionPropertyStateResponse(AckType ack, Priority priority, HopCountType hopType, uint16_t asap,
uint8_t objectIndex, uint8_t propertyId, uint8_t* resultData, uint8_t resultLength)
{
CemiFrame frame(3 + resultLength + 1);
APDU& apdu = frame.apdu();
apdu.type(FunctionPropertyStateResponse);
uint8_t* data = apdu.data() + 1;
data[0] = objectIndex;
data[1] = propertyId;
if (resultLength > 0)
memcpy(&data[2], resultData, resultLength);
if (asap == _connectedTsap)
_transportLayer->dataConnectedRequest(asap, priority, apdu);
else
_transportLayer->dataIndividualRequest(ack, hopType, priority, asap, apdu);
}
void ApplicationLayer::propertyDescriptionReadRequest(AckType ack, Priority priority, HopCountType hopType, uint16_t asap,
uint8_t objectIndex, uint8_t propertyId, uint8_t propertyIndex)
{
@ -751,6 +829,12 @@ void ApplicationLayer::individualIndication(HopCountType hopType, Priority prior
startIndex, data + 5, apdu.length() - 5);
break;
}
case FunctionPropertyCommand:
_bau.functionPropertyCommandIndication(priority, hopType, tsap, data[1], data[2], &data[3], apdu.length() - 4); //TODO: check length
break;
case FunctionPropertyState:
_bau.functionPropertyStateIndication(priority, hopType, tsap, data[1], data[2], &data[3], apdu.length() - 4); //TODO: check length
break;
case PropertyDescriptionRead:
_bau.propertyDescriptionReadIndication(priority, hopType, tsap, data[1], data[2], data[3]);
break;

View File

@ -105,6 +105,8 @@ class ApplicationLayer
uint8_t propertyId, uint8_t numberOfElements, uint16_t startIndex, uint8_t* data, uint8_t length);
void propertyValueWriteRequest(AckType ack, Priority priority, HopCountType hopType, uint16_t asap, uint8_t objectIndex,
uint8_t propertyId, uint8_t numberOfElements, uint16_t startIndex, uint8_t* data, uint8_t length);
void functionPropertyStateResponse(AckType ack, Priority priority, HopCountType hopType, uint16_t asap,
uint8_t objectIndex, uint8_t propertyId, uint8_t *resultData, uint8_t resultLength);
void propertyDescriptionReadRequest(AckType ack, Priority priority, HopCountType hopType, uint16_t asap,
uint8_t objectIndex, uint8_t propertyId, uint8_t propertyIndex);
void propertyDescriptionReadResponse(AckType ack, Priority priority, HopCountType hopType, uint16_t asap,

View File

@ -106,6 +106,14 @@ void BusAccessUnit::propertyValueReadIndication(Priority priority, HopCountType
{
}
void BusAccessUnit::functionPropertyCommandIndication(Priority priority, HopCountType hopType, uint16_t asap, uint8_t objectIndex, uint8_t propertyId, uint8_t* data, uint8_t length)
{
}
void BusAccessUnit::functionPropertyStateIndication(Priority priority, HopCountType hopType, uint16_t asap, uint8_t objectIndex, uint8_t propertyId, uint8_t* data, uint8_t length)
{
}
void BusAccessUnit::propertyValueReadResponseConfirm(AckType ack, Priority priority, HopCountType hopType, uint16_t asap, uint8_t objectIndex, uint8_t propertyId, uint8_t numberOfElements, uint16_t startIndex, uint8_t* data, uint8_t length, bool status)
{
}
@ -256,6 +264,20 @@ void BusAccessUnit::domainAddressSerialNumberReadIndication(Priority priority, H
{
}
void BusAccessUnit::systemNetworkParameterReadLocalConfirm(Priority priority, HopCountType hopType, uint16_t objectType,
uint16_t propertyId, uint8_t* testInfo, uint16_t testInfoLength, bool status)
{
}
void BusAccessUnit::domainAddressSerialNumberWriteLocalConfirm(Priority priority, HopCountType hopType, const uint8_t* rfDoA,
const uint8_t* knxSerialNumber, bool status)
{
}
void BusAccessUnit::domainAddressSerialNumberReadLocalConfirm(Priority priority, HopCountType hopType, const uint8_t* knxSerialNumber, bool status)
{
}
void BusAccessUnit::propertyValueRead(ObjectType objectType, uint8_t objectInstance, uint8_t propertyId,
uint8_t& numberOfElements, uint16_t startIndex,
uint8_t** data, uint32_t& length)

View File

@ -48,6 +48,10 @@ class BusAccessUnit
uint8_t objectIndex, uint8_t propertyId, uint8_t numberOfElements, uint16_t startIndex, bool status);
virtual void propertyValueReadIndication(Priority priority, HopCountType hopType, uint16_t asap, uint8_t objectIndex,
uint8_t propertyId, uint8_t numberOfElements, uint16_t startIndex);
virtual void functionPropertyCommandIndication(Priority priority, HopCountType hopType, uint16_t asap, uint8_t objectIndex,
uint8_t propertyId, uint8_t* data, uint8_t length);
virtual void functionPropertyStateIndication(Priority priority, HopCountType hopType, uint16_t asap, uint8_t objectIndex,
uint8_t propertyId, uint8_t* data, uint8_t length);
virtual void propertyValueReadResponseConfirm(AckType ack, Priority priority, HopCountType hopType, uint16_t asap, uint8_t objectIndex,
uint8_t propertyId, uint8_t numberOfElements, uint16_t startIndex, uint8_t* data, uint8_t length, bool status);
virtual void propertyValueReadAppLayerConfirm(Priority priority, HopCountType hopType, uint16_t asap, uint8_t objectIndex,
@ -119,6 +123,14 @@ class BusAccessUnit
virtual void domainAddressSerialNumberReadIndication(Priority priority, HopCountType hopType, const uint8_t* knxSerialNumber);
virtual void systemNetworkParameterReadLocalConfirm(Priority priority, HopCountType hopType, uint16_t objectType,
uint16_t propertyId, uint8_t* testInfo, uint16_t testInfoLength, bool status);
virtual void domainAddressSerialNumberWriteLocalConfirm(Priority priority, HopCountType hopType, const uint8_t* rfDoA,
const uint8_t* knxSerialNumber, bool status);
virtual void domainAddressSerialNumberReadLocalConfirm(Priority priority, HopCountType hopType, const uint8_t* knxSerialNumber, bool status);
virtual void propertyValueRead(ObjectType objectType, uint8_t objectInstance, uint8_t propertyId,
uint8_t& numberOfElements, uint16_t startIndex,
uint8_t** data, uint32_t& length);

View File

@ -150,4 +150,14 @@ void Bau27B0::individualAddressSerialNumberReadIndication(Priority priority, Hop
_appLayer.IndividualAddressSerialNumberReadResponse(priority, hopType, _rfMediumObj.rfDomainAddress(), knxSerialNumber);
}
#endif // #if MEDIUM_TYPE == 2
void Bau27B0::domainAddressSerialNumberWriteLocalConfirm(Priority priority, HopCountType hopType, const uint8_t* rfDoA,
const uint8_t* knxSerialNumber, bool status)
{
}
void Bau27B0::domainAddressSerialNumberReadLocalConfirm(Priority priority, HopCountType hopType, const uint8_t* knxSerialNumber, bool status)
{
}
#endif // #ifdef USE_RF

View File

@ -34,5 +34,8 @@ class Bau27B0 : public BauSystemB
void individualAddressSerialNumberWriteIndication(Priority priority, HopCountType hopType, uint16_t newIndividualAddress,
uint8_t* knxSerialNumber) override;
void individualAddressSerialNumberReadIndication(Priority priority, HopCountType hopType, uint8_t* knxSerialNumber) override;
void domainAddressSerialNumberWriteLocalConfirm(Priority priority, HopCountType hopType, const uint8_t* rfDoA,
const uint8_t* knxSerialNumber, bool status) override;
void domainAddressSerialNumberReadLocalConfirm(Priority priority, HopCountType hopType, const uint8_t* knxSerialNumber, bool status) override;
};
#endif

View File

@ -240,6 +240,32 @@ void BauSystemB::propertyValueReadIndication(Priority priority, HopCountType hop
startIndex, data, size);
}
void BauSystemB::functionPropertyCommandIndication(Priority priority, HopCountType hopType, uint16_t asap, uint8_t objectIndex,
uint8_t propertyId, uint8_t* data, uint8_t length)
{
uint8_t resultLength = 0;
uint8_t resultData[32];
InterfaceObject* obj = getInterfaceObject(objectIndex);
if(obj)
obj->command((PropertyID)propertyId, data, length, resultData, resultLength);
_appLayer.functionPropertyStateResponse(AckRequested, priority, hopType, asap, objectIndex, propertyId, resultData, resultLength);
}
void BauSystemB::functionPropertyStateIndication(Priority priority, HopCountType hopType, uint16_t asap, uint8_t objectIndex,
uint8_t propertyId, uint8_t* data, uint8_t length)
{
uint8_t resultLength = 0;
uint8_t resultData[32];
InterfaceObject* obj = getInterfaceObject(objectIndex);
if(obj)
obj->state((PropertyID)propertyId, data, length, resultData, resultLength);
_appLayer.functionPropertyStateResponse(AckRequested, priority, hopType, asap, objectIndex, propertyId, resultData, resultLength);
}
void BauSystemB::individualAddressReadIndication(HopCountType hopType)
{
if (_deviceObj.progMode())
@ -393,6 +419,11 @@ void BauSystemB::systemNetworkParameterReadIndication(Priority priority, HopCoun
}
}
void BauSystemB::systemNetworkParameterReadLocalConfirm(Priority priority, HopCountType hopType, uint16_t objectType,
uint16_t propertyId, uint8_t* testInfo, uint16_t testInfoLength, bool status)
{
}
void BauSystemB::propertyValueRead(ObjectType objectType, uint8_t objectInstance, uint8_t propertyId,
uint8_t &numberOfElements, uint16_t startIndex,
uint8_t **data, uint32_t &length)

View File

@ -56,6 +56,10 @@ class BauSystemB : protected BusAccessUnit
uint8_t propertyId, uint8_t numberOfElements, uint16_t startIndex, uint8_t* data, uint8_t length) override;
void propertyValueReadIndication(Priority priority, HopCountType hopType, uint16_t asap, uint8_t objectIndex,
uint8_t propertyId, uint8_t numberOfElements, uint16_t startIndex) override;
void functionPropertyCommandIndication(Priority priority, HopCountType hopType, uint16_t asap, uint8_t objectIndex,
uint8_t propertyId, uint8_t* data, uint8_t length);
void functionPropertyStateIndication(Priority priority, HopCountType hopType, uint16_t asap, uint8_t objectIndex,
uint8_t propertyId, uint8_t* data, uint8_t length);
void individualAddressReadIndication(HopCountType hopType) override;
void individualAddressWriteIndication(HopCountType hopType, uint16_t newaddress) override;
void groupValueWriteLocalConfirm(AckType ack, uint16_t asap, Priority priority, HopCountType hopType,
@ -68,6 +72,8 @@ class BauSystemB : protected BusAccessUnit
uint8_t* data, uint8_t dataLength) override;
void systemNetworkParameterReadIndication(Priority priority, HopCountType hopType, uint16_t objectType,
uint16_t propertyId, uint8_t* testInfo, uint16_t testinfoLength) override;
void systemNetworkParameterReadLocalConfirm(Priority priority, HopCountType hopType, uint16_t objectType,
uint16_t propertyId, uint8_t* testInfo, uint16_t testInfoLength, bool status) override;
void connectConfirm(uint16_t tsap) override;
virtual InterfaceObject* getInterfaceObject(uint8_t idx) = 0;

View File

@ -140,7 +140,12 @@ bool DataLinkLayer::sendTelegram(NPDU & npdu, AckType ack, uint16_t destinationA
frame.addressType(addrType);
frame.priority(priority);
frame.repetition(RepititionAllowed);
#if (MEDIUM_TYPE == 5)||(MEDIUM_TYPE == 0)
// Make sure to always send as normal Broadcast on closed media (TP and IP)
frame.systemBroadcast(Broadcast);
#else
frame.systemBroadcast(systemBroadcast);
#endif
if (npdu.octetCount() <= 15)
frame.frameType(StandardFrame);

View File

@ -0,0 +1,51 @@
#pragma once
#include "property.h"
class InterfaceObject;
template <class T> class FunctionProperty : public Property
{
public:
FunctionProperty(T* io, PropertyID id, uint8_t access,
void (*commandCallback)(T*, uint8_t*, uint8_t, uint8_t*, uint8_t&),
void (*stateCallback)(T*, uint8_t*, uint8_t, uint8_t*, uint8_t&))
: Property(id, false, PDT_FUNCTION, 1, access), _interfaceObject(io), _commandCallback(commandCallback), _stateCallback(stateCallback)
/* max_elements is set to 1, see 3.3.7 Application Layer p.68 */
{}
virtual uint8_t read(uint16_t start, uint8_t count, uint8_t* data) const override
{
return 0;
}
virtual uint8_t write(uint16_t start, uint8_t count, const uint8_t* data) override
{
return 0;
}
virtual void command(uint8_t* data, uint8_t length, uint8_t* resultData, uint8_t& resultLength) override
{
if (length == 0 || _commandCallback == nullptr )
{
resultLength = 0;
return;
}
_commandCallback(_interfaceObject, data, length, resultData, resultLength);
}
virtual void state(uint8_t* data, uint8_t length, uint8_t* resultData, uint8_t& resultLength) override
{
if (length == 0 || _stateCallback == nullptr )
{
resultLength = 0;
return;
}
_stateCallback(_interfaceObject, data, length, resultData, resultLength);
}
private:
T* _interfaceObject = nullptr;
void (*_commandCallback)(T*, uint8_t*, uint8_t, uint8_t*, uint8_t&) = nullptr;
void (*_stateCallback)(T*, uint8_t*, uint8_t, uint8_t*, uint8_t&) = nullptr;
};

View File

@ -137,6 +137,30 @@ uint8_t InterfaceObject::propertySize(PropertyID id)
return prop->ElementSize();
}
void InterfaceObject::command(PropertyID id, uint8_t* data, uint8_t length, uint8_t* resultData, uint8_t& resultLength)
{
Property* prop = property(id);
if (prop == nullptr)
{
resultLength = 0;
return;;
}
prop->command(data, length, resultData, resultLength);
}
void InterfaceObject::state(PropertyID id, uint8_t* data, uint8_t length, uint8_t* resultData, uint8_t resultLength)
{
Property* prop = property(id);
if (prop == nullptr)
{
resultLength = 0;
return;;
}
prop->state(data, length, resultData, resultLength);
}
uint8_t InterfaceObject::propertyDescriptionCount()
{
return 0;

View File

@ -98,6 +98,34 @@ class InterfaceObject : public SaveRestore
* @returns the size in byte or 0 if the interface object does not have the property
*/
virtual uint8_t propertySize(PropertyID id);
/**
* Call command of a function property of the interface object. Property type must be PDT_FUNCTION
*
* @param id id of the property to call
*
* @param[in] length The size of the data buffer
*
* @param[in] data The argument data for the function
*
* @param[out] resultLength The size of the result data buffer
*
* @param[out] resultData The result data for the function
*/
virtual void command(PropertyID id, uint8_t* data, uint8_t length, uint8_t* resultData, uint8_t &resultLength);
/**
* Get state of a function property of the interface object. Property type must be PDT_FUNCTION
*
* @param id id of the property to call
*
* @param[in] length The size of the data buffer
*
* @param[in] data The argument data for the function
*
* @param[out] resultLength The size of the result data buffer
*
* @param[out] resultData The result data for the function
*/
virtual void state(PropertyID id, uint8_t* data, uint8_t length, uint8_t* resultData, uint8_t resultLength);
/**
* Read the Description of a property of the interface object. The output parameters are only valid if nuberOfElements is not zero.
*

View File

@ -1,6 +1,7 @@
#include "knx_ip_device_information_dib.h"
#include "bits.h"
#ifdef USE_IP
KnxIpDeviceInformationDIB::KnxIpDeviceInformationDIB(uint8_t* data) : KnxIpDIB(data)
{}
@ -98,3 +99,4 @@ void KnxIpDeviceInformationDIB::friendlyName(const uint8_t* value)
{
pushByteArray(value, LEN_FRIENDLY_NAME, _data + 24);
}
#endif

View File

@ -54,7 +54,6 @@ void KnxIpFrame::totalLength(uint16_t length)
{
pushWord(length, _data + 4);
}
#endif
uint8_t* KnxIpFrame::data()
{
@ -79,3 +78,4 @@ KnxIpFrame::KnxIpFrame(uint16_t length)
protocolVersion(KnxIp1_0);
totalLength(length);
}
#endif

View File

@ -1,8 +1,6 @@
#include "knx_ip_search_response.h"
#ifdef USE_IP
#endif
#define SERVICE_FAMILIES 2
KnxIpSearchResponse::KnxIpSearchResponse(IpParameterObject& parameters, DeviceObject& deviceObject)
@ -61,3 +59,4 @@ KnxIpSupportedServiceDIB& KnxIpSearchResponse::supportedServices()
{
return _supportedServices;
}
#endif

View File

@ -1,5 +1,6 @@
#include "knx_ip_supported_service_dib.h"
#ifdef USE_IP
KnxIpSupportedServiceDIB::KnxIpSupportedServiceDIB(uint8_t* data) : KnxIpDIB(data)
{}
@ -39,3 +40,4 @@ void KnxIpSupportedServiceDIB::serviceVersion(ServiceFamily family, uint8_t ver
}
}
}
#endif

View File

@ -138,6 +138,9 @@ enum ApduType
UserMemoryWrite = 0x2C2,
UserManufacturerInfoRead = 0x2C5,
UserManufacturerInfoResponse = 0x2C6,
FunctionPropertyCommand = 0x2C7,
FunctionPropertyState = 0x2C8,
FunctionPropertyStateResponse = 0x2C9,
DeviceDescriptorRead = 0x300,
DeviceDescriptorResponse = 0x340,
Restart = 0x380,

View File

@ -95,7 +95,7 @@ void Memory::writeMemory()
{
println(_data - buffer);
println(".");
println((int)_saveRestores[i], HEX);
//println((long)_saveRestores[i], HEX);
buffer = _saveRestores[i]->save(buffer);
}
@ -105,7 +105,7 @@ void Memory::writeMemory()
{
println(_data - buffer);
println(".");
println((int)_tableObjects[i], HEX);
//println((long)_tableObjects[i], HEX);
buffer = _tableObjects[i]->save(buffer);
//save to size of the memoryblock for tableobject too, so that we can rebuild the usedList and freeList

View File

@ -45,7 +45,6 @@ void NetworkLayer::dataIndication(AckType ack, AddressType addrType, uint16_t de
}
// destination == 0
_transportLayer.dataBroadcastIndication(hopType, priority, source, npdu.tpdu());
}
void NetworkLayer::dataConfirm(AckType ack, AddressType addressType, uint16_t destination, FrameFormat format, Priority priority, uint16_t source, NPDU& npdu, bool status)

View File

@ -203,3 +203,19 @@ uint8_t Property::write(uint16_t position, uint16_t value)
pushWord(value, data);
return write(position, 1, data);
}
void Property::command(uint8_t* data, uint8_t length, uint8_t* resultData, uint8_t& resultLength)
{
(void)data;
(void)length;
(void)resultData;
resultLength = 0;
}
void Property::state(uint8_t* data, uint8_t length, uint8_t* resultData, uint8_t &resultLength)
{
(void)data;
(void)length;
(void)resultData;
resultLength = 0;
}

View File

@ -238,6 +238,8 @@ class Property : public SaveRestore
uint8_t ElementSize() const;
virtual uint8_t read(uint16_t start, uint8_t count, uint8_t* data) const = 0;
virtual uint8_t write(uint16_t start, uint8_t count, const uint8_t* data) = 0;
virtual void command(uint8_t* data, uint8_t length, uint8_t* resultData, uint8_t& resultLength);
virtual void state(uint8_t* data, uint8_t length, uint8_t* resultData, uint8_t& resultLength);
uint8_t read(uint8_t& value) const;
uint8_t read(uint16_t& value) const;
uint8_t read(uint32_t& value) const;