Index: trunk/code/lib/include/libdragonfly/spi.h
===================================================================
--- trunk/code/lib/include/libdragonfly/spi.h	(revision 1460)
+++ trunk/code/lib/include/libdragonfly/spi.h	(revision 1461)
@@ -12,6 +12,8 @@
 #ifndef __SPI_H__
 #define __SPI_H__
 
+#include<dragonfly_lib.h>
+
 #define DOUBLE_SCK 1
 #define SPR0_BIT 1
 
@@ -32,7 +34,7 @@
 * @param spi_fun_recv_t The function that handles SPI data, byte for byte.
 * @param spi_fun_recv_complete_t  Called on a completed transmission - typically for cleaning up.
 */
-void spi_init (spi_fun_recv_t, spi_fun_recv_complete_t);
+int spi_init (spi_fun_recv_t, spi_fun_recv_complete_t);
 
 /** 
 * @brief Initialize SPI transfer.
@@ -39,7 +41,7 @@
 * 
 * @param char The number of bytes to transfer.
 */
-void spi_transfer (char);
+int spi_transfer (char);
 
 /**@}**/ //end group
 
Index: trunk/code/lib/include/libdragonfly/time.h
===================================================================
--- trunk/code/lib/include/libdragonfly/time.h	(revision 1460)
+++ trunk/code/lib/include/libdragonfly/time.h	(revision 1461)
@@ -37,6 +37,8 @@
 #ifndef _TIME_H_
 #define _TIME_H_
 
+#include <dragonfly_lib.h>
+
 /*	Predefined times for prescale_opt in time.c.
 	To make you own, know that a pulse is 1/16th of a second. You cannot get less than this. To get more, you need
 	to know how many 16ths of a second are in the time you want. (Time_desired * 16 = prescaler_opt)
@@ -63,7 +65,7 @@
 /** @brief Delay execution for the specified time **/
 void delay_ms(int ms) ;
 /** @brief Enable the realtime clock **/
-void rtc_init(int prescale_opt, void (*rtc_func)(void));
+int rtc_init(int prescale_opt, void (*rtc_func)(void));
 /** @brief Reset the counter of the realtime clock **/
 void rtc_reset(void);
 /** @brief Get the value of the realtime clock. **/
Index: trunk/code/lib/include/libdragonfly/motor.h
===================================================================
--- trunk/code/lib/include/libdragonfly/motor.h	(revision 1460)
+++ trunk/code/lib/include/libdragonfly/motor.h	(revision 1461)
@@ -38,6 +38,7 @@
 #ifndef _MOTOR_H
 #define _MOTOR_H
 
+#include <dragonfly_lib.h>
 #include <avr/io.h>
 /**
  * @addtogroup motors
@@ -50,19 +51,19 @@
 #define BACKWARD 0
 
 /** @brief Initialize the motors **/
-void motors_init(void);
+int motors_init(void);
 /** @brief Set speed and direction of motor1 
  *  @deprecated use the left motor function instead. it's more intuitive and easier to read.**/
-void motor1_set(int direction, int speed);
+int motor1_set(int direction, int speed);
 /** @brief Set speed and direction of motor2 
  *  @deprecated use the right motor function instead. it's more intuitive and easier to read.**/
-void motor2_set(int direction, int speed);
+int motor2_set(int direction, int speed);
 /** @brief Set speed and direction of left motor **/
-void motor_l_set(int direction, int speed);
+int motor_l_set(int direction, int speed);
 /** @brief Set speed and direction of right motor **/
-void motor_r_set(int direction, int speed);
+int motor_r_set(int direction, int speed);
 /** @brief Turn the motors off **/
-void motors_off(void);
+int motors_off(void);
 
 /**@}**/ // end addtogroup
 
Index: trunk/code/lib/include/libdragonfly/analog.h
===================================================================
--- trunk/code/lib/include/libdragonfly/analog.h	(revision 1460)
+++ trunk/code/lib/include/libdragonfly/analog.h	(revision 1461)
@@ -113,11 +113,11 @@
 
 /** @brief Initialize analog ports. Will start running a loop
     if start_conversion is ADC_START.**/
-void analog_init(int start_conversion);
+int analog_init(int start_conversion);
 /** @brief starts the analog loop. Doesn't do anything if the loop is already running. **/
-void analog_start_loop(void);
+int analog_start_loop(void);
 /** @brief Stops the analog loop. Doesn't do anything if the loop is already stopped. **/
-void analog_stop_loop(void);
+int analog_stop_loop(void);
 /** @brief Returns the status of the analog loop. **/
 int analog_loop_status(void);
 /** @brief Returns an 8-bit analog value from the look up table. Use this instead of analog_get8. **/
Index: trunk/code/lib/include/libdragonfly/encoders.h
===================================================================
--- trunk/code/lib/include/libdragonfly/encoders.h	(revision 1460)
+++ trunk/code/lib/include/libdragonfly/encoders.h	(revision 1461)
@@ -51,6 +51,10 @@
 #define MagINCn _BV(1)
 #define MagDECn _BV(0)
 
+#ifdef BUFFER_SIZE
+#error BUFFER_SIZE already defined!
+#endif
+
 /** @brief Buffer size **/
 #define BUFFER_SIZE 46
 
@@ -57,7 +61,7 @@
 #define ERR_VEL 1024
 
 /** @brief Initialize encoders. **/
-void encoders_init(void);
+int encoders_init(void);
 /** @brief Read instantaneous encoder value. **/
 int encoder_read(char encoder);
 
@@ -72,14 +76,14 @@
 /** @brief Get total distance traveled. **/
 int encoder_get_dx(char encoder);
 /** @brief Reset distance counter. **/
-void encoder_rst_dx(char encoder);
+int encoder_rst_dx(char encoder);
 /** @brief Get time count: The number of encoder reads that have occurred. **/
 int encoder_get_tc(void);
 /** @brief Reset the time count. **/
-void encoder_rst_tc(void);
+int encoder_rst_tc(void);
 
 /** @brief Waits for the next n encoder reading, then returns. **/
-void encoder_wait( int nReadings );
+int encoder_wait( int nReadings );
 
 /**@}**/ //end group
 
Index: trunk/code/lib/include/libdragonfly/dragonfly_lib.h
===================================================================
--- trunk/code/lib/include/libdragonfly/dragonfly_lib.h	(revision 1460)
+++ trunk/code/lib/include/libdragonfly/dragonfly_lib.h	(revision 1461)
@@ -41,6 +41,12 @@
  * @{
  **/
 
+//return value definitions
+#define ERROR_INIT_FAILED 1
+#define ERROR_INIT_ALREADY_INITD 2
+
+#define ERROR_LIBRARY_NOT_INITD 3
+
 // Configuration definitions
 /** @brief Initialize analog **/
 #define ANALOG 0x01
Index: trunk/code/lib/include/libdragonfly/bom.h
===================================================================
--- trunk/code/lib/include/libdragonfly/bom.h	(revision 1460)
+++ trunk/code/lib/include/libdragonfly/bom.h	(revision 1461)
@@ -57,10 +57,10 @@
 
 
 /** @brief Initialize the bom according to bom type **/
-void bom_init(char type);
+int bom_init(char type);
 
 /** @brief Refresh bom_val[] with new values from analog8.  analog_init and bom_init must be called for this to work. **/
-void bom_refresh(int bit_field);
+int bom_refresh(int bit_field);
 
 /** @brief Gets the bom reading from bom_val[which].  Call bom_refresh beforehand to read new bom values. **/
 int bom_get(int which);
@@ -72,16 +72,16 @@
 int bom_get_max10(int *dist);
 
 /** @brief Enables the selected bom leds on a BOM1.5 **/
-void bom_set_leds(int bit_field);
+int bom_set_leds(int bit_field);
 
 /** @brief (DEPRECATED) Gets and compares all bom values.  Returns the index to the highest value element since last refresh. **/
 int get_max_bom(void);
 
 /** @brief Turns on all BOM leds, or turns on enabled leds on a BOM1.5. **/
-void bom_on(void);
+int bom_on(void);
 
 /** @brief Turns off all bom leds. **/
-void bom_off(void);
+int bom_off(void);
 
 /** @} **/
 
Index: trunk/code/lib/include/libdragonfly/serial.h
===================================================================
--- trunk/code/lib/include/libdragonfly/serial.h	(revision 1460)
+++ trunk/code/lib/include/libdragonfly/serial.h	(revision 1461)
@@ -68,6 +68,7 @@
 #ifndef _SERIAL_H
 #define _SERIAL_H
 
+#include <dragonfly_lib.h>
 #include <inttypes.h>
 #include <avr/pgmspace.h>
 
@@ -87,7 +88,7 @@
 #endif
 
 /** @brief Initialize the USB **/
-void usb_init(void);
+int usb_init(void);
 /** @brief Print a character to USB **/
 int usb_putc(char c);
 /** @brief Read a character from USB **/
@@ -97,15 +98,15 @@
 /** @brief Print a string to USB **/
 int usb_puts(char *s);
 /** @brief Print a string from program space to USB **/
-void usb_puts_P (PGM_P s);
+int usb_puts_P (PGM_P s);
 /** @brief Print an integer to USB **/
 int usb_puti(int value);
 /** @brief Determine a hexadecimal digit **/
 uint8_t hex_digit (uint8_t value);
 /** @brief Print a fixed width hexadecimal representation to USB **/
-void usb_puth16 (uint16_t value);
+int usb_puth16 (uint16_t value);
 /** @brief Print a fixed width hexadecimal representation to USB **/
-void usb_puth8(uint8_t value);
+int usb_puth8(uint8_t value);
 /** @brief Alias for usb_puth16 **/
 static inline void usb_puth (uint16_t value) { usb_puth16 (value); };
 
@@ -130,7 +131,7 @@
 #endif
 
 /** @brief Initialize the XBee **/
-void xbee_init(void);
+int xbee_init(void);
 /** @brief Print a character to the XBee **/
 int xbee_putc(char c);
 /** @brief Read a character from the XBee **/
Index: trunk/code/lib/include/libdragonfly/rangefinder.h
===================================================================
--- trunk/code/lib/include/libdragonfly/rangefinder.h	(revision 1460)
+++ trunk/code/lib/include/libdragonfly/rangefinder.h	(revision 1461)
@@ -37,6 +37,8 @@
 #ifndef _RANGEFINDER_H_
 #define _RANGEFINDER_H_
 
+#include <dragonfly_lib.h>
+
 /**
  * @addtogroup rangefinder
  * @{
@@ -58,7 +60,7 @@
 #define MAX_IR_ADC8 133
 
 /** @brief Initialize the rangefinders **/
-void range_init(void);
+int range_init(void);
 /** @brief Read the distance from a rangefinder **/
 int range_read_distance(int range_id);
 /** @brief Convert logarithmic-scale distance readings to a linear scale **/
Index: trunk/code/lib/include/libdragonfly/eeprom.h
===================================================================
--- trunk/code/lib/include/libdragonfly/eeprom.h	(revision 1460)
+++ trunk/code/lib/include/libdragonfly/eeprom.h	(revision 1461)
@@ -1,12 +1,3 @@
-/**
- * @file eeprom.h
- * @brief handles eeprom storage for persistent data
- *
- * Contains functions and definitions for reading and writing to eeprom
- *
- * @author Colony Project, Brad Neuman
- */
- 
  #ifndef _EEPROM_H_
  #define _EEPROM_H_
  
@@ -13,35 +4,12 @@
  #define EEPROM_ROBOT_ID_ADDR 0x10
  #define EEPROM_BOM_TYPE_ADDR 0x14
  
- /** @brief store a byte to eeproem
-  *  @return 0 if success, nonzero on failure
-  */
  int eeprom_put_byte(unsigned int addr, unsigned char byte);
  
- /** @brief reads a byte from eeprom
-  *
-  *  Pass it thge address and a pointer to a byte where the byte at the
-  *  address will be stored
-  *
-  *  @return 0 if successful (byte is set to the eeprom value at addr), 
-  *  nonzero if there was a problem
-   */
  int eeprom_get_byte(unsigned int addr, unsigned char *byte);
  
- /** @brief get stored robot ID
-  *
-  *  checks that EEPROM has been programed with an ID and returns it
-  *
-  *  @return the robot id, if it is stored. If it returns 0xFF it is probably invalid
-  */
  unsigned char get_robotid(void);
   
-   /** @brief get stored robot ID
-  *
-  * checks that EEPROM has been programed with an BOM type and returns it
-  *
-  *  @return the robot bom type as defined in bom.h, if it is stored. If it returns 0xFF it is probably invalid
-  */
  unsigned char get_bom_type(void);
  
  #endif
Index: trunk/code/lib/bin/libwireless.a
===================================================================
Cannot display: file marked as a binary type.
svn:mime-type = application/octet-stream
Index: trunk/code/lib/bin/libdragonfly.a
===================================================================
Cannot display: file marked as a binary type.
svn:mime-type = application/octet-stream
Index: trunk/code/projects/test/test_motors.c
===================================================================
--- trunk/code/projects/test/test_motors.c	(revision 1460)
+++ trunk/code/projects/test/test_motors.c	(revision 1461)
@@ -61,6 +61,9 @@
     delay_ms(3000);
 	//while(1){;}
 
+
+    motors_off();
+
     return 0;
 }
 
@@ -69,4 +72,4 @@
 left >154 forward
 right >150 forward
 both >152 backward
-*/
\ No newline at end of file
+*/
Index: trunk/code/projects/test/test_rangefinder.c
===================================================================
--- trunk/code/projects/test/test_rangefinder.c	(revision 1460)
+++ trunk/code/projects/test/test_rangefinder.c	(revision 1461)
@@ -30,6 +30,7 @@
     int i;  // index
     int sensor[5] = {IR4, IR3, IR2, IR1, IR5};
     int color[5] = {RED, ORANGE, YELLOW, GREEN, BLUE};
+    int ret;
 
     // flash orbs BLUE 3 times
     for (i = 0; i < 3; i++) {
@@ -44,9 +45,20 @@
 	orb2_set_color(color[i]);
 
 	// wait for sensor interaction
-	while (range_read_distance(sensor[i]) == -1)
+	while ((ret = range_read_distance(sensor[i])) == -1) {
 	    // stay RED until IR4 sees something
 	    orb1_set_color(RED);
+	    if(ret == -3) { //library not init'd 
+	      while(1) {
+		orb2_set_color(GREEN);
+		orb1_set_color(RED);
+		delay_ms(250);
+		orb1_set_color(GREEN);
+		orb2_set_color(RED);
+		delay_ms(250);
+	      }
+	    }
+	}
 
 	orb1_set_color(GREEN);
 	delay_ms(TEST_TIME);
Index: trunk/code/projects/test/main.c
===================================================================
--- trunk/code/projects/test/main.c	(revision 1460)
+++ trunk/code/projects/test/main.c	(revision 1461)
@@ -3,20 +3,22 @@
 #define RUN_TEST(f) extern int f(void); f();
 
 int main(void) {
+  RUN_TEST(testinits);
+
   dragonfly_init(ALL_ON);
 
   while (1) {
-    // RUN_TEST(testusb);
+    //RUN_TEST(testusb);
     // RUN_TEST(testanalog);
-    // RUN_TEST(testeeprom);
+    //RUN_TEST(testeeprom);
     // RUN_TEST(testencoders);
     // RUN_TEST(testlcd);
-    // RUN_TEST(testlights);
-    // RUN_TEST(testmotors);
-    // RUN_TEST(testrangefinder);
+    //RUN_TEST(testlights);
+    //RUN_TEST(testmotors);
+    RUN_TEST(testrangefinder);
     // RUN_TEST(testtokenring);
     // RUN_TEST(testwireless);
-    RUN_TEST(testxbee);
+    //RUN_TEST(testxbee);
     delay_ms(1000);
   }
 
Index: trunk/code/projects/hunter_prey/testbench/main.c
===================================================================
--- trunk/code/projects/hunter_prey/testbench/main.c	(revision 1460)
+++ trunk/code/projects/hunter_prey/testbench/main.c	(revision 1461)
@@ -62,7 +62,7 @@
     delay8.tv_sec = 2;
     delay8.tv_nsec = 800000000;
 
-    wl_set_com_port("/dev/ttyUSB0");
+    wl_set_com_port("/dev/ttyUSB1");
     // set up wireless
     wl_basic_init_default();
     wl_set_channel(channel);
Index: trunk/code/projects/libdragonfly/motor.c
===================================================================
--- trunk/code/projects/libdragonfly/motor.c	(revision 1460)
+++ trunk/code/projects/libdragonfly/motor.c	(revision 1461)
@@ -43,13 +43,22 @@
  * @{
  **/
 
+unsigned char motors_initd=0;
+
 /**
  * Initializes both motors so that they can be used with future
  * calls to motor1_set and motor2_set.
  *
+ * @return 0 if init succesfull, an error code otherwise
+ *
  * @see motors_off, motor1_set, motor2_set
  **/
-void motors_init( void ) {
+int motors_init( void ) {
+
+  if(motors_initd)
+    return ERROR_INIT_ALREADY_INITD;
+
+
   // Configure counter such that we use phase correct
   // PWM with 8-bit resolution
   PORTA &= 0x0F;
@@ -65,6 +74,9 @@
   OCR1AL=0;
   OCR1BH=0;
   OCR1BL=0;
+
+  motors_initd=1;
+  return 0;
 }
 
 /**
@@ -74,9 +86,13 @@
  * @param direction Either FORWARD or BACKWARD to set the direction of rotation.
  * @param speed The speed the motor will run at, in the range 0-255.
  * 
+ * @return 0 if init succesfull, an error code otherwise
+ *
  * @see motor_r_set, motors_init
  **/
-void motor_l_set(int direction, int speed) {
+int motor_l_set(int direction, int speed) {
+  if(!motors_initd)
+    return ERROR_LIBRARY_NOT_INITD;
 
   if(direction == 0) {
     // turn off PWM first if switching directions
@@ -98,6 +114,8 @@
 	
   // Set the timer to count up to speed, an 8-bit value
   OCR1AL = speed;
+
+  return 0;
 }
 
 /**
@@ -107,9 +125,14 @@
  * @param direction Either FORWARD or BACKWARD to set the direction of rotation.
  * @param speed The speed the motor will run at, in the range 0-255.
  *
+ * @return 0 if init succesfull, an error code otherwise
+ *
  * @see motor_l_set, motors_init
  **/
-void motor_r_set(int direction, int speed) {
+int motor_r_set(int direction, int speed) {
+  if(!motors_initd)
+    return ERROR_LIBRARY_NOT_INITD;
+
   if(direction == 0) {
     //		PORTD |= 0x20;
     //		PORTD &= 0x7F;
@@ -131,6 +154,8 @@
     PORTA = (PORTA & 0x3F) | 0x40;
   }
   OCR1BL = speed;
+
+  return 0;
 }
 
 /**
@@ -140,10 +165,12 @@
  * @param direction Either FORWARD or BACKWARD to set the direction of rotation.
  * @param speed The speed the motor will run at, in the range 0-255.
  *
+ * @return 0 if init succesfull, an error code otherwise
+ *
  * @see motor2_set, motors_init
  **/
-void motor1_set(int direction, int speed) {
-	motor_l_set(direction, speed);
+int motor1_set(int direction, int speed) {
+  return motor_l_set(direction, speed);
 }
 
 /**
@@ -153,10 +180,12 @@
  * @param direction Either FORWARD or BACKWARD to set the direction of rotation.
  * @param speed The speed the motor will run at, in the range 0-255.
  *
+ * @return 0 if init succesfull, an error code otherwise
+ *
  * @see motor2_set, motors_init
  **/
-void motor2_set(int direction, int speed) {
-	motor_r_set(direction, speed);
+int motor2_set(int direction, int speed) {
+  return motor_r_set(direction, speed);
 }
 
 
@@ -163,11 +192,18 @@
 /**
  * Turns off both motors.
  *
+ * @return 0 if init succesfull, an error code otherwise
+ *
  * @see motors_init
  **/
-void motors_off( void ) {
+int motors_off( void ) {
+  if(!motors_initd)
+    return ERROR_LIBRARY_NOT_INITD;
+
   OCR1AL = 0x0;
   OCR1BL = 0x0;
+
+  return 0;
 }
 
 /**@}**///end defgroup
Index: trunk/code/projects/libdragonfly/motor.h
===================================================================
--- trunk/code/projects/libdragonfly/motor.h	(revision 1460)
+++ trunk/code/projects/libdragonfly/motor.h	(revision 1461)
@@ -38,6 +38,7 @@
 #ifndef _MOTOR_H
 #define _MOTOR_H
 
+#include <dragonfly_lib.h>
 #include <avr/io.h>
 /**
  * @addtogroup motors
@@ -50,19 +51,19 @@
 #define BACKWARD 0
 
 /** @brief Initialize the motors **/
-void motors_init(void);
+int motors_init(void);
 /** @brief Set speed and direction of motor1 
  *  @deprecated use the left motor function instead. it's more intuitive and easier to read.**/
-void motor1_set(int direction, int speed);
+int motor1_set(int direction, int speed);
 /** @brief Set speed and direction of motor2 
  *  @deprecated use the right motor function instead. it's more intuitive and easier to read.**/
-void motor2_set(int direction, int speed);
+int motor2_set(int direction, int speed);
 /** @brief Set speed and direction of left motor **/
-void motor_l_set(int direction, int speed);
+int motor_l_set(int direction, int speed);
 /** @brief Set speed and direction of right motor **/
-void motor_r_set(int direction, int speed);
+int motor_r_set(int direction, int speed);
 /** @brief Turn the motors off **/
-void motors_off(void);
+int motors_off(void);
 
 /**@}**/ // end addtogroup
 
Index: trunk/code/projects/libdragonfly/i2c.c
===================================================================
--- trunk/code/projects/libdragonfly/i2c.c	(revision 1460)
+++ trunk/code/projects/libdragonfly/i2c.c	(revision 1461)
@@ -43,6 +43,10 @@
 #include "i2c.h"
 #include "ring_buffer.h"
 
+//NOTE: this is here just to provide colony error codes, it can be safely removed
+// for use in another project
+#include <dragonfly_lib.h>
+
 /**
  * @defgroup i2c I2C 
  *
@@ -78,6 +82,8 @@
  */
 #define I2C_BIT_RATE_DIVIDER 0x0C
 
+unsigned char i2c_initd=0;
+
 static int start_flag;
 
 static fun_mrecv_t master_recv_function;
@@ -105,6 +111,11 @@
  * @return 0 for success, nonzero for failure
  **/
 int i2c_init(char addr, fun_mrecv_t master_recv, fun_srecv_t slave_recv, fun_send_t slave_send) {
+
+    if(i2c_initd)
+      return ERROR_INIT_ALREADY_INITD;
+
+
     master_recv_function = master_recv;
     slave_recv_function = slave_recv;
     slave_send_function = slave_send;
@@ -122,6 +133,7 @@
      * global messages to be accepted */
     TWAR = (addr << 1) | 1;
   
+    i2c_initd = 1;
     return 0;
 }
 
@@ -141,6 +153,10 @@
 int i2c_send(char dest, char *data, unsigned int bytes) {
     int i;
 
+    if(!i2c_initd)
+      return ERROR_LIBRARY_NOT_INITD;
+
+
     /* adding data to be sent to ring buffers is not atomic,
      * so disable interrupts */
     cli();
@@ -180,6 +196,9 @@
  * @return 0 for success, nonzero for failure
  **/ 
 int i2c_request(char dest) {
+    if(!i2c_initd)
+      return ERROR_LIBRARY_NOT_INITD;
+
     if(RING_BUFFER_FULL(i2c_write_buff))
         return -1;
   
Index: trunk/code/projects/libdragonfly/serial.c
===================================================================
--- trunk/code/projects/libdragonfly/serial.c	(revision 1460)
+++ trunk/code/projects/libdragonfly/serial.c	(revision 1461)
@@ -36,6 +36,9 @@
 #include <avr/io.h>
 #include "serial.h"
 
+unsigned char usb_initd=0;
+unsigned char xbee_initd=0;
+
 #ifdef USE_STDIO
 
 #include <stdio.h>
@@ -57,10 +60,15 @@
  * This must be called before any other usb function
  * may be used.
  **/
-void usb_init() {
+int usb_init() {
   //Set baud rate
   // - 115200 (both wired and wireless) is UBRR=8, U2X=1
   // - 9600 is U2X =1, UBRR = 107.
+
+  if(usb_initd) {
+    return ERROR_INIT_ALREADY_INITD;
+  }
+
 #if (USB_BAUD == 115200)
   UBRR0H = 0x00;
   UBRR0L = 8;
@@ -70,7 +78,7 @@
   UBRR0L = 103;
   UCSR0A |= _BV(U2X0);
 #else //Baud rate is defined in the header file, we should not get here
-  return;
+  return 0;
 #endif
 
   /*Enable receiver and transmitter */
@@ -84,6 +92,10 @@
   /* Open the stdio stream corresponding to this port */
   usb_fd = fdevopen(usb_putc, usb_getc);
 #endif
+
+  usb_initd = 1;
+  return 0;
+
 }
 
 /**
@@ -91,7 +103,12 @@
  * This must be called before any other xbee function
  * may be used.
  **/
-void xbee_init() {
+int xbee_init() {
+
+  if(xbee_initd) {
+    return ERROR_INIT_ALREADY_INITD;
+  }
+
   //Set baud rate
   // - 115200 (both wired and wireless) is UBRR=8, U2X=1
   // - 9600 is U2X =1, UBRR = 107.
@@ -104,7 +121,7 @@
   UBRR1L = 103;
   UCSR1A |= _BV(U2X1);
 #else //Baud rate is defined in the header file, we should not get here
-  return;
+  return 0;
 #endif
 
   //Enable receiver and transmitter
@@ -118,6 +135,10 @@
   /* Open the stdio stream corresponding to this port */
   xbee_fd = fdevopen(xbee_putc, xbee_getc);
 #endif
+
+  xbee_initd = 1;
+  return 0;
+
 }
 
 /**
@@ -127,6 +148,10 @@
  * @return 0 for success, nonzero for failure
  **/
 int usb_putc(char c) {
+
+  if(!usb_initd)
+    return ERROR_LIBRARY_NOT_INITD;
+
   // Wait until buffer is clear for sending
   loop_until_bit_is_set(UCSR0A, UDRE0);
 	
@@ -142,6 +167,10 @@
  * @return 0 for success, nonzero for failure
  **/
 int xbee_putc(char c) {
+
+  if(!xbee_initd)
+    return ERROR_LIBRARY_NOT_INITD;
+
   // Wait until buffer is clear for sending
   loop_until_bit_is_set(UCSR1A, UDRE1);
 	
@@ -158,6 +187,10 @@
  **/
 int usb_puts(char *s) {
   char *t = s;
+
+  if(!usb_initd)
+    return ERROR_LIBRARY_NOT_INITD;
+
   while (*t != 0) {
     usb_putc(*t);
     t++;
@@ -169,14 +202,21 @@
  * Sends a sequence of characters from program space over USB.
  *
  * @param s the string to send
+ *
+ * @return 0 if init succesfull, an error code otherwise
  **/
-void usb_puts_P (PGM_P s) {
+int usb_puts_P (PGM_P s) {
     char buf;
+
+    if(!usb_initd)
+      return ERROR_LIBRARY_NOT_INITD;
 	
     while (memcpy_P (&buf, s, sizeof (char)), buf!=0) {
         usb_putc (buf);
         s++;
     }
+
+    return 0;
 }
 
 
@@ -186,11 +226,15 @@
  * This function blocks execution until a character has been received.
  * xbee_init must be called before this function may be used.
  * 
- * @return the first character in the usb buffer
+ * @return the first character in the usb buffer, -1 on error
  *
  * @see usb_init, usb_getc_nb
  **/
 int usb_getc(void) {
+
+  if(!usb_initd)
+    return -1;
+
   // Wait for the receive buffer to be filled
   loop_until_bit_is_set(UCSR0A, RXC0);
 	
@@ -204,11 +248,15 @@
  * received. xbee_init must be called before this function
  * may be used.
  * 
- * @return the first character in the xbee buffer
+ * @return the first character in the xbee buffer, -1 on error
  * 
  * @see xbee_init, xbee_getc_nb
  **/
 int xbee_getc(void) {
+
+  if(!usb_initd)
+    return -1;
+
   // Wait for the receive buffer to be filled
   loop_until_bit_is_set(UCSR1A, RXC1);
 	
@@ -224,11 +272,15 @@
  * @param c the received character. This will be set if a character has
  * been received.
  * 
- * @return -1 if no character is available, 0 otherwise
+ * @return -1 if no character is available, 0 otherwise, positive for error
  * 
  * @see usb_init, usb_getc
  **/
 int usb_getc_nb(char *c) {
+
+  if(!usb_initd)
+    return ERROR_LIBRARY_NOT_INITD;
+
   // check if the receive buffer is filled
   if (UCSR0A & _BV(RXC0)) {
     // Read the receive buffer
@@ -248,11 +300,14 @@
  * @param c the received character. This will be set if a character has
  * been received.
  * 
- * @return -1 if no character is available, 0 otherwise
+ * @return -1 if no character is available, 0 otherwise, positive for error
  *
  * @see xbee_init, xbee_getc
  **/
 int xbee_getc_nb(char *c) {
+  if(!xbee_initd)
+    return ERROR_LIBRARY_NOT_INITD;
+
   // check if the receive buffer is filled
   if (UCSR1A & _BV(RXC1)) {
     // Read the receive buffer
@@ -284,6 +339,10 @@
 int usb_puti(int value ) {
   unsigned char usb_data[6]={'0','0','0','0','0','0' }, position=sizeof(usb_data), radix=10; 
 
+  if(!usb_initd)
+    return ERROR_LIBRARY_NOT_INITD;
+
+
   /* convert int to ascii  */ 
   if(value<0) { 
     usb_putc('-'); 
@@ -329,13 +388,20 @@
  * @param value the value to print
  * 
  * @see usb_init, usb_puti, usb_puts, usb_puth8, hex_digit
+ *
+ * @return 0 if init succesfull, an error code otherwise
  **/
-void usb_puth16 (uint16_t value)
+int usb_puth16 (uint16_t value)
 {
+    if(!usb_initd)
+      return ERROR_LIBRARY_NOT_INITD;
+
     usb_putc (hex_digit((value >>12)&0xF));
     usb_putc (hex_digit((value >>8 )&0xF));
     usb_putc (hex_digit((value >>4 )&0xF));
     usb_putc (hex_digit( value      &0xF));
+
+    return 0;
 }
 
 /**
@@ -346,10 +412,17 @@
  * @param value the value to print
  * 
  * @see usb_init, usb_puti, usb_puts, usb_puth16, hex_digit
+ *
+ * @return 0 if init succesfull, an error code otherwise
  **/
-void usb_puth8(uint8_t value)
+int usb_puth8(uint8_t value)
 {
+    if(!usb_initd)
+      return ERROR_LIBRARY_NOT_INITD;
+
     usb_putc (hex_digit ((value)>>4 &0xF));
     usb_putc (hex_digit ( value     &0xF));
+
+    return 0;
 }
 
Index: trunk/code/projects/libdragonfly/dragonfly_lib.h
===================================================================
--- trunk/code/projects/libdragonfly/dragonfly_lib.h	(revision 1460)
+++ trunk/code/projects/libdragonfly/dragonfly_lib.h	(revision 1461)
@@ -41,6 +41,12 @@
  * @{
  **/
 
+//return value definitions
+#define ERROR_INIT_FAILED 1
+#define ERROR_INIT_ALREADY_INITD 2
+
+#define ERROR_LIBRARY_NOT_INITD 3
+
 // Configuration definitions
 /** @brief Initialize analog **/
 #define ANALOG 0x01
Index: trunk/code/projects/libdragonfly/serial.h
===================================================================
--- trunk/code/projects/libdragonfly/serial.h	(revision 1460)
+++ trunk/code/projects/libdragonfly/serial.h	(revision 1461)
@@ -68,6 +68,7 @@
 #ifndef _SERIAL_H
 #define _SERIAL_H
 
+#include <dragonfly_lib.h>
 #include <inttypes.h>
 #include <avr/pgmspace.h>
 
@@ -87,7 +88,7 @@
 #endif
 
 /** @brief Initialize the USB **/
-void usb_init(void);
+int usb_init(void);
 /** @brief Print a character to USB **/
 int usb_putc(char c);
 /** @brief Read a character from USB **/
@@ -97,15 +98,15 @@
 /** @brief Print a string to USB **/
 int usb_puts(char *s);
 /** @brief Print a string from program space to USB **/
-void usb_puts_P (PGM_P s);
+int usb_puts_P (PGM_P s);
 /** @brief Print an integer to USB **/
 int usb_puti(int value);
 /** @brief Determine a hexadecimal digit **/
 uint8_t hex_digit (uint8_t value);
 /** @brief Print a fixed width hexadecimal representation to USB **/
-void usb_puth16 (uint16_t value);
+int usb_puth16 (uint16_t value);
 /** @brief Print a fixed width hexadecimal representation to USB **/
-void usb_puth8(uint8_t value);
+int usb_puth8(uint8_t value);
 /** @brief Alias for usb_puth16 **/
 static inline void usb_puth (uint16_t value) { usb_puth16 (value); };
 
@@ -130,7 +131,7 @@
 #endif
 
 /** @brief Initialize the XBee **/
-void xbee_init(void);
+int xbee_init(void);
 /** @brief Print a character to the XBee **/
 int xbee_putc(char c);
 /** @brief Read a character from the XBee **/
Index: trunk/code/projects/libdragonfly/eeprom.c
===================================================================
--- trunk/code/projects/libdragonfly/eeprom.c	(revision 1460)
+++ trunk/code/projects/libdragonfly/eeprom.c	(revision 1461)
@@ -1,6 +1,18 @@
+/**
+ * @file eeprom.c
+ * @brief handles eeprom storage for persistent data
+ *
+ * Contains functions and definitions for reading and writing to eeprom
+ *
+ * @author Colony Project, Brad Neuman
+ */
+ 
 #include <avr/io.h>
 #include "eeprom.h"
 
+/** @brief store a byte to eeproem
+ *  @return 0 if success, nonzero on failure
+ */
 int eeprom_put_byte(unsigned int uiAddress, unsigned char ucData) {
     /* Wait for completion of previous write */
     while(EECR & (1<<EEWE));
@@ -15,6 +27,14 @@
     return 0;
 }
 
+/** @brief reads a byte from eeprom
+ *
+ *  Pass it thge address and a pointer to a byte where the byte at the
+ *  address will be stored
+ *
+ *  @return 0 if successful (byte is set to the eeprom value at addr), 
+ *  nonzero if there was a problem
+ */
 int eeprom_get_byte(unsigned int uiAddress, unsigned char *byte) {
     /* Wait for completion of previous write */
     while(EECR & (1<<EEWE));
@@ -28,7 +48,12 @@
     return 0;
 }
 
-
+/** @brief get stored robot ID
+ *
+ *  checks that EEPROM has been programed with an ID and returns it
+ *
+ *  @return the robot id, if it is stored. If it returns 0xFF it is probably invalid
+ */
 unsigned char get_robotid(void) {
     unsigned char c0, c1, c2;
     
@@ -41,6 +66,12 @@
         return 0xFF;
 }
 
+/** @brief get stored robot ID
+ *
+ * checks that EEPROM has been programed with an BOM type and returns it
+ *
+ *  @return the robot bom type as defined in bom.h, if it is stored. If it returns 0xFF it is probably invalid
+ */
 unsigned char get_bom_type(void) {
     unsigned char c0, c1, c2, c3;
     
Index: trunk/code/projects/libdragonfly/spi.c
===================================================================
--- trunk/code/projects/libdragonfly/spi.c	(revision 1460)
+++ trunk/code/projects/libdragonfly/spi.c	(revision 1461)
@@ -8,6 +8,7 @@
 #include <avr/interrupt.h>
 #include "spi.h"
 
+unsigned char spi_initd=0;
 
 static volatile char spi_bytes; /* number of bytes to read */
 static spi_fun_recv_t spi_recv_func; /* byte handler */
@@ -18,9 +19,15 @@
 * 
 * @param recv_func The function to be called for each byte of data received.
 * @param recv_complete_func  The function to be called at the end of a complete transmission.
+*
+* @return 0 if init succesfull, an error code otherwise
 */
-void spi_init (spi_fun_recv_t recv_func, spi_fun_recv_complete_t recv_complete_func)
+int spi_init (spi_fun_recv_t recv_func, spi_fun_recv_complete_t recv_complete_func)
 {
+    if(spi_initd) {
+      return ERROR_INIT_ALREADY_INITD;
+    }
+
     /*  Enable Interrupt, Enable SPI Module, MSB First, Master Mode, Clock div = 64 */
     SPCR = _BV(SPE) | _BV(SPIE) /*| _BV(DORD)*/ | _BV(MSTR) | _BV(SPR1) | _BV(SPR0);
     SPSR = _BV(SPI2X); 
@@ -37,6 +44,9 @@
     spi_recv_complete_func = recv_complete_func;
     spi_bytes = 0;
     //usb_puts("\tspi.c Debug: SPI INITIALIZED\n");
+
+    spi_initd=1;
+    return 0;
 }
 
 /** 
@@ -44,11 +54,16 @@
 * 
 * @param bytes The number of bytes to be transferred.
 **/
-void spi_transfer(char bytes)
+int spi_transfer(char bytes)
 {
+    if(!spi_initd)
+      return ERROR_LIBRARY_NOT_INITD;
+
     spi_bytes = bytes;
     PORTB &= ~SS; /* Set SS low to initiate transmission */
     SPDR = 0xff; /* Initiate data transmision */
+
+    return 0;
 }
 
 ISR(SIG_SPI) 
Index: trunk/code/projects/libdragonfly/eeprom.h
===================================================================
--- trunk/code/projects/libdragonfly/eeprom.h	(revision 1460)
+++ trunk/code/projects/libdragonfly/eeprom.h	(revision 1461)
@@ -1,12 +1,3 @@
-/**
- * @file eeprom.h
- * @brief handles eeprom storage for persistent data
- *
- * Contains functions and definitions for reading and writing to eeprom
- *
- * @author Colony Project, Brad Neuman
- */
- 
  #ifndef _EEPROM_H_
  #define _EEPROM_H_
  
@@ -13,35 +4,12 @@
  #define EEPROM_ROBOT_ID_ADDR 0x10
  #define EEPROM_BOM_TYPE_ADDR 0x14
  
- /** @brief store a byte to eeproem
-  *  @return 0 if success, nonzero on failure
-  */
  int eeprom_put_byte(unsigned int addr, unsigned char byte);
  
- /** @brief reads a byte from eeprom
-  *
-  *  Pass it thge address and a pointer to a byte where the byte at the
-  *  address will be stored
-  *
-  *  @return 0 if successful (byte is set to the eeprom value at addr), 
-  *  nonzero if there was a problem
-   */
  int eeprom_get_byte(unsigned int addr, unsigned char *byte);
  
- /** @brief get stored robot ID
-  *
-  *  checks that EEPROM has been programed with an ID and returns it
-  *
-  *  @return the robot id, if it is stored. If it returns 0xFF it is probably invalid
-  */
  unsigned char get_robotid(void);
   
-   /** @brief get stored robot ID
-  *
-  * checks that EEPROM has been programed with an BOM type and returns it
-  *
-  *  @return the robot bom type as defined in bom.h, if it is stored. If it returns 0xFF it is probably invalid
-  */
  unsigned char get_bom_type(void);
  
  #endif
Index: trunk/code/projects/libdragonfly/time.c
===================================================================
--- trunk/code/projects/libdragonfly/time.c	(revision 1460)
+++ trunk/code/projects/libdragonfly/time.c	(revision 1461)
@@ -1,66 +1,66 @@
-/**
- * Copyright (c) 2007 Colony Project
- * 
- * Permission is hereby granted, free of charge, to any person
- * obtaining a copy of this software and associated documentation
- * files (the "Software"), to deal in the Software without
- * restriction, including without limitation the rights to use,
- * copy, modify, merge, publish, distribute, sublicense, and/or sell
- * copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following
- * conditions:
- * 
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- * 
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
- * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
- * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
- * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- **/
-
-
-/**
- * @file time.c
- * @brief Timer code
- *
- * Implementation of functions for timers.
- *
- * @author Colony Project, CMU Robotics Club
- **/
-
-/*
-  time.c
-  anything that requires a delay
-  mostly delay_ms
-
-  author: Robotics Club, Colony Project
-
-  Change Log:
-  2.5.07 - Kevin
-  Aaron fixed the orb/servo code and made them use timer3 but compare registers B and C. He hard set the prescaler
-  to 8 so the RTC broke. Changed it so that we use a 8 prescaler which sets the compare match at 1/16th of a second.
-  You now count how many 16ths of a second you want until you trigger your actual interrupt. Works. Changed defines
-  for time so you can still call rtc_init with a scale but now it is defined in terms of actual time like second, quarter_second
-  etc. Read that section in the time.h file for more information. Tested and works, though the clock drifts more than
-  it used to
-  1.30.07 - Kevin
-  Modified the clock to run on timer3 on the Dragonfly. Works with decent accuracy. Using a prescaler of 256
-  the timer counts up to a precomputer value which will trigger an interrupt and reset the timer. Multiples of
-  256 change it by that multiple. Refer to the time.h file for all possible prescalers.
-  The interrupt will call a specified function _rtc_func every pulse.
-  All of it has been tested and it works.
-
-*/
-#include <avr/interrupt.h>
-#include <util/delay.h>
-#include "time.h"
-
+/**
+ * Copyright (c) 2007 Colony Project
+ * 
+ * Permission is hereby granted, free of charge, to any person
+ * obtaining a copy of this software and associated documentation
+ * files (the "Software"), to deal in the Software without
+ * restriction, including without limitation the rights to use,
+ * copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following
+ * conditions:
+ * 
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ * 
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
+ * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
+ * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
+ * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
+ * OTHER DEALINGS IN THE SOFTWARE.
+ **/
 
+
+/**
+ * @file time.c
+ * @brief Timer code
+ *
+ * Implementation of functions for timers.
+ *
+ * @author Colony Project, CMU Robotics Club
+ **/
+
+/*
+  time.c
+  anything that requires a delay
+  mostly delay_ms
+
+  author: Robotics Club, Colony Project
+
+  Change Log:
+  2.5.07 - Kevin
+  Aaron fixed the orb/servo code and made them use timer3 but compare registers B and C. He hard set the prescaler
+  to 8 so the RTC broke. Changed it so that we use a 8 prescaler which sets the compare match at 1/16th of a second.
+  You now count how many 16ths of a second you want until you trigger your actual interrupt. Works. Changed defines
+  for time so you can still call rtc_init with a scale but now it is defined in terms of actual time like second, quarter_second
+  etc. Read that section in the time.h file for more information. Tested and works, though the clock drifts more than
+  it used to
+  1.30.07 - Kevin
+  Modified the clock to run on timer3 on the Dragonfly. Works with decent accuracy. Using a prescaler of 256
+  the timer counts up to a precomputer value which will trigger an interrupt and reset the timer. Multiples of
+  256 change it by that multiple. Refer to the time.h file for all possible prescalers.
+  The interrupt will call a specified function _rtc_func every pulse.
+  All of it has been tested and it works.
+
+*/
+#include <avr/interrupt.h>
+#include <util/delay.h>
+#include "time.h"
+
+
 /* Calculate how many cycles to delay for to get 1 ms. Based on F_CPU which should be defined by the makefile */
 #ifdef F_CPU
 #define WAIT_CYCLES ((F_CPU / 1000) / 10)
@@ -67,25 +67,28 @@
 #else
 #define WAIT_CYCLES (8000 / 10)
 #endif
-
-static volatile int _rtc_val = 0;
-static volatile int _rtc_pulse = 0;
-static volatile int _rtc_scale = 32;	//Defaults to 1 Second per pulse
-static void (*_rtc_f)(void) = 0;
 
 
-
-/**
- * @defgroup time Time
- * @brief Time functions
- * 
- * Functions dealing with time.
- * 
- * @{
- **/
-
-/**
- * Delays for the specified number of milliseconds.
+unsigned char time_initd = 0;
+
+static volatile int _rtc_val = 0;
+static volatile int _rtc_pulse = 0;
+static volatile int _rtc_scale = 32;	//Defaults to 1 Second per pulse
+static void (*_rtc_f)(void) = 0;
+
+
+
+/**
+ * @defgroup time Time
+ * @brief Time functions
+ * 
+ * Functions dealing with time.
+ * 
+ * @{
+ **/
+
+/**
+ * Delays for the specified number of milliseconds.
  * It depends on F_CPU to be defined in order to calculate how many cycles
  * it should delay. If it is not defined, a default clock of 8MHz is assumed.
  * 
@@ -92,15 +95,15 @@
  * We use _delay_loop_2 which will run assembly instructions that should be
  * 4 cycles long. Optimizations must be enabled for this to be true.
  * That function is called to ensure around 1ms per execution. To generate
- * multiple ms we run a for loop of how many milliseconds are desired.
+ * multiple ms we run a for loop of how many milliseconds are desired.
  *
  * The error should be just the skew on the oscillator as the formula to 
  * calculate delay cycles should always be a whole number. The is some skew
  * in practice though it is unavoidable. Delaying for less than 1s should make
  * the error negligable.
- *
- * @param ms the number of milliseconds to delay for
- **/
+ *
+ * @param ms the number of milliseconds to delay for
+ **/
 void delay_ms(int ms) {
     for (; ms > 0; ms--) {
         _delay_loop_2(WAIT_CYCLES);
@@ -107,95 +110,105 @@
     }
 }
 
-
-/* 	Prescales defined in time.h. SECOND will give you 1 second.
-	More scales are defined in the time.h file.
-	rtc_func is the address to a function that you want called every clock tick. */
-/**
- * Initializes the real time clock. Prescales are defined in time.h.
- * For example, SECOND will give 1 second. The specified function is
- * called every clock tick. For the real time clock to activate,
- * interrupts must be enabled. (through sei() )
- *
- * @param prescale_opt the period with which the timer is triggered
- * @param rtc_func the function called when the timer is triggered
- *
- * @see rtc_get, rtc_reset
- *
- **/
-void rtc_init(int prescale_opt, void (*rtc_func)(void)) {
-	
-  //Clear timer register for Timer 3
-  TCNT3 = 0;
-	
-  /* 	This sets the Waveform Generation Module to CTC (Clear Timer on Compare) Mode (100)
-	See page135 in Atmega128 Docs for more modes and explanations */
-  TCCR3B |= _BV(WGM32);
-	
-  /* 	This sets the prescaler for the system clock (8MHz) ie: divides the clock by some number.
-	Currently set to a prescaler of 8 because that is what the orb and servos use (they are on this timer as well)
-	See page137 in Atemga128 Docs for all the available prescalers */
-  TCCR3B |= _BV(CS31);
-	
-  /* 	Sets the two regsiters that we compare against. So the timer counts up to this number and
-	then resets back to 0 and calls the compare match interrupt.
-	8x10^6 / 8 = 1/16 Second. All values are based off of this number. Do not change it unless you
-	are l337*/
-		
-  OCR3A = 0xF424;	
-
-  /* 	Enable Output Compare A Interrupt. When OCR3A is met by the timer TCNT3 this interrupt will be
-	triggerd. (See page140 in Atmega128 Docs for more information */
-  ETIMSK |= _BV(OCIE3A);
-	
-  /*	Store the pointer to the function to be used in the interrupt */
-  _rtc_f = rtc_func;
-	
-  /*	Store how many 1/16ths of a second you want to let by before triggering an interrupt */
-  _rtc_scale = prescale_opt;
-}
-
-/**
- * Returns the time elapsed in seconds since the last call to
- * rtc_init or rtc_reset.
- *
- * @return the number of seconds since the last call to rtc_init or rtc_reset
- *
- * @see rtc_init, rtc_reset
- **/
-int rtc_get(void) {
-  return _rtc_val;
-}
-
-/**
- * Resets the real time clock counter to 0.
- *
- * @see rtc_init, rtc_get
- **/
-void rtc_reset(void) {
-  _rtc_val = 0;
-}
-
-/** @} **/ //end defgroup
-
-/*	Called every pulse. Function in _rtc_f is called every _rtc_scale and also the counter is updated.
-	Bascially, since the pulse is hard set at 1/16s  you want to count how many 16ths of a second have passed
-	and when it reaches the amount of time you want, execute the code. */
-SIGNAL(TIMER3_COMPA_vect) {
-
-  if (_rtc_pulse ==  _rtc_scale) {
-    //Increment the real time clock counter
-    _rtc_val++;
-		
-    //Calls the function tied to the real time clock if defined
-    if(_rtc_f != 0)
-      _rtc_f();
-		
-    //Resets the pulse until the next scale is matched
-    _rtc_pulse = 0;
-  }	
-	
-  //Updates the amount of pulses seen since the last scale match
-  _rtc_pulse++;
-	
-}
+
+/* 	Prescales defined in time.h. SECOND will give you 1 second.
+	More scales are defined in the time.h file.
+	rtc_func is the address to a function that you want called every clock tick. */
+/**
+ * Initializes the real time clock. Prescales are defined in time.h.
+ * For example, SECOND will give 1 second. The specified function is
+ * called every clock tick. For the real time clock to activate,
+ * interrupts must be enabled. (through sei() )
+ *
+ * @param prescale_opt the period with which the timer is triggered
+ * @param rtc_func the function called when the timer is triggered
+ *
+ * @return 0 if init succesfull, an error code otherwise
+ *
+ * @see rtc_get, rtc_reset
+ *
+ **/
+int rtc_init(int prescale_opt, void (*rtc_func)(void)) {
+
+  if(time_initd) {
+    return ERROR_INIT_ALREADY_INITD;
+  }
+	
+  //Clear timer register for Timer 3
+  TCNT3 = 0;
+	
+  /* 	This sets the Waveform Generation Module to CTC (Clear Timer on Compare) Mode (100)
+	See page135 in Atmega128 Docs for more modes and explanations */
+  TCCR3B |= _BV(WGM32);
+	
+  /* 	This sets the prescaler for the system clock (8MHz) ie: divides the clock by some number.
+	Currently set to a prescaler of 8 because that is what the orb and servos use (they are on this timer as well)
+	See page137 in Atemga128 Docs for all the available prescalers */
+  TCCR3B |= _BV(CS31);
+	
+  /* 	Sets the two regsiters that we compare against. So the timer counts up to this number and
+	then resets back to 0 and calls the compare match interrupt.
+	8x10^6 / 8 = 1/16 Second. All values are based off of this number. Do not change it unless you
+	are l337*/
+		
+  OCR3A = 0xF424;	
+
+  /* 	Enable Output Compare A Interrupt. When OCR3A is met by the timer TCNT3 this interrupt will be
+	triggerd. (See page140 in Atmega128 Docs for more information */
+  ETIMSK |= _BV(OCIE3A);
+	
+  /*	Store the pointer to the function to be used in the interrupt */
+  _rtc_f = rtc_func;
+	
+  /*	Store how many 1/16ths of a second you want to let by before triggering an interrupt */
+  _rtc_scale = prescale_opt;
+
+  time_initd = 1;
+
+  return 0;
+}
+
+/**
+ * Returns the time elapsed in seconds since the last call to
+ * rtc_init or rtc_reset.
+ *
+ * @return the number of seconds since the last call to rtc_init or rtc_reset
+ *
+ * @see rtc_init, rtc_reset
+ **/
+int rtc_get(void) {
+  return _rtc_val;
+}
+
+/**
+ * Resets the real time clock counter to 0.
+ *
+ * @see rtc_init, rtc_get
+ **/
+void rtc_reset(void) {
+  _rtc_val = 0;
+}
+
+/** @} **/ //end defgroup
+
+/*	Called every pulse. Function in _rtc_f is called every _rtc_scale and also the counter is updated.
+	Bascially, since the pulse is hard set at 1/16s  you want to count how many 16ths of a second have passed
+	and when it reaches the amount of time you want, execute the code. */
+SIGNAL(TIMER3_COMPA_vect) {
+
+  if (_rtc_pulse ==  _rtc_scale) {
+    //Increment the real time clock counter
+    _rtc_val++;
+		
+    //Calls the function tied to the real time clock if defined
+    if(_rtc_f != 0)
+      _rtc_f();
+		
+    //Resets the pulse until the next scale is matched
+    _rtc_pulse = 0;
+  }	
+	
+  //Updates the amount of pulses seen since the last scale match
+  _rtc_pulse++;
+	
+}
Index: trunk/code/projects/libdragonfly/spi.h
===================================================================
--- trunk/code/projects/libdragonfly/spi.h	(revision 1460)
+++ trunk/code/projects/libdragonfly/spi.h	(revision 1461)
@@ -12,6 +12,8 @@
 #ifndef __SPI_H__
 #define __SPI_H__
 
+#include<dragonfly_lib.h>
+
 #define DOUBLE_SCK 1
 #define SPR0_BIT 1
 
@@ -32,7 +34,7 @@
 * @param spi_fun_recv_t The function that handles SPI data, byte for byte.
 * @param spi_fun_recv_complete_t  Called on a completed transmission - typically for cleaning up.
 */
-void spi_init (spi_fun_recv_t, spi_fun_recv_complete_t);
+int spi_init (spi_fun_recv_t, spi_fun_recv_complete_t);
 
 /** 
 * @brief Initialize SPI transfer.
@@ -39,7 +41,7 @@
 * 
 * @param char The number of bytes to transfer.
 */
-void spi_transfer (char);
+int spi_transfer (char);
 
 /**@}**/ //end group
 
Index: trunk/code/projects/libdragonfly/analog.c
===================================================================
--- trunk/code/projects/libdragonfly/analog.c	(revision 1460)
+++ trunk/code/projects/libdragonfly/analog.c	(revision 1461)
@@ -49,6 +49,8 @@
  * @{
  **/
 
+unsigned char analog_initd=0;
+
 volatile int adc_loop_status = ADC_LOOP_STOPPED;
 volatile int adc_sig_stop_loop = 0;
 volatile int adc_current_port = 0;
@@ -58,6 +60,8 @@
  * Initializes the ADC.
  * Call analog_init before reading from the analog ports.
  *
+ * @return returns 0 on success, nonzero on error
+ *
  * @see analog8, analog10, analog_get8, analog_get10
  *
  * @bug First conversion takes a performance penalty of
@@ -73,43 +77,49 @@
  * determine highest clock speed for accurate 8-bit ADC.
  *
  **/
-void analog_init(int start_conversion) {
-	for (int i = 0; i < 11; i++) {
-		an_val[i].adc10 = 0;
-		an_val[i].adc8 = 0;
-	}
+int analog_init(int start_conversion) {
+  if(analog_initd)
+    return ERROR_INIT_ALREADY_INITD;
 
-	// ADMUX register
-	// Bit 7,6 - Set voltage reference to AVcc (0b01)
-	// Bit 5 - ADLAR set to simplify moving from register
-	// Bit 4 - X
-	// Bit 3:0 - Sets the current channel
-	// Initializes to read from AN1 first (AN0 is reservered for the BOM)
-	ADMUX = 0;
-	ADMUX |= ADMUX_OPT | _BV(MUX0);
+  for (int i = 0; i < 11; i++) {
+    an_val[i].adc10 = 0;
+    an_val[i].adc8 = 0;
+  }
 
-	// ADC Status Register A
-	// Bit 7 - ADEN is set (enables analog)
-	// Bit 6 - Start conversion bit is set (must be done once for free-running mode)
-	// Bit 5 - Enable Auto Trigger (for free running mode) NOT DOING THIS RIGHT NOW
-	// Bit 4 - ADC interrupt flag, 0
-	// Bit 3 - Enable ADC Interrupt (required to run free-running mode)
-	// Bits 2-0 - Set to create a clock divisor of 128, to make ADC clock = 8,000,000/64 = 125kHz
-	ADCSRA = 0;
-	ADCSRA |= _BV(ADEN) | _BV(ADPS2) | _BV(ADPS1) | _BV(ADPS0);
+  // ADMUX register
+  // Bit 7,6 - Set voltage reference to AVcc (0b01)
+  // Bit 5 - ADLAR set to simplify moving from register
+  // Bit 4 - X
+  // Bit 3:0 - Sets the current channel
+  // Initializes to read from AN1 first (AN0 is reservered for the BOM)
+  ADMUX = 0;
+  ADMUX |= ADMUX_OPT | _BV(MUX0);
+
+  // ADC Status Register A
+  // Bit 7 - ADEN is set (enables analog)
+  // Bit 6 - Start conversion bit is set (must be done once for free-running mode)
+  // Bit 5 - Enable Auto Trigger (for free running mode) NOT DOING THIS RIGHT NOW
+  // Bit 4 - ADC interrupt flag, 0
+  // Bit 3 - Enable ADC Interrupt (required to run free-running mode)
+  // Bits 2-0 - Set to create a clock divisor of 128, to make ADC clock = 8,000,000/64 = 125kHz
+  ADCSRA = 0;
+  ADCSRA |= _BV(ADEN) | _BV(ADPS2) | _BV(ADPS1) | _BV(ADPS0);
 	
-	// Set external mux lines to outputs
-	DDRG |= 0x1C;
+  // Set external mux lines to outputs
+  DDRG |= 0x1C;
 	
-	// Set up first port for conversions
-	set_adc_mux(0x00);
-	adc_current_port = AN1;
+  // Set up first port for conversions
+  set_adc_mux(0x00);
+  adc_current_port = AN1;
 
-	//Start the conversion loop if requested
-	if (start_conversion)
-		analog_start_loop();
+  //Start the conversion loop if requested
+  if (start_conversion)
+    analog_start_loop();
 		
-	//Conversion loop disabled by default
+  //Conversion loop disabled by default
+
+  analog_initd=1;
+  return 0;
 }	
 
 /**
@@ -170,15 +180,22 @@
  * Starts the analog update loop. Will continue to run
  * until analog_stop_loop is called.
  *
+ * @return returns 0 on success, nonzero on error
+ *
  * @see analog_stop_loop, analog_loop_status
  **/
-void analog_start_loop(void) {
-	if(adc_loop_status != ADC_LOOP_RUNNING){
-		//Start the conversion, enable ADC interrupt
-		ADCSRA |= _BV(ADIE);
-		ADCSRA |= _BV(ADSC);
-		adc_loop_status = ADC_LOOP_RUNNING;
-	}
+int analog_start_loop(void) {
+  if(!analog_initd)
+    return ERROR_LIBRARY_NOT_INITD;
+
+  if(adc_loop_status != ADC_LOOP_RUNNING){
+    //Start the conversion, enable ADC interrupt
+    ADCSRA |= _BV(ADIE);
+    ADCSRA |= _BV(ADSC);
+    adc_loop_status = ADC_LOOP_RUNNING;
+  }
+
+  return 0;
 }
 
 /**
@@ -187,11 +204,18 @@
  * is interrupted. No further updates will be made until
  * the loop is started again.
  *
+ * @return returns 0 on success, nonzero on error
+ *
  * @see analog_start_loop, analog_loop_status
  **/
-void analog_stop_loop() {
-	//Signal to stop after the next conversion
-	adc_sig_stop_loop = 1;
+int analog_stop_loop() {
+  if(!analog_initd)
+    return ERROR_LIBRARY_NOT_INITD;
+
+  //Signal to stop after the next conversion
+  adc_sig_stop_loop = 1;
+
+  return 0;
 }
 
 /**
Index: trunk/code/projects/libdragonfly/encoders.c
===================================================================
--- trunk/code/projects/libdragonfly/encoders.c	(revision 1460)
+++ trunk/code/projects/libdragonfly/encoders.c	(revision 1461)
@@ -3,6 +3,8 @@
 #include "ring_buffer.h"
 #include <avr/io.h>
 
+unsigned char encoders_initd=0;
+
 unsigned int left_data_buf;
 unsigned int right_data_buf;
 char encoder_buf_index;
@@ -21,7 +23,7 @@
 
 volatile short int data_ready;
 
-void encoder_recv(char data);
+int encoder_recv(char data);
 
 //Helper Function Prototypes
 inline void left_data_array_put(unsigned short int value);
@@ -49,28 +51,37 @@
 /** 
 * @brief Initializes encoder variables and the hardware interface.
 */
-void encoders_init(void){
-	int i;
+int encoders_init(void){
+  int i;
 	
-	data_ready=0;
+  if(encoders_initd)
+    return ERROR_INIT_ALREADY_INITD;
 
-	spi_init(encoder_recv, encoder_recv_complete);
-	encoder_buf_index = 0;
-	left_data_buf = 0;
-	right_data_buf= 0;
-	left_data = -1;
-	right_data = -1;
-	
-	//RING_BUFFER_INIT(enc_buffer,BUFFER_SIZE);
-	left_data_idx = 0;
-	right_data_idx = 0;
-	for(i = 0; i < BUFFER_SIZE; i++) {
-		left_data_array[i] = 0;
-	}
-	for(i = 0; i < BUFFER_SIZE; i++) {
-		right_data_array[i] = 0;
-	}
-	spi_transfer(5);
+  data_ready=0;
+
+  if(spi_init(encoder_recv, encoder_recv_complete))
+    return -1; //if spi was inited for something else, bail out
+  encoder_buf_index = 0;
+  left_data_buf = 0;
+  right_data_buf= 0;
+  left_data = -1;
+  right_data = -1;
+
+  //RING_BUFFER_INIT(enc_buffer,BUFFER_SIZE);
+  left_data_idx = 0;
+  right_data_idx = 0;
+
+  for(i = 0; i < BUFFER_SIZE; i++) {
+    left_data_array[i] = 0;
+  }
+  for(i = 0; i < BUFFER_SIZE; i++) {
+    right_data_array[i] = 0;
+  }
+
+  spi_transfer(5);
+
+  encoders_initd=1;
+  return 0;
 }
 
 /**
@@ -81,14 +92,23 @@
  *
  * @return the value of the specified encoder.
  *         -1 usually means low battery.
+ *         -2 means the library was not properly initialized
  *         values above ENCODER_MAX usually means phyiscal problems with
  *         the encoder.
  **/
 int encoder_read(char encoder){
-	
-	if(encoder==LEFT) return left_data;
-	else if(encoder==RIGHT) return right_data;
-	else return -1;
+  if(!encoders_initd)
+    return -2;
+
+  if(encoder==LEFT) {
+    return left_data;
+  }
+  else if(encoder==RIGHT){
+    return right_data;
+  }
+  else{
+    return -1;
+  }
 }
 
 /**
@@ -109,13 +129,18 @@
  *
  * @param encoder the encoder that you want to read, use LEFT or RIGHT
  *
- * @return The distance covered by the specified encoder.
+ * @return The distance covered by the specified encoder, -2 if the library is not initialized
  **/
 int encoder_get_dx(char encoder) {
-	
-	if(encoder==LEFT) return left_dx;
-	else if(encoder==RIGHT) return right_dx;
-	else return -1;
+  if(!encoders_initd)
+    return -2;
+
+  if(encoder==LEFT)
+    return left_dx;
+  else if(encoder==RIGHT)
+    return right_dx;
+  else
+    return -1;
 }
 
 /** 
@@ -132,6 +157,7 @@
  */
 int encoder_get_v(char encoder){
     int vel1, vel2;
+
     vel1 = get_dx(encoder, 0);
     vel2 = get_dx(encoder, 1);
 
@@ -151,10 +177,17 @@
  *
  * @param encoder the encoder that you want to reset distance for
  **/
-void encoder_rst_dx(char encoder) {
-	
-	if(encoder==LEFT) left_dx = 0;
-	else if(encoder==RIGHT) right_dx = 0;
+int encoder_rst_dx(char encoder) {
+
+  if(!encoders_initd)
+    return ERROR_LIBRARY_NOT_INITD;
+
+  if(encoder==LEFT)
+    left_dx = 0;
+  else if(encoder==RIGHT)
+    right_dx = 0;
+
+  return 0;
 }
 
 /** 
@@ -168,9 +201,15 @@
 
 /** 
 * @brief Resets the encoder read counter.
+* @return 0 if init succesfull, an error code otherwise
 */
-void encoder_rst_tc(void) {
-	timecount = 0;
+int encoder_rst_tc(void) {
+  if(!encoders_initd)
+    return ERROR_LIBRARY_NOT_INITD;
+
+  timecount = 0;
+
+  return 0;
 }
 
 /** 
@@ -178,94 +217,110 @@
 * Counter is reset on functions exit.
 * 
 * @param n 
+*
+* @return 0 if init succesfull, an error code otherwise
 */
-void encoder_wait(int n){
-	while(data_ready<n);
-	data_ready=0;
+int encoder_wait(int n){
+  if(!encoders_initd)
+    return ERROR_LIBRARY_NOT_INITD;
+
+  while(data_ready<n);
+  data_ready=0;
+
+  return 0;
 }
 
+/**
+ * @brief This functions recieves data from the encoders directly
+ *
+ * @note Full reads occur every 40 microseconds. This function should be called every 8 microseconds.
+ *
+ * @return 0 if init succesfull, an error code otherwise
+ */
+int encoder_recv(char data){
+  short int dx;
 
-//Full reads occur every 40 microseconds. This function should be called
-//every 8 microseconds.
-void encoder_recv(char data){
-	short int dx;
-	
-	//Parse the encoder data, comes in over 5 bytes 16 bits per encoder,
-	// second is offset by 1 bit.
-	switch(encoder_buf_index){	
-	case 0: 
-		right_data_buf |= ((short)data)<<8 & 0xff00;
-		break;
-	case 1:
-		right_data_buf |= ((short)data) & 0xff;
-		break;
-	case 2:
-		left_data_buf |= (((short)data) << 9) & (0x7F << 9);
-		break;
-	case 3:
-		left_data_buf |= (((short)data) << 1) & (0xFF<<1);
-		break;
-	case 4: left_data_buf |= (((short)data)>>7) & 0x1;
-	}	
+  if(!encoders_initd)
+    return ERROR_LIBRARY_NOT_INITD;
+
+  //Parse the encoder data, comes in over 5 bytes 16 bits per encoder,
+  // second is offset by 1 bit.
+  switch(encoder_buf_index){	
+  case 0: 
+    right_data_buf |= ((short)data)<<8 & 0xff00;
+    break;
+  case 1:
+    right_data_buf |= ((short)data) & 0xff;
+    break;
+  case 2:
+    left_data_buf |= (((short)data) << 9) & (0x7F << 9);
+    break;
+  case 3:
+    left_data_buf |= (((short)data) << 1) & (0xFF<<1);
+    break;
+  case 4: left_data_buf |= (((short)data)>>7) & 0x1;
+  }	
 		
-	encoder_buf_index = (encoder_buf_index + 1) % 5;
+  encoder_buf_index = (encoder_buf_index + 1) % 5;
 
-	if(encoder_buf_index==0) {
+  if(encoder_buf_index==0) {
 		
-		/*Error handling for the left encoder*/ 
-		if(!(left_data_buf & OCF)) 
-			left_data = ENCODER_DATA_NOT_READY; 
-		if(left_data_buf & (COF | LIN))  
-			left_data = ENCODER_MISALIGNED;
-		else if((left_data_buf & MagINCn) && (left_data_buf & MagDECn)) 
-			left_data = ENCODER_MAGNET_FAILURE;
-		else left_data = (left_data_buf>>5) & 1023;
+    /*Error handling for the left encoder*/ 
+    if(!(left_data_buf & OCF)) 
+      left_data = ENCODER_DATA_NOT_READY; 
+    if(left_data_buf & (COF | LIN))  
+      left_data = ENCODER_MISALIGNED;
+    else if((left_data_buf & MagINCn) && (left_data_buf & MagDECn)) 
+      left_data = ENCODER_MAGNET_FAILURE;
+    else left_data = (left_data_buf>>5) & 1023;
 			
-		/*Error handling for the right encoder*/ 
-	 	if(!(right_data_buf & OCF))
-			right_data = ENCODER_DATA_NOT_READY;	
-		if(right_data_buf & (COF | LIN)) 
-			right_data = ENCODER_MISALIGNED;
-		else if ((right_data_buf & MagINCn)  && (right_data_buf & MagDECn)) 
-			right_data = ENCODER_MAGNET_FAILURE;
-		else right_data = (right_data_buf>>5) & 1023;
+    /*Error handling for the right encoder*/ 
+    if(!(right_data_buf & OCF))
+      right_data = ENCODER_DATA_NOT_READY;	
+    if(right_data_buf & (COF | LIN)) 
+      right_data = ENCODER_MISALIGNED;
+    else if ((right_data_buf & MagINCn)  && (right_data_buf & MagDECn)) 
+      right_data = ENCODER_MAGNET_FAILURE;
+    else right_data = (right_data_buf>>5) & 1023;
 			
-  		left_data_buf = 0;
-		right_data_buf = 0;
+    left_data_buf = 0;
+    right_data_buf = 0;
 
-		/*Note: Above 1023 is invalid data*/	
-		if(!(left_data > 1023)) {
-			//Reverse the left wheel since encoders are necessarily mounted backwards.
-			left_data = 1023 - left_data;
-			left_data_array_put(left_data);
+    /*Note: Above 1023 is invalid data*/	
+    if(!(left_data > 1023)) {
+      //Reverse the left wheel since encoders are necessarily mounted backwards.
+      left_data = 1023 - left_data;
+      left_data_array_put(left_data);
 
-			//Adjust left accumulator
-			dx = left_data - left_data_array_prev();
+      //Adjust left accumulator
+      dx = left_data - left_data_array_prev();
 			
-			if(left_data_array_prev()==0)  dx=0;
+      if(left_data_array_prev()==0)  dx=0;
 
-			if(dx > 512) left_dx += dx - 1023; //Underflow
-			else if(dx < -512) left_dx += dx + 1023; //Overflow
-			else left_dx += dx;
-		}
+      if(dx > 512) left_dx += dx - 1023; //Underflow
+      else if(dx < -512) left_dx += dx + 1023; //Overflow
+      else left_dx += dx;
+    }
 
-		/*Above 1023 is invalid data*/	
-		if(!(right_data > 1023)) {
-			right_data_array_put(right_data);
+    /*Above 1023 is invalid data*/	
+    if(!(right_data > 1023)) {
+      right_data_array_put(right_data);
 
-			//Adjust right accumulator
-			dx = right_data - right_data_array_prev();
+      //Adjust right accumulator
+      dx = right_data - right_data_array_prev();
 
-			if(right_data_array_prev()==0) dx=0;
+      if(right_data_array_prev()==0) dx=0;
 			  
-			if(dx > 512) right_dx += dx - 1023; //underflow
-			else if(dx < -512) right_dx += dx + 1023; //overflow 
-			else right_dx += dx;
-		}
-	}
+      if(dx > 512) right_dx += dx - 1023; //underflow
+      else if(dx < -512) right_dx += dx + 1023; //overflow 
+      else right_dx += dx;
+    }
+  }
 
-	//Increment timecount accumulator
-	timecount++;
+  //Increment timecount accumulator
+  timecount++;
+
+  return 0;
 }
 
 
Index: trunk/code/projects/libdragonfly/time.h
===================================================================
--- trunk/code/projects/libdragonfly/time.h	(revision 1460)
+++ trunk/code/projects/libdragonfly/time.h	(revision 1461)
@@ -37,6 +37,8 @@
 #ifndef _TIME_H_
 #define _TIME_H_
 
+#include <dragonfly_lib.h>
+
 /*	Predefined times for prescale_opt in time.c.
 	To make you own, know that a pulse is 1/16th of a second. You cannot get less than this. To get more, you need
 	to know how many 16ths of a second are in the time you want. (Time_desired * 16 = prescaler_opt)
@@ -63,7 +65,7 @@
 /** @brief Delay execution for the specified time **/
 void delay_ms(int ms) ;
 /** @brief Enable the realtime clock **/
-void rtc_init(int prescale_opt, void (*rtc_func)(void));
+int rtc_init(int prescale_opt, void (*rtc_func)(void));
 /** @brief Reset the counter of the realtime clock **/
 void rtc_reset(void);
 /** @brief Get the value of the realtime clock. **/
Index: trunk/code/projects/libdragonfly/analog.h
===================================================================
--- trunk/code/projects/libdragonfly/analog.h	(revision 1460)
+++ trunk/code/projects/libdragonfly/analog.h	(revision 1461)
@@ -113,11 +113,11 @@
 
 /** @brief Initialize analog ports. Will start running a loop
     if start_conversion is ADC_START.**/
-void analog_init(int start_conversion);
+int analog_init(int start_conversion);
 /** @brief starts the analog loop. Doesn't do anything if the loop is already running. **/
-void analog_start_loop(void);
+int analog_start_loop(void);
 /** @brief Stops the analog loop. Doesn't do anything if the loop is already stopped. **/
-void analog_stop_loop(void);
+int analog_stop_loop(void);
 /** @brief Returns the status of the analog loop. **/
 int analog_loop_status(void);
 /** @brief Returns an 8-bit analog value from the look up table. Use this instead of analog_get8. **/
Index: trunk/code/projects/libdragonfly/encoders.h
===================================================================
--- trunk/code/projects/libdragonfly/encoders.h	(revision 1460)
+++ trunk/code/projects/libdragonfly/encoders.h	(revision 1461)
@@ -51,6 +51,10 @@
 #define MagINCn _BV(1)
 #define MagDECn _BV(0)
 
+#ifdef BUFFER_SIZE
+#error BUFFER_SIZE already defined!
+#endif
+
 /** @brief Buffer size **/
 #define BUFFER_SIZE 46
 
@@ -57,7 +61,7 @@
 #define ERR_VEL 1024
 
 /** @brief Initialize encoders. **/
-void encoders_init(void);
+int encoders_init(void);
 /** @brief Read instantaneous encoder value. **/
 int encoder_read(char encoder);
 
@@ -72,14 +76,14 @@
 /** @brief Get total distance traveled. **/
 int encoder_get_dx(char encoder);
 /** @brief Reset distance counter. **/
-void encoder_rst_dx(char encoder);
+int encoder_rst_dx(char encoder);
 /** @brief Get time count: The number of encoder reads that have occurred. **/
 int encoder_get_tc(void);
 /** @brief Reset the time count. **/
-void encoder_rst_tc(void);
+int encoder_rst_tc(void);
 
 /** @brief Waits for the next n encoder reading, then returns. **/
-void encoder_wait( int nReadings );
+int encoder_wait( int nReadings );
 
 /**@}**/ //end group
 
Index: trunk/code/projects/libdragonfly/bom.c
===================================================================
--- trunk/code/projects/libdragonfly/bom.c	(revision 1460)
+++ trunk/code/projects/libdragonfly/bom.c	(revision 1461)
@@ -3,242 +3,273 @@
  * 
  * Permission is hereby granted, free of charge, to any person
  * obtaining a copy of this software and associated documentation
- * files (the "Software"), to deal in the Software without
- * restriction, including without limitation the rights to use,
- * copy, modify, merge, publish, distribute, sublicense, and/or sell
- * copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following
- * conditions:
- * 
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- * 
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
- * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
- * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
- * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- **/
-
-
-/**
- * @file bom.c
- * @brief Implementation for using the BOM
- *
- * Contains functions for using the Bearing and Orientation Module (BOM)
- *
- * @author Colony Project, CMU Robotics Club
- **/
-
-#include "bom.h"
-#include "dio.h"
-#include "serial.h"
-#include "analog.h"
-
-//On the original BOM1.0, the emmitter angular order does not match the analog mux order
-//so you need to iterate through the mux index in the following order if you want to get
-//the detector readings in order:
-static const char lookup[16] = {7,6,5,0xe,1,4,3,2,0xf,0,0xd,8,0xc,0xb,9,0xa};
-
-// internal function prototypes
-static void bom_select(char which);
-
-/*
- Bk R Y (Analog)
----------
- Green
- Blue
- White
----------
- Blue
- White
-*/
-
-
-/*
-the analog pin definitions from dio.h DO NOT work here,
-so we must use PF0 from avrgcc (as opposed to _PIN_F0).
-BUT the dio pin definitions from dio.h must be used (no PE...).
-
-also, _PIN_E2 is initialized to high for some reason,
-which turns the BOM on when the robot is turned on.
-WORK-AROUND: call digital_output(_PIN_E2,0) at some point.
-
-*/
-
-#define MONKI PF0         //analog (yellow)
-//------------------------//
-#define MONKL _PIN_E2     //green
-#define MONK1 _PIN_E3     //blue
-#define MONK0 _PIN_E4     //white
-//------------------------//
-#define MONK3 _PIN_E6     //blue
-#define MONK2 _PIN_E7     //white
-
-#define BOM_VALUE_THRESHOLD 150 //200
-#define NUM_BOM_LEDS 16
-
-/*
-  *The following pin definitions are for the BOM v1.5
-  */
-
-#define BOM_MODE	_PIN_E2	//dio0
-#define BOM_STROBE	_PIN_E3	//dio1
-
-#define BOM_DATA	_PIN_A0 //servo0
-#define BOM_CLOCK	_PIN_A1	//servo1
-
-#define BOM_S0		_PIN_E5	//dio3
-#define BOM_S1		_PIN_E4	//dio2
-#define BOM_S2		_PIN_E7	//dio4
-#define BOM_S3		_PIN_E6	//dio5
-#define BOM_OUT		PF0		//analog(yellow)
-
-/**
- * @defgroup bom BOM (Bearing and Orientation Module)
- * @brief Functions for dealing with the BOM.
- *
- * The Bearing and Orientation Module / Barrel of Monkeys / BOM
- * is a custom sensor designed and built by the Colony Project.
- * It consists of a ring of 16 IR emitters and 16 IR detectors.
- * The BOM is most often use to determine the direction of other
- * robots. This module contains functions for controlling the BOM.
- *
- * Include bom.h to access these functions.
- *
- * @{
- **/
-
-static unsigned int bom_val[NUM_BOM_LEDS];
-static volatile char bom_type = BOM10;
-static int select_pins[4];
-static int analog_pin;
-
-/**
- * Initializes the BOM.
- * Call bom_init before reading bom values or turning bom leds.
- *
- * @bugs INCOMPLETE - No utilization of BOM1.5 RSSI capability. Probably leave this out
- * until Cornell and Pras return
- * 
- * @see bom_refresh, bom_leds_on, bom_leds_off
- **/
-void bom_init(char type) {
-    bom_type = type;
-    
-    switch(bom_type) {
-    case BOM10:
-		select_pins[0] = MONK0; 
-		select_pins[1] = MONK1;
-		select_pins[2] = MONK2;
-		select_pins[3] = MONK3;
-		analog_pin = MONKI;
-        break;
-    case BOM15:
-        //Sets BOM1.5 to normal [BOM] mode
-        digital_output(BOM_MODE, 0);
-		select_pins[0] = BOM_S0; 
-		select_pins[1] = BOM_S1;
-		select_pins[2] = BOM_S2;
-		select_pins[3] = BOM_S3;
-		bom_set_leds(BOM_ALL);
-		analog_pin = BOM_OUT;
-        break;
-    case RBOM:
-        break;
-    //default:
-    }
-}
-
-/**
- * Iterates through each bit in the bit_field. For each set bit, sets the corresponding bom select bits
- *    and updates the corresponding bom value with an analog_get8 reading.  analog_init and bom_init
- *    must be called for this to work. Must call this before reading BOM values!
- *
- *
- * @param bit_field specifies which elements in bom_val[] should be updated. Use BOM_ALL to refresh all values.
- *    Ex. if 0x0003 is passed, bom_val[0] and bom_val[1] will be updated.
- *
- * @see bom_get
- **/
-void bom_refresh(int bit_field) {
-    int i;
-	int loop_was_running = 0;
-    
-	//Check analog loop status
-    if(analog_loop_status() == ADC_LOOP_RUNNING) {
-		loop_was_running = 1;
-		analog_stop_loop();
-	}
-    
-	//Read BOM values
-    for(i = 0; i < NUM_BOM_LEDS; i++) {
-        if(bit_field & 0x1) {
-            bom_select(i);
-            bom_val[i] = analog_get8(analog_pin);
-        }
-        bit_field = bit_field >> 1;
-    }
-    
-	//Restore analog loop status
-	if(loop_was_running)
-		analog_start_loop();
-}
-
-/**
- * Gets the bom reading from bom_val[which].  Call bom_refresh beforehand to read new bom values.
- *
- * @pre must call bom refresh first
- *
- * @param which which bom value to return
- *
- * @return the bom value
- *
- * see bom_refresh
- **/
-int bom_get(int which) {
-    return bom_val[which];
-}
-
-/** 
- * Compares all the values in bom_val[] and returns the index to the lowest (max) value element.
- *
- * @pre must call bom refresh
- * @return index to the lowest (max) bom value element.  -1 if no value is lower than
- *    BOM_VALUE_THRESHOLD
- **/
-int bom_get_max(void) {
-    int i, lowest_val, lowest_i;
-    lowest_i = -1;
-    lowest_val = 255;
-    for(i = 0; i < NUM_BOM_LEDS; i++) {
-        if(bom_val[i] < lowest_val) {
-            lowest_val = bom_val[i];
-            lowest_i = i;
-        }
-    }
-    
-    if(lowest_val < BOM_VALUE_THRESHOLD)
-        return lowest_i;
-    else
-        return -1;
+ * files (the "Software"), to deal in the Software without
+ * restriction, including without limitation the rights to use,
+ * copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following
+ * conditions:
+ * 
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ * 
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
+ * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
+ * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
+ * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
+ * OTHER DEALINGS IN THE SOFTWARE.
+ **/
+
+
+/**
+ * @file bom.c
+ * @brief Implementation for using the BOM
+ *
+ * Contains functions for using the Bearing and Orientation Module (BOM)
+ *
+ * @author Colony Project, CMU Robotics Club
+ **/
+
+#include "bom.h"
+#include "dio.h"
+#include "serial.h"
+#include "analog.h"
+
+//On the original BOM1.0, the emmitter angular order does not match the analog mux order
+//so you need to iterate through the mux index in the following order if you want to get
+//the detector readings in order:
+static const char lookup[16] = {7,6,5,0xe,1,4,3,2,0xf,0,0xd,8,0xc,0xb,9,0xa};
+
+// internal function prototypes
+static void bom_select(char which);
+
+/*
+ Bk R Y (Analog)
+---------
+ Green
+ Blue
+ White
+---------
+ Blue
+ White
+*/
+
+
+/*
+the analog pin definitions from dio.h DO NOT work here,
+so we must use PF0 from avrgcc (as opposed to _PIN_F0).
+BUT the dio pin definitions from dio.h must be used (no PE...).
+
+also, _PIN_E2 is initialized to high for some reason,
+which turns the BOM on when the robot is turned on.
+WORK-AROUND: call digital_output(_PIN_E2,0) at some point.
+
+*/
+
+#define MONKI PF0         //analog (yellow)
+//------------------------//
+#define MONKL _PIN_E2     //green
+#define MONK1 _PIN_E3     //blue
+#define MONK0 _PIN_E4     //white
+//------------------------//
+#define MONK3 _PIN_E6     //blue
+#define MONK2 _PIN_E7     //white
+
+#define BOM_VALUE_THRESHOLD 150 //200
+#define NUM_BOM_LEDS 16
+
+/*
+  *The following pin definitions are for the BOM v1.5
+  */
+
+#define BOM_MODE	_PIN_E2	//dio0
+#define BOM_STROBE	_PIN_E3	//dio1
+
+#define BOM_DATA	_PIN_A0 //servo0
+#define BOM_CLOCK	_PIN_A1	//servo1
+
+#define BOM_S0		_PIN_E5	//dio3
+#define BOM_S1		_PIN_E4	//dio2
+#define BOM_S2		_PIN_E7	//dio4
+#define BOM_S3		_PIN_E6	//dio5
+#define BOM_OUT		PF0		//analog(yellow)
+
+/**
+ * @defgroup bom BOM (Bearing and Orientation Module)
+ * @brief Functions for dealing with the BOM.
+ *
+ * The Bearing and Orientation Module / Barrel of Monkeys / BOM
+ * is a custom sensor designed and built by the Colony Project.
+ * It consists of a ring of 16 IR emitters and 16 IR detectors.
+ * The BOM is most often use to determine the direction of other
+ * robots. This module contains functions for controlling the BOM.
+ *
+ * Include bom.h to access these functions.
+ *
+ * @{
+ **/
+
+unsigned char bom_initd=0;
+
+static unsigned int bom_val[NUM_BOM_LEDS];
+static volatile char bom_type = BOM10;
+static int select_pins[4];
+static int analog_pin;
+
+/**
+ * Initializes the BOM.
+ * Call bom_init before reading bom values or turning bom leds.
+ *
+ * @bugs INCOMPLETE - No utilization of BOM1.5 RSSI capability. Probably leave this out
+ * until Cornell and Pras return
+ *
+ * @return 0 if init succesfull, an error code otherwise 
+ *
+ * @see bom_refresh, bom_leds_on, bom_leds_off
+ **/
+int bom_init(char type) {
+
+    if(bom_initd)
+      return ERROR_INIT_ALREADY_INITD;
+
+
+    bom_type = type;
+    
+    switch(bom_type) {
+    case BOM10:
+		select_pins[0] = MONK0; 
+		select_pins[1] = MONK1;
+		select_pins[2] = MONK2;
+		select_pins[3] = MONK3;
+		analog_pin = MONKI;
+        break;
+    case BOM15:
+        //Sets BOM1.5 to normal [BOM] mode
+        digital_output(BOM_MODE, 0);
+		select_pins[0] = BOM_S0; 
+		select_pins[1] = BOM_S1;
+		select_pins[2] = BOM_S2;
+		select_pins[3] = BOM_S3;
+		bom_set_leds(BOM_ALL);
+		analog_pin = BOM_OUT;
+        break;
+    case RBOM:
+        break;
+    //default:
+    }
+
+    bom_initd=1;
+    return 0;
 }
 
-/** 
- * Computes the weighted average of all the bom readings to estimate the position (and distance) of another robot.
- *
+/**
+ * Iterates through each bit in the bit_field. For each set bit, sets the corresponding bom select bits
+ *    and updates the corresponding bom value with an analog_get8 reading.  analog_init and bom_init
+ *    must be called for this to work. Must call this before reading BOM values!
+ *
+ *
+ * @param bit_field specifies which elements in bom_val[] should be updated. Use BOM_ALL to refresh all values.
+ *    Ex. if 0x0003 is passed, bom_val[0] and bom_val[1] will be updated.
+ *
+ * @return 0 if init succesfull, an error code otherwise
+ *
+ * @see bom_get
+ **/
+int bom_refresh(int bit_field) {
+    int i;
+    int loop_was_running = 0;
+
+    if(!bom_initd)
+      return ERROR_LIBRARY_NOT_INITD;
+
+    
+    //Check analog loop status
+    if(analog_loop_status() == ADC_LOOP_RUNNING) {
+      loop_was_running = 1;
+      analog_stop_loop();
+    }
+    
+    //Read BOM values
+    for(i = 0; i < NUM_BOM_LEDS; i++) {
+      if(bit_field & 0x1) {
+	bom_select(i);
+	bom_val[i] = analog_get8(analog_pin);
+      }
+      bit_field = bit_field >> 1;
+    }
+    
+    //Restore analog loop status
+    if(loop_was_running)
+      analog_start_loop();
+
+    return 0;
+}
+
+/**
+ * Gets the bom reading from bom_val[which].  Call bom_refresh beforehand to read new bom values.
+ *
+ * @pre must call bom refresh first
+ *
+ * @param which which bom value to return
+ *
+ * @return the bom value, -1 on error
+ *
+ * see bom_refresh
+ **/
+int bom_get(int which) {
+    if(!bom_initd)
+      return -1;
+
+    return bom_val[which];
+}
+
+/** 
+ * Compares all the values in bom_val[] and returns the index to the lowest (max) value element.
+ *
  * @pre must call bom refresh
- * @param dist  pointer to int in which to return the estimated distance to the other robot
+ * @return index to the lowest (max) bom value element.  -1 if no value is lower than
+ *    BOM_VALUE_THRESHOLD, -2 if the bom is not initialized
+ **/
+int bom_get_max(void) {
+    int i, lowest_val, lowest_i;
+
+    if(!bom_initd)
+      return -2;
+
+    lowest_i = -1;
+    lowest_val = 255;
+    for(i = 0; i < NUM_BOM_LEDS; i++) {
+        if(bom_val[i] < lowest_val) {
+            lowest_val = bom_val[i];
+            lowest_i = i;
+        }
+    }
+    
+    if(lowest_val < BOM_VALUE_THRESHOLD)
+        return lowest_i;
+    else
+        return -1;
+}
+
+/** 
+ * Computes the weighted average of all the bom readings to estimate the position (and distance) of another robot.
+ *
+ * @pre must call bom refresh
+ * @param dist  pointer to int in which to return the estimated distance to the other robot
  * @return estimated position of the max bom value element as a fixed point value analogous to 10 times the
- *        index of the max bom value.  -1 if no value is lower than BOM_VALUE_THRESHOLD.
+ *        index of the max bom value.  -1 if no value is lower than BOM_VALUE_THRESHOLD, -2 if the bom is not initialized
  **/
 int bom_get_max10(int *dist) {
     int i, max;
     long long mean = 0, sum = 0;
 
+    if(!bom_initd)
+      return ERROR_LIBRARY_NOT_INITD;
+
+
     max = bom_get_max();
     if (max < 0)
     {
@@ -264,125 +295,148 @@
     }
 
     return mean;
-}
-
-/**
- * Iterates through each bit in the bit_field. If the bit is set, the corresponding emitter will
- *    be enabled to turn on when bom_on() is called.
- *    bom_init must be called for this to work. Does nothing if a BOM1.0 is installed
- *
- * @param bit_field specifies which leds should be turned on when bom_on is called.  Use BOM_ALL to turn on all bom leds.
- *    Ex. if 0x0005 is passed, leds 0 and 2 will be turned on.
- **/
-void bom_set_leds(int bit_field) {
-    int i;
-	unsigned int mask = 1<<(NUM_BOM_LEDS-1);
-	switch(bom_type) {
-    case BOM10:
-        //TODO: put an assert here to alert the user that this should not be called
-        break;
-		
-    case BOM15:
-	    for(i=NUM_BOM_LEDS; i>0; i--)
-	    {
-		    //set the current bit, sending MSB first
-		    digital_output(BOM_DATA, bit_field&mask);
-		    //then pulse the clock
-		    digital_output(BOM_CLOCK, 1);
-		    digital_output(BOM_CLOCK, 0);
-			mask = mask>>1;
-	    }
-        break;
-		
-    case RBOM:
-        //add rbom code here
-        break;
-    }
-}
-
-
-/**
- * (DEPRECATED) Returns the direction of the maximum BOM reading,
- * as an integer in the range 0-15. 0 indicates to the
- * robot's right, while the rest of the sensors are
- * numbered counterclockwise. This is useful for determining
- * the direction of a robot flashing its BOM, of only one
- * robot is currently doing so. analog_init must be called
- * before this function can be used.
- *
- * @return the direction of the maximum BOM reading
- *
- * @see analog_init
- **/
-int get_max_bom(void) {
-    bom_refresh(BOM_ALL);
-    return bom_get_max();
-}
-
-/**
- * Flashes the BOM.  If using a BOM1.5, only the emitters that have been enabled using
- * bom_set_leds will turn on.
- * 
- * @see bom_off, bom_set_leds
- **/
-void bom_on(void)
-{
-  switch(bom_type) {
-  case BOM10:
-	digital_output(MONKL, 1);
-	break;
-  case BOM15:
-	digital_output(BOM_STROBE, 1);
-	break;
-  case RBOM:
-	break;
-  }
-}
-
-/**
- * Turns off all bom leds.
- * 
- * @see bom_on
- **/
-void bom_off(void)
-{
-  switch(bom_type) {
-  case BOM10:
-	digital_output(MONKL, 0);
-	break;
-  case BOM15:
-	digital_output(BOM_STROBE, 0);
-	break;
-  case RBOM:
-	break;
-  }
-}
-
-/** @} **/ //end group
-
-//select a detector to read
-static void bom_select(char which) {
-	if(bom_type == BOM10)
-	  which = lookup[(int)which];
-	
-    if (which&8)
-      digital_output(select_pins[3], 1);
-    else
-      digital_output(select_pins[3], 0);
-
-    if (which&4)
-      digital_output(select_pins[2], 1);
-    else
-      digital_output(select_pins[2], 0);
-
-    if (which&2)
-      digital_output(select_pins[1], 1);
-    else
-      digital_output(select_pins[1], 0);
-
-    if (which&1)
-      digital_output(select_pins[0], 1);
-    else
-      digital_output(select_pins[0], 0);
-	
-}
+}
+
+/**
+ * Iterates through each bit in the bit_field. If the bit is set, the corresponding emitter will
+ *    be enabled to turn on when bom_on() is called.
+ *    bom_init must be called for this to work. Does nothing if a BOM1.0 is installed
+ *
+ * @param bit_field specifies which leds should be turned on when bom_on is called.  Use BOM_ALL to turn on all bom leds.
+ *    Ex. if 0x0005 is passed, leds 0 and 2 will be turned on.
+ *
+ * @return 0 if init succesfull, an error code otherwise
+ *
+ **/
+int bom_set_leds(int bit_field) {
+    int i;
+    unsigned int mask = 1<<(NUM_BOM_LEDS-1);
+
+    if(!bom_initd)
+      return ERROR_LIBRARY_NOT_INITD;
+
+    switch(bom_type) {
+    case BOM10:
+        //TODO: put an assert here to alert the user that this should not be called
+        break;
+		
+    case BOM15:
+	    for(i=NUM_BOM_LEDS; i>0; i--)
+	    {
+		    //set the current bit, sending MSB first
+		    digital_output(BOM_DATA, bit_field&mask);
+		    //then pulse the clock
+		    digital_output(BOM_CLOCK, 1);
+		    digital_output(BOM_CLOCK, 0);
+			mask = mask>>1;
+	    }
+        break;
+		
+    case RBOM:
+        //add rbom code here
+        break;
+    }
+
+    return 0;
+}
+
+
+/**
+ * (DEPRECATED) Returns the direction of the maximum BOM reading,
+ * as an integer in the range 0-15. 0 indicates to the
+ * robot's right, while the rest of the sensors are
+ * numbered counterclockwise. This is useful for determining
+ * the direction of a robot flashing its BOM, of only one
+ * robot is currently doing so. analog_init must be called
+ * before this function can be used.
+ *
+ * @return the direction of the maximum BOM reading
+ *
+ * @see analog_init
+ **/
+int get_max_bom(void) {
+    bom_refresh(BOM_ALL);
+    return bom_get_max();
+}
+
+/**
+ * Flashes the BOM.  If using a BOM1.5, only the emitters that have been enabled using
+ * bom_set_leds will turn on.
+ * 
+ * @return 0 if init succesfull, an error code otherwise
+ *
+ * @see bom_off, bom_set_leds
+ **/
+int bom_on(void)
+{
+  if(!bom_initd)
+    return ERROR_LIBRARY_NOT_INITD;
+
+  switch(bom_type) {
+  case BOM10:
+	digital_output(MONKL, 1);
+	break;
+  case BOM15:
+	digital_output(BOM_STROBE, 1);
+	break;
+  case RBOM:
+	break;
+  }
+
+  return 0;
+}
+
+/**
+ * Turns off all bom leds.
+ * 
+ * @return 0 if init succesfull, an error code otherwise
+ *
+ * @see bom_on
+ **/
+int bom_off(void)
+{
+  if(!bom_initd)
+    return ERROR_LIBRARY_NOT_INITD;
+
+  switch(bom_type) {
+  case BOM10:
+	digital_output(MONKL, 0);
+	break;
+  case BOM15:
+	digital_output(BOM_STROBE, 0);
+	break;
+  case RBOM:
+	break;
+  }
+
+  return 0;
+}
+
+/** @} **/ //end group
+
+//select a detector to read
+static void bom_select(char which) {
+	if(bom_type == BOM10)
+	  which = lookup[(int)which];
+	
+    if (which&8)
+      digital_output(select_pins[3], 1);
+    else
+      digital_output(select_pins[3], 0);
+
+    if (which&4)
+      digital_output(select_pins[2], 1);
+    else
+      digital_output(select_pins[2], 0);
+
+    if (which&2)
+      digital_output(select_pins[1], 1);
+    else
+      digital_output(select_pins[1], 0);
+
+    if (which&1)
+      digital_output(select_pins[0], 1);
+    else
+      digital_output(select_pins[0], 0);
+	
+}
Index: trunk/code/projects/libdragonfly/bom.h
===================================================================
--- trunk/code/projects/libdragonfly/bom.h	(revision 1460)
+++ trunk/code/projects/libdragonfly/bom.h	(revision 1461)
@@ -57,10 +57,10 @@
 
 
 /** @brief Initialize the bom according to bom type **/
-void bom_init(char type);
+int bom_init(char type);
 
 /** @brief Refresh bom_val[] with new values from analog8.  analog_init and bom_init must be called for this to work. **/
-void bom_refresh(int bit_field);
+int bom_refresh(int bit_field);
 
 /** @brief Gets the bom reading from bom_val[which].  Call bom_refresh beforehand to read new bom values. **/
 int bom_get(int which);
@@ -72,16 +72,16 @@
 int bom_get_max10(int *dist);
 
 /** @brief Enables the selected bom leds on a BOM1.5 **/
-void bom_set_leds(int bit_field);
+int bom_set_leds(int bit_field);
 
 /** @brief (DEPRECATED) Gets and compares all bom values.  Returns the index to the highest value element since last refresh. **/
 int get_max_bom(void);
 
 /** @brief Turns on all BOM leds, or turns on enabled leds on a BOM1.5. **/
-void bom_on(void);
+int bom_on(void);
 
 /** @brief Turns off all bom leds. **/
-void bom_off(void);
+int bom_off(void);
 
 /** @} **/
 
Index: trunk/code/projects/libdragonfly/rangefinder.c
===================================================================
--- trunk/code/projects/libdragonfly/rangefinder.c	(revision 1460)
+++ trunk/code/projects/libdragonfly/rangefinder.c	(revision 1461)
@@ -63,6 +63,9 @@
 #include "analog.h"
 #include "dio.h"
 
+unsigned char range_initd=0;
+
+
 /*
   read_distance returns the 8-bit reading from the rangefinder
   parameters:
@@ -112,11 +115,19 @@
  * Initializes the rangefinders. This must be called before
  * range_read_distance.
  *
+ * @return 0 if init succesfull, an error code otherwise
+ *
  * @see range_read_distance
  **/
-void range_init(void)
+int range_init(void)
 {
+  if(range_initd)
+    return ERROR_INIT_ALREADY_INITD;
+
   digital_output(_PIN_B4,0);
+
+  range_initd=1;
+  return 0;
 }
 
 /**
@@ -126,11 +137,14 @@
  * @param range_id the rangefinder to use. This should be one
  * of the constants IR1 - IR5.
  *
- * @return the distance measured by the rangefinder
+ * @return the distance measured by the rangefinder, or an error code
  *
  * @see range_init
  **/
 int range_read_distance(int range_id) {
+  if(!range_initd)
+    return -3;
+
   return linearize_distance(analog8(range_id));
 }
 
Index: trunk/code/projects/libdragonfly/rangefinder.h
===================================================================
--- trunk/code/projects/libdragonfly/rangefinder.h	(revision 1460)
+++ trunk/code/projects/libdragonfly/rangefinder.h	(revision 1461)
@@ -37,6 +37,8 @@
 #ifndef _RANGEFINDER_H_
 #define _RANGEFINDER_H_
 
+#include <dragonfly_lib.h>
+
 /**
  * @addtogroup rangefinder
  * @{
@@ -58,7 +60,7 @@
 #define MAX_IR_ADC8 133
 
 /** @brief Initialize the rangefinders **/
-void range_init(void);
+int range_init(void);
 /** @brief Read the distance from a rangefinder **/
 int range_read_distance(int range_id);
 /** @brief Convert logarithmic-scale distance readings to a linear scale **/
