commit 15fa09f75895f37d00e181f55b105bb76d5dbbdc
Author: Tom Mullins <tmullins@andrew.cmu.edu>
Date:   Sun Jan 27 19:02:30 2013 -0500

    Made errors less noisy
    
    If it can't connect to a tool, it will print an error once, and then
    print another message when it is able to reconnect.

diff --git a/mainbox/main.c b/mainbox/main.c
index d8330b8..3b3cb4b 100644
--- a/mainbox/main.c
+++ b/mainbox/main.c
@@ -7,8 +7,9 @@
 
 #define SLEEP_MS 250
 
-struct tool_t tools[] = {
-  {4, "test", TS_INIT}
+static struct tool_t tools[] = {
+  TOOL_DECL("testa", 4),
+  TOOL_DECL("testb", 5)
 };
 
 #define N_TOOLS (sizeof(tools)/sizeof(struct tool_t))
diff --git a/mainbox/tool.c b/mainbox/tool.c
index c3f4d6b..de14da4 100644
--- a/mainbox/tool.c
+++ b/mainbox/tool.c
@@ -1,4 +1,5 @@
 #include "tool.h"
+#include "query.h"
 #include "tooltron_mb.h"
 #include <modbus.h>
 #include <stdio.h>
@@ -56,19 +57,21 @@ static void tool_read_user(struct tool_t *tool) {
 }
 
 static void tool_grant_access(struct tool_t *tool) {
-  printf("Granting access to %08x on %s\n", tool->user, tool->name);
+  printf("Granting access to %08x on %s (%d)\n", tool->user, tool->name,
+      tool->address);
   tool_write_coil(MB_COIL_EN, 1);
   tool->state = TS_ON;
 }
 
 static void tool_deny_access(struct tool_t *tool) {
-  printf("Denying access to %08x on %s\n", tool->user, tool->name);
+  printf("Denying access to %08x on %s (%d)\n", tool->user, tool->name,
+      tool->address);
   tool_write_coil(MB_COIL_EN, 0);
   tool->state = TS_OFF;
 }
 
 void tool_request_disable(struct tool_t *tool) {
-  printf("Requesting disable on %s\n", tool->name);
+  printf("Requesting disable on %s (%d)\n", tool->name, tool->address);
   tool_write_coil(MB_COIL_REQ_DIS, 1);
   tool->state = TS_REQ_DIS;
 }
@@ -80,11 +83,27 @@ void tool_poll(struct tool_t *tool) {
     fprintf(stderr, "modbus_set_slave: %s\n", modbus_strerror(errno));
   }
 
+  /* If we can't read from the tool, we only want this error message to print
+   * once, thus tool->connected */
   if (modbus_read_bits(ctx, 0, N_COILS, status) == -1) {
-    fprintf(stderr, "modbus_read_bits: %s\n", modbus_strerror(errno));
+    if (tool->connected) {
+      fprintf(stderr, "Cannot connect to %s (%d): %s\n", tool->name,
+          tool->address, modbus_strerror(errno));
+      tool->connected = 0;
+    }
     return;
+  } else if (!tool->connected) {
+    fprintf(stderr, "Reconnected to %s (%d)\n", tool->name, tool->address);
+    tool->connected = 1;
   }
 
+  /*uint16_t current;
+  if (modbus_read_input_registers(ctx, MB_INP_CURRENT, 1, &current) == -1) {
+    fprintf(stderr, "modbus_read_registers: %s\n", modbus_strerror(errno));
+  } else {
+    printf("Current: %d\n", current);
+  }*/
+
   /*printf("new:%d en:%d req_dis:%d init:%d\n", status[MB_COIL_NEW],
       status[MB_COIL_EN], status[MB_COIL_REQ_DIS], status[MB_COIL_INIT]);*/
 
@@ -101,8 +120,7 @@ void tool_poll(struct tool_t *tool) {
     case TS_OFF:
       if (status[MB_COIL_NEW]) {
         tool_read_user(tool);
-        // TODO check actual credentials
-        if (tool->user == 0x023acbf6) {
+        if (query_user_permission(tool->address, tool->user)) {
           tool_grant_access(tool);
         } else {
           tool_deny_access(tool);
@@ -112,14 +130,15 @@ void tool_poll(struct tool_t *tool) {
 
     case TS_ON:
       if (!status[MB_COIL_EN]) {
-        printf("Tool %s is off\n", tool->name);
+        printf("Tool %s (%d) is off\n", tool->name, tool->address);
         tool->state = TS_OFF;
       }
       break;
 
     case TS_REQ_DIS:
       if (!status[MB_COIL_EN]) {
-        printf("Tool %s is off after requested disable\n", tool->name);
+        printf("Tool %s (%d) is off after requested disable\n", tool->name,
+            tool->address);
         tool->state = TS_OFF;
       }
       break;
diff --git a/mainbox/tool.h b/mainbox/tool.h
index 705c086..fa62f91 100644
--- a/mainbox/tool.h
+++ b/mainbox/tool.h
@@ -9,12 +9,15 @@ enum toolstate_t {
 };
 
 struct tool_t {
-  int address;
   const char *name;
+  int address;
+  int connected;
   enum toolstate_t state;
   unsigned int user;
 };
 
+#define TOOL_DECL(name, addr) {name, addr, 1, TS_INIT, 0}
+
 int tool_init_mb(const char *device);
 void tool_close_mb();
 void tool_request_disable(struct tool_t *tool);
