mirror of
https://github.com/sunnypilot/sunnypilot.git
synced 2026-07-24 01:12:06 +08:00
Compare commits
3 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| d5b5652165 | |||
| 2c334ede44 | |||
| bf1b93f757 |
@@ -1,20 +1,3 @@
|
||||
#!/usr/bin/env bash
|
||||
set -euo pipefail
|
||||
IFS=$'\n\t'
|
||||
|
||||
# On any failure, run the fallback launcher
|
||||
trap 'exec ./launch_chffrplus.sh' ERR
|
||||
C3_LAUNCH_SH="./openpilot/sunnypilot/system/hardware/c3/launch_chffrplus.sh"
|
||||
|
||||
MODEL="$(tr -d '\0' < "/sys/firmware/devicetree/base/model")"
|
||||
export MODEL
|
||||
|
||||
if [ "$MODEL" = "comma tici" ]; then
|
||||
# Force a failure if the launcher doesn't exist
|
||||
[ -x "$C3_LAUNCH_SH" ] || false
|
||||
|
||||
# If it exists, run it
|
||||
exec "$C3_LAUNCH_SH"
|
||||
fi
|
||||
|
||||
exec ./launch_chffrplus.sh
|
||||
|
||||
@@ -23,13 +23,14 @@ def main():
|
||||
cloudlog.info("plannerd got CarParamsSP")
|
||||
|
||||
gps_location_service = get_gps_location_service(params)
|
||||
ignore_services = ["liveMapDataSP", gps_location_service]
|
||||
|
||||
ldw = LaneDepartureWarning()
|
||||
longitudinal_planner = LongitudinalPlanner(CP, CP_SP)
|
||||
pm = messaging.PubMaster(['longitudinalPlan', 'driverAssistance', 'longitudinalPlanSP'])
|
||||
sm = messaging.SubMaster(['carControl', 'carState', 'controlsState', 'liveParameters', 'radarState', 'modelV2', 'selfdriveState',
|
||||
'liveMapDataSP', 'carStateSP', gps_location_service],
|
||||
poll='carState')
|
||||
poll='carState', ignore_alive=ignore_services, ignore_avg_freq=ignore_services, ignore_valid=ignore_services)
|
||||
|
||||
while True:
|
||||
sm.update()
|
||||
|
||||
@@ -20,6 +20,7 @@ from openpilot.system.ui.widgets.list_view import button_item
|
||||
|
||||
from openpilot.system.ui.sunnypilot.widgets.html_render import HtmlModalSP
|
||||
from openpilot.system.ui.sunnypilot.widgets.list_view import toggle_item_sp
|
||||
from openpilot.selfdrive.ui.sunnypilot.layouts.settings.external_storage import external_storage_item
|
||||
|
||||
PREBUILT_PATH = os.path.join(Paths.comma_home(), "prebuilt") if PC else "/data/openpilot/prebuilt"
|
||||
|
||||
@@ -52,7 +53,11 @@ class DeveloperLayoutSP(DeveloperLayout):
|
||||
|
||||
self.error_log_btn = button_item(tr("Error Log"), tr("VIEW"), tr("View the error log for sunnypilot crashes."), callback=self._on_error_log_clicked)
|
||||
|
||||
self.items: list = [self.show_advanced_controls, self.enable_github_runner_toggle, self.enable_copyparty_toggle, self.prebuilt_toggle, self.error_log_btn,]
|
||||
self.external_storage = external_storage_item(tr("External Storage"), description=tr("Extend your comma device's storage by inserting a USB drive " +
|
||||
"into the aux port."))
|
||||
|
||||
self.items: list = [self.show_advanced_controls, self.enable_github_runner_toggle, self.enable_copyparty_toggle, self.prebuilt_toggle,
|
||||
self.external_storage, self.error_log_btn,]
|
||||
|
||||
@staticmethod
|
||||
def _on_prebuilt_toggled(state):
|
||||
|
||||
@@ -0,0 +1,261 @@
|
||||
"""
|
||||
Copyright (c) 2021-, Haibin Wen, sunnypilot, and a number of other contributors.
|
||||
|
||||
This file is part of sunnypilot and is licensed under the MIT License.
|
||||
See the LICENSE.md file in the root directory for more details.
|
||||
"""
|
||||
import pyray as rl
|
||||
import threading
|
||||
import subprocess
|
||||
import copy
|
||||
from enum import Enum
|
||||
from collections.abc import Callable
|
||||
|
||||
from openpilot.common.params import Params
|
||||
from openpilot.common.hardware import PC
|
||||
from openpilot.system.ui.lib.application import gui_app, FontWeight
|
||||
from openpilot.system.ui.lib.text_measure import measure_text_cached
|
||||
from openpilot.system.ui.lib.multilang import tr, tr_noop
|
||||
from openpilot.system.ui.widgets import DialogResult
|
||||
from openpilot.system.ui.widgets.button import Button, ButtonStyle
|
||||
from openpilot.system.ui.widgets.confirm_dialog import alert_dialog, ConfirmDialog
|
||||
from openpilot.system.ui.widgets.list_view import (
|
||||
ItemAction,
|
||||
ListItem,
|
||||
BUTTON_HEIGHT,
|
||||
BUTTON_BORDER_RADIUS,
|
||||
BUTTON_FONT_SIZE,
|
||||
BUTTON_WIDTH,
|
||||
)
|
||||
|
||||
VALUE_FONT_SIZE = 48
|
||||
|
||||
|
||||
class ExternalStorageState(Enum):
|
||||
DISABLED = tr_noop("DISABLED")
|
||||
LOADING = tr_noop("LOADING")
|
||||
CHECK = tr_noop("CHECK")
|
||||
MOUNT = tr_noop("MOUNT")
|
||||
UNMOUNT = tr_noop("UNMOUNT")
|
||||
FORMAT = tr_noop("FORMAT")
|
||||
|
||||
|
||||
class ExternalStorageAction(ItemAction):
|
||||
MAX_WIDTH = 500
|
||||
|
||||
def __init__(self):
|
||||
super().__init__(self.MAX_WIDTH, True)
|
||||
|
||||
self._params = Params()
|
||||
self._error_message = ""
|
||||
self._text_font = gui_app.font(FontWeight.NORMAL)
|
||||
|
||||
self._button = Button(
|
||||
"",
|
||||
click_callback=self._handle_button_click,
|
||||
button_style=ButtonStyle.LIST_ACTION,
|
||||
border_radius=BUTTON_BORDER_RADIUS,
|
||||
font_size=BUTTON_FONT_SIZE,
|
||||
)
|
||||
|
||||
self._value_text = ""
|
||||
self._formatting = False
|
||||
self._refresh_pending = False
|
||||
|
||||
self._state = ExternalStorageState.CHECK
|
||||
self._refresh_state()
|
||||
self.refresh()
|
||||
|
||||
def set_touch_valid_callback(self, callback):
|
||||
def wrapped():
|
||||
if self._state == ExternalStorageState.DISABLED:
|
||||
return False
|
||||
return callback()
|
||||
super().set_touch_valid_callback(wrapped)
|
||||
self._button.set_touch_valid_callback(wrapped)
|
||||
|
||||
def _run(self, cmd: str) -> bool:
|
||||
return subprocess.call(["sh", "-c", cmd]) == 0
|
||||
|
||||
def _run_output(self, cmd: str) -> str:
|
||||
try:
|
||||
out = subprocess.check_output(["sh", "-c", cmd], universal_newlines=True)
|
||||
return out.strip()
|
||||
except Exception:
|
||||
return ""
|
||||
|
||||
def _render(self, rect: rl.Rectangle) -> bool:
|
||||
if self._error_message:
|
||||
msg = copy.copy(self._error_message)
|
||||
gui_app.set_modal_overlay(alert_dialog(msg))
|
||||
self._error_message = ""
|
||||
|
||||
if self._value_text:
|
||||
text_size = measure_text_cached(self._text_font, self._value_text, VALUE_FONT_SIZE)
|
||||
rl.draw_text_ex(
|
||||
self._text_font,
|
||||
self._value_text,
|
||||
(rect.x + rect.width - BUTTON_WIDTH - text_size.x - 30,
|
||||
rect.y + (rect.height - text_size.y) / 2),
|
||||
VALUE_FONT_SIZE,
|
||||
1.0,
|
||||
rl.Color(170, 170, 170, 255),
|
||||
)
|
||||
|
||||
button_rect = rl.Rectangle(
|
||||
rect.x + rect.width - BUTTON_WIDTH,
|
||||
rect.y + (rect.height - BUTTON_HEIGHT) / 2,
|
||||
BUTTON_WIDTH,
|
||||
BUTTON_HEIGHT
|
||||
)
|
||||
self._button.set_rect(button_rect)
|
||||
self._button.set_text(tr(self._state.value))
|
||||
self._button.set_enabled(self._state not in (ExternalStorageState.LOADING,
|
||||
ExternalStorageState.DISABLED))
|
||||
self._button.render(button_rect)
|
||||
return False
|
||||
|
||||
def _refresh_state(self):
|
||||
if PC:
|
||||
self._state = ExternalStorageState.DISABLED
|
||||
self._button.set_enabled(False)
|
||||
self._value_text = ""
|
||||
|
||||
def debounced_refresh(self):
|
||||
if self._refresh_pending:
|
||||
return
|
||||
self._refresh_pending = True
|
||||
|
||||
def _timer():
|
||||
import time
|
||||
time.sleep(0.25)
|
||||
self._refresh_pending = False
|
||||
self.refresh()
|
||||
|
||||
threading.Thread(target=_timer, daemon=True).start()
|
||||
|
||||
def refresh(self):
|
||||
def _work():
|
||||
is_mounted = self._run("findmnt -n /mnt/external_realdata")
|
||||
has_drive = self._run("lsblk -f /dev/sdg")
|
||||
has_fs = self._run("lsblk -f /dev/sdg1 | grep -q ext4")
|
||||
has_label = self._run("blkid /dev/sdg1 | grep -q 'LABEL=\"openpilot\"'")
|
||||
|
||||
info = ""
|
||||
if is_mounted and has_label:
|
||||
info = self._run_output(
|
||||
"df -h /mnt/external_realdata | awk 'NR==2 {print $3 \"/\" $2}'"
|
||||
)
|
||||
|
||||
def apply():
|
||||
if self._formatting:
|
||||
self._value_text = tr("formatting")
|
||||
self._state = ExternalStorageState.FORMAT
|
||||
return
|
||||
|
||||
if not has_drive:
|
||||
self._value_text = tr("insert drive")
|
||||
self._state = ExternalStorageState.CHECK
|
||||
|
||||
elif not has_fs or not has_label:
|
||||
self._value_text = tr("needs format")
|
||||
self._state = ExternalStorageState.FORMAT
|
||||
|
||||
elif is_mounted:
|
||||
self._value_text = info
|
||||
self._state = ExternalStorageState.UNMOUNT
|
||||
|
||||
else:
|
||||
self._value_text = tr("drive detected")
|
||||
self._state = ExternalStorageState.MOUNT
|
||||
|
||||
apply()
|
||||
|
||||
threading.Thread(target=_work, daemon=True).start()
|
||||
|
||||
def _handle_button_click(self):
|
||||
st = self._state
|
||||
|
||||
if st == ExternalStorageState.DISABLED:
|
||||
return
|
||||
|
||||
if st in (ExternalStorageState.CHECK, ExternalStorageState.MOUNT):
|
||||
self.mount_storage()
|
||||
|
||||
elif st == ExternalStorageState.UNMOUNT:
|
||||
self.unmount_storage()
|
||||
|
||||
elif st == ExternalStorageState.FORMAT:
|
||||
dialog = ConfirmDialog(
|
||||
tr("Are you sure you want to format this drive? This will erase all data."),
|
||||
confirm_text=tr("Format"),
|
||||
cancel_text=tr("Cancel"),
|
||||
)
|
||||
gui_app.set_modal_overlay(dialog, callback=self._confirm_format)
|
||||
|
||||
def _confirm_format(self, result: DialogResult):
|
||||
if result == DialogResult.CONFIRM:
|
||||
self.format_storage()
|
||||
|
||||
def mount_storage(self):
|
||||
self._value_text = tr("mounting")
|
||||
self._state = ExternalStorageState.LOADING
|
||||
|
||||
def _work():
|
||||
cmd = """
|
||||
sudo mount -o remount,rw / &&
|
||||
sudo mkdir -p /mnt/external_realdata &&
|
||||
(grep -q '/dev/sdg1 /mnt/external_realdata' /etc/fstab ||
|
||||
echo '/dev/sdg1 /mnt/external_realdata ext4 defaults,nofail 0 2' >> /etc/fstab) &&
|
||||
sudo systemctl daemon-reexec &&
|
||||
sudo mount /mnt/external_realdata &&
|
||||
sudo chown -R comma:comma /mnt/external_realdata &&
|
||||
sudo chmod -R 775 /mnt/external_realdata &&
|
||||
sudo mount -o remount,ro /
|
||||
"""
|
||||
subprocess.call(["sh", "-c", cmd])
|
||||
self.debounced_refresh()
|
||||
|
||||
threading.Thread(target=_work, daemon=True).start()
|
||||
|
||||
def unmount_storage(self):
|
||||
self._value_text = tr("unmounting")
|
||||
self._state = ExternalStorageState.LOADING
|
||||
|
||||
def _work():
|
||||
subprocess.call(["sh", "-c", "sudo umount /mnt/external_realdata"])
|
||||
self.debounced_refresh()
|
||||
|
||||
threading.Thread(target=_work, daemon=True).start()
|
||||
|
||||
def format_storage(self):
|
||||
self._formatting = True
|
||||
self._value_text = tr("formatting")
|
||||
self._state = ExternalStorageState.LOADING
|
||||
|
||||
def _work():
|
||||
cmd = """
|
||||
sudo wipefs -a /dev/sdg &&
|
||||
sudo parted -s /dev/sdg mklabel gpt mkpart primary ext4 0% 100% &&
|
||||
sudo mkfs.ext4 -F -L openpilot /dev/sdg1
|
||||
"""
|
||||
exitcode = subprocess.call(["sh", "-c", cmd])
|
||||
|
||||
def apply():
|
||||
self._formatting = False
|
||||
if exitcode == 0:
|
||||
self.mount_storage()
|
||||
else:
|
||||
self._value_text = tr("needs format")
|
||||
self._state = ExternalStorageState.FORMAT
|
||||
|
||||
apply()
|
||||
|
||||
threading.Thread(target=_work, daemon=True).start()
|
||||
|
||||
def external_storage_item(title: str | Callable[[], str], description: str | Callable[[], str]) -> ListItem:
|
||||
return ListItem(
|
||||
title=title,
|
||||
description=description,
|
||||
action_item=ExternalStorageAction()
|
||||
)
|
||||
@@ -1,3 +0,0 @@
|
||||
# C3 specific hardware code
|
||||
|
||||
`c3` is known as `tici` and comma three by comma. Not to confuse it with `c3x` which is known as `tizi`.
|
||||
@@ -1,84 +0,0 @@
|
||||
[
|
||||
{
|
||||
"name": "xbl",
|
||||
"url": "https://commadist.azureedge.net/agnosupdate/xbl-effa23294138e2297b85a5b482a885184c437b5ab25d74f2a62d4fce4e68f63b.img.xz",
|
||||
"hash": "effa23294138e2297b85a5b482a885184c437b5ab25d74f2a62d4fce4e68f63b",
|
||||
"hash_raw": "effa23294138e2297b85a5b482a885184c437b5ab25d74f2a62d4fce4e68f63b",
|
||||
"size": 3282256,
|
||||
"sparse": false,
|
||||
"full_check": true,
|
||||
"has_ab": true,
|
||||
"ondevice_hash": "ed61a650bea0c56652dd0fc68465d8fc722a4e6489dc8f257630c42c6adcdc89"
|
||||
},
|
||||
{
|
||||
"name": "xbl_config",
|
||||
"url": "https://commadist.azureedge.net/agnosupdate/xbl_config-63d019efed684601f145ef37628e62c8da73f5053a8e51d7de09e72b8b11f97c.img.xz",
|
||||
"hash": "63d019efed684601f145ef37628e62c8da73f5053a8e51d7de09e72b8b11f97c",
|
||||
"hash_raw": "63d019efed684601f145ef37628e62c8da73f5053a8e51d7de09e72b8b11f97c",
|
||||
"size": 98124,
|
||||
"sparse": false,
|
||||
"full_check": true,
|
||||
"has_ab": true,
|
||||
"ondevice_hash": "b12801ffaa81e58e3cef914488d3b447e35483ba549b28c6cd9deb4814c3265f"
|
||||
},
|
||||
{
|
||||
"name": "abl",
|
||||
"url": "https://commadist.azureedge.net/agnosupdate/abl-32a2174b5f764e95dfc54cf358ba01752943b1b3b90e626149c3da7d5f1830b6.img.xz",
|
||||
"hash": "32a2174b5f764e95dfc54cf358ba01752943b1b3b90e626149c3da7d5f1830b6",
|
||||
"hash_raw": "32a2174b5f764e95dfc54cf358ba01752943b1b3b90e626149c3da7d5f1830b6",
|
||||
"size": 274432,
|
||||
"sparse": false,
|
||||
"full_check": true,
|
||||
"has_ab": true,
|
||||
"ondevice_hash": "32a2174b5f764e95dfc54cf358ba01752943b1b3b90e626149c3da7d5f1830b6"
|
||||
},
|
||||
{
|
||||
"name": "aop",
|
||||
"url": "https://commadist.azureedge.net/agnosupdate/aop-21370172e590bd4ea907a558bcd6df20dc7a6c7d38b8e62fdde18f4a512ba9e9.img.xz",
|
||||
"hash": "21370172e590bd4ea907a558bcd6df20dc7a6c7d38b8e62fdde18f4a512ba9e9",
|
||||
"hash_raw": "21370172e590bd4ea907a558bcd6df20dc7a6c7d38b8e62fdde18f4a512ba9e9",
|
||||
"size": 184364,
|
||||
"sparse": false,
|
||||
"full_check": true,
|
||||
"has_ab": true,
|
||||
"ondevice_hash": "c1be2f4aac5b3af49b904b027faec418d05efd7bd5144eb4fdfcba602bcf2180"
|
||||
},
|
||||
{
|
||||
"name": "devcfg",
|
||||
"url": "https://commadist.azureedge.net/agnosupdate/devcfg-d7d7e52963bbedbbf8a7e66847579ca106a0a729ce2cf60f4b8d8ea4b535d620.img.xz",
|
||||
"hash": "d7d7e52963bbedbbf8a7e66847579ca106a0a729ce2cf60f4b8d8ea4b535d620",
|
||||
"hash_raw": "d7d7e52963bbedbbf8a7e66847579ca106a0a729ce2cf60f4b8d8ea4b535d620",
|
||||
"size": 40336,
|
||||
"sparse": false,
|
||||
"full_check": true,
|
||||
"has_ab": true,
|
||||
"ondevice_hash": "17b229668b20305ff8fa3cd5f94716a3aaa1e5bf9d1c24117eff7f2f81ae719f"
|
||||
},
|
||||
{
|
||||
"name": "boot",
|
||||
"url": "https://commadist.azureedge.net/agnosupdate/boot-0191529aa97d90d1fa04b472d80230b777606459e1e1e9e2323c9519839827b4.img.xz",
|
||||
"hash": "0191529aa97d90d1fa04b472d80230b777606459e1e1e9e2323c9519839827b4",
|
||||
"hash_raw": "0191529aa97d90d1fa04b472d80230b777606459e1e1e9e2323c9519839827b4",
|
||||
"size": 18515968,
|
||||
"sparse": false,
|
||||
"full_check": true,
|
||||
"has_ab": true,
|
||||
"ondevice_hash": "492ae27f569e8db457c79d0e358a7a6297d1a1c685c2b1ae6deba7315d3a6cb0"
|
||||
},
|
||||
{
|
||||
"name": "system",
|
||||
"url": "https://commadist.azureedge.net/agnosupdate/system-e0007afa5d1026671c1943d44bb7f7ad26259f673392dd00a03073a2870df087.img.xz",
|
||||
"hash": "1468d50b7ad0fda0f04074755d21e786e3b1b6ca5dd5b17eb2608202025e6126",
|
||||
"hash_raw": "e0007afa5d1026671c1943d44bb7f7ad26259f673392dd00a03073a2870df087",
|
||||
"size": 5368709120,
|
||||
"sparse": true,
|
||||
"full_check": false,
|
||||
"has_ab": true,
|
||||
"ondevice_hash": "242aa5adad1c04e1398e00e2440d1babf962022eb12b89adf2e60ee3068946e7",
|
||||
"alt": {
|
||||
"hash": "e0007afa5d1026671c1943d44bb7f7ad26259f673392dd00a03073a2870df087",
|
||||
"url": "https://commadist.azureedge.net/agnosupdate/system-e0007afa5d1026671c1943d44bb7f7ad26259f673392dd00a03073a2870df087.img",
|
||||
"size": 5368709120
|
||||
}
|
||||
}
|
||||
]
|
||||
@@ -1,100 +0,0 @@
|
||||
#!/usr/bin/env bash
|
||||
|
||||
SP_C3_DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" >/dev/null && pwd )"
|
||||
DIR="$( cd "$SP_C3_DIR/../../../../.." >/dev/null 2>&1 && pwd )"
|
||||
|
||||
source "$SP_C3_DIR/launch_env.sh"
|
||||
|
||||
function agnos_init {
|
||||
# TODO: move this to agnos
|
||||
sudo rm -f /data/etc/NetworkManager/system-connections/*.nmmeta
|
||||
|
||||
# set success flag for current boot slot
|
||||
sudo abctl --set_success
|
||||
|
||||
# TODO: do this without udev in AGNOS
|
||||
# udev does this, but sometimes we startup faster
|
||||
sudo chgrp gpu /dev/adsprpc-smd /dev/ion /dev/kgsl-3d0
|
||||
sudo chmod 660 /dev/adsprpc-smd /dev/ion /dev/kgsl-3d0
|
||||
|
||||
|
||||
if [ $(< /VERSION) != "$AGNOS_VERSION" ]; then
|
||||
AGNOS_PY="$DIR/openpilot/common/hardware/tici/agnos.py"
|
||||
MANIFEST="$SP_C3_DIR/agnos.json"
|
||||
if $AGNOS_PY --verify $MANIFEST; then
|
||||
sudo reboot
|
||||
fi
|
||||
$DIR/openpilot/common/hardware/tici/updater $AGNOS_PY $MANIFEST
|
||||
fi
|
||||
}
|
||||
|
||||
function launch {
|
||||
# Remove orphaned git lock if it exists on boot
|
||||
[ -f "$DIR/.git/index.lock" ] && rm -f $DIR/.git/index.lock
|
||||
|
||||
# Check to see if there's a valid overlay-based update available. Conditions
|
||||
# are as follows:
|
||||
#
|
||||
# 1. The DIR init file has to exist, with a newer modtime than anything in
|
||||
# the DIR Git repo. This checks for local development work or the user
|
||||
# switching branches/forks, which should not be overwritten.
|
||||
# 2. The FINALIZED consistent file has to exist, indicating there's an update
|
||||
# that completed successfully and synced to disk.
|
||||
|
||||
if [ -f "${DIR}/.overlay_init" ]; then
|
||||
find ${DIR}/.git -newer ${DIR}/.overlay_init | grep -q '.' 2> /dev/null
|
||||
if [ $? -eq 0 ]; then
|
||||
echo "${DIR} has been modified, skipping overlay update installation"
|
||||
else
|
||||
if [ -f "${STAGING_ROOT}/finalized/.overlay_consistent" ]; then
|
||||
if [ ! -d /data/safe_staging/old_openpilot ]; then
|
||||
echo "Valid overlay update found, installing"
|
||||
LAUNCHER_LOCATION="${BASH_SOURCE[0]}"
|
||||
|
||||
mv $DIR /data/safe_staging/old_openpilot
|
||||
mv "${STAGING_ROOT}/finalized" $DIR
|
||||
cd $DIR
|
||||
|
||||
echo "Restarting launch script ${LAUNCHER_LOCATION}"
|
||||
unset AGNOS_VERSION
|
||||
exec "${LAUNCHER_LOCATION}"
|
||||
else
|
||||
echo "openpilot backup found, not updating"
|
||||
# TODO: restore backup? This means the updater didn't start after swapping
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
|
||||
# handle pythonpath
|
||||
ln -sfn $(pwd) /data/pythonpath
|
||||
export PYTHONPATH="$PWD"
|
||||
|
||||
# submodule package symlinks for PYTHONPATH imports on device.
|
||||
# on PC these come from editable installs via pyproject.toml / uv.
|
||||
ln -sfn msgq_repo/msgq msgq
|
||||
ln -sfn opendbc_repo/opendbc opendbc
|
||||
ln -sfn rednose_repo/rednose rednose
|
||||
ln -sfn teleoprtc_repo/teleoprtc teleoprtc
|
||||
ln -sfn tinygrad_repo/tinygrad tinygrad
|
||||
|
||||
# hardware specific init
|
||||
if [ -f /AGNOS ]; then
|
||||
agnos_init
|
||||
fi
|
||||
|
||||
# write tmux scrollback to a file
|
||||
tmux capture-pane -pq -S-1000 > /tmp/launch_log
|
||||
|
||||
# start manager
|
||||
cd $DIR/openpilot/system/manager
|
||||
if [ ! -f $DIR/prebuilt ]; then
|
||||
./build.py
|
||||
fi
|
||||
./manager.py
|
||||
|
||||
# if broken, keep on screen error
|
||||
while true; do sleep 1; done
|
||||
}
|
||||
|
||||
launch
|
||||
@@ -1,13 +0,0 @@
|
||||
#!/usr/bin/env bash
|
||||
|
||||
export OMP_NUM_THREADS=1
|
||||
export MKL_NUM_THREADS=1
|
||||
export NUMEXPR_NUM_THREADS=1
|
||||
export OPENBLAS_NUM_THREADS=1
|
||||
export VECLIB_MAXIMUM_THREADS=1
|
||||
|
||||
if [ -z "$AGNOS_VERSION" ]; then
|
||||
export AGNOS_VERSION="12.8"
|
||||
fi
|
||||
|
||||
export STAGING_ROOT="/data/safe_staging"
|
||||
Reference in New Issue
Block a user