diff --git a/Marlin/Configuration.h b/Marlin/Configuration.h
index e8b960f788843264afdb34289bfd4e7178d6fa24..346db503fd189b455a5b1a7eb632d05e4a1b9361 100644
--- a/Marlin/Configuration.h
+++ b/Marlin/Configuration.h
@@ -4,11 +4,11 @@
 
 
 // This determines the communication speed of the printer
-#define BAUDRATE 250000
-//#define BAUDRATE 115200
+//#define BAUDRATE 250000
+#define BAUDRATE 115200
 //#define BAUDRATE 230400
 
-#define EXTRUDERS 1
+#define EXTRUDERS 2
 
 // Frequency limit
 // See nophead's blog for more info
@@ -32,7 +32,7 @@
 // Sanguinololu 1.2 and above = 62
 // Ultimaker = 7,
 // Teensylu = 8
-#define MOTHERBOARD 7
+#define MOTHERBOARD 33
 
 //===========================================================================
 //=============================Thermal Settings  ============================
@@ -46,17 +46,16 @@
 // 5 is ParCan supplied 104GT-2 100K
 // 6 is EPCOS 100k
 // 7 is 100k Honeywell thermistor 135-104LAG-J01
-//#define THERMISTORHEATER_0 3
-//#define THERMISTORHEATER_1 3
-//#define THERMISTORBED 3
-
-//#define HEATER_0_USES_THERMISTOR
-//#define HEATER_1_USES_THERMISTOR
-#define HEATER_0_USES_AD595
+#define THERMISTORHEATER_0 1
+#define THERMISTORHEATER_1 1
+#define HEATER_0_USES_THERMISTOR
+#define HEATER_1_USES_THERMISTOR
+//#define HEATER_0_USES_AD595
 //#define HEATER_1_USES_AD595
 
 // Select one of these only to define how the bed temp is read.
-//#define BED_USES_THERMISTOR
+#define THERMISTORBED 1
+#define BED_USES_THERMISTOR
 //#define BED_USES_AD595
 
 #define BED_CHECK_INTERVAL 5000 //ms
@@ -68,13 +67,13 @@
 //#define WATCHPERIOD 5000 //5 seconds
 
 // Actual temperature must be close to target for this long before M109 returns success
-//#define TEMP_RESIDENCY_TIME 20  // (seconds)
-//#define TEMP_HYSTERESIS 5       // (C°) range of +/- temperatures considered "close" to the target one
+#define TEMP_RESIDENCY_TIME 30  // (seconds)
+#define TEMP_HYSTERESIS 3       // (C°) range of +/- temperatures considered "close" to the target one
 
 //// The minimal temperature defines the temperature below which the heater will not be enabled
 #define HEATER_0_MINTEMP 5
 //#define HEATER_1_MINTEMP 5
-//#define BED_MINTEMP 5
+#define BED_MINTEMP 5
 
 
 // When temperature exceeds max temp, your heater will be switched off.
@@ -82,7 +81,7 @@
 // You should use MINTEMP for thermistor short/failure protection.
 #define HEATER_0_MAXTEMP 275
 //#define HEATER_1_MAXTEMP 275
-//#define BED_MAXTEMP 150
+#define BED_MAXTEMP 150
 
 
 // Wait for Cooldown
@@ -131,9 +130,14 @@
 //    #define  DEFAULT_Kd (PID_SWING_AT_CRITIAL/8./PID_dT)  
 
 // Ultitmaker
-    #define  DEFAULT_Kp  22.2
-    #define  DEFAULT_Ki (1.25*PID_dT)  
-    #define  DEFAULT_Kd (99/PID_dT)  
+//    #define  DEFAULT_Kp  22.2
+//    #define  DEFAULT_Ki (1.25*PID_dT)  
+//    #define  DEFAULT_Kd (99/PID_dT)  
+
+// Makergear
+    #define  DEFAULT_Kp 7.0
+    #define  DEFAULT_Ki 0.1  
+    #define  DEFAULT_Kd 12  
 
 // Mendel Parts V9 on 12V    
 //    #define  DEFAULT_Kp  63.0
@@ -152,7 +156,7 @@
   // if Kc is choosen well, the additional required power due to increased melting should be compensated.
   #define PID_ADD_EXTRUSION_RATE  
   #ifdef PID_ADD_EXTRUSION_RATE
-    #define  DEFAULT_Kc (3) //heatingpower=Kc*(e_speed)
+    #define  DEFAULT_Kc (1) //heatingpower=Kc*(e_speed)
   #endif
 #endif // PIDTEMP
 
@@ -164,10 +168,11 @@
 
 // Endstop Settings
 #define ENDSTOPPULLUPS // Comment this out (using // at the start of the line) to disable the endstop pullup resistors
+
 // The pullups are needed if you directly connect a mechanical endswitch between the signal and ground pins.
-const bool X_ENDSTOPS_INVERTING = true; // set to true to invert the logic of the endstops. 
-const bool Y_ENDSTOPS_INVERTING = true; // set to true to invert the logic of the endstops. 
-const bool Z_ENDSTOPS_INVERTING = true; // set to true to invert the logic of the endstops. 
+const bool X_ENDSTOPS_INVERTING = false; // set to true to invert the logic of the endstops. 
+const bool Y_ENDSTOPS_INVERTING = false; // set to true to invert the logic of the endstops. 
+const bool Z_ENDSTOPS_INVERTING = false; // set to true to invert the logic of the endstops. 
 // For optos H21LOB set to true, for Mendel-Parts newer optos TCST2103 set to false
 
 //#define ENDSTOPS_ONLY_FOR_HOMING // If defined the endstops will only be used for homing
@@ -176,24 +181,26 @@ const bool Z_ENDSTOPS_INVERTING = true; // set to true to invert the logic of th
 #define X_ENABLE_ON 0
 #define Y_ENABLE_ON 0
 #define Z_ENABLE_ON 0
-#define E_ENABLE_ON 0
+#define E_ENABLE_ON 0 // For all extruders
 
 // Disables axis when it's not being used.
 #define DISABLE_X false
 #define DISABLE_Y false
-#define DISABLE_Z false
-#define DISABLE_E false
+#define DISABLE_Z true
+#define DISABLE_E false // For all extruders
 
 // Inverting axis direction
 //#define INVERT_X_DIR false    // for Mendel set to false, for Orca set to true
 //#define INVERT_Y_DIR true   // for Mendel set to true, for Orca set to false
 //#define INVERT_Z_DIR false    // for Mendel set to false, for Orca set to true
-//#define INVERT_E_DIR true   // for direct drive extruder v9 set to true, for geared extruder set to false
+//#define INVERT_E*_DIR true   // for direct drive extruder v9 set to true, for geared extruder set to false, used for all extruders
 
-#define INVERT_X_DIR true     // for Mendel set to false, for Orca set to true
+#define INVERT_X_DIR false    // for Mendel set to false, for Orca set to true
 #define INVERT_Y_DIR false    // for Mendel set to true, for Orca set to false
 #define INVERT_Z_DIR true     // for Mendel set to false, for Orca set to true
-#define INVERT_E_DIR false    // for direct drive extruder v9 set to true, for geared extruder set to false
+#define INVERT_E0_DIR false   // for direct drive extruder v9 set to true, for geared extruder set to false
+#define INVERT_E1_DIR true    // for direct drive extruder v9 set to true, for geared extruder set to false
+#define INVERT_E2_DIR false   // for direct drive extruder v9 set to true, for geared extruder set to false
 
 //// ENDSTOP SETTINGS:
 // Sets direction of endstops when homing; 1=MAX, -1=MIN
@@ -209,7 +216,7 @@ const bool Z_ENDSTOPS_INVERTING = true; // set to true to invert the logic of th
 
 //// MOVEMENT SETTINGS
 #define NUM_AXIS 4 // The axis order in all axis related arrays is X, Y, Z, E
-#define HOMING_FEEDRATE {50*60, 50*60, 4*60, 0}  // set the homing speeds (mm/min)
+#define HOMING_FEEDRATE {30*60, 30*60, 2*60, 0}  // set the homing speeds (mm/min)
 
 //homing hits the endstop, then retracts by this distance, before it tries to slowly bump again:
 #define X_HOME_RETRACT_MM 5 
@@ -223,8 +230,9 @@ const bool Z_ENDSTOPS_INVERTING = true; // set to true to invert the logic of th
 
 // default settings 
 
-#define DEFAULT_AXIS_STEPS_PER_UNIT   {78.7402,78.7402,200*8/3,760*1.1}                    // default steps per unit for ultimaker 
+//#define DEFAULT_AXIS_STEPS_PER_UNIT   {78.7402,78.7402,200*8/3,760*1.1}                    // default steps per unit for ultimaker 
 //#define DEFAULT_AXIS_STEPS_PER_UNIT   {40, 40, 3333.92, 67} //sells mendel with v9 extruder
+#define DEFAULT_AXIS_STEPS_PER_UNIT   {80.3232, 80.8900, 2284.7651, 757.2218} // SAE Prusa w/ Wade extruder
 #define DEFAULT_MAX_FEEDRATE          {500, 500, 5, 45}    // (mm/sec)    
 #define DEFAULT_MAX_ACCELERATION      {9000,9000,100,10000}    // X, Y, Z, E maximum start speed for accelerated moves. E default values are good for skeinforge 40+, for older versions raise them a lot.
 
@@ -290,7 +298,7 @@ const bool Z_ENDSTOPS_INVERTING = true; // set to true to invert the logic of th
 
 //LCD and SD support
 //#define ULTRA_LCD  //general lcd support, also 16x2
-//#define SDSUPPORT // Enable SD Card Support in Hardware Console
+#define SDSUPPORT // Enable SD Card Support in Hardware Console
 #define SD_FINISHED_STEPPERRELEASE true  //if sd support and the file is finished: disable steppers?
 
 //#define ULTIPANEL
diff --git a/Marlin/Marlin.h b/Marlin/Marlin.h
index 910cf46ad39dc0b9acc999e2c53a203c0a7838bf..626f61b6c84042ed7df977c345f843428cf0fe21 100644
--- a/Marlin/Marlin.h
+++ b/Marlin/Marlin.h
@@ -57,6 +57,8 @@ const prog_char echomagic[] PROGMEM ="echo:";
 
 #define SERIAL_ECHOPAIR(name,value) {SERIAL_ECHOPGM(name);SERIAL_ECHO(value);}
 
+// Macro for getting current active extruder
+#define ACTIVE_EXTRUDER (active_extruder)
 
 //things to write to serial from Programmemory. saves 400 to 2k of RAM.
 #define SerialprintPGM(x) serialprintPGM(MYPGM(x))
@@ -100,14 +102,31 @@ void manage_inactivity(byte debug);
   #define disable_z() ;
 #endif
 
-#if E_ENABLE_PIN > -1
-  #define  enable_e() WRITE(E_ENABLE_PIN, E_ENABLE_ON)
-  #define disable_e() WRITE(E_ENABLE_PIN,!E_ENABLE_ON)
+#if defined(E0_ENABLE_PIN) && (E0_ENABLE_PIN > -1)
+  #define enable_e0() WRITE(E0_ENABLE_PIN, E_ENABLE_ON)
+  #define disable_e0() WRITE(E0_ENABLE_PIN,!E_ENABLE_ON)
 #else
-  #define enable_e() ;
-  #define disable_e() ;
+  #define enable_e0()  /* nothing */
+  #define disable_e0() /* nothing */
 #endif
 
+#if (EXTRUDERS > 1) && defined(E1_ENABLE_PIN) && (E1_ENABLE_PIN > -1)
+  #define enable_e1() WRITE(E1_ENABLE_PIN, E_ENABLE_ON)
+  #define disable_e1() WRITE(E1_ENABLE_PIN,!E_ENABLE_ON)
+#else
+  #define enable_e1()  /* nothing */
+  #define disable_e1() /* nothing */
+#endif
+
+#if (EXTRUDERS > 2) && defined(E2_ENABLE_PIN) && (E2_ENABLE_PIN > -1)
+  #define enable_e2() WRITE(E2_ENABLE_PIN, E_ENABLE_ON)
+  #define disable_e2() WRITE(E2_ENABLE_PIN,!E_ENABLE_ON)
+#else
+  #define enable_e2()  /* nothing */
+  #define disable_e2() /* nothing */
+#endif
+
+
 enum AxisEnum {X_AXIS=0, Y_AXIS=1, Z_AXIS=2, E_AXIS=3};
 
 
@@ -131,4 +150,7 @@ extern bool axis_relative_modes[];
 extern float current_position[NUM_AXIS] ;
 extern float add_homeing[3];
 
+// Handling multiple extruders pins
+extern uint8_t active_extruder;
+
 #endif
diff --git a/Marlin/Marlin.pde b/Marlin/Marlin.pde
index 226a7d35df89973b382e4e36f270109772b60864..9b765ebd05cf8f2e19616396b9526f4f6aff1249 100644
--- a/Marlin/Marlin.pde
+++ b/Marlin/Marlin.pde
@@ -119,7 +119,6 @@
 //===========================================================================
 //=============================imported variables============================
 //===========================================================================
-extern float HeaterPower;
 
 
 //===========================================================================
@@ -133,8 +132,10 @@ bool axis_relative_modes[] = AXIS_RELATIVE_MODES;
 volatile int feedmultiply=100; //100->1 200->2
 int saved_feedmultiply;
 volatile bool feedmultiplychanged=false;
-float current_position[NUM_AXIS] = {  0.0, 0.0, 0.0, 0.0};
+float current_position[NUM_AXIS] = { 0.0, 0.0, 0.0, 0.0 };
 float add_homeing[3]={0,0,0};
+uint8_t active_extruder = 0;
+
 
 //===========================================================================
 //=============================private variables=============================
@@ -601,7 +602,6 @@ FORCE_INLINE void process_commands()
 
   else if(code_seen('M'))
   {
-
     switch( (int)code_value() ) 
     {
     case 17:
@@ -609,10 +609,12 @@ FORCE_INLINE void process_commands()
         enable_x(); 
         enable_y(); 
         enable_z(); 
-        enable_e(); 
+        enable_e0(); 
+        enable_e1(); 
+        enable_e2(); 
       break;
-    #ifdef SDSUPPORT
 
+#ifdef SDSUPPORT
     case 20: // M20 - list SD card
       SERIAL_PROTOCOLLNPGM("Begin file list");
       card.ls();
@@ -641,9 +643,8 @@ FORCE_INLINE void process_commands()
       card.pauseSDPrint();
       break;
     case 26: //M26 - Set SD index
-      if(card.cardOK && code_seen('S')){
+      if(card.cardOK && code_seen('S')) {
         card.setIndex(code_value_long());
-        
       }
       break;
     case 27: //M27 - Get SD status
@@ -657,16 +658,15 @@ FORCE_INLINE void process_commands()
         *(starpos-1) = '\0';
       }
       card.openFile(strchr_pointer+4,false);
-      
       break;
     case 29: //M29 - Stop SD write
       //processed in write to file routine above
       //card,saving = false;
       break;
-    #endif //SDSUPPORT
+#endif //SDSUPPORT
 
     case 30: //M30 take time since the start of the SD print or an M109 command
-    {
+      {
       stoptime=millis();
       char time[30];
       unsigned long t=(stoptime-starttime)/1000;
@@ -678,8 +678,8 @@ FORCE_INLINE void process_commands()
       SERIAL_ECHOLN(time);
       LCD_MESSAGE(time);
       autotempShutdown();
-    }
-    break;
+      }
+      break;
     case 42: //M42 -Change pin status via gcode
       if (code_seen('S'))
       {
@@ -723,7 +723,7 @@ FORCE_INLINE void process_commands()
       if (code_seen('S')) setTargetBed(code_value());
       break;
     case 105 : // M105
-      tmp_extruder = active_extruder;
+      tmp_extruder = ACTIVE_EXTRUDER;
       if(code_seen('T')) {
         tmp_extruder = code_value();
         if(tmp_extruder >= EXTRUDERS) {
@@ -733,21 +733,16 @@ FORCE_INLINE void process_commands()
           break;
         }
       }
-      #if (TEMP_0_PIN > -1) || (TEMP_2_PIN > -1)
+      #if (TEMP_0_PIN > -1)
         SERIAL_PROTOCOLPGM("ok T:");
-        SERIAL_PROTOCOL( degHotend(tmp_extruder)); 
-        #if TEMP_1_PIN > -1 
+        SERIAL_PROTOCOL(degHotend(tmp_extruder)); 
+        #if TEMP_BED_PIN > -1 
           SERIAL_PROTOCOLPGM(" B:");  
           SERIAL_PROTOCOL(degBed());
-        #endif //TEMP_1_PIN
+        #endif //TEMP_BED_PIN
       #else
         SERIAL_ERROR_START;
         SERIAL_ERRORLNPGM("No thermistors - no temp");
-      #endif
-      #ifdef PIDTEMP
-        SERIAL_PROTOCOLPGM(" @:");
-        SERIAL_PROTOCOL( HeaterPower); 
-       
       #endif
         SERIAL_PROTOCOLLN("");
       return;
@@ -790,19 +785,31 @@ FORCE_INLINE void process_commands()
         residencyStart = -1;
         /* continue to loop until we have reached the target temp   
           _and_ until TEMP_RESIDENCY_TIME hasn't passed since we reached it */
-        while((target_direction ? (isHeatingHotend(tmp_extruder)) : (isCoolingHotend(tmp_extruder))) ||
-                (residencyStart > -1 && (millis() - residencyStart) < TEMP_RESIDENCY_TIME*1000) ) {
+        while((residencyStart == -1) ||
+              (residencyStart > -1 && (millis() - residencyStart) < TEMP_RESIDENCY_TIME*1000) ) {
       #else
-        while ( target_direction ? (isHeatingHotend(tmp_extruder)) : (isCoolingHotend(tmp_extruder)&&(CooldownNoWait==false)) ) {
+        while ( target_direction ? (isHeatingHotend(tmp_extruder)) : (isCoolingHotend(tmp_extruder)&&(CooldownNoWait==false)) ) {
       #endif //TEMP_RESIDENCY_TIME
-        if( (millis() - codenum) > 1000 ) 
-        { //Print Temp Reading every 1 second while heating up/cooling down
-          SERIAL_PROTOCOLPGM("T:");
-          SERIAL_PROTOCOLLN( degHotend(tmp_extruder) ); 
-          codenum = millis();
-        }
-        manage_heater();
-        LCD_STATUS;
+          if( (millis() - codenum) > 1000 ) 
+          { //Print Temp Reading and remaining time every 1 second while heating up/cooling down
+            SERIAL_PROTOCOLPGM("T:");
+            SERIAL_PROTOCOLLN( degHotend(tmp_extruder) ); 
+            SERIAL_PROTOCOLPGM(" E:");
+            SERIAL_PROTOCOLLN( (int)tmp_extruder ); 
+            SERIAL_PROTOCOLPGM(" W:");
+            if(residencyStart > -1)
+            {
+               codenum = TEMP_RESIDENCY_TIME - ((millis() - residencyStart) / 1000);
+               SERIAL_PROTOCOLLN( codenum );
+            }
+            else 
+            {
+               SERIAL_PROTOCOLLN( "?" );
+            }
+            codenum = millis();
+          }
+          manage_heater();
+          LCD_STATUS;
         #ifdef TEMP_RESIDENCY_TIME
             /* start/restart the TEMP_RESIDENCY_TIME timer whenever we reach target temp for the first time
               or when current temp falls outside the hysteresis after target temp was reached */
@@ -818,8 +825,8 @@ FORCE_INLINE void process_commands()
         starttime=millis();
       }
       break;
-    case 190: // M190 - Wait bed for heater to reach target.
-    #if TEMP_1_PIN > -1
+    case 190: // M190 - Wait for bed heater to reach target.
+    #if TEMP_BED_PIN > -1
         LCD_MESSAGEPGM("Bed Heating.");
         if (code_seen('S')) setTargetBed(code_value());
         codenum = millis(); 
@@ -827,13 +834,13 @@ FORCE_INLINE void process_commands()
         {
           if( (millis()-codenum) > 1000 ) //Print Temp Reading every 1 second while heating up.
           {
-            float tt=degHotend0();
+            float tt=degHotend(ACTIVE_EXTRUDER);
             SERIAL_PROTOCOLPGM("T:");
-            SERIAL_PROTOCOLLN(tt );
-            SERIAL_PROTOCOLPGM("ok T:");
-            SERIAL_PROTOCOL(tt );
+            SERIAL_PROTOCOL(tt);
+            SERIAL_PROTOCOLPGM(" E:");
+            SERIAL_PROTOCOLLN( (int)tmp_extruder ); 
             SERIAL_PROTOCOLPGM(" B:");
-            SERIAL_PROTOCOLLN(degBed() ); 
+            SERIAL_PROTOCOLLN(degBed()); 
             codenum = millis(); 
           }
           manage_heater();
@@ -886,7 +893,9 @@ FORCE_INLINE void process_commands()
         if(code_seen('E')) {
           st_synchronize();
           LCD_MESSAGEPGM("Free Move");
-          disable_e();
+          disable_e0();
+          disable_e1();
+          disable_e2();
         }
         else {
           finishAndDisableSteppers();
@@ -1061,7 +1070,9 @@ FORCE_INLINE void process_commands()
 
     }
   }
-  else if(code_seen('T')) {
+
+  else if(code_seen('T')) 
+  {
     tmp_extruder = code_value();
     if(tmp_extruder >= EXTRUDERS) {
       SERIAL_ECHO_START;
@@ -1071,8 +1082,12 @@ FORCE_INLINE void process_commands()
     }
     else {
       active_extruder = tmp_extruder;
+      SERIAL_ECHO_START;
+      SERIAL_ECHO("Active Extruder: ");
+      SERIAL_PROTOCOLLN((int)active_extruder);
     }
   }
+
   else
   {
     SERIAL_ECHO_START;
@@ -1167,7 +1182,9 @@ void manage_inactivity(byte debug)
       disable_x(); 
       disable_y(); 
       disable_z(); 
-      disable_e(); 
+      disable_e0(); 
+      disable_e1(); 
+      disable_e2(); 
     }
   check_axes_activity();
 }
@@ -1179,7 +1196,9 @@ void kill()
   disable_x();
   disable_y();
   disable_z();
-  disable_e();
+  disable_e0();
+  disable_e1();
+  disable_e2();
   
   if(PS_ON_PIN > -1) pinMode(PS_ON_PIN,INPUT);
   SERIAL_ERROR_START;
diff --git a/Marlin/cardreader.pde b/Marlin/cardreader.pde
index 1eb19ba00c2858f713d5406740f07e058c5b94ac..4d3eac789d4a8f8581fe2042d7568378f15d853b 100644
--- a/Marlin/cardreader.pde
+++ b/Marlin/cardreader.pde
@@ -438,4 +438,4 @@ void CardReader::printingHasFinished()
  }
  autotempShutdown();
 }
-#endif //SDSUPPORT
\ No newline at end of file
+#endif //SDSUPPORT
diff --git a/Marlin/fastio.h b/Marlin/fastio.h
index 7fd42a6c8e833557b0631bd0f89f93c9557c03fe..634571e3a1041c175e4205d2fdadc917a3876355 100644
--- a/Marlin/fastio.h
+++ b/Marlin/fastio.h
@@ -44,9 +44,23 @@
 //	why double up on these macros? see http://gcc.gnu.org/onlinedocs/cpp/Stringification.html
 
 /// Read a pin wrapper
-#define		READ(IO)					_READ(IO)
+#define		READ(IO)				_READ(IO)
 /// Write to a pin wrapper
 #define		WRITE(IO, v)			_WRITE(IO, v)
+#if EXTRUDERS > 2
+  #define WRITE_E_STEP(v) { if(ACTIVE_EXTRUDER == 2) { WRITE(E2_STEP_PIN, v); } else { if(ACTIVE_EXTRUDER == 1) { WRITE(E1_STEP_PIN, v); } else { WRITE(E0_STEP_PIN, v); }}}
+  #define NORM_E_DIR() { if(ACTIVE_EXTRUDER == 2) { WRITE(E2_DIR_PIN, INVERT_E2_DIR); } else { if(ACTIVE_EXTRUDER == 1) { WRITE(E1_DIR_PIN, INVERT_E1_DIR); } else { WRITE(E0_DIR_PIN, INVERT_E0_DIR); }}}
+  #define REV_E_DIR() { if(ACTIVE_EXTRUDER == 2) { WRITE(E2_DIR_PIN, !INVERT_E2_DIR); } else { if(ACTIVE_EXTRUDER == 1) { WRITE(E1_DIR_PIN, !INVERT_E1_DIR); } else { WRITE(E0_DIR_PIN, !INVERT_E0_DIR); }}}
+#elif EXTRUDERS > 1
+  #define WRITE_E_STEP(v) { if(ACTIVE_EXTRUDER == 1) { WRITE(E1_STEP_PIN, v); } else { WRITE(E0_STEP_PIN, v); }}
+  #define NORM_E_DIR() { if(ACTIVE_EXTRUDER == 1) { WRITE(E1_DIR_PIN, INVERT_E1_DIR); } else { WRITE(E0_DIR_PIN, INVERT_E0_DIR); }}
+  #define REV_E_DIR() { if(ACTIVE_EXTRUDER == 1) { WRITE(E1_DIR_PIN, !INVERT_E1_DIR); } else { WRITE(E0_DIR_PIN, !INVERT_E0_DIR); }}
+#else
+  #define WRITE_E_STEP(v) WRITE(E0_STEP_PIN, v)
+  #define NORM_E_DIR() WRITE(E0_DIR_PIN, INVERT_E0_DIR)
+  #define REV_E_DIR() WRITE(E0_DIR_PIN, !INVERT_E0_DIR)
+#endif
+
 /// toggle a pin wrapper
 #define		TOGGLE(IO)				_TOGGLE(IO)
 
diff --git a/Marlin/pins.h b/Marlin/pins.h
index 60dd6e514819c388d0980dd9a424631320653340..2c2bc91445ad3d019c96448cb82fa52ad9cbcfe8 100644
--- a/Marlin/pins.h
+++ b/Marlin/pins.h
@@ -47,9 +47,9 @@
 #define Z_MIN_PIN          17
 #define Z_MAX_PIN          16
 
-#define E_STEP_PIN         11
-#define E_DIR_PIN          12
-#define E_ENABLE_PIN       -1
+#define E0_STEP_PIN         11
+#define E0_DIR_PIN          12
+#define E0_ENABLE_PIN       -1
 
 #define SDPOWER          -1
 #define SDSS          -1
@@ -59,9 +59,13 @@
 #define KILL_PIN           -1
 
 #define HEATER_0_PIN        6
-#define TEMP_0_PIN          0    // MUST USE ANALOG INPUT NUMBERING NOT DIGITAL OUTPUT NUMBERING!!!!!!!!!
 #define HEATER_1_PIN        -1
 #define HEATER_2_PIN        -1
+#define TEMP_0_PIN          0    // MUST USE ANALOG INPUT NUMBERING NOT DIGITAL OUTPUT NUMBERING!!!!!!!!!
+#define TEMP_1_PIN          -1   // MUST USE ANALOG INPUT NUMBERING NOT DIGITAL OUTPUT NUMBERING!!!!!!!!!
+#define TEMP_2_PIN          -1   // MUST USE ANALOG INPUT NUMBERING NOT DIGITAL OUTPUT NUMBERING!!!!!!!!!
+#define HEATER_BED_PIN      -1
+#define TEMP_BED_PIN        -1
 #endif
 
 
@@ -120,9 +124,9 @@
 #define Z_MIN_PIN           2
 #define Z_MAX_PIN           1
 
-#define E_STEP_PIN         12
-#define E_DIR_PIN          16
-#define E_ENABLE_PIN        3
+#define E0_STEP_PIN         12
+#define E0_DIR_PIN          16
+#define E0_ENABLE_PIN        3
 
 #define SDPOWER          -1
 #define SDSS          -1
@@ -132,9 +136,13 @@
 #define KILL_PIN           -1
 
 #define HEATER_0_PIN       14
+#define HEATER_1_PIN       -1
+#define HEATER_2_PIN       -1
 #define TEMP_0_PIN          4 //D27   // MUST USE ANALOG INPUT NUMBERING NOT DIGITAL OUTPUT NUMBERING!!!!!!!!!
-#define HEATER_1_PIN        -1
-#define HEATER_2_PIN        -1
+#define TEMP_1_PIN         -1 
+#define TEMP_2_PIN         -1 
+#define HEATER_BED_PIN     -1
+#define TEMP_BED_PIN       -1
 /*  Unused (1) (2) (3) 4 5 6 7 8 9 10 11 12 13 (14) (15) (16) 17 (18) (19) (20) (21) (22) (23) 24 (25) (26) (27) 28 (29) (30) (31)  */
 
 
@@ -171,9 +179,9 @@
 #define Z_MIN_PIN       30
 #define Z_MAX_PIN       31
 
-#define E_STEP_PIN      17
-#define E_DIR_PIN       16
-#define E_ENABLE_PIN    -1
+#define E0_STEP_PIN      17
+#define E0_DIR_PIN       16
+#define E0_ENABLE_PIN    -1
 
 #define SDPOWER          -1
 #define SDSS          4
@@ -194,11 +202,13 @@
 #define KILL_PIN        -1
 
 #define HEATER_0_PIN    -1
+#define HEATER_1_PIN    -1
+#define HEATER_2_PIN    -1
 #define TEMP_0_PIN      -1    // MUST USE ANALOG INPUT NUMBERING NOT DIGITAL OUTPUT NUMBERING!!!!!!!!!
-#define HEATER_1_PIN        -1
-#define HEATER_2_PIN        -1
-
-
+#define TEMP_1_PIN      -1    
+#define TEMP_2_PIN      -1    
+#define HEATER_BED_PIN  -1
+#define TEMP_BED_PIN    -1
 
 #endif
 
@@ -230,37 +240,43 @@
 #define X_DIR_PIN          55
 #define X_ENABLE_PIN       38
 #define X_MIN_PIN           3
-#define X_MAX_PIN          -1   //2 //Max endstops default to disabled "-1", set to commented value to enable.
+#define X_MAX_PIN           2   //2 //Max endstops default to disabled "-1", set to commented value to enable.
 
 #define Y_STEP_PIN         60
 #define Y_DIR_PIN          61
 #define Y_ENABLE_PIN       56
 #define Y_MIN_PIN          14
-#define Y_MAX_PIN          -1   //15
+#define Y_MAX_PIN          15   //15
 
 #define Z_STEP_PIN         46
 #define Z_DIR_PIN          48
 #define Z_ENABLE_PIN       62
 #define Z_MIN_PIN          18
-#define Z_MAX_PIN          -1   //19
+#define Z_MAX_PIN          19   //19
 
-#define E_STEP_PIN         26
-#define E_DIR_PIN          28
-#define E_ENABLE_PIN       24
+#define E0_STEP_PIN        26
+#define E0_DIR_PIN         28
+#define E0_ENABLE_PIN      24
+
+#define E1_STEP_PIN        36
+#define E1_DIR_PIN         34
+#define E1_ENABLE_PIN      30
 
 #define SDPOWER            -1
 #define SDSS               53
 #define LED_PIN            13
-#define FAN_PIN            9
+#define FAN_PIN            4
 #define PS_ON_PIN          12
 #define KILL_PIN           -1
 
-#define HEATER_0_PIN       10
-#define HEATER_1_PIN       8
-#define HEATER_2_PIN        -1
+#define HEATER_0_PIN       10   // EXTRUDER 1
+#define HEATER_1_PIN       9    // EXTRUDER 2
+#define HEATER_2_PIN       -1   // EXTRUDER 2
 #define TEMP_0_PIN         13   // ANALOG NUMBERING
-#define TEMP_1_PIN         14   // ANALOG NUMBERING
+#define TEMP_1_PIN         15   // ANALOG NUMBERING
 #define TEMP_2_PIN         -1   // ANALOG NUMBERING
+#define HEATER_BED_PIN     8    // BED
+#define TEMP_BED_PIN       14   // ANALOG NUMBERING
 
 
 #else // RAMPS_V_1_1 or RAMPS_V_1_2 as default
@@ -283,9 +299,9 @@
 #define Z_MIN_PIN          18
 #define Z_MAX_PIN          -1    //19
 
-#define E_STEP_PIN         32
-#define E_DIR_PIN          34
-#define E_ENABLE_PIN       30
+#define E0_STEP_PIN         32
+#define E0_DIR_PIN          34
+#define E0_ENABLE_PIN       30
 
 #define SDPOWER            48
 #define SDSS               53
@@ -297,18 +313,19 @@
 
 #ifdef RAMPS_V_1_0 // RAMPS_V_1_0
   #define HEATER_0_PIN     12    // RAMPS 1.0
-  #define HEATER_1_PIN     -1    // RAMPS 1.0
+  #define HEATER_BED_PIN   -1    // RAMPS 1.0
   #define FAN_PIN          11    // RAMPS 1.0
-
 #else // RAMPS_V_1_1 or RAMPS_V_1_2
   #define HEATER_0_PIN     10    // RAMPS 1.1
-  #define HEATER_1_PIN      8    // RAMPS 1.1
+  #define HEATER_BED_PIN    8    // RAMPS 1.1
   #define FAN_PIN           9    // RAMPS 1.1
 #endif
+#define HEATER_1_PIN        -1
 #define HEATER_2_PIN        -1
 #define TEMP_0_PIN          2    // MUST USE ANALOG INPUT NUMBERING NOT DIGITAL OUTPUT NUMBERING!!!!!!!!!
-#define TEMP_1_PIN          1    // MUST USE ANALOG INPUT NUMBERING NOT DIGITAL OUTPUT NUMBERING!!!!!!!!!
-#define TEMP_2_PIN          -1    // MUST USE ANALOG INPUT NUMBERING NOT DIGITAL OUTPUT NUMBERING!!!!!!!!!
+#define TEMP_1_PIN          -1   
+#define TEMP_2_PIN          -1   
+#define TEMP_BED_PIN        1    // MUST USE ANALOG INPUT NUMBERING NOT DIGITAL OUTPUT NUMBERING!!!!!!!!!
 #endif
 
 // SPI for Max6675 Thermocouple 
@@ -353,9 +370,9 @@
 #define Z_MIN_PIN           4
 #define Z_MAX_PIN          -1
 
-#define E_STEP_PIN         11
-#define E_DIR_PIN          12
-#define E_ENABLE_PIN       -1
+#define E0_STEP_PIN         11
+#define E0_DIR_PIN          12
+#define E0_ENABLE_PIN       -1
 
 #define SDPOWER          -1
 #define SDSS          -1
@@ -365,9 +382,13 @@
 #define KILL_PIN           -1
 
 #define HEATER_0_PIN        6
-#define TEMP_0_PIN          0    // MUST USE ANALOG INPUT NUMBERING NOT DIGITAL OUTPUT NUMBERING!!!!!!!!!
 #define HEATER_1_PIN        -1
 #define HEATER_2_PIN        -1
+#define TEMP_0_PIN          0    // MUST USE ANALOG INPUT NUMBERING NOT DIGITAL OUTPUT NUMBERING!!!!!!!!!
+#define TEMP_1_PIN          -1    
+#define TEMP_2_PIN          -1    
+#define HEATER_BED_PIN      -1
+#define TEMP_BED_PIN        -1
 
 #endif
 
@@ -404,19 +425,21 @@
     #define Z_MAX_PIN       -1
     
     //extruder pins
-    #define E_STEP_PIN      4     //Edited @ EJE Electronics 20100715
-    #define E_DIR_PIN       2     //Edited @ EJE Electronics 20100715
-    #define E_ENABLE_PIN    3     //Added @ EJE Electronics 20100715
+    #define E0_STEP_PIN      4    //Edited @ EJE Electronics 20100715
+    #define E0_DIR_PIN       2    //Edited @ EJE Electronics 20100715
+    #define E0_ENABLE_PIN    3    //Added @ EJE Electronics 20100715
     #define TEMP_0_PIN      5     //changed @ rkoeppl 20110410
+    #define TEMP_1_PIN      -1    //changed @ rkoeppl 20110410
+    #define TEMP_2_PIN      -1    //changed @ rkoeppl 20110410
     #define HEATER_0_PIN    14    //changed @ rkoeppl 20110410
-    #define HEATER_1_PIN    -1    //changed @ rkoeppl 20110410
-    #define HEATER_2_PIN        -1
+    #define HEATER_1_PIN    -1
+    #define HEATER_2_PIN    -1
+    #define HEATER_BED_PIN  -1    //changed @ rkoeppl 20110410
+    #define TEMP_BED_PIN    -1    //changed @ rkoeppl 20110410
     
     #define SDPOWER          -1
     #define SDSS          17
     #define LED_PIN         -1    //changed @ rkoeppl 20110410
-    #define TEMP_1_PIN      -1    //changed @ rkoeppl 20110410
-    #define TEMP_2_PIN      -1
     #define FAN_PIN         -1    //changed @ rkoeppl 20110410
     #define PS_ON_PIN       -1    //changed @ rkoeppl 20110410
     //our pin for debugging.
@@ -459,8 +482,8 @@
 #define Z_MIN_PIN          20
 #define Z_MAX_PIN          -1
 
-#define E_STEP_PIN         1
-#define E_DIR_PIN          0
+#define E0_STEP_PIN         1
+#define E0_DIR_PIN          0
 
 #define LED_PIN            -1
 
@@ -470,31 +493,33 @@
 #define KILL_PIN           -1
 
 #define HEATER_0_PIN       13 // (extruder)
+#define HEATER_1_PIN       -1
+#define HEATER_2_PIN       -1
 
 #ifdef SANGUINOLOLU_V_1_2
 
-#define HEATER_1_PIN       12 // (bed)
+#define HEATER_BED_PIN     12 // (bed)
 #define X_ENABLE_PIN       14
 #define Y_ENABLE_PIN       14
 #define Z_ENABLE_PIN       26
-#define E_ENABLE_PIN       14
+#define E0_ENABLE_PIN       14
 
 #else
 
-#define HEATER_1_PIN       14  // (bed)
+#define HEATER_BED_PIN       14  // (bed)
 #define X_ENABLE_PIN       -1
 #define Y_ENABLE_PIN       -1
 #define Z_ENABLE_PIN       -1
-#define E_ENABLE_PIN       -1
+#define E0_ENABLE_PIN       -1
 
 #endif
 
 #define TEMP_0_PIN          7   // MUST USE ANALOG INPUT NUMBERING NOT DIGITAL OUTPUT NUMBERING!!!!!!!!! (pin 33 extruder)
-#define TEMP_1_PIN          6   // MUST USE ANALOG INPUT NUMBERING NOT DIGITAL OUTPUT NUMBERING!!!!!!!!! (pin 34 bed)
+#define TEMP_1_PIN         -1
 #define TEMP_2_PIN         -1
+#define TEMP_BED_PIN        6   // MUST USE ANALOG INPUT NUMBERING NOT DIGITAL OUTPUT NUMBERING!!!!!!!!! (pin 34 bed)
 #define SDPOWER            -1
 #define SDSS               31
-#define HEATER_2_PIN       -1
 
 #endif
 
@@ -529,8 +554,8 @@
 #define Z_MAX_PIN 32
 #define Z_ENABLE_PIN 35
 
-#define HEATER_1_PIN 4 
-#define TEMP_1_PIN 11  
+#define HEATER_BED_PIN 4 
+#define TEMP_BED_PIN 11  
 
 #define EXTRUDER_0_STEP_PIN 43 
 #define EXTRUDER_0_DIR_PIN 45
@@ -543,14 +568,14 @@
 #define EXTRUDER_1_ENABLE_PIN 51
 #define EXTRUDER_1_HEATER_PIN 3
 #define EXTRUDER_1_TEMPERATURE_PIN 10 
-#define HEATER_2_PIN 51
-#define TEMP_2_PIN 3
+#define HEATER_1_PIN 51
+#define TEMP_1_PIN 3
 
 
 
-#define E_STEP_PIN         EXTRUDER_0_STEP_PIN
-#define E_DIR_PIN          EXTRUDER_0_DIR_PIN
-#define E_ENABLE_PIN       EXTRUDER_0_ENABLE_PIN
+#define E0_STEP_PIN         EXTRUDER_0_STEP_PIN
+#define E0_DIR_PIN          EXTRUDER_0_DIR_PIN
+#define E0_ENABLE_PIN       EXTRUDER_0_ENABLE_PIN
 
 #define SDPOWER            -1
 #define SDSS               53
@@ -655,20 +680,22 @@
 #define Z_MIN_PIN          15 
 #define Z_MAX_PIN          -1    
 
-#define E_STEP_PIN          6  
-#define E_DIR_PIN           7 
-#define E_ENABLE_PIN       19 
+#define E0_STEP_PIN         6  
+#define E0_DIR_PIN          7 
+#define E0_ENABLE_PIN       19 
 
 
 
 #define HEATER_0_PIN       21  // Extruder
-#define HEATER_1_PIN       20  // Bed
+#define HEATER_1_PIN       -1
 #define HEATER_2_PIN       -1
+#define HEATER_BED_PIN     20  // Bed
 #define FAN_PIN            22  // Fan   
 
 #define TEMP_0_PIN          7  // Extruder
-#define TEMP_1_PIN          6  // Bed
+#define TEMP_1_PIN         -1
 #define TEMP_2_PIN         -1
+#define TEMP_BED_PIN        6  // Bed
 
 #define SDPOWER            -1
 #define SDSS                8
@@ -690,6 +717,22 @@
 #endif
 
 //List of pins which to ignore when asked to change by gcode, 0 and 1 are RX and TX, do not mess with those!
-#define SENSITIVE_PINS {0, 1, X_STEP_PIN, X_DIR_PIN, X_ENABLE_PIN, X_MIN_PIN, X_MAX_PIN, Y_STEP_PIN, Y_DIR_PIN, Y_ENABLE_PIN, Y_MIN_PIN, Y_MAX_PIN, Z_STEP_PIN, Z_DIR_PIN, Z_ENABLE_PIN, Z_MIN_PIN, Z_MAX_PIN, E_STEP_PIN, E_DIR_PIN, E_ENABLE_PIN, LED_PIN, PS_ON_PIN, HEATER_0_PIN, HEATER_1_PIN, HEATER_2_PIN, FAN_PIN, TEMP_0_PIN, TEMP_1_PIN, TEMP_2_PIN}
-
+#define _E0_PINS E0_STEP_PIN, E0_DIR_PIN, E0_ENABLE_PIN
+#if EXTRUDERS == 3
+  #define _E1_PINS E1_STEP_PIN, E1_DIR_PIN, E1_ENABLE_PIN
+  #define _E2_PINS E2_STEP_PIN, E2_DIR_PIN, E2_ENABLE_PIN
+#elif EXTRUDERS == 2
+  #define _E1_PINS E1_STEP_PIN, E1_DIR_PIN, E1_ENABLE_PIN
+  #define _E2_PINS -1
+#elif EXTRUDERS == 1
+  #define _E1_PINS -1 
+  #define _E2_PINS -1
+#else
+  #error Unsupported number of extruders
+#endif
+#define SENSITIVE_PINS {0, 1, X_STEP_PIN, X_DIR_PIN, X_ENABLE_PIN, X_MIN_PIN, X_MAX_PIN, Y_STEP_PIN, Y_DIR_PIN, Y_ENABLE_PIN, Y_MIN_PIN, Y_MAX_PIN, Z_STEP_PIN, Z_DIR_PIN, Z_ENABLE_PIN, Z_MIN_PIN, Z_MAX_PIN, LED_PIN, PS_ON_PIN, \
+                        HEATER_0_PIN, HEATER_1_PIN, HEATER_2_PIN, \
+                        HEATER_BED_PIN, FAN_PIN,                  \
+                        _E0_PINS, _E1_PINS, _E2_PINS,             \
+                        TEMP_0_PIN, TEMP_1_PIN, TEMP_2_PIN, TEMP_BED_PIN }
 #endif
diff --git a/Marlin/planner.cpp b/Marlin/planner.cpp
index a8f41d3532edc4957fa5c48c012093e0f072fc99..d2179301f20ecd32c26c91256003fd380a33663e 100644
--- a/Marlin/planner.cpp
+++ b/Marlin/planner.cpp
@@ -56,9 +56,9 @@
 //#include <math.h>       
 //#include <stdlib.h>
 
-#include "Marlin.h"
 #include "Configuration.h"
 #include "pins.h"
+#include "Marlin.h"
 #include "fastio.h"
 #include "planner.h"
 #include "stepper.h"
@@ -81,8 +81,6 @@ float max_z_jerk;
 float mintravelfeedrate;
 unsigned long axis_steps_per_sqr_second[NUM_AXIS];
 
-uint8_t active_extruder = 0;
-
 // The current position of the tool in absolute steps
 long position[4];   //rescaled from extern when axis_steps_per_unit are changed by gcode
 static float previous_speed[4]; // Speed of previous path line segment
@@ -95,7 +93,6 @@ static float previous_nominal_speed; // Nominal speed of previous path line segm
     bool autotemp_enabled=false;
 #endif
 
-    
 //===========================================================================
 //=================semi-private variables, used in inline  functions    =====
 //===========================================================================
@@ -437,7 +434,7 @@ void check_axes_activity() {
   if((DISABLE_X) && (x_active == 0)) disable_x();
   if((DISABLE_Y) && (y_active == 0)) disable_y();
   if((DISABLE_Z) && (z_active == 0)) disable_z();
-  if((DISABLE_E) && (e_active == 0)) disable_e();
+  if((DISABLE_E) && (e_active == 0)) { disable_e0();disable_e1();disable_e2(); }
 }
 
 
@@ -496,15 +493,10 @@ void plan_buffer_line(const float &x, const float &y, const float &z, const floa
   if(block->steps_x != 0) enable_x();
   if(block->steps_y != 0) enable_y();
   if(block->steps_z != 0) enable_z();
-  if(extruder == 0) {
-    if(block->steps_e != 0) enable_e();
-  }
-  #if (EXTRUDERS > 1)
-  if(extruder == 1) {
-    if(block->steps_e != 0) enable_e1();
-  }
-  #endif
-  
+
+  // Enable all
+  if(block->steps_e != 0) { enable_e0();enable_e1();enable_e2(); }
+
   float delta_mm[4];
   delta_mm[X_AXIS] = (target[X_AXIS]-position[X_AXIS])/axis_steps_per_unit[X_AXIS];
   delta_mm[Y_AXIS] = (target[Y_AXIS]-position[Y_AXIS])/axis_steps_per_unit[Y_AXIS];
diff --git a/Marlin/planner.h b/Marlin/planner.h
index 53ac3d84470197c86f94ea7295c03c04fb4ecf65..66bd9025c375c64982335d449bc69385c5be6ad5 100644
--- a/Marlin/planner.h
+++ b/Marlin/planner.h
@@ -91,8 +91,6 @@ extern float max_z_jerk;
 extern float mintravelfeedrate;
 extern unsigned long axis_steps_per_sqr_second[NUM_AXIS];
 
-extern uint8_t active_extruder;
-
 #ifdef AUTOTEMP
     extern bool autotemp_enabled;
     extern float autotemp_max;
diff --git a/Marlin/stepper.cpp b/Marlin/stepper.cpp
index 9cf8ddd17650bdb7b271a2900532f269a913fc17..465ab89ddf4b2ca73ef5ea41a2fdc43a88bf5b21 100644
--- a/Marlin/stepper.cpp
+++ b/Marlin/stepper.cpp
@@ -24,9 +24,9 @@
 
 #include "stepper.h"
 #include "Configuration.h"
+#include "pins.h"
 #include "Marlin.h"
 #include "planner.h"
-#include "pins.h"
 #include "fastio.h"
 #include "temperature.h"
 #include "ultralcd.h"
@@ -41,7 +41,6 @@
 block_t *current_block;  // A pointer to the block currently being traced
 
 
-
 //===========================================================================
 //=============================private variables ============================
 //===========================================================================
@@ -419,11 +418,11 @@ ISR(TIMER1_COMPA_vect)
 
     #ifndef ADVANCE
       if ((out_bits & (1<<E_AXIS)) != 0) {  // -direction
-        WRITE(E_DIR_PIN,INVERT_E_DIR);
+        NORM_E_DIR();
         count_direction[E_AXIS]=-1;
       }
       else { // +direction
-        WRITE(E_DIR_PIN,!INVERT_E_DIR);
+        REV_E_DIR();
         count_direction[E_AXIS]=-1;
       }
     #endif //!ADVANCE
@@ -473,9 +472,9 @@ ISR(TIMER1_COMPA_vect)
       #ifndef ADVANCE
         counter_e += current_block->steps_e;
         if (counter_e > 0) {
-          WRITE(E_STEP_PIN, HIGH);
+          WRITE_E_STEP(HIGH);
           counter_e -= current_block->step_event_count;
-          WRITE(E_STEP_PIN, LOW);
+          WRITE_E_STEP(LOW);
           count_position[E_AXIS]+=count_direction[E_AXIS];
         }
       #endif //!ADVANCE
@@ -559,18 +558,18 @@ ISR(TIMER1_COMPA_vect)
     OCR0A = old_OCR0A;
     // Set E direction (Depends on E direction + advance)
     for(unsigned char i=0; i<4;) {
-      WRITE(E_STEP_PIN, LOW);
+      WRITE_E_STEP(LOW);
       if (e_steps == 0) break;
       i++;
       if (e_steps < 0) {
-        WRITE(E_DIR_PIN,INVERT_E_DIR);    
+        WRITE_E_DIR(INVERT_E_DIR);    
         e_steps++;
-        WRITE(E_STEP_PIN, HIGH);
+        WRITE_E_STEP(HIGH);
       } 
       else if (e_steps > 0) {
-        WRITE(E_DIR_PIN,!INVERT_E_DIR);
+        WRITE_E_DIR(!INVERT_E_DIR);
         e_steps--;
-        WRITE(E_STEP_PIN, HIGH);
+        WRITE_E_STEP(HIGH);
       }
     }
   }
@@ -578,7 +577,7 @@ ISR(TIMER1_COMPA_vect)
 
 void st_init()
 {
-    //Initialize Dir Pins
+  //Initialize Dir Pins
   #if X_DIR_PIN > -1
     SET_OUTPUT(X_DIR_PIN);
   #endif
@@ -588,8 +587,14 @@ void st_init()
   #if Z_DIR_PIN > -1 
     SET_OUTPUT(Z_DIR_PIN);
   #endif
-  #if E_DIR_PIN > -1 
-    SET_OUTPUT(E_DIR_PIN);
+  #if E0_DIR_PIN > -1 
+    SET_OUTPUT(E0_DIR_PIN);
+  #endif
+  #if defined(E1_DIR_PIN) && (E1_DIR_PIN > -1)
+    SET_OUTPUT(E1_DIR_PIN);
+  #endif
+  #if defined(E2_DIR_PIN) && (E2_DIR_PIN > -1)
+    SET_OUTPUT(E2_DIR_PIN);
   #endif
 
   //Initialize Enable Pins - steppers default to disabled.
@@ -606,9 +611,17 @@ void st_init()
     SET_OUTPUT(Z_ENABLE_PIN);
     if(!Z_ENABLE_ON) WRITE(Z_ENABLE_PIN,HIGH);
   #endif
-  #if (E_ENABLE_PIN > -1)
-    SET_OUTPUT(E_ENABLE_PIN);
-    if(!E_ENABLE_ON) WRITE(E_ENABLE_PIN,HIGH);
+  #if (E0_ENABLE_PIN > -1)
+    SET_OUTPUT(E0_ENABLE_PIN);
+    if(!E_ENABLE_ON) WRITE(E0_ENABLE_PIN,HIGH);
+  #endif
+  #if defined(E1_ENABLE_PIN) && (E1_ENABLE_PIN > -1)
+    SET_OUTPUT(E1_ENABLE_PIN);
+    if(!E_ENABLE_ON) WRITE(E1_ENABLE_PIN,HIGH);
+  #endif
+  #if defined(E2_ENABLE_PIN) && (E2_ENABLE_PIN > -1)
+    SET_OUTPUT(E2_ENABLE_PIN);
+    if(!E_ENABLE_ON) WRITE(E2_ENABLE_PIN,HIGH);
   #endif
 
   //endstops and pullups
@@ -669,8 +682,14 @@ void st_init()
   #if (Z_STEP_PIN > -1) 
     SET_OUTPUT(Z_STEP_PIN);
   #endif  
-  #if (E_STEP_PIN > -1) 
-    SET_OUTPUT(E_STEP_PIN);
+  #if (E0_STEP_PIN > -1) 
+    SET_OUTPUT(E0_STEP_PIN);
+  #endif  
+  #if defined(E1_STEP_PIN) && (E1_STEP_PIN > -1) 
+    SET_OUTPUT(E1_STEP_PIN);
+  #endif  
+  #if defined(E2_STEP_PIN) && (E2_STEP_PIN > -1) 
+    SET_OUTPUT(E2_STEP_PIN);
   #endif  
 
   // waveform generation = 0100 = CTC
@@ -749,5 +768,7 @@ void finishAndDisableSteppers()
   disable_x(); 
   disable_y(); 
   disable_z(); 
-  disable_e(); 
+  disable_e0(); 
+  disable_e1(); 
+  disable_e2(); 
 }
diff --git a/Marlin/temperature.cpp b/Marlin/temperature.cpp
index ac5aeaa3e58145cbe5688c23230fe6ea7afbf760..72b89597916d9a05ff06a845adbf556a75005d21 100644
--- a/Marlin/temperature.cpp
+++ b/Marlin/temperature.cpp
@@ -41,17 +41,14 @@
 //===========================================================================
 //=============================public variables============================
 //===========================================================================
-int target_raw[3] = {0, 0, 0};
-int current_raw[3] = {0, 0, 0};
-int heatingtarget_raw[3]= {0, 0, 0};
-
+int target_raw[EXTRUDERS] = { 0 };
+int target_raw_bed = 0;
+int current_raw[EXTRUDERS] = { 0 };
+int current_raw_bed = 0;
 
 #ifdef PIDTEMP
-  
-  // probably used external
-  float HeaterPower;
-  float pid_setpoint = 0.0;
-
+  // used external
+  float pid_setpoint[EXTRUDERS] = { 0.0 };
   
   float Kp=DEFAULT_Kp;
   float Ki=DEFAULT_Ki;
@@ -72,42 +69,74 @@ static unsigned long  previous_millis_bed_heater;
 
 #ifdef PIDTEMP
   //static cannot be external:
-  static float temp_iState = 0;
-  static float temp_dState = 0;
-  static float pTerm;
-  static float iTerm;
-  static float dTerm;
+  static float temp_iState[EXTRUDERS] = { 0 };
+  static float temp_dState[EXTRUDERS] = { 0 };
+  static float pTerm[EXTRUDERS];
+  static float iTerm[EXTRUDERS];
+  static float dTerm[EXTRUDERS];
   //int output;
-  static float pid_error;
-  static float temp_iState_min;
-  static float temp_iState_max;
- // static float pid_input; 
- // static float pid_output;
-  static bool pid_reset;
- 
+  static float pid_error[EXTRUDERS];
+  static float temp_iState_min[EXTRUDERS];
+  static float temp_iState_max[EXTRUDERS];
+  // static float pid_input[EXTRUDERS];
+  // static float pid_output[EXTRUDERS];
+  static bool pid_reset[EXTRUDERS];
 #endif //PIDTEMP
   
 #ifdef WATCHPERIOD
-  static int watch_raw[3] = {-1000,-1000,-1000};
+  static int watch_raw[EXTRUDERS] = { -1000 }; // the first value used for all
   static unsigned long watchmillis = 0;
 #endif //WATCHPERIOD
 
 // Init min and max temp with extreme values to prevent false errors during startup
-  static int minttemp_0   = 0;
-  static int maxttemp_0   = 16383;
-  //static int minttemp_1   = 0;
-  //static int maxttemp_1   = 16383;
+  static int minttemp[EXTRUDERS] = { 0 };
+  static int maxttemp[EXTRUDERS] = { 16383 }; // the first value used for all
   static int bed_minttemp = 0;
   static int bed_maxttemp = 16383;
+  static int heater_pin_map[EXTRUDERS] = { HEATER_0_PIN
+#if EXTRUDERS > 1
+                                         , HEATER_1_PIN
+#endif
+#if EXTRUDERS > 2
+                                         , HEATER_2_PIN
+#endif
+#if EXTRUDERS > 3
+  #error Unsupported number of extruders
+#endif
+  };
+  static void *heater_ttbl_map[EXTRUDERS] = { (void *)heater_0_temptable
+#if EXTRUDERS > 1
+                                            , (void *)heater_1_temptable
+#endif
+#if EXTRUDERS > 2
+                                            , (void *)heater_2_temptable
+#endif
+#if EXTRUDERS > 3
+  #error Unsupported number of extruders
+#endif
+  };
+  static int heater_ttbllen_map[EXTRUDERS] = { heater_0_temptable_len
+#if EXTRUDERS > 1
+                                             , heater_1_temptable_len
+#endif
+#if EXTRUDERS > 2
+                                             , heater_2_temptable_len
+#endif
+#if EXTRUDERS > 3
+  #error Unsupported number of extruders
+#endif
+  };
 
 //===========================================================================
-//=============================functions         ============================
+//=============================   functions      ============================
 //===========================================================================
   
 void updatePID()
 {
 #ifdef PIDTEMP
-  temp_iState_max = PID_INTEGRAL_DRIVE_MAX / Ki;
+  for(int e = 0; e < EXTRUDERS; e++) { 
+     temp_iState_max[e] = PID_INTEGRAL_DRIVE_MAX / Ki;  
+  }
 #endif
 }
   
@@ -119,92 +148,85 @@ void manage_heater()
   
   float pid_input;
   float pid_output;
+
   if(temp_meas_ready != true)   //better readability
     return; 
 
   CRITICAL_SECTION_START;
-    temp_meas_ready = false;
+  temp_meas_ready = false;
   CRITICAL_SECTION_END;
 
+  for(int e = 0; e < EXTRUDERS; e++) 
+  {
+
   #ifdef PIDTEMP
-    pid_input = analog2temp(current_raw[TEMPSENSOR_HOTEND_0]);
+    pid_input = analog2temp(current_raw[e], e);
 
     #ifndef PID_OPENLOOP
-        pid_error = pid_setpoint - pid_input;
-        if(pid_error > 10){
+        pid_error[e] = pid_setpoint[e] - pid_input;
+        if(pid_error[e] > 10) {
           pid_output = PID_MAX;
-          pid_reset = true;
+          pid_reset[e] = true;
         }
-        else if(pid_error < -10) {
+        else if(pid_error[e] < -10) {
           pid_output = 0;
-          pid_reset = true;
+          pid_reset[e] = true;
         }
         else {
-          if(pid_reset == true) {
-            temp_iState = 0.0;
-            pid_reset = false;
+          if(pid_reset[e] == true) {
+            temp_iState[e] = 0.0;
+            pid_reset[e] = false;
           }
-          pTerm = Kp * pid_error;
-          temp_iState += pid_error;
-          temp_iState = constrain(temp_iState, temp_iState_min, temp_iState_max);
-          iTerm = Ki * temp_iState;
+          pTerm[e] = Kp * pid_error[e];
+          temp_iState[e] += pid_error[e];
+          temp_iState[e] = constrain(temp_iState[e], temp_iState_min[e], temp_iState_max[e]);
+          iTerm[e] = Ki * temp_iState[e];
           //K1 defined in Configuration.h in the PID settings
           #define K2 (1.0-K1)
-          dTerm = (Kd * (pid_input - temp_dState))*K2 + (K1 * dTerm);
-          temp_dState = pid_input;
-//          #ifdef PID_ADD_EXTRUSION_RATE
-//            pTerm+=Kc*current_block->speed_e; //additional heating if extrusion speed is high
-//          #endif
-          pid_output = constrain(pTerm + iTerm - dTerm, 0, PID_MAX);
-          
+          dTerm[e] = (Kd * (pid_input - temp_dState[e]))*K2 + (K1 * dTerm[e]);
+          temp_dState[e] = pid_input;
+          pid_output = constrain(pTerm[e] + iTerm[e] - dTerm[e], 0, PID_MAX);
         }
     #endif //PID_OPENLOOP
     #ifdef PID_DEBUG
-     //SERIAL_ECHOLN(" PIDDEBUG Input "<<pid_input<<" Output "<<pid_output" pTerm "<<pTerm<<" iTerm "<<iTerm<<" dTerm "<<dTerm);  
+    SERIAL_ECHOLN(" PIDDEBUG "<<e<<": Input "<<pid_input<<" Output "<<pid_output" pTerm "<<pTerm[e]<<" iTerm "<<iTerm[e]<<" dTerm "<<dTerm[e]);  
     #endif //PID_DEBUG
-    HeaterPower=pid_output;
-    // Check if temperature is within the correct range
-    if((current_raw[TEMPSENSOR_HOTEND_0] > minttemp_0) && (current_raw[TEMPSENSOR_HOTEND_0] < maxttemp_0)) {
-      analogWrite(HEATER_0_PIN, pid_output);
-    }
-    else {
-      analogWrite(HEATER_0_PIN, 0);
-    }
-  #endif //PIDTEMP
-
-  #ifndef PIDTEMP
-    // Check if temperature is within the correct range
-    if((current_raw[TEMPSENSOR_HOTEND_0] > minttemp_0) && (current_raw[TEMPSENSOR_HOTEND_0] < maxttemp_0)) {
-      if(current_raw[TEMPSENSOR_HOTEND_0] >= target_raw[TEMPSENSOR_HOTEND_0]) {
-        WRITE(HEATER_0_PIN,LOW);
-      }
-      else {
-        WRITE(HEATER_0_PIN,HIGH);
-      }
+  #else /* PID off */
+    pid_output = 0;
+    if(current_raw[e] < target_raw[e]) {
+      pid_output = PID_MAX;
     }
-    else {
-      WRITE(HEATER_0_PIN,LOW);
-    }    
   #endif
+
+  // Check if temperature is within the correct range
+  if((current_raw[e] > minttemp[e]) && (current_raw[e] < maxttemp[e])) 
+  {
+    analogWrite(heater_pin_map[e], pid_output);
+  }
+  else {
+    analogWrite(heater_pin_map[e], 0);
+  }
+
+  } // End extruder for loop
     
   if(millis() - previous_millis_bed_heater < BED_CHECK_INTERVAL)
     return;
   previous_millis_bed_heater = millis();
   
-  #if TEMP_1_PIN > -1
+  #if TEMP_BED_PIN > -1
     // Check if temperature is within the correct range
-    if((current_raw[TEMPSENSOR_BED] > bed_minttemp) && (current_raw[TEMPSENSOR_BED] < bed_maxttemp)) {
-      if(current_raw[TEMPSENSOR_BED] >= target_raw[TEMPSENSOR_BED])
+    if((current_raw_bed > bed_minttemp) && (current_raw_bed < bed_maxttemp)) {
+      if(current_raw_bed >= target_raw_bed)
       {
-        WRITE(HEATER_1_PIN,LOW);
+        WRITE(HEATER_BED_PIN,LOW);
       }
       else 
       {
-        WRITE(HEATER_1_PIN,HIGH);
+        WRITE(HEATER_BED_PIN,HIGH);
       }
     }
     else {
-      WRITE(HEATER_1_PIN,LOW);
+      WRITE(HEATER_BED_PIN,LOW);
     }  
   #endif
 }
@@ -214,30 +236,38 @@ void manage_heater()
 // For a thermistor, it uses the RepRap thermistor temp table.
 // This is needed because PID in hydra firmware hovers around a given analog value, not a temp value.
 // This function is derived from inversing the logic from a portion of getTemperature() in FiveD RepRap firmware.
-int temp2analog(int celsius) {
-  #ifdef HEATER_0_USES_THERMISTOR
+int temp2analog(int celsius, uint8_t e) {
+  if(e >= EXTRUDERS)
+  {
+      SERIAL_ERROR_START;
+      SERIAL_ERROR((int)e);
+      SERIAL_ERRORLNPGM(" - Invalid extruder number!");
+      kill();
+  }
+  if(heater_ttbl_map[e] != 0)
+  {
     int raw = 0;
     byte i;
+    short (*tt)[][2] = (short (*)[][2])(heater_ttbl_map[e]);
 
-    for (i=1; i<NUMTEMPS_HEATER_0; i++)
+    for (i=1; i<heater_ttbllen_map[e]; i++)
     {
-      if (PGM_RD_W(heater_0_temptable[i][1]) < celsius)
+      if (PGM_RD_W((*tt)[i][1]) < celsius)
       {
-        raw = PGM_RD_W(heater_0_temptable[i-1][0]) + 
-          (celsius - PGM_RD_W(heater_0_temptable[i-1][1])) * 
-          (PGM_RD_W(heater_0_temptable[i][0]) - PGM_RD_W(heater_0_temptable[i-1][0])) /
-          (PGM_RD_W(heater_0_temptable[i][1]) - PGM_RD_W(heater_0_temptable[i-1][1]));  
+        raw = PGM_RD_W((*tt)[i-1][0]) + 
+          (celsius - PGM_RD_W((*tt)[i-1][1])) * 
+          (PGM_RD_W((*tt)[i][0]) - PGM_RD_W((*tt)[i-1][0])) /
+          (PGM_RD_W((*tt)[i][1]) - PGM_RD_W((*tt)[i-1][1]));  
         break;
       }
     }
 
     // Overflow: Set to last value in the table
-    if (i == NUMTEMPS_HEATER_0) raw = PGM_RD_W(heater_0_temptable[i-1][0]);
+    if (i == heater_ttbllen_map[e]) raw = PGM_RD_W((*tt)[i-1][0]);
 
     return (1023 * OVERSAMPLENR) - raw;
-  #elif defined HEATER_0_USES_AD595
-    return celsius * (1024.0 / (5.0 * 100.0) ) * OVERSAMPLENR;
-  #endif
+  }
+  return celsius * (1024.0 / (5.0 * 100.0) ) * OVERSAMPLENR;
 }
 
 // Takes bed temperature value as input and returns corresponding raw value. 
@@ -245,12 +275,11 @@ int temp2analog(int celsius) {
 // This is needed because PID in hydra firmware hovers around a given analog value, not a temp value.
 // This function is derived from inversing the logic from a portion of getTemperature() in FiveD RepRap firmware.
 int temp2analogBed(int celsius) {
-  #ifdef BED_USES_THERMISTOR
-
+#ifdef BED_USES_THERMISTOR
     int raw = 0;
     byte i;
     
-    for (i=1; i<BNUMTEMPS; i++)
+    for (i=1; i<bedtemptable_len; i++)
     {
       if (PGM_RD_W(bedtemptable[i][1]) < celsius)
       {
@@ -264,45 +293,52 @@ int temp2analogBed(int celsius) {
     }
 
     // Overflow: Set to last value in the table
-    if (i == BNUMTEMPS) raw = PGM_RD_W(bedtemptable[i-1][0]);
+    if (i == bedtemptable_len) raw = PGM_RD_W(bedtemptable[i-1][0]);
 
     return (1023 * OVERSAMPLENR) - raw;
-  #elif defined BED_USES_AD595
+#elif defined BED_USES_AD595
     return lround(celsius * (1024.0 * OVERSAMPLENR/ (5.0 * 100.0) ) );
-  #else
+#else
     #warning No heater-type defined for the bed.
-  #endif
-  return 0;
+    return 0;
+#endif
 }
 
 // Derived from RepRap FiveD extruder::getTemperature()
 // For hot end temperature measurement.
-float analog2temp(int raw) {
-  #ifdef HEATER_0_USES_THERMISTOR
+float analog2temp(int raw, uint8_t e) {
+  if(e >= EXTRUDERS)
+  {
+      SERIAL_ERROR_START;
+      SERIAL_ERROR((int)e);
+      SERIAL_ERRORLNPGM(" - Invalid extruder number !");
+      kill();
+  }
+  if(heater_ttbl_map[e] != 0)
+  {
     float celsius = 0;
     byte i;  
+    short (*tt)[][2] = (short (*)[][2])(heater_ttbl_map[e]);
+
     raw = (1023 * OVERSAMPLENR) - raw;
-    for (i=1; i<NUMTEMPS_HEATER_0; i++)
+    for (i=1; i<heater_ttbllen_map[e]; i++)
     {
-      if (PGM_RD_W(heater_0_temptable[i][0]) > raw)
+      if (PGM_RD_W((*tt)[i][0]) > raw)
       {
-        celsius  = PGM_RD_W(heater_0_temptable[i-1][1]) + 
-          (raw - PGM_RD_W(heater_0_temptable[i-1][0])) * 
-          (float)(PGM_RD_W(heater_0_temptable[i][1]) - PGM_RD_W(heater_0_temptable[i-1][1])) /
-          (float)(PGM_RD_W(heater_0_temptable[i][0]) - PGM_RD_W(heater_0_temptable[i-1][0]));
+        celsius = PGM_RD_W((*tt)[i-1][1]) + 
+          (raw - PGM_RD_W((*tt)[i-1][0])) * 
+          (float)(PGM_RD_W((*tt)[i][1]) - PGM_RD_W((*tt)[i-1][1])) /
+          (float)(PGM_RD_W((*tt)[i][0]) - PGM_RD_W((*tt)[i-1][0]));
         break;
       }
     }
 
     // Overflow: Set to last value in the table
-    if (i == NUMTEMPS_HEATER_0) celsius = PGM_RD_W(heater_0_temptable[i-1][1]);
+    if (i == heater_ttbllen_map[e]) celsius = PGM_RD_W((*tt)[i-1][1]);
 
     return celsius;
-  #elif defined HEATER_0_USES_AD595
-    return raw * ((5.0 * 100.0) / 1024.0) / OVERSAMPLENR;
-  #else
-    #error PLEASE DEFINE HEATER TYPE 
-  #endif
+  }
+  return raw * ((5.0 * 100.0) / 1024.0) / OVERSAMPLENR;
 }
 
 // Derived from RepRap FiveD extruder::getTemperature()
@@ -314,7 +350,7 @@ float analog2tempBed(int raw) {
 
     raw = (1023 * OVERSAMPLENR) - raw;
 
-    for (i=1; i<BNUMTEMPS; i++)
+    for (i=1; i<bedtemptable_len; i++)
     {
       if (PGM_RD_W(bedtemptable[i][0]) > raw)
       {
@@ -328,7 +364,7 @@ float analog2tempBed(int raw) {
     }
 
     // Overflow: Set to last value in the table
-    if (i == BNUMTEMPS) celsius = PGM_RD_W(bedtemptable[i-1][1]);
+    if (i == bedtemptable_len) celsius = PGM_RD_W(bedtemptable[i-1][1]);
 
     return celsius;
     
@@ -342,6 +378,19 @@ float analog2tempBed(int raw) {
 
 void tp_init()
 {
+  // Finish init of mult extruder arrays 
+  for(int e = 0; e < EXTRUDERS; e++) {
+    // populate with the first value 
+#ifdef WATCHPERIOD
+    watch_raw[e] = watch_raw[0];
+#endif
+    maxttemp[e] = maxttemp[0];
+#ifdef PIDTEMP
+    temp_iState_min[e] = 0.0;
+    temp_iState_max[e] = PID_INTEGRAL_DRIVE_MAX / Ki;
+#endif //PIDTEMP
+  }
+
   #if (HEATER_0_PIN > -1) 
     SET_OUTPUT(HEATER_0_PIN);
   #endif  
@@ -351,11 +400,12 @@ void tp_init()
   #if (HEATER_2_PIN > -1) 
     SET_OUTPUT(HEATER_2_PIN);
   #endif  
-
-  #ifdef PIDTEMP
-    temp_iState_min = 0.0;
-    temp_iState_max = PID_INTEGRAL_DRIVE_MAX / Ki;
-  #endif //PIDTEMP
+  #if (HEATER_BED_PIN > -1) 
+    SET_OUTPUT(HEATER_BED_PIN);
+  #endif  
+  #if (FAN_PIN > -1) 
+    SET_OUTPUT(FAN_PIN);
+  #endif  
 
   // Set analog inputs
   ADCSRA = 1<<ADEN | 1<<ADSC | 1<<ADIF | 0x07;
@@ -387,6 +437,14 @@ void tp_init()
        ADCSRB = 1<<MUX5;
     #endif
   #endif
+  #if (TEMP_BED_PIN > -1)
+    #if TEMP_BED_PIN < 8
+       DIDR0 |= 1<<TEMP_BED_PIN; 
+    #else
+       DIDR2 |= 1<<(TEMP_BED_PIN - 8); 
+       ADCSRB = 1<<MUX5;
+    #endif
+  #endif
   
   // Use timer0 for temperature measurement
   // Interleave temperature interrupt with millies interrupt
@@ -394,27 +452,34 @@ void tp_init()
   TIMSK0 |= (1<<OCIE0B);  
   
   // Wait for temperature measurement to settle
-  delay(200);
+  delay(250);
 
 #ifdef HEATER_0_MINTEMP
-  minttemp_0 = temp2analog(HEATER_0_MINTEMP);
+  minttemp[0] = temp2analog(HEATER_0_MINTEMP, 0);
 #endif //MINTEMP
 #ifdef HEATER_0_MAXTEMP
-  maxttemp_0 = temp2analog(HEATER_0_MAXTEMP);
+  maxttemp[0] = temp2analog(HEATER_0_MAXTEMP, 0);
 #endif //MAXTEMP
 
-#ifdef HEATER_1_MINTEMP
-  minttemp_1 = temp2analog(HEATER_1_MINTEMP);
-#endif //MINTEMP
-#ifdef HEATER_1_MAXTEMP
-  maxttemp_1 = temp2analog(HEATER_1_MAXTEMP);
-#endif //MAXTEMP
+#if (EXTRUDERS > 1) && defined(HEATER_1_MINTEMP)
+  minttemp[1] = temp2analog(HEATER_1_MINTEMP, 1);
+#endif // MINTEMP 1
+#if (EXTRUDERS > 1) && defined(HEATER_1_MAXTEMP)
+  maxttemp[1] = temp2analog(HEATER_1_MAXTEMP, 1);
+#endif //MAXTEMP 1
+
+#if (EXTRUDERS > 2) && defined(HEATER_2_MINTEMP)
+  minttemp[2] = temp2analog(HEATER_2_MINTEMP, 2);
+#endif //MINTEMP 2
+#if (EXTRUDERS > 2) && defined(HEATER_2_MAXTEMP)
+  maxttemp[2] = temp2analog(HEATER_2_MAXTEMP, 2);
+#endif //MAXTEMP 2
 
 #ifdef BED_MINTEMP
-  bed_minttemp = temp2analog(BED_MINTEMP);
+  bed_minttemp = temp2analogBed(BED_MINTEMP);
 #endif //BED_MINTEMP
 #ifdef BED_MAXTEMP
-  bed_maxttemp = temp2analog(BED_MAXTEMP);
+  bed_maxttemp = temp2analogBed(BED_MAXTEMP);
 #endif //BED_MAXTEMP
 }
 
@@ -423,15 +488,16 @@ void tp_init()
 void setWatch() 
 {  
 #ifdef WATCHPERIOD
-  if(isHeatingHotend0())
+  int t = 0;
+  for (int e = 0; e < EXTRUDERS; e++)
   {
-    watchmillis = max(1,millis());
-    watch_raw[TEMPSENSOR_HOTEND_0] = current_raw[TEMPSENSOR_HOTEND_0];
+    if(isHeatingHotend(e))
+    {
+      t = max(t,millis());
+      watch_raw[e] = current_raw[e];
+    } 
   }
-  else
-  {
-    watchmillis = 0;
-  } 
+  watchmillis = t;
 #endif 
 }
 
@@ -458,6 +524,13 @@ void disable_heater()
       digitalWrite(HEATER_2_PIN,LOW);
     #endif
   #endif 
+
+  #if TEMP_BED_PIN > -1
+    target_raw_bed=0;
+    #if HEATER_BED_PIN > -1  
+      digitalWrite(HEATER_BED_PIN,LOW);
+    #endif
+  #endif 
 }
 
 // Timer 0 is shared with millies
@@ -468,6 +541,7 @@ ISR(TIMER0_COMPB_vect)
   static unsigned long raw_temp_0_value = 0;
   static unsigned long raw_temp_1_value = 0;
   static unsigned long raw_temp_2_value = 0;
+  static unsigned long raw_temp_bed_value = 0;
   static unsigned char temp_state = 0;
   
   switch(temp_state) {
@@ -492,7 +566,26 @@ ISR(TIMER0_COMPB_vect)
       #endif
       temp_state = 2;
       break;
-    case 2: // Prepare TEMP_1
+    case 2: // Prepare TEMP_BED
+      #if (TEMP_BED_PIN > -1)
+        #if TEMP_BED_PIN > 7
+          ADCSRB = 1<<MUX5;
+        #endif
+        ADMUX = ((1 << REFS0) | (TEMP_BED_PIN & 0x07));
+        ADCSRA |= 1<<ADSC; // Start conversion
+      #endif
+      #ifdef ULTIPANEL
+        buttons_check();
+      #endif
+      temp_state = 3;
+      break;
+    case 3: // Measure TEMP_BED
+      #if (TEMP_BED_PIN > -1)
+        raw_temp_bed_value += ADC;
+      #endif
+      temp_state = 4;
+      break;
+    case 4: // Prepare TEMP_1
       #if (TEMP_1_PIN > -1)
         #if TEMP_1_PIN > 7
           ADCSRB = 1<<MUX5;
@@ -505,15 +598,15 @@ ISR(TIMER0_COMPB_vect)
       #ifdef ULTIPANEL
         buttons_check();
       #endif
-      temp_state = 3;
+      temp_state = 5;
       break;
-    case 3: // Measure TEMP_1
+    case 5: // Measure TEMP_1
       #if (TEMP_1_PIN > -1)
         raw_temp_1_value += ADC;
       #endif
-      temp_state = 4;
+      temp_state = 6;
       break;
-    case 4: // Prepare TEMP_2
+    case 6: // Prepare TEMP_2
       #if (TEMP_2_PIN > -1)
         #if TEMP_2_PIN > 7
           ADCSRB = 1<<MUX5;
@@ -526,9 +619,9 @@ ISR(TIMER0_COMPB_vect)
       #ifdef ULTIPANEL
         buttons_check();
       #endif
-      temp_state = 5;
+      temp_state = 7;
       break;
-    case 5: // Measure TEMP_2
+    case 7: // Measure TEMP_2
       #if (TEMP_2_PIN > -1)
         raw_temp_2_value += ADC;
       #endif
@@ -541,24 +634,34 @@ ISR(TIMER0_COMPB_vect)
       break;
   }
     
-  if(temp_count >= 16) // 6 ms * 16 = 96ms.
+  if(temp_count >= 16) // 8 ms * 16 = 128ms.
   {
     #ifdef HEATER_0_USES_AD595
       current_raw[0] = raw_temp_0_value;
     #else
       current_raw[0] = 16383 - raw_temp_0_value;
     #endif
-    
+
+#if EXTRUDERS > 1    
     #ifdef HEATER_1_USES_AD595
+      current_raw[1] = raw_temp_1_value;
+    #else
+      current_raw[1] = 16383 - raw_temp_1_value;
+    #endif
+#endif
+    
+#if EXTRUDERS > 2
+    #ifdef HEATER_2_USES_AD595
       current_raw[2] = raw_temp_2_value;
     #else
       current_raw[2] = 16383 - raw_temp_2_value;
     #endif
+#endif
     
     #ifdef BED_USES_AD595
-      current_raw[1] = raw_temp_1_value;
+      current_raw_bed = raw_temp_bed_value;
     #else
-      current_raw[1] = 16383 - raw_temp_1_value;
+      current_raw_bed = 16383 - raw_temp_bed_value;
     #endif
     
     temp_meas_ready = true;
@@ -566,77 +669,36 @@ ISR(TIMER0_COMPB_vect)
     raw_temp_0_value = 0;
     raw_temp_1_value = 0;
     raw_temp_2_value = 0;
-    #ifdef HEATER_0_MAXTEMP
-      #if (HEATER_0_PIN > -1)
-        if(current_raw[TEMPSENSOR_HOTEND_0] >= maxttemp_0) {
-          target_raw[TEMPSENSOR_HOTEND_0] = 0;
-          digitalWrite(HEATER_0_PIN, 0);
+    raw_temp_bed_value = 0;
+
+    for(int e = 0; e < EXTRUDERS; e++) {
+       if(current_raw[e] >= maxttemp[e]) {
+          target_raw[e] = 0;
+          digitalWrite(heater_pin_map[e], 0);
           SERIAL_ERROR_START;
-          SERIAL_ERRORLNPGM("Temperature extruder 0 switched off. MAXTEMP triggered !!");
+          SERIAL_ERRORLN((int)e);
+          SERIAL_ERRORLNPGM(": Extruder switched off. MAXTEMP triggered !");
           kill();
-        }
-      #endif
-    #endif
-  #ifdef HEATER_1_MAXTEMP
-    #if (HEATER_1_PIN > -1)
-      if(current_raw[TEMPSENSOR_HOTEND_1] >= maxttemp_1) {
-        target_raw[TEMPSENSOR_HOTEND_1] = 0;
-        digitalWrite(HEATER_2_PIN, 0);
-        SERIAL_ERROR_START;
-        SERIAL_ERRORLNPGM("Temperature extruder 1 switched off. MAXTEMP triggered !!");
-        kill();
-      }
-    #endif
-  #endif //MAXTEMP
-  
-  #ifdef HEATER_0_MINTEMP
-    #if (HEATER_0_PIN > -1)
-      if(current_raw[TEMPSENSOR_HOTEND_0] <= minttemp_0) {
-        target_raw[TEMPSENSOR_HOTEND_0] = 0;
-        digitalWrite(HEATER_0_PIN, 0);
-        SERIAL_ERROR_START;
-        SERIAL_ERRORLNPGM("Temperature extruder 0 switched off. MINTEMP triggered !!");
-        kill();
-      }
-    #endif
-  #endif
-  
-  #ifdef HEATER_1_MINTEMP
-    #if (HEATER_2_PIN > -1)
-      if(current_raw[TEMPSENSOR_HOTEND_1] <= minttemp_1) {
-        target_raw[TEMPSENSOR_HOTEND_1] = 0;
-        digitalWrite(HEATER_2_PIN, 0);
-        SERIAL_ERROR_START;
-        SERIAL_ERRORLNPGM("Temperature extruder 1 switched off. MINTEMP triggered !!");
-        kill();
-      }
-    #endif
-  #endif //MAXTEMP
-  
-  #ifdef BED_MINTEMP
-    #if (HEATER_1_PIN > -1)
-      if(current_raw[1] <= bed_minttemp) {
-        target_raw[1] = 0;
-        digitalWrite(HEATER_1_PIN, 0);
-        SERIAL_ERROR_START;
-        SERIAL_ERRORLNPGM("Temperatur heated bed switched off. MINTEMP triggered !!");
-        kill();
-      }
-    #endif
-  #endif
+       }
+       if(current_raw[e] <= minttemp[e]) {
+          target_raw[e] = 0;
+          digitalWrite(heater_pin_map[e], 0);
+          SERIAL_ERROR_START;
+          SERIAL_ERRORLN(e);
+          SERIAL_ERRORLNPGM(": Extruder switched off. MINTEMP triggered !");
+          kill();
+       }
+    }
   
-  #ifdef BED_MAXTEMP
-    #if (HEATER_1_PIN > -1)
-      if(current_raw[1] >= bed_maxttemp) {
-        target_raw[1] = 0;
-        digitalWrite(HEATER_1_PIN, 0);
-        SERIAL_ERROR_START;
-        SERIAL_ERRORLNPGM("Temperature heated bed switched off. MAXTEMP triggered !!");
-        kill();
-      }
-    #endif
-  #endif
+#if defined(BED_MAXTEMP) && (HEATER_BED_PIN > -1)
+    if(current_raw_bed >= bed_maxttemp) {
+       target_raw_bed = 0;
+       digitalWrite(HEATER_BED_PIN, 0);
+       SERIAL_ERROR_START;
+       SERIAL_ERRORLNPGM("Temperature heated bed switched off. MAXTEMP triggered !!");
+       kill();
+    }
+#endif
   }
 }
 
-
diff --git a/Marlin/temperature.h b/Marlin/temperature.h
index 623f890bb04792fa88f051bbb722239604dd9b54..15bc8a8352d97e7c46d560ac53b2158af96f90e4 100644
--- a/Marlin/temperature.h
+++ b/Marlin/temperature.h
@@ -31,95 +31,110 @@
 void tp_init();  //initialise the heating
 void manage_heater(); //it is critical that this is called periodically.
 
-
-enum TempSensor {TEMPSENSOR_HOTEND_0=0,TEMPSENSOR_BED=1, TEMPSENSOR_HOTEND_1=2};
-
 //low leven conversion routines
 // do not use this routines and variables outsie of temperature.cpp
-int temp2analog(int celsius);
+int temp2analog(int celsius, uint8_t e);
 int temp2analogBed(int celsius);
-float analog2temp(int raw);
+float analog2temp(int raw, uint8_t e);
 float analog2tempBed(int raw);
-extern int target_raw[3];  
-extern int heatingtarget_raw[3];
-extern int current_raw[3];
+extern int target_raw[EXTRUDERS];  
+extern int heatingtarget_raw[EXTRUDERS];  
+extern int current_raw[EXTRUDERS];
+extern int target_raw_bed;
+extern int current_raw_bed;
 extern float Kp,Ki,Kd,Kc;
 
 #ifdef PIDTEMP
-  extern float pid_setpoint ;
+  extern float pid_setpoint[EXTRUDERS];
 #endif
   
 #ifdef WATCHPERIOD
-  extern int watch_raw[3] ;
+  extern int watch_raw[EXTRUDERS] ;
   extern unsigned long watchmillis;
 #endif
 
 
-
 //high level conversion routines, for use outside of temperature.cpp
 //inline so that there is no performance decrease.
 //deg=degreeCelsius
 
-FORCE_INLINE float degHotend0(){  return analog2temp(current_raw[TEMPSENSOR_HOTEND_0]);};
-FORCE_INLINE float degHotend1(){  return analog2temp(current_raw[TEMPSENSOR_HOTEND_1]);};
-FORCE_INLINE float degBed() {  return analog2tempBed(current_raw[TEMPSENSOR_BED]);};
-FORCE_INLINE float degHotend(uint8_t extruder){  
-  if(extruder == 0) return analog2temp(current_raw[TEMPSENSOR_HOTEND_0]);
-  if(extruder == 1) return analog2temp(current_raw[TEMPSENSOR_HOTEND_1]);
+FORCE_INLINE float degHotend(uint8_t extruder) {  
+  return analog2temp(current_raw[extruder], extruder);
 };
 
-FORCE_INLINE float degTargetHotend0() {  return analog2temp(target_raw[TEMPSENSOR_HOTEND_0]);};
-FORCE_INLINE float degTargetHotend1() {  return analog2temp(target_raw[TEMPSENSOR_HOTEND_1]);};
-FORCE_INLINE float degTargetHotend(uint8_t extruder){  
-  if(extruder == 0) return analog2temp(target_raw[TEMPSENSOR_HOTEND_0]);
-  if(extruder == 1) return analog2temp(target_raw[TEMPSENSOR_HOTEND_1]);
+FORCE_INLINE float degBed() {
+  return analog2tempBed(current_raw_bed);
 };
 
-FORCE_INLINE float degTargetBed() {   return analog2tempBed(target_raw[TEMPSENSOR_BED]);};
+FORCE_INLINE float degTargetHotend(uint8_t extruder) {  
+  return analog2temp(target_raw[extruder], extruder);
+};
 
-FORCE_INLINE void setTargetHotend0(const float &celsius) 
-{  
-  target_raw[TEMPSENSOR_HOTEND_0]=temp2analog(celsius);
-  heatingtarget_raw[TEMPSENSOR_HOTEND_0]=temp2analog(celsius-HEATING_EARLY_FINISH_DEG_OFFSET);
-  #ifdef PIDTEMP
-    pid_setpoint = celsius;
-  #endif //PIDTEMP
+FORCE_INLINE float degTargetBed() {   
+  return analog2tempBed(target_raw_bed);
 };
-FORCE_INLINE void setTargetHotend1(const float &celsius) {  target_raw[TEMPSENSOR_HOTEND_1]=temp2analog(celsius);};
-FORCE_INLINE void setTargetHotend(const float &celcius, uint8_t extruder){  
-  if(extruder == 0) setTargetHotend0(celcius);
-  if(extruder == 1) setTargetHotend1(celcius);
+
+FORCE_INLINE void setTargetHotend(const float &celsius, uint8_t extruder) {  
+  target_raw[extruder] = temp2analog(celsius, extruder);
+#ifdef PIDTEMP
+  pid_setpoint[extruder] = celsius;
+#endif //PIDTEMP
+};
+
+FORCE_INLINE void setTargetBed(const float &celsius) {  
+  target_raw_bed = temp2analogBed(celsius);
 };
-FORCE_INLINE void setTargetBed(const float &celsius)     {  target_raw[TEMPSENSOR_BED     ]=temp2analogBed(celsius);};
 
-FORCE_INLINE bool isHeatingHotend0() {return heatingtarget_raw[TEMPSENSOR_HOTEND_0] > current_raw[TEMPSENSOR_HOTEND_0];};
-FORCE_INLINE bool isHeatingHotend1() {return target_raw[TEMPSENSOR_HOTEND_1] > current_raw[TEMPSENSOR_HOTEND_1];};
 FORCE_INLINE bool isHeatingHotend(uint8_t extruder){  
-  if(extruder == 0) return heatingtarget_raw[TEMPSENSOR_HOTEND_0] > current_raw[TEMPSENSOR_HOTEND_0];
-  if(extruder == 1) return target_raw[TEMPSENSOR_HOTEND_1] > current_raw[TEMPSENSOR_HOTEND_1];
-  return false; 
+  return target_raw[extruder] > current_raw[extruder];
+};
+
+FORCE_INLINE bool isHeatingBed() {
+  return target_raw_bed > current_raw_bed;
 };
-FORCE_INLINE bool isHeatingBed() {return target_raw[TEMPSENSOR_BED] > current_raw[TEMPSENSOR_BED];};
-
-FORCE_INLINE bool isCoolingHotend0() {return target_raw[TEMPSENSOR_HOTEND_0] < current_raw[TEMPSENSOR_HOTEND_0];};
-FORCE_INLINE bool isCoolingHotend1() {return target_raw[TEMPSENSOR_HOTEND_1] < current_raw[TEMPSENSOR_HOTEND_1];};
-FORCE_INLINE bool isCoolingHotend(uint8_t extruder){  
-  if(extruder == 0) return target_raw[TEMPSENSOR_HOTEND_0] < current_raw[TEMPSENSOR_HOTEND_0];
-  if(extruder == 1) return target_raw[TEMPSENSOR_HOTEND_1] < current_raw[TEMPSENSOR_HOTEND_1];
-  return false; 
+
+FORCE_INLINE bool isCoolingHotend(uint8_t extruder) {  
+  return target_raw[extruder] < current_raw[extruder];
 };
-FORCE_INLINE bool isCoolingBed() {return target_raw[TEMPSENSOR_BED] < current_raw[TEMPSENSOR_BED];};
+
+FORCE_INLINE bool isCoolingBed() {
+  return target_raw_bed < current_raw_bed;
+};
+
+#define degHotend0() degHotend(0)
+#define degTargetHotend0() degTargetHotend(0)
+#define setTargetHotend0(_celsius) setTargetHotend((_celsius), 0)
+#define isHeatingHotend0() isHeatingHotend(0)
+#define isCoolingHotend0() isCoolingHotend(0)
+#if EXTRUDERS > 1
+#define degHotend1() degHotend(1)
+#define degTargetHotend1() degTargetHotend(1)
+#define setTargetHotend1(_celsius) setTargetHotend((_celsius), 1)
+#define isHeatingHotend1() isHeatingHotend(1)
+#define isCoolingHotend1() isCoolingHotend(1)
+#endif
+#if EXTRUDERS > 2
+#define degHotend2() degHotend(2)
+#define degTargetHotend2() degTargetHotend(2)
+#define setTargetHotend2(_celsius) setTargetHotend((_celsius), 2)
+#define isHeatingHotend2() isHeatingHotend(2)
+#define isCoolingHotend2() isCoolingHotend(2)
+#endif
+#if EXTRUDERS > 3
+#error Invalid number of extruders
+#endif
 
 FORCE_INLINE void autotempShutdown(){
  #ifdef AUTOTEMP
  if(autotemp_enabled)
  {
   autotemp_enabled=false;
-  if(degTargetHotend0()>autotemp_min)
-    setTargetHotend0(0);
+  if(degTargetHotend(ACTIVE_EXTRUDER)>autotemp_min)
+    setTargetHotend(0,ACTIVE_EXTRUDER);
  }
  #endif
 }
+
 void disable_heater();
 void setWatch();
 void updatePID();
diff --git a/Marlin/thermistortables.h b/Marlin/thermistortables.h
index 22d9f02487a96f4c0383656f2c114b362d1d432d..30f5b62ac703a720dfb8b6f779b457bfadba41fb 100644
--- a/Marlin/thermistortables.h
+++ b/Marlin/thermistortables.h
@@ -5,10 +5,9 @@
 
 #define OVERSAMPLENR 16
 
-#if (THERMISTORHEATER_0 == 1) || (THERMISTORHEATER_1 == 1) || (THERMISTORBED == 1) //100k bed thermistor
+#if (THERMISTORHEATER_0 == 1) || (THERMISTORHEATER_1 == 1)  || (THERMISTORHEATER_2 == 1) || (THERMISTORBED == 1) //100k bed thermistor
 
-#define NUMTEMPS_1 61
-const short temptable_1[NUMTEMPS_1][2] PROGMEM = {
+const short temptable_1[][2] PROGMEM = {
 {       23*OVERSAMPLENR ,       300     },
 {       25*OVERSAMPLENR ,       295     },
 {       27*OVERSAMPLENR ,       290     },
@@ -72,9 +71,8 @@ const short temptable_1[NUMTEMPS_1][2] PROGMEM = {
 {       1008*OVERSAMPLENR       ,       0       } //safety
 };
 #endif
-#if (THERMISTORHEATER_0 == 2) || (THERMISTORHEATER_1 == 2) || (THERMISTORBED == 2) //200k bed thermistor
-#define NUMTEMPS_2 21
-const short temptable_2[NUMTEMPS_2][2] PROGMEM = {
+#if (THERMISTORHEATER_0 == 2) || (THERMISTORHEATER_1 == 2) || (THERMISTORHEATER_2 == 2) || (THERMISTORBED == 2) //200k bed thermistor
+const short temptable_2[][2] PROGMEM = {
    {1*OVERSAMPLENR, 848},
    {54*OVERSAMPLENR, 275},
    {107*OVERSAMPLENR, 228},
@@ -99,9 +97,8 @@ const short temptable_2[NUMTEMPS_2][2] PROGMEM = {
 };
 
 #endif
-#if (THERMISTORHEATER_0 == 3) || (THERMISTORHEATER_1 == 3) || (THERMISTORBED == 3) //mendel-parts
-#define NUMTEMPS_3 28
-const short temptable_3[NUMTEMPS_3][2] PROGMEM = {
+#if (THERMISTORHEATER_0 == 3) || (THERMISTORHEATER_1 == 3) || (THERMISTORHEATER_2 == 3) || (THERMISTORBED == 3) //mendel-parts
+const short temptable_3[][2] PROGMEM = {
                 {1*OVERSAMPLENR,864},
                 {21*OVERSAMPLENR,300},
                 {25*OVERSAMPLENR,290},
@@ -133,10 +130,8 @@ const short temptable_3[NUMTEMPS_3][2] PROGMEM = {
         };
 
 #endif
-#if (THERMISTORHEATER_0 == 4) || (THERMISTORHEATER_1 == 4) || (THERMISTORBED == 4) //10k thermistor
-
-#define NUMTEMPS_4 20
-const short temptable_4[NUMTEMPS_4][2] PROGMEM = {
+#if (THERMISTORHEATER_0 == 4) || (THERMISTORHEATER_1 == 4) || (THERMISTORHEATER_2 == 4) || (THERMISTORBED == 4) //10k thermistor
+const short temptable_4[][2] PROGMEM = {
    {1*OVERSAMPLENR, 430},
    {54*OVERSAMPLENR, 137},
    {107*OVERSAMPLENR, 107},
@@ -160,10 +155,8 @@ const short temptable_4[NUMTEMPS_4][2] PROGMEM = {
 };
 #endif
 
-#if (THERMISTORHEATER_0 == 5) || (THERMISTORHEATER_1 == 5) || (THERMISTORBED == 5) //100k ParCan thermistor (104GT-2)
-
-#define NUMTEMPS_5 61
-const short temptable_5[NUMTEMPS_5][2] PROGMEM = {
+#if (THERMISTORHEATER_0 == 5) || (THERMISTORHEATER_1 == 5) || (THERMISTORHEATER_2 == 5) || (THERMISTORBED == 5) //100k ParCan thermistor (104GT-2)
+const short temptable_5[][2] PROGMEM = {
 {1*OVERSAMPLENR, 713},
 {18*OVERSAMPLENR, 316},
 {35*OVERSAMPLENR, 266},
@@ -228,9 +221,8 @@ const short temptable_5[NUMTEMPS_5][2] PROGMEM = {
 };
 #endif
 
-#if (THERMISTORHEATER_0 == 6) || (THERMISTORHEATER_1 == 6) || (THERMISTORBED == 6) // 100k Epcos thermistor
-#define NUMTEMPS_6 36
-const short temptable_6[NUMTEMPS_6][2] PROGMEM = {
+#if (THERMISTORHEATER_0 == 6) || (THERMISTORHEATER_1 == 6) || (THERMISTORHEATER_2 == 6) || (THERMISTORBED == 6) // 100k Epcos thermistor
+const short temptable_6[][2] PROGMEM = {
    {28*OVERSAMPLENR, 250},
    {31*OVERSAMPLENR, 245},
    {35*OVERSAMPLENR, 240},
@@ -270,9 +262,8 @@ const short temptable_6[NUMTEMPS_6][2] PROGMEM = {
 };
 #endif
 
-#if (THERMISTORHEATER_0 == 7) || (THERMISTORHEATER_1 == 7) || (THERMISTORBED == 7) // 100k Honeywell 135-104LAG-J01
-#define NUMTEMPS_7 54
-const short temptable_7[NUMTEMPS_7][2] PROGMEM = {
+#if (THERMISTORHEATER_0 == 7) || (THERMISTORHEATER_1 == 7) || (THERMISTORHEATER_2 == 7) || (THERMISTORBED == 7) // 100k Honeywell 135-104LAG-J01
+const short temptable_7[][2] PROGMEM = {
    {46*OVERSAMPLENR, 270},
    {50*OVERSAMPLENR, 265},
    {54*OVERSAMPLENR, 260},
@@ -330,82 +321,52 @@ const short temptable_7[NUMTEMPS_7][2] PROGMEM = {
 };
 #endif
 
+#define _TT_NAME(_N) temptable_ ## _N
+#define TT_NAME(_N) _TT_NAME(_N)
 
-
-#if THERMISTORHEATER_0 == 1
-#define NUMTEMPS_HEATER_0 NUMTEMPS_1
-#define heater_0_temptable temptable_1
-#elif THERMISTORHEATER_0 == 2
-#define NUMTEMPS_HEATER_0 NUMTEMPS_2
-#define heater_0_temptable temptable_2
-#elif THERMISTORHEATER_0 == 3
-#define NUMTEMPS_HEATER_0 NUMTEMPS_3
-#define heater_0_temptable temptable_3
-#elif THERMISTORHEATER_0 == 4
-#define NUMTEMPS_HEATER_0 NUMTEMPS_4
-#define heater_0_temptable temptable_4
-#elif THERMISTORHEATER_0 == 5
-#define NUMTEMPS_HEATER_0 NUMTEMPS_5
-#define heater_0_temptable temptable_5
-#elif THERMISTORHEATER_0 == 6
-#define NUMTEMPS_HEATER_0 NUMTEMPS_6
-#define heater_0_temptable temptable_6
-#elif THERMISTORHEATER_0 == 7
-#define NUMTEMPS_HEATER_0 NUMTEMPS_7
-#define heater_0_temptable temptable_7
-#elif defined HEATER_0_USES_THERMISTOR
-#error No heater 0 thermistor table specified
+#ifdef THERMISTORHEATER_0
+  #define heater_0_temptable TT_NAME(THERMISTORHEATER_0)
+  #define heater_0_temptable_len (sizeof(heater_0_temptable)/sizeof(*heater_0_temptable))
+#else
+#ifdef HEATER_0_USES_THERMISTOR
+  #error No heater 0 thermistor table specified
+#else  // HEATER_0_USES_THERMISTOR
+  #define heater_0_temptable 0
+  #define heater_0_temptable_len 0
+#endif // HEATER_0_USES_THERMISTOR
 #endif
 
-#if THERMISTORHEATER_1 == 1
-#define NUMTEMPS_HEATER_1 NUMTEMPS_1
-#define heater_1_temptable temptable_1
-#elif THERMISTORHEATER_1 == 2
-#define NUMTEMPS_HEATER_1 NUMTEMPS_2
-#define heater_1_temptable temptable_2
-#elif THERMISTORHEATER_1 == 3
-#define NUMTEMPS_HEATER_1 NUMTEMPS_3
-#define heater_1_temptable temptable_3
-#elif THERMISTORHEATER_1 == 4
-#define NUMTEMPS_HEATER_1 NUMTEMPS_4
-#define heater_1_temptable temptable_4
-#elif THERMISTORHEATER_1 == 5
-#define NUMTEMPS_HEATER_1 NUMTEMPS_5
-#define heater_1_temptable temptable_5
-#elif THERMISTORHEATER_1 == 6
-#define NUMTEMPS_HEATER_1 NUMTEMPS_6
-#define heater_1_temptable temptable_6
-#elif THERMISTORHEATER_1 == 7
-#define NUMTEMPS_HEATER_1 NUMTEMPS_7
-#define heater_1_temptable temptable_7
-#elif defined HEATER_1_USES_THERMISTOR
-#error No heater 1 thermistor table specified
+#ifdef THERMISTORHEATER_1
+  #define heater_1_temptable TT_NAME(THERMISTORHEATER_1)
+  #define heater_1_temptable_len (sizeof(heater_1_temptable)/sizeof(*heater_1_temptable))
+#else
+#ifdef HEATER_1_USES_THERMISTOR
+  #error No heater 1 thermistor table specified
+#else  // HEATER_1_USES_THERMISTOR
+  #define heater_1_temptable 0
+  #define heater_1_temptable_len 0
+#endif // HEATER_1_USES_THERMISTOR
 #endif
 
+#ifdef THERMISTORHEATER_2
+  #define heater_2_temptable TT_NAME(THERMISTORHEATER_2)
+  #define heater_2_temptable_len (sizeof(heater_2_temptable)/sizeof(*heater_2_temptable))
+#else
+#ifdef HEATER_2_USES_THERMISTOR
+  #error No heater 2 thermistor table specified
+#else  // HEATER_2_USES_THERMISTOR
+  #define heater_2_temptable 0
+  #define heater_2_temptable_len 0
+#endif // HEATER_2_USES_THERMISTOR
+#endif
 
-#if THERMISTORBED == 1
-#define BNUMTEMPS NUMTEMPS_1
-#define bedtemptable temptable_1
-#elif THERMISTORBED == 2
-#define BNUMTEMPS NUMTEMPS_2
-#define bedtemptable temptable_2
-#elif THERMISTORBED == 3
-#define BNUMTEMPS NUMTEMPS_3
-#define bedtemptable temptable_3
-#elif THERMISTORBED == 4
-#define BNUMTEMPS NUMTEMPS_4
-#define bedtemptable temptable_4
-#elif THERMISTORBED == 5
-#define BNUMTEMPS NUMTEMPS_5
-#define bedtemptable temptable_5
-#elif THERMISTORBED == 6
-#define BNUMTEMPS NUMTEMPS_6
-#define bedtemptable temptable_6
-#elif THERMISTORBED == 7
-#define BNUMTEMPS NUMTEMPS_7
-#define bedtemptable temptable_7
-#elif defined BED_USES_THERMISTOR
-#error No bed thermistor table specified
+#ifdef THERMISTORBED
+  #define bedtemptable TT_NAME(THERMISTORBED)
+  #define bedtemptable_len (sizeof(bedtemptable)/sizeof(*bedtemptable))
+#else
+#ifdef BED_USES_THERMISTOR
+  #error No bed thermistor table specified
+#endif // BED_USES_THERMISTOR
 #endif
 
 #endif //THERMISTORTABLES_H_