mirror of
				https://github.com/thelsing/knx.git
				synced 2025-10-26 10:26:25 +01:00 
			
		
		
		
	reimplement dpt1 and dpt9
This commit is contained in:
		
							parent
							
								
									d1bdc6ef51
								
							
						
					
					
						commit
						60b414bab2
					
				@ -71,10 +71,13 @@ set(${PROJECT_NAME}_SOURCES
 | 
			
		||||
    ../../src/knx/interface_object/data_property.h
 | 
			
		||||
    ../../src/knx/interface_object/device_object.cpp
 | 
			
		||||
    ../../src/knx/interface_object/device_object.h
 | 
			
		||||
    ../../src/knx/group_object/dpt.cpp
 | 
			
		||||
    ../../src/knx/group_object/dpt.h
 | 
			
		||||
    ../../src/knx/group_object/dptconvert.cpp
 | 
			
		||||
    ../../src/knx/group_object/dptconvert.h
 | 
			
		||||
    ../../src/knx/group_object/dpt/dpt.cpp
 | 
			
		||||
    ../../src/knx/group_object/dpt/dpt.h
 | 
			
		||||
    ../../src/knx/group_object/dpt/dptconvert.cpp
 | 
			
		||||
    ../../src/knx/group_object/dpt/dptconvert.h
 | 
			
		||||
    ../../src/knx/group_object/dpt/dpt1.cpp
 | 
			
		||||
    ../../src/knx/group_object/dpt/dpt1.h
 | 
			
		||||
    ../../src/knx/group_object/dpt/dpts.h
 | 
			
		||||
    ../../src/knx/interface_object/function_property.h
 | 
			
		||||
    ../../src/knx/group_object/group_object.cpp
 | 
			
		||||
    ../../src/knx/group_object/group_object.h
 | 
			
		||||
 | 
			
		||||
@ -40,25 +40,25 @@ void measureTemp()
 | 
			
		||||
    currentValue *= 100 * 100;
 | 
			
		||||
 | 
			
		||||
    // write new value to groupobject
 | 
			
		||||
    goCurrent.value(currentValue);
 | 
			
		||||
    goCurrent.value<Dpt9>(currentValue);
 | 
			
		||||
 | 
			
		||||
    if (currentValue > maxValue)
 | 
			
		||||
    {
 | 
			
		||||
        maxValue = currentValue;
 | 
			
		||||
        goMax.value(maxValue);
 | 
			
		||||
        goMax.value<Dpt9>(maxValue);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    if (currentValue < minValue)
 | 
			
		||||
    {
 | 
			
		||||
        minValue = currentValue;
 | 
			
		||||
        goMin.value(minValue);
 | 
			
		||||
        goMin.value<Dpt9>(minValue);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// callback from reset-GO
 | 
			
		||||
void handler(GroupObject& go)
 | 
			
		||||
{
 | 
			
		||||
    if (go == goReset && go.value())
 | 
			
		||||
    if (go == goReset && go.value<Dpt1>())
 | 
			
		||||
    {
 | 
			
		||||
        maxValue = 0;
 | 
			
		||||
        minValue = 10000;
 | 
			
		||||
@ -86,11 +86,6 @@ void setup()
 | 
			
		||||
    // print values of parameters if device is already configured
 | 
			
		||||
    if (knx.configured())
 | 
			
		||||
    {
 | 
			
		||||
        goReset.dataPointType(DPT_Trigger);
 | 
			
		||||
        goCurrent.dataPointType(DPT_Value_Temp);
 | 
			
		||||
        goMin.dataPointType(DPT_Value_Temp);
 | 
			
		||||
        goMax.dataPointType(DPT_Value_Temp);
 | 
			
		||||
 | 
			
		||||
        Serial.print("Startverzögerung s: ");
 | 
			
		||||
        Serial.println(knx.paramByte(0));
 | 
			
		||||
        Serial.print("Aenderung senden (*0.1K): ");
 | 
			
		||||
 | 
			
		||||
@ -6,6 +6,8 @@
 | 
			
		||||
 | 
			
		||||
#include "knx/interface_object/group_object_table_object.h"
 | 
			
		||||
#include "knx/bits.h"
 | 
			
		||||
#include "knx/group_object/dpt/dpts.h"
 | 
			
		||||
 | 
			
		||||
#include <time.h>
 | 
			
		||||
#include <stdlib.h>
 | 
			
		||||
#include <stdio.h>
 | 
			
		||||
@ -61,28 +63,28 @@ void measureTemp()
 | 
			
		||||
 | 
			
		||||
    lastsend = now;
 | 
			
		||||
    int r = rand();
 | 
			
		||||
    double currentValue = (r * 1.0) / (RAND_MAX * 1.0);
 | 
			
		||||
    float currentValue = (r * 1.0f) / (RAND_MAX * 1.0f);
 | 
			
		||||
    currentValue *= 100;
 | 
			
		||||
    currentValue -= 50;
 | 
			
		||||
    //    currentValue *= (670433.28 + 273);
 | 
			
		||||
    //    currentValue -= 273;
 | 
			
		||||
    LOGGER.info("current value: %f",currentValue);
 | 
			
		||||
    GO_CURR.value(currentValue);
 | 
			
		||||
    GO_CURR.value<Dpt9>(currentValue);
 | 
			
		||||
 | 
			
		||||
    double max = GO_MAX.value();
 | 
			
		||||
    float max = GO_MAX.value<Dpt9>();
 | 
			
		||||
    if (currentValue > max)
 | 
			
		||||
        GO_MAX.value(currentValue);
 | 
			
		||||
        GO_MAX.value<Dpt9>(currentValue);
 | 
			
		||||
 | 
			
		||||
    if (currentValue < (double)GO_MIN.value())
 | 
			
		||||
        GO_MIN.value(currentValue);
 | 
			
		||||
    if (currentValue < GO_MIN.value<Dpt9>())
 | 
			
		||||
        GO_MIN.value<Dpt9>(currentValue);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void handler(GroupObject& go)
 | 
			
		||||
{
 | 
			
		||||
    if (go == GO_RESET && go.value())
 | 
			
		||||
    if (go == GO_RESET && go.value<Dpt1>())
 | 
			
		||||
    {
 | 
			
		||||
        GO_MAX.valueNoSend(-273.0);
 | 
			
		||||
        GO_MIN.valueNoSend(670433.28);
 | 
			
		||||
        GO_MAX.valueNoSend<Dpt9>(-273.0f);
 | 
			
		||||
        GO_MIN.valueNoSend<Dpt9>(670433.28f);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@ -110,12 +112,8 @@ void setup()
 | 
			
		||||
 | 
			
		||||
    if (knx.configured())
 | 
			
		||||
    {
 | 
			
		||||
        GO_CURR.dataPointType(Dpt(9, 1));
 | 
			
		||||
        GO_MIN.dataPointType(Dpt(9, 1));
 | 
			
		||||
        GO_MIN.value(670433.28);
 | 
			
		||||
        GO_MAX.dataPointType(Dpt(9, 1));
 | 
			
		||||
        GO_MAX.valueNoSend(-273.0);
 | 
			
		||||
        GO_RESET.dataPointType(Dpt(1, 15));
 | 
			
		||||
        GO_MIN.value<Dpt9>(670433.28f);
 | 
			
		||||
        GO_MAX.valueNoSend<Dpt9>(-273.0f);
 | 
			
		||||
        LOGGER.info("Startverzögerung s: %d", knx.paramByte(0));
 | 
			
		||||
        LOGGER.info("Aenderung senden (*0.1K): %d", knx.paramByte(1));
 | 
			
		||||
        LOGGER.info("Zykl. senden min: %d", knx.paramByte(2));
 | 
			
		||||
 | 
			
		||||
@ -85,8 +85,6 @@ void setup(void)
 | 
			
		||||
        cyclSend = knx.paramInt(0);
 | 
			
		||||
        Serial1.print("Zykl. send:");
 | 
			
		||||
        Serial1.println(cyclSend);
 | 
			
		||||
        goTemperature.dataPointType(Dpt(9, 1));
 | 
			
		||||
        goHumidity.dataPointType(Dpt(9, 1));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // start the framework.
 | 
			
		||||
@ -123,8 +121,8 @@ void loop(void)
 | 
			
		||||
    {
 | 
			
		||||
        sendCounter = 0;
 | 
			
		||||
 | 
			
		||||
        goTemperature.value(temp);
 | 
			
		||||
        goHumidity.value(humi);
 | 
			
		||||
        goTemperature.value<Dpt9>(temp);
 | 
			
		||||
        goHumidity.value<Dpt9>(humi);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@ -38,12 +38,15 @@ set(SOURCES
 | 
			
		||||
./knx/data_secure/secure_application_layer.h
 | 
			
		||||
./knx/data_secure/security_interface_object.cpp
 | 
			
		||||
./knx/data_secure/security_interface_object.h
 | 
			
		||||
./knx/group_object/datapoint_types.cpp
 | 
			
		||||
./knx/group_object/datapoint_types.h
 | 
			
		||||
./knx/group_object/dpt.cpp
 | 
			
		||||
./knx/group_object/dpt.h
 | 
			
		||||
./knx/group_object/dptconvert.cpp
 | 
			
		||||
./knx/group_object/dptconvert.h
 | 
			
		||||
./knx/group_object/dpt/dpts.h
 | 
			
		||||
./knx/group_object/dpt/dpt.cpp
 | 
			
		||||
./knx/group_object/dpt/dpt.h
 | 
			
		||||
./knx/group_object/dpt/dpt1.cpp
 | 
			
		||||
./knx/group_object/dpt/dpt1.h
 | 
			
		||||
./knx/group_object/dpt/dpt9.cpp
 | 
			
		||||
./knx/group_object/dpt/dpt9.h
 | 
			
		||||
./knx/group_object/dpt/dptconvert.cpp
 | 
			
		||||
./knx/group_object/dpt/dptconvert.h
 | 
			
		||||
./knx/group_object/group_object.cpp
 | 
			
		||||
./knx/group_object/group_object.h
 | 
			
		||||
./knx/group_object/knx_value.cpp
 | 
			
		||||
 | 
			
		||||
@ -246,4 +246,5 @@ knx-->Platform
 | 
			
		||||
 | 
			
		||||
 */
 | 
			
		||||
#include "knx/knx_facade.h"
 | 
			
		||||
#include "knx/group_object/dpt/dpts.h"
 | 
			
		||||
using namespace Knx;
 | 
			
		||||
@ -1,68 +0,0 @@
 | 
			
		||||
/*
 | 
			
		||||
 *  datapoint_types.h - Conversion functions for datapoint types.
 | 
			
		||||
 *
 | 
			
		||||
 *  Copyright (c) 2014 Stefan Taferner <stefan.taferner@gmx.at>
 | 
			
		||||
 *
 | 
			
		||||
 *  This program is free software; you can redistribute it and/or modify
 | 
			
		||||
 *  it under the terms of the GNU General Public License version 3 as
 | 
			
		||||
 *  published by the Free Software Foundation.
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include "datapoint_types.h"
 | 
			
		||||
 | 
			
		||||
#include <stdint.h>
 | 
			
		||||
 | 
			
		||||
namespace Knx
 | 
			
		||||
{
 | 
			
		||||
    // Sign for a negative DPT9 float value
 | 
			
		||||
#define DPT_FLOAT_NEG_SIGN 0x8000
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    uint16_t dptToFloat(int32_t value)
 | 
			
		||||
    {
 | 
			
		||||
        uint16_t exp = 0;
 | 
			
		||||
 | 
			
		||||
        if (value < -67108864 || value > 67076096)
 | 
			
		||||
            return 0x7fff;
 | 
			
		||||
 | 
			
		||||
        if (value < 0)
 | 
			
		||||
        {
 | 
			
		||||
            while (value < -2048)
 | 
			
		||||
            {
 | 
			
		||||
                value >>= 1;
 | 
			
		||||
                ++exp;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            return DPT_FLOAT_NEG_SIGN | (((int32_t) value) & 2047) | (exp << 11);
 | 
			
		||||
        }
 | 
			
		||||
        else
 | 
			
		||||
        {
 | 
			
		||||
            while (value > 2047)
 | 
			
		||||
            {
 | 
			
		||||
                value >>= 1;
 | 
			
		||||
                ++exp;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            return value | (exp << 11);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    int32_t dptFromFloat(uint16_t dptValue)
 | 
			
		||||
    {
 | 
			
		||||
        uint16_t exp = (dptValue >> 11) & 15;
 | 
			
		||||
        int32_t value;
 | 
			
		||||
 | 
			
		||||
        if (dptValue == 0x7fff)
 | 
			
		||||
            return INVALID_DPT_FLOAT;
 | 
			
		||||
 | 
			
		||||
        if (dptValue >= 0x8000)
 | 
			
		||||
            value = dptValue | (-1L & ~2047);
 | 
			
		||||
        else
 | 
			
		||||
            value = dptValue & 2047;
 | 
			
		||||
 | 
			
		||||
        for (; exp; --exp)
 | 
			
		||||
            value <<= 1;
 | 
			
		||||
 | 
			
		||||
        return value;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@ -1,41 +0,0 @@
 | 
			
		||||
/*
 | 
			
		||||
 *  datapoint_types.h - Conversion functions for datapoint types.
 | 
			
		||||
 *
 | 
			
		||||
 *  Copyright (c) 2014 Stefan Taferner <stefan.taferner@gmx.at>
 | 
			
		||||
 *
 | 
			
		||||
 *  This program is free software; you can redistribute it and/or modify
 | 
			
		||||
 *  it under the terms of the GNU General Public License version 3 as
 | 
			
		||||
 *  published by the Free Software Foundation.
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#pragma once
 | 
			
		||||
#include <stdint.h>
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
namespace Knx
 | 
			
		||||
{
 | 
			
		||||
    /**
 | 
			
		||||
     * An invalid 2 uint8_t float (DPT9/EIS5).
 | 
			
		||||
     * To be used for dptToFloat() and dptFromFloat().
 | 
			
		||||
     */
 | 
			
		||||
#define INVALID_DPT_FLOAT  2147483647U
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Convert a value from uint32_t to 2 uint8_t float (DPT9/EIS5). The possible range
 | 
			
		||||
     * of the values is -67108864 to 67076096.
 | 
			
		||||
     *
 | 
			
		||||
     * @param value - the value to convert.
 | 
			
		||||
     *                Use INVALID_DPT_FLOAT for the DPT9 "invalid data" value.
 | 
			
		||||
     * @return The 2 uint8_t float (DPT9/EIS5).
 | 
			
		||||
     */
 | 
			
		||||
    uint16_t dptToFloat(int32_t value);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Convert a value from 2 uint8_t float (DPT9/EIS5) to integer.
 | 
			
		||||
     *
 | 
			
		||||
     * @param dptValue - the 2 uint8_t float (DPT9/EIS5) to convert
 | 
			
		||||
     * @return The value as integer, or INVALID_DPT_FLOAT for the
 | 
			
		||||
     *         DPT9 "invalid data" value.
 | 
			
		||||
     */
 | 
			
		||||
    int32_t dptFromFloat(uint16_t dptValue);
 | 
			
		||||
}
 | 
			
		||||
@ -1,7 +1,7 @@
 | 
			
		||||
#include "dpt.h"
 | 
			
		||||
 | 
			
		||||
#include "../util/logger.h"
 | 
			
		||||
#include "../bits.h"
 | 
			
		||||
#include "../../util/logger.h"
 | 
			
		||||
#include "../../bits.h"
 | 
			
		||||
 | 
			
		||||
#define LOGGER Logger::logger("Dpt")
 | 
			
		||||
 | 
			
		||||
@ -16,14 +16,4 @@ namespace Knx
 | 
			
		||||
        if (subGroup == 0)
 | 
			
		||||
            println("WARNING: You used and invalid Dpt *.0");
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    bool Dpt::operator==(const Dpt& other) const
 | 
			
		||||
    {
 | 
			
		||||
        return other.mainGroup == mainGroup && other.subGroup == subGroup && other.index == index;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    bool Dpt::operator!=(const Dpt& other) const
 | 
			
		||||
    {
 | 
			
		||||
        return !(other == *this);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@ -1,5 +1,6 @@
 | 
			
		||||
#pragma once
 | 
			
		||||
 | 
			
		||||
#include "../group_object.h"
 | 
			
		||||
namespace Knx
 | 
			
		||||
{
 | 
			
		||||
#define DPT_Switch Dpt(1, 1)
 | 
			
		||||
@ -367,12 +368,14 @@ namespace Knx
 | 
			
		||||
        public:
 | 
			
		||||
            Dpt();
 | 
			
		||||
            Dpt(short mainGroup, short subGroup, short index = 0);
 | 
			
		||||
            virtual ~Dpt() {}
 | 
			
		||||
            unsigned short mainGroup;
 | 
			
		||||
            unsigned short subGroup;
 | 
			
		||||
            unsigned short index;
 | 
			
		||||
            bool operator==(const Dpt& other) const;
 | 
			
		||||
            bool operator!=(const Dpt& other) const;
 | 
			
		||||
 | 
			
		||||
             
 | 
			
		||||
            virtual Go_SizeCode size() const = 0;
 | 
			
		||||
 | 
			
		||||
            virtual void encode(uint8_t* data) const = 0;
 | 
			
		||||
            virtual void decode(uint8_t* data) = 0;
 | 
			
		||||
    };
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										44
									
								
								src/knx/group_object/dpt/dpt1.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										44
									
								
								src/knx/group_object/dpt/dpt1.cpp
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,44 @@
 | 
			
		||||
#include "dpt1.h"
 | 
			
		||||
 | 
			
		||||
#include "dptconvert.h"
 | 
			
		||||
 | 
			
		||||
Knx::Dpt1::Dpt1() {}
 | 
			
		||||
 | 
			
		||||
Knx::Dpt1::Dpt1(bool value) : _value(value) {}
 | 
			
		||||
 | 
			
		||||
Knx::Go_SizeCode Knx::Dpt1::size() const
 | 
			
		||||
{
 | 
			
		||||
    return Go_1_Bit;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Knx::Dpt1::encode(uint8_t* data) const
 | 
			
		||||
{
 | 
			
		||||
    bitToPayload(data, 7, _value);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Knx::Dpt1::decode(uint8_t* data)
 | 
			
		||||
{
 | 
			
		||||
    _value = bitFromPayload(data, 7);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Knx::Dpt1::value(bool value)
 | 
			
		||||
{
 | 
			
		||||
    _value = value;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
bool Knx::Dpt1::value()
 | 
			
		||||
{
 | 
			
		||||
    return _value;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
Knx::Dpt1::operator bool() const
 | 
			
		||||
{
 | 
			
		||||
    return _value;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
Knx::Dpt1& Knx::Dpt1::operator=(const bool value)
 | 
			
		||||
{
 | 
			
		||||
    _value = value;
 | 
			
		||||
    return *this;
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										22
									
								
								src/knx/group_object/dpt/dpt1.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										22
									
								
								src/knx/group_object/dpt/dpt1.h
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,22 @@
 | 
			
		||||
#pragma once
 | 
			
		||||
#include "dpt.h"
 | 
			
		||||
namespace Knx
 | 
			
		||||
{
 | 
			
		||||
    class Dpt1: public Dpt
 | 
			
		||||
    {
 | 
			
		||||
        public:
 | 
			
		||||
            Dpt1();
 | 
			
		||||
            Dpt1(bool value);
 | 
			
		||||
            Go_SizeCode size() const override;
 | 
			
		||||
 | 
			
		||||
            virtual void encode(uint8_t* data) const override;
 | 
			
		||||
            virtual void decode(uint8_t* data) override;
 | 
			
		||||
 | 
			
		||||
            void value(bool value);
 | 
			
		||||
            bool value();
 | 
			
		||||
            operator bool() const;
 | 
			
		||||
            Dpt1& operator=(const bool value);
 | 
			
		||||
        private:
 | 
			
		||||
            bool _value;
 | 
			
		||||
    };
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										47
									
								
								src/knx/group_object/dpt/dpt9.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										47
									
								
								src/knx/group_object/dpt/dpt9.cpp
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,47 @@
 | 
			
		||||
#include "dpt9.h"
 | 
			
		||||
 | 
			
		||||
#include "dptconvert.h"
 | 
			
		||||
 | 
			
		||||
Knx::Dpt9::Dpt9() {}
 | 
			
		||||
 | 
			
		||||
Knx::Dpt9::Dpt9(float value) : _value(value) {}
 | 
			
		||||
 | 
			
		||||
Knx::Go_SizeCode Knx::Dpt9::size() const
 | 
			
		||||
{
 | 
			
		||||
    return Go_1_Bit;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Knx::Dpt9::encode(uint8_t* data) const
 | 
			
		||||
{
 | 
			
		||||
    float16ToPayload(data, 0, _value, 0xFFFF);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Knx::Dpt9::decode(uint8_t* data)
 | 
			
		||||
{
 | 
			
		||||
    if (unsigned16FromPayload(data, 0) == 0x7FFF)
 | 
			
		||||
        return;
 | 
			
		||||
 | 
			
		||||
    _value = float16FromPayload(data, 0);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void Knx::Dpt9::value(float value)
 | 
			
		||||
{
 | 
			
		||||
    _value = value;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
bool Knx::Dpt9::value()
 | 
			
		||||
{
 | 
			
		||||
    return _value;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
Knx::Dpt9::operator float() const
 | 
			
		||||
{
 | 
			
		||||
    return _value;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
Knx::Dpt9& Knx::Dpt9::operator=(const float value)
 | 
			
		||||
{
 | 
			
		||||
    _value = value;
 | 
			
		||||
    return *this;
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										22
									
								
								src/knx/group_object/dpt/dpt9.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										22
									
								
								src/knx/group_object/dpt/dpt9.h
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,22 @@
 | 
			
		||||
#pragma once
 | 
			
		||||
#include "dpt.h"
 | 
			
		||||
namespace Knx
 | 
			
		||||
{
 | 
			
		||||
    class Dpt9: public Dpt
 | 
			
		||||
    {
 | 
			
		||||
        public:
 | 
			
		||||
            Dpt9();
 | 
			
		||||
            Dpt9(float value);
 | 
			
		||||
            Go_SizeCode size() const override;
 | 
			
		||||
 | 
			
		||||
            virtual void encode(uint8_t* data) const override;
 | 
			
		||||
            virtual void decode(uint8_t* data) override;
 | 
			
		||||
 | 
			
		||||
            void value(float value);
 | 
			
		||||
            bool value();
 | 
			
		||||
            operator float() const;
 | 
			
		||||
            Dpt9& operator=(const float value);
 | 
			
		||||
        private:
 | 
			
		||||
            float _value;
 | 
			
		||||
    };
 | 
			
		||||
}
 | 
			
		||||
@ -1,6 +1,6 @@
 | 
			
		||||
#include "dptconvert.h"
 | 
			
		||||
 | 
			
		||||
#include "../bits.h"
 | 
			
		||||
#include "../../bits.h"
 | 
			
		||||
 | 
			
		||||
#include <cmath>
 | 
			
		||||
#include <cstdlib>
 | 
			
		||||
@ -18,11 +18,7 @@ namespace Knx
 | 
			
		||||
    {
 | 
			
		||||
        if (payload_length > 0)
 | 
			
		||||
        {
 | 
			
		||||
            // DPT 1.* - Binary
 | 
			
		||||
            if (datatype.mainGroup == 1 && datatype.subGroup >= 1 && datatype.subGroup <= 23 && datatype.subGroup != 20 && !datatype.index)
 | 
			
		||||
            {
 | 
			
		||||
                return busValueToBinary(payload, payload_length, datatype, value);
 | 
			
		||||
            } // DPT 2.* - Binary Control
 | 
			
		||||
             // DPT 2.* - Binary Control
 | 
			
		||||
 | 
			
		||||
            if (datatype.mainGroup == 2 && datatype.subGroup >= 1 && datatype.subGroup <= 12 && datatype.index <= 1)
 | 
			
		||||
                return busValueToBinaryControl(payload, payload_length, datatype, value);
 | 
			
		||||
@ -63,10 +59,6 @@ namespace Knx
 | 
			
		||||
            if (datatype.mainGroup == 8 && datatype.subGroup >= 2 && datatype.subGroup <= 7 && !datatype.index)
 | 
			
		||||
                return busValueToTimeDelta(payload, payload_length, datatype, value);
 | 
			
		||||
 | 
			
		||||
            // DPT 9.* - 16 Bit Float
 | 
			
		||||
            if (datatype.mainGroup == 9 && ((datatype.subGroup >= 1 && datatype.subGroup <= 11) || (datatype.subGroup >= 20 && datatype.subGroup <= 29)) && !datatype.index)
 | 
			
		||||
                return busValueToFloat16(payload, payload_length, datatype, value);
 | 
			
		||||
 | 
			
		||||
            // DPT 10.* - Time and Weekday
 | 
			
		||||
            if (datatype.mainGroup == 10 && datatype.subGroup == 1 && datatype.index <= 1)
 | 
			
		||||
                return busValueToTime(payload, payload_length, datatype, value);
 | 
			
		||||
@ -181,8 +173,6 @@ namespace Knx
 | 
			
		||||
 | 
			
		||||
    int KNX_Encode_Value(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype)
 | 
			
		||||
    {
 | 
			
		||||
        if (datatype.mainGroup == 1 && datatype.subGroup >= 1 && datatype.subGroup <= 23 && datatype.subGroup != 20 && !datatype.index)
 | 
			
		||||
            return valueToBusValueBinary(value, payload, payload_length, datatype);
 | 
			
		||||
 | 
			
		||||
        // DPT 2.* - Binary Control
 | 
			
		||||
        if (datatype.mainGroup == 2 && datatype.subGroup >= 1 && datatype.subGroup <= 12 && datatype.index <= 1)
 | 
			
		||||
@ -224,10 +214,6 @@ namespace Knx
 | 
			
		||||
        if (datatype.mainGroup == 8 && datatype.subGroup >= 2 && datatype.subGroup <= 7 && !datatype.index)
 | 
			
		||||
            return valueToBusValueTimeDelta(value, payload, payload_length, datatype);
 | 
			
		||||
 | 
			
		||||
        // DPT 9.* - 16 Bit Float
 | 
			
		||||
        if (datatype.mainGroup == 9 && ((datatype.subGroup >= 1 && datatype.subGroup <= 11 ) || (datatype.subGroup >= 20 && datatype.subGroup <= 29)) && !datatype.index)
 | 
			
		||||
            return valueToBusValueFloat16(value, payload, payload_length, datatype);
 | 
			
		||||
 | 
			
		||||
        // DPT 10.* - Time and Weekday
 | 
			
		||||
        if (datatype.mainGroup == 10 && datatype.subGroup == 1 && datatype.index <= 1)
 | 
			
		||||
            return valueToBusValueTime(value, payload, payload_length, datatype);
 | 
			
		||||
@ -339,13 +325,6 @@ namespace Knx
 | 
			
		||||
        return false;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    int busValueToBinary(const uint8_t* payload, size_t payload_length, const Dpt& datatype, KNXValue& value)
 | 
			
		||||
    {
 | 
			
		||||
        ASSERT_PAYLOAD(1);
 | 
			
		||||
        value = bitFromPayload(payload, 7);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    int busValueToBinaryControl(const uint8_t* payload, size_t payload_length, const Dpt& datatype, KNXValue& value)
 | 
			
		||||
    {
 | 
			
		||||
        ASSERT_PAYLOAD(1);
 | 
			
		||||
@ -496,16 +475,6 @@ namespace Knx
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    int busValueToFloat16(const uint8_t* payload, size_t payload_length, const Dpt& datatype, KNXValue& value)
 | 
			
		||||
    {
 | 
			
		||||
        ASSERT_PAYLOAD(2);
 | 
			
		||||
 | 
			
		||||
        if (unsigned16FromPayload(payload, 0) == 0x7FFF)
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        value = float16FromPayload(payload, 0);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    int busValueToTime(const uint8_t* payload, size_t payload_length, const Dpt& datatype, KNXValue& value)
 | 
			
		||||
    {
 | 
			
		||||
@ -1019,22 +988,16 @@ namespace Knx
 | 
			
		||||
 | 
			
		||||
    //-------------------------------------------------------------------------------------------------------------------------------------
 | 
			
		||||
 | 
			
		||||
    int valueToBusValueBinary(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype)
 | 
			
		||||
    {
 | 
			
		||||
        bitToPayload(payload, payload_length, 7, value);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    int valueToBusValueBinaryControl(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype)
 | 
			
		||||
    {
 | 
			
		||||
        switch (datatype.index)
 | 
			
		||||
        {
 | 
			
		||||
            case 0:
 | 
			
		||||
                bitToPayload(payload, payload_length, 6, value);
 | 
			
		||||
                bitToPayload(payload, 6, value);
 | 
			
		||||
                break;
 | 
			
		||||
 | 
			
		||||
            case 1:
 | 
			
		||||
                bitToPayload(payload, payload_length, 7, value);
 | 
			
		||||
                bitToPayload(payload, 7, value);
 | 
			
		||||
                break;
 | 
			
		||||
 | 
			
		||||
            default:
 | 
			
		||||
@ -1049,7 +1012,7 @@ namespace Knx
 | 
			
		||||
        switch (datatype.index)
 | 
			
		||||
        {
 | 
			
		||||
            case 0:
 | 
			
		||||
                bitToPayload(payload, payload_length, 4, value);
 | 
			
		||||
                bitToPayload(payload, 4, value);
 | 
			
		||||
                break;
 | 
			
		||||
 | 
			
		||||
            case 1:
 | 
			
		||||
@ -1057,7 +1020,7 @@ namespace Knx
 | 
			
		||||
                if ((int64_t)value < INT64_C(0) || (int64_t)value > INT64_C(7))
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 0, (uint64_t)value, 0x07);
 | 
			
		||||
                unsigned8ToPayload(payload, 0, (uint64_t)value, 0x07);
 | 
			
		||||
            }
 | 
			
		||||
            break;
 | 
			
		||||
 | 
			
		||||
@ -1073,7 +1036,7 @@ namespace Knx
 | 
			
		||||
        if ((uint64_t)value > INT64_C(255) || (datatype.subGroup == 1 && (uint64_t)value > INT64_C(127)))
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        unsigned8ToPayload(payload, payload_length, 0, (uint64_t)value, 0xFF);
 | 
			
		||||
        unsigned8ToPayload(payload, 0, (uint64_t)value, 0xFF);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -1089,7 +1052,7 @@ namespace Knx
 | 
			
		||||
                if ((double)value > 100.0)
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 0, round((double)value * 255.0 / 100.0), 0xFF);
 | 
			
		||||
                unsigned8ToPayload(payload, 0, round((double)value * 255.0 / 100.0), 0xFF);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1098,7 +1061,7 @@ namespace Knx
 | 
			
		||||
                if ((double)value > 360.0)
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 0, round((double)value * 255.0 / 360.0), 0xFF);
 | 
			
		||||
                unsigned8ToPayload(payload, 0, round((double)value * 255.0 / 360.0), 0xFF);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1107,7 +1070,7 @@ namespace Knx
 | 
			
		||||
                if ((int64_t)value > INT64_C(254))
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 0, (uint64_t)value, 0xFF);
 | 
			
		||||
                unsigned8ToPayload(payload, 0, (uint64_t)value, 0xFF);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1116,7 +1079,7 @@ namespace Knx
 | 
			
		||||
                if ((int64_t)value > INT64_C(255))
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 0, (uint64_t)value, 0xFF);
 | 
			
		||||
                unsigned8ToPayload(payload, 0, (uint64_t)value, 0xFF);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
@ -1128,20 +1091,20 @@ namespace Knx
 | 
			
		||||
        if ((int64_t)value < INT64_C(-128) || (int64_t)value > INT64_C(127))
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        signed8ToPayload(payload, payload_length, 0, (uint64_t)value, 0xFF);
 | 
			
		||||
        signed8ToPayload(payload, 0, (uint64_t)value, 0xFF);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    int valueToBusValueStatusAndMode(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype)
 | 
			
		||||
    {
 | 
			
		||||
        if (datatype.index < 5)
 | 
			
		||||
            bitToPayload(payload, payload_length, datatype.index, value);
 | 
			
		||||
            bitToPayload(payload, datatype.index, value);
 | 
			
		||||
        else if (datatype.index == 5)
 | 
			
		||||
        {
 | 
			
		||||
            if ((int64_t)value < INT64_C(0) || (int64_t)value > INT64_C(7))
 | 
			
		||||
                return false;
 | 
			
		||||
 | 
			
		||||
            unsigned8ToPayload(payload, payload_length, 0, (uint64_t)value, 0x07);
 | 
			
		||||
            unsigned8ToPayload(payload, 0, (uint64_t)value, 0x07);
 | 
			
		||||
        }
 | 
			
		||||
        else
 | 
			
		||||
            return false;
 | 
			
		||||
@ -1154,7 +1117,7 @@ namespace Knx
 | 
			
		||||
        if ((int64_t)value < INT64_C(0) || (int64_t)value > INT64_C(65535))
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        unsigned16ToPayload(payload, payload_length, 0, (uint64_t)value, 0xFFFF);
 | 
			
		||||
        unsigned16ToPayload(payload, 0, (uint64_t)value, 0xFFFF);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -1166,7 +1129,7 @@ namespace Knx
 | 
			
		||||
        if (timeSinceEpoch < INT64_C(0) || timeSinceEpoch > INT64_C(65535))
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        unsigned16ToPayload(payload, payload_length, 0, timeSinceEpoch, 0xFFFF);
 | 
			
		||||
        unsigned16ToPayload(payload, 0, timeSinceEpoch, 0xFFFF);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -1180,10 +1143,10 @@ namespace Knx
 | 
			
		||||
            if ((double)value < -327.68 || (double)value > 327.67)
 | 
			
		||||
                return false;
 | 
			
		||||
 | 
			
		||||
            signed16ToPayload(payload, payload_length, 0, (int16_t)((double)value * 100.0), 0xFFFF);
 | 
			
		||||
            signed16ToPayload(payload, 0, (int16_t)((double)value * 100.0), 0xFFFF);
 | 
			
		||||
        }
 | 
			
		||||
        else
 | 
			
		||||
            signed16ToPayload(payload, payload_length, 0, (uint64_t)value, 0xffff);
 | 
			
		||||
            signed16ToPayload(payload, 0, (uint64_t)value, 0xffff);
 | 
			
		||||
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
@ -1196,66 +1159,11 @@ namespace Knx
 | 
			
		||||
        if (timeSinceEpoch < INT64_C(-32768) || timeSinceEpoch > INT64_C(32767))
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        signed16ToPayload(payload, payload_length, 0, timeSinceEpoch, 0xFFFF);
 | 
			
		||||
        signed16ToPayload(payload, 0, timeSinceEpoch, 0xFFFF);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    int valueToBusValueFloat16(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype)
 | 
			
		||||
    {
 | 
			
		||||
        double numValue = value;
 | 
			
		||||
 | 
			
		||||
        // bigger values like 670760.0 result in 0x7FFF which denotes invalid data.
 | 
			
		||||
        // I'm not sure if the GO shouldn't be updated to this value instead
 | 
			
		||||
        if (numValue > 670433.28)
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        if (numValue < -671088.64)
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        switch (datatype.subGroup)
 | 
			
		||||
        {
 | 
			
		||||
            case 1:
 | 
			
		||||
                if (numValue < -273.0)
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                break;
 | 
			
		||||
 | 
			
		||||
            case 2:
 | 
			
		||||
            case 3:
 | 
			
		||||
            case 10:
 | 
			
		||||
            case 11:
 | 
			
		||||
            case 20:
 | 
			
		||||
            case 21:
 | 
			
		||||
            case 22:
 | 
			
		||||
            case 23:
 | 
			
		||||
            case 24:
 | 
			
		||||
            case 25:
 | 
			
		||||
                if (numValue < -670760.0)
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                break;
 | 
			
		||||
 | 
			
		||||
            case 4:
 | 
			
		||||
            case 5:
 | 
			
		||||
            case 6:
 | 
			
		||||
            case 7:
 | 
			
		||||
            case 8:
 | 
			
		||||
            case 28:
 | 
			
		||||
                if (numValue < 0.0)
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                break;
 | 
			
		||||
 | 
			
		||||
            case 27:
 | 
			
		||||
                if (numValue < -459.6)
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                break;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        float16ToPayload(payload, payload_length, 0, numValue, 0xFFFF);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
   
 | 
			
		||||
 | 
			
		||||
    int valueToBusValueTime(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype)
 | 
			
		||||
    {
 | 
			
		||||
@ -1267,16 +1175,16 @@ namespace Knx
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                ENSURE_PAYLOAD(3);
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 0, (uint64_t)value << 5, 0xE0);
 | 
			
		||||
                unsigned8ToPayload(payload, 0, (uint64_t)value << 5, 0xE0);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            case 1:
 | 
			
		||||
            {
 | 
			
		||||
                struct tm tmp = value;
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 0, tmp.tm_hour, 0x1F);
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 1, tmp.tm_min, 0x3F);
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 2, tmp.tm_sec, 0x3F);
 | 
			
		||||
                unsigned8ToPayload(payload, 0, tmp.tm_hour, 0x1F);
 | 
			
		||||
                unsigned8ToPayload(payload, 1, tmp.tm_min, 0x3F);
 | 
			
		||||
                unsigned8ToPayload(payload, 2, tmp.tm_sec, 0x3F);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1294,9 +1202,9 @@ namespace Knx
 | 
			
		||||
        if (tmp.tm_year < 1990 || tmp.tm_year > 2089)
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        unsigned8ToPayload(payload, payload_length, 0, tmp.tm_mday, 0x1F);
 | 
			
		||||
        unsigned8ToPayload(payload, payload_length, 1, tmp.tm_mon, 0x0F);
 | 
			
		||||
        unsigned8ToPayload(payload, payload_length, 2, tmp.tm_year % 100, 0x7F);
 | 
			
		||||
        unsigned8ToPayload(payload, 0, tmp.tm_mday, 0x1F);
 | 
			
		||||
        unsigned8ToPayload(payload, 1, tmp.tm_mon, 0x0F);
 | 
			
		||||
        unsigned8ToPayload(payload, 2, tmp.tm_year % 100, 0x7F);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -1305,7 +1213,7 @@ namespace Knx
 | 
			
		||||
        if ((int64_t)value < INT64_C(0) || (int64_t)value > INT64_C(4294967295))
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        unsigned32ToPayload(payload, payload_length, 0, (uint64_t)value, 0xFFFFFFFF);
 | 
			
		||||
        unsigned32ToPayload(payload, 0, (uint64_t)value, 0xFFFFFFFF);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -1314,7 +1222,7 @@ namespace Knx
 | 
			
		||||
        if ((int64_t)value < INT64_C(-2147483648) || (int64_t)value > INT64_C(2147483647))
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        signed32ToPayload(payload, payload_length, 0, (uint64_t)value, 0xFFFFFFFF);
 | 
			
		||||
        signed32ToPayload(payload, 0, (uint64_t)value, 0xFFFFFFFF);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -1323,7 +1231,7 @@ namespace Knx
 | 
			
		||||
        if ((int64_t)value < INT64_C(-2147483648) || (int64_t)value > INT64_C(2147483647))
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        signed32ToPayload(payload, payload_length, 0, (uint64_t)value, 0xFFFFFFFF);
 | 
			
		||||
        signed32ToPayload(payload, 0, (uint64_t)value, 0xFFFFFFFF);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -1334,7 +1242,7 @@ namespace Knx
 | 
			
		||||
        if (numValue < (-8388608.0 * pow(2, 255)) || numValue > (8388607.0 * pow(2, 255)))
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        float32ToPayload(payload, payload_length, 0, numValue, 0xFFFFFFFF);
 | 
			
		||||
        float32ToPayload(payload, 0, numValue, 0xFFFFFFFF);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -1350,7 +1258,7 @@ namespace Knx
 | 
			
		||||
                ENSURE_PAYLOAD(4);
 | 
			
		||||
 | 
			
		||||
                for (int n = 0, factor = 100000; n < 6; ++n, factor /= 10)
 | 
			
		||||
                    bcdToPayload(payload, payload_length, n, ((uint64_t)value / factor) % 10);
 | 
			
		||||
                    bcdToPayload(payload, n, ((uint64_t)value / factor) % 10);
 | 
			
		||||
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
@ -1359,7 +1267,7 @@ namespace Knx
 | 
			
		||||
            case 2:
 | 
			
		||||
            case 3:
 | 
			
		||||
            case 4:
 | 
			
		||||
                bitToPayload(payload, payload_length, 23 + datatype.index, value);
 | 
			
		||||
                bitToPayload(payload, 23 + datatype.index, value);
 | 
			
		||||
                break;
 | 
			
		||||
 | 
			
		||||
            case 5:
 | 
			
		||||
@ -1367,7 +1275,7 @@ namespace Knx
 | 
			
		||||
                if ((uint64_t)value > INT64_C(15))
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                bcdToPayload(payload, payload_length, 7, (uint64_t)value);
 | 
			
		||||
                bcdToPayload(payload, 7, (uint64_t)value);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1388,7 +1296,7 @@ namespace Knx
 | 
			
		||||
            if (val)
 | 
			
		||||
                val = strValue[n]; //string terminator 0x00 will stop further assignments and init the remainig payload with zero
 | 
			
		||||
 | 
			
		||||
            unsigned8ToPayload(payload, payload_length, n, val, 0xff);
 | 
			
		||||
            unsigned8ToPayload(payload, n, val, 0xff);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return true;
 | 
			
		||||
@ -1399,7 +1307,7 @@ namespace Knx
 | 
			
		||||
        if ((int64_t)value < INT64_C(0) || (int64_t)value > INT64_C(63))
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        unsigned8ToPayload(payload, payload_length, 0, (uint64_t)value, 0xFF);
 | 
			
		||||
        unsigned8ToPayload(payload, 0, (uint64_t)value, 0xFF);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -1408,7 +1316,7 @@ namespace Knx
 | 
			
		||||
        switch (datatype.index)
 | 
			
		||||
        {
 | 
			
		||||
            case 0:
 | 
			
		||||
                bitToPayload(payload, payload_length, 0, value);
 | 
			
		||||
                bitToPayload(payload, 0, value);
 | 
			
		||||
                break;
 | 
			
		||||
 | 
			
		||||
            case 1:
 | 
			
		||||
@ -1416,7 +1324,7 @@ namespace Knx
 | 
			
		||||
                if ((int64_t)value < INT64_C(0) || (int64_t)value > INT64_C(63))
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 0, (int64_t)value, 0x3F);
 | 
			
		||||
                unsigned8ToPayload(payload, 0, (int64_t)value, 0x3F);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1432,7 +1340,7 @@ namespace Knx
 | 
			
		||||
        switch (datatype.index)
 | 
			
		||||
        {
 | 
			
		||||
            case 0:
 | 
			
		||||
                bitToPayload(payload, payload_length, 1, value);
 | 
			
		||||
                bitToPayload(payload, 1, value);
 | 
			
		||||
                break;
 | 
			
		||||
 | 
			
		||||
            case 1:
 | 
			
		||||
@ -1440,7 +1348,7 @@ namespace Knx
 | 
			
		||||
                if ((int64_t)value < INT64_C(0) || (int64_t)value > INT64_C(63))
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 0, (int64_t)value, 0x3F);
 | 
			
		||||
                unsigned8ToPayload(payload, 0, (int64_t)value, 0x3F);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1460,13 +1368,13 @@ namespace Knx
 | 
			
		||||
                if ((int64_t)value < INT64_C(0) || (int64_t)value > INT64_C(63))
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 0, (int64_t)value, 0x3F);
 | 
			
		||||
                unsigned8ToPayload(payload, 0, (int64_t)value, 0x3F);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            case 1:
 | 
			
		||||
            case 2:
 | 
			
		||||
                bitToPayload(payload, payload_length, 2 - datatype.index, value);
 | 
			
		||||
                bitToPayload(payload, 2 - datatype.index, value);
 | 
			
		||||
                break;
 | 
			
		||||
 | 
			
		||||
            default:
 | 
			
		||||
@ -1490,16 +1398,16 @@ namespace Knx
 | 
			
		||||
 | 
			
		||||
                ENSURE_PAYLOAD(8);
 | 
			
		||||
                struct tm tmp = value;
 | 
			
		||||
                bitToPayload(payload, payload_length, 51, false);
 | 
			
		||||
                bitToPayload(payload, payload_length, 52, false);
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 0, tmp.tm_year - 1900, 0xFF);
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 1, tmp.tm_mon, 0x0F);
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 2, tmp.tm_mday, 0x1F);
 | 
			
		||||
                bitToPayload(payload, 51, false);
 | 
			
		||||
                bitToPayload(payload, 52, false);
 | 
			
		||||
                unsigned8ToPayload(payload, 0, tmp.tm_year - 1900, 0xFF);
 | 
			
		||||
                unsigned8ToPayload(payload, 1, tmp.tm_mon, 0x0F);
 | 
			
		||||
                unsigned8ToPayload(payload, 2, tmp.tm_mday, 0x1F);
 | 
			
		||||
 | 
			
		||||
                bitToPayload(payload, payload_length, 54, false);
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 3, tmp.tm_hour, 0x1F);
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 4, tmp.tm_min, 0x3F);
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 5, tmp.tm_sec, 0x3F);
 | 
			
		||||
                bitToPayload(payload, 54, false);
 | 
			
		||||
                unsigned8ToPayload(payload, 3, tmp.tm_hour, 0x1F);
 | 
			
		||||
                unsigned8ToPayload(payload, 4, tmp.tm_min, 0x3F);
 | 
			
		||||
                unsigned8ToPayload(payload, 5, tmp.tm_sec, 0x3F);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1508,11 +1416,11 @@ namespace Knx
 | 
			
		||||
                ENSURE_PAYLOAD(8);
 | 
			
		||||
 | 
			
		||||
                if ((int64_t)value < INT64_C(0) || (int64_t)value > INT64_C(7))
 | 
			
		||||
                    bitToPayload(payload, payload_length, 53, true);
 | 
			
		||||
                    bitToPayload(payload, 53, true);
 | 
			
		||||
                else
 | 
			
		||||
                {
 | 
			
		||||
                    bitToPayload(payload, payload_length, 53, false);
 | 
			
		||||
                    unsigned8ToPayload(payload, payload_length, 3, (int64_t)value << 5, 0xE0);
 | 
			
		||||
                    bitToPayload(payload, 53, false);
 | 
			
		||||
                    unsigned8ToPayload(payload, 3, (int64_t)value << 5, 0xE0);
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
                break;
 | 
			
		||||
@ -1521,28 +1429,28 @@ namespace Knx
 | 
			
		||||
            case 2:
 | 
			
		||||
            {
 | 
			
		||||
                ENSURE_PAYLOAD(8);
 | 
			
		||||
                bitToPayload(payload, payload_length, 49, value);
 | 
			
		||||
                bitToPayload(payload, payload_length, 50, false);
 | 
			
		||||
                bitToPayload(payload, 49, value);
 | 
			
		||||
                bitToPayload(payload, 50, false);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            case 3:
 | 
			
		||||
            {
 | 
			
		||||
                ENSURE_PAYLOAD(8);
 | 
			
		||||
                bitToPayload(payload, payload_length, 48, value);
 | 
			
		||||
                bitToPayload(payload, 48, value);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            case 9:
 | 
			
		||||
            {
 | 
			
		||||
                ENSURE_PAYLOAD(8);
 | 
			
		||||
                bitToPayload(payload, payload_length, 55, value);
 | 
			
		||||
                bitToPayload(payload, 55, value);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            case 10:
 | 
			
		||||
            {
 | 
			
		||||
                bitToPayload(payload, payload_length, 56, value);
 | 
			
		||||
                bitToPayload(payload, 56, value);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1561,7 +1469,7 @@ namespace Knx
 | 
			
		||||
 | 
			
		||||
    int valueToBusValueSigned64(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype)
 | 
			
		||||
    {
 | 
			
		||||
        signed64ToPayload(payload, payload_length, 0, (int64_t)value, UINT64_C(0xFFFFFFFFFFFFFFFF));
 | 
			
		||||
        signed64ToPayload(payload, 0, (int64_t)value, UINT64_C(0xFFFFFFFFFFFFFFFF));
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -1575,7 +1483,7 @@ namespace Knx
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                ENSURE_PAYLOAD(6);
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 1, (int64_t)value, 0xFF);
 | 
			
		||||
                unsigned8ToPayload(payload, 1, (int64_t)value, 0xFF);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1587,7 +1495,7 @@ namespace Knx
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                ENSURE_PAYLOAD(6);
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, datatype.index, (int64_t)value, 0xFF);
 | 
			
		||||
                unsigned8ToPayload(payload, datatype.index, (int64_t)value, 0xFF);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1597,7 +1505,7 @@ namespace Knx
 | 
			
		||||
            case 7:
 | 
			
		||||
            {
 | 
			
		||||
                ENSURE_PAYLOAD(6);
 | 
			
		||||
                bitToPayload(payload, payload_length, 43 - datatype.index, value);
 | 
			
		||||
                bitToPayload(payload, 43 - datatype.index, value);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1606,7 +1514,7 @@ namespace Knx
 | 
			
		||||
            case 10:
 | 
			
		||||
            {
 | 
			
		||||
                ENSURE_PAYLOAD(6);
 | 
			
		||||
                bitToPayload(payload, payload_length, 55 - datatype.index, value);
 | 
			
		||||
                bitToPayload(payload, 55 - datatype.index, value);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1627,7 +1535,7 @@ namespace Knx
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                ENSURE_PAYLOAD(6);
 | 
			
		||||
                unsigned16ToPayload(payload, payload_length, 0, (int64_t)value, 0xFFFF);
 | 
			
		||||
                unsigned16ToPayload(payload, 0, (int64_t)value, 0xFFFF);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1637,7 +1545,7 @@ namespace Knx
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                ENSURE_PAYLOAD(6);
 | 
			
		||||
                unsigned32ToPayload(payload, payload_length, 2, (int64_t)value, 0xFFFF);
 | 
			
		||||
                unsigned32ToPayload(payload, 2, (int64_t)value, 0xFFFF);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1658,7 +1566,7 @@ namespace Knx
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                ENSURE_PAYLOAD(2);
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 0, (int64_t)value << 3, 0xF8);
 | 
			
		||||
                unsigned8ToPayload(payload, 0, (int64_t)value << 3, 0xF8);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1667,7 +1575,7 @@ namespace Knx
 | 
			
		||||
                if ((int64_t)value < INT64_C(0) || (int64_t)value > INT64_C(31))
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                unsigned16ToPayload(payload, payload_length, 0, (int64_t)value << 6, 0x07C0);
 | 
			
		||||
                unsigned16ToPayload(payload, 0, (int64_t)value << 6, 0x07C0);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1676,7 +1584,7 @@ namespace Knx
 | 
			
		||||
                if ((int64_t)value < INT64_C(0) || (int64_t)value > INT64_C(63))
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 1, (int64_t)value, 0x3F);
 | 
			
		||||
                unsigned8ToPayload(payload, 1, (int64_t)value, 0x3F);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1699,7 +1607,7 @@ namespace Knx
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                ENSURE_PAYLOAD(3);
 | 
			
		||||
                unsigned16ToPayload(payload, payload_length, 0, duration, 0xFFFF);
 | 
			
		||||
                unsigned16ToPayload(payload, 0, duration, 0xFFFF);
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1708,7 +1616,7 @@ namespace Knx
 | 
			
		||||
                if ((double)value < 0.0 || (double)value > 100.0)
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 2, round((double)value * 255.0 / 100.0), 0xff);
 | 
			
		||||
                unsigned8ToPayload(payload, 2, round((double)value * 255.0 / 100.0), 0xff);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
@ -1728,7 +1636,7 @@ namespace Knx
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                ENSURE_PAYLOAD(3);
 | 
			
		||||
                unsigned16ToPayload(payload, payload_length, 0, duration, 0xFFFF);
 | 
			
		||||
                unsigned16ToPayload(payload, 0, duration, 0xFFFF);
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1737,7 +1645,7 @@ namespace Knx
 | 
			
		||||
                if ((int64_t)value < INT64_C(0) || (int64_t)value > INT64_C(254))
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 2, (int64_t)value, 0xff);
 | 
			
		||||
                unsigned8ToPayload(payload, 2, (int64_t)value, 0xff);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
@ -1755,8 +1663,8 @@ namespace Knx
 | 
			
		||||
        if (!datatype.index || (datatype.mainGroup == 231 && datatype.index == 1))
 | 
			
		||||
        {
 | 
			
		||||
            ENSURE_PAYLOAD(datatype.mainGroup == 231 ? 4 : 2);
 | 
			
		||||
            unsigned8ToPayload(payload, payload_length, datatype.index * 2, ((const char*)value)[0], 0xff);
 | 
			
		||||
            unsigned8ToPayload(payload, payload_length, datatype.index * 2 + 1, ((const char*)value)[1], 0xff);
 | 
			
		||||
            unsigned8ToPayload(payload, datatype.index * 2, ((const char*)value)[0], 0xff);
 | 
			
		||||
            unsigned8ToPayload(payload, datatype.index * 2 + 1, ((const char*)value)[1], 0xff);
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
@ -1770,8 +1678,8 @@ namespace Knx
 | 
			
		||||
 | 
			
		||||
        unsigned int rgb = (int64_t)value;
 | 
			
		||||
 | 
			
		||||
        unsigned16ToPayload(payload, payload_length, 0, rgb / 256, 0xffff);
 | 
			
		||||
        unsigned8ToPayload(payload, payload_length, 2, rgb % 256, 0xff);
 | 
			
		||||
        unsigned16ToPayload(payload, 0, rgb / 256, 0xffff);
 | 
			
		||||
        unsigned8ToPayload(payload, 2, rgb % 256, 0xff);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -1782,12 +1690,12 @@ namespace Knx
 | 
			
		||||
            case 0: // RGBW
 | 
			
		||||
            {
 | 
			
		||||
                uint32_t rgbw = (uint32_t)value;
 | 
			
		||||
                unsigned32ToPayload(payload, payload_length, 0, rgbw, 0xffffffff); // RGBW
 | 
			
		||||
                unsigned32ToPayload(payload, 0, rgbw, 0xffffffff); // RGBW
 | 
			
		||||
            }
 | 
			
		||||
            break;
 | 
			
		||||
 | 
			
		||||
            case 1: // Mask bits
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 5, (uint8_t)value, 0x0f);
 | 
			
		||||
                unsigned8ToPayload(payload, 5, (uint8_t)value, 0x0f);
 | 
			
		||||
                break;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
@ -1804,12 +1712,12 @@ namespace Knx
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                ENSURE_PAYLOAD(2);
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 0, round((double)value * 255.0 / 100.0), 0xff);
 | 
			
		||||
                unsigned8ToPayload(payload, 0, round((double)value * 255.0 / 100.0), 0xff);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            case 1:
 | 
			
		||||
                bitToPayload(payload, payload_length, 15, value);
 | 
			
		||||
                bitToPayload(payload, 15, value);
 | 
			
		||||
                break;
 | 
			
		||||
 | 
			
		||||
            default:
 | 
			
		||||
@ -1829,7 +1737,7 @@ namespace Knx
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                ENSURE_PAYLOAD(6);
 | 
			
		||||
                signed32ToPayload(payload, payload_length, 0, (int64_t)value, 0xffffffff);
 | 
			
		||||
                signed32ToPayload(payload, 0, (int64_t)value, 0xffffffff);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -1839,13 +1747,13 @@ namespace Knx
 | 
			
		||||
                    return false;
 | 
			
		||||
 | 
			
		||||
                ENSURE_PAYLOAD(6);
 | 
			
		||||
                unsigned8ToPayload(payload, payload_length, 4, (int64_t)value, 0xff);
 | 
			
		||||
                unsigned8ToPayload(payload, 4, (int64_t)value, 0xff);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            case 2:
 | 
			
		||||
            case 3:
 | 
			
		||||
                bitToPayload(payload, payload_length, datatype.index + 44, value);
 | 
			
		||||
                bitToPayload(payload, datatype.index + 44, value);
 | 
			
		||||
                break;
 | 
			
		||||
 | 
			
		||||
            default:
 | 
			
		||||
@ -1899,14 +1807,14 @@ namespace Knx
 | 
			
		||||
               ((((uint64_t)payload[index + 6]) << 8) & 0x000000000000FF00) |
 | 
			
		||||
               (((uint64_t)payload[index + 7]) & 0x00000000000000FF);
 | 
			
		||||
    }
 | 
			
		||||
    double float16FromPayload(const uint8_t* payload, int index)
 | 
			
		||||
    float float16FromPayload(const uint8_t* payload, int index)
 | 
			
		||||
    {
 | 
			
		||||
        uint16_t mantissa = unsigned16FromPayload(payload, index) & 0x87FF;
 | 
			
		||||
 | 
			
		||||
        if (mantissa & 0x8000)
 | 
			
		||||
            return ((~mantissa & 0x07FF) + 1.0) * -0.01 * (1 << ((payload[index] >> 3) & 0x0F));
 | 
			
		||||
 | 
			
		||||
        return mantissa * 0.01 * (1 << ((payload[index] >> 3) & 0x0F));
 | 
			
		||||
        return mantissa * 0.01f * (1 << ((payload[index] >> 3) & 0x0F));
 | 
			
		||||
    }
 | 
			
		||||
    float float32FromPayload(const uint8_t* payload, int index)
 | 
			
		||||
    {
 | 
			
		||||
@ -1947,34 +1855,34 @@ namespace Knx
 | 
			
		||||
        return (uint8_t)((payload[index / 2] >> 4) & 0x0F);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    void bitToPayload(uint8_t* payload, size_t payload_length, int index, bool value)
 | 
			
		||||
    void bitToPayload(uint8_t* payload, int index, bool value)
 | 
			
		||||
    {
 | 
			
		||||
        ENSURE_PAYLOAD(index / 8 + 1);
 | 
			
		||||
        payload[index / 8] = (payload[index / 8] & ~(1 << (7 - (index % 8)))) | (value ? (1 << (7 - (index % 8))) : 0);
 | 
			
		||||
    }
 | 
			
		||||
    void unsigned8ToPayload(uint8_t* payload, size_t payload_length, int index, uint8_t value, uint8_t mask)
 | 
			
		||||
    void unsigned8ToPayload(uint8_t* payload, int index, uint8_t value, uint8_t mask)
 | 
			
		||||
    {
 | 
			
		||||
        ENSURE_PAYLOAD(index + 1);
 | 
			
		||||
        payload[index] = (payload[index] & ~mask) | (value & mask);
 | 
			
		||||
    }
 | 
			
		||||
    void signed8ToPayload(uint8_t* payload, size_t payload_length, int index, int8_t value, uint8_t mask)
 | 
			
		||||
    void signed8ToPayload(uint8_t* payload, int index, int8_t value, uint8_t mask)
 | 
			
		||||
    {
 | 
			
		||||
        ENSURE_PAYLOAD(index + 1);
 | 
			
		||||
        payload[index] = (payload[index] & ~mask) | (value & mask);
 | 
			
		||||
    }
 | 
			
		||||
    void unsigned16ToPayload(uint8_t* payload, size_t payload_length, int index, uint16_t value, uint16_t mask)
 | 
			
		||||
    void unsigned16ToPayload(uint8_t* payload, int index, uint16_t value, uint16_t mask)
 | 
			
		||||
    {
 | 
			
		||||
        ENSURE_PAYLOAD(index + 2);
 | 
			
		||||
        payload[index] = (payload[index] & (~mask >> 8)) | ((value >> 8) & (mask >> 8));
 | 
			
		||||
        payload[index + 1] = (payload[index + 1] & ~mask) | (value & mask);
 | 
			
		||||
    }
 | 
			
		||||
    void signed16ToPayload(uint8_t* payload, size_t payload_length, int index, int16_t value, uint16_t mask)
 | 
			
		||||
    void signed16ToPayload(uint8_t* payload, int index, int16_t value, uint16_t mask)
 | 
			
		||||
    {
 | 
			
		||||
        ENSURE_PAYLOAD(index + 2);
 | 
			
		||||
        payload[index] = (payload[index] & (~mask >> 8)) | ((value >> 8) & (mask >> 8));
 | 
			
		||||
        payload[index + 1] = (payload[index + 1] & ~mask) | (value & mask);
 | 
			
		||||
    }
 | 
			
		||||
    void unsigned32ToPayload(uint8_t* payload, size_t payload_length, int index, uint32_t value, uint32_t mask)
 | 
			
		||||
    void unsigned32ToPayload(uint8_t* payload, int index, uint32_t value, uint32_t mask)
 | 
			
		||||
    {
 | 
			
		||||
        ENSURE_PAYLOAD(index + 4);
 | 
			
		||||
        payload[index] = (payload[index] & (~mask >> 24)) | ((value >> 24) & (mask >> 24));
 | 
			
		||||
@ -1982,7 +1890,7 @@ namespace Knx
 | 
			
		||||
        payload[index + 2] = (payload[index + 2] & (~mask >> 8)) | ((value >> 8) & (mask >> 8));
 | 
			
		||||
        payload[index + 3] = (payload[index + 3] & ~mask) | (value & mask);
 | 
			
		||||
    }
 | 
			
		||||
    void signed32ToPayload(uint8_t* payload, size_t payload_length, int index, int32_t value, uint32_t mask)
 | 
			
		||||
    void signed32ToPayload(uint8_t* payload, int index, int32_t value, uint32_t mask)
 | 
			
		||||
    {
 | 
			
		||||
        ENSURE_PAYLOAD(index + 4);
 | 
			
		||||
        payload[index] = (payload[index] & (~mask >> 24)) | ((value >> 24) & (mask >> 24));
 | 
			
		||||
@ -1991,7 +1899,7 @@ namespace Knx
 | 
			
		||||
        payload[index + 3] = (payload[index + 3] & ~mask) | (value & mask);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    void float16ToPayload(uint8_t* payload, size_t payload_length, int index, double value, uint16_t mask)
 | 
			
		||||
    void float16ToPayload(uint8_t* payload, int index, float value, uint16_t mask)
 | 
			
		||||
    {
 | 
			
		||||
        bool wasNegative = false;
 | 
			
		||||
 | 
			
		||||
@ -2021,10 +1929,10 @@ namespace Knx
 | 
			
		||||
 | 
			
		||||
        // println(mantissa);
 | 
			
		||||
 | 
			
		||||
        signed16ToPayload(payload, payload_length, index, mantissa, mask);
 | 
			
		||||
        unsigned8ToPayload(payload, payload_length, index, exponent << 3, 0x78 & (mask >> 8));
 | 
			
		||||
        signed16ToPayload(payload, index, mantissa, mask);
 | 
			
		||||
        unsigned8ToPayload(payload, index, exponent << 3, 0x78 & (mask >> 8));
 | 
			
		||||
    }
 | 
			
		||||
    void float32ToPayload(uint8_t* payload, size_t payload_length, int index, double value, uint32_t mask)
 | 
			
		||||
    void float32ToPayload(uint8_t* payload, int index, float value, uint32_t mask)
 | 
			
		||||
    {
 | 
			
		||||
        union
 | 
			
		||||
        {
 | 
			
		||||
@ -2032,9 +1940,9 @@ namespace Knx
 | 
			
		||||
            uint32_t i;
 | 
			
		||||
        } num;
 | 
			
		||||
        num.f = value;
 | 
			
		||||
        unsigned32ToPayload(payload, payload_length, index, num.i, mask);
 | 
			
		||||
        unsigned32ToPayload(payload, index, num.i, mask);
 | 
			
		||||
    }
 | 
			
		||||
    void signed64ToPayload(uint8_t* payload, size_t payload_length, int index, int64_t value, uint64_t mask)
 | 
			
		||||
    void signed64ToPayload(uint8_t* payload, int index, int64_t value, uint64_t mask)
 | 
			
		||||
    {
 | 
			
		||||
        ENSURE_PAYLOAD(index + 8);
 | 
			
		||||
        payload[index] = (payload[index] & (~mask >> 56)) | ((value >> 56) & (mask >> 56));
 | 
			
		||||
@ -2046,7 +1954,7 @@ namespace Knx
 | 
			
		||||
        payload[index + 6] = (payload[index + 6] & (~mask >> 8)) | ((value >> 8) & (mask >> 8));
 | 
			
		||||
        payload[index + 7] = (payload[index + 7] & ~mask) | (value & mask);
 | 
			
		||||
    }
 | 
			
		||||
    void bcdToPayload(uint8_t* payload, size_t payload_length, int index, uint8_t value)
 | 
			
		||||
    void bcdToPayload(uint8_t* payload, int index, uint8_t value)
 | 
			
		||||
    {
 | 
			
		||||
        ENSURE_PAYLOAD(index / 2 + 1);
 | 
			
		||||
 | 
			
		||||
@ -29,7 +29,7 @@
 | 
			
		||||
#pragma once
 | 
			
		||||
 | 
			
		||||
#include "dpt.h"
 | 
			
		||||
#include "knx_value.h"
 | 
			
		||||
#include "../knx_value.h"
 | 
			
		||||
 | 
			
		||||
#include <cstdint>
 | 
			
		||||
 | 
			
		||||
@ -47,7 +47,6 @@ namespace Knx
 | 
			
		||||
    int KNX_Encode_Value(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype);
 | 
			
		||||
 | 
			
		||||
    //KNX to internal
 | 
			
		||||
    int busValueToBinary(const uint8_t* payload, size_t payload_length, const Dpt& datatype, KNXValue& value);
 | 
			
		||||
    int busValueToBinaryControl(const uint8_t* payload, size_t payload_length, const Dpt& datatype, KNXValue& value);
 | 
			
		||||
    int busValueToStepControl(const uint8_t* payload, size_t payload_length, const Dpt& datatype, KNXValue& value);
 | 
			
		||||
    int busValueToCharacter(const uint8_t* payload, size_t payload_length, const Dpt& datatype, KNXValue& value);
 | 
			
		||||
@ -58,7 +57,6 @@ namespace Knx
 | 
			
		||||
    int busValueToTimePeriod(const uint8_t* payload, size_t payload_length, const Dpt& datatype, KNXValue& value);
 | 
			
		||||
    int busValueToSigned16(const uint8_t* payload, size_t payload_length, const Dpt& datatype, KNXValue& value);
 | 
			
		||||
    int busValueToTimeDelta(const uint8_t* payload, size_t payload_length, const Dpt& datatype, KNXValue& value);
 | 
			
		||||
    int busValueToFloat16(const uint8_t* payload, size_t payload_length, const Dpt& datatype, KNXValue& value);
 | 
			
		||||
    int busValueToTime(const uint8_t* payload, size_t payload_length, const Dpt& datatype, KNXValue& value);
 | 
			
		||||
    int busValueToDate(const uint8_t* payload, size_t payload_length, const Dpt& datatype, KNXValue& value);
 | 
			
		||||
    int busValueToUnsigned32(const uint8_t* payload, size_t payload_length, const Dpt& datatype, KNXValue& value);
 | 
			
		||||
@ -86,7 +84,6 @@ namespace Knx
 | 
			
		||||
    int busValueToActiveEnergy(const uint8_t* payload, size_t payload_length, const Dpt& datatype, KNXValue& value);
 | 
			
		||||
 | 
			
		||||
    //Internal to KNX
 | 
			
		||||
    int valueToBusValueBinary(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype);
 | 
			
		||||
    int valueToBusValueBinaryControl(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype);
 | 
			
		||||
    int valueToBusValueStepControl(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype);
 | 
			
		||||
    int valueToBusValueCharacter(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype);
 | 
			
		||||
@ -97,7 +94,6 @@ namespace Knx
 | 
			
		||||
    int valueToBusValueTimePeriod(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype);
 | 
			
		||||
    int valueToBusValueSigned16(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype);
 | 
			
		||||
    int valueToBusValueTimeDelta(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype);
 | 
			
		||||
    int valueToBusValueFloat16(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype);
 | 
			
		||||
    int valueToBusValueTime(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype);
 | 
			
		||||
    int valueToBusValueDate(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype);
 | 
			
		||||
    int valueToBusValueUnsigned32(const KNXValue& value, uint8_t* payload, size_t payload_length, const Dpt& datatype);
 | 
			
		||||
@ -133,21 +129,21 @@ namespace Knx
 | 
			
		||||
    uint32_t unsigned32FromPayload(const uint8_t* payload, int index);
 | 
			
		||||
    int32_t signed32FromPayload(const uint8_t* payload, int index);
 | 
			
		||||
    uint64_t unsigned64FromPayload(const uint8_t* payload, int index);
 | 
			
		||||
    double float16FromPayload(const uint8_t* payload, int index);
 | 
			
		||||
    float float16FromPayload(const uint8_t* payload, int index);
 | 
			
		||||
    float float32FromPayload(const uint8_t* payload, int index);
 | 
			
		||||
    double float64FromPayload(const uint8_t* payload, int index);
 | 
			
		||||
    int64_t signed64FromPayload(const uint8_t* payload, int index);
 | 
			
		||||
    uint8_t bcdFromPayload(const uint8_t* payload, int index);
 | 
			
		||||
 | 
			
		||||
    void bitToPayload(uint8_t* payload, size_t payload_length, int index, bool value);
 | 
			
		||||
    void unsigned8ToPayload(uint8_t* payload, size_t payload_length, int index, uint8_t value, uint8_t mask);    //mask 0xFF
 | 
			
		||||
    void signed8ToPayload(uint8_t* payload, size_t payload_length, int index, int8_t value, uint8_t mask);       //mask 0xFF
 | 
			
		||||
    void unsigned16ToPayload(uint8_t* payload, size_t payload_length, int index, uint16_t value, uint16_t mask); //mask 0xFFFF
 | 
			
		||||
    void signed16ToPayload(uint8_t* payload, size_t payload_length, int index, int16_t value, uint16_t mask);    //mask 0xFFFF
 | 
			
		||||
    void unsigned32ToPayload(uint8_t* payload, size_t payload_length, int index, uint32_t value, uint32_t mask); //mask = 0xFFFFFFFF
 | 
			
		||||
    void signed32ToPayload(uint8_t* payload, size_t payload_length, int index, int32_t value, uint32_t mask);    //mask  = 0xFFFFFFFF
 | 
			
		||||
    void float16ToPayload(uint8_t* payload, size_t payload_length, int index, double value, uint16_t mask);      //mask = 0xFFFF
 | 
			
		||||
    void float32ToPayload(uint8_t* payload, size_t payload_length, int index, double value, uint32_t mask);      //mask  = 0xFFFFFFFF
 | 
			
		||||
    void signed64ToPayload(uint8_t* payload, size_t payload_length, int index, int64_t value, uint64_t mask);    //mask = UINT64_C(0xFFFFFFFFFFFFFFFF)
 | 
			
		||||
    void bcdToPayload(uint8_t* payload, size_t payload_length, int index, uint8_t value);
 | 
			
		||||
    void bitToPayload(uint8_t* payload, int index, bool value);
 | 
			
		||||
    void unsigned8ToPayload(uint8_t* payload, int index, uint8_t value, uint8_t mask);    //mask 0xFF
 | 
			
		||||
    void signed8ToPayload(uint8_t* payload, int index, int8_t value, uint8_t mask);       //mask 0xFF
 | 
			
		||||
    void unsigned16ToPayload(uint8_t* payload, int index, uint16_t value, uint16_t mask); //mask 0xFFFF
 | 
			
		||||
    void signed16ToPayload(uint8_t* payload, int index, int16_t value, uint16_t mask);    //mask 0xFFFF
 | 
			
		||||
    void unsigned32ToPayload(uint8_t* payload, int index, uint32_t value, uint32_t mask); //mask = 0xFFFFFFFF
 | 
			
		||||
    void signed32ToPayload(uint8_t* payload, int index, int32_t value, uint32_t mask);    //mask  = 0xFFFFFFFF
 | 
			
		||||
    void float16ToPayload(uint8_t* payload, int index, float value, uint16_t mask);      //mask = 0xFFFF
 | 
			
		||||
    void float32ToPayload(uint8_t* payload, int index, float value, uint32_t mask);      //mask  = 0xFFFFFFFF
 | 
			
		||||
    void signed64ToPayload(uint8_t* payload, int index, int64_t value, uint64_t mask);    //mask = UINT64_C(0xFFFFFFFFFFFFFFFF)
 | 
			
		||||
    void bcdToPayload(uint8_t* payload, int index, uint8_t value);
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										4
									
								
								src/knx/group_object/dpt/dpts.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										4
									
								
								src/knx/group_object/dpt/dpts.h
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,4 @@
 | 
			
		||||
#pragma once
 | 
			
		||||
 | 
			
		||||
#include "dpt1.h"
 | 
			
		||||
#include "dpt9.h"
 | 
			
		||||
@ -1,6 +1,5 @@
 | 
			
		||||
#include "group_object.h"
 | 
			
		||||
 | 
			
		||||
#include "datapoint_types.h"
 | 
			
		||||
#include "../interface_object/group_object_table_object.h"
 | 
			
		||||
#include "../util/logger.h"
 | 
			
		||||
#include "../bits.h"
 | 
			
		||||
@ -101,6 +100,11 @@ namespace Knx
 | 
			
		||||
        return _asap;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    Go_SizeCode GroupObject::sizeCode() const
 | 
			
		||||
    {
 | 
			
		||||
        return (Go_SizeCode)lowByte(ntohs(_table->_tableData[_asap]));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    size_t GroupObject::goSize()
 | 
			
		||||
    {
 | 
			
		||||
        size_t size = sizeInTelegram();
 | 
			
		||||
@ -220,105 +224,6 @@ namespace Knx
 | 
			
		||||
            _updateHandlerStatic(go);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    void GroupObject::value(const KNXValue& value, const Dpt& type)
 | 
			
		||||
    {
 | 
			
		||||
        valueNoSend(value, type);
 | 
			
		||||
        objectWritten();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    KNXValue GroupObject::value(const Dpt& type)
 | 
			
		||||
    {
 | 
			
		||||
        KNXValue value = "";
 | 
			
		||||
        KNX_Decode_Value(_data, _dataLength, type, value);
 | 
			
		||||
        return value;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    bool GroupObject::tryValue(KNXValue& value, const Dpt& type)
 | 
			
		||||
    {
 | 
			
		||||
        return KNX_Decode_Value(_data, _dataLength, type, value);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
#ifndef SMALL_GROUPOBJECT
 | 
			
		||||
    void GroupObject::dataPointType(Dpt value)
 | 
			
		||||
    {
 | 
			
		||||
        _datapointType = value;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    Dpt GroupObject::dataPointType()
 | 
			
		||||
    {
 | 
			
		||||
        return _datapointType;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    bool GroupObject::tryValue(KNXValue& value)
 | 
			
		||||
    {
 | 
			
		||||
        return tryValue(value, _datapointType);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    void GroupObject::value(const KNXValue& value)
 | 
			
		||||
    {
 | 
			
		||||
        this->value(value, _datapointType);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    KNXValue GroupObject::value()
 | 
			
		||||
    {
 | 
			
		||||
        return value(_datapointType);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    void GroupObject::valueNoSend(const KNXValue& value)
 | 
			
		||||
    {
 | 
			
		||||
        valueNoSend(value, _datapointType);
 | 
			
		||||
    }
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
    void GroupObject::valueNoSend(const KNXValue& value, const Dpt& type)
 | 
			
		||||
    {
 | 
			
		||||
        if (_uninitialized)
 | 
			
		||||
            commFlag(Ok);
 | 
			
		||||
 | 
			
		||||
        KNX_Encode_Value(value, _data, _dataLength, type);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    bool GroupObject::valueNoSendCompare(const KNXValue& value, const Dpt& type)
 | 
			
		||||
    {
 | 
			
		||||
        if (_uninitialized)
 | 
			
		||||
        {
 | 
			
		||||
            // always set first value
 | 
			
		||||
            this->valueNoSend(value, type);
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
        else
 | 
			
		||||
        {
 | 
			
		||||
            // convert new value to given dtp
 | 
			
		||||
            uint8_t newData[_dataLength];
 | 
			
		||||
            memset(newData, 0, _dataLength);
 | 
			
		||||
            KNX_Encode_Value(value, newData, _dataLength, type);
 | 
			
		||||
 | 
			
		||||
            // check for change in converted value / update value on change only
 | 
			
		||||
            const bool dataChanged = memcmp(_data, newData, _dataLength);
 | 
			
		||||
 | 
			
		||||
            if (dataChanged)
 | 
			
		||||
                memcpy(_data, newData, _dataLength);
 | 
			
		||||
 | 
			
		||||
            return dataChanged;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    bool GroupObject::valueCompare(const KNXValue& value, const Dpt& type)
 | 
			
		||||
    {
 | 
			
		||||
        if (valueNoSendCompare(value, type))
 | 
			
		||||
        {
 | 
			
		||||
            objectWritten();
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return false;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    bool operator==(const GroupObject& lhs, const GroupObject& rhs)
 | 
			
		||||
    {
 | 
			
		||||
        return lhs.asap() == rhs.asap();
 | 
			
		||||
 | 
			
		||||
@ -1,7 +1,6 @@
 | 
			
		||||
#pragma once
 | 
			
		||||
 | 
			
		||||
#include "../knx_types.h"
 | 
			
		||||
#include "dptconvert.h"
 | 
			
		||||
 | 
			
		||||
#include <stddef.h>
 | 
			
		||||
#include <stdint.h>
 | 
			
		||||
@ -38,6 +37,266 @@ namespace Knx
 | 
			
		||||
        Uninitialized = 6 //!< uninitialized Group Object, its value is not valid
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
    enum Go_SizeCode
 | 
			
		||||
    {
 | 
			
		||||
        Go_1_Bit = 0,
 | 
			
		||||
        Go_2_Bit = 1,
 | 
			
		||||
        Go_3_Bit = 2,
 | 
			
		||||
        Go_4_Bit = 3,
 | 
			
		||||
        Go_5_Bit = 4,
 | 
			
		||||
        Go_6_Bit = 5,
 | 
			
		||||
        Go_7_Bit = 6,
 | 
			
		||||
        Go_1_Octet = 7,
 | 
			
		||||
        Go_2_Octets = 8,
 | 
			
		||||
        Go_3_Octets = 9,
 | 
			
		||||
        Go_4_Octets = 10,
 | 
			
		||||
        Go_6_Octets = 11,
 | 
			
		||||
        Go_8_Octets = 12,
 | 
			
		||||
        Go_10_Octets = 13,
 | 
			
		||||
        Go_14_Octets = 14,
 | 
			
		||||
        Go_5_Octets = 15,
 | 
			
		||||
        Go_7_Octets = 16,
 | 
			
		||||
        Go_9_Octets = 17,
 | 
			
		||||
        Go_11_Octets = 18,
 | 
			
		||||
        Go_12_Octets = 19,
 | 
			
		||||
        Go_13_Octets = 20,
 | 
			
		||||
        Go_15_Octets = 21,
 | 
			
		||||
        Go_16_Octets = 22,
 | 
			
		||||
        Go_17_Octets = 23,
 | 
			
		||||
        Go_18_Octets = 24,
 | 
			
		||||
        Go_19_Octets = 25,
 | 
			
		||||
        Go_20_Octets = 26,
 | 
			
		||||
        Go_21_Octets = 27,
 | 
			
		||||
        Go_22_Octets = 28,
 | 
			
		||||
        Go_23_Octets = 29,
 | 
			
		||||
        Go_24_Octets = 30,
 | 
			
		||||
        Go_25_Octets = 31,
 | 
			
		||||
        Go_26_Octets = 32,
 | 
			
		||||
        Go_27_Octets = 33,
 | 
			
		||||
        Go_28_Octets = 34,
 | 
			
		||||
        Go_29_Octets = 35,
 | 
			
		||||
        Go_30_Octets = 36,
 | 
			
		||||
        Go_31_Octets = 37,
 | 
			
		||||
        Go_32_Octets = 38,
 | 
			
		||||
        Go_33_Octets = 39,
 | 
			
		||||
        Go_34_Octets = 40,
 | 
			
		||||
        Go_35_Octets = 41,
 | 
			
		||||
        Go_36_Octets = 42,
 | 
			
		||||
        Go_37_Octets = 43,
 | 
			
		||||
        Go_38_Octets = 44,
 | 
			
		||||
        Go_39_Octets = 45,
 | 
			
		||||
        Go_40_Octets = 46,
 | 
			
		||||
        Go_41_Octets = 47,
 | 
			
		||||
        Go_42_Octets = 48,
 | 
			
		||||
        Go_43_Octets = 49,
 | 
			
		||||
        Go_44_Octets = 50,
 | 
			
		||||
        Go_45_Octets = 51,
 | 
			
		||||
        Go_46_Octets = 52,
 | 
			
		||||
        Go_47_Octets = 53,
 | 
			
		||||
        Go_48_Octets = 54,
 | 
			
		||||
        Go_49_Octets = 55,
 | 
			
		||||
        Go_50_Octets = 56,
 | 
			
		||||
        Go_51_Octets = 57,
 | 
			
		||||
        Go_52_Octets = 58,
 | 
			
		||||
        Go_53_Octets = 59,
 | 
			
		||||
        Go_54_Octets = 60,
 | 
			
		||||
        Go_55_Octets = 61,
 | 
			
		||||
        Go_56_Octets = 62,
 | 
			
		||||
        Go_57_Octets = 63,
 | 
			
		||||
        Go_58_Octets = 64,
 | 
			
		||||
        Go_59_Octets = 65,
 | 
			
		||||
        Go_60_Octets = 66,
 | 
			
		||||
        Go_61_Octets = 67,
 | 
			
		||||
        Go_62_Octets = 68,
 | 
			
		||||
        Go_63_Octets = 69,
 | 
			
		||||
        Go_64_Octets = 70,
 | 
			
		||||
        Go_65_Octets = 71,
 | 
			
		||||
        Go_66_Octets = 72,
 | 
			
		||||
        Go_67_Octets = 73,
 | 
			
		||||
        Go_68_Octets = 74,
 | 
			
		||||
        Go_69_Octets = 75,
 | 
			
		||||
        Go_70_Octets = 76,
 | 
			
		||||
        Go_71_Octets = 77,
 | 
			
		||||
        Go_72_Octets = 78,
 | 
			
		||||
        Go_73_Octets = 79,
 | 
			
		||||
        Go_74_Octets = 80,
 | 
			
		||||
        Go_75_Octets = 81,
 | 
			
		||||
        Go_76_Octets = 82,
 | 
			
		||||
        Go_77_Octets = 83,
 | 
			
		||||
        Go_78_Octets = 84,
 | 
			
		||||
        Go_79_Octets = 85,
 | 
			
		||||
        Go_80_Octets = 86,
 | 
			
		||||
        Go_81_Octets = 87,
 | 
			
		||||
        Go_82_Octets = 88,
 | 
			
		||||
        Go_83_Octets = 89,
 | 
			
		||||
        Go_84_Octets = 90,
 | 
			
		||||
        Go_85_Octets = 91,
 | 
			
		||||
        Go_86_Octets = 92,
 | 
			
		||||
        Go_87_Octets = 93,
 | 
			
		||||
        Go_88_Octets = 94,
 | 
			
		||||
        Go_89_Octets = 95,
 | 
			
		||||
        Go_90_Octets = 96,
 | 
			
		||||
        Go_91_Octets = 97,
 | 
			
		||||
        Go_92_Octets = 98,
 | 
			
		||||
        Go_93_Octets = 99,
 | 
			
		||||
        Go_94_Octets = 100,
 | 
			
		||||
        Go_95_Octets = 101,
 | 
			
		||||
        Go_96_Octets = 102,
 | 
			
		||||
        Go_97_Octets = 103,
 | 
			
		||||
        Go_98_Octets = 104,
 | 
			
		||||
        Go_99_Octets = 105,
 | 
			
		||||
        Go_100_Octets = 106,
 | 
			
		||||
        Go_101_Octets = 107,
 | 
			
		||||
        Go_102_Octets = 108,
 | 
			
		||||
        Go_103_Octets = 109,
 | 
			
		||||
        Go_104_Octets = 110,
 | 
			
		||||
        Go_105_Octets = 111,
 | 
			
		||||
        Go_106_Octets = 112,
 | 
			
		||||
        Go_107_Octets = 113,
 | 
			
		||||
        Go_108_Octets = 114,
 | 
			
		||||
        Go_109_Octets = 115,
 | 
			
		||||
        Go_110_Octets = 116,
 | 
			
		||||
        Go_111_Octets = 117,
 | 
			
		||||
        Go_112_Octets = 118,
 | 
			
		||||
        Go_113_Octets = 119,
 | 
			
		||||
        Go_114_Octets = 120,
 | 
			
		||||
        Go_115_Octets = 121,
 | 
			
		||||
        Go_116_Octets = 122,
 | 
			
		||||
        Go_117_Octets = 123,
 | 
			
		||||
        Go_118_Octets = 124,
 | 
			
		||||
        Go_119_Octets = 125,
 | 
			
		||||
        Go_120_Octets = 126,
 | 
			
		||||
        Go_121_Octets = 127,
 | 
			
		||||
        Go_122_Octets = 128,
 | 
			
		||||
        Go_123_Octets = 129,
 | 
			
		||||
        Go_124_Octets = 130,
 | 
			
		||||
        Go_125_Octets = 131,
 | 
			
		||||
        Go_126_Octets = 132,
 | 
			
		||||
        Go_127_Octets = 133,
 | 
			
		||||
        Go_128_Octets = 134,
 | 
			
		||||
        Go_129_Octets = 135,
 | 
			
		||||
        Go_130_Octets = 136,
 | 
			
		||||
        Go_131_Octets = 137,
 | 
			
		||||
        Go_132_Octets = 138,
 | 
			
		||||
        Go_133_Octets = 139,
 | 
			
		||||
        Go_134_Octets = 140,
 | 
			
		||||
        Go_135_Octets = 141,
 | 
			
		||||
        Go_136_Octets = 142,
 | 
			
		||||
        Go_137_Octets = 143,
 | 
			
		||||
        Go_138_Octets = 144,
 | 
			
		||||
        Go_139_Octets = 145,
 | 
			
		||||
        Go_140_Octets = 146,
 | 
			
		||||
        Go_141_Octets = 147,
 | 
			
		||||
        Go_142_Octets = 148,
 | 
			
		||||
        Go_143_Octets = 149,
 | 
			
		||||
        Go_144_Octets = 150,
 | 
			
		||||
        Go_145_Octets = 151,
 | 
			
		||||
        Go_146_Octets = 152,
 | 
			
		||||
        Go_147_Octets = 153,
 | 
			
		||||
        Go_148_Octets = 154,
 | 
			
		||||
        Go_149_Octets = 155,
 | 
			
		||||
        Go_150_Octets = 156,
 | 
			
		||||
        Go_151_Octets = 157,
 | 
			
		||||
        Go_152_Octets = 158,
 | 
			
		||||
        Go_153_Octets = 159,
 | 
			
		||||
        Go_154_Octets = 160,
 | 
			
		||||
        Go_155_Octets = 161,
 | 
			
		||||
        Go_156_Octets = 162,
 | 
			
		||||
        Go_157_Octets = 163,
 | 
			
		||||
        Go_158_Octets = 164,
 | 
			
		||||
        Go_159_Octets = 165,
 | 
			
		||||
        Go_160_Octets = 166,
 | 
			
		||||
        Go_161_Octets = 167,
 | 
			
		||||
        Go_162_Octets = 168,
 | 
			
		||||
        Go_163_Octets = 169,
 | 
			
		||||
        Go_164_Octets = 170,
 | 
			
		||||
        Go_165_Octets = 171,
 | 
			
		||||
        Go_166_Octets = 172,
 | 
			
		||||
        Go_167_Octets = 173,
 | 
			
		||||
        Go_168_Octets = 174,
 | 
			
		||||
        Go_169_Octets = 175,
 | 
			
		||||
        Go_170_Octets = 176,
 | 
			
		||||
        Go_171_Octets = 177,
 | 
			
		||||
        Go_172_Octets = 178,
 | 
			
		||||
        Go_173_Octets = 179,
 | 
			
		||||
        Go_174_Octets = 180,
 | 
			
		||||
        Go_175_Octets = 181,
 | 
			
		||||
        Go_176_Octets = 182,
 | 
			
		||||
        Go_177_Octets = 183,
 | 
			
		||||
        Go_178_Octets = 184,
 | 
			
		||||
        Go_179_Octets = 185,
 | 
			
		||||
        Go_180_Octets = 186,
 | 
			
		||||
        Go_181_Octets = 187,
 | 
			
		||||
        Go_182_Octets = 188,
 | 
			
		||||
        Go_183_Octets = 189,
 | 
			
		||||
        Go_184_Octets = 190,
 | 
			
		||||
        Go_185_Octets = 191,
 | 
			
		||||
        Go_186_Octets = 192,
 | 
			
		||||
        Go_187_Octets = 193,
 | 
			
		||||
        Go_188_Octets = 194,
 | 
			
		||||
        Go_189_Octets = 195,
 | 
			
		||||
        Go_190_Octets = 196,
 | 
			
		||||
        Go_191_Octets = 197,
 | 
			
		||||
        Go_192_Octets = 198,
 | 
			
		||||
        Go_193_Octets = 199,
 | 
			
		||||
        Go_194_Octets = 200,
 | 
			
		||||
        Go_195_Octets = 201,
 | 
			
		||||
        Go_196_Octets = 202,
 | 
			
		||||
        Go_197_Octets = 203,
 | 
			
		||||
        Go_198_Octets = 204,
 | 
			
		||||
        Go_199_Octets = 205,
 | 
			
		||||
        Go_200_Octets = 206,
 | 
			
		||||
        Go_201_Octets = 207,
 | 
			
		||||
        Go_202_Octets = 208,
 | 
			
		||||
        Go_203_Octets = 209,
 | 
			
		||||
        Go_204_Octets = 210,
 | 
			
		||||
        Go_205_Octets = 211,
 | 
			
		||||
        Go_206_Octets = 212,
 | 
			
		||||
        Go_207_Octets = 213,
 | 
			
		||||
        Go_208_Octets = 214,
 | 
			
		||||
        Go_209_Octets = 215,
 | 
			
		||||
        Go_210_Octets = 216,
 | 
			
		||||
        Go_211_Octets = 217,
 | 
			
		||||
        Go_212_Octets = 218,
 | 
			
		||||
        Go_213_Octets = 219,
 | 
			
		||||
        Go_214_Octets = 220,
 | 
			
		||||
        Go_215_Octets = 221,
 | 
			
		||||
        Go_216_Octets = 222,
 | 
			
		||||
        Go_217_Octets = 223,
 | 
			
		||||
        Go_218_Octets = 224,
 | 
			
		||||
        Go_219_Octets = 225,
 | 
			
		||||
        Go_220_Octets = 226,
 | 
			
		||||
        Go_221_Octets = 227,
 | 
			
		||||
        Go_222_Octets = 228,
 | 
			
		||||
        Go_223_Octets = 229,
 | 
			
		||||
        Go_224_Octets = 230,
 | 
			
		||||
        Go_225_Octets = 231,
 | 
			
		||||
        Go_226_Octets = 232,
 | 
			
		||||
        Go_227_Octets = 233,
 | 
			
		||||
        Go_228_Octets = 234,
 | 
			
		||||
        Go_229_Octets = 235,
 | 
			
		||||
        Go_230_Octets = 236,
 | 
			
		||||
        Go_231_Octets = 237,
 | 
			
		||||
        Go_232_Octets = 238,
 | 
			
		||||
        Go_233_Octets = 239,
 | 
			
		||||
        Go_234_Octets = 240,
 | 
			
		||||
        Go_235_Octets = 241,
 | 
			
		||||
        Go_236_Octets = 242,
 | 
			
		||||
        Go_237_Octets = 243,
 | 
			
		||||
        Go_238_Octets = 244,
 | 
			
		||||
        Go_239_Octets = 245,
 | 
			
		||||
        Go_240_Octets = 246,
 | 
			
		||||
        Go_241_Octets = 247,
 | 
			
		||||
        Go_242_Octets = 248,
 | 
			
		||||
        Go_243_Octets = 249,
 | 
			
		||||
        Go_244_Octets = 250,
 | 
			
		||||
        Go_245_Octets = 251,
 | 
			
		||||
        Go_246_Octets = 252,
 | 
			
		||||
        Go_247_Octets = 253,
 | 
			
		||||
        Go_248_Octets = 254,
 | 
			
		||||
        Go_252_Octets = 255
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * This class represents a single group object. In german they are called "Kommunikationsobjekt" or "KO".
 | 
			
		||||
     */
 | 
			
		||||
@ -140,18 +399,22 @@ namespace Knx
 | 
			
		||||
            uint16_t asap() const;
 | 
			
		||||
 | 
			
		||||
            /**
 | 
			
		||||
             * return the current value of the group object.
 | 
			
		||||
             * @param type the datapoint type used for the conversion. If this doesn't fit to the group object the returned value is invalid.
 | 
			
		||||
             * returns The size of the group object encoded as the size code. See knxspec 3.5.1 p. 178.
 | 
			
		||||
             */
 | 
			
		||||
            KNXValue value(const Dpt& type);
 | 
			
		||||
            Go_SizeCode sizeCode() const;
 | 
			
		||||
 | 
			
		||||
            /**
 | 
			
		||||
             * return the current value of the group object.
 | 
			
		||||
             * If the DPT class doesn't fit to the group object size the returned value is invalid.
 | 
			
		||||
             */
 | 
			
		||||
            template<class DPT> DPT value();
 | 
			
		||||
            /**
 | 
			
		||||
             * set the current value of the group object and changes the state of the group object to ::WriteRequest.
 | 
			
		||||
             * @param value the value the group object is set to
 | 
			
		||||
             * @param type the datapoint type used for the conversion.
 | 
			
		||||
             * @param value the value the group object is set to.
 | 
			
		||||
             *
 | 
			
		||||
             * The parameters must fit the group object. Otherwise it will stay unchanged.
 | 
			
		||||
             */
 | 
			
		||||
            void value(const KNXValue& value, const Dpt& type);
 | 
			
		||||
            template<class DPT> void value(const DPT& value);
 | 
			
		||||
 | 
			
		||||
            /**
 | 
			
		||||
             * Check if the value (after conversion to dpt) will differ from current value of the group object and changes the state of the group object to ::WriteRequest if different.
 | 
			
		||||
@ -163,79 +426,37 @@ namespace Knx
 | 
			
		||||
             *
 | 
			
		||||
             * @returns true if the value of the group object has changed
 | 
			
		||||
             */
 | 
			
		||||
            bool valueCompare(const KNXValue& value, const Dpt& type);
 | 
			
		||||
            template<class DPT> bool valueCompare(const DPT& value);
 | 
			
		||||
 | 
			
		||||
            /**
 | 
			
		||||
             * set the current value of the group object.
 | 
			
		||||
             * @param value the value the group object is set to
 | 
			
		||||
             * @param type the datapoint type used for the conversion.
 | 
			
		||||
             *
 | 
			
		||||
             * The parameters must fit the group object. Otherwise it will stay unchanged.
 | 
			
		||||
             * The parameters must fit size of the group object. Otherwise it will stay unchanged.
 | 
			
		||||
             */
 | 
			
		||||
            void valueNoSend(const KNXValue& value, const Dpt& type);
 | 
			
		||||
            template<class DPT> void valueNoSend(const DPT& value);
 | 
			
		||||
 | 
			
		||||
            /**
 | 
			
		||||
             * Check if the value (after conversion to dpt) will differ from current value of the group object and update if necessary.
 | 
			
		||||
             * Use this method only, when the value change is relevant, otherwise valueNoSend(const KNXValue&, const Dpt&) will do the same (without overhead for comparing)
 | 
			
		||||
             * @param value the value the group object is set to
 | 
			
		||||
             * @param type the datapoint type used for the conversion.
 | 
			
		||||
             * Use this method only, when the value change is relevant, otherwise valueNoSend(...) will do the same (without overhead for comparing)
 | 
			
		||||
             * @param value the value the group object is set to.
 | 
			
		||||
             *
 | 
			
		||||
             * The parameters must fit the group object. Otherwise it will stay unchanged.
 | 
			
		||||
             * The parameters must fit the size of the group object. Otherwise it will stay unchanged.
 | 
			
		||||
             *
 | 
			
		||||
             * @returns true if the value of the group object has changed
 | 
			
		||||
             */
 | 
			
		||||
            bool valueNoSendCompare(const KNXValue& value, const Dpt& type);
 | 
			
		||||
            template<class DPT> bool valueNoSendCompare(const DPT& value);
 | 
			
		||||
 | 
			
		||||
            /**
 | 
			
		||||
             * set the current value of the group object.
 | 
			
		||||
             * @param value the value the group object is set to
 | 
			
		||||
             * @param type the datapoint type used for the conversion.
 | 
			
		||||
             *
 | 
			
		||||
             * The parameters must fit the group object. Otherwise it will stay unchanged.
 | 
			
		||||
             *
 | 
			
		||||
             * @returns true if the value of the group object was changed successfully.
 | 
			
		||||
             */
 | 
			
		||||
            bool tryValue(KNXValue& value, const Dpt& type);
 | 
			
		||||
            template<class DPT> bool tryValue(const DPT& value);
 | 
			
		||||
 | 
			
		||||
#ifndef SMALL_GROUPOBJECT
 | 
			
		||||
            /**
 | 
			
		||||
             * return the current value of the group object. The datapoint type must be set with dataPointType(). Otherwise the returned
 | 
			
		||||
             * value is invalid.
 | 
			
		||||
             */
 | 
			
		||||
            KNXValue value();
 | 
			
		||||
            /**
 | 
			
		||||
             * set the current value of the group object and changes the state of the group object to ::WriteRequest.
 | 
			
		||||
             * @param value the value the group object is set to
 | 
			
		||||
             *
 | 
			
		||||
             * The parameters must fit the group object and dhe datapoint type must be set with dataPointType(). Otherwise it will stay unchanged.
 | 
			
		||||
             */
 | 
			
		||||
            void value(const KNXValue& value);
 | 
			
		||||
            /**
 | 
			
		||||
             * set the current value of the group object.
 | 
			
		||||
             * @param value the value the group object is set to
 | 
			
		||||
             *
 | 
			
		||||
             * The parameters must fit the group object and dhe datapoint type must be set with dataPointType(). Otherwise it will stay unchanged.
 | 
			
		||||
             */
 | 
			
		||||
            void valueNoSend(const KNXValue& value);
 | 
			
		||||
            /**
 | 
			
		||||
             * set the current value of the group object.
 | 
			
		||||
             * @param value the value the group object is set to
 | 
			
		||||
             *
 | 
			
		||||
             * The parameters must fit the group object and dhe datapoint type must be set with dataPointType(). Otherwise it will stay unchanged.
 | 
			
		||||
             *
 | 
			
		||||
             * @returns true if the value of the group object was changed successfully.
 | 
			
		||||
             */
 | 
			
		||||
            bool tryValue(KNXValue& value);
 | 
			
		||||
 | 
			
		||||
            /**
 | 
			
		||||
             * returns the currently configured datapoint type.
 | 
			
		||||
             */
 | 
			
		||||
            Dpt dataPointType();
 | 
			
		||||
            /**
 | 
			
		||||
             * sets the datapoint type of the group object.
 | 
			
		||||
             */
 | 
			
		||||
            void dataPointType(Dpt value);
 | 
			
		||||
#endif
 | 
			
		||||
            /**
 | 
			
		||||
             * Callback processing: register one global callback for all group object.
 | 
			
		||||
             * The registered callback will be called if any group object was changed from the bus.
 | 
			
		||||
@ -257,10 +478,83 @@ namespace Knx
 | 
			
		||||
            ComFlag _commFlag : 7;
 | 
			
		||||
            uint8_t* _data = 0;
 | 
			
		||||
            uint8_t _dataLength = 0;
 | 
			
		||||
#ifndef SMALL_GROUPOBJECT
 | 
			
		||||
            Dpt _datapointType;
 | 
			
		||||
#endif
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
    bool operator==(const GroupObject& lhs, const GroupObject& rhs);
 | 
			
		||||
 | 
			
		||||
    template<class DPT> void GroupObject::value(const DPT& value)
 | 
			
		||||
    {
 | 
			
		||||
        valueNoSend(value);
 | 
			
		||||
        objectWritten();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    template<class DPT> DPT GroupObject::value()
 | 
			
		||||
    {
 | 
			
		||||
        DPT dpt;
 | 
			
		||||
 | 
			
		||||
        if (dpt.size() != sizeCode())
 | 
			
		||||
            return dpt;
 | 
			
		||||
 | 
			
		||||
        dpt.decode(_data);
 | 
			
		||||
        return dpt;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    template<class DPT> bool GroupObject::tryValue(const DPT& value)
 | 
			
		||||
    {
 | 
			
		||||
        if (value.size() != sizeCode())
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        value.decode(_data);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    template<class DPT> void GroupObject::valueNoSend(const DPT& value)
 | 
			
		||||
    {
 | 
			
		||||
        if (value.size() != sizeCode())
 | 
			
		||||
            return;
 | 
			
		||||
 | 
			
		||||
        if (_uninitialized)
 | 
			
		||||
            commFlag(Ok);
 | 
			
		||||
 | 
			
		||||
        value.encode(_data);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    template<class DPT> bool GroupObject::valueNoSendCompare(const DPT& value)
 | 
			
		||||
    {
 | 
			
		||||
        if (value.size() != sizeCode())
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        if (_uninitialized)
 | 
			
		||||
        {
 | 
			
		||||
            // always set first value
 | 
			
		||||
            this->valueNoSend(value);
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
        else
 | 
			
		||||
        {
 | 
			
		||||
            // convert new value to given dtp
 | 
			
		||||
            uint8_t newData[_dataLength];
 | 
			
		||||
            memset(newData, 0, _dataLength);
 | 
			
		||||
            value.encode(newData);
 | 
			
		||||
 | 
			
		||||
            // check for change in converted value / update value on change only
 | 
			
		||||
            const bool dataChanged = memcmp(_data, newData, _dataLength);
 | 
			
		||||
 | 
			
		||||
            if (dataChanged)
 | 
			
		||||
                memcpy(_data, newData, _dataLength);
 | 
			
		||||
 | 
			
		||||
            return dataChanged;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    template<class DPT> bool GroupObject::valueCompare(const DPT& value)
 | 
			
		||||
    {
 | 
			
		||||
        if (valueNoSendCompare(value))
 | 
			
		||||
        {
 | 
			
		||||
            objectWritten();
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return false;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@ -1,6 +1,6 @@
 | 
			
		||||
#include "application_program_object.h"
 | 
			
		||||
 | 
			
		||||
#include "../group_object/dptconvert.h"
 | 
			
		||||
#include "../group_object/dpt/dptconvert.h"
 | 
			
		||||
#include "../util/logger.h"
 | 
			
		||||
#include "../bits.h"
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
@ -33,8 +33,8 @@ namespace Knx
 | 
			
		||||
    {
 | 
			
		||||
        public:
 | 
			
		||||
            enum LogType { Info, Warning, Error, Critical, Exception, Disabled};
 | 
			
		||||
            static Logger& logger(const loggername_t name);
 | 
			
		||||
            static void logLevel(const loggername_t name, LogType level);
 | 
			
		||||
            static Logger& logger(loggername_t name);
 | 
			
		||||
            static void logLevel(loggername_t name, LogType level);
 | 
			
		||||
            void info(const char* message, IPrintable& object)
 | 
			
		||||
            {
 | 
			
		||||
                if (!log(LogType::Info))
 | 
			
		||||
 | 
			
		||||
		Loading…
	
		Reference in New Issue
	
	Block a user