]> mj.ucw.cz Git - home-hw.git/commitdiff
Power: CGI for Prometheus
authorMartin Mares <mj@ucw.cz>
Sat, 11 Aug 2018 11:16:41 +0000 (13:16 +0200)
committerMartin Mares <mj@ucw.cz>
Sat, 11 Aug 2018 11:16:41 +0000 (13:16 +0200)
power/Makefile [new file with mode: 0644]
power/power-cgi.c [new file with mode: 0644]

diff --git a/power/Makefile b/power/Makefile
new file mode 100644 (file)
index 0000000..973d6e6
--- /dev/null
@@ -0,0 +1,21 @@
+TOPDIR=/root/turris
+
+include $(TOPDIR)/rules.mk
+include $(TOPDIR)/include/package.mk
+
+PC := PATH=$(STAGING_DIR_HOST)/bin:$(PATH) PKG_CONFIG_PATH=$(PKG_CONFIG_PATH) PKG_CONFIG_LIBDIR=$(PKG_CONFIG_PATH) STAGING_PREFIX=$(STAGING_DIR)/usr $(PKG_CONFIG)
+MB_CFLAGS := $(shell $(PC) --cflags libmodbus)
+MB_LDFLAGS := $(shell $(PC) --libs libmodbus)
+
+export PATH=$(TARGET_PATH_PKG)
+CC=$(TARGET_CC_NOCACHE)
+LD=$(TARGET_LD_NOCACHE)
+CFLAGS=$(TARGET_CFLAGS) $(MB_CFLAGS) -std=gnu99
+LDFLAGS=$(TARGET_LDFLAGS) $(MB_LDFLAGS)
+
+all: power-cgi upload
+
+power-cgi: power-cgi.c
+
+upload:
+       rsync -av power-cgi micac:/www/burrow/power.cgi
diff --git a/power/power-cgi.c b/power/power-cgi.c
new file mode 100644 (file)
index 0000000..ac0f361
--- /dev/null
@@ -0,0 +1,77 @@
+#include <stdio.h>
+#include <stdarg.h>
+#include <stdlib.h>
+#include <syslog.h>
+#include <modbus.h>
+
+typedef unsigned int uint;
+
+void die(const char *msg, ...)
+{
+       va_list args;
+       va_start(args, msg);
+       vsyslog(LOG_ERR, msg, args);
+       // vfprintf(stderr, msg, args);
+       // fputc('\n', stderr);
+       printf("Status: 500\n");
+       printf("Content-Type: text/plain\n\n");
+       printf("Internal error, see syslog.\n");
+       exit(0);
+}
+
+static uint16_t reg[22];
+
+int32_t get_s32(uint i)
+{
+       if (reg[i+1] < 0x8000)
+               return (reg[i+1] << 16) | reg[i];
+       else
+               return ((reg[i+1] - 65536) * 65536) + reg[i];
+}
+
+int main(void)
+{
+       openlog("power.cgi", LOG_PID, LOG_LOCAL0);
+
+       modbus_t *ctx = modbus_new_rtu("/dev/ttyUSB0", 9600, 'N', 8, 1);
+       if (!ctx)
+               die("Unable to establish Modbus context");
+       modbus_set_slave(ctx, 42);
+       if (modbus_connect(ctx) < 0)
+               die("Unable to connect to Modbus");
+
+       if (modbus_read_registers(ctx, 0, 22, reg) < 0)
+               die("Modbus read failed");
+
+       printf("Content-type: text/plain; version=0.0.4\n\n");
+
+       printf("# HELP pm_voltage Voltage between phases and neutral [V]\n");
+       printf("# TYPE pm_voltage gauge\n");
+       printf("pm_voltage{phase=\"L1N\"} %.1f\n", get_s32(0) / 10.);
+       printf("pm_voltage{phase=\"L2N\"} %.1f\n", get_s32(2) / 10.);
+       printf("pm_voltage{phase=\"L3N\"} %.1f\n", get_s32(4) / 10.);
+
+       printf("# HELP pm_current Current through phases [A]\n");
+       printf("# TYPE pm_current gauge\n");
+       printf("pm_current{phase=\"L1\"} %.3f\n", get_s32(6) / 1000.);
+       printf("pm_current{phase=\"L2\"} %.3f\n", get_s32(8) / 1000.);
+       printf("pm_current{phase=\"L3\"} %.3f\n", get_s32(10) / 1000.);
+
+       printf("# HELP pm_power Total power [W]\n");
+       printf("# TYPE pm_power gauge\n");
+       printf("pm_power %.1f\n", get_s32(12) / 10.);
+
+       printf("# HELP pm_energy Total energy [kWh]\n");
+       printf("# TYPE pm_energy gauge\n");
+       printf("pm_energy %.1f\n", get_s32(14) / 10.);
+
+       printf("# HELP pm_reactive_power Reactive power [VAr]\n");
+       printf("# TYPE pm_reactive_power gauge\n");
+       printf("pm_reactive_power %.1f\n", get_s32(18) / 10.);
+
+       printf("# HELP pm_reactive_energy Total reactive energy [kVArh]\n");
+       printf("# TYPE pm_reactive_energy gauge\n");
+       printf("pm_reactive_energy %.1f\n", get_s32(20) / 10.);
+
+       return 0;
+}