Advertisement
frankiepankie

P1 reader_minute_interval

Aug 19th, 2014
258
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 6.21 KB | None | 0 0
  1. /* Arduino 'slimme meter' P1 port reader.
  2.  
  3.  This sketch reads data from a Dutch smart meter that is equipped with a P1 port.
  4.  Connect 'RTS' from meter to Arduino pin 5
  5.  Connect 'GND' from meter to Arduino GND
  6.  Connect 'RxD' from meter to Arduino pin 8 (Digital)
  7.  
  8.  Baudrate 115200, 8N1.
  9.  BS170 transistor & 10k resistor is needed to make data readable if meter spits out inverted data
  10.  
  11.  A .php file is requested (with consumption numbers in the GET request) every minute (interval set at line #52)
  12.  created by 'ThinkPad' @ Tweakers.net, september 2014
  13.  
  14.  http://gathering.tweakers.net/forum/list_messages/1601301
  15.  */
  16.  
  17. #include <AltSoftSerial.h>
  18. #include <SPI.h>
  19. #include <Ethernet.h>
  20. // AltSoftSerial always uses these pins:
  21. //
  22. // Board          Transmit  Receive   PWM Unusable
  23. // -----          --------  -------   ------------
  24. // Teensy 2.0         9        10       (none)
  25. // Teensy++ 2.0      25         4       26, 27
  26. // Arduino Uno        9         8         10
  27. // Arduino Mega      46        48       44, 45
  28. // Wiring-S           5         6          4
  29. // Sanguino          13        14         12
  30.  
  31. AltSoftSerial altSerial;
  32.  
  33. byte mac[] = {
  34.   0xDE, 0xAD, 0xBE, 0x30, 0x32, 0x31};
  35. IPAddress ip(192,168,4,7);
  36. IPAddress server(192,168,4,4);
  37. EthernetClient client;
  38.  
  39. const int requestPin =  5;        
  40. char input; // incoming serial data (byte)
  41. bool readnextLine = false;
  42. #define BUFSIZE 75
  43. char buffer[BUFSIZE]; //Buffer for serial data to find \n .
  44. int bufpos = 0;
  45. long mEVLT = 0; //Meter reading Electrics - consumption low tariff
  46. long mEVHT = 0; //Meter reading Electrics - consumption high tariff
  47. long mEAV = 0;  //Meter reading Electrics - Actual consumption
  48. long mG = 0;   //Meter reading Gas
  49.  
  50. long lastTime = 0;        // will store last time
  51. long interval = 60000;           // interval at which to blink (milliseconds)
  52.  
  53. void setup() {
  54.   Serial.begin(9600);
  55.   delay(1000);
  56.  
  57.   altSerial.begin(115200);
  58.   delay(1000);
  59.  
  60.   Ethernet.begin(mac, ip);
  61.   delay(1000);
  62.   Serial.print("My IP address: ");
  63.   Serial.println(Ethernet.localIP());
  64.   Serial.print("Server IP address: ");
  65.   Serial.println(server);
  66.  
  67.   pinMode(4, OUTPUT);                  // SD select pin
  68.   digitalWrite(4, HIGH);               // Explicitly disable SD
  69.  
  70.   //Set RTS pin high, so smart meter will start sending telegrams
  71.   pinMode(requestPin, OUTPUT);
  72.   digitalWrite(requestPin, HIGH);
  73. }
  74.  
  75. void loop() {
  76.  
  77.   decodeTelegram();
  78.  
  79.   if(millis() - lastTime > interval) {
  80.     lastTime = millis();  
  81.  
  82.     //send data to PHP/MySQL
  83.     httpRequest();
  84.  
  85.     //Reset variables to zero for next run
  86.     mEVLT = 0;
  87.     mEVHT = 0;
  88.     mEAV = 0;
  89.     mG = 0;
  90.  
  91.     //Stop Ethernet
  92.     client.stop();
  93.  
  94.   }
  95.  
  96.  
  97.  
  98. } //Einde loop
  99.  
  100. void decodeTelegram() {
  101.   long tl = 0;
  102.   long tld =0;
  103.  
  104.   if (altSerial.available()) {
  105.     input = altSerial.read();
  106.  
  107.     char inChar = (char)input;
  108.     // Fill buffer up to and including a new line (\n)
  109.     buffer[bufpos] = input&127;
  110.     bufpos++;
  111.  
  112.     if (input == '\n') { // We received a new line (data up to \n)
  113.       if (sscanf(buffer,"1-0:1.8.1(%ld.%ld" ,&tl, &tld)==2){
  114.         tl *= 1000;
  115.         tl += tld;
  116.         mEVLT = tl;
  117.         if (mEVLT > 0) {
  118.           Serial.println("*** BEGIN LOOP ***");
  119.           Serial.print("Elektra - meterstand verbruik LAAG tarief: ");
  120.           Serial.println(mEVLT);
  121.  
  122.         }
  123.       }
  124.  
  125.         // 1-0:1.8.2 = Elektra verbruik hoog tarief (DSMR v4.0)
  126.         if (sscanf(buffer,"1-0:1.8.2(%ld.%ld" ,&tl, &tld)==2){
  127.         tl *= 1000;
  128.         tl += tld;
  129.         mEVHT = tl;
  130.         if (mEVHT > 0) {
  131.           Serial.print("Elektra - meterstand verbruik HOOG tarief: ");
  132.           Serial.println(mEVHT);
  133.  
  134.         }
  135.       }
  136.  
  137.       // 1-0:1.7.0 = Electricity consumption actual usage (DSMR v4.0)
  138.       if (sscanf(buffer,"1-0:1.7.0(%ld.%ld" ,&tl , &tld) == 2)
  139.       {
  140.         mEAV = (tl*1000)+tld;
  141.         if (mEAV > 0) {
  142.           Serial.print("Elektra - actueel verbruik (W): ");
  143.           Serial.println(mEAV);
  144.         }
  145.       }
  146.  
  147.       // 0-1:24.2.1 = Gas (DSMR v4.0) on Kaifa MA105 meter
  148.       if (strncmp(buffer, "0-1:24.2.1", strlen("0-1:24.2.1")) == 0) {
  149.         if (sscanf(strrchr(buffer, '(') + 1, "%d.%d", &tl, &tld) == 2) {
  150.           mG = (tl*1000)+tld;
  151.           Serial.print("Gas - meterstand (liters): ");
  152.           Serial.println(mG);
  153.           Serial.println("");
  154.         }
  155.       }
  156.  
  157.       // Empty buffer again (whole array)
  158.       for (int i=0; i<75; i++)
  159.       {
  160.         buffer[i] = 0;
  161.       }
  162.       bufpos = 0;
  163.  
  164.     }
  165.  
  166.     /*if (input == '!') {   //uitroepteken geeft einde van telegram aan, dus we gaan data versturen
  167.      httpRequest();
  168.      mEVLT = 0;
  169.      mEAV = 0;
  170.      mG = 0;
  171.      client.stop();
  172.      } //Einde vraagteken detectie   */
  173.  
  174.   } //Einde 'if AltSerial.available'
  175.  
  176. } //Einde 'decodeTelegram()' functie
  177.  
  178. void httpRequest() {
  179.   // if there's a successful connection:
  180.   if (client.connect(server, 80)) {
  181.     client.print("GET /www/slimmemeter/p1.php?mEVLT=");
  182.     client.print(mEVLT);
  183.     client.print("&mEVHT=");
  184.     client.print(mEVHT);
  185.     client.print("&mEAV=");
  186.     client.print(mEAV);
  187.     client.print("&mG=");
  188.     client.print(mG);
  189.     client.println(" HTTP/1.1");
  190.     client.println("Host: 192.168.4.4");
  191.     client.println("User-Agent: arduino-ethernet");
  192.     client.println("Connection: close");
  193.     client.println();
  194.     //Request complete; empty recieve buffer
  195.     while (client.available()) { //data available
  196.       char c = client.read(); //gets byte from ethernet buffer
  197.     }
  198.     client.println();
  199.     Serial.println("----------------------------Versturen naar database--------------------------");
  200.     Serial.println("Connection OK!");
  201.     Serial.print("GET /www/slimmemeter/p1.php?mEVLT=");
  202.     Serial.print(mEVLT);
  203.     Serial.print("&mEVHT=");
  204.     Serial.print(mEVHT);
  205.     Serial.print("&mEAV=");
  206.     Serial.print(mEAV);
  207.     Serial.print("&mG=");
  208.     Serial.println(mG);
  209.     Serial.println("-----------------------------------------------------------------------------");
  210.     Serial.println();
  211.     Serial.println("*** EINDE LOOP - Wachten op volgende telegram vanuit slimme meter ***");
  212.   }
  213.   else {
  214.     Serial.println("Connection failed");
  215.     client.stop();
  216.   }
  217. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement