@@ -53,14 +53,14 @@ import {
5353
5454const DEFAULT_SCOPE = '__DEFAULT_GLOBAL_SCOPE__' ;
5555
56- function Logix5000DecodeDataType ( buffer , offsetRef , cb ) {
56+ function Logix5000DecodeDataType ( buffer , offsetRef ) {
5757 const startingOffset = offsetRef . current ;
58- const type = EPath . Decode ( buffer , offsetRef , null , false , cb ) ;
58+ const segment = EPath . Decode ( buffer , offsetRef , null , false ) ;
5959 /** TODO: Why is this necessary? */
6060 if ( offsetRef . current - startingOffset < 2 ) {
6161 offsetRef . current += 1 ;
6262 }
63- return type ;
63+ return segment ;
6464}
6565
6666async function readTagFragmented ( layer , path , elements ) {
@@ -69,20 +69,21 @@ async function readTagFragmented(layer, path, elements) {
6969 const reqData = Buffer . allocUnsafe ( 6 ) ;
7070 reqData . writeUInt16LE ( elements , 0 ) ;
7171
72- const offsetRef = { current : 0 } ;
72+ let requestOffset = 0 ;
7373 const chunks = [ ] ;
7474
7575 while ( true ) {
76- reqData . writeUInt32LE ( offsetRef . current , 2 ) ;
76+ reqData . writeUInt32LE ( requestOffset , 2 ) ;
7777 const reply = await sendPromise ( layer , service , path , reqData , 5000 ) ;
7878
79- /** remove the tag type bytes if already received */
79+ /** each reply starts with the tag type; keep it on the first chunk only */
80+ const offsetRef = { current : 0 } ;
8081 Logix5000DecodeDataType ( reply . data , offsetRef ) ;
8182 const dataTypeOffset = offsetRef . current ;
8283 chunks . push ( chunks . length > 0 ? reply . data . slice ( dataTypeOffset ) : reply . data ) ;
8384
8485 if ( reply . status . code === GeneralStatusCodes . PartialTransfer ) {
85- offsetRef . current = reply . data . length - dataTypeOffset ;
86+ requestOffset + = reply . data . length - dataTypeOffset ;
8687 } else if ( reply . status . code === 0 ) {
8788 break ;
8889 } else {
@@ -101,7 +102,7 @@ async function parseReadTagMemberStructure(layer, structureType, data, offset) {
101102
102103 const template = await layer . readTemplate ( structureType . template . id ) ;
103104 if ( ! template || ! Array . isArray ( template . members ) ) {
104- return new Error ( `Unable to read template: ${ structureType . template . id } ` ) ;
105+ throw new Error ( `Unable to read template: ${ structureType . template . id } ` ) ;
105106 }
106107
107108 const { members } = template ;
@@ -153,15 +154,15 @@ async function parseReadTag(layer, scope, tag, elements, data) {
153154 return undefined ;
154155 }
155156
156- let typeInfo ;
157- const offset = Logix5000DecodeDataType ( data , 0 , ( val ) => { typeInfo = val . value ; } ) ;
157+ const offsetRef = { current : 0 } ;
158+ const typeSegment = Logix5000DecodeDataType ( data , offsetRef ) ;
159+ const typeInfo = typeSegment ? typeSegment . value : undefined ;
158160
159161 if ( ! typeInfo ) {
160162 throw new Error ( 'Unable to decode data type from read tag response data' ) ;
161163 }
162164
163165 const values = [ ] ;
164- const offsetRef = { current : offset } ;
165166
166167 if ( ! typeInfo . constructed || typeInfo . abbreviated === false ) {
167168 for ( let i = 0 ; i < elements ; i ++ ) {
@@ -225,23 +226,27 @@ async function parseReadTag(layer, scope, tag, elements, data) {
225226
226227function statusHandler ( code , extended , cb ) {
227228 let error = GenericServiceStatusDescriptions [ code ] ;
228- if ( typeof error === 'object' && Buffer . isBuffer ( extended ) && extended . length >= 0 ) {
229- error = error [ extended . readUInt16LE ( 0 ) ] ;
229+ if ( typeof error === 'object' ) {
230+ if ( Buffer . isBuffer ( extended ) && extended . length >= 2 ) {
231+ error = error [ extended . readUInt16LE ( 0 ) ] ;
232+ } else {
233+ error = undefined ;
234+ }
230235 }
231236 if ( error ) {
232237 cb ( null , error ) ;
233238 }
234239}
235240
236241/** Use driver specific error handling if exists */
237- async function send ( self , service , path , data , callback /* , timeout */ ) {
242+ async function send ( self , service , path , data , callback , timeout ) {
238243 try {
239244 const request = new CIPRequest ( service , path , data , null , {
240245 serviceNames : SymbolServiceNames ,
241246 statusHandler,
242247 } ) ;
243248
244- const response = await self . sendRequest ( true , request ) ;
249+ const response = await self . sendRequest ( true , request , null , timeout ) ;
245250 // console.log(response);
246251 if ( response . status . error ) {
247252 callback ( response . status . description , response ) ;
@@ -395,11 +400,11 @@ function parseTemplateNameInfo(data, offset, cb) {
395400// return error;
396401// }
397402
398- function scopedGenerator ( ) {
403+ function scopedGenerator ( ... scopeArgs ) {
399404 const separator = '::' ;
400- const args = [ ... arguments ] . filter ( ( arg ) => ! ! arg ) ;
401- const preface = args . length > 0 ? args . join ( separator ) + separator : '' ;
402- return ( ) => preface + [ ... arguments ] . join ( separator ) ;
405+ const scopes = scopeArgs . filter ( ( arg ) => ! ! arg ) ;
406+ const preface = scopes . length > 0 ? scopes . join ( separator ) + separator : '' ;
407+ return ( ... parts ) => preface + parts . join ( separator ) ;
403408}
404409
405410async function getSymbolInstanceID ( layer , scope , tag ) {
@@ -886,7 +891,7 @@ export default class Logix5000 extends CIPLayer {
886891 }
887892
888893 for ( let i = 0 ; i < sizeOfMasks ; i ++ ) {
889- if ( ORmasks [ i ] < 0 || ORmasks > 0xFF || ANDmasks [ i ] < 0 || ANDmasks > 0xFF ) {
894+ if ( ORmasks [ i ] < 0 || ORmasks [ i ] > 0xFF || ANDmasks [ i ] < 0 || ANDmasks [ i ] > 0xFF ) {
890895 resolver . reject ( 'Values in masks must be greater than or equal to zero and less than or equal to 255' ) ;
891896 return ;
892897 }
0 commit comments