{
 }
 
+/**
+ * Cycle of scheduler is 10ms. So the cycle below is 1s
+ *
+ */
 void WorkMeterHandler::run()
 {
     if (m_Ticks++ > 100)
         {
              uint8_t  _present = 0; 
              m_Params->readValue(PID_BadgePresent,_present);
-            if (_present> 0) 
-            {
-                m_LCD->print(reinterpret_cast<const Uint8_t *>("1"));
-            } else
-            {
+             if (_present> 0) 
+             {
+                 m_LCD->print(reinterpret_cast<const Uint8_t *>("1"));
+             } else
+             {
                 m_LCD->print(reinterpret_cast<const Uint8_t *>("0"));
-            }
-            m_State = ST_WAIT;
+             }
+             m_State = ST_WAIT;
         }
         break;
         case ST_DISP_UPDATE_TIME:
-            timeToString();
-            m_LCD->print(m_StrTime);
-            m_State = ST_WAIT_BADGE;
+             timeToString();
+             m_LCD->print(m_StrTime);
+             m_State = ST_WAIT_BADGE;
         break;
         case ST_WAIT_BADGE:
-            /* 0 is fail :*/
-            m_State = ST_DISP_UPDATE_CURSOR_TAG;
-            //m_State = ST_WAIT;
+             /* 0 is fail :*/
+             m_State = ST_DISP_UPDATE_CURSOR_TAG;
+             //m_State = ST_WAIT;
         break;
         case ST_WAIT:
-            m_State = ST_WAIT;
+             m_State = ST_WAIT;
+            if (tagPresenceChanged())
+            {
+                 m_State = ST_DISP_UPDATE_CURSOR_TAG;
+            }
         break;
     };
 }
+
+Bool_t WorkMeterHandler::tagPresenceChanged()
+{
+    uint8_t  _present = 0; 
+    m_Params->readValue(PID_BadgePresent,_present);
+    if (_present != m_TagChange)
+    {
+        m_TagChange = _present;
+        return true;
+    }
+    return false;
+}
 
         void getTime();
         /**/
         void setTime();
+    
+        Bool_t tagPresenceChanged();
     private:
         Uint8_t m_StrTime[9];
         Uint8_t m_UID[7];
         RtcTime_t          m_Time;
         Uint32_t           m_Ticks;
         Uint8_t            m_State;
+        Bool_t             m_TagChange;
 };
 
 #endif
 
 #include <AVR/AvrEeprom.h>
 #include <AVR/AvrI2C.h>
 #include <Platform/IParameterHandler.h>
+#include <Platform/ErrorHandler/IErrorHandler.h>
+#include <Platform/ErrorHandler/ErrorHandler.h>
 #include <Metadata/WorkmeterParamIds.h>
 #include <Platform/ParameterHandler.h>
 #include <Platform/PersistentStorage.h>
  */
 class Scheduler : public IInterruptActivity
 {
+      typedef void (Scheduler::*pFunction_t)();
   private:
       enum TIME_SLOTS {
               FIRST_TIME_SLOT        =  0,
       } Task_type ;
 
       static Task_type gTasks[TASK_COUNT];
+  private:
+    Led0                   *m_Led;
+    IProtocolLayer2        *m_Netstring;
+    CommunicationHandler   *m_Com;
+    ITask                  *m_WorkMeter;
+    ITask                  *m_Storage;
+    ITask                  *m_RFIDReader;
+    volatile TIME_SLOTS     m_CurrentTimeslot;
+    ETASK_ID                m_CurrentTask;
+    RtcTime_t               m_Time;
+  private:
+        void doTask1()
+        {
+            m_WorkMeter->run();
+        }
+        void doTask2()
+        {
+            m_Led->tick();
+            m_RFIDReader->run();
+        }
+        void doTask3()
+        {
+            m_Led->tick();
+            m_Storage->run();
+        }
   public:
     Scheduler( Led0 *_led,IProtocolLayer2 *_net
              , CommunicationHandler *_com
     // main entry point
     void schedule()
     {
+
+        static const Scheduler::pFunction_t task[3] = {
+           &Scheduler::doTask1
+         , &Scheduler::doTask2
+         , &Scheduler::doTask3
+       };
+
+
         waitForTimeslot();
         m_Com->run();
-        switch (m_CurrentTask)
+#if 1
+       (this->*(task[m_CurrentTask]))();
+#else
+       switch (m_CurrentTask)
         {
             case TASK1:
                //m_Adc->run();
             ;
         
         }
+#endif
         m_CurrentTask = gTasks[m_CurrentTask].m_NextTask;
     }
+
     // called  by the interrupt timer handler
     virtual void tick()
     {
                 ;
             }
     }
-  private:
-    Led0                   *m_Led;
-    IProtocolLayer2        *m_Netstring;
-    CommunicationHandler   *m_Com;
-    ITask                  *m_WorkMeter;
-    ITask                  *m_Storage;
-    ITask                  *m_RFIDReader;
-    volatile TIME_SLOTS     m_CurrentTimeslot;
-    ETASK_ID                m_CurrentTask;
-    RtcTime_t               m_Time;
 
 
 };
  */
 int main(void)
 {
-   ParameterHandler gParam; 
+   ParameterHandler gParam;
+   ErrorHandler     gError(&gParam);
 #if defined (__AVR_ATmega32U4__)
    Led0                 led(&PORTC, &DDRC, PINB7,&gParam);
 #else
    NetString            netstring(&uart);
    CommunicationHandler gCom(&netstring,&gParam);
    PersistentStorage    gStorage(&gEeprom,&gParam);
-   RFIDReaderHandler    gRFIDReader(&nfc,&gParam);
+   RFIDReaderHandler    gRFIDReader(&nfc,&gParam,&gError);
    WorkMeterHandler     gWorkMeter(&gRtc,&lcd,&gParam,&nfc);
    Scheduler            sched( &led
                              , &netstring
 
             break;
         }
         timeout--;
-        _delay_ms(1);
+        _delay_us(500);
     } while (timeout > 0);
     /* If Succeed compare result */
     m_ReadReady = false;
                 break;
             }
             timeout--;
-            _delay_ms(1);
+            _delay_us(500);
         } while(timeout);
     }
 
 
 #define __ERRORS_H__
 
 enum ErrorIds_t {
-   ERROR_Application_Starting        = 0
-  ,ERROR_Eeprom_Read_Invalid_Length  = 1
-  ,ERROR_Eeprom_Read_Invalid_Address = 2
-  ,ERROR_Eeprom_Write_Invalid_Length  = 3
-  ,ERROR_Eeprom_Write_Invalid_Address = 4
-  ,ERROR_MAX = 5
+   ERR_Application_Starting         = 0
+  ,ERR_Eeprom_Read_Invalid_Length   = 1
+  ,ERR_Eeprom_Read_Invalid_Address  = 2
+  ,ERR_Eeprom_Write_Invalid_Length  = 3
+  ,ERR_Eeprom_Write_Invalid_Address = 4
+  ,ERR_I2C_Transaction_Ongoing      = 5
+  ,ERR_I2C_Write_Failed             = 6
+  ,ERR_I2C_Read_Failed              = 7
+  ,ERR_I2C_Timeout                  = 8
+  ,ERROR_MAX 
 };
 #endif
 
 #include <Utils/StdTypes.h>
 
 #include <Platform/IParameterHandler.h>
+#include <Application/ITask.h>
 
 #include <Metadata/ParameterTable.h>
 
 #include "IErrorHandler.h"
 #include "ErrorHandler.h"
 
-static Uint8_t  m_PID_Errors[ERROR_VECTORS] = {PID_LowLevelError1,PID_LowLevelError2};
-static Uint32_t m_LowLevelErrors[ERROR_VECTORS] {0,0};
+Uint8_t  ErrorHandler::m_PID_Errors[ERROR_VECTORS] = {PID_LowLevelError1,PID_LowLevelError2};
+Uint32_t ErrorHandler::m_LowLevelErrors[ERROR_VECTORS] = {0,0};
 
 
-void ErrorHandler::ErrorHandler()
+ErrorHandler::ErrorHandler(IParameterHandler *argParams)
+  : m_Params(argParams)
 {
 }
 
     updateErrors();
 }
 
-void ErrorHandler::setError(Error_t _err)
+void ErrorHandler::setError(Uint16_t _err)
 {
     Uint16_t _offset = 0;
     Uint8_t _vect    = 0;
     Bool_t  _found   = false;
-    while (!_found && (_vect < ERROR_VECTOR) )
+    while (!_found && (_vect < ERROR_VECTORS) )
     {
-        if (_err < (offset + 32))
+        if (_err < (_offset + 32))
         {
-            Uint32_t _errorBit = static_cast<Uin32_t>(1)<<(_err - ofsset);
-            m_LowLevelErrors[_vect] |=
+            Uint32_t _errorBit = static_cast<Uint32_t>(1)<<(_err - _offset);
+            m_LowLevelErrors[_vect] |= _errorBit;
             _found = true;
         }
-        offset+=32;
+        _offset+=32;
         _vect++;
     };
 }
 
 void ErrorHandler::updateErrors()
 {
-    for (Uint8_t i = 0; i < ERROR_VECTOR ; ++i)
+    for (Uint8_t i = 0; i < ERROR_VECTORS ; ++i)
     {
         m_Params->writeValue(m_PID_Errors[i],m_LowLevelErrors[i]);
         m_LowLevelErrors[i] = 0L;
 
     private:
         void updateErrors();
     private:
-       static Uint8_t  m_PID_Errors[ERROR_VECTORS];
-       static Uint32_t m_LowLevelErrors[ERROR_VECTORS];
+        IParameterHandler *m_Params;
+        static Uint8_t  m_PID_Errors[ERROR_VECTORS];
+        static Uint32_t m_LowLevelErrors[ERROR_VECTORS];
 };
 
 #endif
 
     public:
         IErrorHandler() {};
         /// 
-        virtual setError(Uint16_t error_id) = 0 ;
+        virtual void setError(Uint16_t error_id) = 0 ;
 };
 #endif
 
 #include "Abstract/RFID/IPN532Interface.h"
 #include "HAL/Drivers/PN532.h"
 #include "Platform/IParameterHandler.h"
+#include "Platform/ErrorHandler/IErrorHandler.h"
 
 #include "Metadata/WorkmeterParamIds.h"
+#include "Metadata/Errors.h"
 #include "Platform/RFIDReader/RFIDReaderHandler.h"
 
 
 
 
 
-RFIDReaderHandler::RFIDReaderHandler(PN532 *argNFC,IParameterHandler *argParam)
-  : m_NFC(argNFC), m_Param(argParam),m_State(ST_INIT)
+RFIDReaderHandler::RFIDReaderHandler(PN532 *argNFC
+                                    ,IParameterHandler *argParam
+                                    ,IErrorHandler *argError)
+  : m_NFC(argNFC), m_Param(argParam),m_Error(argError),m_State(ST_INIT)
     , m_1Milli(10),m_CurrentRequest(ST_IDLE),m_Ticks(0)
 {
 }
        {
            Uint32_t ver = m_NFC->getFirmwareVersion();
            m_Param->writeValue(PID_RFFirmwareVersion,ver);
+           m_State = ST_IDLE;
        }
        break;
        case ST_REQ_BADGE_ID:
            m_State = ST_DISP_ON; // Do nothing
        } else 
        {
-           m_1Milli = 10;
+           m_1Milli = 1;
            m_State  = ST_WAIT_RESPONSE;
        }
        break;
        break;
        case ST_DISP_OFF:
            doDisplay(true);
-           m_1Milli = 10;
+           m_1Milli = 1;
            m_State  = ST_WAIT_RESPONSE;
            m_CurrentRequest = ST_REQ_BADGE_ID;
        break;
 
       ,ST_DELAY_1MILLI
     };
     public:
-        RFIDReaderHandler(PN532 *argNFC,IParameterHandler *argParam);
+        RFIDReaderHandler(PN532 *argNFC,IParameterHandler *argParam,IErrorHandler *argError);
         void run();
     private:
         void doStateMachine();
     private:
         PN532             *m_NFC;
         IParameterHandler *m_Param;
+        IErrorHandler     *m_Error;
         Uint8_t            m_State;
         Uint8_t            m_1Milli;
         Uint8_t            m_CurrentRequest;