mbed Weather Platform firmware http://mbed.org/users/okini3939/notebook/mbed-weather-platform-firmware/
Dependencies: EthernetNetIf SDHCFileSystem I2CLEDDisp Agentbed NTPClient_NetServices mbed BMP085 HTTPClient ConfigFile I2CLCD
Revision 0:d7b4484099bf, committed 2011-05-18
- Comitter:
- okini3939
- Date:
- Wed May 18 15:01:56 2011 +0000
- Commit message:
Changed in this revision
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/Agentbed.lib Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/okini3939/code/Agentbed/#9e4369522e03
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/BMP085.lib Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/okini3939/code/BMP085/#6245372b9179
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/ConfigFile.lib Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/shintamainjp/code/ConfigFile/#f6ceafabe9f8
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/EthernetNetIf.lib Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/donatien/code/EthernetNetIf/#bc7df6da7589
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/FATFileSystem.lib Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/mbed_unsupported/code/fatfilesystem/ \ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/HTTPClient.lib Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/mamezu/code/HTTPClient/#62fac7f06c8d
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/I2CLCD.lib Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/okini3939/code/I2CLCD/#bc4583ce560e
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/I2CLEDDisp.lib Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/okini3939/code/I2CLEDDisp/#eae10b76cd72
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/MSCFileSystem.lib Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/chris/code/MSCFileSystem/#3e7d2baed4b4
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/NTPClient.lib Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/donatien/code/NTPClient/#7c3f1199256a
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/SDHCFileSystem.lib Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/davervw/code/SDHCFileSystem/#248d03543f5f
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/SHT_v1/SHT.cpp Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,224 @@ +/* mbed module to use a Sensirion SHT1x /SHT7x sensor + * Copyright (c) 2007-2009 Stephen McGarry + * Released under the MIT License: http://mbed.org/license/mit + */ + +#include "SHT.h" + +#include "mbed.h" + +SHT::SHT(PinName p_sclk, PinName p_data, SHT_acc p_accuracy) : sclk(p_sclk), data(p_data), accuracy(p_accuracy) { + sclk=0; + data=0; // data pin will be used as open collector pin + data.mode(PullUp); // with the pull up internally active + data.input(); // with line released to go high + temperature = humidity = dewpoint=0.0f; + printf("constructor\n"); +} + +char SHT::write_byte(byte value) +//---------------------------------------------------------------------------------- +// writes a byte on the Sensibus and checks the acknowledge +{ + int i; + char error=0; + + for (i=0x80;i>0;i/=2) { //shift bit for masking + if (i & value) data.input(); //masking value with i , write to SENSI-BUS + else data.output(); + wait_us(1); //ensure sclk is low for min time + sclk=1; //clk for SENSI-BUS + wait_us(1); //pulsewith approx. 2 us + sclk=0; + } + data.input(); //release DATA-line + wait_us(1); //ensure sclk is low for min time + sclk=1; //clk #9 for ack + error=data; //check ack (DATA will be pulled down by SHT11) + wait_us(1); + sclk=0; + return error; //error=1 in case of no acknowledge +} + +byte SHT::read_byte(bool send_ack) +//---------------------------------------------------------------------------------- +// reads a byte form the Sensibus and gives an acknowledge in case of "ack=1" +{ + byte i,val=0; + data.input(); //release DATA-line + for (i=0x80;i>0;i/=2) { //shift bit for masking + wait_us(1); + sclk=1; //clk for SENSI-BUS + if (data) val=(val | i); //read bit + wait_us(1); + sclk=0; + } + wait_us(1); + if (send_ack) data.output(); // if ack needed then drive data low + sclk=1; //clk #9 for ack + wait_us(1); + sclk=0; + data.input(); //release DATA-line + return val; +} + +void SHT::trans_start(void) +//---------------------------------------------------------------------------------- +// generates a transmission start +// _____ ________ +// DATA: |_______| +// ___ ___ +// SCK : ___| |___| |______ +{ + data.input(); + sclk=0; //Initial state + wait_us(1); + sclk=1; + wait_us(1); + data.output(); // data low + wait_us(1); + sclk=0; + wait_us(1); + sclk=1; + wait_us(1); + data.input(); // allow data to high + wait_us(1); + sclk=0; + wait_us(1); +} + +void SHT::connection_reset(void) +//---------------------------------------------------------------------------------- +// communication reset: DATA-line=1 and at least 9 SCK cycles followed by transstart +// _____________________________________________________ ________ +// DATA: |_______| +// _ _ _ _ _ _ _ _ _ ___ ___ +// SCK : __| |__| |__| |__| |__| |__| |__| |__| |__| |______| |___| |______ +{ + int i; + data.input(); // allow data high + sclk=0; // and clk low + for (i=0;i<9;i++) { // 9 SCK cycles + wait_us(1); + sclk=1; + wait_us(1); + sclk=0; + } +} +char SHT::soft_reset(void) +//---------------------------------------------------------------------------------- +// resets the sensor by a softreset +{ + char error=0; + SHT::connection_reset(); //reset communication + trans_start(); + error+=write_byte(com_reset); //send RESET-command to sensor + return error; //error=1 in case of no response form the sensor +} + +char SHT::read_status(byte &value) +//---------------------------------------------------------------------------------- +// reads the status register with checksum (8-bit) +{ + //byte checksum; + + char error=0; + trans_start(); //transmission start + error=write_byte(com_read_status_reg); //send command to sensor + value=read_byte(send_ack); //read status register (8-bit) + /* checksum= */ + (void)read_byte(no_ack); //read checksum (8-bit) + // check the checksum ?? + return error; //error=1 in case of no response form the sensor +} + +char SHT::write_status(byte value) +//---------------------------------------------------------------------------------- +// writes the status register (8-bit) +{ + char error=0; + trans_start(); //transmission start + error+=write_byte(com_write_status_reg); //send command to sensor + error+=write_byte(value); //send value of status register + return error; //error>=1 in case of no response form the sensor +} + +char SHT::measure(int &value, byte command) +//---------------------------------------------------------------------------------- +// makes a measurement (humidity/temperature) with checksum +{ + unsigned int i; + byte msb; + // byte checksum; + + trans_start(); //transmission start + if (write_byte(command)) return 1; // if command fails return + + for (i=10000;i;i--) { //wait until sensor has finished the measurement + wait_us(100); + if (data==0) break; + } + if (data) return 1; // or timeout (~1 sec.) is reached !! + msb = read_byte(send_ack); //read the first byte (MSB) + value = msb*256 + read_byte(send_ack); //read the second byte (LSB) + /* checksum= */ + (void)read_byte(no_ack); //read checksum + return 0; +} + +void SHT::calculate() +//---------------------------------------------------------------------------------------- +// calculates temperature [°C] and humidity [%RH] +// input : hum [Ticks] (12 bit) +// temp [Ticks] (14 bit) +// output: humidity [%RH] +// temperature [°C] +{ + const float C1=-4.0; // for 12 Bit + const float C2=+0.0405; // for 12 Bit + const float C3=-0.0000028; // for 12 Bit + //const float T1=+0.01; // for 14 Bit @ 5V + //const float T2=+0.00008; // for 14 Bit @ 5V + + float rh; // rh: Humidity [Ticks] 12 Bit + float t; // t: Temperature [Ticks] 14 Bit + //float rh_lin; // rh_lin: Humidity linear + if (accuracy==SHT_low) { + rh=hum*16; // rescale to high accuracy values - 8 to 12 bits + t=temp*4; // and 12 to 14 bits + } else { + rh=hum; + t=temp; + } + + temperature=t*0.01 - 40; //calc. temperature from ticks to [°C] + humidity=C3*rh*rh + C2*rh + C1; //calc. humidity from ticks to [%RH] + // =(temperature-25)*(T1+T2*rh)+rh_lin; //calc. temperature compensated humidity [%RH] (ignore as never >0.25%) + if (humidity>100)humidity=100; //cut if the value is outside of + if (humidity<0.1)humidity=0.1; //the physical possible range +} + +float SHT::get_temperature() { // get the most recent temp reading + return temperature; +} + +float SHT::get_humidity() { // get the most recent humidity reading + return humidity; +} + +float SHT::get_dewpoint() { // get the most recent dewpoint value + return dewpoint; +} + +void SHT::update(SHT_acc acc) { // update stored values from sensor + int error=0; + connection_reset(); + if (acc!=accuracy) { + accuracy=acc; + error+=write_status((acc==SHT_low)?0x01:0x00); //set the status reg to high or low accuarcy + } + error+=measure(temp,com_measure_temp); + error+=measure(hum,com_measure_humid); + if (!error) calculate(); + +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/SHT_v1/SHT.h Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,66 @@ +/* mbed module to use a Sensirion SHT1x /SHT7x sensor + * Copyright (c) 2007-2009 Stephen McGarry + * Released under the MIT License: http://mbed.org/license/mit + */ +#ifndef SHT_H +#define SHT_H + +#include "mbed.h" + +enum SHT_acc { + SHT_low=0, + SHT_high=1 +}; + +typedef unsigned char byte; + +class SHT : public Base { +public: + /* Constructor: SHT + * Creates an SHT interface connected to specific pins. + * + */ + SHT(PinName p_sclk, PinName p_data, SHT_acc p_accuracy); + + /* Functions + */ + float get_temperature(); // get the most recent temp reading + float get_humidity(); // get the most recent humidity reading + float get_dewpoint(); // get the most recent dewpoint value + void update(SHT_acc accuracy); // update stored values from sensor + +protected: + byte read_byte(bool send_ack); + char write_byte(byte value); + void trans_start(void); + void connection_reset(void); + char soft_reset(); + char read_status(byte &value); + char write_status(byte value); + char measure(int &value, byte mode); + void calculate(); + + DigitalOut sclk; + DigitalInOut data; + SHT_acc accuracy; // will we use high or low accuracy mode on the sensor + + float temperature; // calculated from sensor reading + float humidity; + float dewpoint; + int temp,hum; // integer values from sensor before conversion + + enum commands { + com_read_status_reg=0x06, + com_write_status_reg=0x07, + com_measure_temp=0x03, + com_measure_humid=0x05, + com_reset=0x1E + }; + + enum acks { + no_ack=0, + send_ack=1 + }; +}; + +#endif \ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/WeatherMeters.lib Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/okini3939/code/WeatherMeters/#dc42aeff64e6
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/conf.cpp Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,392 @@ +/** @file + * @brief mbed Weather Platform + */ +#include "mbed.h" +#include "conf.h" +#include "ConfigFile.h" + +extern Serial xbee; +extern Config conf; +extern Sensor sensor, offset, sensor_old; + +void int_counter(); + +char* chop (char *s) { + int i; + + for (i = strlen(s) - 1; i >= 0; i --) { + if (s[i] == ' ' || s[i] == '\n' || s[i] == '\r') { + s[i] = 0; + } else { + break; + } + } + return s; +} + +int check_action (char type) { + int i, j, count; + float value, vold; + time_t sec = time(NULL) + (60 * 60 * 9); + struct tm *tim = localtime(&sec); + + for(i = 0; i < conf.actionscount; i ++) { + if (conf.actions[i].action != type) continue; + + count = 0; + for (j = 0; j < conf.actions[i].count; j ++) { + switch (conf.actions[i].exps[j].key) { + case 'P': + value = sensor.pres; + vold = sensor_old.pres; + break; + case 'T': + value = sensor.temp; + vold = sensor_old.temp; + break; + case 'H': + value = sensor.humi; + vold = sensor_old.humi; + break; + case 'A': + value = sensor.anemo; + vold = sensor_old.anemo; + break; + case 'V': + value = sensor.vane; + vold = sensor_old.vane; + break; + case 'R': + value = sensor.rain; + vold = sensor_old.rain; + break; + case 'L': + value = sensor.light; + vold = sensor_old.light; + break; + case 'U': + value = sensor.uv; + vold = sensor_old.uv; + break; + case 'M': + value = sensor.moist; + vold = sensor_old.moist; + break; + + case 'y': + value = tim->tm_year + 1900; + break; + case 'm': + value = tim->tm_mon; + break; + case 'd': + value = tim->tm_mday; + break; + case 'h': + value = tim->tm_hour; + break; + case 'i': + value = tim->tm_min; + break; + case 's': + value = tim->tm_sec; + break; + + default: + value = 0; + break; + } + + switch (conf.actions[i].exps[j].expression) { + case EXP_EQ: + if (value == conf.actions[i].exps[j].value) { + count ++; + } + break; + case EXP_NE: + if (value != conf.actions[i].exps[j].value) { + count ++; + } + break; + case EXP_LE: + if (value <= conf.actions[i].exps[j].value) { + count ++; + } + break; + case EXP_LT: + if (value < conf.actions[i].exps[j].value) { + count ++; + } + break; + case EXP_GE: + if (value >= conf.actions[i].exps[j].value) { + count ++; + } + break; + case EXP_GT: + if (value > conf.actions[i].exps[j].value) { + count ++; + } + break; + case EXP_MOD: + if ((int)value % (int)conf.actions[i].exps[j].value) { + count ++; + } + break; + case EXP_NMOD: + if (! (int)value % (int)conf.actions[i].exps[j].value) { + count ++; + } + break; + case EXP_FALL: + if (value < conf.actions[i].exps[j].value && vold >= conf.actions[i].exps[j].value) { + count ++; + } + break; + case EXP_RISE: + if (value > conf.actions[i].exps[j].value && vold <= conf.actions[i].exps[j].value) { + count ++; + } + break; + + default: + count ++; + break; + } + } + if (count == conf.actions[i].count) { + return conf.actions[i].sub ? conf.actions[i].sub : ' '; + } + } + return 0; +} + +void add_actionsub (struct tExpression *exp, char *buf) { + + exp->key = buf[0]; + + switch (buf[1]) { + case '=': + if (buf[2] == '=') { + exp->expression = EXP_EQ; + exp->value = atof(&buf[3]); + } + break; + + case '!': + if (buf[2] == '=') { + exp->expression = EXP_NE; + exp->value = atof(&buf[3]); + } else + if (buf[2] == '%') { + exp->expression = EXP_NMOD; + exp->value = atof(&buf[3]); + } + break; + + case '<': + if (buf[2] == '=') { + exp->expression = EXP_LE; + exp->value = atof(&buf[3]); + } else { + exp->expression = EXP_LT; + exp->value = atof(&buf[2]); + } + break; + + case '>': + if (buf[2] == '=') { + exp->expression = EXP_GE; + exp->value = atof(&buf[3]); + } else { + exp->expression = EXP_GT; + exp->value = atof(&buf[2]); + } + break; + + case '%': + exp->expression = EXP_MOD; + exp->value = atof(&buf[2]); + break; + + case '_': + exp->expression = EXP_FALL; + exp->value = atof(&buf[2]); + break; + case '^': + exp->expression = EXP_RISE; + exp->value = atof(&buf[2]); + break; + + default: + exp->expression = EXP_NULL; + break; + } +} + +void add_action (char *buf) { + int i, len, count; + char c; + char *tmp = NULL; + + if (conf.actionscount >= CF_ACTION_NUM) return; + +// conf.actions[conf.actionscount].action = atoi(&buf[0]); + conf.actions[conf.actionscount].action = buf[0]; + conf.actions[conf.actionscount].sub = buf[1]; + + count = 0; + strcat(buf, "\n"); + len = strlen(buf); + for (i = 1; i < len; i ++) { + c = buf[i]; + if (c == ' ' || c == '\t' || c == '\n' || c == '\r') { + buf[i] = 0; + if (count) { + add_actionsub(&conf.actions[conf.actionscount].exps[count - 1], tmp); + } + if (count >= CF_ACTION_EXPS || c == '\n') break; + tmp = &buf[i + 1]; + count ++; + } + } + + conf.actions[conf.actionscount].count = count; + conf.actionscount ++; +} + +int config (char *file) { + int i; + ConfigFile cfg; + char buf[80], key[20]; + int ip0, ip1, ip2, ip3; + + conf.ipaddr = IpAddr(0, 0, 0, 0); + conf.netmask = IpAddr(255, 255, 255, 0); + conf.gateway = IpAddr(0, 0, 0, 0); + conf.nameserver = IpAddr(0, 0, 0, 0); + conf.interval = 60; + conf.ntpserver[0] = 0; + conf.filetype = 0; + conf.actionscount = 0; + conf.pachube_apikey[0] = 0; + conf.pachube_feedid[0] = 0; + conf.twitter_user[0] = 0; + conf.twitter_pwd[0] = 0; + for (i = 0; i < CF_TWITTER_NUM; i ++) { + conf.twitter_mesg[i][0] = 0; + } + conf.stations_id[0] = 0; + conf.stations_pin[0] = 0; + conf.snmp_commname[0] = 0; + conf.leddisp_mesg[0] = 0; + conf.lcd_mesg[0] = 0; + conf.lcdtype = LCD16x2; + conf.lcdconf = LCDCFG_3V; + memset(&offset, 0, sizeof(offset)); + memset(&sensor_old, 0, sizeof(sensor_old)); + + if (! cfg.read(file)) { + return -1; + } + + if (cfg.getValue("INTERVAL", buf, sizeof(buf))) { + conf.interval = atoi(chop(buf)); + } + if (cfg.getValue("FILE", buf, sizeof(buf))) { + chop(buf); + if (strcmp(buf, "SD") == 0) { + conf.filetype = 1; + } else + if (strcmp(buf, "USB") == 0) { + conf.filetype = 2; + } + } + + if (cfg.getValue("IPADDRESS", buf, sizeof(buf))) { + chop(buf); + if (strcmp(buf, "DHCP") == 0) { + conf.ipaddr = IpAddr(255, 255, 255, 255); + } else { + sscanf(buf, "%d.%d.%d.%d", &ip0, &ip1, &ip2, &ip3); + conf.ipaddr = IpAddr(ip0, ip1, ip2, ip3); + } + } + if (cfg.getValue("NETMASK", buf, sizeof(buf))) { + sscanf(chop(buf), "%d.%d.%d.%d", &ip0, &ip1, &ip2, &ip3); + conf.netmask = IpAddr(ip0, ip1, ip2, ip3); + } + if (cfg.getValue("GATEWAY", buf, sizeof(buf))) { + sscanf(chop(buf), "%d.%d.%d.%d", &ip0, &ip1, &ip2, &ip3); + conf.gateway = IpAddr(ip0, ip1, ip2, ip3); + } + if (cfg.getValue("NAMESERVER", buf, sizeof(buf))) { + sscanf(chop(buf), "%d.%d.%d.%d", &ip0, &ip1, &ip2, &ip3); + conf.nameserver = IpAddr(ip0, ip1, ip2, ip3); + } + + cfg.getValue("NTPSERVER", conf.ntpserver, sizeof(conf.ntpserver)); + chop(conf.ntpserver); + cfg.getValue("PACHUBE_APIKEY", conf.pachube_apikey, sizeof(conf.pachube_apikey)); + chop(conf.pachube_apikey); + cfg.getValue("PACHUBE_FEEDID", conf.pachube_feedid, sizeof(conf.pachube_feedid)); + chop(conf.pachube_feedid); + cfg.getValue("TWITTER_USER", conf.twitter_user, sizeof(conf.twitter_user)); + chop(conf.twitter_user); + cfg.getValue("TWITTER_PWD", conf.twitter_pwd, sizeof(conf.twitter_pwd)); + chop(conf.twitter_pwd); + cfg.getValue("TWITTER_MESG", conf.twitter_mesg[0], sizeof(conf.twitter_mesg[0])); + chop(conf.twitter_mesg[0]); + for (i = 0; i < CF_TWITTER_NUM; i ++) { + sprintf(key, "TWITTER_MESG[%d]", i); + cfg.getValue(key, conf.twitter_mesg[i], sizeof(conf.twitter_mesg[i])); + chop(conf.twitter_mesg[i]); + } + + cfg.getValue("STATIONS_ID", conf.stations_id, sizeof(conf.stations_id)); + chop(conf.stations_id); + cfg.getValue("STATIONS_PIN", conf.stations_pin, sizeof(conf.stations_pin)); + chop(conf.stations_pin); + cfg.getValue("SNMP_COMMNAME", conf.snmp_commname, sizeof(conf.snmp_commname)); + chop(conf.snmp_commname); + + if (cfg.getValue("LCD_TYPE", buf, sizeof(buf))) { + conf.lcdtype = (enum I2CLCDType)atoi(chop(buf)); + } + if (cfg.getValue("LCD_CONF", buf, sizeof(buf))) { + conf.lcdconf = (enum I2CLCDConfig)atoi(chop(buf)); + } + if (cfg.getValue("LCD_MESG", conf.lcd_mesg, sizeof(conf.lcd_mesg))) { + chop(conf.lcd_mesg); + } + if (cfg.getValue("LEDDISP_MESG", conf.leddisp_mesg, sizeof(conf.leddisp_mesg))) { + chop(conf.leddisp_mesg); + } + + if (cfg.getValue("XBEE", buf, sizeof(buf))) { + xbee.baud(atoi(chop(buf))); + } + + if (cfg.getValue("INPUT", buf, sizeof(buf))) { + conf.inputtype = (enum eINPUTTYPE)atoi(chop(buf)); + } + + for (i = 0; i < CF_ACTION_NUM; i ++) { + sprintf(key, "ACTION[%d]", i); + if (cfg.getValue(key, buf, sizeof(buf))) { + add_action(chop(buf)); + } + } + + if (cfg.getValue("OFFSET[P]", buf, sizeof(buf))) { + offset.pres = atof(chop(buf)); + } + if (cfg.getValue("OFFSET[T]", buf, sizeof(buf))) { + offset.temp = atof(chop(buf)); + } + if (cfg.getValue("OFFSET[H]", buf, sizeof(buf))) { + offset.humi = atof(chop(buf)); + } + + return 0; +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/conf.h Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,72 @@ +/** @file + * @brief mbed Weather Platform + */ +#include "mbed.h" +#include "EthernetNetIf.h" +#include "I2CLEDDisp.h" +#include "I2CLCD.h" + +#define CONFIG_FILE "weather.cfg" + + +#define CF_MAXLEN_VALUE 128 +#define CF_ACTION_EXPS 10 +#define CF_ACTION_NUM 10 +#define CF_TWITTER_NUM 5 + +enum eEXPRESSION { + EXP_NULL, + EXP_EQ, + EXP_NE, + EXP_LE, + EXP_LT, + EXP_GE, + EXP_GT, + EXP_MOD, + EXP_NMOD, + EXP_FALL, + EXP_RISE, +}; + +enum eINPUTTYPE { + INPUT_MOIST = 0, + INPUT_FALL = 1, + INPUT_RISE = 2, + INPUT_CPM = 4, +}; + +struct tExpression { + char key; + enum eEXPRESSION expression; + float value; +}; + +struct tAction { + char action; + char sub; + int count; + struct tExpression exps[CF_ACTION_EXPS]; +}; + +struct Sensor { + float pres, temp, humi, light, anemo, vane, rain, uv, moist, temp2; +}; + +struct Config { + int interval; + IpAddr ipaddr, netmask, gateway, nameserver; + char ntpserver[32]; + int filetype, actionscount; + struct tAction actions[CF_ACTION_NUM]; + char pachube_apikey[70], pachube_feedid[8]; + char twitter_user[30], twitter_pwd[30], twitter_mesg[CF_TWITTER_NUM][CF_MAXLEN_VALUE]; + char stations_id[8], stations_pin[34]; + char snmp_commname[30]; + char lcd_mesg[CF_MAXLEN_VALUE]; + enum I2CLCDType lcdtype; + enum I2CLCDConfig lcdconf; + char leddisp_mesg[CF_MAXLEN_VALUE]; + enum eINPUTTYPE inputtype; +}; + +int config (char *);
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/func.cpp Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,274 @@ +#include "mbed.h" +#include "ConfigFile.h" +#include "SDHCFileSystem.h" +#include "EthernetNetIf.h" +#include "NTPClient.h" +#include "HTTPClient.h" +#include "conf.h" + +#define TIMEZONE 9 +//#define NONBLOCKING +/** @file + * @brief mbed Weather Platform + */ + +#define STATION_URL "http://weather.sugakoubou.com/p" +#define TWITTER_URL "http://api.supertweet.net/1/statuses/update.xml" + +extern Serial pc; +extern int seq; +extern char filename[]; +extern Config conf; +extern DigitalOut led_y, led2; + +extern EthernetNetIf *eth; +extern NTPClient *ntp; +extern HTTPClient *clientP, *clientT; +extern Sensor sensor; + +void writefile (char *buf) { + FILE *fp; + + fp = fopen(filename, "a"); + if (fp) { + fprintf(fp, buf); + fclose(fp); + } else { + led2 = 0; + conf.filetype = 0; + } +} + +void weatherstations () { + char post_data[200]; + HTTPResult ret; + HTTPText postContent("application/x-www-form-urlencoded"); + + led_y = 0; + strcpy(post_data, "fcd="); + strcat(post_data, conf.stations_id); + strcat(post_data, "&pin="); + strcat(post_data, conf.stations_pin); + sprintf(&post_data[strlen(post_data)], "&d0=%.2f&d1=%.2f&d2=%.2f&d3=%.2f&d4=%.2f&d5=%.2f&d6=%.2f&d7=%.2f&d8=%.2f&d9=%.2f", + sensor.pres, sensor.temp, sensor.humi, sensor.anemo, sensor.vane, sensor.rain, sensor.light, sensor.uv, sensor.moist, sensor.temp2); + postContent.puts(post_data); + +#ifdef NONBLOCKING + Net::poll(); + ret = clientP->post(STATION_URL, postContent, NULL, &cb_clientP); + Net::poll(); +#else + ret = clientP->post(STATION_URL, postContent, NULL); +#endif + + if (ret != HTTP_OK && ret != HTTP_PROCESSING) { + pc.printf("error: Weather Statuons %d\r\n", ret); + } +} + +void pachube (char *buf) { + char uri[100]; + HTTPResult ret; + HTTPText csvContent("text/csv"); + + led_y = 0; + clientP->setRequestHeader("X-PachubeApiKey", conf.pachube_apikey); + csvContent.set(buf); + strcpy(uri, "http://api.pachube.com/v1/feeds/"); + strcat(uri, conf.pachube_feedid); + strcat(uri, ".csv?_method=put"); +#ifdef NONBLOCKING + Net::poll(); + ret = clientP->post(uri, csvContent, NULL, &cb_clientP); + Net::poll(); +#else + ret = clientP->post(uri, csvContent, NULL); +#endif + + if (ret != HTTP_OK && ret != HTTP_PROCESSING) { + pc.printf("error: Pachube %d\r\n", ret); + } +} + +void cb_clientP (HTTPResult status) { + if (status != HTTP_OK) { + pc.printf("Pachube failure (%d)\r\n", status); +// pc.printf("Pachube failure (%d, %d)\r\n", status, clientP->getHTTPResponseCode()); + } +} + +char *fmtstr (char *fmt, char *buf, int len) { + int i, j, flg; + char c; + float value; + time_t sec = time(NULL); + struct tm *tim = localtime(&sec); + + j = 0; + for (i = 0; i < strlen(fmt) && j < len; i ++) { + c = fmt[i]; + if (c == '%') { + flg = 0; + i ++; + c = fmt[i]; + + if (c == '.') { + // float format + if (fmt[i + 1] >= '0' && fmt[i + 1] <= '9') { + flg = fmt[i + 1] - '0'; + i ++; + + c = fmt[i + 1]; + i ++; + } + } + + switch (c) { + case 'P': + value = sensor.pres; + break; + case 'T': + value = sensor.temp; + break; + case 'H': + value = sensor.humi; + break; + case 'A': + value = sensor.anemo; + break; + case 'V': + value = sensor.vane; + break; + case 'R': + value = sensor.rain; + break; + case 'L': + value = sensor.light; + break; + case 'U': + value = sensor.uv; + break; + case 'M': + value = sensor.moist; + break; + + case 'y': + value = tim->tm_year + 1900; + break; + case 'm': + value = tim->tm_mon; + break; + case 'd': + value = tim->tm_mday; + break; + case 'h': + value = tim->tm_hour; + break; + case 'i': + value = tim->tm_min; + break; + case 's': + value = tim->tm_sec; + break; + + case '0': + case '1': + case '2': + case '3': + case '4': + case '5': + case '6': + case '7': + case '8': + case '9': + // Ascii + c = c - '0'; + if (fmt[i + 1] >= '0' && fmt[i + 1] <= '9') { + c = (c << 3) | (fmt[i + 1] - '0'); + i ++; + if (fmt[i + 1] >= '0' && fmt[i + 1] <= '9') { + c = (c << 3) | (fmt[i + 1] - '0'); + i ++; + } + } + buf[j] = c; + j ++; + continue; + + default: + buf[j] = c; + j ++; + continue; + } + + switch (flg) { + case 1: + sprintf(&buf[j], "%.1f", value); + break; + case 2: + sprintf(&buf[j], "%.2f", value); + break; + default: + sprintf(&buf[j], "%02d", (int)value); + break; + } + j = strlen(buf); + } else { + buf[j] = c; + j ++; + } + } + buf[j] = 0; + return buf; +} + +void twitter (int num) { + HTTPMap msg; + HTTPResult ret; + char buf[170]; + + led_y = 0; + fmtstr(conf.twitter_mesg[num], buf, sizeof(buf)); + msg["status"] = buf; + + clientT->basicAuth(conf.twitter_user, conf.twitter_pwd); +#ifdef NONBLOCKING + Net::poll(); + ret = clientT->post(TWITTER_URL, msg, NULL, &cb_clientT); + Net::poll(); +#else + ret = clientT->post(TWITTER_URL, msg, NULL); +#endif + + if (ret != HTTP_OK && ret != HTTP_PROCESSING) { + pc.printf("error: Twitter %d\r\n", ret); + } +} + +void ntpdate () { + ntp = new NTPClient; + Host ntpserver(IpAddr(), 123, conf.ntpserver); + + led_y = 0; +#ifdef NONBLOCKING + Net::poll(); + ntp->setTime(ntpserver, &cb_settime); + Net::poll(); +#else + ntp->setTime(ntpserver); + time_t sec = time(NULL) + (60 * 60 * TIMEZONE); + set_time(sec); +#endif +} + +void cb_settime (NTPResult status) { + if (status == NTP_OK) { + led_y = 0; + time_t sec = time(NULL) + (60 * 60 * TIMEZONE); + set_time(sec); + pc.printf("Ntp success: %s\r\n", ctime(&sec)); + } else { + pc.printf("Ntp failure (%d)\r\n", status); + } +// ntp->close(); +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/main.cpp Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,431 @@ +/* + * mbed Weather Platform + * Copyright (c) 2011 Hiroshi Suga + * Released under the MIT License: http://mbed.org/license/mit + */ + +/** @file + * @brief mbed Weather Platform + */ + +#define VERSION "mbed Weather Platform 0.2.1 (C) 2011 Suga koubou Co.,Ltd." + +//#define NONBLOCKING // ethernet function non-bloking + +#include "mbed.h" +#include "BMP085.h" +#include "SHT.h" +#include "WeatherMeters.h" +#include "SDHCFileSystem.h" +#include "MSCFileSystem.h" +#include "EthernetNetIf.h" +#include "NTPClient.h" +#include "HTTPClient.h" +#include "Agentbed.h" +#include "conf.h" +#include "I2CLEDDisp.h" +#include "I2CLCD.h" + +Serial pc(USBTX, USBRX), xbee(p13, p14); +int seq = 0; +char filename[20]; +struct Config conf; +DigitalOut led1(LED1), led2(LED2), led3(LED3), led4(LED4); +LocalFileSystem local("local"); +SDFileSystem sd(p5, p6, p7, p8, "sd"); +MSCFileSystem *usb; + +// Sensors +struct Sensor sensor, offset, sensor_old; +I2C i2c(p9, p10); +BMP085 bmp085(i2c, BMP085_oss4); +SHT sht15(p12, p11, SHT_high); // sclock, data +WeatherMeters wmeters(p21, p15, p22); // anemo, vane, rain +AnalogIn ailight(p16), aiuv(p17); +AnalogIn *aimoist; +InterruptIn *intcounter; +int count_counter; +unsigned long lastCountTime; + +DigitalOut swout1(p29), swout2(p30); +I2CLEDDisp *leddisp; +I2CLCD *lcd; +int ledpos, ledflg; +char ledbuf[200]; +Ticker ticker; + +// Ethernet +EthernetNetIf *eth; +NTPClient *ntp; +HTTPClient *clientP, *clientT; +DigitalOut led_g2(p24),led_g(p25), led_y(p26); +DigitalIn eth_link(P1_25), eth_speed(P1_26); + +extern AgentbedClass Agentbed; +extern uint32_t locUpTime; + +void writefile (char *); +void pachube (char *); +char *fmtstr (char *, char *, int); +void twitter (int); +void weatherstations (); +void ntpdate (); +int check_action (char); +void pduReceived (); + +float get_photo (AnalogIn &ain) { + float f; + + f = ain * 5.0 / 1000; // A + return f / 0.0000026; // lx +} + +float get_moist (AnalogIn &ain) { + float f; + + f = ain * 5.0; // V + f = f / ((3.3 - f) / 10.0); // k ohm + if (f < 0) f = 0; + return f; +} + +float get_uv (AnalogIn &ain) { + float f; + + f = ain * 5.0 / 100000; // A + f = f / 0.000384; // mW/cm2 + if (f < 0) f = 0; + return f; +} + +void int_counter () { + count_counter ++; +} + +float get_counter (char flg) { + float t; + + if (flg) { + t = (float)count_counter; + } else { + if (locUpTime > lastCountTime) { + t = (float)(locUpTime - lastCountTime) / 6000.0; + } else { + t = (float)(0xffffffff - lastCountTime + locUpTime) / 6000.0; + } + t = (float)count_counter / t; + } + lastCountTime = locUpTime; + count_counter = 0; + return t; +} + + +void ledscroll () { + + if (conf.leddisp_mesg[0]) { + int i, addr, len; + + len = strlen(ledbuf); + leddisp->locate(0, 0); + for (i = 0; i < 4; i ++) { + addr = ledpos + i; + if (addr >= 0 && addr < len) { + leddisp->putc(ledbuf[addr]); + } else { + leddisp->putc(' '); + } + } + ledpos ++; + if (ledpos >= len + 4) { + ledpos = -4; + } + } + + locUpTime = locUpTime + 40; // 0.4s + led_y = 1; +} + +void action (char *buf) { + int i; + + i = check_action('A'); + if (i) { + swout1 = (i == ' ' ? 1 : i - '0'); + led3 = swout1; + } + i = check_action('B'); + if (i) { + swout2 = (i == ' ' ? 1 : i - '0'); + led4 = swout2; + } + if (check_action('P')) { + if (conf.ipaddr[0] && conf.pachube_apikey[0] && conf.pachube_feedid[0]) { + pachube(buf); + } + } + i = check_action('T'); + if (i) { + if (conf.ipaddr[0] && conf.twitter_user[0] && conf.twitter_pwd[0]) { + twitter(i == ' ' ? 0 : i - '0'); + } + } + if (check_action('S')) { + if (conf.ipaddr[0] && conf.stations_id[0] && conf.stations_pin[0]) { + weatherstations(); + } + } + if (check_action('X')) { + xbee.printf(buf); + } + sensor_old = sensor; +} + +void init () { + FILE *fp; + + if (config("/sd/" CONFIG_FILE) == -1) { + pc.printf("local strage\r\n", conf.interval); + config("/local/" CONFIG_FILE); + } + + pc.printf("\r\nInterval: %d sec\r\n", conf.interval); + + if (conf.lcd_mesg[0]) { + // use I2C LCD + lcd = new I2CLCD(i2c, I2CLCD_ADDR, conf.lcdtype, conf.lcdconf); + } + + if (conf.leddisp_mesg[0]) { + // use I2C LED Display + leddisp = new I2CLEDDisp(i2c); + } + + if (conf.ipaddr[0]) { + // use ethernet + + eth_link.mode(PullUp); + eth_speed.mode(PullUp); + led_g = eth_link ? 1 : 0; + led_g2 = 1; + led_y = 0; + if (conf.ipaddr[0] == 255) { + // dhcp + eth = new EthernetNetIf; + } else { + // static + eth = new EthernetNetIf(conf.ipaddr, conf.netmask, conf.gateway, conf.nameserver); + } + + EthernetErr ethErr = eth->setup(); + if(ethErr) { + // error + conf.ipaddr = IpAddr(0, 0, 0, 0); + } else + if (conf.ipaddr[0] == 255) { + // succeed dhcp + conf.ipaddr = eth->getIp(); + } + pc.printf("Ethernet: %d.%d.%d.%d\r\n", eth->getIp()[0], eth->getIp()[1], eth->getIp()[2], eth->getIp()[3]); + + if (conf.ipaddr[0]) { + + if (conf.ntpserver[0]) { + // ntp + pc.printf("Ntp: %s\r\n", conf.ntpserver); + ntpdate(); + } + + clientP = new HTTPClient; + clientT = new HTTPClient; + + if (conf.snmp_commname[0]) { + Agentbed.begin(conf.snmp_commname, "None", SNMP_DEFAULT_PORT, eth); + Agentbed.onPduReceive(pduReceived); + pc.printf("Snmp community name: %s\r\n", conf.snmp_commname); + } + } + } else { + // not use ethernet + led_g = eth_link ? 0 : 1; + led_g2 = 0; + } + + if (conf.filetype) { + // seq num + + if (conf.filetype == 1) { + strcpy(filename, "/sd"); + } else + if (conf.filetype == 2) { + usb = new MSCFileSystem("usb"); + strcpy(filename, "/usb"); + } + strcat(filename, "/weather.seq"); + + // load + fp = fopen(filename, "r"); + if (fp) { + fscanf(fp, "%d", &seq); + fclose(fp); + } + seq ++; + // save + fp = fopen(filename, "w"); + if (fp) { + fprintf(fp, "%d", seq); + fclose(fp); + // csv filename + if (conf.filetype == 1) { + sprintf(filename, "/sd/w%05d.csv", seq); + } else + if (conf.filetype == 2) { + sprintf(filename, "/usb/w%05d.csv", seq); + } + pc.printf("Filename: %s\r\n", filename); + led2 = 1; + } + } + + pc.printf("Actions: %d\r\n", conf.actionscount); + + if (conf.inputtype & INPUT_FALL) { + intcounter = new InterruptIn(p18); + intcounter->fall(&int_counter); + } else + if (conf.inputtype & INPUT_RISE) { + intcounter = new InterruptIn(p18); + intcounter->rise(&int_counter); + } else { + aimoist = new AnalogIn(p18); + } + + count_counter = 0; + lastCountTime = 0; +} + +int main () { + Timer timer; + time_t sec; + char buf[100]; + + swout1 = 0; + swout2 = 0; + led1 = 1; + ledpos = -4; + ledflg = 0; + strcpy(ledbuf, VERSION); + ticker.attach(&ledscroll, 0.4); + init(); + pc.printf("%s\r\n\r\n", VERSION); + + if (conf.filetype) { + strcpy(buf, "date,pres(hPa),temp(`C),humi(%%),anemo(m/s),vane(`),rain(mm),light(lx),uv(mW/cm2),moist(kohm),\r\n"); + writefile(buf); + } + + if (conf.leddisp_mesg[0]) { + ledpos = -4; + sec = time(NULL); + strftime(ledbuf, sizeof(ledbuf), "%H:%M", localtime(&sec)); + sprintf(&ledbuf[5], " %ds %s", conf.interval, filename); + if (conf.ipaddr[0]) { + sprintf(&ledbuf[strlen(ledbuf)], " %d.%d.%d.%d", conf.ipaddr[0], conf.ipaddr[1], conf.ipaddr[2], conf.ipaddr[3]); + if (conf.pachube_apikey[0] && conf.pachube_feedid[0]) { + strcat(ledbuf, " P"); + } + if (conf.twitter_user[0] && conf.twitter_pwd[0]) { + strcat(ledbuf, " T"); + } + } + } + + timer.start(); +#ifdef NONBLOCKING + while (timer.read() < 5) { + wait_ms(1); + Net::poll(); + } + timer.reset(); +#endif + + while(1) { + led1 = 0; + + sec = time(NULL); + strftime(buf, sizeof(buf), "%Y-%m-%d %H:%M:%S", localtime(&sec)); + + // sensors + __disable_irq(); + bmp085.update(); + sensor.pres = bmp085.get_pressure() + offset.pres; + sensor.temp2 = bmp085.get_temperature(); + + sht15.update(SHT_high); + sensor.temp = sht15.get_temperature() + offset.temp; + sensor.humi = sht15.get_humidity() + offset.humi; + + sensor.anemo = wmeters.get_windspeed(); + sensor.vane = wmeters.get_windvane(); + sensor.rain = wmeters.get_raingauge(); + + sensor.light = get_photo(ailight); + if (conf.inputtype == INPUT_MOIST) { + sensor.moist = get_moist(*aimoist); + } else { + sensor.moist = get_counter(conf.inputtype & INPUT_CPM ? 0 : 1); + } + sensor.uv = get_uv(aiuv); + + sprintf(&buf[strlen(buf)], ",%.2f,%.2f,%.2f,%.2f,%.2f,%.2f,%.2f,%.2f,%.2f,%.2f\r\n", + sensor.pres, sensor.temp, sensor.humi, sensor.anemo, sensor.vane, sensor.rain, sensor.light, sensor.uv, sensor.moist, sensor.temp2); + if (conf.filetype) { + // csv + writefile(buf); + } + __enable_irq(); + pc.printf(buf); + + action(&buf[20]); + + if (conf.leddisp_mesg[0]) { + if (ledflg) { + ledpos = -4; + fmtstr(conf.leddisp_mesg, ledbuf, sizeof(ledbuf)); + } + ledflg = 1; + } + if (conf.lcd_mesg[0]) { + fmtstr(conf.lcd_mesg, buf, sizeof(buf)); + lcd->cls(); + lcd->puts(buf); + } + + led1 = 1; + + while (timer.read() < conf.interval) { +// wait(1); +// pc.putc('.'); + wait_ms(1); + if (conf.ipaddr[0]) { + led_g = eth_link ? 1 : 0; + led_g2 = 1; + } else { + led_g = eth_link ? 0 : 1; + led_g2 = 0; + } + Net::poll(); + + if (pc.readable()) { + int i; + i = pc.getc(); + if (i == ' ') { + break; + } else { + pc.printf("( %d )\r\n", (int)timer.read()); + } + } + } + timer.reset(); + } +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/mbed.bld Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/mbed_official/code/mbed/builds/e2ac27c8e93e
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/snmp.cpp Wed May 18 15:01:56 2011 +0000 @@ -0,0 +1,179 @@ +/** +* Agentbed SNMP Server +* Modified for mbed, 2011 Suga. +* +* Agentuino SNMP Agent Library Prototyping... +* Copyright 2010 Eric C. Gionet <lavco_eg@hotmail.com> +*/ +#include "mbed.h" +#include "Agentbed.h" +#include "EthernetNetIf.h" +#include "ConfigFile.h" +#include "conf.h" + +AgentbedClass Agentbed; + +// RFC1213-MIB OIDs +// .iso (.1) +// .iso.org (.1.3) +// .iso.org.dod (.1.3.6) +// .iso.org.dod.internet (.1.3.6.1) +// .iso.org.dod.internet.mgmt (.1.3.6.1.2) +// .iso.org.dod.internet.mgmt.mib-2 (.1.3.6.1.2.1) +// .iso.org.dod.internet.mgmt.mib-2.system (.1.3.6.1.2.1.1) +// .iso.org.dod.internet.mgmt.mib-2.system.sysDescr (.1.3.6.1.2.1.1.1) +const char sysDescr[] = "1.3.6.1.2.1.1.1.0"; // read-only (DisplayString) +// .iso.org.dod.internet.mgmt.mib-2.system.sysObjectID (.1.3.6.1.2.1.1.2) +const char sysObjectID[] = "1.3.6.1.2.1.1.2.0"; // read-only (ObjectIdentifier) +// .iso.org.dod.internet.mgmt.mib-2.system.sysUpTime (.1.3.6.1.2.1.1.3) +const char sysUpTime[] = "1.3.6.1.2.1.1.3.0"; // read-only (TimeTicks) +// .iso.org.dod.internet.mgmt.mib-2.system.sysContact (.1.3.6.1.2.1.1.4) +const char sysContact[] = "1.3.6.1.2.1.1.4.0"; // read-write (DisplayString) +// .iso.org.dod.internet.mgmt.mib-2.system.sysName (.1.3.6.1.2.1.1.5) +const char sysName[] = "1.3.6.1.2.1.1.5.0"; // read-write (DisplayString) +// .iso.org.dod.internet.mgmt.mib-2.system.sysLocation (.1.3.6.1.2.1.1.6) +const char sysLocation[] = "1.3.6.1.2.1.1.6.0"; // read-write (DisplayString) +// .iso.org.dod.internet.mgmt.mib-2.system.sysServices (.1.3.6.1.2.1.1.7) +const char sysServices[] = "1.3.6.1.2.1.1.7.0"; // read-only (Integer) +// +// Arduino defined OIDs +// .iso.org.dod.internet.private (.1.3.6.1.4) +// .iso.org.dod.internet.private.enterprises (.1.3.6.1.4.1) +// .iso.org.dod.internet.private.enterprises.arduino (.1.3.6.1.4.1.36582) +const char enterprises[] = "1.3.6.1.4.1.36582."; // read-only (Integer) +// +// +// RFC1213 local values +static char locDescr[] = "mbed Weather Platform"; // read-only (static) +static char locObjectID[] = "1.3.6.1.4.1.36582"; // read-only (static) +uint32_t locUpTime = 0; // read-only (static) +static char locContact[] = "<root@weather>"; // should be stored/read from EEPROM - read/write (not done for simplicity) +static char locName[] = "weather.mbed"; // should be stored/read from EEPROM - read/write (not done for simplicity) +static char locLocation[] = "weather"; // should be stored/read from EEPROM - read/write (not done for simplicity) +static int32_t locServices = 7; // read-only (static) + +uint32_t prevMillis = 0; +char oid[SNMP_MAX_OID_LEN]; +SNMP_API_STAT_CODES api_status; +SNMP_ERR_CODES status; + +extern DigitalOut led_y; +extern Sensor sensor; + +void pduReceived() +{ + SNMP_PDU pdu; + // + led_y = 1; + api_status = Agentbed.requestPdu(&pdu); + // + if ( pdu.type == SNMP_PDU_GET || pdu.type == SNMP_PDU_GET_NEXT || pdu.type == SNMP_PDU_SET + && pdu.error == SNMP_ERR_NO_ERROR && api_status == SNMP_API_STAT_SUCCESS ) { + // + pdu.OID.toString(oid); + // + pdu.error = SNMP_ERR_READ_ONLY; + // + if ( strcmp(oid, sysDescr ) == 0 ) { + // handle sysDescr (set/get) requests + if ( pdu.type == SNMP_PDU_GET ) { + // response packet from get-request - locDescr + status = pdu.VALUE.encode(SNMP_SYNTAX_OCTETS, locDescr); + pdu.error = status; + } + } else if ( strcmp(oid, sysObjectID ) == 0 ) { + // handle sysName (set/get) requests + if ( pdu.type == SNMP_PDU_GET ) { + // response packet from get-request - locUpTime + status = pdu.VALUE.encode(SNMP_SYNTAX_OCTETS, locObjectID); + pdu.error = status; + } + } else if ( strcmp(oid, sysUpTime ) == 0 ) { + // handle sysName (set/get) requests + if ( pdu.type == SNMP_PDU_GET ) { + // response packet from get-request - locUpTime + status = pdu.VALUE.encode(SNMP_SYNTAX_TIME_TICKS, locUpTime); + pdu.error = status; + } + } else if ( strcmp(oid, sysName ) == 0 ) { + // handle sysName (set/get) requests + if ( pdu.type == SNMP_PDU_GET ) { + // response packet from get-request - locName + status = pdu.VALUE.encode(SNMP_SYNTAX_OCTETS, locName); + pdu.error = status; + } + } else if ( strcmp(oid, sysContact ) == 0 ) { + // handle sysContact (set/get) requests + if ( pdu.type == SNMP_PDU_GET ) { + // response packet from get-request - locContact + status = pdu.VALUE.encode(SNMP_SYNTAX_OCTETS, locContact); + pdu.error = status; + } + } else if ( strcmp(oid, sysLocation ) == 0 ) { + // handle sysLocation (set/get) requests + if ( pdu.type == SNMP_PDU_GET ) { + // response packet from get-request - locLocation + status = pdu.VALUE.encode(SNMP_SYNTAX_OCTETS, locLocation); + pdu.error = status; + } + } else if ( strcmp(oid, sysServices) == 0 ) { + // handle sysServices (set/get) requests + if ( pdu.type == SNMP_PDU_GET ) { + // response packet from get-request - locServices + status = pdu.VALUE.encode(SNMP_SYNTAX_INT, locServices); + pdu.error = status; + } + } else if ( strncmp(oid, enterprises, strlen(enterprises)) == 0 ) { + // handle enterprises (set/get) requests + if ( pdu.type == SNMP_PDU_GET ) { + // response packet from get-request - enterprises + switch (oid[strlen(enterprises)]) { + case '0': + status = pdu.VALUE.encode(SNMP_SYNTAX_OPAQUE_FLOAT, sensor.pres); + break; + case '1': + status = pdu.VALUE.encode(SNMP_SYNTAX_OPAQUE_FLOAT, sensor.temp); + break; + case '2': + status = pdu.VALUE.encode(SNMP_SYNTAX_OPAQUE_FLOAT, sensor.humi); + break; + case '3': + status = pdu.VALUE.encode(SNMP_SYNTAX_OPAQUE_FLOAT, sensor.anemo); + break; + case '4': + status = pdu.VALUE.encode(SNMP_SYNTAX_OPAQUE_FLOAT, sensor.vane); + break; + case '5': + status = pdu.VALUE.encode(SNMP_SYNTAX_OPAQUE_FLOAT, sensor.rain); + break; + case '6': + status = pdu.VALUE.encode(SNMP_SYNTAX_OPAQUE_FLOAT, sensor.light); + break; + case '7': + status = pdu.VALUE.encode(SNMP_SYNTAX_OPAQUE_FLOAT, sensor.uv); + break; + case '8': + status = pdu.VALUE.encode(SNMP_SYNTAX_OPAQUE_FLOAT, sensor.moist); + break; + case '9': + status = pdu.VALUE.encode(SNMP_SYNTAX_OPAQUE_FLOAT, sensor.temp2); + break; + } + pdu.error = status; + } + } else { + // oid does not exist + // + // response packet - object not found + pdu.error = SNMP_ERR_NO_SUCH_NAME; + } + // + pdu.type = SNMP_PDU_RESPONSE; + + Agentbed.responsePdu(&pdu); + } + // + Agentbed.freePdu(&pdu); + // + //Serial << "UDP Packet Received End.." << " RAM:" << freeMemory() << endl; +}