diff --git a/src/config/conf_board.h b/src/config/conf_board.h
index 94192c65b53d77c068da0c041a4637f4dfb8c365..37265f9eb252d631814dc8f08fd196f6f6321e41 100644
--- a/src/config/conf_board.h
+++ b/src/config/conf_board.h
@@ -19,6 +19,8 @@
     #define LED2    IOPORT_CREATE_PIN(PORTF,6)
 #endif
 
+#define MAX_COMMAND_BYTES   64
+
 // Default Settings (only used if EEPROM is empty)
 #define SETTINGS_MAX5443_OFFSET 0
 #define SETTINGS_TCS_ENABLED 1
diff --git a/src/experiment.c b/src/experiment.c
index 3b86ab7baed1854e1fe56db9cbacbe619f420f2e..340cbdac33e76293cc7482cf9772387457689b7b 100644
--- a/src/experiment.c
+++ b/src/experiment.c
@@ -25,6 +25,7 @@
 #include "eis_shield/ad5272.h"
 #include "eis_shield/eis_misc.h"
 #include "eis_shield/eis.h"
+#include <util/atomic.h>
 
 //Public variable definitions
 uint16_t g_gain = POT_GAIN_30k;
@@ -63,7 +64,7 @@ typedef void (*port_callback_t) (void);
 static port_callback_t portd_int0_callback;
 static port_callback_t portd_int1_callback;
 
-void experiment_handler(char command){
+void experiment_handler(char command[]){
 	struct usart_spi_device spi_device_conf_d = {
           .id = IOPORT_CREATE_PIN(PORTD, 0)
       };
@@ -77,40 +78,41 @@ void experiment_handler(char command){
     
 
     double p6;
-
-    switch (command){
+    
+    
+    switch (command[0]){
         case 'A': //ADS Buffer/rate/PGA values from ads1255.h
-            scanf("%hhx%hhx%hhx",&o1,&o2,&o3);
+            sscanf(command+1, "%hhx%hhx%hhx",&o1,&o2,&o3);
             printf("#A: %x %x %x\n",o1,o2,o3);
             ads1255_setup(o1, o2, o3);
             break;
             
         case 'G': //Gain
-            scanf("%u%hhu",&g_gain, &g_short);
+            sscanf(command+1, "%u%hhu",&g_gain, &g_short);
             printf("#G: %u %u\n", g_gain, g_short);
             pot_set_gain(); //uses global g_gain, so no params
             break;
             
         case 'L': //LSV - start, stop, slope
-            scanf("%u%u%i%i%i%i%u",&pct1,&pct2,&pcv1,&pcv2,&p1,&p2,&u1);
+            sscanf(command+1, "%u%u%i%i%i%i%u",&pct1,&pct2,&pcv1,&pcv2,&p1,&p2,&u1);
             precond(pcv1,pct1,pcv2,pct2);
             lsv_experiment(p1,p2,u1,2);
             break;
             
         case 'C': //CV - v1, v2, start, scans, slope
-            scanf("%u%u%i%i%i%i%i%hhu%u",&pct1,&pct2,&pcv1,&pcv2,&p1,&p2,&p3,&p5,&u1);
+            sscanf(command+1, "%u%u%i%i%i%i%i%hhu%u",&pct1,&pct2,&pcv1,&pcv2,&p1,&p2,&p3,&p5,&u1);
             precond(pcv1,pct1,pcv2,pct2);
             cv_experiment(p1,p2,p3,p5,u1);
             break;
             
         case 'S': //SWV - start, stop, step size, pulse_height, frequency, scans
-            scanf("%u%u%i%i%i%i%u%u%u%u",&pct1,&pct2,&pcv1,&pcv2,&p1,&p2,&u1,&u2,&u3,&u4);
+            sscanf(command+1, "%u%u%i%i%i%i%u%u%u%u",&pct1,&pct2,&pcv1,&pcv2,&p1,&p2,&u1,&u2,&u3,&u4);
             precond(pcv1,pct1,pcv2,pct2);
             swv_experiment(p1,p2,u1,u2,u3,u4);
             break;
             
         case 'D': //DPV - start, stop, step size, pulse_height, period, width
-            scanf("%u%u%i%i%i%i%u%u%u%u",&pct1,&pct2,&pcv1,&pcv2,&p1,&p2,&u1,&u2,&u3,&u4);
+            sscanf(command+1, "%u%u%i%i%i%i%u%u%u%u",&pct1,&pct2,&pcv1,&pcv2,&p1,&p2,&u1,&u2,&u3,&u4);
             precond(pcv1,pct1,pcv2,pct2);
             dpv_experiment(p1,p2,u1,u2,u3,u4);
             break;
@@ -118,13 +120,14 @@ void experiment_handler(char command){
         case 'I':
         {
             uint32_t start_f, increment_f;
-            uint16_t n_increments, settle_cycles, attenuation, offset, mclk_div2;
-            uint8_t pga_gain, output_range, iv_gain, reference;
+            uint16_t n_increments, settle_cycles, attenuation, offset, mclk_div2, init_ms;
+            uint8_t pga_gain, output_range, iv_gain, reference, avg_samples;
             
             uint8_t avg_counter = 0;
             
-            scanf("%lu%lu%u%u%hhu%hhu%hhu%u%u%hhu%u", &start_f, &increment_f, &n_increments, &settle_cycles,
-                  &pga_gain, &output_range, &iv_gain, &attenuation, &offset, &reference, &mclk_div2);
+            sscanf(command+1, "%lu%lu%u%u%hhu%hhu%hhu%u%u%hhu%u%hhu%u", &start_f, &increment_f, &n_increments,
+                  &settle_cycles, &pga_gain, &output_range, &iv_gain, &attenuation, &offset, &reference,
+                  &mclk_div2, &avg_samples, &init_ms);
 
             
             struct result {
@@ -133,12 +136,18 @@ void experiment_handler(char command){
             } result;
             
             result.increment = 0;
+
+            cint16_t * imp_avg = malloc(avg_samples*sizeof(cint16_t));
             
-            cint16_t imp_avg[4];
+            //check for successful allocation
+            if (!imp_avg){
+                printf("#ERR: Could not allocate memory\n");
+                break;
+            }
             
             pot_exp_start(); //Disconnect DStat from shield
             eis_set_params(start_f, increment_f, n_increments-1, settle_cycles, pga_gain, output_range,
-                              iv_gain, attenuation, offset, reference, mclk_div2);
+                              iv_gain, attenuation, offset, reference, mclk_div2, init_ms);
             
             while (eis_status != EIS_STATUS_DONE){
                 if (udi_cdc_is_rx_ready()){
@@ -153,7 +162,7 @@ void experiment_handler(char command){
                 if (eis_status == EIS_STATUS_DONE)
                     break;
                 
-                else if (avg_counter < 4){
+                else if (avg_counter < avg_samples){
                     eis_status = EIS_STATUS_REPEAT;
                     avg_counter++;
                 }
@@ -164,14 +173,14 @@ void experiment_handler(char command){
                     int32_t sum_real = 0;
                     int32_t sum_imag = 0;
                     
-                    for (uint8_t i = 0; i < 4; i++) {
+                    for (uint8_t i = 0; i < avg_samples; i++) {
 //                        printf("#IMP: %i \n", imp_avg[i].real);
                         sum_real += imp_avg[i].real;
                         sum_imag += imp_avg[i].imag;
                     }
                     
-                    sum_real /= 4;
-                    sum_imag /= 4;
+                    sum_real /= avg_samples;
+                    sum_imag /= avg_samples;
                     
                     result.imp.real = sum_real;
                     result.imp.imag = sum_imag;
@@ -196,13 +205,14 @@ void experiment_handler(char command){
             
     #if BOARD_VER_MAJOR == 1 && BOARD_VER_MINOR >= 2
         case 'P': //potentiometry - time, OCP/poteniometry
-            scanf("%u%hhu",&pct1, &o1);
+            sscanf(command+1, "%u%hhu",&pct1, &o1);
             pot_experiment(pct1, o1);
             break;
     #endif
             
         case 'R': //CA - steps, step_dac[], step_seconds[]
-            scanf("%hhu",&p5); //get number of steps
+        {
+            sscanf(command+1, "%hhu%hhu",&p5, &o1); //get number of steps
             printf("#INFO: Steps: %u\n", p5);
             
             //allocate arrays for steps
@@ -215,6 +225,9 @@ void experiment_handler(char command){
                 break;
             }
             
+            //request additional parameters from computer
+            printf("@RQP %u\n", 2*(uint16_t)p5);
+            
             uint8_t i;
             
             for (i=0; i<p5; i++){
@@ -227,7 +240,8 @@ void experiment_handler(char command){
                 printf("#INFO: Time: %u\n", step_seconds[i]);
             }
             
-            scanf("%hhu", &o1);
+            printf("@RCP %u\n", 2*(uint16_t)p5);
+            
             printf("#INFO: TCS_check: %hhu\n", o1);
             if (o1 > 0) {
                 if (settings.settings.tcs_enabled > 0){
@@ -262,7 +276,7 @@ void experiment_handler(char command){
             break;
             
         case 'Z': //Shutter sync
-            scanf("%lg",&p6);
+            sscanf(command+1, "%lg", &p6);
             shutter_cont(p6);
             break;
             
diff --git a/src/experiment.h b/src/experiment.h
index eabe34fd1e65b4ee7d5b6a1690100cdc1b58097b..304cee2c776492e772756c9c12a46a868090de52 100644
--- a/src/experiment.h
+++ b/src/experiment.h
@@ -85,7 +85,7 @@ extern uint8_t g_short;
 extern uint8_t autogain_enable;
 
 uint16_t set_timer_period(uint32_t period, volatile void *tc);
-void experiment_handler(char command);
+void experiment_handler(char command[]);
 void pot_init(void);
 void pot_set_gain(void);
 void volt_exp_start(void);
diff --git a/src/main.c b/src/main.c
index 53b1af77002921bb4c32e478f91e0472b5102e32..8c1c514cc1e45f6b2d10acc39acbd8e2e975d54e 100644
--- a/src/main.c
+++ b/src/main.c
@@ -16,25 +16,56 @@
 #include "conf_board.h"
 #include "ext_twi.h"
 #include "eis_shield/eis.h"
+#include <util/atomic.h>
 
 //Internal function declarations
-int8_t command_handler(char command);
+static void command_handler(uint16_t bytes);
 
-int8_t command_handler(char command){
+static void command_handler(uint16_t bytes){
 	/**
 	 * Deals with commands over USB
 	 *
 	 * Calls functions in 
 	 * @param command Command character input.
+     * @param bytes Number of command bytes to wait for
 	 */
-
+    
+    if (bytes == 0) {
+        printf("@RCV 0\n");
+        return;
+    }
+    else if (bytes >= MAX_COMMAND_BYTES){
+        printf("@ERR Command too long\n");
+        return;
+    }
+    
+    char command_buffer[MAX_COMMAND_BYTES];
+    
+read_data:
+    while (!udi_cdc_is_rx_ready());
+    delay_ms(100);
+    if(!fgets(command_buffer, MAX_COMMAND_BYTES, stdin)){
+        printf("@ERR Could not read string\n");
+        return;
+    }
+    
+    command_buffer[strcspn(command_buffer, "\r\n")] = 0;
+    
+    if (strlen(command_buffer) == 0)
+        goto read_data;
+    
+    printf("@RCV %u\n", strlen(command_buffer));
+    printf("#%s\n", command_buffer);
+    
+    char command = command_buffer[0];
+    
 	switch (command){
         case 'E': //Experiment options
-            experiment_handler(getchar());
+            experiment_handler(command_buffer+1);
             break;
         
         case 'S': //Settings options
-            settings_handler(getchar());
+            settings_handler(command_buffer+1);
             break;
             
         case 'T': ;
@@ -63,8 +94,8 @@ int8_t command_handler(char command){
 			printf("@ERR Command %c not recognized\n", command);
 			return;
 	}
-	printf("no\n\r");
-	return 0;
+	printf("@DONE\n");
+	return;
 }
 
 int main(void){
@@ -124,15 +155,25 @@ int main(void){
     
     eis_init();
     
+    uint16_t bytes_sent = 0;
+    
 	program_loop:
         #if BOARD_VER_MAJOR >= 1 && BOARD_VER_MINOR >= 2 && BOARD_VER_MICRO >=3
             ioport_set_pin_level(LED1, 1);
         #endif
-		while(getchar() != '!');
-		printf ("C\r\n");
+		while (getchar() != '!');
+        scanf("%u", &bytes_sent);
+    
+    
+//        // Empty buffer
+//        while (udi_cdc_is_rx_ready())
+//            udi_cdc_getc();
+    
+		printf ("@ACK %u\n", bytes_sent);
         #if BOARD_VER_MAJOR >= 1 && BOARD_VER_MINOR >= 2 && BOARD_VER_MICRO >=3
             ioport_set_pin_level(LED1, 0);
         #endif
-		command_handler(getchar());
+    
+		command_handler(bytes_sent);
 	goto program_loop;
 }
diff --git a/src/settings.c b/src/settings.c
index d2ee0645fd4b7a83b0b78f8ac3535acf9e3a02ac..a03a25b2375de4604a35309117184afd571861a3 100644
--- a/src/settings.c
+++ b/src/settings.c
@@ -16,8 +16,8 @@
 
 void update_firmware(void);
 
-void settings_handler(char command){
-    switch (command){
+void settings_handler(char command[]){
+    switch (command[0]){
         case 'D': //Reset defaults
             settings_restore_defaults();
             break;
@@ -31,7 +31,7 @@ void settings_handler(char command){
             break;
             
         case 'W': //Write new settings
-            scanf("%i%hhu%u%i%i%i%i%i%i%i%lu%lu",
+            sscanf(command+1, "%i%hhu%u%i%i%i%i%i%i%i%lu%lu",
                   &settings.settings.max5443_offset,
                   &settings.settings.tcs_enabled,
                   &settings.settings.tcs_clear_threshold,
diff --git a/src/settings.h b/src/settings.h
index 98e53caa90ff9ad6fea28739e5193192a5db5b06..b2b50915a3d374f0fc340b79c2269cd629112d4d 100644
--- a/src/settings.h
+++ b/src/settings.h
@@ -38,7 +38,7 @@ union {
     char temp_char[EEPROM_PAGE_SIZE]; //makes sure struct fills whole page
 } settings;
 
-void settings_handler(char command);
+void settings_handler(char command[]);
 void settings_read_eeprom(void);
 void settings_write_eeprom(void);
 void settings_restore_defaults(void);