mirror of
				https://github.com/thelsing/knx.git
				synced 2025-10-26 10:26:25 +01:00 
			
		
		
		
	delegate memory management for knx tables to Platform class. Preallocate memory for them on linux.
This commit is contained in:
		
							parent
							
								
									bdaca43642
								
							
						
					
					
						commit
						bd93aa12fa
					
				| @ -5,7 +5,7 @@ cmake_minimum_required(VERSION 2.7) | ||||
| project(knx) | ||||
| 
 | ||||
| set(LIBRARIES_FROM_REFERENCES "") | ||||
| add_library(knx SHARED ../src/knx/address_table_object.cpp ../src/knx/apdu.cpp ../src/knx/application_layer.cpp ../src/knx/application_program_object.cpp ../src/knx/association_table_object.cpp ../src/knx/bau.cpp ../src/knx/bau07B0.cpp ../src/knx/bau57B0.cpp ../src/knx/bau_systemB.cpp ../src/knx/bits.cpp ../src/knx/cemi_frame.cpp ../src/knx/datapoint_types.cpp ../src/knx/data_link_layer.cpp ../src/knx/device_object.cpp ../src/knx/group_object.cpp ../src/knx/group_object_table_object.cpp ../src/knx/interface_object.cpp ../src/knx/ip_data_link_layer.cpp ../src/knx/ip_parameter_object.cpp ../src/knx/memory.cpp ../src/knx/network_layer.cpp ../src/knx/npdu.cpp ../src/knx/table_object.cpp ../src/knx/tpdu.cpp ../src/knx/tpuart_data_link_layer.cpp ../src/knx/transport_layer.cpp ../src/linux_platform.cpp knxmodule.cpp) | ||||
| add_library(knx SHARED ../src/knx/address_table_object.cpp ../src/knx/apdu.cpp ../src/knx/application_layer.cpp ../src/knx/application_program_object.cpp ../src/knx/association_table_object.cpp ../src/knx/bau.cpp ../src/knx/bau07B0.cpp ../src/knx/bau57B0.cpp ../src/knx/bau_systemB.cpp ../src/knx/bits.cpp ../src/knx/cemi_frame.cpp ../src/knx/datapoint_types.cpp ../src/knx/data_link_layer.cpp ../src/knx/device_object.cpp ../src/knx/group_object.cpp ../src/knx/group_object_table_object.cpp ../src/knx/interface_object.cpp ../src/knx/ip_data_link_layer.cpp ../src/knx/ip_parameter_object.cpp ../src/knx/memory.cpp ../src/knx/network_layer.cpp ../src/knx/npdu.cpp ../src/knx/platform.cpp ../src/knx/table_object.cpp ../src/knx/tpdu.cpp ../src/knx/tpuart_data_link_layer.cpp ../src/knx/transport_layer.cpp ../src/linux_platform.cpp knxmodule.cpp) | ||||
| target_link_libraries(knx python3.5m "${LIBRARIES_FROM_REFERENCES}") | ||||
| include_directories(/usr/include/python3.5m ../src) | ||||
| SET_TARGET_PROPERTIES(knx PROPERTIES PREFIX "") | ||||
|  | ||||
| @ -7,5 +7,5 @@ project(knx) | ||||
| set(LIBRARIES_FROM_REFERENCES "") | ||||
| add_library(knx SHARED ../src/knx/address_table_object.cpp ../src/knx/apdu.cpp ../src/knx/application_layer.cpp ../src/knx/application_program_object.cpp ../src/knx/association_table_object.cpp ../src/knx/bau.cpp ../src/knx/bau07B0.cpp ../src/knx/bau57B0.cpp ../src/knx/bau_systemB.cpp ../src/knx/bits.cpp ../src/knx/cemi_frame.cpp ../src/knx/datapoint_types.cpp ../src/knx/data_link_layer.cpp ../src/knx/device_object.cpp ../src/knx/group_object.cpp ../src/knx/group_object_table_object.cpp ../src/knx/interface_object.cpp ../src/knx/ip_data_link_layer.cpp ../src/knx/ip_parameter_object.cpp ../src/knx/memory.cpp ../src/knx/network_layer.cpp ../src/knx/npdu.cpp ../src/knx/table_object.cpp ../src/knx/tpdu.cpp ../src/knx/tpuart_data_link_layer.cpp ../src/knx/transport_layer.cpp ../src/linux_platform.cpp knxmodule.cpp) | ||||
| target_link_libraries(knx python3.5m "${LIBRARIES_FROM_REFERENCES}") | ||||
| include_directories(/usr/include/python3.5m) | ||||
| include_directories(/usr/include/python3.5m ../src) | ||||
| SET_TARGET_PROPERTIES(knx PROPERTIES PREFIX "") | ||||
|  | ||||
| @ -128,6 +128,7 @@ | ||||
|     <ClCompile Include="..\src\knx\memory.cpp" /> | ||||
|     <ClCompile Include="..\src\knx\network_layer.cpp" /> | ||||
|     <ClCompile Include="..\src\knx\npdu.cpp" /> | ||||
|     <ClCompile Include="..\src\knx\platform.cpp" /> | ||||
|     <ClCompile Include="..\src\knx\table_object.cpp" /> | ||||
|     <ClCompile Include="..\src\knx\tpdu.cpp" /> | ||||
|     <ClCompile Include="..\src\knx\tpuart_data_link_layer.cpp" /> | ||||
|  | ||||
| @ -122,6 +122,9 @@ | ||||
|     <ClCompile Include="..\src\knx\transport_layer.cpp"> | ||||
|       <Filter>Source files\knx</Filter> | ||||
|     </ClCompile> | ||||
|     <ClCompile Include="..\src\knx\platform.cpp"> | ||||
|       <Filter>Source files\knx</Filter> | ||||
|     </ClCompile> | ||||
|   </ItemGroup> | ||||
|   <ItemGroup> | ||||
|     <ClInclude Include="..\src\linux_platform.h"> | ||||
|  | ||||
| @ -171,4 +171,4 @@ size_t EspPlatform::readBytesUart(uint8_t *buffer, size_t length) | ||||
|     printHex("p>", buffer, length); | ||||
|     return length; | ||||
| } | ||||
| #endif | ||||
| #endif | ||||
|  | ||||
| @ -6,7 +6,8 @@ | ||||
| using namespace std; | ||||
| 
 | ||||
| 
 | ||||
| AddressTableObject::AddressTableObject(uint8_t* memoryReference): TableObject(memoryReference) | ||||
| AddressTableObject::AddressTableObject(Platform& platform) | ||||
|     : TableObject(platform) | ||||
| { | ||||
| 
 | ||||
| } | ||||
|  | ||||
| @ -5,11 +5,8 @@ | ||||
| class AddressTableObject: public TableObject | ||||
| { | ||||
| public: | ||||
|     AddressTableObject(uint8_t* memoryReference); | ||||
|     #pragma GCC diagnostic push | ||||
|     #pragma GCC diagnostic ignored "-Woverloaded-virtual" | ||||
|     AddressTableObject(Platform& platform); | ||||
|     void readProperty(PropertyID id, uint32_t start, uint32_t& count, uint8_t* data); | ||||
|     #pragma GCC diagnostic pop | ||||
|     uint16_t entryCount(); | ||||
|     uint16_t getGa(uint16_t tsap); | ||||
|     uint16_t getTsap(uint16_t ga); | ||||
|  | ||||
| @ -1,7 +1,8 @@ | ||||
| #include "application_program_object.h" | ||||
| #include "bits.h" | ||||
| 
 | ||||
| ApplicationProgramObject::ApplicationProgramObject(uint8_t* memoryReference): TableObject(memoryReference) | ||||
| ApplicationProgramObject::ApplicationProgramObject(Platform& platform) | ||||
|     : TableObject(platform) | ||||
| { | ||||
| 
 | ||||
| } | ||||
|  | ||||
| @ -5,11 +5,8 @@ | ||||
| class ApplicationProgramObject: public TableObject | ||||
| { | ||||
| public: | ||||
|     ApplicationProgramObject(uint8_t* memoryReference); | ||||
|     #pragma GCC diagnostic push | ||||
|     #pragma GCC diagnostic ignored "-Woverloaded-virtual" | ||||
|     ApplicationProgramObject(Platform& platform); | ||||
|     void readProperty(PropertyID id, uint32_t start, uint32_t& count, uint8_t* data); | ||||
|     #pragma GCC diagnostic pop | ||||
|     void writeProperty(PropertyID id, uint8_t start, uint8_t* data, uint8_t count); | ||||
|     uint8_t propertySize(PropertyID id); | ||||
|     uint8_t* data(uint32_t addr); | ||||
|  | ||||
| @ -6,7 +6,8 @@ | ||||
| using namespace std; | ||||
| 
 | ||||
| 
 | ||||
| AssociationTableObject::AssociationTableObject(uint8_t* memoryReference): TableObject(memoryReference) | ||||
| AssociationTableObject::AssociationTableObject(Platform& platform) | ||||
|     : TableObject(platform) | ||||
| { | ||||
| 
 | ||||
| } | ||||
|  | ||||
| @ -5,11 +5,8 @@ | ||||
| class AssociationTableObject: public TableObject | ||||
| { | ||||
| public: | ||||
|     AssociationTableObject(uint8_t* memoryReference); | ||||
|     #pragma GCC diagnostic push | ||||
|     #pragma GCC diagnostic ignored "-Woverloaded-virtual" | ||||
|     AssociationTableObject(Platform& platform); | ||||
|     void readProperty(PropertyID id, uint32_t start, uint32_t& count, uint8_t* data); | ||||
|     #pragma GCC diagnostic pop | ||||
|     uint16_t entryCount(); | ||||
|     uint16_t operator[](uint16_t idx); | ||||
|     uint8_t* save(uint8_t* buffer); | ||||
|  | ||||
| @ -2,8 +2,8 @@ | ||||
| #include <string.h> | ||||
| #include <stdio.h> | ||||
| 
 | ||||
| BauSystemB::BauSystemB(Platform& platform): _memoryReference((uint8_t*)&_deviceObj), _memory(platform), _addrTable(_memoryReference), | ||||
|     _assocTable(_memoryReference), _groupObjTable(_memoryReference), _appProgram(_memoryReference), | ||||
| BauSystemB::BauSystemB(Platform& platform): _memory(platform), _addrTable(platform), | ||||
|     _assocTable(platform), _groupObjTable(platform), _appProgram(platform), | ||||
|     _platform(platform), _appLayer(_assocTable, *this), | ||||
|     _transLayer(_appLayer, _addrTable, _platform), _netLayer(_transLayer) | ||||
| { | ||||
| @ -138,7 +138,7 @@ void BauSystemB::deviceDescriptorReadIndication(Priority priority, HopCountType | ||||
| void BauSystemB::memoryWriteIndication(Priority priority, HopCountType hopType, uint16_t asap, uint8_t number, | ||||
|     uint16_t memoryAddress, uint8_t * data) | ||||
| { | ||||
|     memcpy(_memoryReference + memoryAddress, data, number); | ||||
|     memcpy(_platform.memoryReference() + memoryAddress, data, number); | ||||
|     _memory.memoryModified(); | ||||
| 
 | ||||
|     if (_deviceObj.verifyMode()) | ||||
| @ -149,7 +149,7 @@ void BauSystemB::memoryReadIndication(Priority priority, HopCountType hopType, u | ||||
|     uint16_t memoryAddress) | ||||
| { | ||||
|     _appLayer.memoryReadResponse(AckRequested, priority, hopType, asap, number, memoryAddress, | ||||
|         _memoryReference + memoryAddress); | ||||
|         _platform.memoryReference() + memoryAddress); | ||||
| } | ||||
| 
 | ||||
| void BauSystemB::restartRequestIndication(Priority priority, HopCountType hopType, uint16_t asap) | ||||
| @ -160,6 +160,7 @@ void BauSystemB::restartRequestIndication(Priority priority, HopCountType hopTyp | ||||
|     _platform.restart(); | ||||
|      | ||||
|     // for platforms that don't really restart
 | ||||
|     _memory.readMemory(); | ||||
|     _deviceObj.progMode(false); | ||||
|     _configured = true; | ||||
| } | ||||
| @ -172,12 +173,12 @@ void BauSystemB::authorizeIndication(Priority priority, HopCountType hopType, ui | ||||
| void BauSystemB::userMemoryReadIndication(Priority priority, HopCountType hopType, uint16_t asap, uint8_t number, uint32_t memoryAddress) | ||||
| { | ||||
|     _appLayer.userMemoryReadResponse(AckRequested, priority, hopType, asap, number, memoryAddress, | ||||
|         _memoryReference + memoryAddress); | ||||
|         _platform.memoryReference() + memoryAddress); | ||||
| } | ||||
| 
 | ||||
| void BauSystemB::userMemoryWriteIndication(Priority priority, HopCountType hopType, uint16_t asap, uint8_t number, uint32_t memoryAddress, uint8_t* data) | ||||
| { | ||||
|     memcpy(_memoryReference + memoryAddress, data, number); | ||||
|     memcpy(_platform.memoryReference() + memoryAddress, data, number); | ||||
|     _memory.memoryModified(); | ||||
| 
 | ||||
|     if (_deviceObj.verifyMode()) | ||||
|  | ||||
| @ -62,9 +62,6 @@ protected: | ||||
|     void updateGroupObject(GroupObject& go, uint8_t* data, uint8_t length); | ||||
| 
 | ||||
|     DeviceObject _deviceObj; | ||||
|     // pointer to first private variable as reference to memory read/write commands
 | ||||
|     // addesses are to big for memory read/write calls on 64bit systems otherwise
 | ||||
|     uint8_t* _memoryReference; | ||||
|     Memory _memory; | ||||
|     AddressTableObject _addrTable; | ||||
|     AssociationTableObject _assocTable; | ||||
|  | ||||
| @ -4,7 +4,8 @@ | ||||
| #include "group_object.h" | ||||
| #include "bits.h" | ||||
| 
 | ||||
| GroupObjectTableObject::GroupObjectTableObject(uint8_t* memoryReference): TableObject(memoryReference) | ||||
| GroupObjectTableObject::GroupObjectTableObject(Platform& platform) | ||||
|     : TableObject(platform) | ||||
| { | ||||
|     _groupObjects = 0; | ||||
|     _groupObjectCount = 0; | ||||
|  | ||||
| @ -8,11 +8,8 @@ class GroupObjectTableObject: public TableObject | ||||
|     friend class GroupObject; | ||||
| 
 | ||||
| public: | ||||
|     GroupObjectTableObject(uint8_t* memoryReference); | ||||
|     #pragma GCC diagnostic push | ||||
|     #pragma GCC diagnostic ignored "-Woverloaded-virtual" | ||||
|     GroupObjectTableObject(Platform& platform); | ||||
|     void readProperty(PropertyID id, uint32_t start, uint32_t& count, uint8_t* data); | ||||
|     #pragma GCC diagnostic pop | ||||
|     uint16_t entryCount(); | ||||
|     GroupObject& get(uint16_t asap); | ||||
|     GroupObject& nextUpdatedObject(bool& valid); | ||||
|  | ||||
							
								
								
									
										23
									
								
								src/knx/platform.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										23
									
								
								src/knx/platform.cpp
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,23 @@ | ||||
| #include "platform.h" | ||||
| 
 | ||||
| #include <cstdlib> | ||||
| 
 | ||||
| uint8_t* Platform::memoryReference() | ||||
| { | ||||
|     return _memoryReference; | ||||
| } | ||||
| 
 | ||||
| 
 | ||||
| uint8_t* Platform::allocMemory(size_t size) | ||||
| { | ||||
|     uint8_t* address =  (uint8_t*)malloc(size); | ||||
|     if (_memoryReference == 0) | ||||
|         _memoryReference = address; | ||||
|      | ||||
|     return address; | ||||
| } | ||||
| 
 | ||||
| void Platform::freeMemory(uint8_t* ptr) | ||||
| { | ||||
|     free(ptr); | ||||
| } | ||||
| @ -32,4 +32,10 @@ public: | ||||
|          | ||||
|     virtual uint8_t* getEepromBuffer(uint16_t size) = 0; | ||||
|     virtual void commitToEeprom() = 0; | ||||
|      | ||||
|     virtual uint8_t* memoryReference(); | ||||
|     virtual uint8_t* allocMemory(size_t size); | ||||
|     virtual void freeMemory(uint8_t* ptr); | ||||
| protected: | ||||
|     uint8_t* _memoryReference = 0; | ||||
| }; | ||||
| @ -1,10 +1,9 @@ | ||||
| #include <stdlib.h> | ||||
| #include <string.h> | ||||
| 
 | ||||
| #include "table_object.h" | ||||
| #include "bits.h" | ||||
| 
 | ||||
| TableObject::TableObject(uint8_t* memoryReference): _memoryReference(memoryReference) | ||||
| TableObject::TableObject(Platform& platform): _platform(platform) | ||||
| { | ||||
| 
 | ||||
| } | ||||
| @ -61,7 +60,7 @@ uint8_t TableObject::propertySize(PropertyID id) | ||||
| TableObject::~TableObject() | ||||
| { | ||||
|     if (_data != 0) | ||||
|         free(_data); | ||||
|         _platform.freeMemory(_data); | ||||
| } | ||||
| 
 | ||||
| LoadState TableObject::loadState() | ||||
| @ -101,9 +100,9 @@ uint8_t* TableObject::restore(uint8_t* buffer) | ||||
|     buffer = popInt(_size, buffer); | ||||
| 
 | ||||
|     if (_data) | ||||
|         free(_data); | ||||
|         _platform.freeMemory(_data); | ||||
| 
 | ||||
|     _data = (uint8_t*) malloc(_size); | ||||
|     _data = _platform.allocMemory(_size); | ||||
| 
 | ||||
|     buffer = popByteArray(_data, _size, buffer); | ||||
| 
 | ||||
| @ -112,21 +111,22 @@ uint8_t* TableObject::restore(uint8_t* buffer) | ||||
| 
 | ||||
| uint32_t TableObject::tableReference() | ||||
| { | ||||
|     return (uint32_t)(_data - _memoryReference); | ||||
|     return (uint32_t)(_data - _platform.memoryReference()); | ||||
| } | ||||
| 
 | ||||
| bool TableObject::allocTable(uint32_t size, bool doFill, uint8_t fillByte) | ||||
| { | ||||
|     if (_data) | ||||
|     { | ||||
|         free(_data); | ||||
|         _platform.freeMemory(_data); | ||||
|         _data = 0; | ||||
|         _size = 0; | ||||
|     } | ||||
| 
 | ||||
|     if (size == 0) | ||||
|         return true; | ||||
|      | ||||
|     _data = (uint8_t*)malloc(size); | ||||
|     _data = _platform.allocMemory(size); | ||||
|     if (!_data) | ||||
|         return false; | ||||
| 
 | ||||
|  | ||||
| @ -1,11 +1,12 @@ | ||||
| #pragma once | ||||
| 
 | ||||
| #include "interface_object.h" | ||||
| #include "platform.h" | ||||
| 
 | ||||
| class TableObject: public InterfaceObject | ||||
| { | ||||
| public: | ||||
|     TableObject(uint8_t* memoryReference); | ||||
|     TableObject(Platform& platform); | ||||
|     virtual void readProperty(PropertyID id, uint32_t start, uint32_t count, uint8_t* data); | ||||
|     virtual void writeProperty(PropertyID id, uint8_t start, uint8_t* data, uint8_t count); | ||||
|     virtual uint8_t propertySize(PropertyID id); | ||||
| @ -29,5 +30,5 @@ private: | ||||
|     void additionalLoadControls(uint8_t* data); | ||||
|     void loadState(LoadState newState); | ||||
|     LoadState _state = LS_UNLOADED; | ||||
|     uint8_t* _memoryReference; | ||||
|     Platform& _platform; | ||||
| }; | ||||
|  | ||||
| @ -1,13 +1,16 @@ | ||||
| #include "linux_platform.h" | ||||
| #ifdef __linux__ | ||||
| #include <stdio.h> | ||||
| #include <cstdio> | ||||
| #include <string> | ||||
| #include <string.h> | ||||
| #include <cstring> | ||||
| #include <cstdlib> | ||||
| #include <stdexcept> | ||||
| #include <cmath> | ||||
| 
 | ||||
| #include <unistd.h> | ||||
| #include <sys/types.h> | ||||
| #include <sys/stat.h> | ||||
| #include <sys/mman.h> | ||||
| #include <math.h> | ||||
| #include <fcntl.h> | ||||
| #include <sys/socket.h> | ||||
| #include <netinet/in.h> | ||||
| @ -23,9 +26,13 @@ | ||||
| #include "knx/application_program_object.h" | ||||
| #include "knx/ip_parameter_object.h" | ||||
| 
 | ||||
| #define MAX_MEM 4096 | ||||
| 
 | ||||
| LinuxPlatform::LinuxPlatform() | ||||
| { | ||||
|     doMemoryMapping(); | ||||
|     Platform::_memoryReference = (uint8_t*)malloc(MAX_MEM); | ||||
|     _currentMaxMem = Platform::_memoryReference; | ||||
| } | ||||
| 
 | ||||
| uint32_t LinuxPlatform::currentIpAddress() | ||||
| @ -72,7 +79,13 @@ void LinuxPlatform::macAddress(uint8_t* data) | ||||
| 
 | ||||
| void LinuxPlatform::restart() | ||||
| { | ||||
|     // do nothing
 | ||||
|     // clear alocated memory
 | ||||
|     if(_memoryReference != 0) | ||||
|     { | ||||
|         free(_memoryReference); | ||||
|         Platform::_memoryReference = (uint8_t*)malloc(MAX_MEM); | ||||
|         _currentMaxMem = Platform::_memoryReference; | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| void LinuxPlatform::fatalError() | ||||
| @ -276,4 +289,23 @@ void LinuxPlatform::closeUart() | ||||
| void LinuxPlatform::setupUart() | ||||
| { | ||||
| } | ||||
| #endif | ||||
| 
 | ||||
| /*
 | ||||
|  * On linux the memory addresses from malloc may be to big for usermermory_write. | ||||
|  * So we allocate some memory at the beginning and use it for address table, group object table etc. | ||||
|  * | ||||
|  **/ | ||||
| uint8_t* LinuxPlatform::allocMemory(size_t size) | ||||
| { | ||||
|     uint8_t* addr = _currentMaxMem; | ||||
|     _currentMaxMem += size; | ||||
|     if ((_currentMaxMem - Platform::_memoryReference) > MAX_MEM) | ||||
|         throw std::overflow_error("MAX_MEM was to small"); | ||||
|     return addr; | ||||
| } | ||||
| #endif | ||||
| 
 | ||||
| void LinuxPlatform::freeMemory(uint8_t* ptr) | ||||
| { | ||||
|     /* do nothing. Memory is freed on restart()*/ | ||||
| } | ||||
|  | ||||
| @ -6,6 +6,7 @@ | ||||
| 
 | ||||
| class LinuxPlatform: public Platform | ||||
| { | ||||
|     using Platform::_memoryReference; | ||||
| public: | ||||
|     LinuxPlatform(); | ||||
| 
 | ||||
| @ -39,6 +40,8 @@ public: | ||||
|     //memory
 | ||||
|     uint8_t* getEepromBuffer(uint16_t size); | ||||
|     void commitToEeprom(); | ||||
|     uint8_t* allocMemory(size_t size); | ||||
|     void freeMemory(uint8_t* ptr); | ||||
| private: | ||||
|     uint32_t _multicastAddr; | ||||
|     uint16_t _port; | ||||
| @ -46,6 +49,7 @@ private: | ||||
|     void doMemoryMapping(); | ||||
|     uint8_t* _mappedFile; | ||||
|     int _fd; | ||||
|     uint8_t* _currentMaxMem = 0; | ||||
| }; | ||||
| 
 | ||||
| #endif | ||||
| @ -153,5 +153,4 @@ size_t SamdPlatform::readBytesUart(uint8_t *buffer, size_t length) | ||||
|     //printHex("p>", buffer, length);
 | ||||
|     return length; | ||||
| } | ||||
| 
 | ||||
| #endif | ||||
		Loading…
	
		Reference in New Issue
	
	Block a user