mirror of
				https://github.com/thelsing/knx.git
				synced 2025-10-26 10:26:25 +01:00 
			
		
		
		
	first working version
This commit is contained in:
		
							parent
							
								
									96f8a1bffb
								
							
						
					
					
						commit
						c0c6c99315
					
				
							
								
								
									
										20
									
								
								apdu.cpp
									
									
									
									
									
								
							
							
						
						
									
										20
									
								
								apdu.cpp
									
									
									
									
									
								
							@ -40,14 +40,14 @@ uint8_t APDU::length() const
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
void APDU::printPDU()
 | 
					void APDU::printPDU()
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
    //Print.print("APDU: ");
 | 
					    _print("APDU: ");
 | 
				
			||||||
    //print.print(type(), HEX, 4);
 | 
					    _print(type(), HEX);
 | 
				
			||||||
    //print.print("  ");
 | 
					    _print("  ");
 | 
				
			||||||
    //print.print(_data[0] & 0x3, HEX, 2);
 | 
					    _print(_data[0] & 0x3, HEX);
 | 
				
			||||||
    //for (uint8_t i = 1; i < length() + 1; ++i)
 | 
					    for (uint8_t i = 1; i < length() + 1; ++i)
 | 
				
			||||||
    //{
 | 
					    {
 | 
				
			||||||
    //    if (i) print.print(" ");
 | 
					        if (i) _print(" ");
 | 
				
			||||||
    //    print.print(_data[i], HEX, 2);
 | 
					        _print(_data[i], HEX);
 | 
				
			||||||
    //}
 | 
					    }
 | 
				
			||||||
    //print.println();
 | 
					    _println();
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										11
									
								
								bits.cpp
									
									
									
									
									
								
							
							
						
						
									
										11
									
								
								bits.cpp
									
									
									
									
									
								
							@ -7,6 +7,17 @@ uint8_t* popByte(uint8_t& b, uint8_t* data)
 | 
				
			|||||||
    return data;
 | 
					    return data;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void printHex(const char* suffix, const uint8_t *data, size_t length)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
					    _print(suffix);
 | 
				
			||||||
 | 
					    for (int i = 0; i < length; i++) {
 | 
				
			||||||
 | 
					        if (data[i] < 0x10) { _print("0"); }
 | 
				
			||||||
 | 
					        _print(data[i], HEX);
 | 
				
			||||||
 | 
					        _print(" ");
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					    _println();
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
uint8_t* popWord(uint16_t& w, uint8_t* data)
 | 
					uint8_t* popWord(uint16_t& w, uint8_t* data)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
    w = getWord(data);
 | 
					    w = getWord(data);
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										3
									
								
								bits.h
									
									
									
									
									
								
							
							
						
						
									
										3
									
								
								bits.h
									
									
									
									
									
								
							@ -9,7 +9,7 @@
 | 
				
			|||||||
#define bitRead(val, bitno) (((val) >> (bitno)) & 1)
 | 
					#define bitRead(val, bitno) (((val) >> (bitno)) & 1)
 | 
				
			||||||
#elif ARDUINO_ARCH_SAMD
 | 
					#elif ARDUINO_ARCH_SAMD
 | 
				
			||||||
#include <Arduino.h>
 | 
					#include <Arduino.h>
 | 
				
			||||||
#define htons(x) ( ((x)<<8) | (((x)>>8)&0xFF) )
 | 
					#define htons(x) ( (((x)<<8)&0xFF00) | (((x)>>8)&0xFF) )
 | 
				
			||||||
#define ntohs(x) htons(x)
 | 
					#define ntohs(x) htons(x)
 | 
				
			||||||
#define htonl(x) ( ((x)<<24 & 0xFF000000UL) | \
 | 
					#define htonl(x) ( ((x)<<24 & 0xFF000000UL) | \
 | 
				
			||||||
                   ((x)<< 8 & 0x00FF0000UL) | \
 | 
					                   ((x)<< 8 & 0x00FF0000UL) | \
 | 
				
			||||||
@ -36,3 +36,4 @@ uint8_t* pushInt(uint32_t i, uint8_t* data);
 | 
				
			|||||||
uint8_t* pushByteArray(const uint8_t* src, uint32_t size, uint8_t* data);
 | 
					uint8_t* pushByteArray(const uint8_t* src, uint32_t size, uint8_t* data);
 | 
				
			||||||
uint16_t getWord(uint8_t* data);
 | 
					uint16_t getWord(uint8_t* data);
 | 
				
			||||||
uint32_t getInt(uint8_t* data);
 | 
					uint32_t getInt(uint8_t* data);
 | 
				
			||||||
 | 
					void printHex(const char* suffix, const uint8_t *data, size_t length);
 | 
				
			||||||
@ -71,13 +71,14 @@ uint16_t CemiFrame::telegramLengthtTP() const
 | 
				
			|||||||
void CemiFrame::fillTelegramTP(uint8_t* data)
 | 
					void CemiFrame::fillTelegramTP(uint8_t* data)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
    uint16_t len = telegramLengthtTP();
 | 
					    uint16_t len = telegramLengthtTP();
 | 
				
			||||||
 | 
					    
 | 
				
			||||||
    if (frameType() == StandardFrame)
 | 
					    if (frameType() == StandardFrame)
 | 
				
			||||||
    {
 | 
					    {
 | 
				
			||||||
        uint8_t octet5 = (_ctrl1[1] & 0xF0) | (_ctrl1[6] & 0x0F);
 | 
					        uint8_t octet5 = (_ctrl1[1] & 0xF0) | (_ctrl1[6] & 0x0F);
 | 
				
			||||||
        data[0] = _ctrl1[0]; //CTRL
 | 
					        data[0] = _ctrl1[0]; //CTRL
 | 
				
			||||||
        memcpy(data + 1, _ctrl1 + 2, 4); // SA, DA
 | 
					        memcpy(data + 1, _ctrl1 + 2, 4); // SA, DA
 | 
				
			||||||
        data[5] = octet5; // LEN; Hopcount, ..
 | 
					        data[5] = octet5; // LEN; Hopcount, ..
 | 
				
			||||||
        memcpy(data + 6, _ctrl1 + 8, len - 7); // APDU
 | 
					        memcpy(data + 6, _ctrl1 + 7, len - 7); // APDU
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
    else
 | 
					    else
 | 
				
			||||||
    {
 | 
					    {
 | 
				
			||||||
 | 
				
			|||||||
@ -50,7 +50,7 @@ void DataLinkLayer::frameRecieved(CemiFrame& frame)
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
//        if (frame.npdu().octetCount() > 0)
 | 
					//        if (frame.npdu().octetCount() > 0)
 | 
				
			||||||
//        {
 | 
					//        {
 | 
				
			||||||
        //    print.print("<- DLL ");
 | 
					//            _print("-> DLL ");
 | 
				
			||||||
//            frame.apdu().printPDU();
 | 
					//            frame.apdu().printPDU();
 | 
				
			||||||
//        }
 | 
					//        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -82,7 +82,7 @@ bool DataLinkLayer::sendTelegram(NPDU & npdu, AckType ack, uint16_t destinationA
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
//    if (frame.npdu().octetCount() > 0)
 | 
					//    if (frame.npdu().octetCount() > 0)
 | 
				
			||||||
//    {
 | 
					//    {
 | 
				
			||||||
    //    print.print("-> DLL ");
 | 
					//        _print("<- DLL ");
 | 
				
			||||||
//        frame.apdu().printPDU();
 | 
					//        frame.apdu().printPDU();
 | 
				
			||||||
//    }
 | 
					//    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
				
			|||||||
@ -33,7 +33,7 @@
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
//knx transmit data commands
 | 
					//knx transmit data commands
 | 
				
			||||||
#define U_L_DATA_START_CONT_REQ 0x80 //-0xBF
 | 
					#define U_L_DATA_START_CONT_REQ 0x80 //-0xBF
 | 
				
			||||||
#define U_L_DATA_END_REQ        0x47 //-0x7F
 | 
					#define U_L_DATA_END_REQ        0x40 //-0x7F
 | 
				
			||||||
 | 
					
 | 
				
			||||||
//serices to host controller
 | 
					//serices to host controller
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -99,8 +99,6 @@ void TpUartDataLinkLayer::stopChip()
 | 
				
			|||||||
#endif
 | 
					#endif
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void printHex(const char* suffix, const uint8_t *data, size_t length);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
TpUartDataLinkLayer::TpUartDataLinkLayer(DeviceObject& devObj, AddressTableObject& addrTab,
 | 
					TpUartDataLinkLayer::TpUartDataLinkLayer(DeviceObject& devObj, AddressTableObject& addrTab,
 | 
				
			||||||
    NetworkLayer& layer, Platform& platform) : DataLinkLayer(devObj, addrTab, layer, platform)
 | 
					    NetworkLayer& layer, Platform& platform) : DataLinkLayer(devObj, addrTab, layer, platform)
 | 
				
			||||||
@ -184,7 +182,10 @@ bool TpUartDataLinkLayer::checkDataInd(uint8_t firstByte)
 | 
				
			|||||||
        return false;
 | 
					        return false;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    int len = 0;
 | 
					    int len = 0;
 | 
				
			||||||
    uint8_t buffer[bufferSize];
 | 
					    uint8_t cemiBuffer[bufferSize + 2];
 | 
				
			||||||
 | 
					    cemiBuffer[0] = 0x29;
 | 
				
			||||||
 | 
					    cemiBuffer[1] = 0;
 | 
				
			||||||
 | 
					    uint8_t* buffer = cemiBuffer + 2;
 | 
				
			||||||
    buffer[0] = firstByte;
 | 
					    buffer[0] = firstByte;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    uint8_t payloadLength = 0;
 | 
					    uint8_t payloadLength = 0;
 | 
				
			||||||
@ -192,11 +193,9 @@ bool TpUartDataLinkLayer::checkDataInd(uint8_t firstByte)
 | 
				
			|||||||
    {
 | 
					    {
 | 
				
			||||||
        //convert to extended frame format
 | 
					        //convert to extended frame format
 | 
				
			||||||
        _platform.readBytesUart(buffer + 2, 5);
 | 
					        _platform.readBytesUart(buffer + 2, 5);
 | 
				
			||||||
 | 
					        sendAck((AddressType)(buffer[6] & GroupAddress), getWord(buffer + 4));
 | 
				
			||||||
        payloadLength = buffer[6] & 0xF;
 | 
					        payloadLength = buffer[6] & 0xF;
 | 
				
			||||||
        _platform.readBytesUart(buffer + 7, payloadLength + 2); //+1 for TCPI +1 for CRC
 | 
					        _platform.readBytesUart(buffer + 7, payloadLength + 2); //+1 for TCPI +1 for CRC
 | 
				
			||||||
        printHex("->", buffer, 1);
 | 
					 | 
				
			||||||
        printHex("->", buffer + 2, 5);
 | 
					 | 
				
			||||||
        printHex("->", buffer + 7, payloadLength + 3);
 | 
					 | 
				
			||||||
        buffer[1] = buffer[6] & 0xF0;
 | 
					        buffer[1] = buffer[6] & 0xF0;
 | 
				
			||||||
        buffer[6] = payloadLength;
 | 
					        buffer[6] = payloadLength;
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
@ -204,29 +203,15 @@ bool TpUartDataLinkLayer::checkDataInd(uint8_t firstByte)
 | 
				
			|||||||
    {
 | 
					    {
 | 
				
			||||||
        //extended frame
 | 
					        //extended frame
 | 
				
			||||||
        _platform.readBytesUart(buffer + 1, 6);
 | 
					        _platform.readBytesUart(buffer + 1, 6);
 | 
				
			||||||
 | 
					        sendAck((AddressType)(buffer[1] & GroupAddress), getWord(buffer + 4));
 | 
				
			||||||
        payloadLength = buffer[6];
 | 
					        payloadLength = buffer[6];
 | 
				
			||||||
        _platform.readBytesUart(buffer + 7, payloadLength + 2); //+1 for TCPI +1 for CRC
 | 
					        _platform.readBytesUart(buffer + 7, payloadLength + 2); //+1 for TCPI +1 for CRC
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
    len = payloadLength + 9;
 | 
					    len = payloadLength + 9;
 | 
				
			||||||
    
 | 
					    
 | 
				
			||||||
    printHex("=>", buffer, len);
 | 
					 | 
				
			||||||
    CemiFrame frame(buffer, len);
 | 
					 | 
				
			||||||
    
 | 
					 | 
				
			||||||
    if (frame.addressType() == InduvidualAddress &&  _deviceObject.induvidualAddress() == frame.destinationAddress()
 | 
					 | 
				
			||||||
        || frame.addressType() == GroupAddress &&  _groupAddressTable.contains(frame.destinationAddress()))
 | 
					 | 
				
			||||||
    {
 | 
					 | 
				
			||||||
        //send ack. 
 | 
					 | 
				
			||||||
        _platform.writeUart(U_ACK_REQ + 1);
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
    else
 | 
					 | 
				
			||||||
    {
 | 
					 | 
				
			||||||
        // send not addressed
 | 
					 | 
				
			||||||
        _platform.writeUart(U_ACK_REQ);
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
    
 | 
					 | 
				
			||||||
    
 | 
					    
 | 
				
			||||||
    const uint8_t queueLength = 5;
 | 
					    const uint8_t queueLength = 5;
 | 
				
			||||||
    static uint8_t buffers[queueLength][bufferSize];
 | 
					    static uint8_t buffers[queueLength][bufferSize + 2];
 | 
				
			||||||
    static uint16_t bufferLengths[queueLength];
 | 
					    static uint16_t bufferLengths[queueLength];
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    if (_sendBuffer != 0)
 | 
					    if (_sendBuffer != 0)
 | 
				
			||||||
@ -253,7 +238,7 @@ bool TpUartDataLinkLayer::checkDataInd(uint8_t firstByte)
 | 
				
			|||||||
                continue;
 | 
					                continue;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
            bufferLengths[i] = len;
 | 
					            bufferLengths[i] = len;
 | 
				
			||||||
            memcpy(&buffers[i][0], buffer, len);
 | 
					            memcpy(&buffers[i][0], cemiBuffer, len + 2);
 | 
				
			||||||
            break;
 | 
					            break;
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
@ -265,11 +250,11 @@ bool TpUartDataLinkLayer::checkDataInd(uint8_t firstByte)
 | 
				
			|||||||
            if (bufferLengths[i] == 0)
 | 
					            if (bufferLengths[i] == 0)
 | 
				
			||||||
                break;
 | 
					                break;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
            frameBytesReceived(&buffers[i][0], bufferLengths[i]);
 | 
					            frameBytesReceived(&buffers[i][0], bufferLengths[i]+2);
 | 
				
			||||||
            bufferLengths[i] = 0;
 | 
					            bufferLengths[i] = 0;
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        frameBytesReceived(buffer, len);
 | 
					        frameBytesReceived(cemiBuffer, len+2);
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    return true;
 | 
					    return true;
 | 
				
			||||||
@ -277,6 +262,7 @@ bool TpUartDataLinkLayer::checkDataInd(uint8_t firstByte)
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
void TpUartDataLinkLayer::frameBytesReceived(uint8_t* buffer, uint16_t length)
 | 
					void TpUartDataLinkLayer::frameBytesReceived(uint8_t* buffer, uint16_t length)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
 | 
					    //printHex("=>", buffer, length);
 | 
				
			||||||
    CemiFrame frame(buffer, length);
 | 
					    CemiFrame frame(buffer, length);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    frameRecieved(frame);
 | 
					    frameRecieved(frame);
 | 
				
			||||||
@ -416,7 +402,8 @@ void TpUartDataLinkLayer::enabled(bool value)
 | 
				
			|||||||
    if (value && !_enabled)
 | 
					    if (value && !_enabled)
 | 
				
			||||||
    {
 | 
					    {
 | 
				
			||||||
        _platform.setupUart();
 | 
					        _platform.setupUart();
 | 
				
			||||||
 | 
					        _print("ownaddr ");
 | 
				
			||||||
 | 
					        _println(_deviceObject.induvidualAddress(), HEX);
 | 
				
			||||||
        resetChip();
 | 
					        resetChip();
 | 
				
			||||||
        _enabled = true;
 | 
					        _enabled = true;
 | 
				
			||||||
        return;
 | 
					        return;
 | 
				
			||||||
@ -439,21 +426,43 @@ bool TpUartDataLinkLayer::enabled() const
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
void TpUartDataLinkLayer::sendBytes(uint8_t* bytes, uint16_t length)
 | 
					void TpUartDataLinkLayer::sendBytes(uint8_t* bytes, uint16_t length)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
 | 
					    //printHex("<=", bytes, length);
 | 
				
			||||||
    uint8_t cmd[2];
 | 
					    uint8_t cmd[2];
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    uint8_t oldIdx = 0;
 | 
				
			||||||
 | 
					        
 | 
				
			||||||
    for (int i = 0; i < length; i++)
 | 
					    for (int i = 0; i < length; i++)
 | 
				
			||||||
    {
 | 
					    {
 | 
				
			||||||
        uint8_t idx = length / 64;
 | 
					        uint8_t idx = length / 64;
 | 
				
			||||||
 | 
					        if (idx != oldIdx)
 | 
				
			||||||
 | 
					        {
 | 
				
			||||||
 | 
					            oldIdx = idx;
 | 
				
			||||||
            cmd[0] = U_L_DATA_OFFSET_REQ | idx;
 | 
					            cmd[0] = U_L_DATA_OFFSET_REQ | idx;
 | 
				
			||||||
            _platform.writeUart(cmd, 1);
 | 
					            _platform.writeUart(cmd, 1);
 | 
				
			||||||
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        if (i != length - 1)
 | 
					        if (i != length - 1)
 | 
				
			||||||
            cmd[0] = U_L_DATA_START_CONT_REQ | i;
 | 
					            cmd[0] = U_L_DATA_START_CONT_REQ | i;
 | 
				
			||||||
        else
 | 
					        else
 | 
				
			||||||
            cmd[0] = U_L_DATA_END_REQ;
 | 
					            cmd[0] = U_L_DATA_END_REQ | i;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        cmd[1] = bytes[i];
 | 
					        cmd[1] = bytes[i];
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        _platform.writeUart(cmd, 2);
 | 
					        _platform.writeUart(cmd, 2);
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void TpUartDataLinkLayer::sendAck(AddressType type, uint16_t address)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
					    if ( (type == InduvidualAddress &&  _deviceObject.induvidualAddress() == address) 
 | 
				
			||||||
 | 
					      || (type == GroupAddress &&  (_groupAddressTable.contains(address) || address == 0)))
 | 
				
			||||||
 | 
					    {
 | 
				
			||||||
 | 
					        //send ack. 
 | 
				
			||||||
 | 
					        _platform.writeUart(U_ACK_REQ + 1);
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					    else
 | 
				
			||||||
 | 
					    {
 | 
				
			||||||
 | 
					        // send not addressed
 | 
				
			||||||
 | 
					        _platform.writeUart(U_ACK_REQ);
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
				
			|||||||
@ -37,4 +37,5 @@ private:
 | 
				
			|||||||
    void frameBytesReceived(uint8_t* buffer, uint16_t length);
 | 
					    void frameBytesReceived(uint8_t* buffer, uint16_t length);
 | 
				
			||||||
    void resetChip();
 | 
					    void resetChip();
 | 
				
			||||||
    void stopChip();
 | 
					    void stopChip();
 | 
				
			||||||
 | 
					    void sendAck(AddressType type, uint16_t address);
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
		Loading…
	
		Reference in New Issue
	
	Block a user