|  |  | @ -26,10 +26,8 @@ typedef struct { | 
			
		
	
		
			
				
					|  |  |  |     uint8_t invId; | 
			
		
	
		
			
				
					|  |  |  |     uint8_t retransmits; | 
			
		
	
		
			
				
					|  |  |  |     bool gotFragment; | 
			
		
	
		
			
				
					|  |  |  |     /*
 | 
			
		
	
		
			
				
					|  |  |  |     uint8_t data[MAX_PAYLOAD_ENTRIES][MAX_RF_PAYLOAD_SIZE]; | 
			
		
	
		
			
				
					|  |  |  |     uint8_t maxPackId; | 
			
		
	
		
			
				
					|  |  |  |     bool lastFound;*/ | 
			
		
	
		
			
				
					|  |  |  |     uint8_t rtrRes; // for limiting resets
 | 
			
		
	
		
			
				
					|  |  |  |     uint8_t multi_parts;  // for quality
 | 
			
		
	
		
			
				
					|  |  |  | } miPayload_t; | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
	
		
			
				
					|  |  | @ -102,6 +100,7 @@ class MiPayload { | 
			
		
	
		
			
				
					|  |  |  |                                 DBGPRINTLN(F(")")); | 
			
		
	
		
			
				
					|  |  |  |                             } | 
			
		
	
		
			
				
					|  |  |  |                         } | 
			
		
	
		
			
				
					|  |  |  |                         mPayload[iv->id].complete = true; | 
			
		
	
		
			
				
					|  |  |  |                         iv->setQueuedCmdFinished(); // command failed
 | 
			
		
	
		
			
				
					|  |  |  |                     } | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
	
		
			
				
					|  |  | @ -131,12 +130,9 @@ class MiPayload { | 
			
		
	
		
			
				
					|  |  |  |                 mPayload[iv->id].limitrequested = true; | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 iv->clearCmdQueue(); | 
			
		
	
		
			
				
					|  |  |  |                 iv->enqueCommand<InfoCommand>(SystemConfigPara); // try to read back power limit
 | 
			
		
	
		
			
				
					|  |  |  |                 //iv->enqueCommand<InfoCommand>(SystemConfigPara); // read back power limit is not possible with MI
 | 
			
		
	
		
			
				
					|  |  |  |             } else { | 
			
		
	
		
			
				
					|  |  |  |                 uint8_t cmd = iv->getQueuedCmd(); | 
			
		
	
		
			
				
					|  |  |  |                 DPRINT_IVID(DBG_INFO, iv->id); | 
			
		
	
		
			
				
					|  |  |  |                 DBGPRINT(F("prepareDevInformCmd 0x")); | 
			
		
	
		
			
				
					|  |  |  |                 DBGHEXLN(cmd); | 
			
		
	
		
			
				
					|  |  |  |                 uint8_t cmd2 = cmd; | 
			
		
	
		
			
				
					|  |  |  |                 if ( cmd == SystemConfigPara ) { //0x05 for HM-types
 | 
			
		
	
		
			
				
					|  |  |  |                     if (!mPayload[iv->id].limitrequested) { // only do once at startup
 | 
			
		
	
	
		
			
				
					|  |  | @ -148,12 +144,15 @@ class MiPayload { | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 if (cmd == 0x01 || cmd == SystemConfigPara ) { //0x1 and 0x05 for HM-types
 | 
			
		
	
		
			
				
					|  |  |  |                     cmd  = 0x0f;                              // for MI, these seem to make part of the  Polling the device software and hardware version number command
 | 
			
		
	
		
			
				
					|  |  |  |                     cmd2 = cmd == SystemConfigPara ? 0x01 : 0x00;  //perhaps we can only try to get second frame?
 | 
			
		
	
		
			
				
					|  |  |  |                     cmd  = 0x0f;                              // for MI, these seem to make part of polling the device software and hardware version number command
 | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  |                 if (mSerialDebug) { | 
			
		
	
		
			
				
					|  |  |  |                     DPRINT_IVID(DBG_INFO, iv->id); | 
			
		
	
		
			
				
					|  |  |  |                     DBGPRINT(F("prepareDevInformCmd 0x")); | 
			
		
	
		
			
				
					|  |  |  |                     DBGHEXLN(cmd); | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  |                 mRadio->sendCmdPacket(iv->radioId.u64, cmd, cmd2, false, false); | 
			
		
	
		
			
				
					|  |  |  |                 } else { | 
			
		
	
		
			
				
					|  |  |  |                     mRadio->sendCmdPacket(iv->radioId.u64, cmd, cmd2, false, false); | 
			
		
	
		
			
				
					|  |  |  |                 }; | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 mPayload[iv->id].txCmd = cmd; | 
			
		
	
		
			
				
					|  |  |  |                 if (iv->type == INV_TYPE_1CH || iv->type == INV_TYPE_2CH) { | 
			
		
	
	
		
			
				
					|  |  | @ -161,14 +160,13 @@ class MiPayload { | 
			
		
	
		
			
				
					|  |  |  |                     mPayload[iv->id].stsAB[CH1] = false; | 
			
		
	
		
			
				
					|  |  |  |                     mPayload[iv->id].dataAB[CH0] = false; | 
			
		
	
		
			
				
					|  |  |  |                     mPayload[iv->id].stsAB[CH0] = false; | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                     if (iv->type == INV_TYPE_2CH) { | 
			
		
	
		
			
				
					|  |  |  |                         mPayload[iv->id].dataAB[CH2] = false; | 
			
		
	
		
			
				
					|  |  |  |                         mPayload[iv->id].stsAB[CH2] = false; | 
			
		
	
		
			
				
					|  |  |  |                     } | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  |             } | 
			
		
	
		
			
				
					|  |  |  |         } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |         void add(Inverter<> *iv, packet_t *p) { | 
			
		
	
		
			
				
					|  |  |  |             //DPRINTLN(DBG_INFO, F("MI got data [0]=") + String(p->packet[0], HEX));
 | 
			
		
	
	
		
			
				
					|  |  | @ -190,125 +188,8 @@ class MiPayload { | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |             else if (p->packet[0] == ( 0x0f + ALL_FRAMES)) { | 
			
		
	
		
			
				
					|  |  |  |                 // MI response from get hardware information request
 | 
			
		
	
		
			
				
					|  |  |  |                 record_t<> *rec = iv->getRecordStruct(InverterDevInform_All);  // choose the record structure
 | 
			
		
	
		
			
				
					|  |  |  |                 rec->ts = mPayload[iv->id].ts; | 
			
		
	
		
			
				
					|  |  |  |                 mPayload[iv->id].gotFragment = true; | 
			
		
	
		
			
				
					|  |  |  |                 if(mHighPrioIv == NULL)                          // process next request immediately if possible
 | 
			
		
	
		
			
				
					|  |  |  |                     mHighPrioIv = iv; | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  | /*
 | 
			
		
	
		
			
				
					|  |  |  |  Polling the device software and hardware version number command | 
			
		
	
		
			
				
					|  |  |  |  start byte	Command word	 routing address				 target address				 User data	 check	 end byte | 
			
		
	
		
			
				
					|  |  |  |  byte[0]	 byte[1]	 byte[2]	 byte[3]	 byte[4]	 byte[5]	 byte[6]	 byte[7]	 byte[8]	 byte[9]	 byte[10]	 byte[11]	 byte[12] | 
			
		
	
		
			
				
					|  |  |  |  0x7e	 0x0f	 xx	 xx	 xx	 xx	 YY	 YY	 YY	 YY	 0x00	 CRC	 0x7f | 
			
		
	
		
			
				
					|  |  |  |  Command Receipt - First Frame | 
			
		
	
		
			
				
					|  |  |  |  start byte	Command word	 target address				 routing address				 Multi-frame marking	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 check	 end byte | 
			
		
	
		
			
				
					|  |  |  |  byte[0]	 byte[1]	 byte[2]	 byte[3]	 byte[4]	 byte[5]	 byte[6]	 byte[7]	 byte[8]	 byte[9]	 byte[10]	 byte[11]	 byte[12]	 byte[13]	 byte[14]	 byte[15]	 byte[16]	 byte[17]	 byte[18]	 byte[19]	 byte[20]	 byte[21]	 byte[22]	 byte[23]	 byte[24]	 byte[25]	 byte[26]	 byte[27]	 byte[28] | 
			
		
	
		
			
				
					|  |  |  |  0x7e	 0x8f	 YY	 YY	 YY	 YY	 xx	 xx	 xx	 xx	 0x00	 USFWBuild_VER		 APPFWBuild_VER		 APPFWBuild_YYYY		 APPFWBuild_MMDD		 APPFWBuild_HHMM		 APPFW_PN				 HW_VER		 CRC	 0x7f | 
			
		
	
		
			
				
					|  |  |  |  Command Receipt - Second Frame | 
			
		
	
		
			
				
					|  |  |  |  start byte	Command word	 target address				 routing address				 Multi-frame marking	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 check	 end byte | 
			
		
	
		
			
				
					|  |  |  |  byte[0]	 byte[1]	 byte[2]	 byte[3]	 byte[4]	 byte[5]	 byte[6]	 byte[7]	 byte[8]	 byte[9]	 byte[10]	 byte[11]	 byte[12]	 byte[13]	 byte[14]	 byte[15]	 byte[16]	 byte[17]	 byte[18]	 byte[19]	 byte[20]	 byte[21]	 byte[22]	 byte[23]	 byte[24]	 byte[25]	 byte[26]	 byte[27]	 byte[28] | 
			
		
	
		
			
				
					|  |  |  |  0x7e	 0x8f	 YY	 YY	 YY	 YY	 xx	 xx	 xx	 xx	 0x01	 HW_PN				 HW_FB_TLmValue		 HW_FB_ReSPRT		 HW_GridSamp_ResValule		 HW_ECapValue		 Matching_APPFW_PN				 CRC	 0x7f | 
			
		
	
		
			
				
					|  |  |  |  Command receipt - third frame | 
			
		
	
		
			
				
					|  |  |  |  start byte	Command word	 target address				 routing address				 Multi-frame marking	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 check	 end byte | 
			
		
	
		
			
				
					|  |  |  |  byte[0]	 byte[1]	 byte[2]	 byte[3]	 byte[4]	 byte[5]	 byte[6]	 byte[7]	 byte[8]	 byte[9]	 byte[10]	 byte[11]	 byte[12]	 byte[13]	 byte[14]	 byte[15]	 byte[16]	 byte[15]	 byte[16]	 byte[17]	 byte[18] | 
			
		
	
		
			
				
					|  |  |  |  0x7e	 0x8f	 YY	 YY	 YY	 YY	 xx	 xx	 xx	 xx	 0x12	 APPFW_MINVER		 HWInfoAddr		 PNInfoCRC_gusv		 PNInfoCRC_gusv		 CRC	 0x7f | 
			
		
	
		
			
				
					|  |  |  | */ | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  | /*
 | 
			
		
	
		
			
				
					|  |  |  | case InverterDevInform_All: | 
			
		
	
		
			
				
					|  |  |  |                     rec->length  = (uint8_t)(HMINFO_LIST_LEN); | 
			
		
	
		
			
				
					|  |  |  |                     rec->assign  = (byteAssign_t *)InfoAssignment; | 
			
		
	
		
			
				
					|  |  |  |                     rec->pyldLen = HMINFO_PAYLOAD_LEN; | 
			
		
	
		
			
				
					|  |  |  |                     break; | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  | const byteAssign_t InfoAssignment[] = { | 
			
		
	
		
			
				
					|  |  |  |     { FLD_FW_VERSION,           UNIT_NONE,   CH0,  0, 2, 1 }, | 
			
		
	
		
			
				
					|  |  |  |     { FLD_FW_BUILD_YEAR,        UNIT_NONE,   CH0,  2, 2, 1 }, | 
			
		
	
		
			
				
					|  |  |  |     { FLD_FW_BUILD_MONTH_DAY,   UNIT_NONE,   CH0,  4, 2, 1 }, | 
			
		
	
		
			
				
					|  |  |  |     { FLD_FW_BUILD_HOUR_MINUTE, UNIT_NONE,   CH0,  6, 2, 1 }, | 
			
		
	
		
			
				
					|  |  |  |     { FLD_BOOTLOADER_VER,       UNIT_NONE,   CH0,  8, 2, 1 } | 
			
		
	
		
			
				
					|  |  |  | }; | 
			
		
	
		
			
				
					|  |  |  | */ | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 if ( p->packet[9] == 0x00 ) {//first frame
 | 
			
		
	
		
			
				
					|  |  |  |                     //FLD_FW_VERSION
 | 
			
		
	
		
			
				
					|  |  |  |                     for (uint8_t i = 0; i < 5; i++) { | 
			
		
	
		
			
				
					|  |  |  |                         iv->setValue(i, rec, (float) ((p->packet[(12+2*i)] << 8) + p->packet[(13+2*i)])/1); | 
			
		
	
		
			
				
					|  |  |  |                     } | 
			
		
	
		
			
				
					|  |  |  |                     iv->isConnected = true; | 
			
		
	
		
			
				
					|  |  |  |                     mPayload[iv->id].gotFragment = true; | 
			
		
	
		
			
				
					|  |  |  |                     if(mSerialDebug) { | 
			
		
	
		
			
				
					|  |  |  |                         DPRINT_IVID(DBG_INFO, iv->id); | 
			
		
	
		
			
				
					|  |  |  |                         DPRINT(DBG_INFO,F("HW_VER is ")); | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINTLN(String((p->packet[24] << 8) + p->packet[25])); | 
			
		
	
		
			
				
					|  |  |  |                     } | 
			
		
	
		
			
				
					|  |  |  |                     record_t<> *rec = iv->getRecordStruct(InverterDevInform_Simple);  // choose the record structure
 | 
			
		
	
		
			
				
					|  |  |  |                     rec->ts = mPayload[iv->id].ts; | 
			
		
	
		
			
				
					|  |  |  |                     iv->setValue(1, rec, (uint32_t) ((p->packet[24] << 8) + p->packet[25])/1); | 
			
		
	
		
			
				
					|  |  |  |                     //notify(InverterDevInform_All, iv);
 | 
			
		
	
		
			
				
					|  |  |  |                     //28737
 | 
			
		
	
		
			
				
					|  |  |  |                 } else if ( p->packet[9] == 0x01 || p->packet[9] == 0x10 ) {//second frame for MI, 3rd gen. answers in 0x10
 | 
			
		
	
		
			
				
					|  |  |  |                     DPRINT_IVID(DBG_INFO, iv->id); | 
			
		
	
		
			
				
					|  |  |  |                     if ( p->packet[9] == 0x01 ) { | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINTLN(F("got 2nd frame (hw info)")); | 
			
		
	
		
			
				
					|  |  |  |                         /* according to xlsx (different start byte -1!)
 | 
			
		
	
		
			
				
					|  |  |  |                         byte[11] to	 byte[14] HW_PN | 
			
		
	
		
			
				
					|  |  |  |                         byte[15]	 byte[16] HW_FB_TLmValue | 
			
		
	
		
			
				
					|  |  |  |                         byte[17]	 byte[18] HW_FB_ReSPRT | 
			
		
	
		
			
				
					|  |  |  |                         byte[19]	 byte[20] HW_GridSamp_ResValule | 
			
		
	
		
			
				
					|  |  |  |                         byte[21]	 byte[22] HW_ECapValue | 
			
		
	
		
			
				
					|  |  |  |                         byte[23] to	 byte[26] Matching_APPFW_PN | 
			
		
	
		
			
				
					|  |  |  |                     */ | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                         DPRINT(DBG_INFO,F("HW_PartNo ")); | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINTLN(String((uint32_t) (((p->packet[10] << 8) | p->packet[11]) << 8 | p->packet[12]) << 8 | p->packet[13])); | 
			
		
	
		
			
				
					|  |  |  |                         mPayload[iv->id].gotFragment = true; | 
			
		
	
		
			
				
					|  |  |  |                         record_t<> *rec = iv->getRecordStruct(InverterDevInform_Simple);  // choose the record structure
 | 
			
		
	
		
			
				
					|  |  |  |                         rec->ts = mPayload[iv->id].ts; | 
			
		
	
		
			
				
					|  |  |  |                         iv->setValue(0, rec, (uint32_t) ((((p->packet[10] << 8) | p->packet[11]) << 8 | p->packet[12]) << 8 | p->packet[13])/1); | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                         if(mSerialDebug) { | 
			
		
	
		
			
				
					|  |  |  |                             DPRINT(DBG_INFO,F("HW_FB_TLmValue ")); | 
			
		
	
		
			
				
					|  |  |  |                             DBGPRINTLN(String((p->packet[14] << 8) + p->packet[15])); | 
			
		
	
		
			
				
					|  |  |  |                             DPRINT(DBG_INFO,F("HW_FB_ReSPRT ")); | 
			
		
	
		
			
				
					|  |  |  |                             DBGPRINTLN(String((p->packet[16] << 8) + p->packet[17])); | 
			
		
	
		
			
				
					|  |  |  |                             DPRINT(DBG_INFO,F("HW_GridSamp_ResValule ")); | 
			
		
	
		
			
				
					|  |  |  |                             DBGPRINTLN(String((p->packet[18] << 8) + p->packet[19])); | 
			
		
	
		
			
				
					|  |  |  |                             DPRINT(DBG_INFO,F("HW_ECapValue ")); | 
			
		
	
		
			
				
					|  |  |  |                             DBGPRINTLN(String((p->packet[20] << 8) + p->packet[21])); | 
			
		
	
		
			
				
					|  |  |  |                             DPRINT(DBG_INFO,F("Matching_APPFW_PN ")); | 
			
		
	
		
			
				
					|  |  |  |                             DBGPRINTLN(String((uint32_t) (((p->packet[22] << 8) | p->packet[23]) << 8 | p->packet[24]) << 8 | p->packet[25])); | 
			
		
	
		
			
				
					|  |  |  |                         } | 
			
		
	
		
			
				
					|  |  |  |                         //notify(InverterDevInform_Simple, iv);
 | 
			
		
	
		
			
				
					|  |  |  |                         notify(InverterDevInform_All, iv); | 
			
		
	
		
			
				
					|  |  |  |                     } else { | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINTLN(F("3rd gen. inverter!"));           // see table in OpenDTU code, DevInfoParser.cpp devInfo[]
 | 
			
		
	
		
			
				
					|  |  |  |                     } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 } else if ( p->packet[9] == 0x12 ) {//3rd frame
 | 
			
		
	
		
			
				
					|  |  |  |                     DPRINT_IVID(DBG_INFO, iv->id); | 
			
		
	
		
			
				
					|  |  |  |                     DBGPRINTLN(F("got 3rd frame (hw info)")); | 
			
		
	
		
			
				
					|  |  |  |                     /* according to xlsx (different start byte -1!)
 | 
			
		
	
		
			
				
					|  |  |  |                         byte[11]	 byte[12] APPFW_MINVER | 
			
		
	
		
			
				
					|  |  |  |                         byte[13]	 byte[14] HWInfoAddr | 
			
		
	
		
			
				
					|  |  |  |                         byte[15]	 byte[16] PNInfoCRC_gusv | 
			
		
	
		
			
				
					|  |  |  |                         byte[15]	 byte[16] PNInfoCRC_gusv | 
			
		
	
		
			
				
					|  |  |  |                     */ | 
			
		
	
		
			
				
					|  |  |  |                     if(mSerialDebug) { | 
			
		
	
		
			
				
					|  |  |  |                         DPRINT(DBG_INFO,F("APPFW_MINVER ")); | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINTLN(String((p->packet[10] << 8) + p->packet[11])); | 
			
		
	
		
			
				
					|  |  |  |                         DPRINT(DBG_INFO,F("HWInfoAddr ")); | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINTLN(String((p->packet[12] << 8) + p->packet[13])); | 
			
		
	
		
			
				
					|  |  |  |                         DPRINT(DBG_INFO,F("PNInfoCRC_gusv ")); | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINTLN(String((p->packet[14] << 8) + p->packet[15])); | 
			
		
	
		
			
				
					|  |  |  |                         DPRINT(DBG_INFO,F("PNInfoCRC_gusv (pt. 2?) ")); | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINTLN(String((p->packet[16] << 8) + p->packet[17])); | 
			
		
	
		
			
				
					|  |  |  |                     } | 
			
		
	
		
			
				
					|  |  |  |                     iv->setQueuedCmdFinished(); | 
			
		
	
		
			
				
					|  |  |  |                     mPayload[iv->id].complete = true; | 
			
		
	
		
			
				
					|  |  |  |                     mStat->rxSuccess++; | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  |                 miHwDecode(iv, p); | 
			
		
	
		
			
				
					|  |  |  |                 mPayload[iv->id].txId = p->packet[0]; | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |             } else if ( p->packet[0] == (TX_REQ_INFO + ALL_FRAMES) // response from get information command
 | 
			
		
	
		
			
				
					|  |  |  |                      || (p->packet[0] == 0xB6 && mPayload[iv->id].txCmd != 0x36)) {                   // strange short response from MI-1500 3rd gen; might be misleading!
 | 
			
		
	
	
		
			
				
					|  |  | @ -326,23 +207,7 @@ const byteAssign_t InfoAssignment[] = { | 
			
		
	
		
			
				
					|  |  |  |                     iv->ivGen = IV_HM; | 
			
		
	
		
			
				
					|  |  |  |                     iv->setQueuedCmdFinished(); | 
			
		
	
		
			
				
					|  |  |  |                     iv->clearCmdQueue(); | 
			
		
	
		
			
				
					|  |  |  |                     //DPRINTLN(DBG_DEBUG, "PID: 0x" + String(*pid, HEX));
 | 
			
		
	
		
			
				
					|  |  |  |                     /* (old else-tree)
 | 
			
		
	
		
			
				
					|  |  |  |                     if ((*pid & 0x7F) < MAX_PAYLOAD_ENTRIES) {^ | 
			
		
	
		
			
				
					|  |  |  |                         memcpy(mPayload[iv->id].data[(*pid & 0x7F) - 1], &p->packet[10], p->len - 11); | 
			
		
	
		
			
				
					|  |  |  |                         mPayload[iv->id].len[(*pid & 0x7F) - 1] = p->len - 11; | 
			
		
	
		
			
				
					|  |  |  |                         mPayload[iv->id].gotFragment = true; | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  |                     if ((*pid & ALL_FRAMES) == ALL_FRAMES) { | 
			
		
	
		
			
				
					|  |  |  |                         // Last packet
 | 
			
		
	
		
			
				
					|  |  |  |                         if (((*pid & 0x7f) > mPayload[iv->id].maxPackId) || (MAX_PAYLOAD_ENTRIES == mPayload[iv->id].maxPackId)) { | 
			
		
	
		
			
				
					|  |  |  |                             mPayload[iv->id].maxPackId = (*pid & 0x7f); | 
			
		
	
		
			
				
					|  |  |  |                             if (*pid > 0x81) | 
			
		
	
		
			
				
					|  |  |  |                                 mPayload[iv->id].lastFound = true; | 
			
		
	
		
			
				
					|  |  |  |                         } | 
			
		
	
		
			
				
					|  |  |  |                     }*/ | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  |             //}
 | 
			
		
	
		
			
				
					|  |  |  |             } else if (p->packet[0] == (TX_REQ_DEVCONTROL + ALL_FRAMES )       // response from dev control command
 | 
			
		
	
		
			
				
					|  |  |  |                     || p->packet[0] == (TX_REQ_DEVCONTROL + ALL_FRAMES -1)) {  // response from DRED instruction
 | 
			
		
	
		
			
				
					|  |  |  |                 DPRINT_IVID(DBG_DEBUG, iv->id); | 
			
		
	
	
		
			
				
					|  |  | @ -354,23 +219,27 @@ const byteAssign_t InfoAssignment[] = { | 
			
		
	
		
			
				
					|  |  |  |                 if ((p->packet[9] == 0x5a) && (p->packet[10] == 0x5a)) { | 
			
		
	
		
			
				
					|  |  |  |                     mApp->setMqttPowerLimitAck(iv); | 
			
		
	
		
			
				
					|  |  |  |                     iv->powerLimitAck = true; | 
			
		
	
		
			
				
					|  |  |  |                     if (mSerialDebug) { | 
			
		
	
		
			
				
					|  |  |  |                         DPRINT_IVID(DBG_INFO, iv->id); | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINT(F("has accepted power limit set point ")); | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINT(String(iv->powerLimit[0])); | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINT(F(" with PowerLimitControl ")); | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINTLN(String(iv->powerLimit[1])); | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                     } | 
			
		
	
		
			
				
					|  |  |  |                     iv->clearCmdQueue(); | 
			
		
	
		
			
				
					|  |  |  |                     iv->enqueCommand<InfoCommand>(SystemConfigPara); // read back power limit
 | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  |                 iv->devControlCmd = Init; | 
			
		
	
		
			
				
					|  |  |  |             } else {  // some other response; copied from hmPayload:process; might not be correct to do that here!!!
 | 
			
		
	
		
			
				
					|  |  |  |                 DPRINT(DBG_INFO, F("procPyld: cmd:  0x")); | 
			
		
	
		
			
				
					|  |  |  |                 if (mSerialDebug) { | 
			
		
	
		
			
				
					|  |  |  |                     DPRINT_IVID(DBG_INFO,iv->id); | 
			
		
	
		
			
				
					|  |  |  |                     DBGPRINT(F("procPyld: cmd:  0x")); | 
			
		
	
		
			
				
					|  |  |  |                     DBGHEXLN(mPayload[iv->id].txCmd); | 
			
		
	
		
			
				
					|  |  |  |                 DPRINT(DBG_INFO, F("procPyld: txid: 0x")); | 
			
		
	
		
			
				
					|  |  |  |                     DPRINT_IVID(DBG_INFO,iv->id); | 
			
		
	
		
			
				
					|  |  |  |                     DBGPRINT(F("procPyld: txid: 0x")); | 
			
		
	
		
			
				
					|  |  |  |                     DBGHEXLN(mPayload[iv->id].txId); | 
			
		
	
		
			
				
					|  |  |  |                 //DPRINT(DBG_DEBUG, F("procPyld: max:  "));
 | 
			
		
	
		
			
				
					|  |  |  |                 //DBGPRINTLN(String(mPayload[iv->id].maxPackId));
 | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 record_t<> *rec = iv->getRecordStruct(mPayload[iv->id].txCmd);  // choose the parser
 | 
			
		
	
		
			
				
					|  |  |  |                 mPayload[iv->id].complete = true; | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
	
		
			
				
					|  |  | @ -379,11 +248,6 @@ const byteAssign_t InfoAssignment[] = { | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 memset(payload, 0, 128); | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 /*for (uint8_t i = 0; i < (mPayload[iv->id].maxPackId); i++) {
 | 
			
		
	
		
			
				
					|  |  |  |                     memcpy(&payload[payloadLen], mPayload[iv->id].data[i], (mPayload[iv->id].len[i])); | 
			
		
	
		
			
				
					|  |  |  |                     payloadLen += (mPayload[iv->id].len[i]); | 
			
		
	
		
			
				
					|  |  |  |                     yield(); | 
			
		
	
		
			
				
					|  |  |  |                 }*/ | 
			
		
	
		
			
				
					|  |  |  |                 payloadLen -= 2; | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 if (mSerialDebug) { | 
			
		
	
	
		
			
				
					|  |  | @ -432,7 +296,7 @@ const byteAssign_t InfoAssignment[] = { | 
			
		
	
		
			
				
					|  |  |  |                 if (NULL == iv) | 
			
		
	
		
			
				
					|  |  |  |                     continue; // skip to next inverter
 | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 if (IV_HM == iv->ivGen) // only process MI inverters
 | 
			
		
	
		
			
				
					|  |  |  |                 if (IV_MI != iv->ivGen) // only process MI inverters
 | 
			
		
	
		
			
				
					|  |  |  |                     continue; // skip to next inverter
 | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 if ( !mPayload[iv->id].complete && | 
			
		
	
	
		
			
				
					|  |  | @ -443,24 +307,17 @@ const byteAssign_t InfoAssignment[] = { | 
			
		
	
		
			
				
					|  |  |  |                     (mPayload[iv->id].txId != (0x11 + ALL_FRAMES)) && | 
			
		
	
		
			
				
					|  |  |  |                     (mPayload[iv->id].txId != (0x88)) && | 
			
		
	
		
			
				
					|  |  |  |                     (mPayload[iv->id].txId != (0x92)) && | 
			
		
	
		
			
				
					|  |  |  |                     (mPayload[iv->id].txId != 0 )) { | 
			
		
	
		
			
				
					|  |  |  |                     (mPayload[iv->id].txId != 0 && | 
			
		
	
		
			
				
					|  |  |  |                     mPayload[iv->id].txCmd != 0x0f)) { | 
			
		
	
		
			
				
					|  |  |  |                     // no processing needed if txId is not one of 0x95, 0x88, 0x89, 0x91, 0x92 or response to 0x36ff
 | 
			
		
	
		
			
				
					|  |  |  |                     mPayload[iv->id].complete = true; | 
			
		
	
		
			
				
					|  |  |  |                     continue; // skip to next inverter
 | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 //delayed next message?
 | 
			
		
	
		
			
				
					|  |  |  |                 //mPayload[iv->id].skipfirstrepeat++;
 | 
			
		
	
		
			
				
					|  |  |  |                 /*if (mPayload[iv->id].skipfirstrepeat) {
 | 
			
		
	
		
			
				
					|  |  |  |                     mPayload[iv->id].skipfirstrepeat = 0; //reset counter
 | 
			
		
	
		
			
				
					|  |  |  |                     continue; // skip to next inverter
 | 
			
		
	
		
			
				
					|  |  |  |                 }*/ | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 if (!mPayload[iv->id].complete) { | 
			
		
	
		
			
				
					|  |  |  |                     //DPRINTLN(DBG_INFO, F("Pyld incompl code")); //info for testing only
 | 
			
		
	
		
			
				
					|  |  |  |                     bool crcPass, pyldComplete; | 
			
		
	
		
			
				
					|  |  |  |                     crcPass = build(iv->id, &pyldComplete); | 
			
		
	
		
			
				
					|  |  |  |                     if (!crcPass && !pyldComplete) { // payload not complete
 | 
			
		
	
		
			
				
					|  |  |  |                     bool gotAllMsgParts, pyldComplete, fastNext; | 
			
		
	
		
			
				
					|  |  |  |                     gotAllMsgParts = build(iv, &pyldComplete, &fastNext); | 
			
		
	
		
			
				
					|  |  |  |                     if (!gotAllMsgParts && !pyldComplete) { // payload not complete
 | 
			
		
	
		
			
				
					|  |  |  |                         if ((mPayload[iv->id].requested) && (retransmit)) { | 
			
		
	
		
			
				
					|  |  |  |                             if (iv->devControlCmd == Restart || iv->devControlCmd == CleanState_LockAndAlarm) { | 
			
		
	
		
			
				
					|  |  |  |                                 // This is required to prevent retransmissions without answer.
 | 
			
		
	
	
		
			
				
					|  |  | @ -482,8 +339,7 @@ const byteAssign_t InfoAssignment[] = { | 
			
		
	
		
			
				
					|  |  |  |                                     } else if ( cmd == 0x0f ) { | 
			
		
	
		
			
				
					|  |  |  |                                         //hard/firmware request
 | 
			
		
	
		
			
				
					|  |  |  |                                         mRadio->sendCmdPacket(iv->radioId.u64, 0x0f, 0x00, true, false); | 
			
		
	
		
			
				
					|  |  |  |                                         //iv->setQueuedCmdFinished();
 | 
			
		
	
		
			
				
					|  |  |  |                                         //cmd = iv->getQueuedCmd();
 | 
			
		
	
		
			
				
					|  |  |  |                                         mPayload[id].multi_parts = 0; | 
			
		
	
		
			
				
					|  |  |  |                                     } else { | 
			
		
	
		
			
				
					|  |  |  |                                         bool change = false; | 
			
		
	
		
			
				
					|  |  |  |                                         if ( cmd >= 0x36 && cmd < 0x39 ) { // MI-1500 Data command
 | 
			
		
	
	
		
			
				
					|  |  | @ -496,6 +352,7 @@ const byteAssign_t InfoAssignment[] = { | 
			
		
	
		
			
				
					|  |  |  |                                                 else if (!mPayload[iv->id].stsAB[CH2] || !mPayload[iv->id].dataAB[CH2] ) { | 
			
		
	
		
			
				
					|  |  |  |                                                     cmd = 0x11; | 
			
		
	
		
			
				
					|  |  |  |                                                     change = true; | 
			
		
	
		
			
				
					|  |  |  |                                                     if (mPayload[iv->id].rtrRes < 3) //only get back to first channel twice
 | 
			
		
	
		
			
				
					|  |  |  |                                                         mPayload[iv->id].retransmits = 0; //reset counter
 | 
			
		
	
		
			
				
					|  |  |  |                                                 } | 
			
		
	
		
			
				
					|  |  |  |                                             } | 
			
		
	
	
		
			
				
					|  |  | @ -510,32 +367,48 @@ const byteAssign_t InfoAssignment[] = { | 
			
		
	
		
			
				
					|  |  |  |                                         DPRINT_IVID(DBG_INFO, iv->id); | 
			
		
	
		
			
				
					|  |  |  |                                         if (change) { | 
			
		
	
		
			
				
					|  |  |  |                                             DBGPRINT(F("next request is")); | 
			
		
	
		
			
				
					|  |  |  |                                             //mPayload[iv->id].skipfirstrepeat = 0;
 | 
			
		
	
		
			
				
					|  |  |  |                                             mPayload[iv->id].txCmd = cmd; | 
			
		
	
		
			
				
					|  |  |  |                                             mPayload[iv->id].rtrRes++; | 
			
		
	
		
			
				
					|  |  |  |                                         } else { | 
			
		
	
		
			
				
					|  |  |  |                                             DBGPRINT(F("sth.")); | 
			
		
	
		
			
				
					|  |  |  |                                             DBGPRINT(F(" missing: Request Retransmit")); | 
			
		
	
		
			
				
					|  |  |  |                                         } | 
			
		
	
		
			
				
					|  |  |  |                                         DBGPRINT(F(" 0x")); | 
			
		
	
		
			
				
					|  |  |  |                                         DBGHEXLN(cmd); | 
			
		
	
		
			
				
					|  |  |  |                                         mPayload[id].multi_parts = 0; | 
			
		
	
		
			
				
					|  |  |  |                                         mRadio->sendCmdPacket(iv->radioId.u64, cmd, cmd, true, false); | 
			
		
	
		
			
				
					|  |  |  |                                         yield(); | 
			
		
	
		
			
				
					|  |  |  |                                     } | 
			
		
	
		
			
				
					|  |  |  |                                 } | 
			
		
	
		
			
				
					|  |  |  |                             } | 
			
		
	
		
			
				
					|  |  |  |                         } | 
			
		
	
		
			
				
					|  |  |  |                     } else if(!crcPass && pyldComplete) { // crc error on complete Payload
 | 
			
		
	
		
			
				
					|  |  |  |                     } else if(!gotAllMsgParts && pyldComplete) { // crc error on complete Payload
 | 
			
		
	
		
			
				
					|  |  |  |                         if (mPayload[iv->id].retransmits < mMaxRetrans) { | 
			
		
	
		
			
				
					|  |  |  |                             mPayload[iv->id].retransmits++; | 
			
		
	
		
			
				
					|  |  |  |                             mPayload[iv->id].txCmd = iv->getQueuedCmd(); | 
			
		
	
		
			
				
					|  |  |  |                             mPayload[id].multi_parts  = 0; | 
			
		
	
		
			
				
					|  |  |  |                             if (mSerialDebug) { | 
			
		
	
		
			
				
					|  |  |  |                                 DPRINT_IVID(DBG_WARN, iv->id); | 
			
		
	
		
			
				
					|  |  |  |                                 DBGPRINTLN(F("CRC Error: Request Complete Retransmit")); | 
			
		
	
		
			
				
					|  |  |  |                             mPayload[iv->id].txCmd = iv->getQueuedCmd(); | 
			
		
	
		
			
				
					|  |  |  |                                 DPRINT_IVID(DBG_INFO, iv->id); | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                                 DBGPRINT(F("prepareDevInformCmd 0x")); | 
			
		
	
		
			
				
					|  |  |  |                                 DBGHEXLN(mPayload[iv->id].txCmd); | 
			
		
	
		
			
				
					|  |  |  |                             } | 
			
		
	
		
			
				
					|  |  |  |                             mRadio->sendCmdPacket(iv->radioId.u64, mPayload[iv->id].txCmd, mPayload[iv->id].txCmd, false, false); | 
			
		
	
		
			
				
					|  |  |  |                         } | 
			
		
	
		
			
				
					|  |  |  |                     } else { | 
			
		
	
		
			
				
					|  |  |  |                         if (fastNext) { | 
			
		
	
		
			
				
					|  |  |  |                             uint8_t cmd = iv->getQueuedCmd(); | 
			
		
	
		
			
				
					|  |  |  |                             if (mSerialDebug) { | 
			
		
	
		
			
				
					|  |  |  |                                 DPRINT_IVID(DBG_INFO, iv->id); | 
			
		
	
		
			
				
					|  |  |  |                                 DBGPRINT(F("fast mode ")); | 
			
		
	
		
			
				
					|  |  |  |                                 DBGPRINT(F("prepareDevInformCmd 0x")); | 
			
		
	
		
			
				
					|  |  |  |                                 DBGHEXLN(cmd); | 
			
		
	
		
			
				
					|  |  |  |                             } | 
			
		
	
		
			
				
					|  |  |  |                             mStat->rxSuccess++; | 
			
		
	
		
			
				
					|  |  |  |                             mRadio->prepareDevInformCmd(iv->radioId.u64, cmd, mPayload[iv->id].ts, iv->alarmMesIndex, false); | 
			
		
	
		
			
				
					|  |  |  |                             mPayload[iv->id].txCmd = cmd; | 
			
		
	
		
			
				
					|  |  |  |                         } | 
			
		
	
		
			
				
					|  |  |  |                     } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
	
		
			
				
					|  |  | @ -550,19 +423,15 @@ const byteAssign_t InfoAssignment[] = { | 
			
		
	
		
			
				
					|  |  |  |         } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |         void miStsDecode(Inverter<> *iv, packet_t *p, uint8_t stschan = CH1) { | 
			
		
	
		
			
				
					|  |  |  |             //DPRINTLN(DBG_INFO, F("(#") + String(iv->id) + F(") status msg 0x") + String(p->packet[0], HEX));
 | 
			
		
	
		
			
				
					|  |  |  |             record_t<> *rec = iv->getRecordStruct(RealTimeRunData_Debug);  // choose the record structure
 | 
			
		
	
		
			
				
					|  |  |  |             rec->ts = mPayload[iv->id].ts; | 
			
		
	
		
			
				
					|  |  |  |             mPayload[iv->id].gotFragment = true; | 
			
		
	
		
			
				
					|  |  |  |             mPayload[iv->id].multi_parts += 3; | 
			
		
	
		
			
				
					|  |  |  |             mPayload[iv->id].txId = p->packet[0]; | 
			
		
	
		
			
				
					|  |  |  |             miStsConsolidate(iv, stschan, rec, p->packet[10], p->packet[12], p->packet[9], p->packet[11]); | 
			
		
	
		
			
				
					|  |  |  |             mPayload[iv->id].stsAB[stschan] = true; | 
			
		
	
		
			
				
					|  |  |  |             if (mPayload[iv->id].stsAB[CH1] && mPayload[iv->id].stsAB[CH2]) | 
			
		
	
		
			
				
					|  |  |  |                 mPayload[iv->id].stsAB[CH0] = true; | 
			
		
	
		
			
				
					|  |  |  |             //mPayload[iv->id].skipfirstrepeat = 1;
 | 
			
		
	
		
			
				
					|  |  |  |             if (mPayload[iv->id].stsAB[CH0] && mPayload[iv->id].dataAB[CH0] && !mPayload[iv->id].complete) { | 
			
		
	
		
			
				
					|  |  |  |                 miComplete(iv); | 
			
		
	
		
			
				
					|  |  |  |             } | 
			
		
	
		
			
				
					|  |  |  |         } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |         void miStsConsolidate(Inverter<> *iv, uint8_t stschan,  record_t<> *rec, uint8_t uState, uint8_t uEnum, uint8_t lState = 0, uint8_t lEnum = 0) { | 
			
		
	
	
		
			
				
					|  |  | @ -588,24 +457,27 @@ const byteAssign_t InfoAssignment[] = { | 
			
		
	
		
			
				
					|  |  |  |             uint16_t prntsts = statusMi == 3 ? 1 : statusMi; | 
			
		
	
		
			
				
					|  |  |  |             if ( statusMi != mPayload[iv->id].sts[stschan] ) { //sth.'s changed?
 | 
			
		
	
		
			
				
					|  |  |  |                 mPayload[iv->id].sts[stschan] = statusMi; | 
			
		
	
		
			
				
					|  |  |  |                 DPRINT(DBG_WARN, F("Status change for CH")); | 
			
		
	
		
			
				
					|  |  |  |                 if (mSerialDebug) { | 
			
		
	
		
			
				
					|  |  |  |                     DPRINT(DBG_WARN, F("New state on CH")); | 
			
		
	
		
			
				
					|  |  |  |                     DBGPRINT(String(stschan)); DBGPRINT(F(" (")); | 
			
		
	
		
			
				
					|  |  |  |                     DBGPRINT(String(prntsts)); DBGPRINT(F("): ")); | 
			
		
	
		
			
				
					|  |  |  |                     DBGPRINTLN(iv->getAlarmStr(prntsts)); | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  |             } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |             if ( !mPayload[iv->id].sts[0] || prntsts < mPayload[iv->id].sts[0] ) { | 
			
		
	
		
			
				
					|  |  |  |                 mPayload[iv->id].sts[0] = prntsts; | 
			
		
	
		
			
				
					|  |  |  |                 iv->setValue(iv->getPosByChFld(0, FLD_EVT, rec), rec, prntsts); | 
			
		
	
		
			
				
					|  |  |  |             } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |             if (iv->alarmMesIndex < rec->record[iv->getPosByChFld(0, FLD_EVT, rec)]){ | 
			
		
	
		
			
				
					|  |  |  |             if (iv->alarmMesIndex < rec->record[iv->getPosByChFld(0, FLD_EVT, rec)]) { | 
			
		
	
		
			
				
					|  |  |  |                 iv->alarmMesIndex = rec->record[iv->getPosByChFld(0, FLD_EVT, rec)]; // seems there's no status per channel in 3rd gen. models?!?
 | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 if (mSerialDebug) { | 
			
		
	
		
			
				
					|  |  |  |                     DPRINT_IVID(DBG_INFO, iv->id); | 
			
		
	
		
			
				
					|  |  |  |                     DBGPRINT(F("alarm ID incremented to ")); | 
			
		
	
		
			
				
					|  |  |  |                     DBGPRINTLN(String(iv->alarmMesIndex)); | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  |             } | 
			
		
	
		
			
				
					|  |  |  |             /*if(AlarmData == mPayload[iv->id].txCmd) {
 | 
			
		
	
		
			
				
					|  |  |  |                                 uint8_t i = 0; | 
			
		
	
		
			
				
					|  |  |  |                                 uint16_t code; | 
			
		
	
	
		
			
				
					|  |  | @ -625,6 +497,7 @@ const byteAssign_t InfoAssignment[] = { | 
			
		
	
		
			
				
					|  |  |  |             record_t<> *rec = iv->getRecordStruct(RealTimeRunData_Debug);  // choose the parser
 | 
			
		
	
		
			
				
					|  |  |  |             rec->ts = mPayload[iv->id].ts; | 
			
		
	
		
			
				
					|  |  |  |             mPayload[iv->id].gotFragment = true; | 
			
		
	
		
			
				
					|  |  |  |             mPayload[iv->id].multi_parts += 4; | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |             uint8_t datachan = ( p->packet[0] == 0x89 || p->packet[0] == (0x36 + ALL_FRAMES) ) ? CH1 : | 
			
		
	
		
			
				
					|  |  |  |                            ( p->packet[0] == 0x91 || p->packet[0] == (0x37 + ALL_FRAMES) ) ? CH2 : | 
			
		
	
	
		
			
				
					|  |  | @ -653,50 +526,23 @@ const byteAssign_t InfoAssignment[] = { | 
			
		
	
		
			
				
					|  |  |  |             } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |             if (p->packet[0] >= (0x36 + ALL_FRAMES) ) { | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 /*For MI1500:
 | 
			
		
	
		
			
				
					|  |  |  |                 if (MI1500) { | 
			
		
	
		
			
				
					|  |  |  |                   STAT = (uint8_t)(p->packet[25] ); | 
			
		
	
		
			
				
					|  |  |  |                   FCNT = (uint8_t)(p->packet[26]); | 
			
		
	
		
			
				
					|  |  |  |                   FCODE = (uint8_t)(p->packet[27]); | 
			
		
	
		
			
				
					|  |  |  |                 }*/ | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 /*uint16_t status = (uint8_t)(p->packet[23]);
 | 
			
		
	
		
			
				
					|  |  |  |                 mPayload[iv->id].sts[datachan] = status; | 
			
		
	
		
			
				
					|  |  |  |                 if ( !mPayload[iv->id].sts[0] || status < mPayload[iv->id].sts[0]) { | 
			
		
	
		
			
				
					|  |  |  |                     mPayload[iv->id].sts[0] = status; | 
			
		
	
		
			
				
					|  |  |  |                     iv->setValue(iv->getPosByChFld(0, FLD_EVT, rec), rec, status); | 
			
		
	
		
			
				
					|  |  |  |                 }*/ | 
			
		
	
		
			
				
					|  |  |  |                 miStsConsolidate(iv, datachan, rec, p->packet[23], p->packet[24]); | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 if (p->packet[0] < (0x39 + ALL_FRAMES) ) { | 
			
		
	
		
			
				
					|  |  |  |                     mPayload[iv->id].txCmd++; | 
			
		
	
		
			
				
					|  |  |  |                     mPayload[iv->id].retransmits = 0; // reserve retransmissions for each response
 | 
			
		
	
		
			
				
					|  |  |  |                     mPayload[iv->id].complete = false; | 
			
		
	
		
			
				
					|  |  |  |                 } else { | 
			
		
	
		
			
				
					|  |  |  |                     miComplete(iv); | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  |             } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  | /*
 | 
			
		
	
		
			
				
					|  |  |  |                             if(AlarmData == mPayload[iv->id].txCmd) { | 
			
		
	
		
			
				
					|  |  |  |                                 uint8_t i = 0; | 
			
		
	
		
			
				
					|  |  |  |                                 uint16_t code; | 
			
		
	
		
			
				
					|  |  |  |                                 uint32_t start, end; | 
			
		
	
		
			
				
					|  |  |  |                                 while(1) { | 
			
		
	
		
			
				
					|  |  |  |                                     code = iv->parseAlarmLog(i++, payload, payloadLen, &start, &end); | 
			
		
	
		
			
				
					|  |  |  |                                     if(0 == code) | 
			
		
	
		
			
				
					|  |  |  |                                         break; | 
			
		
	
		
			
				
					|  |  |  |                                     if (NULL != mCbAlarm) | 
			
		
	
		
			
				
					|  |  |  |                                         (mCbAl    { FLD_YT,  UNIT_KWH,  CH0, CALC_YT_CH0,   0, CMD_CALC }, | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                             }*/ | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |             //if ( mPayload[iv->id].complete ||  //4ch device
 | 
			
		
	
		
			
				
					|  |  |  |             if ( p->packet[0] == (0x39 + ALL_FRAMES) ||  //4ch device - last message
 | 
			
		
	
		
			
				
					|  |  |  |                  (iv->type != INV_TYPE_4CH               //other devices
 | 
			
		
	
		
			
				
					|  |  |  |                  && mPayload[iv->id].dataAB[CH0] | 
			
		
	
		
			
				
					|  |  |  |                  && mPayload[iv->id].stsAB[CH0])) { | 
			
		
	
		
			
				
					|  |  |  |                      miComplete(iv); | 
			
		
	
		
			
				
					|  |  |  |         } | 
			
		
	
		
			
				
					|  |  |  |         } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |         void miComplete(Inverter<> *iv) { | 
			
		
	
	
		
			
				
					|  |  | @ -729,51 +575,165 @@ const byteAssign_t InfoAssignment[] = { | 
			
		
	
		
			
				
					|  |  |  |             notify(RealTimeRunData_Debug, iv); | 
			
		
	
		
			
				
					|  |  |  |         } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |         bool build(uint8_t id, bool *complete) { | 
			
		
	
		
			
				
					|  |  |  |         bool build(Inverter<> *iv, bool *complete, bool *fastNext ) { | 
			
		
	
		
			
				
					|  |  |  |             DPRINTLN(DBG_VERBOSE, F("build")); | 
			
		
	
		
			
				
					|  |  |  |             // check if all messages are there
 | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |             *complete = mPayload[id].complete; | 
			
		
	
		
			
				
					|  |  |  |             uint8_t txCmd = mPayload[id].txCmd; | 
			
		
	
		
			
				
					|  |  |  |             *complete = mPayload[iv->id].complete; | 
			
		
	
		
			
				
					|  |  |  |             *fastNext = false; | 
			
		
	
		
			
				
					|  |  |  |             uint8_t txCmd = mPayload[iv->id].txCmd; | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |             if(!*complete) { | 
			
		
	
		
			
				
					|  |  |  |                 DPRINTLN(DBG_VERBOSE, F("incomplete, txCmd is 0x") + String(txCmd, HEX)); | 
			
		
	
		
			
				
					|  |  |  |                 //DBGHEXLN(txCmd);
 | 
			
		
	
		
			
				
					|  |  |  |                 if (txCmd == 0x09 || txCmd == 0x11 || (txCmd >= 0x36 && txCmd <= 0x39)) | 
			
		
	
		
			
				
					|  |  |  |                 //we got some delayed status msgs?!?
 | 
			
		
	
		
			
				
					|  |  |  |                 if (txCmd == 0x09 || txCmd == 0x11) | 
			
		
	
		
			
				
					|  |  |  |                     if (mPayload[iv->id].stsAB[CH0] && mPayload[iv->id].dataAB[CH0]) { | 
			
		
	
		
			
				
					|  |  |  |                       miComplete(iv); | 
			
		
	
		
			
				
					|  |  |  |                       return true; | 
			
		
	
		
			
				
					|  |  |  |                     } | 
			
		
	
		
			
				
					|  |  |  |                     return false; | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                 DPRINTLN(DBG_VERBOSE, F("incomlete, txCmd is 0x") + String(txCmd, HEX)); | 
			
		
	
		
			
				
					|  |  |  |                 if (txCmd >= 0x36 && txCmd <= 0x39) { | 
			
		
	
		
			
				
					|  |  |  |                     return false; | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  |                 if (txCmd == 0x0f) {  //hw info request, at least hw part nr. and version have to be there...
 | 
			
		
	
		
			
				
					|  |  |  |                     bool gotRelevant = iv->getFwVersion() | 
			
		
	
		
			
				
					|  |  |  |                         && iv->getChannelFieldValue(CH0, FLD_PART_NUM, iv->getRecordStruct(InverterDevInform_Simple)); | 
			
		
	
		
			
				
					|  |  |  |                     if (gotRelevant) | 
			
		
	
		
			
				
					|  |  |  |                         *fastNext = true; | 
			
		
	
		
			
				
					|  |  |  |                     return gotRelevant; | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  |             } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |             //check if we want the next request to be executed faster
 | 
			
		
	
		
			
				
					|  |  |  |             if (txCmd == 0x0f) | 
			
		
	
		
			
				
					|  |  |  |                 *fastNext = true; | 
			
		
	
		
			
				
					|  |  |  |             return true; | 
			
		
	
		
			
				
					|  |  |  |         } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  | /*        uint16_t mParseAlarmLog(uint8_t id, uint8_t pyld[], uint8_t len, uint32_t *start, uint32_t *endTime) {
 | 
			
		
	
		
			
				
					|  |  |  |             uint8_t startOff = 2 + id * ALARM_LOG_ENTRY_SIZE; | 
			
		
	
		
			
				
					|  |  |  |             if((startOff + ALARM_LOG_ENTRY_SIZE) > len) | 
			
		
	
		
			
				
					|  |  |  |                 return 0; | 
			
		
	
		
			
				
					|  |  |  |         void miHwDecode(Inverter<> *iv, packet_t *p ) { | 
			
		
	
		
			
				
					|  |  |  |             record_t<> *rec = iv->getRecordStruct(InverterDevInform_All);  // choose the record structure
 | 
			
		
	
		
			
				
					|  |  |  |             rec->ts = mPayload[iv->id].ts; | 
			
		
	
		
			
				
					|  |  |  |             mPayload[iv->id].gotFragment = true; | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |             uint16_t wCode = ((uint16_t)pyld[startOff]) << 8 | pyld[startOff+1]; | 
			
		
	
		
			
				
					|  |  |  |             uint32_t startTimeOffset = 0, endTimeOffset = 0; | 
			
		
	
		
			
				
					|  |  |  | /*
 | 
			
		
	
		
			
				
					|  |  |  | Polling the device software and hardware version number command | 
			
		
	
		
			
				
					|  |  |  | start byte	Command word	 routing address				 target address				 User data	 check	 end byte | 
			
		
	
		
			
				
					|  |  |  | byte[0]	 byte[1]	 byte[2]	 byte[3]	 byte[4]	 byte[5]	 byte[6]	 byte[7]	 byte[8]	 byte[9]	 byte[10]	 byte[11]	 byte[12] | 
			
		
	
		
			
				
					|  |  |  | 0x7e	 0x0f	 xx	 xx	 xx	 xx	 YY	 YY	 YY	 YY	 0x00	 CRC	 0x7f | 
			
		
	
		
			
				
					|  |  |  | Command Receipt - First Frame | 
			
		
	
		
			
				
					|  |  |  | start byte	Command word	 target address				 routing address				 Multi-frame marking	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 check	 end byte | 
			
		
	
		
			
				
					|  |  |  | byte[0]	 byte[1]	 byte[2]	 byte[3]	 byte[4]	 byte[5]	 byte[6]	 byte[7]	 byte[8]	 byte[9]	 byte[10]	 byte[11]	 byte[12]	 byte[13]	 byte[14]	 byte[15]	 byte[16]	 byte[17]	 byte[18]	 byte[19]	 byte[20]	 byte[21]	 byte[22]	 byte[23]	 byte[24]	 byte[25]	 byte[26]	 byte[27]	 byte[28] | 
			
		
	
		
			
				
					|  |  |  | 0x7e	 0x8f	 YY	 YY	 YY	 YY	 xx	 xx	 xx	 xx	 0x00	 USFWBuild_VER		 APPFWBuild_VER		 APPFWBuild_YYYY		 APPFWBuild_MMDD		 APPFWBuild_HHMM		 APPFW_PN				 HW_VER		 CRC	 0x7f | 
			
		
	
		
			
				
					|  |  |  | Command Receipt - Second Frame | 
			
		
	
		
			
				
					|  |  |  | start byte	Command word	 target address				 routing address				 Multi-frame marking	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 check	 end byte | 
			
		
	
		
			
				
					|  |  |  | byte[0]	 byte[1]	 byte[2]	 byte[3]	 byte[4]	 byte[5]	 byte[6]	 byte[7]	 byte[8]	 byte[9]	 byte[10]	 byte[11]	 byte[12]	 byte[13]	 byte[14]	 byte[15]	 byte[16]	 byte[17]	 byte[18]	 byte[19]	 byte[20]	 byte[21]	 byte[22]	 byte[23]	 byte[24]	 byte[25]	 byte[26]	 byte[27]	 byte[28] | 
			
		
	
		
			
				
					|  |  |  | 0x7e	 0x8f	 YY	 YY	 YY	 YY	 xx	 xx	 xx	 xx	 0x01	 HW_PN				 HW_FB_TLmValue		 HW_FB_ReSPRT		 HW_GridSamp_ResValule		 HW_ECapValue		 Matching_APPFW_PN				 CRC	 0x7f | 
			
		
	
		
			
				
					|  |  |  | Command receipt - third frame | 
			
		
	
		
			
				
					|  |  |  | start byte	Command word	 target address				 routing address				 Multi-frame marking	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 User data	 check	 end byte | 
			
		
	
		
			
				
					|  |  |  | byte[0]	 byte[1]	 byte[2]	 byte[3]	 byte[4]	 byte[5]	 byte[6]	 byte[7]	 byte[8]	 byte[9]	 byte[10]	 byte[11]	 byte[12]	 byte[13]	 byte[14]	 byte[15]	 byte[16]	 byte[15]	 byte[16]	 byte[17]	 byte[18] | 
			
		
	
		
			
				
					|  |  |  | 0x7e	 0x8f	 YY	 YY	 YY	 YY	 xx	 xx	 xx	 xx	 0x12	 APPFW_MINVER		 HWInfoAddr		 PNInfoCRC_gusv		 PNInfoCRC_gusv		 CRC	 0x7f | 
			
		
	
		
			
				
					|  |  |  | */ | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |             if (((wCode >> 13) & 0x01) == 1) // check if is AM or PM
 | 
			
		
	
		
			
				
					|  |  |  |                 startTimeOffset = 12 * 60 * 60; | 
			
		
	
		
			
				
					|  |  |  |             if (((wCode >> 12) & 0x01) == 1) // check if is AM or PM
 | 
			
		
	
		
			
				
					|  |  |  |                 endTimeOffset = 12 * 60 * 60; | 
			
		
	
		
			
				
					|  |  |  | /*
 | 
			
		
	
		
			
				
					|  |  |  | case InverterDevInform_All: | 
			
		
	
		
			
				
					|  |  |  |             rec->length  = (uint8_t)(HMINFO_LIST_LEN); | 
			
		
	
		
			
				
					|  |  |  |             rec->assign  = (byteAssign_t *)InfoAssignment; | 
			
		
	
		
			
				
					|  |  |  |             rec->pyldLen = HMINFO_PAYLOAD_LEN; | 
			
		
	
		
			
				
					|  |  |  |             break; | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |             *start     = (((uint16_t)pyld[startOff + 4] << 8) | ((uint16_t)pyld[startOff + 5])) + startTimeOffset; | 
			
		
	
		
			
				
					|  |  |  |             *endTime   = (((uint16_t)pyld[startOff + 6] << 8) | ((uint16_t)pyld[startOff + 7])) + endTimeOffset; | 
			
		
	
		
			
				
					|  |  |  | const byteAssign_t InfoAssignment[] = { | 
			
		
	
		
			
				
					|  |  |  | { FLD_FW_VERSION,           UNIT_NONE,   CH0,  0, 2, 1 }, | 
			
		
	
		
			
				
					|  |  |  | { FLD_FW_BUILD_YEAR,        UNIT_NONE,   CH0,  2, 2, 1 }, | 
			
		
	
		
			
				
					|  |  |  | { FLD_FW_BUILD_MONTH_DAY,   UNIT_NONE,   CH0,  4, 2, 1 }, | 
			
		
	
		
			
				
					|  |  |  | { FLD_FW_BUILD_HOUR_MINUTE, UNIT_NONE,   CH0,  6, 2, 1 }, | 
			
		
	
		
			
				
					|  |  |  | { FLD_BOOTLOADER_VER,       UNIT_NONE,   CH0,  8, 2, 1 } | 
			
		
	
		
			
				
					|  |  |  | }; | 
			
		
	
		
			
				
					|  |  |  | */ | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |             DPRINTLN(DBG_INFO, "Alarm #" + String(pyld[startOff+1]) + " '" + String(getAlarmStr(pyld[startOff+1])) + "' start: " + ah::getTimeStr(*start) + ", end: " + ah::getTimeStr(*endTime)); | 
			
		
	
		
			
				
					|  |  |  |             return pyld[startOff+1]; | 
			
		
	
		
			
				
					|  |  |  |             if ( p->packet[9] == 0x00 ) {//first frame
 | 
			
		
	
		
			
				
					|  |  |  |                 //FLD_FW_VERSION
 | 
			
		
	
		
			
				
					|  |  |  |                 for (uint8_t i = 0; i < 5; i++) { | 
			
		
	
		
			
				
					|  |  |  |                     iv->setValue(i, rec, (float) ((p->packet[(12+2*i)] << 8) + p->packet[(13+2*i)])/1); | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  |                 iv->isConnected = true; | 
			
		
	
		
			
				
					|  |  |  |                 if(mSerialDebug) { | 
			
		
	
		
			
				
					|  |  |  |                     DPRINT_IVID(DBG_INFO, iv->id); | 
			
		
	
		
			
				
					|  |  |  |                     DPRINT(DBG_INFO,F("HW_VER is ")); | 
			
		
	
		
			
				
					|  |  |  |                     DBGPRINTLN(String((p->packet[24] << 8) + p->packet[25])); | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  |                 record_t<> *rec = iv->getRecordStruct(InverterDevInform_Simple);  // choose the record structure
 | 
			
		
	
		
			
				
					|  |  |  |                 rec->ts = mPayload[iv->id].ts; | 
			
		
	
		
			
				
					|  |  |  |                 iv->setValue(1, rec, (uint32_t) ((p->packet[24] << 8) + p->packet[25])/1); | 
			
		
	
		
			
				
					|  |  |  |                 mPayload[iv->id].multi_parts +=4; | 
			
		
	
		
			
				
					|  |  |  |             } else if ( p->packet[9] == 0x01 || p->packet[9] == 0x10 ) {//second frame for MI, 3rd gen. answers in 0x10
 | 
			
		
	
		
			
				
					|  |  |  |                 DPRINT_IVID(DBG_INFO, iv->id); | 
			
		
	
		
			
				
					|  |  |  |                 if ( p->packet[9] == 0x01 ) { | 
			
		
	
		
			
				
					|  |  |  |                     DBGPRINTLN(F("got 2nd frame (hw info)")); | 
			
		
	
		
			
				
					|  |  |  |                     /* according to xlsx (different start byte -1!)
 | 
			
		
	
		
			
				
					|  |  |  |                     byte[11] to	 byte[14] HW_PN | 
			
		
	
		
			
				
					|  |  |  |                     byte[15]	 byte[16] HW_FB_TLmValue | 
			
		
	
		
			
				
					|  |  |  |                     byte[17]	 byte[18] HW_FB_ReSPRT | 
			
		
	
		
			
				
					|  |  |  |                     byte[19]	 byte[20] HW_GridSamp_ResValule | 
			
		
	
		
			
				
					|  |  |  |                     byte[21]	 byte[22] HW_ECapValue | 
			
		
	
		
			
				
					|  |  |  |                     byte[23] to	 byte[26] Matching_APPFW_PN*/ | 
			
		
	
		
			
				
					|  |  |  |                     DPRINT(DBG_INFO,F("HW_PartNo ")); | 
			
		
	
		
			
				
					|  |  |  |                     DBGPRINTLN(String((uint32_t) (((p->packet[10] << 8) | p->packet[11]) << 8 | p->packet[12]) << 8 | p->packet[13])); | 
			
		
	
		
			
				
					|  |  |  |                     record_t<> *rec = iv->getRecordStruct(InverterDevInform_Simple);  // choose the record structure
 | 
			
		
	
		
			
				
					|  |  |  |                     rec->ts = mPayload[iv->id].ts; | 
			
		
	
		
			
				
					|  |  |  |                     iv->setValue(0, rec, (uint32_t) ((((p->packet[10] << 8) | p->packet[11]) << 8 | p->packet[12]) << 8 | p->packet[13])/1); | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |                     if(mSerialDebug) { | 
			
		
	
		
			
				
					|  |  |  |                         DPRINT(DBG_INFO,F("HW_FB_TLmValue ")); | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINTLN(String((p->packet[14] << 8) + p->packet[15])); | 
			
		
	
		
			
				
					|  |  |  |                         DPRINT(DBG_INFO,F("HW_FB_ReSPRT ")); | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINTLN(String((p->packet[16] << 8) + p->packet[17])); | 
			
		
	
		
			
				
					|  |  |  |                         DPRINT(DBG_INFO,F("HW_GridSamp_ResValule ")); | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINTLN(String((p->packet[18] << 8) + p->packet[19])); | 
			
		
	
		
			
				
					|  |  |  |                         DPRINT(DBG_INFO,F("HW_ECapValue ")); | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINTLN(String((p->packet[20] << 8) + p->packet[21])); | 
			
		
	
		
			
				
					|  |  |  |                         DPRINT(DBG_INFO,F("Matching_APPFW_PN ")); | 
			
		
	
		
			
				
					|  |  |  |                         DBGPRINTLN(String((uint32_t) (((p->packet[22] << 8) | p->packet[23]) << 8 | p->packet[24]) << 8 | p->packet[25])); | 
			
		
	
		
			
				
					|  |  |  |                     } | 
			
		
	
		
			
				
					|  |  |  |                     //notify(InverterDevInform_Simple, iv);
 | 
			
		
	
		
			
				
					|  |  |  |                     mPayload[iv->id].multi_parts +=2; | 
			
		
	
		
			
				
					|  |  |  |                     notify(InverterDevInform_All, iv); | 
			
		
	
		
			
				
					|  |  |  |                 } else { | 
			
		
	
		
			
				
					|  |  |  |                     DBGPRINTLN(F("3rd gen. inverter!")); | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |             } else if ( p->packet[9] == 0x12 ) {//3rd frame
 | 
			
		
	
		
			
				
					|  |  |  |                 DPRINT_IVID(DBG_INFO, iv->id); | 
			
		
	
		
			
				
					|  |  |  |                 DBGPRINTLN(F("got 3rd frame (hw info)")); | 
			
		
	
		
			
				
					|  |  |  |                 /* according to xlsx (different start byte -1!)
 | 
			
		
	
		
			
				
					|  |  |  |                     byte[11]	 byte[12] APPFW_MINVER | 
			
		
	
		
			
				
					|  |  |  |                     byte[13]	 byte[14] HWInfoAddr | 
			
		
	
		
			
				
					|  |  |  |                     byte[15]	 byte[16] PNInfoCRC_gusv | 
			
		
	
		
			
				
					|  |  |  |                     byte[15]	 byte[16] PNInfoCRC_gusv (this really is double mentionned in xlsx...) | 
			
		
	
		
			
				
					|  |  |  |                 */ | 
			
		
	
		
			
				
					|  |  |  |                 if(mSerialDebug) { | 
			
		
	
		
			
				
					|  |  |  |                     DPRINT(DBG_INFO,F("APPFW_MINVER ")); | 
			
		
	
		
			
				
					|  |  |  |                     DBGPRINTLN(String((p->packet[10] << 8) + p->packet[11])); | 
			
		
	
		
			
				
					|  |  |  |                     DPRINT(DBG_INFO,F("HWInfoAddr ")); | 
			
		
	
		
			
				
					|  |  |  |                     DBGPRINTLN(String((p->packet[12] << 8) + p->packet[13])); | 
			
		
	
		
			
				
					|  |  |  |                     DPRINT(DBG_INFO,F("PNInfoCRC_gusv ")); | 
			
		
	
		
			
				
					|  |  |  |                     DBGPRINTLN(String((p->packet[14] << 8) + p->packet[15])); | 
			
		
	
		
			
				
					|  |  |  |                 } | 
			
		
	
		
			
				
					|  |  |  |                 mPayload[iv->id].multi_parts++; | 
			
		
	
		
			
				
					|  |  |  |             } | 
			
		
	
		
			
				
					|  |  |  |             if (mPayload[iv->id].multi_parts > 5) { | 
			
		
	
		
			
				
					|  |  |  |                 iv->setQueuedCmdFinished(); | 
			
		
	
		
			
				
					|  |  |  |                 mPayload[iv->id].complete = true; | 
			
		
	
		
			
				
					|  |  |  |                 mPayload[iv->id].requested= false; | 
			
		
	
		
			
				
					|  |  |  |                 mStat->rxSuccess++; | 
			
		
	
		
			
				
					|  |  |  |             } | 
			
		
	
		
			
				
					|  |  |  |         } | 
			
		
	
		
			
				
					|  |  |  | */ | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |         void reset(uint8_t id, bool clrSts = false) { | 
			
		
	
		
			
				
					|  |  |  |             //DPRINT_IVID(DBG_INFO, id);
 | 
			
		
	
		
			
				
					|  |  |  |             //DBGPRINTLN(F("resetPayload"));
 | 
			
		
	
		
			
				
					|  |  |  |             memset(mPayload[id].len, 0, MAX_PAYLOAD_ENTRIES); | 
			
		
	
		
			
				
					|  |  |  |             mPayload[id].gotFragment = false; | 
			
		
	
		
			
				
					|  |  |  |             /*mPayload[id].maxPackId   = MAX_PAYLOAD_ENTRIES;
 | 
			
		
	
		
			
				
					|  |  |  |             mPayload[id].lastFound   = false;*/ | 
			
		
	
		
			
				
					|  |  |  |             mPayload[id].rtrRes      = 0; | 
			
		
	
		
			
				
					|  |  |  |             mPayload[id].multi_parts  = 0; | 
			
		
	
		
			
				
					|  |  |  |             mPayload[id].retransmits = 0; | 
			
		
	
		
			
				
					|  |  |  |             mPayload[id].complete    = false; | 
			
		
	
		
			
				
					|  |  |  |             mPayload[id].dataAB[CH0] = true; //required for 1CH and 2CH devices
 | 
			
		
	
	
		
			
				
					|  |  | @ -796,8 +756,6 @@ const byteAssign_t InfoAssignment[] = { | 
			
		
	
		
			
				
					|  |  |  |             } | 
			
		
	
		
			
				
					|  |  |  |         } | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |         IApp *mApp; | 
			
		
	
		
			
				
					|  |  |  |         HMSYSTEM *mSys; | 
			
		
	
		
			
				
					|  |  |  |         HMRADIO *mRadio; | 
			
		
	
	
		
			
				
					|  |  | 
 |