コード例 #1
0
ファイル: OTGWBase.cpp プロジェクト: ZaaaV/domoticz
void OTGWBase::ParseLine()
{
	if (m_bufferpos<2)
		return;
	std::string sLine((char*)&m_buffer);

	std::vector<std::string> results;
	StringSplit(sLine,",",results);
	if (results.size()==25)
	{
		//status report
		//0    Status (MsgID=0) - Printed as two 8-bit bitfields
		//1    Control setpoint (MsgID=1) - Printed as a floating point value
		//2    Remote parameter flags (MsgID= 6) - Printed as two 8-bit bitfields
		//3    Maximum relative modulation level (MsgID=14) - Printed as a floating point value
		//4    Boiler capacity and modulation limits (MsgID=15) - Printed as two bytes
		//5    Room Setpoint (MsgID=16) - Printed as a floating point value
		//6    Relative modulation level (MsgID=17) - Printed as a floating point value
		//7    CH water pressure (MsgID=18) - Printed as a floating point value
		//8    Room temperature (MsgID=24) - Printed as a floating point value
		//9    Boiler water temperature (MsgID=25) - Printed as a floating point value
		//10    DHW temperature (MsgID=26) - Printed as a floating point value
		//11    Outside temperature (MsgID=27) - Printed as a floating point value
		//12    Return water temperature (MsgID=28) - Printed as a floating point value
		//13    DHW setpoint boundaries (MsgID=48) - Printed as two bytes
		//14    Max CH setpoint boundaries (MsgID=49) - Printed as two bytes
		//15    DHW setpoint (MsgID=56) - Printed as a floating point value
		//16    Max CH water setpoint (MsgID=57) - Printed as a floating point value
		//17    Burner starts (MsgID=116) - Printed as a decimal value
		//18    CH pump starts (MsgID=117) - Printed as a decimal value
		//19    DHW pump/valve starts (MsgID=118) - Printed as a decimal value
		//20    DHW burner starts (MsgID=119) - Printed as a decimal value
		//21    Burner operation hours (MsgID=120) - Printed as a decimal value
		//22    CH pump operation hours (MsgID=121) - Printed as a decimal value
		//23    DHW pump/valve operation hours (MsgID=122) - Printed as a decimal value
		//24    DHW burner operation hours (MsgID=123) - Printed as a decimal value 
		_tOTGWStatus _status;
		int idx=0;

		_status.MsgID=results[idx++];
		if (_status.MsgID.size()==17)
		{
			bool bCH_enabled=(_status.MsgID[7]=='1');										UpdateSwitch(101,bCH_enabled,"CH_enabled");
			bool bDHW_enabled=(_status.MsgID[6]=='1');										UpdateSwitch(102,bDHW_enabled,"DHW_enabled");
			bool bCooling_enable=(_status.MsgID[5]=='1');									UpdateSwitch(103,bCooling_enable,"Cooling_enable");
			bool bOTC_active=(_status.MsgID[4]=='1');										UpdateSwitch(104,bOTC_active,"OTC_active");
			bool bCH2_enabled=(_status.MsgID[3]=='1');										UpdateSwitch(105,bCH2_enabled,"CH2_enabled");

			bool bFault_indication=(_status.MsgID[9+7]=='1');								UpdateSwitch(110,bFault_indication,"Fault_indication");
			bool bCH_active=(_status.MsgID[9+6]=='1');										UpdateSwitch(111,bCH_active,"CH_active");
			bool bDHW_active=(_status.MsgID[9+5]=='1');										UpdateSwitch(112,bDHW_active,"DHW_active");
			bool bFlameOn=(_status.MsgID[9+4]=='1');										UpdateSwitch(113,bFlameOn,"FlameOn");
			bool bCooling_Mode_Active=(_status.MsgID[9+3]=='1');							UpdateSwitch(114,bCooling_Mode_Active,"Cooling_Mode_Active");
			bool bCH2_Active=(_status.MsgID[9+2]=='1');										UpdateSwitch(115,bCH2_Active,"CH2_Active");
			bool bDiagnosticEvent=(_status.MsgID[9+1]=='1');								UpdateSwitch(116,bDiagnosticEvent,"DiagnosticEvent");
		}
		
		_status.Control_setpoint=(float)atof(results[idx++].c_str());						UpdateTempSensor(idx-1,_status.Control_setpoint,"Control Setpoint");
		_status.Remote_parameter_flags=results[idx++];
		_status.Maximum_relative_modulation_level=(float)atof(results[idx++].c_str());
		_status.Boiler_capacity_and_modulation_limits=results[idx++];
		_status.Room_Setpoint=(float)atof(results[idx++].c_str());							UpdateSetPointSensor(idx-1,_status.Room_Setpoint,"Room Setpoint");
		_status.Relative_modulation_level=(float)atof(results[idx++].c_str());
		_status.CH_water_pressure=(float)atof(results[idx++].c_str());
		if (_status.CH_water_pressure!=0)
		{
			UpdatePressureSensor(idx-1,_status.CH_water_pressure,"CH Water Pressure");
		}

		_status.Room_temperature=(float)atof(results[idx++].c_str());						UpdateTempSensor(idx-1,_status.Room_temperature,"Room Temperature");
		_status.Boiler_water_temperature=(float)atof(results[idx++].c_str());				UpdateTempSensor(idx-1,_status.Boiler_water_temperature,"Boiler Water Temperature");
		_status.DHW_temperature=(float)atof(results[idx++].c_str());						UpdateTempSensor(idx-1,_status.DHW_temperature,"DHW Temperature");
		_status.Outside_temperature=(float)atof(results[idx++].c_str());					UpdateTempSensor(idx-1,_status.Outside_temperature,"Outside Temperature");
		_status.Return_water_temperature=(float)atof(results[idx++].c_str());				UpdateTempSensor(idx-1,_status.Return_water_temperature,"Return Water Temperature");
		_status.DHW_setpoint_boundaries=results[idx++];
		_status.Max_CH_setpoint_boundaries=results[idx++];
		_status.DHW_setpoint=(float)atof(results[idx++].c_str());							UpdateSetPointSensor(idx-1,_status.DHW_setpoint,"DHW Setpoint");
		_status.Max_CH_water_setpoint=(float)atof(results[idx++].c_str());					UpdateSetPointSensor(idx-1,_status.Max_CH_water_setpoint,"Max_CH Water Setpoint");
		_status.Burner_starts=atol(results[idx++].c_str());
		_status.CH_pump_starts=atol(results[idx++].c_str());
		_status.DHW_pump_valve_starts=atol(results[idx++].c_str());
		_status.DHW_burner_starts=atol(results[idx++].c_str());
		_status.Burner_operation_hours=atol(results[idx++].c_str());
		_status.CH_pump_operation_hours=atol(results[idx++].c_str());
		_status.DHW_pump_valve_operation_hours=atol(results[idx++].c_str());
		_status.DHW_burner_operation_hours=atol(results[idx++].c_str());
		return;
	}
	else
	{
		if (sLine=="SE")
		{
			_log.Log(LOG_ERROR,"OTGW: Error received!");
		}
		else
		{
			if (
				(sLine.find("OT")==std::string::npos)&&
				(sLine.find("PS")==std::string::npos)
				)
			{
				//Dont report OT/PS feedback
				_log.Log(LOG_STATUS,"OTGW: %s",sLine.c_str());
			}
		}
	}

}
コード例 #2
0
ファイル: DavisLoggerSerial.cpp プロジェクト: n326/domoticz
bool CDavisLoggerSerial::HandleLoopData(const unsigned char *data, size_t len)
{
	const uint8_t *pData=data+1;

#ifndef DEBUG_DAVIS
	if (len!=100)
		return false;

	if (
		(data[1]!='L')||
		(data[2]!='O')||
		(data[3]!='O')||
		(data[96]!=0x0a)||
		(data[97]!=0x0d)
		)
		return false;
	bool bIsRevA = (data[4]=='P');
#else
//	FILE *fOut=fopen("davisrob.bin","wb+");
//	fwrite(data,1,len,fOut);
//	fclose(fOut);
	unsigned char szBuffer[200];
	FILE *fIn=fopen("E:\\davis2.bin","rb+");
	//FILE *fIn=fopen("davisrob.bin","rb+");
	fread(&szBuffer,1,100,fIn);
	fclose(fIn);
	pData=szBuffer+1;
	bool bIsRevA(szBuffer[4]=='P');
#endif

	RBUF tsen;
	memset(&tsen,0,sizeof(RBUF));


	unsigned char tempIdx=1;

	bool bBaroValid=false;
	float BaroMeter=0;
	bool bInsideTemperatureValid=false;
	float InsideTemperature=0;
	bool bInsideHumidityValid=false;
	int InsideHumidity=0;
	bool bOutsideTemperatureValid=false;
	float OutsideTemperature=0;
	bool bOutsideHumidityValid=false;
	int OutsideHumidity=0;

	bool bWindDirectionValid=false;
	int WindDirection=0;

	bool bWindSpeedValid=false;
	float WindSpeed=0;
	bool bWindSpeedAVR10Valid=false;
	float WindSpeedAVR10=0;

	bool bUVValid=false;
	float UV=0;

	//Barometer
	if ((pData[7]!=0xFF)&&(pData[8]!=0xFF))
	{
		bBaroValid=true;
		BaroMeter=((unsigned int)((pData[8] << 8) | pData[7])) / 29.53f; //in hPa
	}
	//Inside Temperature
	if ((pData[9]!=0xFF)||(pData[10]!=0x7F))
	{
		bInsideTemperatureValid=true;
		InsideTemperature=((unsigned int)((pData[10] << 8) | pData[9])) / 10.f;
		InsideTemperature = (InsideTemperature - 32.0f) * 5.0f / 9.0f;
	}
	//Inside Humidity
	if (pData[11]!=0xFF)
	{
		InsideHumidity=pData[11];
		if (InsideHumidity<101)
			bInsideHumidityValid=true;
	}

	if (bBaroValid&&bInsideTemperatureValid&&bInsideHumidityValid)
	{
		memset(&tsen,0,sizeof(RBUF));
		tsen.TEMP_HUM_BARO.packetlength=sizeof(tsen.TEMP_HUM_BARO)-1;
		tsen.TEMP_HUM_BARO.packettype=pTypeTEMP_HUM_BARO;
		tsen.TEMP_HUM_BARO.subtype=sTypeTHBFloat;
		tsen.TEMP_HUM_BARO.battery_level=9;
		tsen.TEMP_HUM_BARO.rssi=12;
		tsen.TEMP_HUM_BARO.id1=0;
		tsen.TEMP_HUM_BARO.id2=tempIdx++;

		tsen.TEMP_HUM_BARO.tempsign=(InsideTemperature>=0)?0:1;
		int at10=round(abs(InsideTemperature*10.0f));
		tsen.TEMP_HUM_BARO.temperatureh=(BYTE)(at10/256);
		at10-=(tsen.TEMP_HUM_BARO.temperatureh*256);
		tsen.TEMP_HUM_BARO.temperaturel=(BYTE)(at10);
		tsen.TEMP_HUM_BARO.humidity=(BYTE)InsideHumidity;
		tsen.TEMP_HUM_BARO.humidity_status=Get_Humidity_Level(tsen.TEMP_HUM.humidity);

		int ab10=round(BaroMeter*10.0f);
		tsen.TEMP_HUM_BARO.baroh=(BYTE)(ab10/256);
		ab10-=(tsen.TEMP_HUM_BARO.baroh*256);
		tsen.TEMP_HUM_BARO.barol=(BYTE)(ab10);

		uint8_t forecastitem=pData[89];
		int forecast=0;

		if ((forecastitem&0x01)==0x01)
			forecast=wsbaroforcast_rain;
		else if ((forecastitem&0x02)==0x02)
			forecast=wsbaroforcast_cloudy;
		else if ((forecastitem&0x04)==0x04)
			forecast=wsbaroforcast_some_clouds;
		else if ((forecastitem&0x08)==0x08)
			forecast=wsbaroforcast_sunny;
		else if ((forecastitem&0x10)==0x10)
			forecast=wsbaroforcast_snow;

		tsen.TEMP_HUM_BARO.forecast=forecast;

		sDecodeRXMessage(this, (const unsigned char *)&tsen.TEMP_HUM_BARO);//decode message
	}

	//Outside Temperature
	if ((pData[12]!=0xFF)||(pData[13]!=0x7F))
	{
		bOutsideTemperatureValid=true;
		OutsideTemperature=((unsigned int)((pData[13] << 8) | pData[12])) / 10.f;

		OutsideTemperature = (OutsideTemperature - 32.0f) * 5.0f / 9.0f;
	}
	//Outside Humidity
	if (pData[33]!=0xFF)
	{
		OutsideHumidity=pData[33];
		if (OutsideHumidity<101)
			bOutsideHumidityValid=true;
	}
	if (bOutsideTemperatureValid||bOutsideHumidityValid)
	{
		//add outside sensor
		memset(&tsen,0,sizeof(RBUF));

		if ((bOutsideTemperatureValid)&&(bOutsideHumidityValid))
		{
			//Temp+hum
			UpdateTempHumSensor(tempIdx++,OutsideTemperature,OutsideHumidity);
		}
		else if (bOutsideTemperatureValid)
		{
			//Temp
			UpdateTempSensor(tempIdx++,OutsideTemperature);
		}
		else if (bOutsideHumidityValid)
		{
			//hum
			UpdateHumSensor(tempIdx++,OutsideHumidity);
		}
	}

	tempIdx=10;
	//Add Extra Temp/Hum Sensors
	int iTmp;
	for (int iTmp=0; iTmp<7; iTmp++)
	{
		bool bTempValid=false;
		bool bHumValid=false;
		float temp=0;
		uint8_t hum=0;

		if (pData[18+iTmp]!=0xFF)
		{
			bTempValid=true;
			temp=pData[18+iTmp]-90.0f;
			temp = (temp - 32.0f) * 5.0f / 9.0f;
		}
		if (pData[34+iTmp]!=0xFF)
		{
			bHumValid=true;
			hum=pData[34+iTmp];
		}
		if ((bTempValid)&&(bHumValid))
		{
			//Temp+hum
			UpdateTempHumSensor(tempIdx++,temp,hum);
		}
		else if (bTempValid)
		{
			//Temp
			UpdateTempSensor(tempIdx++,temp);
		}
		else if (bHumValid)
		{
			//hum
			UpdateHumSensor(tempIdx++,hum);
		}
	}

	tempIdx=20;
	//Add Extra Soil Temp Sensors
	for (iTmp=0; iTmp<4; iTmp++)
	{
		bool bTempValid=false;
		float temp=0;

		if (pData[25+iTmp]!=0xFF)
		{
			bTempValid=true;
			temp=pData[25+iTmp]-90.0f;
			temp = (temp - 32.0f) * 5.0f / 9.0f;
		}
		if (bTempValid)
		{
			UpdateTempSensor(tempIdx++,temp);
		}
	}

	tempIdx=30;
	//Add Extra Leaf Temp Sensors
	for (iTmp=0; iTmp<4; iTmp++)
	{
		bool bTempValid=false;
		float temp=0;

		if (pData[29+iTmp]!=0xFF)
		{
			bTempValid=true;
			temp=pData[29+iTmp]-90.0f;
			temp = (temp - 32.0f) * 5.0f / 9.0f;
		}
		if (bTempValid)
		{
			UpdateTempSensor(tempIdx++,temp);
		}
	}

	//Wind Speed
	if (pData[14]!=0xFF)
	{
		bWindSpeedValid=true;
		WindSpeed=(pData[14])*(4.0f/9.0f);
	}
	//Wind Speed AVR 10 minutes
	if (pData[15]!=0xFF)
	{
		bWindSpeedAVR10Valid=true;
		WindSpeedAVR10=(pData[15])*(4.0f/9.0f);
	}
	//Wind Direction
	if ((pData[16]!=0xFF)&&(pData[17]!=0x7F))
	{
		bWindDirectionValid=true;
		WindDirection=((unsigned int)((pData[17] << 8) | pData[16]));
	}

	if ((bWindSpeedValid)&&(bWindDirectionValid))
	{
		memset(&tsen,0,sizeof(RBUF));
		tsen.WIND.packetlength=sizeof(tsen.WIND)-1;
		tsen.WIND.packettype=pTypeWIND;
		tsen.WIND.subtype=sTypeWINDNoTemp;
		tsen.WIND.battery_level=9;
		tsen.WIND.rssi=12;
		tsen.WIND.id1=0;
		tsen.WIND.id2=1;

		int aw=round(WindDirection);
		tsen.WIND.directionh=(BYTE)(aw/256);
		aw-=(tsen.WIND.directionh*256);
		tsen.WIND.directionl=(BYTE)(aw);

		tsen.WIND.av_speedh=0;
		tsen.WIND.av_speedl=0;
		int sw=round(WindSpeed*10.0f);
		tsen.WIND.av_speedh=(BYTE)(sw/256);
		sw-=(tsen.WIND.av_speedh*256);
		tsen.WIND.av_speedl=(BYTE)(sw);

		tsen.WIND.gusth=0;
		tsen.WIND.gustl=0;

		//this is not correct, why no wind temperature? and only chill?
		tsen.WIND.chillh=0;
		tsen.WIND.chilll=0;
		tsen.WIND.temperatureh=0;
		tsen.WIND.temperaturel=0;
		if (bOutsideTemperatureValid)
		{
			tsen.WIND.tempsign=(OutsideTemperature>=0)?0:1;
			tsen.WIND.chillsign=(OutsideTemperature>=0)?0:1;
			int at10=round(abs(OutsideTemperature*10.0f));
			tsen.WIND.temperatureh=(BYTE)(at10/256);
			tsen.WIND.chillh=(BYTE)(at10/256);
			at10-=(tsen.WIND.chillh*256);
			tsen.WIND.temperaturel=(BYTE)(at10);
			tsen.WIND.chilll=(BYTE)(at10);
		}

		sDecodeRXMessage(this, (const unsigned char *)&tsen.WIND);//decode message
	}

	//UV
	if (pData[43]!=0xFF)
	{
		UV=(pData[43])/10.0f;
		if (UV<100)
			bUVValid=true;
	}
	if (bUVValid)
	{
		RBUF tsen;
		memset(&tsen,0,sizeof(RBUF));
		tsen.UV.packetlength=sizeof(tsen.UV)-1;
		tsen.UV.packettype=pTypeUV;
		tsen.UV.subtype=sTypeUV1;
		tsen.UV.battery_level=9;
		tsen.UV.rssi=12;
		tsen.UV.id1=0;
		tsen.UV.id2=1;

		tsen.UV.uv=(BYTE)round(UV*10);
		sDecodeRXMessage(this, (const unsigned char *)&tsen.UV);//decode message
	}
	
	//Rain Rate
	if ((pData[41]!=0xFF)&&(pData[42]!=0xFF))
	{
		float rainRate=((unsigned int)((pData[42] << 8) | pData[41])) / 100.0f; //inches
		rainRate*=25.4f; //mm
	}
	//Rain Day
	if ((pData[50]!=0xFF)&&(pData[51]!=0xFF))
	{
		float rainDay=((unsigned int)((pData[51] << 8) | pData[50])) / 100.0f; //inches
		rainDay*=25.4f; //mm
	}
	//Rain Year
	if ((pData[54]!=0xFF)&&(pData[55]!=0xFF))
	{
		float rainYear=((unsigned int)((pData[55] << 8) | pData[54])) / 100.0f; //inches
		rainYear*=25.4f; //mm

		RBUF tsen;
		memset(&tsen,0,sizeof(RBUF));
		tsen.RAIN.packetlength=sizeof(tsen.RAIN)-1;
		tsen.RAIN.packettype=pTypeRAIN;
		tsen.RAIN.subtype=sTypeRAIN3;
		tsen.RAIN.battery_level=9;
		tsen.RAIN.rssi=12;
		tsen.RAIN.id1=0;
		tsen.RAIN.id2=1;

		tsen.RAIN.rainrateh=0;
		tsen.RAIN.rainratel=0;

		int tr10=int(float(rainYear)*10.0f);

		tsen.RAIN.raintotal1=0;
		tsen.RAIN.raintotal2=(BYTE)(tr10/256);
		tr10-=(tsen.RAIN.raintotal2*256);
		tsen.RAIN.raintotal3=(BYTE)(tr10);

		sDecodeRXMessage(this, (const unsigned char *)&tsen.RAIN);//decode message
	}

	//Solar Radiation
	if ((pData[44]!=0xFF)&&(pData[45]!=0x7F))
	{
		unsigned int solarRadiation=((unsigned int)((pData[45] << 8) | pData[44]));//Watt/M2
		_tGeneralDevice gdevice;
		gdevice.subtype=sTypeSolarRadiation;
		gdevice.floatval1=float(solarRadiation);
		sDecodeRXMessage(this, (const unsigned char *)&gdevice);

	}

	//Soil Moistures
	for (int iMoister=0; iMoister<4; iMoister++)
	{
		if (pData[62+iMoister]!=0xFF)
		{
			int moister=pData[62+iMoister];
			SendMoistureSensor(1 + iMoister, 255, moister, "Moisture");
		}
	}

	//Leaf Wetness
	for (int iLeaf=0; iLeaf<4; iLeaf++)
	{
		if (pData[66+iLeaf]!=0xFF)
		{
			int leaf_wetness=pData[66+iLeaf];

			_tGeneralDevice gdevice;
			gdevice.subtype=sTypeLeafWetness;
			gdevice.intval1=leaf_wetness;
			gdevice.id=1+iLeaf;
			sDecodeRXMessage(this, (const unsigned char *)&gdevice);
		}
	}

	return true;
}