]> git.basschouten.com Git - openhab-addons.git/blob
0f6768f2c4562419a74f9d4ff91258cb236c0997
[openhab-addons.git] /
1 /**
2  * Copyright (c) 2010-2023 Contributors to the openHAB project
3  *
4  * See the NOTICE file(s) distributed with this work for additional
5  * information.
6  *
7  * This program and the accompanying materials are made available under the
8  * terms of the Eclipse Public License 2.0 which is available at
9  * http://www.eclipse.org/legal/epl-2.0
10  *
11  * SPDX-License-Identifier: EPL-2.0
12  */
13 package org.openhab.binding.paradoxalarm.internal.util;
14
15 import java.io.ByteArrayOutputStream;
16 import java.io.IOException;
17 import java.nio.ByteBuffer;
18 import java.nio.ByteOrder;
19 import java.nio.charset.StandardCharsets;
20
21 import org.slf4j.Logger;
22 import org.slf4j.LoggerFactory;
23
24 /**
25  * The {@link ParadoxUtil} Utility class for different calculations / manipulations of data in the model and
26  * communicators.
27  *
28  * @author Konstantin Polihronov - Initial contribution
29  */
30 public class ParadoxUtil {
31
32     private static final String SPACE_DELIMITER = " ";
33     private static final Logger logger = LoggerFactory.getLogger(ParadoxUtil.class);
34
35     public static byte calculateChecksum(byte[] payload) {
36         int result = 0;
37         for (byte everyByte : payload) {
38             result += everyByte;
39         }
40
41         return (byte) (result % 256);
42     }
43
44     public static byte getBit(int value, int bitNumber) {
45         return (byte) ((value >> bitNumber) & 1);
46     }
47
48     public static boolean isBitSet(int value, int bitNumber) {
49         return ((value >> bitNumber) & 1) == 1;
50     }
51
52     public static void printPacket(String description, byte[] array) {
53         if (logger.isTraceEnabled()) {
54             logger.trace("Packet payload size: {}", array[1]);
55             printByteArray(description, array, array[1] + 16);
56         }
57     }
58
59     public static void printByteArray(String description, byte[] array) {
60         if (array == null) {
61             logger.trace("Array is null");
62             return;
63         }
64         printByteArray(description, array, array.length);
65     }
66
67     public static void printByteArray(String description, byte[] array, int length) {
68         if (!logger.isTraceEnabled()) {
69             return;
70         }
71
72         String result = byteArrayToString(array, length);
73         if (!result.isEmpty()) {
74             logger.trace("{}", description + SPACE_DELIMITER + result);
75         }
76     }
77
78     public static String byteArrayToString(byte[] array) {
79         return byteArrayToString(array, array.length);
80     }
81
82     /**
83      *
84      * Returns passed array as HEX string. On every 8 bytes we put space for better readability. Example 16
85      * bytes array output: AA47000263000000 03EE00EEEEEEB727
86      *
87      * @param array
88      * @param length
89      * @return String
90      */
91     public static String byteArrayToString(byte[] array, int length) {
92         if (array == null) {
93             throw new IllegalArgumentException("Array must not be null.");
94         }
95         if (length > array.length) {
96             throw new IllegalArgumentException("Length should be lower than or equal to array length. Length=" + length
97                     + ". Array length=" + array.length);
98         }
99         StringBuilder sb = new StringBuilder();
100         for (int i = 0; i < length; i++) {
101             if (i != 0 && i % 8 == 0) {
102                 sb.append(SPACE_DELIMITER);
103             }
104             sb.append(String.format("%02X", array[i]));
105         }
106         return sb.toString();
107     }
108
109     public static byte setBit(byte byteValue, int i, int j) {
110         if (j == 1) {
111             return (byte) (byteValue | (1 << i));
112         } else {
113             return (byte) (byteValue & ~(1 << i));
114         }
115     }
116
117     public static byte getHighNibble(byte value) {
118         return (byte) ((value & 0xF0) >> 4);
119     }
120
121     public static byte getLowNibble(byte value) {
122         return (byte) (value & 0x0F);
123     }
124
125     public static byte[] mergeByteArrays(byte[]... arrays) {
126         try {
127             ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
128             for (byte[] array : arrays) {
129                 outputStream.write(array);
130             }
131             byte[] byteArray = outputStream.toByteArray();
132             return byteArray;
133         } catch (IOException e) {
134             logger.warn("Exception merging arrays:", e);
135             return new byte[0];
136         }
137     }
138
139     public static byte[] intToByteArray(int value) {
140         return ByteBuffer.allocate(Integer.SIZE / Byte.SIZE).order(ByteOrder.BIG_ENDIAN).putInt(value).array();
141     }
142
143     public static byte[] shortToByteArray(short value) {
144         return ByteBuffer.allocate(Short.SIZE / Byte.SIZE).order(ByteOrder.BIG_ENDIAN).putShort(value).array();
145     }
146
147     public static byte[] stringToBCD(String pcPassword) {
148         return stringToBCD(pcPassword, 4);
149     }
150
151     public static byte[] stringToBCD(String pcPassword, int numberOfDigits) {
152         byte[] result = new byte[numberOfDigits / 2];
153         for (int i = 0, j = 0; i < 2; i++, j += 2) {
154             String substring = pcPassword.substring(j, j + 1);
155             int parseInt = Integer.parseInt(substring);
156             result[i] = (byte) ((parseInt & 0x0F) << 4);
157
158             substring = pcPassword.substring(j + 1, j + 2);
159             parseInt = Integer.parseInt(substring);
160             result[i] |= (byte) (parseInt & 0x0F);
161         }
162         return result;
163     }
164
165     /**
166      * This method fills array with 0xEE based on rate.
167      * Example: If input array length is 5 and rate is 8 the array will be extended with 3 more bytes filled with 0xEE
168      *
169      * @param inputArray
170      * @param rate
171      * @return byte[]
172      */
173     public static byte[] extendArray(byte[] inputArray, int rate) {
174         if (inputArray == null || inputArray.length % rate == 0) {
175             return inputArray;
176         }
177
178         final int newLength = inputArray.length + (rate - inputArray.length % rate);
179         byte[] result = new byte[newLength];
180         for (int i = 0; i < result.length; i++) {
181             if (i < inputArray.length) {
182                 result[i] = inputArray[i];
183             } else {
184                 result[i] = (byte) 0xEE;
185             }
186         }
187         return result;
188     }
189
190     /**
191      * Returns bytes from string with standard US_ASCII standard charset to ensure everywhere in the binding we use same
192      * charset.
193      *
194      * @param str
195      * @return byte[]
196      *
197      */
198     public static byte[] getBytesFromString(String str) {
199         if (str == null) {
200             throw new IllegalArgumentException("String must not be null !");
201         }
202
203         return str.getBytes(StandardCharsets.US_ASCII);
204     }
205
206     public static int[] toIntArray(byte[] input) {
207         if (input == null) {
208             throw new IllegalArgumentException("Input array must not be null");
209         }
210         int[] result = new int[input.length];
211         for (int i = 0; i < input.length; i++) {
212             result[i] = input[i] & 0xFF;
213         }
214
215         return result;
216     }
217
218     public static byte[] toByteArray(int[] input) {
219         if (input == null) {
220             throw new IllegalArgumentException("Input array must not be null");
221         }
222         byte[] result = new byte[input.length];
223         for (int i = 0; i < input.length; i++) {
224             result[i] = (byte) (input[i]);
225         }
226
227         return result;
228     }
229 }