Esempio n. 1
0
	def disconnect_session(self, session):
		Logger.info("SessionManagement::disconnect %s"%(session.id))
		
		if session.user.created or not session.domain.manage_user():
			# Doesn't have to disconnect the session if the user was never created
			
			try:
				sessid = TS.getSessionID(session.user.name)
			except Exception:
				Logger.exception("RDP server dialog failed ... ")
				return False
			
			try:
				status = TS.getState(sessid)
			except Exception:
				Logger.exception("RDP server dialog failed ... ")
				return
			
			if status in [TS.STATUS_LOGGED]:
				Logger.info("must disconnect ts session %s user %s"%(sessid, session.user.name))
				
				try:
					TS.disconnect(sessid)
				except Exception:
					Logger.exception("RDP server dialog failed ... ")
					return
		
		session.switch_status(Session.SESSION_STATUS_INACTIVE)
Esempio n. 2
0
    def disconnect_session(self, session):
        Logger.info("SessionManagement::disconnect %s" % (session.id))

        if session.user.created or not session.domain.manage_user():
            # Doesn't have to disconnect the session if the user was never created

            try:
                sessid = TS.getSessionID(session.user.name)
            except Exception:
                Logger.exception("RDP server dialog failed ... ")
                return False

            try:
                status = TS.getState(sessid)
            except Exception:
                Logger.exception("RDP server dialog failed ... ")
                return

            if status in [TS.STATUS_LOGGED]:
                Logger.info("must disconnect ts session %s user %s" %
                            (sessid, session.user.name))

                try:
                    TS.disconnect(sessid)
                except Exception:
                    Logger.exception("RDP server dialog failed ... ")
                    return

        session.switch_status(Session.SESSION_STATUS_INACTIVE)
Esempio n. 3
0
    def init(self):
        Logger.debug("ApplicationServer init")

        try:
            TS.getList()
        except Exception:
            Logger.exception("RDP server dialog failed ... exiting")
            return

        if not System.groupExist(self.manager.ts_group_name):
            Logger.error("The group '%s' doesn't exist" %
                         (self.manager.ts_group_name))
            return False

        if not System.groupExist(self.manager.ovd_group_name):
            if not System.groupCreate(self.manager.ovd_group_name):
                return False

        if not self.manager.purgeGroup():
            Logger.error("Unable to purge group")
            return False

        if Config.clean_dump_archive:
            self.purgeArchives()

        if Config.thread_count is None:
            cpuInfos = System.getCPUInfos()
            vcpu = cpuInfos[0]
            ram_total = System.getRAMTotal()
            ram = int(round(ram_total / 1024.0 / 1024.0))

            nb_thread = int(round(1 + (ram + vcpu * 2) / 3))
        else:
            nb_thread = Config.thread_count

        Logger._instance.setQueue(self.logging_queue, True)
        for _ in xrange(nb_thread):
            self.threads.append(
                SessionManagement(self.manager, self.sessions_spooler,
                                  self.sessions_spooler2, self.sessions_sync,
                                  self.logging_queue))

        if self.canManageApplications():
            self.apt = Apt()
            self.apt.init()
            self.threads.append(self.apt)

        Logger.info(
            "ApplicationServer:: retrieve all applications installed (can take some time)"
        )
        self.updateApplications()

        return True
Esempio n. 4
0
	def req_user_loggedin(self, request):
		try:
			document = minidom.parseString(request["data"])
			rootNode = document.documentElement
			
			if rootNode.nodeName != "user":
				raise Exception("invalid root node")
			
			if not rootNode.hasAttribute("login"):
				raise Exception("invalid root node")
			
			login = rootNode.getAttribute("login")
			
		except:
			Logger.warn("Invalid xml input !!")
			doc = Document()
			rootNode = doc.createElement('error')
			rootNode.setAttribute("id", "usage")
			doc.appendChild(rootNode)
			return self.req_answer(doc)
		
		try:
			ret = TS.getSessionID(login)
		except Exception:
			Logger.exception("RDP server dialog failed ... ")
			doc = Document()
			rootNode = doc.createElement('error')
			rootNode.setAttribute("id", "internalerror")
			doc.appendChild(rootNode)
			return self.req_answer(doc)
		
		rootNode.setAttribute("loggedin", str((ret is not None)).lower())
		
		return self.req_answer(document)
Esempio n. 5
0
	def init(self):
		Logger.debug("ApplicationServer init")
		
		try:
			TS.getList()
		except Exception:
			Logger.exception("RDP server dialog failed ... exiting")
			return
		
		if not System.groupExist(self.manager.ts_group_name):
			Logger.error("The group '%s' doesn't exist"%(self.manager.ts_group_name))
			return False
		
		if not System.groupExist(self.manager.ovd_group_name):
			if not System.groupCreate(self.manager.ovd_group_name):
				return False
		
		if not self.manager.purgeGroup():
			Logger.error("Unable to purge group")
			return False
		
		if Config.clean_dump_archive:
			self.purgeArchives()
		
		if Config.thread_count is None:
			cpuInfos = System.getCPUInfos()
			vcpu = cpuInfos[0]
			ram_total = System.getRAMTotal()
			ram = int(round(ram_total / 1024.0 / 1024.0))
			
			nb_thread = int(round(1 + (ram + vcpu * 2)/3))
		else:
			nb_thread = Config.thread_count
		
		Logger._instance.setQueue(self.logging_queue, True)
		for _ in xrange(nb_thread):
			self.threads.append(SessionManagement(self.manager, self.sessions_spooler, self.sessions_spooler2, self.sessions_sync, self.logging_queue))
		
		if self.canManageApplications():
			self.apt = Apt()
			self.apt.init()
			self.threads.append(self.apt)
		
		Logger.info("ApplicationServer:: retrieve all applications installed (can take some time)")
		self.updateApplications()
		
		return True
Esempio n. 6
0
	def logoff_user(self, user):
		Logger.info("SessionManagement::logoff_user %s"%(user.name))
		
		if user.infos.has_key("tsid"):
			sessid = user.infos["tsid"]
			
			try:
				status = TS.getState(sessid)
			except Exception:
				Logger.exception("RDP server dialog failed ... ")
				return
			
			if status in [TS.STATUS_LOGGED, TS.STATUS_DISCONNECTED]:
				Logger.info("must log off ts session %s user %s"%(sessid, user.name))
				
				try:
					TS.logoff(sessid)
				except Exception:
					Logger.exception("RDP server dialog failed ... ")
					return
				
				del(user.infos["tsid"])
Esempio n. 7
0
    def logoff_user(self, user):
        Logger.info("SessionManagement::logoff_user %s" % (user.name))

        if user.infos.has_key("tsid"):
            sessid = user.infos["tsid"]

            try:
                status = TS.getState(sessid)
            except Exception:
                Logger.exception("RDP server dialog failed ... ")
                return

            if status in [TS.STATUS_LOGGED, TS.STATUS_DISCONNECTED]:
                Logger.info("must log off ts session %s user %s" %
                            (sessid, user.name))

                try:
                    TS.logoff(sessid)
                except Exception:
                    Logger.exception("RDP server dialog failed ... ")
                    return

                del (user.infos["tsid"])
Esempio n. 8
0
    def destroy_session(self, session):
        Logger.info("SessionManagement::destroy %s" % (session.id))

        if session.user.created or not session.domain.manage_user():
            # Doesn't have to destroy the session if the user was never created

            try:
                sessid = TS.getSessionID(session.user.name)
            except Exception:
                Logger.exception("RDP server dialog failed ... ")
                return

            if sessid is not None:
                session.user.infos["tsid"] = sessid

            self.logoff_user(session.user)

        session.uninstall_client()

        if session.domain.manage_user():
            self.destroy_user(session.user)

        session.domain.onSessionEnd()
        session.switch_status(Session.SESSION_STATUS_DESTROYED)
Esempio n. 9
0
	def destroy_session(self, session):
		Logger.info("SessionManagement::destroy %s"%(session.id))
		
		if session.user.created or not session.domain.manage_user():
			# Doesn't have to destroy the session if the user was never created
			
			try:
				sessid = TS.getSessionID(session.user.name)
			except Exception:
				Logger.exception("RDP server dialog failed ... ")
				return
			
			if sessid is not None:
				session.user.infos["tsid"] = sessid
			
			self.logoff_user(session.user)
		
		session.uninstall_client()
		
		if session.domain.manage_user():
			self.destroy_user(session.user)
		
		session.domain.onSessionEnd()
		session.switch_status(Session.SESSION_STATUS_DESTROYED)
Esempio n. 10
0
class Manager:
    ts_group_name = TS.getUsersGroup()
    ovd_group_name = "OVDUsers"

    def __init__(self, smManager):
        self.smManager = smManager

    def send_session_status(self, session):
        try:
            doc = Document()
            rootNode = doc.createElement('session')
            rootNode.setAttribute("id", session.id)
            rootNode.setAttribute("status", session.status)
            if session.status == Session.SESSION_STATUS_DESTROYED and session.end_status is not None:
                rootNode.setAttribute("reason", session.end_status)

            doc.appendChild(rootNode)
        except Exception:
            Logger.exception("ApplicationServer: send_session_status")

        response = self.smManager.send_packet("/session/status", doc)
        Logger.debug2("ApplicationServer: send_session_status: %s" %
                      (response))
        if response is False:
            Logger.warn("ApplicationServer: unable to send session status")
        else:
            response.close()
            response = None

    def send_session_dump(self, session):
        dumps = {}

        for path in glob.glob(
                os.path.join(Config.spool_dir, "sessions dump archive",
                             "%s %s-*" % (session.id, session.user.name))):
            try:
                f = file(path, "r")
            except IOError, err:
                continue

            data = f.read()
            f.close()

            name = os.path.basename(path)
            name = name[len("%s %s-" % (session.id, session.user.name)):]

            dumps[name] = data

        data = session.log.get_full_log()
        if len(data) > 0:
            dumps["server.log"] = data

        try:
            doc = Document()
            rootNode = doc.createElement('session')
            rootNode.setAttribute("id", session.id)

            for (name, data) in dumps.items():
                textNode = doc.createTextNode(base64.encodestring(data))

                node = doc.createElement('dump')
                node.setAttribute("name", name)
                node.appendChild(textNode)

                rootNode.appendChild(node)

            doc.appendChild(rootNode)
        except Exception:
            Logger.exception("ApplicationServer: send_session_dump")

        response = self.smManager.send_packet("/session/dump", doc)
        Logger.debug2("ApplicationServer: send_session_dump: %s" % (response))
        if response is False:
            Logger.warn("ApplicationServer: unable to send session dump")
        else:
            response.close()
            response = None
Esempio n. 11
0
class Role(AbstractRole):
    sessions = {}
    sessions_spooler = None

    def __init__(self, main_instance):
        AbstractRole.__init__(self, main_instance)
        self.sessions = {}
        self.locked_sessions = []
        self.sessions_spooler = MPQueue.Queue()
        self.sessions_spooler2 = MPQueue.Queue()
        self.sessions_sync = MPQueue.Queue()
        self.logging_queue = MPQueue.Queue()

        self.manager = Manager(self.main_instance.smRequestManager)
        self.threads = []

        self.applications = {}
        self.applications_id_SM = {}
        self.applications_mutex = threading.Lock()

        self.static_apps = ApplicationsStatic(
            self.main_instance.smRequestManager)
        self.static_apps_must_synced = False
        self.static_apps_lock = threading.Lock()

        self.scripts = Scripts(self.main_instance.smRequestManager)
        self.scripts_lock = threading.Lock()
        self.scripts_must_synced = False

    def init(self):
        Logger.debug("ApplicationServer init")

        try:
            TS.getList()
        except Exception:
            Logger.exception("RDP server dialog failed ... exiting")
            return

        if not System.groupExist(self.manager.ts_group_name):
            Logger.error("The group '%s' doesn't exist" %
                         (self.manager.ts_group_name))
            return False

        if not System.groupExist(self.manager.ovd_group_name):
            if not System.groupCreate(self.manager.ovd_group_name):
                return False

        if not self.manager.purgeGroup():
            Logger.error("Unable to purge group")
            return False

        if Config.clean_dump_archive:
            self.purgeArchives()

        if Config.thread_count is None:
            cpuInfos = System.getCPUInfos()
            vcpu = cpuInfos[0]
            ram_total = System.getRAMTotal()
            ram = int(round(ram_total / 1024.0 / 1024.0))

            nb_thread = int(round(1 + (ram + vcpu * 2) / 3))
        else:
            nb_thread = Config.thread_count

        Logger._instance.setQueue(self.logging_queue, True)
        for _ in xrange(nb_thread):
            self.threads.append(
                SessionManagement(self.manager, self.sessions_spooler,
                                  self.sessions_spooler2, self.sessions_sync,
                                  self.logging_queue))

        if self.canManageApplications():
            self.apt = Apt()
            self.apt.init()
            self.threads.append(self.apt)

        Logger.info(
            "ApplicationServer:: retrieve all applications installed (can take some time)"
        )
        self.updateApplications()

        return True

    @staticmethod
    def getName():
        return "ApplicationServer"

    def switch_to_production(self):
        self.setStaticAppsMustBeSync(True)
        self.setScriptsMustBeSync(True)

    def order_stop(self):
        AbstractRole.order_stop(self)

        for session in self.sessions.values():
            self.manager.session_switch_status(
                session, Session.SESSION_STATUS_WAIT_DESTROY)
            self.spool_action("destroy", session.id)

    def force_stop(self):
        AbstractRole.force_stop(self)

        for thread in self.threads:
            thread.terminate()

        for thread in self.threads:
            thread.join()

    def finalize(self):
        Logger._instance.setThreadedMode(False)

        self.update_locked_sessions()

        for session in self.sessions.values():
            self.manager.session_switch_status(
                session, Session.SESSION_STATUS_WAIT_DESTROY)

        System.prepareForSessionActions()

        cleaner = SessionManagement(self.manager, None, None, None, None)
        for session in self.sessions.values():
            session.end_status = Session.SESSION_END_STATUS_SHUTDOWN
            cleaner.destroy_session(session)

        self.manager.purgeGroup()
        Profile.cleanup()

    def get_session_from_login(self, login_):
        for session in self.sessions.values():
            if session["login"] == login_:
                return session

        return None

    def run(self):
        Logger._instance.lock.acquire()
        Logger._instance.close()
        for thread in self.threads:
            thread.start()
            thread.known_death = False
        Logger._instance.lock.release()

        t0_update_app = time.time()

        self.status = Role.STATUS_RUNNING

        while self.loop:
            if self.status == Role.STATUS_ERROR:
                break

            if self.status == Role.STATUS_STOPPING and len(self.sessions) == 0:
                break

            while True:
                try:
                    session = self.sessions_sync.get_nowait()
                except Queue.Empty, e:
                    break
                except (EOFError, socket.error):
                    Logger.debug("APS:: Role stopping")
                    self.status = Role.STATUS_ERROR
                    break

                if not self.sessions.has_key(session.id):
                    Logger.warn(
                        "Session %s do not exist, session information are ignored"
                        % (session.id))
                    continue

                if session.status != self.sessions[session.id].status:
                    self.manager.session_switch_status(session, session.status)

                if session.status == Session.SESSION_STATUS_DESTROYED:
                    del (self.sessions[session.id])
                else:
                    self.sessions[session.id] = session

            if self.status == Role.STATUS_ERROR:
                break

            self.update_locked_sessions()

            for session in self.sessions.values():
                try:
                    ts_id = TS.getSessionID(session.user.name)
                except Exception:
                    Logger.exception("RDP server dialog failed ... exiting")
                    self.status = Role.STATUS_ERROR
                    break

                if ts_id is None:
                    if session.status in [
                            Session.SESSION_STATUS_ACTIVE,
                            Session.SESSION_STATUS_INACTIVE
                    ]:
                        Logger.error(
                            "Weird, running session %s no longer exist" %
                            (session.id))

                        if session.status == Session.SESSION_STATUS_ACTIVE:
                            # User has logged off
                            session.end_status = Session.SESSION_END_STATUS_NORMAL

                        if session.status not in [
                                Session.SESSION_STATUS_WAIT_DESTROY,
                                Session.SESSION_STATUS_DESTROYED,
                                Session.SESSION_STATUS_ERROR
                        ]:
                            self.manager.session_switch_status(
                                session, Session.SESSION_STATUS_WAIT_DESTROY)
                            self.spool_action("destroy", session.id)
                    continue

                try:
                    ts_status = TS.getState(ts_id)
                except Exception:
                    Logger.exception("RDP server dialog failed ... exiting")
                    self.status = Role.STATUS_ERROR
                    break

                if session.status == Session.SESSION_STATUS_INITED:
                    if ts_status is TS.STATUS_LOGGED:
                        self.manager.session_switch_status(
                            session, Session.SESSION_STATUS_ACTIVE)
                        if not session.domain.manage_user():
                            self.spool_action("manage_new", session.id)

                        continue

                    if ts_status is TS.STATUS_DISCONNECTED:
                        self.manager.session_switch_status(
                            session, Session.SESSION_STATUS_INACTIVE)
                        continue

                if session.status == Session.SESSION_STATUS_ACTIVE and ts_status is TS.STATUS_DISCONNECTED:
                    self.manager.session_switch_status(
                        session, Session.SESSION_STATUS_INACTIVE)
                    continue

                if session.status == Session.SESSION_STATUS_INACTIVE and ts_status is TS.STATUS_LOGGED:
                    self.manager.session_switch_status(
                        session, Session.SESSION_STATUS_ACTIVE)
                    if not session.domain.manage_user():
                        self.spool_action("manage_new", session.id)
                    continue

            if self.isStaticAppsMustBeSync():
                self.static_apps.synchronize()
                self.setStaticAppsMustBeSync(False)

            if self.isScriptsMustBeSync():
                self.scripts.synchronize()
                self.setScriptsMustBeSync(False)

            for thread in self.threads:
                if not thread.known_death and not thread.is_alive():
                    Logger.error(
                        "SessionManagement process (pid: %d, name: %s) is dead (return code: %d) while managed session '%s'"
                        % (thread.pid, repr(thread.name), thread.exitcode,
                           repr(thread.current_session_id.value)))
                    thread.known_death = True

            t1 = time.time()
            if t1 - t0_update_app > 30:
                self.updateApplications()

                t0_update_app = time.time()
            else:
                time.sleep(1)