fix: add udev rules for Kneron USB access on Linux
Without udev rules, only root can access Kneron USB devices, so the web server running as a normal user cannot scan/connect to devices. Adds /etc/udev/rules.d/99-kneron.rules granting MODE=0666 for KL520 (PID 0x0100), KL720 KDP (PID 0x0200), KL720 KDP2 (PID 0x0720). Applied in both GUI installer (platform_linux.go installLibusb) and CLI installer (install.sh setup_libusb). Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
parent
b7e6da4c05
commit
559d0fdb8a
@ -43,18 +43,51 @@ func removeSystemLink() {
|
||||
}
|
||||
|
||||
func installLibusb(installDir string) error {
|
||||
// Check if already installed
|
||||
if _, err := exec.LookPath("lsusb"); err == nil {
|
||||
return nil
|
||||
// Install libusb if not present
|
||||
if exec.Command("dpkg", "-s", "libusb-1.0-0-dev").Run() != nil {
|
||||
cmd := exec.Command("pkexec", "apt-get", "install", "-y", "libusb-1.0-0-dev")
|
||||
if out, err := cmd.CombinedOutput(); err != nil {
|
||||
return fmt.Errorf("apt install libusb failed: %s — %w", string(out), err)
|
||||
}
|
||||
}
|
||||
|
||||
cmd := exec.Command("pkexec", "apt-get", "install", "-y", "libusb-1.0-0-dev")
|
||||
if out, err := cmd.CombinedOutput(); err != nil {
|
||||
return fmt.Errorf("apt install libusb failed: %s — %w", string(out), err)
|
||||
}
|
||||
// Install udev rules so non-root users can access Kneron USB devices
|
||||
installKneronUdevRules()
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// installKneronUdevRules writes a udev rule file granting non-root access
|
||||
// to Kneron KL520/KL720 USB devices and reloads udev.
|
||||
func installKneronUdevRules() {
|
||||
const rulesPath = "/etc/udev/rules.d/99-kneron.rules"
|
||||
|
||||
// Skip if already installed
|
||||
if _, err := os.Stat(rulesPath); err == nil {
|
||||
return
|
||||
}
|
||||
|
||||
rules := strings.Join([]string{
|
||||
`# Kneron KL520`,
|
||||
`SUBSYSTEM=="usb", ATTR{idVendor}=="3231", ATTR{idProduct}=="0100", MODE="0666"`,
|
||||
`# Kneron KL720 KDP (legacy)`,
|
||||
`SUBSYSTEM=="usb", ATTR{idVendor}=="3231", ATTR{idProduct}=="0200", MODE="0666"`,
|
||||
`# Kneron KL720 KDP2`,
|
||||
`SUBSYSTEM=="usb", ATTR{idVendor}=="3231", ATTR{idProduct}=="0720", MODE="0666"`,
|
||||
}, "\n") + "\n"
|
||||
|
||||
// Write to a temp file then move with pkexec (needs root)
|
||||
tmpFile := filepath.Join(os.TempDir(), "99-kneron.rules")
|
||||
if err := os.WriteFile(tmpFile, []byte(rules), 0644); err != nil {
|
||||
return
|
||||
}
|
||||
defer os.Remove(tmpFile)
|
||||
|
||||
exec.Command("pkexec", "cp", tmpFile, rulesPath).Run()
|
||||
exec.Command("pkexec", "udevadm", "control", "--reload-rules").Run()
|
||||
exec.Command("pkexec", "udevadm", "trigger").Run()
|
||||
}
|
||||
|
||||
func checkLibusbInstalled() bool {
|
||||
return exec.Command("dpkg", "-s", "libusb-1.0-0-dev").Run() == nil
|
||||
}
|
||||
|
||||
@ -116,6 +116,30 @@ setup_python_venv() {
|
||||
info "Installing pyusb ..."
|
||||
"$VENV_DIR/bin/pip" install --quiet pyusb
|
||||
|
||||
# Install KneronPLUS SDK wheel if bundled
|
||||
local scripts_dir="$INSTALL_DIR/scripts"
|
||||
local os_type
|
||||
os_type="$(uname -s)"
|
||||
local kp_wheel=""
|
||||
|
||||
if [ "$os_type" = "Darwin" ]; then
|
||||
# macOS wheels are stored in scripts/macos/ subdirectory
|
||||
kp_wheel="$(ls "$scripts_dir"/macos/KneronPLUS*.whl 2>/dev/null | head -1)"
|
||||
fi
|
||||
if [ -z "$kp_wheel" ]; then
|
||||
kp_wheel="$(ls "$scripts_dir"/KneronPLUS*.whl 2>/dev/null | head -1)"
|
||||
fi
|
||||
|
||||
if [ -n "$kp_wheel" ]; then
|
||||
info "Installing Kneron SDK: $(basename "$kp_wheel") ..."
|
||||
"$VENV_DIR/bin/pip" install --quiet "$kp_wheel" || true
|
||||
|
||||
# On macOS, ad-hoc codesign bundled dylibs for Gatekeeper
|
||||
if [ "$os_type" = "Darwin" ]; then
|
||||
find "$VENV_DIR" -path "*/kp/lib/*.dylib" -exec codesign --force --sign - {} \; 2>/dev/null || true
|
||||
fi
|
||||
fi
|
||||
|
||||
info "Python environment ready"
|
||||
}
|
||||
|
||||
@ -141,6 +165,22 @@ setup_libusb() {
|
||||
info "Installing libusb ..."
|
||||
sudo apt-get install -y libusb-1.0-0-dev
|
||||
fi
|
||||
|
||||
# Install udev rules so non-root users can access Kneron USB devices
|
||||
if [ ! -f /etc/udev/rules.d/99-kneron.rules ]; then
|
||||
info "Installing Kneron USB udev rules ..."
|
||||
cat <<'UDEV' | sudo tee /etc/udev/rules.d/99-kneron.rules >/dev/null
|
||||
# Kneron KL520
|
||||
SUBSYSTEM=="usb", ATTR{idVendor}=="3231", ATTR{idProduct}=="0100", MODE="0666"
|
||||
# Kneron KL720 KDP (legacy)
|
||||
SUBSYSTEM=="usb", ATTR{idVendor}=="3231", ATTR{idProduct}=="0200", MODE="0666"
|
||||
# Kneron KL720 KDP2
|
||||
SUBSYSTEM=="usb", ATTR{idVendor}=="3231", ATTR{idProduct}=="0720", MODE="0666"
|
||||
UDEV
|
||||
sudo udevadm control --reload-rules
|
||||
sudo udevadm trigger
|
||||
info "udev rules installed. Please re-plug Kneron USB devices."
|
||||
fi
|
||||
fi
|
||||
}
|
||||
|
||||
@ -186,6 +226,12 @@ setup_launchd_service() {
|
||||
<string>${INSTALL_DIR}/edge-ai-server</string>
|
||||
</array>
|
||||
|
||||
<key>EnvironmentVariables</key>
|
||||
<dict>
|
||||
<key>PATH</key>
|
||||
<string>/usr/local/bin:/opt/homebrew/bin:/usr/bin:/bin:/usr/sbin:/sbin</string>
|
||||
</dict>
|
||||
|
||||
<key>WorkingDirectory</key>
|
||||
<string>${INSTALL_DIR}</string>
|
||||
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user