Files
StarPilot/openpilot/starpilot/galaxy/device_name.py
T
firestar5683 408ab1a9d7 Galaxy device and remote-access exports
Expose Galaxy device, crash and remote-access services with the bundled frpc license.
2026-10-03 22:34:37 +00:00

64 lines
2.2 KiB
Python

"""A device-owned display name, independent of driving preferences and pairing credentials."""
import json
import os
from pathlib import Path
import stat
import tempfile
def validate_name(value: str) -> str:
if type(value) is not str or len(value) > 40 or any(ord(char) < 32 or 127 <= ord(char) < 160 or 0xD800 <= ord(char) <= 0xDFFF for char in value):
raise ValueError('Use a name of up to 40 characters without control characters')
return value.strip()
class DeviceName:
FILE = 'device-name.json'
def __init__(self, root: Path):
self.root = root
def _directory(self) -> None:
info = self.root.lstat()
if not stat.S_ISDIR(info.st_mode) or info.st_uid != os.geteuid() or info.st_mode & 0o077:
raise OSError('Device name storage is unavailable')
def read(self) -> str:
if not self.root.exists():
return ''
self._directory()
try:
fd = os.open(self.root / self.FILE, os.O_RDONLY | os.O_NOFOLLOW)
except FileNotFoundError:
return ''
with os.fdopen(fd, encoding='utf-8') as stream:
info = os.fstat(stream.fileno())
if not stat.S_ISREG(info.st_mode) or info.st_uid != os.geteuid() or info.st_mode & 0o077 or info.st_size > 512:
raise OSError('Device name storage is unavailable')
data = json.load(stream)
if type(data) is not dict or set(data) != {'version', 'name'} or type(data['version']) is not int or data['version'] != 1:
raise ValueError('Invalid device name')
return validate_name(data['name'])
def save(self, name: str) -> str:
name = validate_name(name)
self.root.mkdir(mode=0o700, parents=True, exist_ok=True)
self._directory()
fd, temporary = tempfile.mkstemp(prefix='.device-name-', dir=self.root)
try:
with os.fdopen(fd, 'w', encoding='utf-8') as stream:
json.dump({'version': 1, 'name': name}, stream, ensure_ascii=False)
stream.flush()
os.fsync(stream.fileno())
os.replace(temporary, self.root / self.FILE)
directory = os.open(self.root, os.O_RDONLY | os.O_DIRECTORY | os.O_NOFOLLOW)
try:
os.fsync(directory)
finally:
os.close(directory)
finally:
if os.path.exists(temporary):
os.unlink(temporary)
return self.read()