diff --git a/Marlin/EEPROMwrite.h b/Marlin/EEPROMwrite.h
index ae31bc9ec4..fcb3d8d391 100644
--- a/Marlin/EEPROMwrite.h
+++ b/Marlin/EEPROMwrite.h
@@ -25,18 +25,9 @@ template <class T> int EEPROM_readAnything(int &ee, T& value)
 }
 //======================================================================================
 
-#include <avr/pgmspace.h>
+#define SERIAL_ECHOPAIR(name,value) {SERIAL_ECHOPGM(name);SERIAL_ECHO(value);}
+
 
-void serialprintPGM(const char *str)
-{
-  char ch=pgm_read_byte(str);
-  while(ch)
-  {
-    Serial.print(ch);
-    ch=pgm_read_byte(++str);
-  }
-}
-#define SerialprintPGM(x) serialprintPGM(PSTR(x))
 
 #define EEPROM_OFFSET 100
 
@@ -48,8 +39,9 @@ void serialprintPGM(const char *str)
 // ALSO:  always make sure the variables in the Store and retrieve sections are in the same order.
 #define EEPROM_VERSION "V04"  
 
-void StoreSettings() 
+inline void StoreSettings() 
 {
+#ifdef EEPROM_SETTINGS
   char ver[4]= "000";
   int i=EEPROM_OFFSET;
   EEPROM_writeAnything(i,ver); // invalidate data first 
@@ -75,107 +67,115 @@ void StoreSettings()
   char ver2[4]=EEPROM_VERSION;
   i=EEPROM_OFFSET;
   EEPROM_writeAnything(i,ver2); // validate data
-  SerialprintPGM("echo: Settings Stored\n");
+  SERIAL_ECHO_START;
+  SERIAL_ECHOLNPGM("Settings Stored");
+#endif //EEPROM_SETTINGS
 }
 
-void RetrieveSettings(bool def=false)
+inline void RetrieveSettings(bool def=false)
 {  // if def=true, the default values will be used
-  int i=EEPROM_OFFSET;
-  char stored_ver[4];
-  char ver[4]=EEPROM_VERSION;
-  EEPROM_readAnything(i,stored_ver); //read stored version
-  //  SERIAL_ECHOLN("Version: [" << ver << "] Stored version: [" << stored_ver << "]");
-  if ((!def)&&(strncmp(ver,stored_ver,3)==0)) 
-  {   // version number match
-    EEPROM_readAnything(i,axis_steps_per_unit);  
-    EEPROM_readAnything(i,max_feedrate);  
-    EEPROM_readAnything(i,max_acceleration_units_per_sq_second);
-    EEPROM_readAnything(i,acceleration);
-    EEPROM_readAnything(i,retract_acceleration);
-    EEPROM_readAnything(i,minimumfeedrate);
-    EEPROM_readAnything(i,mintravelfeedrate);
-    EEPROM_readAnything(i,minsegmenttime);
-    EEPROM_readAnything(i,max_xy_jerk);
-    EEPROM_readAnything(i,max_z_jerk);
-    #ifndef PIDTEMP
-      float Kp,Ki,Kd;
-    #endif
-    EEPROM_readAnything(i,Kp);
-    EEPROM_readAnything(i,Ki);
-    EEPROM_readAnything(i,Kd);
+  #ifdef EEPROM_SETTINGS
+    int i=EEPROM_OFFSET;
+    char stored_ver[4];
+    char ver[4]=EEPROM_VERSION;
+    EEPROM_readAnything(i,stored_ver); //read stored version
+    //  SERIAL_ECHOLN("Version: [" << ver << "] Stored version: [" << stored_ver << "]");
+    if ((!def)&&(strncmp(ver,stored_ver,3)==0)) 
+    {   // version number match
+      EEPROM_readAnything(i,axis_steps_per_unit);  
+      EEPROM_readAnything(i,max_feedrate);  
+      EEPROM_readAnything(i,max_acceleration_units_per_sq_second);
+      EEPROM_readAnything(i,acceleration);
+      EEPROM_readAnything(i,retract_acceleration);
+      EEPROM_readAnything(i,minimumfeedrate);
+      EEPROM_readAnything(i,mintravelfeedrate);
+      EEPROM_readAnything(i,minsegmenttime);
+      EEPROM_readAnything(i,max_xy_jerk);
+      EEPROM_readAnything(i,max_z_jerk);
+      #ifndef PIDTEMP
+        float Kp,Ki,Kd;
+      #endif
+      EEPROM_readAnything(i,Kp);
+      EEPROM_readAnything(i,Ki);
+      EEPROM_readAnything(i,Kd);
 
-    SerialprintPGM("echo: Stored settings retreived:\n");
-  }
-  else 
-  {
-    float tmp1[]=DEFAULT_AXIS_STEPS_PER_UNIT;
-    float tmp2[]=DEFAULT_MAX_FEEDRATE;
-    long tmp3[]=DEFAULT_MAX_ACCELERATION;
-    for (short i=0;i<4;i++) 
-    {
-      axis_steps_per_unit[i]=tmp1[i];  
-      max_feedrate[i]=tmp2[i];  
-      max_acceleration_units_per_sq_second[i]=tmp3[i];
+      SERIAL_ECHO_START;
+      SERIAL_ECHOLNPGM("Stored settings retreived:");
     }
-    acceleration=DEFAULT_ACCELERATION;
-    retract_acceleration=DEFAULT_RETRACT_ACCELERATION;
-    minimumfeedrate=DEFAULT_MINIMUMFEEDRATE;
-    minsegmenttime=DEFAULT_MINSEGMENTTIME;       
-    mintravelfeedrate=DEFAULT_MINTRAVELFEEDRATE;
-    max_xy_jerk=DEFAULT_XYJERK;
-    max_z_jerk=DEFAULT_ZJERK;
-    SerialprintPGM("echo: Using Default settings:\n");
-  }
-  SerialprintPGM("echo: Steps per unit:\n   M92 X");
-    Serial.print(axis_steps_per_unit[0]);
-    SerialprintPGM(" Y"); 
-    Serial.print(axis_steps_per_unit[1]);
-    SerialprintPGM(" Z");
-    Serial.print(axis_steps_per_unit[2]);
-    SerialprintPGM(" E");
-    Serial.print(axis_steps_per_unit[3]);
-    
-  SerialprintPGM("\nMaximum feedrates (mm/s):\n   M203 X"  );
-    Serial.print(max_feedrate[0]/60);
-    SerialprintPGM(" Y" ); 
-    Serial.print(max_feedrate[1]/60 ); 
-    SerialprintPGM(" Z" ); 
-    Serial.print(max_feedrate[2]/60 ); 
-    SerialprintPGM(" E" ); 
-    Serial.print(max_feedrate[3]/60);
-  SerialprintPGM("\nMaximum Acceleration (mm/s2):\n   M201 X"  );
-    Serial.print(max_acceleration_units_per_sq_second[0] ); 
-    SerialprintPGM(" Y" ); 
-    Serial.print(max_acceleration_units_per_sq_second[1] ); 
-    SerialprintPGM(" Z" ); 
-    Serial.print(max_acceleration_units_per_sq_second[2] );
-    SerialprintPGM(" E" ); 
-    Serial.print(max_acceleration_units_per_sq_second[3]);
-  SerialprintPGM("\necho: Acceleration: S=acceleration, T=retract acceleration\n   M204 S"  );
-    Serial.print(acceleration ); 
-    SerialprintPGM(" T" ); 
-    Serial.print(retract_acceleration);
-  SerialprintPGM("\necho: Advanced variables: S=Min feedrate (mm/s), T=Min travel feedrate (mm/s), B=minimum segment time (ms), X=maximum xY jerk (mm/s),  Z=maximum Z jerk (mm/s)");
-  SerialprintPGM("   M205 S"  );
-    Serial.print(minimumfeedrate/60 ); 
-    SerialprintPGM(" T" ); 
-    Serial.print(mintravelfeedrate/60 ); 
-    SerialprintPGM(" B" ); 
-    Serial.print(minsegmenttime ); 
-    SerialprintPGM(" X" ); 
-    Serial.print(max_xy_jerk/60 ); 
-    SerialprintPGM(" Z" ); 
-    Serial.print(max_z_jerk/60);
-    SerialprintPGM("\n" ); 
-  #ifdef PIDTEMP
-    SerialprintPGM("PID settings:");
-    SerialprintPGM("   M301 P"  ); 
-    Serial.print(Kp ); 
-    SerialprintPGM(" I" ); 
-    Serial.print(Ki ); 
-    SerialprintPGM(" D" ); 
-    Serial.print(Kd);  
+    else 
+    {
+      float tmp1[]=DEFAULT_AXIS_STEPS_PER_UNIT;
+      float tmp2[]=DEFAULT_MAX_FEEDRATE;
+      long tmp3[]=DEFAULT_MAX_ACCELERATION;
+      for (short i=0;i<4;i++) 
+      {
+        axis_steps_per_unit[i]=tmp1[i];  
+        max_feedrate[i]=tmp2[i];  
+        max_acceleration_units_per_sq_second[i]=tmp3[i];
+      }
+      acceleration=DEFAULT_ACCELERATION;
+      retract_acceleration=DEFAULT_RETRACT_ACCELERATION;
+      minimumfeedrate=DEFAULT_MINIMUMFEEDRATE;
+      minsegmenttime=DEFAULT_MINSEGMENTTIME;       
+      mintravelfeedrate=DEFAULT_MINTRAVELFEEDRATE;
+      max_xy_jerk=DEFAULT_XYJERK;
+      max_z_jerk=DEFAULT_ZJERK;
+      SERIAL_ECHO_START;
+      SERIAL_ECHOLN("Using Default settings:");
+    }
+  #ifdef EEPROM_CHITCHAT
+    SERIAL_ECHO_START;
+      SERIAL_ECHOLNPGM("Steps per unit:");
+      SERIAL_ECHO_START;
+      SERIAL_ECHOPAIR("  M92 X",axis_steps_per_unit[0]);
+      SERIAL_ECHOPAIR(" Y",axis_steps_per_unit[1]);
+      SERIAL_ECHOPAIR(" Z",axis_steps_per_unit[2]);
+      SERIAL_ECHOPAIR(" E",axis_steps_per_unit[3]);
+      SERIAL_ECHOLN("");
+      
+    SERIAL_ECHO_START;
+      SERIAL_ECHOLNPGM("Maximum feedrates (mm/s):");
+      SERIAL_ECHO_START;
+      SERIAL_ECHOPAIR("  M203 X",max_feedrate[0]/60);
+      SERIAL_ECHOPAIR(" Y",max_feedrate[1]/60 ); 
+      SERIAL_ECHOPAIR(" Z", max_feedrate[2]/60 ); 
+      SERIAL_ECHOPAIR(" E", max_feedrate[3]/60);
+      SERIAL_ECHOLN("");
+    SERIAL_ECHO_START;
+      SERIAL_ECHOLNPGM("Maximum Acceleration (mm/s2):");
+      SERIAL_ECHO_START;
+      SERIAL_ECHOPAIR("  M201 X" ,max_acceleration_units_per_sq_second[0] ); 
+      SERIAL_ECHOPAIR(" Y" , max_acceleration_units_per_sq_second[1] ); 
+      SERIAL_ECHOPAIR(" Z" ,max_acceleration_units_per_sq_second[2] );
+      SERIAL_ECHOPAIR(" E" ,max_acceleration_units_per_sq_second[3]);
+      SERIAL_ECHOLN("");
+    SERIAL_ECHO_START;
+      SERIAL_ECHOLNPGM("Acceleration: S=acceleration, T=retract acceleration");
+      SERIAL_ECHO_START;
+      SERIAL_ECHOPAIR("  M204 S",acceleration ); 
+      SERIAL_ECHOPAIR(" T" ,retract_acceleration);
+      SERIAL_ECHOLN("");
+    SERIAL_ECHO_START;
+      SERIAL_ECHOLNPGM("Advanced variables: S=Min feedrate (mm/s), T=Min travel feedrate (mm/s), B=minimum segment time (ms), X=maximum xY jerk (mm/s),  Z=maximum Z jerk (mm/s)");
+      SERIAL_ECHO_START;
+      SERIAL_ECHOPAIR("  M205 S",minimumfeedrate/60 ); 
+      SERIAL_ECHOPAIR(" T" ,mintravelfeedrate/60 ); 
+      SERIAL_ECHOPAIR(" B" ,minsegmenttime ); 
+      SERIAL_ECHOPAIR(" X" ,max_xy_jerk/60 ); 
+      SERIAL_ECHOPAIR(" Z" ,max_z_jerk/60);
+      SERIAL_ECHOLN(""); 
+    #ifdef PIDTEMP
+      SERIAL_ECHO_START;
+      SERIAL_ECHOLNPGM("PID settings:");
+      SERIAL_ECHO_START;
+      SERIAL_ECHOPAIR("   M301 P",Kp ); 
+      SERIAL_ECHOPAIR(" I" ,Ki ); 
+      SERIAL_ECHOPAIR(" D" ,Kd);
+      SERIAL_ECHOLN(""); 
+    #endif
   #endif
+    
+  #endif //EEPROM_SETTINGS
 }  
 
 #endif
diff --git a/Marlin/Marlin.h b/Marlin/Marlin.h
index 61b56fb97c..99cd8021b3 100644
--- a/Marlin/Marlin.h
+++ b/Marlin/Marlin.h
@@ -5,14 +5,49 @@
 // Licence: GPL
 #include <WProgram.h>
 #include "fastio.h"
-
 #include "streaming.h"
-#define SERIAL_ECHO(x) Serial << "echo: " << x;
-#define SERIAL_ECHOLN(x) Serial << "echo: "<<x<<endl;
-#define SERIAL_ERROR(x) Serial << "Error: " << x;
-#define SERIAL_ERRORLN(x) Serial << "Error: " << x<<endl;
-#define SERIAL_PROTOCOL(x) Serial << x;
-#define SERIAL_PROTOCOLLN(x) Serial << x<<endl;
+#include <avr/pgmspace.h>
+
+//#define SERIAL_ECHO(x) Serial << "echo: " << x;
+//#define SERIAL_ECHOLN(x) Serial << "echo: "<<x<<endl;
+//#define SERIAL_ERROR(x) Serial << "Error: " << x;
+//#define SERIAL_ERRORLN(x) Serial << "Error: " << x<<endl;
+//#define SERIAL_PROTOCOL(x) Serial << x;
+//#define SERIAL_PROTOCOLLN(x) Serial << x<<endl;
+
+
+
+#define SERIAL_PROTOCOL(x) Serial.print(x);
+#define SERIAL_PROTOCOLPGM(x) serialprintPGM(PSTR(x));
+#define SERIAL_PROTOCOLLN(x) {Serial.print(x);Serial.write('\n');}
+#define SERIAL_PROTOCOLLNPGM(x) {serialprintPGM(PSTR(x));Serial.write('\n');}
+
+const char errormagic[] PROGMEM ="Error:";
+const char echomagic[] PROGMEM ="echo:";
+#define SERIAL_ERROR_START serialprintPGM(errormagic);
+#define SERIAL_ERROR(x) SERIAL_PROTOCOL(x)
+#define SERIAL_ERRORPGM(x) SERIAL_PROTOCOLPGM(x)
+#define SERIAL_ERRORLN(x) SERIAL_PROTOCOLLN(x)
+#define SERIAL_ERRORLNPGM(x) SERIAL_PROTOCOLLNPGM(x)
+
+#define SERIAL_ECHO_START serialprintPGM(echomagic);
+#define SERIAL_ECHO(x) SERIAL_PROTOCOL(x)
+#define SERIAL_ECHOPGM(x) SERIAL_PROTOCOLPGM(x)
+#define SERIAL_ECHOLN(x) SERIAL_PROTOCOLLN(x)
+#define SERIAL_ECHOLNPGM(x) SERIAL_PROTOCOLLNPGM(x)
+
+//things to write to serial from Programmemory. saves 400 to 2k of RAM.
+#define SerialprintPGM(x) serialprintPGM(PSTR(x))
+inline void serialprintPGM(const char *str)
+{
+  char ch=pgm_read_byte(str);
+  while(ch)
+  {
+    Serial.write(ch);
+    ch=pgm_read_byte(++str);
+  }
+}
+
 
 void get_command();
 void process_commands();
diff --git a/Marlin/Marlin.pde b/Marlin/Marlin.pde
index 311ab0180d..7b67cfcf5b 100644
--- a/Marlin/Marlin.pde
+++ b/Marlin/Marlin.pde
@@ -101,7 +101,7 @@ char version_string[] = "1.0.0 Alpha 1";
 // M220 - set speed factor override percentage S:factor in percent
 // M301 - Set PID parameters P I and D
 // M500 - stores paramters in EEPROM
-// M501 - reads parameters from EEPROM (if you need reset them after you changed them temporarily).  D
+// M501 - reads parameters from EEPROM (if you need reset them after you changed them temporarily).  
 // M502 - reverts to the default "factory settings".  You still need to store them in EEPROM afterwards if you want to.
 
 //Stepper Movement Variables
@@ -199,7 +199,10 @@ void enquecommand(const char *cmd)
   {
     //this is dangerous if a mixing of serial and this happsens
     strcpy(&(cmdbuffer[bufindw][0]),cmd);
-    SERIAL_ECHOLN("enqueing \""<<cmdbuffer[bufindw]<<"\"");
+    SERIAL_ECHO_START;
+    SERIAL_ECHOPGM("enqueing \"");
+    SERIAL_ECHO(cmdbuffer[bufindw]);
+    SERIAL_ECHOLNPGM("\"");
     bufindw= (bufindw + 1)%BUFSIZE;
     buflen += 1;
   }
@@ -208,10 +211,13 @@ void enquecommand(const char *cmd)
 void setup()
 { 
   Serial.begin(BAUDRATE);
-  SERIAL_ECHOLN("Marlin "<<version_string);
-  SERIAL_PROTOCOLLN("start");
-  Serial.print("echo: Free Memory:");
-  serial.println(freeMemory());
+  SERIAL_ECHO_START;
+  SERIAL_ECHOPGM("Marlin ");
+  SERIAL_ECHOLN(version_string);
+  SERIAL_PROTOCOLLNPGM("start");
+  SERIAL_ECHO_START;
+  SERIAL_ECHOPGM("Free Memory:");
+  SERIAL_ECHOLN(freeMemory());
   for(int8_t i = 0; i < BUFSIZE; i++)
   {
     fromsd[i] = false;
@@ -244,12 +250,12 @@ void loop()
 	if(strstr(cmdbuffer[bufindr],"M29") == NULL)
 	{
 	  card.write_command(cmdbuffer[bufindr]);
-	  SERIAL_PROTOCOLLN("ok");
+	  SERIAL_PROTOCOLLNPGM("ok");
 	}
 	else
 	{
 	  card.closefile();
-	  SERIAL_PROTOCOLLN("Done saving file.");
+	  SERIAL_PROTOCOLLNPGM("Done saving file.");
 	}
       }
       else
@@ -284,7 +290,9 @@ inline void get_command()
           strchr_pointer = strchr(cmdbuffer[bufindw], 'N');
           gcode_N = (strtol(&cmdbuffer[bufindw][strchr_pointer - cmdbuffer[bufindw] + 1], NULL, 10));
           if(gcode_N != gcode_LastN+1 && (strstr(cmdbuffer[bufindw], "M110") == NULL) ) {
-            SERIAL_ERRORLN("Line Number is not Last Line Number+1, Last Line:"<<gcode_LastN);
+            SERIAL_ERROR_START;
+            SERIAL_ERRORPGM("Line Number is not Last Line Number+1, Last Line:");
+            SERIAL_ERRORLN(gcode_LastN);
             //Serial.println(gcode_N);
             FlushSerialRequestResend();
             serial_count = 0;
@@ -299,7 +307,9 @@ inline void get_command()
             strchr_pointer = strchr(cmdbuffer[bufindw], '*');
 
             if( (int)(strtod(&cmdbuffer[bufindw][strchr_pointer - cmdbuffer[bufindw] + 1], NULL)) != checksum) {
-              SERIAL_ERRORLN("checksum mismatch, Last Line:"<<gcode_LastN);
+              SERIAL_ERROR_START;
+              SERIAL_ERRORPGM("checksum mismatch, Last Line:");
+              SERIAL_ERRORLN(gcode_LastN);
               FlushSerialRequestResend();
               serial_count = 0;
               return;
@@ -308,7 +318,9 @@ inline void get_command()
           }
           else 
           {
-            SERIAL_ERRORLN("No Checksum with line number, Last Line:"<<gcode_LastN);
+            SERIAL_ERROR_START;
+            SERIAL_ERRORPGM("No Checksum with line number, Last Line:");
+            SERIAL_ERRORLN(gcode_LastN);
             FlushSerialRequestResend();
             serial_count = 0;
             return;
@@ -321,7 +333,9 @@ inline void get_command()
         {
           if((strstr(cmdbuffer[bufindw], "*") != NULL))
           {
-            SERIAL_ERRORLN("No Line Number with checksum, Last Line:"<<gcode_LastN);
+            SERIAL_ERROR_START;
+            SERIAL_ERRORPGM("No Line Number with checksum, Last Line:");
+            SERIAL_ERRORLN(gcode_LastN);
             serial_count = 0;
             return;
           }
@@ -337,7 +351,7 @@ inline void get_command()
             if(card.saving)
               break;
 	    #endif //SDSUPPORT
-            SERIAL_PROTOCOLLN("ok"); 
+            SERIAL_PROTOCOLLNPGM("ok"); 
             break;
           default:
             break;
@@ -362,14 +376,14 @@ inline void get_command()
     return;
   }
   while( !card.eof()  && buflen < BUFSIZE) {
-    
-    serial_char = card.get();
-    if(serial_char == '\n' || serial_char == '\r' || serial_char == ':' || serial_count >= (MAX_CMD_SIZE - 1)) 
+    int16_t n=card.get();
+    serial_char = (char)n;
+    if(serial_char == '\n' || serial_char == '\r' || serial_char == ':' || serial_count >= (MAX_CMD_SIZE - 1)||n==-1) 
     {
      
       if(card.eof()){
         card.sdprinting = false;
-        SERIAL_PROTOCOL("Done printing file");
+        SERIAL_PROTOCOLLNPGM("Done printing file");
         stoptime=millis();
         char time[30];
         unsigned long t=(stoptime-starttime)/1000;
@@ -377,6 +391,7 @@ inline void get_command()
         min=t/60;
         sec=t%60;
         sprintf(time,"%i min, %i sec",min,sec);
+        SERIAL_ECHO_START;
         SERIAL_ECHOLN(time);
         LCD_MESSAGE(time);
         card.checkautostart(true);
@@ -398,6 +413,7 @@ inline void get_command()
       if(!comment_mode) cmdbuffer[bufindw][serial_count++] = serial_char;
     }
   }
+  
   #endif //SDSUPPORT
 
 }
@@ -473,6 +489,7 @@ inline void process_commands()
       previous_millis_cmd = millis();
       return;
     case 4: // G4 dwell
+      LCD_MESSAGEPGM("DWELL...");
       codenum = 0;
       if(code_seen('P')) codenum = code_value(); // milliseconds to wait
       if(code_seen('S')) codenum = code_value() * 1000; // seconds to wait
@@ -533,13 +550,14 @@ inline void process_commands()
     #ifdef SDSUPPORT
 
     case 20: // M20 - list SD card
-      SERIAL_PROTOCOLLN("Begin file list");
+      SERIAL_PROTOCOLLNPGM("Begin file list");
       card.ls();
-      SERIAL_PROTOCOLLN("End file list");
+      SERIAL_PROTOCOLLNPGM("End file list");
       break;
     case 21: // M21 - init SD card
       
       card.initsd();
+      
       break;
     case 22: //M22 - release SD card
       card.release();
@@ -592,7 +610,8 @@ inline void process_commands()
       min=t/60;
       sec=t%60;
       sprintf(time,"%i min, %i sec",min,sec);
-      SERIAL_ERRORLN(time);
+      SERIAL_ECHO_START;
+      SERIAL_ECHOLN(time);
       LCD_MESSAGE(time);
     }
     break;
@@ -637,7 +656,7 @@ inline void process_commands()
           bt = degBed();
       #endif
       #if (TEMP_0_PIN > -1) || defined (HEATER_USES_AD595)
-        SERIAL_PROTOCOL("ok T:");
+        SERIAL_PROTOCOLPGM("ok T:");
         SERIAL_PROTOCOL(tt); 
         #if TEMP_1_PIN > -1 
           #ifdef PIDTEMP
@@ -654,13 +673,14 @@ inline void process_commands()
             SERIAL_PROTOCOLLN("");
           #endif //TEMP_1_PIN
         #else
-          SERIAL_ERRORLN("No thermistors - no temp");
+          SERIAL_ERROR_START;
+          SERIAL_ERRORLNPGM("No thermistors - no temp");
       #endif
       return;
       break;
     case 109: 
     {// M109 - Wait for extruder heater to reach target.
-        LCD_MESSAGE("Heating...");
+        LCD_MESSAGEPGM("Heating...");
         if (code_seen('S')) setTargetHotend0(code_value());
         
         setWatch();
@@ -681,7 +701,8 @@ inline void process_commands()
         #endif //TEMP_RESIDENCY_TIME
         if( (millis() - codenum) > 1000 ) 
         { //Print Temp Reading every 1 second while heating up/cooling down
-          SERIAL_PROTOCOLLN("T:"<< degHotend0() ); 
+          SERIAL_PROTOCOLPGM("T:");
+          SERIAL_PROTOCOLLN( degHotend0() ); 
           codenum = millis();
         }
         manage_heater();
@@ -697,12 +718,13 @@ inline void process_commands()
           }
         #endif //TEMP_RESIDENCY_TIME
         }
-        LCD_MESSAGE("Heating done.");
+        LCD_MESSAGEPGM("Heating done.");
         starttime=millis();
       }
       break;
     case 190: // M190 - Wait bed for heater to reach target.
     #if TEMP_1_PIN > -1
+        LCD_MESSAGEPGM("Bed Heating.");
         if (code_seen('S')) setTargetBed(code_value());
         codenum = millis(); 
         while(isHeatingBed()) 
@@ -710,12 +732,17 @@ inline void process_commands()
           if( (millis()-codenum) > 1000 ) //Print Temp Reading every 1 second while heating up.
           {
             float tt=degHotend0();
-            SERIAL_PROTOCOLLN("T:"<<tt );
-            SERIAL_PROTOCOLLN("ok T:"<<tt <<" B:"<<degBed() ); 
+            SERIAL_PROTOCOLPGM("T:");
+            SERIAL_PROTOCOLLN(tt );
+            SERIAL_PROTOCOLPGM("ok T:");
+            SERIAL_PROTOCOL(tt );
+            SERIAL_PROTOCOLPGM(" B:");
+            SERIAL_PROTOCOLLN(degBed() ); 
             codenum = millis(); 
           }
           manage_heater();
         }
+        LCD_MESSAGEPGM("Bed done.");
     #endif
     break;
 
@@ -759,6 +786,7 @@ inline void process_commands()
       }
       else
       { 
+        LCD_MESSAGEPGM("Free move.");
         st_synchronize(); 
         disable_x(); 
         disable_y(); 
@@ -778,50 +806,50 @@ inline void process_commands()
       }
       break;
     case 115: // M115
-      SERIAL_PROTOCOLLN("FIRMWARE_NAME:Marlin; Sprinter/grbl mashup for gen6 FIRMWARE_URL:http://www.mendel-parts.com PROTOCOL_VERSION:1.0 MACHINE_TYPE:Mendel EXTRUDER_COUNT:1");
+      SerialprintPGM("FIRMWARE_NAME:Marlin; Sprinter/grbl mashup for gen6 FIRMWARE_URL:http://www.mendel-parts.com PROTOCOL_VERSION:1.0 MACHINE_TYPE:Mendel EXTRUDER_COUNT:1");
       break;
     case 114: // M114
-      SERIAL_PROTOCOL("X:");
+      SERIAL_PROTOCOLPGM("X:");
       SERIAL_PROTOCOL(current_position[X_AXIS]);
-      SERIAL_PROTOCOL("Y:");
+      SERIAL_PROTOCOLPGM("Y:");
       SERIAL_PROTOCOL(current_position[Y_AXIS]);
-      SERIAL_PROTOCOL("Z:");
+      SERIAL_PROTOCOLPGM("Z:");
       SERIAL_PROTOCOL(current_position[Z_AXIS]);
-      SERIAL_PROTOCOL("E:");      
+      SERIAL_PROTOCOLPGM("E:");      
       SERIAL_PROTOCOL(current_position[E_AXIS]);
       #ifdef DEBUG_STEPS
-        SERIAL_PROTOCOL(" Count X:");
+        SERIAL_PROTOCOLPGM(" Count X:");
         SERIAL_PROTOCOL(float(count_position[X_AXIS])/axis_steps_per_unit[X_AXIS]);
-        SERIAL_PROTOCOL("Y:");
+        SERIAL_PROTOCOLPGM("Y:");
         SERIAL_PROTOCOL(float(count_position[Y_AXIS])/axis_steps_per_unit[Y_AXIS]);
-        SERIAL_PROTOCOL("Z:");
+        SERIAL_PROTOCOLPGM("Z:");
         SERIAL_PROTOCOL(float(count_position[Z_AXIS])/axis_steps_per_unit[Z_AXIS]);
       #endif
       SERIAL_PROTOCOLLN("");
       break;
     case 119: // M119
       #if (X_MIN_PIN > -1)
-        SERIAL_PROTOCOL("x_min:");
+        SERIAL_PROTOCOLPGM("x_min:");
         SERIAL_PROTOCOL(((READ(X_MIN_PIN)^ENDSTOPS_INVERTING)?"H ":"L "));
       #endif
       #if (X_MAX_PIN > -1)
-        SERIAL_PROTOCOL("x_max:");
+        SERIAL_PROTOCOLPGM("x_max:");
         SERIAL_PROTOCOL(((READ(X_MAX_PIN)^ENDSTOPS_INVERTING)?"H ":"L "));
       #endif
       #if (Y_MIN_PIN > -1)
-        SERIAL_PROTOCOL("y_min:");
+        SERIAL_PROTOCOLPGM("y_min:");
         SERIAL_PROTOCOL(((READ(Y_MIN_PIN)^ENDSTOPS_INVERTING)?"H ":"L "));
       #endif
       #if (Y_MAX_PIN > -1)
-        SERIAL_PROTOCOL("y_max:");
+        SERIAL_PROTOCOLPGM("y_max:");
         SERIAL_PROTOCOL(((READ(Y_MAX_PIN)^ENDSTOPS_INVERTING)?"H ":"L "));
       #endif
       #if (Z_MIN_PIN > -1)
-        SERIAL_PROTOCOL("z_min:");
+        SERIAL_PROTOCOLPGM("z_min:");
         SERIAL_PROTOCOL(((READ(Z_MIN_PIN)^ENDSTOPS_INVERTING)?"H ":"L "));
       #endif
       #if (Z_MAX_PIN > -1)
-        SERIAL_PROTOCOL("z_max:");
+        SERIAL_PROTOCOLPGM("z_max:");
         SERIAL_PROTOCOL(((READ(Z_MAX_PIN)^ENDSTOPS_INVERTING)?"H ":"L "));
       #endif
       SERIAL_PROTOCOLLN("");
@@ -897,7 +925,10 @@ inline void process_commands()
   }
   else
   {
-    SERIAL_ECHOLN("Unknown command:\""<<cmdbuffer[bufindr]<<"\"");
+    SERIAL_ECHO_START;
+    SERIAL_ECHOPGM("Unknown command:\"");
+    SERIAL_ECHO(cmdbuffer[bufindr]);
+    SERIAL_ECHOLNPGM("\"");
   }
 
   ClearToSend();
@@ -907,7 +938,8 @@ void FlushSerialRequestResend()
 {
   //char cmdbuffer[bufindr][100]="Resend:";
   Serial.flush();
-  SERIAL_PROTOCOLLN("Resend:"<<gcode_LastN + 1);
+  SERIAL_PROTOCOLPGM("Resend:");
+  SERIAL_PROTOCOLLN(gcode_LastN + 1);
   ClearToSend();
 }
 
@@ -918,7 +950,7 @@ void ClearToSend()
   if(fromsd[bufindr])
     return;
   #endif //SDSUPPORT
-  SERIAL_PROTOCOLLN("ok"); 
+  SERIAL_PROTOCOLLNPGM("ok"); 
 }
 
 inline void get_coordinates()
@@ -992,7 +1024,9 @@ void kill()
   disable_e();
   
   if(PS_ON_PIN > -1) pinMode(PS_ON_PIN,INPUT);
-  SERIAL_ERRORLN("Printer halted. kill() called !!");
+  SERIAL_ERROR_START;
+  SERIAL_ERRORLNPGM("Printer halted. kill() called !!");
+  LCD_MESSAGEPGM("KILLED. ");
   while(1); // Wait for reset
 }
 
diff --git a/Marlin/cardreader.h b/Marlin/cardreader.h
index 03696fa616..b3f514f61f 100644
--- a/Marlin/cardreader.h
+++ b/Marlin/cardreader.h
@@ -30,8 +30,8 @@ public:
   
 
   inline void ls() {root.ls();};
-  inline bool eof() { sdpos = file.curPosition();return sdpos>=filesize ;};
-  inline char get() {  int16_t n = file.read(); return (n==-1)?'\n':(char)n;};
+  inline bool eof() { return sdpos>=filesize ;};
+  inline int16_t get() {  sdpos = file.curPosition();return (int16_t)file.read();};
   inline void setIndex(long index) {sdpos = index;file.seekSet(index);};
 
 public:
diff --git a/Marlin/cardreader.pde b/Marlin/cardreader.pde
index cd4bfeb7ab..605af11bf5 100644
--- a/Marlin/cardreader.pde
+++ b/Marlin/cardreader.pde
@@ -29,20 +29,24 @@ void CardReader::initsd()
     if (!card.init(SPI_FULL_SPEED,SDSS))
     {
       //if (!card.init(SPI_HALF_SPEED,SDSS))
-      SERIAL_ECHOLN("SD init fail");
+      SERIAL_ECHO_START;
+      SERIAL_ECHOLNPGM("SD init fail");
     }
     else if (!volume.init(&card))
     {
-      SERIAL_ERRORLN("volume.init failed");
+      SERIAL_ERROR_START;
+      SERIAL_ERRORLNPGM("volume.init failed");
     }
     else if (!root.openRoot(&volume)) 
     {
-      SERIAL_ERRORLN("openRoot failed");
+      SERIAL_ERROR_START;
+      SERIAL_ERRORLNPGM("openRoot failed");
     }
     else 
     {
       cardOK = true;
-      SERIAL_ECHOLN("SD card ok");
+      SERIAL_ECHO_START;
+      SERIAL_ECHOLNPGM("SD card ok");
     }
   #endif //SDSS
 }
@@ -77,13 +81,16 @@ void CardReader::selectFile(char* name)
    
     if (file.open(&root, name, O_READ)) {
       filesize = file.fileSize();
-      SERIAL_PROTOCOLLN("File opened:"<<name<<" Size:"<<filesize);
+      SERIAL_PROTOCOLPGM("File opened:");
+      SERIAL_PROTOCOL(name);
+      SERIAL_PROTOCOLPGM(" Size:");
+      SERIAL_PROTOCOLLN(filesize);
       sdpos = 0;
       
-      SERIAL_PROTOCOLLN("File selected");
+      SERIAL_PROTOCOLLNPGM("File selected");
     }
     else{
-      SERIAL_PROTOCOLLN("file.open failed");
+      SERIAL_PROTOCOLLNPGM("file.open failed");
     }
   }
 }
@@ -98,11 +105,14 @@ void CardReader::startFilewrite(char *name)
     
     if (!file.open(&root, name, O_CREAT | O_APPEND | O_WRITE | O_TRUNC))
     {
-      SERIAL_PROTOCOLLN("open failed, File: "<<name<<".");
+      SERIAL_PROTOCOLPGM("open failed, File: ");
+      SERIAL_PROTOCOL(name);
+      SERIAL_PROTOCOLLNPGM(".");
     }
     else{
       saving = true;
-      SERIAL_PROTOCOLLN("Writing to file: "<<name);
+      SERIAL_PROTOCOLPGM("Writing to file: ");
+      SERIAL_PROTOCOLLN(name);
     }
   }
 }
@@ -110,10 +120,13 @@ void CardReader::startFilewrite(char *name)
 void CardReader::getStatus()
 {
   if(cardOK){
-    SERIAL_PROTOCOLLN("SD printing byte "<<sdpos<<"/"<<filesize);
+    SERIAL_PROTOCOLPGM("SD printing byte ");
+    SERIAL_PROTOCOL(sdpos);
+    SERIAL_PROTOCOLPGM("/");
+    SERIAL_PROTOCOLLN(filesize);
   }
   else{
-    SERIAL_PROTOCOLLN("Not SD printing");
+    SERIAL_PROTOCOLLNPGM("Not SD printing");
   }
 }
 void CardReader::write_command(char *buf)
@@ -134,7 +147,8 @@ void CardReader::write_command(char *buf)
   file.write(begin);
   if (file.writeError)
   {
-    SERIAL_ERRORLN("error writing to file");
+    SERIAL_ERROR_START;
+    SERIAL_ERRORLNPGM("error writing to file");
   }
 }
 
diff --git a/Marlin/stepper.cpp b/Marlin/stepper.cpp
index 7d94d8063d..d5d41b1736 100644
--- a/Marlin/stepper.cpp
+++ b/Marlin/stepper.cpp
@@ -232,7 +232,9 @@ inline void trapezoid_generator_reset() {
 ISR(TIMER1_COMPA_vect)
 {        
   if(busy){ 
-    SERIAL_ERRORLN(*(unsigned short *)OCR1A<< " ISR overtaking itself.");
+    SERIAL_ERROR_START
+    SERIAL_ERROR(*(unsigned short *)OCR1A);
+    SERIAL_ERRORLNPGM(" ISR overtaking itself.");
     return; 
   } // The busy-flag is used to avoid reentering this interrupt
 
diff --git a/Marlin/temperature.cpp b/Marlin/temperature.cpp
index 6d81a9811d..87d9ee5434 100644
--- a/Marlin/temperature.cpp
+++ b/Marlin/temperature.cpp
@@ -160,7 +160,7 @@ void manage_heater()
         }
     #endif //PID_OPENLOOP
     #ifdef PID_DEBUG
-     SERIAL_ECHOLN(" PIDDEBUG Input "<<pid_input<<" Output "<<pid_output" pTerm "<<pTerm<<" iTerm "<<iTerm<<" dTerm "<<dTerm);  
+     //SERIAL_ECHOLN(" PIDDEBUG Input "<<pid_input<<" Output "<<pid_output" pTerm "<<pTerm<<" iTerm "<<iTerm<<" dTerm "<<dTerm);  
     #endif //PID_DEBUG
     analogWrite(HEATER_0_PIN, pid_output);
   #endif //PIDTEMP
@@ -462,7 +462,8 @@ ISR(TIMER0_COMPB_vect)
       temp_count++;
       break;
     default:
-      SERIAL_ERRORLN("Temp measurement error!");
+      SERIAL_ERROR_START;
+      SERIAL_ERRORLNPGM("Temp measurement error!");
       break;
   }
     
@@ -496,7 +497,8 @@ ISR(TIMER0_COMPB_vect)
         if(current_raw[TEMPSENSOR_HOTEND_0] >= maxttemp_0) {
           target_raw[TEMPSENSOR_HOTEND_0] = 0;
           analogWrite(HEATER_0_PIN, 0);
-          SERIAL_ERRORLN("Temperature extruder 0 switched off. MAXTEMP triggered !!");
+          SERIAL_ERROR_START;
+          SERIAL_ERRORLNPGM("Temperature extruder 0 switched off. MAXTEMP triggered !!");
           kill();
         }
       #endif
@@ -507,7 +509,8 @@ ISR(TIMER0_COMPB_vect)
         target_raw[TEMPSENSOR_HOTEND_1] = 0;
       if(current_raw[2] >= maxttemp_1) {
         analogWrite(HEATER_2_PIN, 0);
-        SERIAL_ERRORLN("Temperature extruder 1 switched off. MAXTEMP triggered !!");
+        SERIAL_ERROR_START;
+        SERIAL_ERRORLNPGM("Temperature extruder 1 switched off. MAXTEMP triggered !!");
         kill()
       }
     #endif
@@ -518,7 +521,8 @@ ISR(TIMER0_COMPB_vect)
       if(current_raw[TEMPSENSOR_HOTEND_0] <= minttemp_0) {
         target_raw[TEMPSENSOR_HOTEND_0] = 0;
         analogWrite(HEATER_0_PIN, 0);
-        SERIAL_ERRORLN("Temperature extruder 0 switched off. MINTEMP triggered !!");
+        SERIAL_ERROR_START;
+        SERIAL_ERRORLNPGM("Temperature extruder 0 switched off. MINTEMP triggered !!");
         kill();
       }
     #endif
@@ -529,7 +533,8 @@ ISR(TIMER0_COMPB_vect)
       if(current_raw[TEMPSENSOR_HOTEND_1] <= minttemp_1) {
         target_raw[TEMPSENSOR_HOTEND_1] = 0;
         analogWrite(HEATER_2_PIN, 0);
-        SERIAL_ERRORLN("Temperature extruder 1 switched off. MINTEMP triggered !!");
+        SERIAL_ERROR_START;
+        SERIAL_ERRORLNPGM("Temperature extruder 1 switched off. MINTEMP triggered !!");
         kill();
       }
     #endif
@@ -540,7 +545,8 @@ ISR(TIMER0_COMPB_vect)
       if(current_raw[1] <= bed_minttemp) {
         target_raw[1] = 0;
         WRITE(HEATER_1_PIN, 0);
-        SERIAL_ERRORLN("Temperatur heated bed switched off. MINTEMP triggered !!");
+        SERIAL_ERROR_START;
+        SERIAL_ERRORLNPGM("Temperatur heated bed switched off. MINTEMP triggered !!");
         kill();
       }
     #endif
@@ -551,7 +557,8 @@ ISR(TIMER0_COMPB_vect)
       if(current_raw[1] >= bed_maxttemp) {
         target_raw[1] = 0;
         WRITE(HEATER_1_PIN, 0);
-        SERIAL_ERRORLN("Temperature heated bed switched off. MAXTEMP triggered !!");
+        SERIAL_ERROR_START;
+        SERIAL_ERRORLNPGM("Temperature heated bed switched off. MAXTEMP triggered !!");
         kill();
       }
     #endif
diff --git a/Marlin/ultralcd.h b/Marlin/ultralcd.h
index 0822e502b0..4c725329df 100644
--- a/Marlin/ultralcd.h
+++ b/Marlin/ultralcd.h
@@ -83,6 +83,7 @@
 
 
   #define LCD_MESSAGE(x) lcd_status(x);
+  #define LCD_MESSAGEPGM(x) lcd_statuspgm(PSTR(x));
   #define LCD_STATUS lcd_status()
 #else //no lcd
   #define LCD_STATUS
diff --git a/Marlin/ultralcd.pde b/Marlin/ultralcd.pde
index 91d1a54a80..59edb34702 100644
--- a/Marlin/ultralcd.pde
+++ b/Marlin/ultralcd.pde
@@ -67,6 +67,18 @@ void lcd_status(const char* message)
   strncpy(messagetext,message,LCD_WIDTH);
 }
 
+void lcd_statuspgm(const char* message)
+{
+  char ch=pgm_read_byte(message);
+  char *target=messagetext;
+  while(ch)
+  {
+    *target=ch;
+    target++;
+    ch=pgm_read_byte(++message);
+  }
+}
+
 inline void clear()
 {
   lcd.clear();
@@ -105,7 +117,7 @@ void lcd_init()
   lcd.createChar(2,Thermometer);
   lcd.createChar(3,uplevel);
   lcd.createChar(4,refresh);
-  LCD_MESSAGE(fillto(LCD_WIDTH,"UltiMarlin ready."));
+  LCD_MESSAGEPGM("UltiMarlin ready.");
 }
 
 
@@ -1369,7 +1381,8 @@ void MainMenu::showMainMenu()
       }break;
       #endif
       default: 
-        SERIAL_ERRORLN("Something is wrong in the MenuStructure.");
+        SERIAL_ERROR_START;
+        SERIAL_ERRORLNPGM("Something is wrong in the MenuStructure.");
       break;
     }
   }
diff --git a/Marlin/watchdog.pde b/Marlin/watchdog.pde
index 167bc633d3..9cf710a0c7 100644
--- a/Marlin/watchdog.pde
+++ b/Marlin/watchdog.pde
@@ -41,10 +41,11 @@ ISR(WDT_vect)
   {
  
     #ifdef RESET_MANUAL
-      LCD_MESSAGE("Please Reset!");
-      SERIAL_ERRORLN("Something is wrong, please turn off the printer.");
+      LCD_MESSAGEPGM("Please Reset!");
+      SERIAL_ERROR_START;
+      SERIAL_ERRORLNPGM("Something is wrong, please turn off the printer.");
     #else
-      LCD_MESSAGE("Timeout, resetting!");
+      LCD_MESSAGEPGM("Timeout, resetting!");
     #endif 
     //disable watchdog, it will survife reboot.
     WDTCSR |= (1<<WDCE) | (1<<WDE);