broken out from uci-utils into it's own repository. fixed issues with PLC conversion of multiple bytes and big/little endian
commit
80b50b3b9a
|
@ -0,0 +1,37 @@
|
|||
module.exports = {
|
||||
"ecmaFeatures": {
|
||||
"modules": true,
|
||||
"spread" : true,
|
||||
"restParams" : true
|
||||
},
|
||||
// "plugins": [
|
||||
// "unicorn"
|
||||
// ],
|
||||
"env": {
|
||||
"es6": true,
|
||||
"node": true,
|
||||
"mocha": true
|
||||
},
|
||||
"parserOptions": {
|
||||
"ecmaVersion": 2017,
|
||||
"sourceType": "module"
|
||||
},
|
||||
"extends": "eslint:recommended",
|
||||
"rules": {
|
||||
"indent": [
|
||||
"error",
|
||||
2
|
||||
],
|
||||
// "unicorn/no-array-instanceof": "error",
|
||||
"no-console": 0,
|
||||
"semi": ["error", "never"],
|
||||
"linebreak-style": [
|
||||
"error",
|
||||
"unix"
|
||||
],
|
||||
"quotes": [
|
||||
"error",
|
||||
"single"
|
||||
]
|
||||
}
|
||||
}
|
|
@ -0,0 +1,2 @@
|
|||
/node_modules/
|
||||
/coverage/
|
|
@ -0,0 +1,4 @@
|
|||
tests/
|
||||
test/
|
||||
*.test.js
|
||||
testing/
|
|
@ -0,0 +1,39 @@
|
|||
{
|
||||
"name": "@uci-utils/byte",
|
||||
"version": "0.2.0",
|
||||
"description": "Byte Class and related functions",
|
||||
"main": "src/byte.js",
|
||||
"scripts": {
|
||||
"test": "./node_modules/.bin/mocha -r esm --timeout 30000",
|
||||
"testd": "UCI_ENV=dev ./node_modules/.bin/nodemon --exec './node_modules/.bin/mocha -r esm --timeout 30000' || exit 0",
|
||||
"testdd": "UCI_LOG_LEVEL='trace' npm run testd",
|
||||
"testde": "UCI_LOG_LEVEL='warn' npm run testd",
|
||||
"testl": "UCI_ENV=pro UCI_LOG_PATH=./test/test.log 0 npm run test || exit 0"
|
||||
},
|
||||
"author": "David Kebler",
|
||||
"license": "MIT",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "git+https://github.com/uCOMmandIt/uci-utils.git"
|
||||
},
|
||||
"keywords": [
|
||||
"node.js",
|
||||
"communication",
|
||||
"serial",
|
||||
"utilities",
|
||||
"helpers"
|
||||
],
|
||||
"bugs": {
|
||||
"url": "https://github.com/uCOMmandIt/uci-utils/issues"
|
||||
},
|
||||
"homepage": "https://github.com/uCOMmandIt/uci-utils#readme",
|
||||
"dependencies": {
|
||||
"bitwise": "^2.0.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"chai": "^4.2.0",
|
||||
"esm": "^3.2.4",
|
||||
"mocha": "^5.2.0",
|
||||
"nodemon": "^1.18.10"
|
||||
}
|
||||
}
|
|
@ -0,0 +1,2 @@
|
|||
### Byte Me
|
||||
#### a uCOMmandIt Byte Class and Utility Functions
|
|
@ -0,0 +1,51 @@
|
|||
// example jsdoc syntax
|
||||
// // -----------------------------------
|
||||
// // Values
|
||||
//
|
||||
// /**
|
||||
// * Get the object type string
|
||||
// * @param {any} value
|
||||
// * @returns {string}
|
||||
// */
|
||||
// function getObjectType (value /* :mixed */) /* :string */ {
|
||||
// return Object.prototype.toString.call(value)
|
||||
// }
|
||||
|
||||
function flatten(array) {
|
||||
const flatten = arr => arr.reduce((a, b) => a.concat(Array.isArray(b) ? flatten(b) : b), [])
|
||||
return flatten(array)
|
||||
}
|
||||
|
||||
function sum(arr) {
|
||||
return arr.reduce(function (a, b) {
|
||||
return a + b
|
||||
})
|
||||
}
|
||||
|
||||
function padStart (arr, len, c) {
|
||||
len = len || 8
|
||||
c = c || 0
|
||||
if (len < arr.length) {
|
||||
return false
|
||||
}
|
||||
let pad = len - arr.length
|
||||
for (var i = 0; i < pad; i++) {
|
||||
arr.unshift(c)
|
||||
}
|
||||
return arr
|
||||
}
|
||||
|
||||
function padEnd (arr, len, c) {
|
||||
len = len || 8
|
||||
c = c || 0
|
||||
if (len < arr.length) {
|
||||
return false
|
||||
}
|
||||
let pad = len - arr.length
|
||||
for (var i = 0; i < pad; i++) {
|
||||
arr.push(c)
|
||||
}
|
||||
return arr
|
||||
}
|
||||
|
||||
export { flatten, sum, padStart, padEnd }
|
|
@ -0,0 +1,437 @@
|
|||
// third party modules
|
||||
import bits from 'bitwise/bits'
|
||||
import toBits from 'bitwise/string/to-bits'
|
||||
import readUInt from 'bitwise/buffer/read-u-int'
|
||||
import createBuffer from 'bitwise/buffer/create'
|
||||
import readByte from 'bitwise/byte/read'
|
||||
import writeByte from 'bitwise/byte/write'
|
||||
//local
|
||||
import * as array from './array'
|
||||
|
||||
// Classes
|
||||
|
||||
// Byte Class is a single byte value with an attached format designation which allows easy
|
||||
// conversion of the byte to any of the other formats
|
||||
// of ['STR', 'BUF', 'BUF', 'DEC', 'HEX', 'ARY', 'PLC'] like this
|
||||
// examples:
|
||||
// '1100101', 'STR' will be left padded to 8 chars with 0
|
||||
// Buffer.from([0x65]), 'BUF'
|
||||
// 101, 'DEC'
|
||||
// 65, 'HEX'
|
||||
// [1,1,0,0,1,0,1], 'ARY' will be left padded/unshifted to 8 elements, with 0
|
||||
// [7,3,1,6], 'PLC' any order, the number of the bit that is "on" or "1" from 1-8, 1=rightmost LSB
|
||||
|
||||
/**
|
||||
* Byte - A class to hold and manipulate a bitwise byte
|
||||
*/
|
||||
class Byte {
|
||||
/**
|
||||
* constructor - Description
|
||||
*
|
||||
* @param {number} [byte=0] Description
|
||||
* @param {string} [format=DEC] Description
|
||||
*
|
||||
* @returns {Object} instance of Byte Class
|
||||
*/
|
||||
|
||||
constructor(byte = 0, format = 'DEC') {
|
||||
this.cur = byte
|
||||
this.prv = byte
|
||||
this.format = format
|
||||
}
|
||||
|
||||
static validateFmt(fmt) {
|
||||
return ['STR', 'BUF', 'DEC', 'HEX', 'ARY', 'PLC'].indexOf(fmt) === -1
|
||||
? false
|
||||
: true
|
||||
}
|
||||
|
||||
// getter/setters
|
||||
get value() {
|
||||
return this.cur
|
||||
}
|
||||
set value(byte) {
|
||||
this.prv = this.cur
|
||||
this.cur = byte
|
||||
}
|
||||
|
||||
get fmt() {
|
||||
return this.format
|
||||
}
|
||||
|
||||
set fmt(f) {
|
||||
this.cur = this.toFmt(f)
|
||||
this.prv = byteFormat(this.prv, { in: this.format, out: f })
|
||||
this.format = f
|
||||
}
|
||||
|
||||
get prev() {
|
||||
return this.prv
|
||||
}
|
||||
|
||||
toFmt(fmt) {
|
||||
return byteFormat(this.cur, { in: this.format, out: fmt })
|
||||
}
|
||||
|
||||
toFmtPrev(fmt) {
|
||||
return byteFormat(this.prv, { in: this.format, out: fmt })
|
||||
}
|
||||
|
||||
reset(byte, fmt) {
|
||||
this.cur = byte
|
||||
this.prv = byte
|
||||
this.format = fmt ? fmt : 'DEC'
|
||||
}
|
||||
|
||||
// used for setting bytes when passed byte format needs to be adapted to current instance's format
|
||||
adaptFmt(byte, format) {
|
||||
return byteFormat(byte, { in: format, out: this.format })
|
||||
}
|
||||
|
||||
bwOp(byte, op, format = { in: 'DEC', out: 'DEC' }) {
|
||||
let bwop
|
||||
switch (op) {
|
||||
case 'toggle':
|
||||
bwop = bits.xor
|
||||
break
|
||||
case 'off': // NOT mask then AND which is not the same as NAND = AND then NOT result
|
||||
bwop = (byte, mask) => {
|
||||
return bits.and(byte, bits.not(mask))
|
||||
}
|
||||
break
|
||||
case 'on':
|
||||
bwop = bits.or
|
||||
break
|
||||
case 'check':
|
||||
bwop = bits.and
|
||||
break
|
||||
}
|
||||
// console.log('byte and state as passed', byte, this.value)
|
||||
let opbyte = bwop(
|
||||
this.toFmt('ARY'),
|
||||
byteFormat(byte, { in: format.in, out: 'ARY' })
|
||||
)
|
||||
return byteFormat(opbyte, { in: 'ARY', out: format.out })
|
||||
}
|
||||
|
||||
changes() {
|
||||
return bitChanges(this.toFmt('ARY'), this.toFmtPrev('ARY'))
|
||||
}
|
||||
|
||||
stateChanges() {
|
||||
return stateChanges(this.toFmt('ARY'), this.toFmtPrev('ARY'))
|
||||
}
|
||||
} // end Byte Class
|
||||
|
||||
// Library functions and objects
|
||||
|
||||
const BYTE_FORMATS = ['STR', 'BUF', 'DEC', 'HEX', 'ARY', 'PLC']
|
||||
|
||||
//can be used with the BYTE Class or stand alone if you supply by and fmt object
|
||||
//can accept single multiple byte input
|
||||
// multiple bytes stored in array with most significant byte with index 0
|
||||
function byteFormat(bytes, fmt) {
|
||||
// TODO support STR and ARY formats that a long string or single flat array rather than array of each
|
||||
|
||||
if (fmt.in === 'PLC') {
|
||||
bytes = plc2bytes(bytes)
|
||||
return byteFormat(bytes.length === 1 ? bytes[0] : bytes, {
|
||||
in: 'DEC',
|
||||
out: fmt.out
|
||||
})
|
||||
}
|
||||
|
||||
if (fmt.in === 'BUF') {
|
||||
bytes = buf2ary(bytes)
|
||||
return byteFormat(bytes.length === 1 ? bytes[0] : bytes, {
|
||||
in: 'DEC',
|
||||
out: fmt.out
|
||||
})
|
||||
}
|
||||
|
||||
// It's a single byte
|
||||
if (
|
||||
(fmt.in === 'ARY' && !Array.isArray(bytes[0])) ||
|
||||
(fmt.in !== 'ARY' && !Array.isArray(bytes))
|
||||
) {
|
||||
return format(bytes, fmt)
|
||||
}
|
||||
|
||||
// process multiple bytes
|
||||
|
||||
if (fmt.out === 'PLC') {
|
||||
return bytes2plc(byteFormat(bytes, { in: fmt.in, out: 'DEC' }))
|
||||
}
|
||||
if (fmt.out === 'BUF') {
|
||||
if (fmt.in !== 'DEC') {
|
||||
bytes = byteFormat(bytes, { in: fmt.in, out: 'DEC' })
|
||||
}
|
||||
return Buffer.from(bytes)
|
||||
}
|
||||
// everything else
|
||||
return bytes.map(byte => {
|
||||
return format(byte, fmt)
|
||||
})
|
||||
}
|
||||
|
||||
// curr and prev need to be arrays of bits as arrays ARY
|
||||
// returns changes if any otherwise false
|
||||
function bitChanges(curr, prev) {
|
||||
let changes = bits.xor(curr, prev)
|
||||
|
||||
// nothing changed
|
||||
if (!array.sum(changes)) {
|
||||
return false
|
||||
}
|
||||
// something changed
|
||||
return changes
|
||||
}
|
||||
|
||||
// all bit changes
|
||||
// changes and curr need to be an array of arrays of 8 bits/byte in ARY format
|
||||
// returns array of array pairs
|
||||
// where each pair is the bit that changed and it's current state (1=on,0=off)
|
||||
function stateChanges(curr, prev) {
|
||||
let bitchanges = bitChanges(curr, prev)
|
||||
if (!bitchanges) {
|
||||
return false
|
||||
}
|
||||
console.log(prev)
|
||||
console.log(curr)
|
||||
console.log(bitchanges)
|
||||
|
||||
let nowon = curr.map((bit, i) => {
|
||||
console.log(bit, bitchanges[i], bit & bitchanges[i])
|
||||
return bit & bitchanges[i]
|
||||
})
|
||||
nowon = byteFormat(nowon, {
|
||||
in: 'ARY',
|
||||
out: 'PLC'
|
||||
})
|
||||
|
||||
console.log('nowon', nowon)
|
||||
|
||||
return byteFormat(bitchanges, {
|
||||
in: 'ARY',
|
||||
out: 'PLC'
|
||||
}).map(swtch => {
|
||||
return [swtch, nowon.indexOf(swtch) === -1 ? 'off' : 'on']
|
||||
})
|
||||
}
|
||||
|
||||
function bitsReverse(byte) {
|
||||
// in DEC out DEC
|
||||
return writeByte(readByte(byte).reverse())
|
||||
}
|
||||
|
||||
// exports here
|
||||
export default Byte
|
||||
export { Byte, byteFormat, BYTE_FORMATS, bitsReverse, bitChanges, stateChanges }
|
||||
|
||||
|
||||
///////// module scoped not exported functions /////
|
||||
|
||||
/*
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*
|
||||
*/
|
||||
// Takes a SINGLE byte in one format and returns it in another,
|
||||
// byteFormat function above allows multiple bytes and uses this
|
||||
const format = function(byte, fmt) {
|
||||
let ifmt = fmt.in || 'STR' // default STR
|
||||
let ofmt = fmt.out || 'DEC' // default DEC
|
||||
// debug.L2('input: ', byte, ' input format: ', ifmt, ' output format:', ofmt);
|
||||
|
||||
let decimal = NaN
|
||||
switch (ifmt) {
|
||||
case 'STR':
|
||||
decimal = writeByte(toBits(byte.padStart(8,'0')))
|
||||
break
|
||||
case 'BUF':
|
||||
decimal = readUInt(byte, 0, 8)
|
||||
break
|
||||
case 'DEC':
|
||||
decimal = byte
|
||||
break
|
||||
case 'HEX':
|
||||
decimal = parseInt(byte, 16)
|
||||
break
|
||||
case 'ARY':
|
||||
decimal = writeByte(array.padStart(byte))
|
||||
break
|
||||
case 'PLC':
|
||||
decimal = plc2dec(byte)
|
||||
break
|
||||
default:
|
||||
ofmt = false
|
||||
break
|
||||
}
|
||||
|
||||
let output
|
||||
//TODO only BIT and DEC are working
|
||||
switch (ofmt) {
|
||||
case 'STR':
|
||||
output = bits.toString(readByte(decimal))
|
||||
break
|
||||
case 'BUF':
|
||||
output = createBuffer(readByte(decimal))
|
||||
break
|
||||
case 'DEC':
|
||||
output = decimal
|
||||
break
|
||||
case 'HEX':
|
||||
output = decimal.toString(16)
|
||||
break
|
||||
case 'ARY':
|
||||
output = readByte(decimal)
|
||||
break
|
||||
case 'PLC':
|
||||
output = dec2plc(decimal)
|
||||
break
|
||||
default:
|
||||
console.log('unknown input or output format')
|
||||
output = false
|
||||
break
|
||||
}
|
||||
|
||||
return output
|
||||
}
|
||||
|
||||
/*
|
||||
*
|
||||
*
|
||||
*
|
||||
*/
|
||||
function bytes2plc(bytes) {
|
||||
// bytes must be in 'DEC' format first
|
||||
|
||||
let plc = bytes.map((byte, bytenum) => {
|
||||
return format(byte, {
|
||||
in: 'DEC',
|
||||
out: 'PLC'
|
||||
}).map(cmpt => {
|
||||
return bytenum * 8 + cmpt
|
||||
})
|
||||
})
|
||||
|
||||
plc = plc.reduce(function(a, b) {
|
||||
// combine plc arrays
|
||||
return a.concat(b)
|
||||
}, [])
|
||||
plc.sort((a, b) => a - b)
|
||||
return plc
|
||||
}
|
||||
|
||||
/*
|
||||
*
|
||||
*
|
||||
*
|
||||
*/
|
||||
function plc2bytes(cmpts) {
|
||||
// cmpts is an array of bit numbers that can be of any value (beyond 8 ok)
|
||||
// returns an object of pairs, each pair a byte number (bank) and the value for that byte(bank) in
|
||||
// in 'DEC' format.
|
||||
|
||||
let UCI_ENDIAN = process.env.UCI_ENDIAN || 'little'
|
||||
|
||||
let byte = 0,
|
||||
cmpt = 0,
|
||||
maxbyte = 0,
|
||||
bytes = {}
|
||||
|
||||
for (let i in cmpts) {
|
||||
cmpt = cmpts[i]
|
||||
byte = Math.floor((cmpt - 1) / 8) + 1
|
||||
if (byte > maxbyte) {
|
||||
maxbyte = byte
|
||||
}
|
||||
if (bytes[byte] === undefined) {
|
||||
bytes[byte] = []
|
||||
}
|
||||
bytes[byte].push(cmpt % 8 === 0 ? 8 : cmpt % 8)
|
||||
}
|
||||
let bytearr = []
|
||||
// bytes index 0 with be least signficant, need to reverse that
|
||||
for (byte in bytes) {
|
||||
bytes[byte] = format(bytes[byte], {
|
||||
in: 'PLC',
|
||||
out: 'DEC'
|
||||
})
|
||||
if (UCI_ENDIAN==='little') bytearr[byte-1] = bytes[byte]
|
||||
else bytearr[maxbyte - byte] = bytes[byte]
|
||||
}
|
||||
|
||||
// pad in "zero" for missing byte elements
|
||||
for (let i = 0; i < maxbyte-1; i++) {
|
||||
if (!bytearr[i]) {
|
||||
bytearr[i] = 0
|
||||
}
|
||||
}
|
||||
// log.debug({places:cmpts, bytes:bytearr, endian:UCI_ENDIAN, msg:'plc to bytes conversion')
|
||||
return bytearr
|
||||
}
|
||||
|
||||
// can't just do split map because split doesn't work on single number
|
||||
function numStr2Arr(str, del) {
|
||||
del = del || ' ' //default delimimter is a space, see string.protoype.split
|
||||
// let arr = []
|
||||
// TODO change to single line
|
||||
if (typeof str === 'number') {
|
||||
// just a single number
|
||||
// arr[0] = parseInt(str, 10)
|
||||
// return arr;
|
||||
return parseInt(str, 10)
|
||||
} else {
|
||||
//it's a string of numbers
|
||||
return str.split(del).map(Number)
|
||||
}
|
||||
}
|
||||
|
||||
function bits2dec(bits) {
|
||||
let decimal = 0
|
||||
let place = bits.length
|
||||
bits.split('').forEach(function(bit) {
|
||||
decimal += Math.pow(2, bit * (place - 1))
|
||||
--place
|
||||
})
|
||||
return decimal
|
||||
}
|
||||
|
||||
function plc2dec(nums, string) {
|
||||
let decimal = 0
|
||||
// log.debug('nums', nums)
|
||||
|
||||
if (string) {
|
||||
nums = numStr2Arr(nums)
|
||||
}
|
||||
nums.forEach(function(num) {
|
||||
decimal += Math.pow(2, num - 1)
|
||||
// log.debug('place', num, 'dec ', decimal);
|
||||
})
|
||||
return decimal
|
||||
}
|
||||
|
||||
function dec2plc(decimal, toStr) {
|
||||
//outputs an array unless str is true
|
||||
let place = 8
|
||||
let plc = []
|
||||
readByte(decimal).forEach(function(bit) {
|
||||
if (bit) {
|
||||
plc.push(place)
|
||||
}
|
||||
--place
|
||||
})
|
||||
if (toStr) {
|
||||
return plc.join(' ')
|
||||
} else {
|
||||
return plc
|
||||
}
|
||||
}
|
||||
|
||||
function buf2ary(buf) {
|
||||
return Array.from(new Uint8Array(buf))
|
||||
}
|
|
@ -0,0 +1,47 @@
|
|||
let date = new Date(Date.now())
|
||||
console.log('run:', date.getMinutes(), ':', date.getSeconds())
|
||||
|
||||
import { expect } from 'chai'
|
||||
import * as _ from '../src/array'
|
||||
|
||||
|
||||
describe('Array Library - ', function () {
|
||||
|
||||
it('Should flatten an array', function () {
|
||||
expect(_.flatten([
|
||||
[1],
|
||||
[2],
|
||||
[3]
|
||||
])).deep.equal([1, 2, 3])
|
||||
expect(_.flatten([1, 2, 3])).deep.equal([1, 2, 3])
|
||||
})
|
||||
it('Should sum an array', function () {
|
||||
expect(_.sum([1, 2, 3])).to.equal(6)
|
||||
expect(_.sum([1, 'shut', 'up'])).to.equal('1shutup')
|
||||
})
|
||||
|
||||
it('Should pad left an array to 8 with zeros by defaul', function () {
|
||||
expect(_.padStart([1, 2, 3])).to.deep.equal([0,0,0,0,0,1,2,3])
|
||||
})
|
||||
|
||||
it('Should ignore pad when not longer than array', function () {
|
||||
expect(_.padStart([1, 2, 3],3,'a')).to.deep.equal([1,2,3])
|
||||
})
|
||||
|
||||
it('Should pad left an array with character', function () {
|
||||
expect(_.padStart([1, 2, 3],5,'a')).to.deep.equal(['a','a',1,2,3])
|
||||
})
|
||||
|
||||
it('Should pad right an array to 8 with zeros by defaul', function () {
|
||||
expect(_.padEnd([1, 2, 3])).to.deep.equal([1,2,3,0,0,0,0,0])
|
||||
})
|
||||
|
||||
it('Should ignore pad when not longer than array', function () {
|
||||
expect(_.padEnd([1, 2, 3],3,'a')).to.deep.equal([1,2,3])
|
||||
})
|
||||
|
||||
it('Should pad left an array with character', function () {
|
||||
expect(_.padEnd([1, 2, 3],5,'a')).to.deep.equal([1,2,3,'a','a'])
|
||||
})
|
||||
|
||||
})
|
|
@ -0,0 +1,135 @@
|
|||
let date = new Date(Date.now())
|
||||
console.log('run:', date.getMinutes(), ':', date.getSeconds())
|
||||
|
||||
import { expect } from 'chai'
|
||||
import * as _ from '../src/byte'
|
||||
|
||||
describe('Byte Library - ', function () {
|
||||
|
||||
it('Should Convert Byte Format for Single Byte', function () {
|
||||
|
||||
let byte = '10000001'
|
||||
let fmt = {}
|
||||
|
||||
let results = ['10000001', Buffer.from([0x81]), 129, '81', [1, 0, 0, 0, 0, 0, 0, 1],
|
||||
[8, 1]
|
||||
]
|
||||
|
||||
_.BYTE_FORMATS.forEach((ifmt, i) => {
|
||||
byte = results[i]
|
||||
fmt.in = ifmt
|
||||
// console.log('input', ifmt, byte)
|
||||
_.BYTE_FORMATS.forEach((ofmt, o) => {
|
||||
fmt.out = ofmt
|
||||
// console.log(fmt.out, _.byteFormat(byte, fmt))
|
||||
expect(_.byteFormat(byte, fmt)).deep.equal(results[o])
|
||||
})
|
||||
})
|
||||
|
||||
})
|
||||
|
||||
it('Should Convert from Any Format to Any Other', function () {
|
||||
|
||||
let bytes
|
||||
let fmt = {}
|
||||
|
||||
let results = [
|
||||
['10000001', '01010111'],
|
||||
Buffer.from([0x81, 0x57]), [129, 87],
|
||||
['81', '57'],
|
||||
[
|
||||
[1, 0, 0, 0, 0, 0, 0, 1],
|
||||
[0, 1, 0, 1, 0, 1, 1, 1]
|
||||
],
|
||||
[1, 8, 9, 10, 11, 13, 15]
|
||||
]
|
||||
|
||||
_.BYTE_FORMATS.forEach((ifmt, i) => {
|
||||
bytes = results[i]
|
||||
fmt.in = ifmt
|
||||
// console.log('input', ifmt, bytes)
|
||||
_.BYTE_FORMATS.forEach((ofmt, o) => {
|
||||
fmt.out = ofmt
|
||||
// console.log('=',i, fmt.in, bytes, o, fmt.out, _.byteFormat(bytes, fmt))
|
||||
expect(_.byteFormat(bytes, fmt)).deep.equal(results[o])
|
||||
})
|
||||
})
|
||||
|
||||
})
|
||||
|
||||
it('It should deal with missing byte when converting from PLC', function () {
|
||||
|
||||
let fmt={}
|
||||
|
||||
// check for missing place
|
||||
fmt.in = 'PLC'
|
||||
fmt.out = 'DEC'
|
||||
let bytes = [1, 8, 17]
|
||||
expect(_.byteFormat(bytes, fmt)).deep.equal([129, 0, 1])
|
||||
|
||||
})
|
||||
|
||||
it('PLC should return as with Big Endian when set in environment', function () {
|
||||
// check Big endian
|
||||
|
||||
let fmt={}
|
||||
process.env.UCI_ENDIAN='big'
|
||||
fmt.in = 'PLC'
|
||||
fmt.out = 'DEC'
|
||||
let bytes = [1, 8, 17]
|
||||
expect(_.byteFormat(bytes, fmt)).deep.equal([1, 0, 129])
|
||||
|
||||
})
|
||||
|
||||
})
|
||||
|
||||
describe('Byte Class - ', function () {
|
||||
|
||||
let byte = new _.Byte(20, 'HEX')
|
||||
let byte2 = new _.Byte(20)
|
||||
|
||||
it('Should set the default format to DEC', function () {
|
||||
|
||||
expect(byte2.fmt).to.equal('DEC')
|
||||
})
|
||||
|
||||
it('Should output an alternative format', function () {
|
||||
expect(byte.toFmt('DEC')).to.equal(32)
|
||||
expect(byte.toFmt('STR')).to.equal('00100000')
|
||||
})
|
||||
|
||||
it('Verify getters and setters ', function () {
|
||||
// value getter and setter
|
||||
expect(byte.value, 'value getter failed').to.equal(20)
|
||||
byte.value = 40
|
||||
expect(byte.value, 'value setter failed').to.equal(40)
|
||||
expect(byte.prev, 'previous value not set').to.equal(20)
|
||||
|
||||
// format getter/setter
|
||||
expect(byte.fmt, 'format getter failed').to.equal('HEX')
|
||||
byte.fmt = 'STR'
|
||||
expect(byte.fmt, 'format setter failed').to.equal('STR')
|
||||
expect(byte.value, 'format getter value change failed').to.equal('01000000')
|
||||
})
|
||||
|
||||
it('should update value with format', function () {
|
||||
// change the value with same format
|
||||
// change value and set format
|
||||
byte.reset(32)
|
||||
expect(byte.value, 'value reset failed').to.equal(32)
|
||||
expect(byte.value, 'previous value reset failed').to.equal(32)
|
||||
expect(byte.fmt, 'default format reset failed').to.equal('DEC')
|
||||
byte.reset(20, 'HEX')
|
||||
expect(byte.value, 'value reset failed').to.equal(20)
|
||||
expect(byte.fmt, 'format reset failed').to.equal('HEX')
|
||||
byte.reset('10000000', 'STR')
|
||||
expect(byte.toFmt('DEC'), 'string reset and convert failed').to.equal(128)
|
||||
})
|
||||
|
||||
it('!!!-should find bit changes and state of those changes between previous and current', function () {
|
||||
// change the value with same format
|
||||
// change value and set format
|
||||
expect(true, 'value reset failed').to.equal(true)
|
||||
})
|
||||
|
||||
})
|
Loading…
Reference in New Issue