diff --git a/tools/pysflphone/sflphonectrlsimple.py b/tools/pysflphone/sflphonectrl.py
similarity index 76%
rename from tools/pysflphone/sflphonectrlsimple.py
rename to tools/pysflphone/sflphonectrl.py
index a8aa40c8b8d83ee20b73e91131fbebb0bd843341..88a4fe90380722fc7a672b2c2096c42d6af707fd 100755
--- a/tools/pysflphone/sflphonectrlsimple.py
+++ b/tools/pysflphone/sflphonectrl.py
@@ -47,43 +47,46 @@ except ImportError, e:
 	raise SflPhoneError("No python-dbus module found")
 
 
-class SflPhoneCtrlSimple(Thread):
-    """ Simple class for controlling SflPhoned through DBUS
-
-        If option testSuite (ts) is put to true,
-	simple actions are implemented on incoming call.
+class SflPhoneCtrl(Thread):
+    """ class for controlling SflPhoned through DBUS
+
+    Classes deriving this class should reimplement signal handlers,
+    more especially:
+	onIncomingCall_cb
+        onCallHangup_cb
+        onCallRinging_cb
+        onCallHold_cb
+        onCallCurrent_cb
+        onCallBusy_cb
+        onCallFailure_cb
     """
 
     # list of active calls (known by the client)
     activeCalls = {}
 
-    def __init__(self, test=False, name=sys.argv[0]):
-        print "Create SFLphone instance"
-	Thread.__init__(self)
-       	# current active account
+    def __init__(self, name=sys.argv[0]):
+        Thread.__init__(self)
+
+        # current active account
         self.account = None
+
         # client name
         self.name = name
+
+	self.currentCallId = ""
+
+	self.isStop = False
+
         # client registered to sflphoned ?
         self.registered = False
         self.register()
-	self.currentCallId = ""
 
+        # Glib MainLoop for processing callbacks
 	self.loop = MainLoop()
 
-	self.isStop = False
-
-	self.test = test
-	self.onIncomingCall_cb = None
-        self.onCallRinging_cb = None
-        self.onCallCurrent_cb = None
-        self.onCallFailure_cb = None
-	self.event = Event()
-
 	gobject.threads_init()
 
 
-
     def __del__(self):
         if self.registered:
             self.unregister()
@@ -91,11 +94,9 @@ class SflPhoneCtrlSimple(Thread):
 
 
     def stopThread(self):
-        print "Stop PySFLphone"
         self.isStop = True
 
 
-
     def register(self):
         if self.registered:
             return
@@ -148,14 +149,10 @@ class SflPhoneCtrlSimple(Thread):
             print e
 
 
-
     def unregister(self):
 
-        print "Unregister"
-
         if not self.registered:
             return
-            #raise SflPhoneError("Not registered !")
         try:
             self.instance.Unregister(os.getpid())
             self.registered = False
@@ -167,80 +164,115 @@ class SflPhoneCtrlSimple(Thread):
         return self.registered
 
 
-    def getEvent(self):
-        return self.event
+    #
+    # Signal handling
+    #
+
+    def onIncomingCall_cb(self):
+        pass
+
+    def onCallHangup_cb(self):
+        pass
 
-    def wait(self):
-        self.event.wait()
+    def onCallRinging_cb(self):
+        pass
 
-    def isSet(self):
-        self.event.isSet()
+    def onCallHold_cb(self):
+        pass
 
-    def set(self):
-        self.event.set()
+    def onCallCurrent_cb(self):
+        pass
 
-    def clear(self):
-        self.event.clear()
+    def onCallBusy_cb(self):
+        pass
 
-    #
-    # Signal handling
-    #
+    def onCallFailure_cb(self):
+        pass
 
-    # On incoming call event, add the call to the list of active calls
     def onIncomingCall(self, account, callid, to):
-        print "Incoming call: " + account + ", " + callid + ", " + to
-        self.activeCalls[callid] = {'Account': account, 'To': to, 'State': '' }
+        """ On incoming call event, add the call to the list of active calls """
+
+        self.activeCalls[callid] = {'Account': account,
+                                         'To': to,
+                                      'State': ''}
 	self.currentCallId = callid
+	self.onIncomingCall_cb()
+
+
+    def onCallHangUp(self, callid):
+        """ Remove callid from call list """
+
+        self.onCallHangup_cb()
+	self.currentCallId = ""
+        del self.activeCalls[callid]
+
+
+    def onCallRinging(self, callid, state):
+        """ Update state for this call to Ringing """
+
+        self.activeCalls[callid]['State'] = state
+        self.onCallRinging_cb()
+
+
+    def onCallHold(self, callid, state):
+        """ Update state for this call to Hold """
+
+        self.activeCalls[callid]['State'] = state
+        self.onCallHold_cb()
+
 
-	if(self.test):
-            # TODO fix this bug in daemon, cannot answer too fast
-            time.sleep(0.5)
-	    if self.onIncomingCall_cb(self):
-                self.onIncomingCall_cb(self)
+    def onCallCurrent(self, callid, state):
+        """ Update state for this call to current """
 
+        self.activeCalls[callid]['State'] = state
+        self.onCallCurrent_cb()
+
+
+    def onCallBusy(self, callid, state):
+        """ Update state for this call to busy """
+
+        self.activeCalls[callid]['State'] = state
+        self.onCallBusy_cb()
+
+
+    def onCallFailure(self, callid, state):
+        """ Handle call failure """
+
+        self.onCallFailure_cb(self)
+        del self.activeCalls[callid]
 
 
-    # On call state changed event, set the values for new calls,
-    # or delete the call from the list of active calls
     def onCallStateChanged(self, callid, state):
-        print "Call state changed: " + callid + ", " + state
+        """ On call state changed event, set the values for new calls,
+        or delete the call from the list of active calls
+        """
+
+        print "On call state changed " + callid + " " + state
+
+        if callid not in self.activeCalls:
+            print "This call didn't exist!: " + callid + ". Adding it to the list."
+            callDetails = self.getCallDetails(callid)
+            self.activeCalls[callid] = {'Account': callDetails['ACCOUNTID'],
+                                             'To': callDetails['PEER_NUMBER'],
+                                          'State': state }
+
+
         self.currentCallId = callid
-        if state is "HUNGUP":
-            try:
-                del self.activeCalls[callid]
-            except KeyError:
-                print "Call " + callid + " didn't exist. Cannot delete."
-
-        elif state is "RINGING":
-            try:
-                self.activeCalls[callid]['State'] = state
-                if self.onCallRinging_cb:
-                    self.onCallRinging_cb(self)
-            except KeyError, e:
-                print "This call didn't exist!: " + callid + ". Adding it to the list."
-                callDetails = self.getCallDetails(callid)
-                self.activeCalls[callid] = {'Account': callDetails['ACCOUNTID'],
-					    'To': callDetails['PEER_NUMBER'], 'State': state }
-        elif state in [ "CURRENT", "INCOMING", "HOLD" ]:
-            try:
-                self.activeCalls[callid]['State'] = state
-                if self.onCallCurrent_cb:
-                    self.onCallCurrent_cb(self)
-                callDetails = self.getCallDetails(callid)
-                self.activeCalls[callid] = {'Account': callDetails['ACCOUNTID'],
-					    'To': callDetails['PEER_NUMBER'], 'State': state }
-            except KeyError, e:
-                print "This call didn't exist!: " + callid + ". Adding it to the list."
-        elif state in [ "BUSY", "FAILURE" ]:
-            try:
-	        if self.onCallFailure_cb:
-                    self.onCallFailure_cb(self)
-                del self.activeCalls[callid]
-            except KeyError, e:
-                print "This call didn't exist!: " + callid
-
-#		elif state == "UNHOLD_CURRENT":
-#			self.activeCalls[callid]['State'] = "UNHOLD_CURRENT"
+
+        if state == "HUNGUP":
+            self.onCallHangUp(callid)
+        elif state == "RINGING":
+            self.onCallRinging(callid, state)
+        elif state == "CURRENT":
+            self.onCallCurrent(callid, state)
+        elif state == "HOLD":
+            self.onCallHold(callid, state)
+        elif state == "BUSY":
+            self.onCallBusy(callid, state)
+        elif state == "FAILURE":
+            self.onCallFailure(self, callid, state)
+        else:
+            print "unknown state"
 
 
     #
@@ -265,6 +297,7 @@ class SflPhoneCtrlSimple(Thread):
 
 	return self.configurationmanager.addAccount(details)
 
+
     def removeAccount(self, accountID=None):
         """Remove an account from internal list"""
 
@@ -273,13 +306,16 @@ class SflPhoneCtrlSimple(Thread):
 
         self.configurationmanager.removeAccount(accountID)
 
+
     def getAllAccounts(self):
         """Return a list with all accounts"""
+
         return self.configurationmanager.getAccountList()
 
 
     def getAllEnabledAccounts(self):
         """Return a list with all enabled accounts"""
+
         accounts = self.getAllAccounts()
         activeaccounts = []
         for testedaccount in accounts:
@@ -324,6 +360,7 @@ class SflPhoneCtrlSimple(Thread):
 
         raise SPaccountError("No account matched with alias")
 
+
     def setAccount(self, account):
         """Define the active account
 
@@ -336,6 +373,7 @@ class SflPhoneCtrlSimple(Thread):
             print account
             raise SflPhoneError("Not a valid account")
 
+
     def setFirstRegisteredAccount(self):
         """Find the first enabled account and define it as active"""
 
@@ -344,6 +382,7 @@ class SflPhoneCtrlSimple(Thread):
             raise SflPhoneError("No registered account !")
         self.account = rAccounts[0]
 
+
     def setFirstActiveAccount(self):
         """Find the first enabled account and define it as active"""
 
@@ -373,33 +412,37 @@ class SflPhoneCtrlSimple(Thread):
         """Return True if the account is enabled. If no account is provided, active account is used"""
 
         if account is None:
-	       	if self.account is None:
-		       	raise SflPhoneError("No provided or current account !")
+            if self.account is None:
+                raise SflPhoneError("No provided or current account !")
                 account = self.account
         return self.getAccountDetails(account)['Account.enable'] == "TRUE"
 
+
     def setAccountEnable(self, account=None, enable=False):
-       	"""Set account enabled"""
+        """Set account enabled"""
         if account is None:
-	       	if self.account is None:
-		       	raise SflPhoneError("No provided or current account !")
+            if self.account is None:
+                raise SflPhoneError("No provided or current account !")
                 account = self.account
 
-       	if enable == True:
-	       	details = self.getAccountDetails(account)
-                details['Account.enable'] = "true"
-                self.configurationmanager.setAccountDetails(account, details)
+        if enable == True:
+	    details = self.getAccountDetails(account)
+            details['Account.enable'] = "true"
+            self.configurationmanager.setAccountDetails(account, details)
         else:
-	       	details = self.getAccountDetails(account)
-                details['Account.enable'] = "false"
-                self.configurationmanager.setAccountDetails(account, details)
+            details = self.getAccountDetails(account)
+            details['Account.enable'] = "false"
+            self.configurationmanager.setAccountDetails(account, details)
+
 
     def checkAccountExists(self, account=None):
         """ Checks if the account exists """
+
         if account is None:
             raise SflPhoneError("No provided or current account !")
         return account in self.getAllAccounts()
 
+
     def getAllRegisteredAccounts(self):
         """Return a list of registered accounts"""
 
@@ -410,6 +453,7 @@ class SflPhoneCtrlSimple(Thread):
 
         return registeredAccountsList
 
+
     def getAllEnabledAccounts(self):
         """Return a list of enabled accounts"""
 
@@ -420,8 +464,10 @@ class SflPhoneCtrlSimple(Thread):
 
         return enabledAccountsList
 
+
     def getAllSipAccounts(self):
         """Return a list of SIP accounts"""
+
         sipAccountsList = []
         for accountName in self.getAllAccounts():
             if  self.getAccountDetails(accountName)['Account.type'] == "SIP":
@@ -429,6 +475,7 @@ class SflPhoneCtrlSimple(Thread):
 
         return sipAccountsList
 
+
     def getAllIaxAccounts(self):
         """Return a list of IAX accounts"""
 
@@ -439,23 +486,22 @@ class SflPhoneCtrlSimple(Thread):
 
         return iaxAccountsList
 
+
     def setAccountRegistered(self, account=None, register=False):
-       	""" Tries to register the account """
-
-       	if account is None:
-       		if self.account is None:
-       			raise SflPhoneError("No provided or current account !")
-       		account = self.account
-
-       	try:
-       		if register:
-       			self.configurationmanager.sendRegister(account, int(1))
-       			#self.setAccount(account)
-       		else:
-       			self.configurationmanager.sendRegister(account, int(0))
-       			#self.setFirstRegisteredAccount()
+        """ Tries to register the account """
+
+        if account is None:
+            if self.account is None:
+                raise SflPhoneError("No provided or current account !")
+            account = self.account
+
+        try:
+            if register:
+                self.configurationmanager.sendRegister(account, int(1))
+            else:
+                self.configurationmanager.sendRegister(account, int(0))
         except SflPhoneError, e:
-       		print e
+            print e
 
     #
     # Codec manager
@@ -463,12 +509,14 @@ class SflPhoneCtrlSimple(Thread):
 
     def getCodecList(self):
         """ Return the codec list """
+
         return self.configurationmanager.getCodecList()
 
+
     def getActiveCodecList(self):
         """ Return the active codec list """
-        return self.configurationmanager.getActiveCodecList()
 
+        return self.configurationmanager.getActiveCodecList()
 
 
     #
@@ -539,26 +587,18 @@ class SflPhoneCtrlSimple(Thread):
 
     def HangUp(self, callid):
         """End a call identified by a CallID"""
+
         if not self.account:
             self.setFirstRegisteredAccount()
 
-        # if not self.isAccountRegistered() and self.accout is not "IP2IP":
-        #    raise SflPhoneError("Can't hangup a call without a registered account")
-
         if callid is None or callid == "":
             pass # just to see
-            #raise SflPhoneError("Invalid callID")
 
 	self.callmanager.hangUp(callid)
 
 
     def Transfer(self, callid, to):
         """Transfert a call identified by a CallID"""
-        # if not self.account:
-        #    self.setFirstRegisteredAccount()
-
-        # if not self.isAccountRegistered():
-        #     raise SflPhoneError("Can't transfert a call without a registered account")
 
         if callid is None or callid == "":
             raise SflPhoneError("Invalid callID")
@@ -571,12 +611,6 @@ class SflPhoneCtrlSimple(Thread):
 
 	print "Refuse call " + callid
 
-        # if not self.account:
-        #     self.setFirstRegisteredAccount()
-
-        # if not self.isAccountRegistered():
-        #     raise SflPhoneError("Can't refuse a call without a registered account")
-
         if callid is None or callid == "":
             raise SflPhoneError("Invalid callID")
 
@@ -585,11 +619,12 @@ class SflPhoneCtrlSimple(Thread):
 
     def Accept(self, callid):
         """Accept an incoming call identified by a CallID"""
+
 	print "Accept call " + callid
         if not self.account:
             self.setFirstRegisteredAccount()
 
-       	if not self.isAccountRegistered():
+        if not self.isAccountRegistered():
             raise SflPhoneError("Can't accept a call without a registered account")
 
         if callid is None or callid == "":
@@ -600,6 +635,7 @@ class SflPhoneCtrlSimple(Thread):
 
     def Hold(self, callid):
         """Hold a call identified by a CallID"""
+
         # if not self.account:
         #    self.setFirstRegisteredAccount()
 
@@ -614,6 +650,7 @@ class SflPhoneCtrlSimple(Thread):
 
     def UnHold(self, callid):
         """Unhold an incoming call identified by a CallID"""
+
         # if not self.account:
         #    self.setFirstRegisteredAccount()
 
@@ -628,11 +665,13 @@ class SflPhoneCtrlSimple(Thread):
 
     def Dtmf(self, key):
         """Send a DTMF"""
+
         self.callmanager.playDTMF(key)
 
 
     def GenerateCallID(self):
         """Generate Call ID"""
+
 	m = hashlib.md5()
         t = long( time.time() * 1000 )
         r = long( random.random()*100000000000000000L )
@@ -649,4 +688,4 @@ class SflPhoneCtrlSimple(Thread):
             context.iteration(True)
 
 	    if self.isStop:
-	        return
+                return
diff --git a/tools/pysflphone/test_sflphone_dbus_interface.py b/tools/pysflphone/test_sflphone_dbus_interface.py
index e865efaa4dfa79af68871bea80009a7f2c0be722..2af61f5c554feb681cfeb5d0da1bca3baf4e9ea8 100644
--- a/tools/pysflphone/test_sflphone_dbus_interface.py
+++ b/tools/pysflphone/test_sflphone_dbus_interface.py
@@ -21,7 +21,7 @@ import time
 import logging
 from sippwrap import SippWrapper
 from sippwrap import SippScreenStatParser
-from sflphonectrlsimple import SflPhoneCtrlSimple
+from sflphonectrl import SflPhoneCtrl
 
 from nose.tools import nottest
 
@@ -33,37 +33,11 @@ accountList = ["IP2IP", "Account:1332798167"]
 
 SCENARIO_PATH = "../sippxml/"
 
-def callHangup(sflphone):
-    """ On incoming call, answer the callm, then hangup """
-
-    print "Hangup Call with id " + sflphone.currentCallId
-    sflphone.HangUp(sflphone.currentCallId)
-
-    time.sleep(3)
-
-    print "Stopping Thread"
-    sflphone.stopThread()
-
-
-def callIsRinging(sflphone):
-    """ Display messages when call is ringing """
-
-    print "The call is ringing"
-
-
-def leaveThreadOnFailure(sflphone):
-    """ If a failure occurs duing the call, just leave the running thread """
-
-    print "Stopping Thread"
-    sflphone.stopThread()
-
-
-
-class TestSFLPhoneAccountConfig:
+class TestSFLPhoneAccountConfig(SflPhoneCtrl):
     """ The test suite for account configuration """
 
     def __init__(self):
-        self.sflphone = SflPhoneCtrlSimple(True)
+        SflPhoneCtrl.__init__(self)
 
         self.logger = logging.getLogger("TestSFLPhoneAccountConfig")
         filehdlr = logging.FileHandler("/tmp/sflphonedbustest.log")
@@ -75,28 +49,28 @@ class TestSFLPhoneAccountConfig:
     @nottest
     def test_get_account_list(self):
         self.logger.info("Test get account list")
-        accList = self.sflphone.getAllAccounts()
+        accList = self.getAllAccounts()
         listIntersection = set(accList) & set(accountList)
         assert len(listIntersection) == len(accountList)
 
     @nottest
     def test_account_registration(self):
         self.logger.info("Test account registration")
-        accList = [x for x in self.sflphone.getAllAccounts() if x != "IP2IP"]
+        accList = [x for x in self.getAllAccounts() if x != "IP2IP"]
         for acc in accList:
 	    self.logger.info("Registering account " + acc)
 
-            if self.sflphone.isAccountEnable(acc):
-               self.sflphone.setAccountEnable(acc, False)
+            if self.isAccountEnable(acc):
+               self.setAccountEnable(acc, False)
                time.sleep(2)
 
             # Account should not be registered
-            assert self.sflphone.isAccountRegistered(acc)
+            assert self.isAccountRegistered(acc)
 
-            self.sflphone.setAccountEnable(acc, True)
+            self.setAccountEnable(acc, True)
             time.sleep(2)
 
-            assert self.sflphone.isAccountRegistered(acc)
+            assert self.isAccountRegistered(acc)
 
     @nottest
     def test_add_remove_account(self):
@@ -105,31 +79,31 @@ class TestSFLPhoneAccountConfig:
         newAccList = []
 
         # consider only true accounts
-        accList = [x for x in self.sflphone.getAllAccounts() if x != "IP2IP"]
+        accList = [x for x in self.getAllAccounts() if x != "IP2IP"]
 
         # Store the account details localy
         for acc in accList:
-            accountDetails[acc] = self.sflphone.getAccountDetails(acc)
+            accountDetails[acc] = self.getAccountDetails(acc)
 
         # Remove all accounts from sflphone
         for acc in accountDetails:
-            self.sflphone.removeAccount(acc)
+            self.removeAccount(acc)
 
         # Recreate all accounts
         for acc in accountDetails:
-            newAccList.append(self.sflphone.addAccount(accountDetails[acc]))
+            newAccList.append(self.addAccount(accountDetails[acc]))
 
         # New accounts should be automatically registered
         for acc in newAccList:
-            assert self.sflphone.isAccountRegistered(acc)
+            assert self.isAccountRegistered(acc)
 
 
 
-class TestSFLPhoneRegisteredCalls:
+class TestSFLPhoneRegisteredCalls(SflPhoneCtrl):
     """ The test suite for call interaction """
 
     def __init__(self):
-        self.sflphone = SflPhoneCtrlSimple(True)
+        SflPhoneCtrl.__init__(self)
 
         self.logger = logging.getLogger("TestSFLPhoneRegisteredCalls")
         filehdlr = logging.FileHandler("/tmp/sfltestregisteredcall.log")
@@ -141,19 +115,41 @@ class TestSFLPhoneRegisteredCalls:
         self.sippCallInstance = SippWrapper()
         self.localInterface = "127.0.0.1"
         self.localPort = str(5064)
-        self.sflphone.onCallRinging_cb = callIsRinging
-        self.sflphone.onCallCurrent_cb = callHangup
-        self.sflphone.onCallFailure_cb = leaveThreadOnFailure
 
         # Make sure the test directory is populated with most recent log files
         self.clean_log_directory()
 
+
+    def onCallCurrent_cb(self):
+        """ On incoming call, answer the callm, then hangup """
+
+        print "Hangup Call with id " + self.currentCallId
+        self.HangUp(self.currentCallId)
+
+        print "Stopping Thread"
+        self.stopThread()
+
+
+    def onCallRinging_cb(self):
+        """ Display messages when call is ringing """
+
+        print "The call is ringing"
+
+
+    def onCallFailure_cb(self):
+        """ If a failure occurs duing the call, just leave the running thread """
+
+        print "Stopping Thread"
+        self.stopThread()
+
+
     def clean_log_directory(self):
         dirlist = os.listdir("./")
         files = [x for x in dirlist if "screen.log" in x]
         for f in files:
 	    os.remove(f)
 
+
     def find_sipp_pid(self):
         # Retreive the PID of the last
         # The /proc/PID/cmdline contain the command line from
@@ -162,6 +158,7 @@ class TestSFLPhoneRegisteredCalls:
 
         return sippPid[0]
 
+
     def parse_results(self):
         dirlist = os.listdir("./")
         logfile = [x for x in dirlist if "screen.log" in x]
@@ -175,6 +172,7 @@ class TestSFLPhoneRegisteredCalls:
         assert(not resultParser.isAnyFailedCall())
         assert(resultParser.isAnySuccessfulCall())
 
+
     def test_registered_call(self):
         self.logger.info("Test Registered Call")
 
@@ -209,16 +207,16 @@ class TestSFLPhoneRegisteredCalls:
         sippPid = self.find_sipp_pid()
 
         # make sure every account are enabled
-        accList = [x for x in self.sflphone.getAllAccounts() if x != "IP2IP"]
+        accList = [x for x in self.getAllAccounts() if x != "IP2IP"]
         for acc in accList:
-            if not self.sflphone.isAccountRegistered(acc):
-                self.sflphone.setAccountEnable(acc, True)
+            if not self.isAccountRegistered(acc):
+                self.setAccountEnable(acc, True)
 
         # Make a call to the SIPP instance
-        self.sflphone.Call("300")
+        self.Call("300")
 
         # Start Glib mainloop to process callbacks
-        self.sflphone.start()
+        self.start()
 
         # Wait the sipp instance to dump log files
         while os.path.exists("/proc/" + str(sippPid)):