import os import operator import platform from types import SimpleNamespace from cereal import car from openpilot.common.params import Params from openpilot.system.hardware import HARDWARE, PC, TICI from openpilot.system.manager.process import PythonProcess, NativeProcess, DaemonProcess WEBCAM = os.getenv("USE_WEBCAM") is not None def driverview(started: bool, params: Params, CP: car.CarParams, frogpilot_toggles: SimpleNamespace) -> bool: return started or params.get_bool("IsDriverViewEnabled") def notcar(started: bool, params: Params, CP: car.CarParams, frogpilot_toggles: SimpleNamespace) -> bool: return started and CP.notCar def iscar(started: bool, params: Params, CP: car.CarParams, frogpilot_toggles: SimpleNamespace) -> bool: return started and not CP.notCar def logging(started: bool, params: Params, CP: car.CarParams, frogpilot_toggles: SimpleNamespace) -> bool: run = (not CP.notCar) or not params.get_bool("DisableLogging") return started and run def ublox_available() -> bool: return os.path.exists('/dev/ttyHS0') and not os.path.exists('/persist/comma/use-quectel-gps') def ublox(started: bool, params: Params, CP: car.CarParams, frogpilot_toggles: SimpleNamespace) -> bool: use_ublox = ublox_available() if use_ublox != params.get_bool("UbloxAvailable"): params.put_bool("UbloxAvailable", use_ublox) return started and use_ublox def joystick(started: bool, params: Params, CP: car.CarParams, frogpilot_toggles: SimpleNamespace) -> bool: return started and params.get_bool("JoystickDebugMode") def not_joystick(started: bool, params: Params, CP: car.CarParams, frogpilot_toggles: SimpleNamespace) -> bool: return started and not params.get_bool("JoystickDebugMode") def long_maneuver(started: bool, params: Params, CP: car.CarParams, frogpilot_toggles: SimpleNamespace) -> bool: return started and params.get_bool("LongitudinalManeuverMode") def not_long_maneuver(started: bool, params: Params, CP: car.CarParams, frogpilot_toggles: SimpleNamespace) -> bool: return started and not params.get_bool("LongitudinalManeuverMode") def qcomgps(started: bool, params: Params, CP: car.CarParams, frogpilot_toggles: SimpleNamespace) -> bool: return started and not ublox_available() def always_run(started: bool, params: Params, CP: car.CarParams, frogpilot_toggles: SimpleNamespace) -> bool: return True def only_onroad(started: bool, params: Params, CP: car.CarParams, frogpilot_toggles: SimpleNamespace) -> bool: return started def only_offroad(started: bool, params: Params, CP: car.CarParams, frogpilot_toggles: SimpleNamespace) -> bool: return not started def or_(*fns): return lambda *args: operator.or_(*(fn(*args) for fn in fns)) def and_(*fns): return lambda *args: operator.and_(*(fn(*args) for fn in fns)) # FrogPilot variables def allow_logging(started: bool, params: Params, CP: car.CarParams, frogpilot_toggles: SimpleNamespace) -> bool: return not frogpilot_toggles.no_logging def allow_uploads(started: bool, params: Params, CP: car.CarParams, frogpilot_toggles: SimpleNamespace) -> bool: return params.get_bool("AlwaysAllowUploads") or not frogpilot_toggles.no_uploads or frogpilot_toggles.no_onroad_uploads def run_speed_limit_filler(started: bool, params: Params, CP: car.CarParams, frogpilot_toggles: SimpleNamespace) -> bool: return frogpilot_toggles.speed_limit_filler procs = [ DaemonProcess("manage_athenad", "system.athena.manage_athenad", "AthenadPid"), NativeProcess("loggerd", "system/loggerd", ["./loggerd"], and_(allow_logging, logging)), NativeProcess("encoderd", "system/loggerd", ["./encoderd"], and_(allow_logging, only_onroad)), NativeProcess("stream_encoderd", "system/loggerd", ["./encoderd", "--stream"], notcar), PythonProcess("logmessaged", "system.logmessaged", always_run), NativeProcess("camerad", "system/camerad", ["./camerad"], driverview, enabled=not WEBCAM), PythonProcess("webcamerad", "tools.webcam.camerad", driverview, enabled=WEBCAM), PythonProcess("proclogd", "system.proclogd", and_(allow_logging, only_onroad), enabled=platform.system() != "Darwin"), PythonProcess("journald", "system.journald", and_(allow_logging, only_onroad), platform.system() != "Darwin"), PythonProcess("micd", "system.micd", iscar), PythonProcess("timed", "system.timed", always_run, enabled=not PC), PythonProcess("modeld", "frogpilot.tinygrad_modeld.tinygrad_modeld", only_onroad), PythonProcess("dmonitoringmodeld", "frogpilot.tinygrad_modeld.dmonitoringmodeld", driverview, enabled=(WEBCAM or not PC)), PythonProcess("sensord", "system.sensord.sensord", only_onroad, enabled=not PC), PythonProcess("soundd", "selfdrive.ui.soundd", driverview), PythonProcess("locationd", "selfdrive.locationd.locationd", only_onroad), NativeProcess("_pandad", "selfdrive/pandad", ["./pandad"], always_run, enabled=False), PythonProcess("calibrationd", "selfdrive.locationd.calibrationd", only_onroad), PythonProcess("torqued", "selfdrive.locationd.torqued", only_onroad), PythonProcess("controlsd", "selfdrive.controls.controlsd", and_(not_joystick, iscar)), PythonProcess("joystickd", "tools.joystick.joystickd", or_(joystick, notcar)), PythonProcess("selfdrived", "selfdrive.selfdrived.selfdrived", only_onroad), PythonProcess("card", "selfdrive.car.card", only_onroad), PythonProcess("deleter", "system.loggerd.deleter", always_run), PythonProcess("dmonitoringd", "selfdrive.monitoring.dmonitoringd", driverview, enabled=(WEBCAM or not PC)), PythonProcess("qcomgpsd", "system.qcomgpsd.qcomgpsd", qcomgps, enabled=TICI), PythonProcess("pandad", "selfdrive.pandad.pandad", always_run), PythonProcess("paramsd", "selfdrive.locationd.paramsd", only_onroad), PythonProcess("lagd", "selfdrive.locationd.lagd", only_onroad), PythonProcess("ubloxd", "system.ubloxd.ubloxd", ublox, enabled=TICI), PythonProcess("pigeond", "system.ubloxd.pigeond", ublox, enabled=TICI), PythonProcess("plannerd", "selfdrive.controls.plannerd", not_long_maneuver), PythonProcess("maneuversd", "tools.longitudinal_maneuvers.maneuversd", long_maneuver), PythonProcess("radard", "selfdrive.controls.radard", only_onroad), PythonProcess("hardwared", "system.hardware.hardwared", always_run), PythonProcess("tombstoned", "system.tombstoned", always_run, enabled=not PC), PythonProcess("updated", "system.updated.updated", always_run, enabled=not PC), PythonProcess("uploader", "system.loggerd.uploader", allow_uploads), PythonProcess("statsd", "system.statsd", always_run), PythonProcess("feedbackd", "selfdrive.ui.feedback.feedbackd", only_onroad), # debug procs NativeProcess("bridge", "cereal/messaging", ["./bridge"], notcar), PythonProcess("webrtcd", "system.webrtc.webrtcd", notcar), PythonProcess("webjoystick", "tools.bodyteleop.web", notcar), PythonProcess("joystick", "tools.joystick.joystick_control", and_(joystick, iscar)), ] # FrogPilot variables device_type = HARDWARE.get_device_type() if device_type in ("tici", "tizi"): procs.append(NativeProcess("ui", "selfdrive/ui", ["./ui"], always_run, watchdog_max_dt=5)) else: # C4 (mici) runs the Python raylib UI path; keep watchdog parity with C3/C3X. procs.append(PythonProcess("ui", "selfdrive.ui.ui", always_run, watchdog_max_dt=5)) procs += [ PythonProcess("device_syncd", "frogpilot.system.device_syncd", always_run), PythonProcess("frogpilot_process", "frogpilot.frogpilot_process", always_run), NativeProcess("mapd", "frogpilot/navigation", ["./mapd"], always_run), PythonProcess("the_pond", "frogpilot.system.the_pond.the_pond", always_run, nice=19), PythonProcess("galaxy", "frogpilot.system.galaxy.galaxy", always_run, nice=19), PythonProcess("speed_limit_filler", "frogpilot.system.speed_limit_filler", run_speed_limit_filler), ] managed_processes = {p.name: p for p in procs}