วิธีการผูกอุปกรณ์ USB ในชื่อคงที่?


43

ฉันมี Arduino ซึ่งบางครั้งก็ถูกผูกมัด/dev/ttyUSB0และบางครั้ง/dev/ttyUSB1ทำให้สคริปต์ของฉันล้มเหลว

ฉันไม่ต้องการให้ระบุเป็นไปได้ทั้งหมดของการที่อุปกรณ์ของฉันอาจจะมี /dev/arduinoแต่ฉันอยากจะมีมันจะผูกพันแบบคงที่บางแห่งเช่น

ฉันจะบรรลุสิ่งนั้นได้อย่างไร


4
เพียงแค่เขียนกฎ udev-simple ซึ่งจะกำหนด symlink / dev / arduino ให้กับการประดิษฐ์ที่ถูกต้องโดย VID & PID
Eddy_Em


1
หลังจากที่คุณเปลี่ยนกฎแล้วโปรดดูวิธีโหลด udev กฎโดยไม่ต้องรีบูต
Gilles 'หยุดความชั่วร้าย'

คำตอบ:


41

ตามที่แนะนำคุณสามารถเพิ่มกฎ udev ฉันแก้ไข/etc/udev/rules.d/10-local.rulesเพื่อให้มี:

ACTION=="add", ATTRS{idVendor}=="0403", ATTRS{idProduct}=="6001", SYMLINK+="my_uart"

คุณสามารถตรวจสอบตัวแปรของอุปกรณ์ของคุณโดยการเรียกใช้

udevadm info -a -p  $(udevadm info -q path -n /dev/ttyUSB0)

มีแนวทางเชิงลึกเพิ่มเติมที่คุณสามารถอ่านได้ที่http://www.reactivated.net/writing_udev_rules.html


ทำงานเหมือนจับใจ หนึ่งคำถาม: วิธีการออกudevam? และมันก็เป็นสิ่งสำคัญที่จะทราบว่าmy_uartจะสร้าง symlink /dev/my_uartภายใต้ ฉันเขียน/dev/arduinoครั้งแรกและมันล้มเหลวในขณะที่arduinoเพียงพอ
k0pernikus

udevadmควรออกด้วยตัวเองเมื่อเสร็จแล้ว
Kotte

จากนั้นด้วยเหตุผลที่ไม่ทราบสาเหตุบางอย่างมันจะทำให้เซสชันเทอร์มินัลค้างกับราสเบอร์รี่ Pi ของฉันในขณะที่สร้างรายงาน
k0pernikus

35

ไวยากรณ์ของกฎด้านบนอาจทำงานกับการกระจายบางอย่าง แต่ไม่สามารถใช้งานได้กับฉัน (Raspbian) ตั้งแต่ฉันไม่เคยพบเอกสารฉบับเดียวที่อธิบายทุก ins ลึกหนาบางผมเขียนของตัวเองที่จะพบได้ที่นี่ นี่คือสิ่งที่มันเดือดลงไป
1. ค้นหาว่ามีอะไรใน ttyUSB:

dmesg | grep ttyUSB  

2. รายการคุณสมบัติทั้งหมดของอุปกรณ์:

udevadm info --name=/dev/ttyUSBx --attribute-walk

(ด้วยหมายเลขอุปกรณ์ของคุณแทน x, แน่นอน) เลือกชุดตัวระบุที่ไม่ซ้ำกันเช่น idVendor + idProduct คุณอาจต้องใช้ SerialNumber หากคุณมีอุปกรณ์มากกว่าหนึ่งเครื่องที่มี idVendor และ idProduct เดียวกัน SerialNumbers ควรจะไม่ซ้ำกันสำหรับแต่ละอุปกรณ์
3. สร้างไฟล์ที่/etc/udev/rules.d/99-usb-serial.rulesมีลักษณะคล้ายบรรทัดนี้:

SUBSYSTEM=="tty", ATTRS{idVendor}=="1234", ATTRS{idProduct}=="5678", SYMLINK+="your_device_name" 

(สมมติว่าคุณไม่จำเป็นต้องมีหมายเลขซีเรียลและแน่นอนด้วยหมายเลขสำหรับ idVendor และ idProduct ที่คุณพบในขั้นตอนที่ 2
4. โหลดกฎใหม่:

sudo udevadm trigger

5. ตรวจสอบสิ่งที่เกิดขึ้น:

ls -l /dev/your_device_name  

จะแสดงหมายเลข ttyUSB ที่ symlink ไป หากเป็น/dev/ttyUSB1เช่นนั้นให้ยืนยันว่าใครเป็นเจ้าของและกลุ่มนั้นอยู่ในกลุ่มใด:

ls -l /dev/ttyUSB1   

จากนั้นเพียงเพื่อความสนุกของมัน:

udevadm test -a -p  $(udevadm info -q path -n /dev/your_device_name)

ดังนั้นจะมีวิธีการแก้ปัญหาถ้าidVendorและidProductเหมือนกันหรือไม่ (เซ็นเซอร์สองตัวต่อกับโมดูล USB รุ่น UART เดียวกัน)
Steven Lu

@StevenLu ใช่ดูขั้นตอนที่ 2 ทำudevadm info --name=/dev/ttyUSB1 --attribute-walkทั้งสองอุปกรณ์และค้นหาหมายเลขซีเรียลควรเป็นหมายเลขเฉพาะสำหรับแต่ละอุปกรณ์ หากเซ็นเซอร์ของคุณไม่มีหมายเลขซีเรียลคุณสามารถระบุได้ไหม
RolfBly

มันยอดเยี่ยมมากฉันจะรายงานกลับมาเมื่อฉันลองทำสิ่งนี้
Steven Lu

USB ดองเกิล $ 2 ถึง UART ของฉันมีหมายเลขซีเรียล 0001 ไม่สามารถพูดได้ว่าฉันประหลาดใจ ดูเหมือนว่าฉันต้องระบุเซ็นเซอร์ตามโปรโตคอลการส่งออกของพวกเขา
Steven Lu

@StevenLu โชคไม่ดี ตัวแปลง FTDI USB-UART มีหมายเลขซีเรียลที่เป็นเอกลักษณ์คือ AFAIK bucks พิเศษบางอย่าง แต่ใช้เวลาน้อยลงในการพัฒนา
RolfBly

9

ปัญหาอุปกรณ์หลายอุปกรณ์เหมือนกัน

ฉันมี Rasperry Pi กับกล้องสี่ตัว ผมใช้เวลากับ Pix fswebcamซึ่งระบุกล้องเป็น../dev/video0 video3บางครั้งกล้องvideo0, vide02, video4และvideo6แต่เราสามารถลืมเกี่ยวกับว่าสำหรับในตอนนี้

ฉันต้องการ ID ถาวรเพื่อระบุหมายเลขกล้องเพื่อให้เช่นvideo0เป็นกล้องเดียวกันเสมอเพราะฉันใส่ภาพ โชคไม่ดีที่สิ่งนี้ไม่ได้เกิดขึ้นอย่างน่าเชื่อถือ - ในการบู๊ตกล้องจะระบุเป็นvideo0.. video3แต่ไม่เหมือนกันเสมอไป

กล้องทุกตัวมี ID และหมายเลขซีเรียลเหมือนกัน

การแก้ปัญหานี้เกี่ยวข้องกับกฎของ udev แต่มีเบ็ดตกปลามากมายเช่นกัน

หากคุณออกคำสั่ง

udevadm info –attribute-walk –path=/dev/video0

คุณได้รับการพูดนานน่าเบื่อของเอาท์พุท แต่บิตสำคัญคือ

KERNEL=”video0”, SUBSYSTEM=”video4linux” and KERNELS=”1:1.2.4:1.0”.

KERNELS bit เป็นพอร์ตฮับ USB ด้วยกล้องสี่ตัวมีสี่ตัวนี้ - พวกมันจะไม่เปลี่ยนเมื่อทำการรีบูท แต่สิ่งที่video{x}เกี่ยวข้องกับพอร์ตอาจเปลี่ยนไป

ดังนั้นเราจึงจำเป็นต้องมีกฎ udev เพื่อผูกหมายเลขวิดีโอเข้ากับพอร์ตฮับ USB - เช่น:

KERNEL==”video0”,SUBSYSTEM=”video4linux”,KERNELS==”1:1.2.4:1.0”,SYMLINK+=”camera0” 

ดูเรียบง่าย - เข้าถึงกล้องด้วย

fswebcam –d  $realpath /dev/camera0

ยกเว้นว่าจะไม่ทำงาน - หากคุณใส่สิ่งนี้ในกฎ udev และระบบได้จัดสรร video0 (ขณะบู๊ต) ไปยังพอร์ตอื่นกฎ udev จะถูกละเว้น symlink ไปโดยทั่วไปว่า/dev/camera0 no such deviceสแควร์หนึ่ง

สิ่งที่เราต้องการคือการผูก symlink กับที่อยู่ฮับ USB ไม่ใช่video{x}ตัวเลข มันใช้โปรแกรม Python

ขั้นตอนแรกคือการทำงาน

fswebcam –d /dev/video${x}  tst.jpg

สำหรับxระหว่าง 1 และ 8 การมีอยู่ของtst.jpgหลังจากการโทรแต่ละครั้งจะระบุว่ามีกล้องในหมายเลขวิดีโอนี้หรือไม่ จากนี้ทำรายการหมายเลขวิดีโอที่ใช้งานอยู่ ประสบการณ์ของฉันคือว่ามันเป็นอย่างใดอย่างหนึ่ง0,1,2,3หรือ0,2,4,6สำหรับกล้องที่ฉันได้ใช้

บางคนอาจสร้างรายชื่อนี้โดยใช้กระบวนการที่แตกต่างกัน

จากนั้นสำหรับแต่ละหมายเลขวิดีโอในรายการที่เรียกใช้

udevadm info –attribute-walk –path=/dev/videox > dd

และสารสกัดจากKERNELS= line ddจากกระบวนการนี้คุณจะพบรายการที่อยู่พอร์ต USB สำหรับกล้อง เรียงลำดับรายการนี้เพื่อให้ในขั้นตอนถัดไปคุณจะดำเนินการตามลำดับเดียวกันเสมอ เรียกสิ่งนี้ว่า "รายการที่อยู่"

เรียกใช้udevadm … > ddสิ่งนั้นอีกครั้งและสร้างรายการที่ดูเหมือน

KERNEL==”video0”, SUBSYSTEM=”video4linux”,KERNELS==”1:1.2.4:1.0 ”,SYMLINK+=”camerax”. Call this the “video list”.

ตอนนี้ผ่านรายการที่อยู่ - สำหรับแต่ละรายการค้นหารายการที่เกี่ยวข้องจากรายการวิดีโอ สร้างรายการใหม่ที่ดูเหมือนคอลเลกชันบรรทัดเช่น

KERNEL==”video0”, SUBSYSTEM=”video4linux”,KERNELS==”1:1.2.4:1.0 ”,SYMLINK+=”camera2”

x (หมายเลข symlink) จะถูกแทนที่ด้วยหมายเลขลำดับในรายการที่อยู่

ตอนนี้คุณมีกฎ udev ที่ใช้งานได้ symlink ที่เชื่อมโยงกับที่อยู่ฮับ USB ไม่ว่าหมายเลขวิดีโอใดจะถูกจัดสรรให้กับพอร์ตนั้นเมื่อบู๊ต

/etc/udev/rules.d/cam.rulesเขียนรายการสุดท้ายลงในไฟล์ เรียกใช้udevadm triggerเพื่อเปิดใช้งานและดำเนินการเสร็จสิ้น /dev/camera2จะเป็นกล้องเดียวกัน (พอร์ต USB) โดยไม่คำนึงถึงหมายเลขวิดีโอ


ยินดีต้อนรับสู่ unix stackexchange โปรดจัดรูปแบบคำตอบของคุณโดยใช้ markdown ฉันแค่ทำเพื่อคุณ โปรดทราบว่าเราต้องการคำตอบให้ตรงประเด็น สิ่งนี้อ่านเพิ่มเติมเช่นรายการบล็อก (ซึ่งไม่ได้เลวร้ายอย่างสิ้นเชิง) แต่ก็ไม่มีประโยชน์ที่จะอ่านเกี่ยวกับวิธีการที่ไม่ได้ผล คุณอาจจะสนใจเรื่องนั้น
k0pernikus

ขอโทษ ฉันใหม่ที่นี่ ฉันค้นคว้าปัญหานี้มาหลายเดือนแล้ว ฉันพบว่าคนอื่น ๆ กำลังดิ้นรนกับปัญหาเดียวกันและฉันไม่พบคำตอบที่เหมาะกับฉัน แค่ฉันรู้คุณจะแนะนำให้ฉันโพสต์สิ่งนี้ได้ที่ไหน ฉันควบคุมตัวเองและไม่รวมแหล่งที่มาของ Python :-)
Ian Boag

1

/dev/serial/by-idผมก็สามารถที่จะหาอุปกรณ์ที่ไม่ซ้ำกันใน ฉันยังไม่ได้ลองรีบูต แต่ไฟล์ในไดเรกทอรีนั้นเป็นเพียงลิงก์ไปยังไฟล์อุปกรณ์ที่เหมาะสม ( ttyACM[0-9])

ฉันกำลังเรียกใช้ arch linux บน Raspberry Pi แต่ฉันพบเจอพวกเขาเพียงแค่ทำfindชื่อไฟล์ที่มี "Arduino" โปรแกรมไพ ธ อนของฉันทำงานได้ดีโดยใช้ไฟล์เหล่านั้นเป็นอุปกรณ์เพื่ออ่าน / เขียนข้อมูลไปยัง / จาก Arduinos ของฉัน (จนถึงสองตัวใน Pi เดียว)


0

เพิ่งจะบอกว่าข้างต้นใช้งานได้สำหรับฉันและยังติดตั้งอุปกรณ์ให้ฉันโดยอัตโนมัติหลังจากที่ฉันวางรายการใน / etc / fstab (และมันก็เรียกว่า umount หลังจากลบแท่ง)

กล่าวคือ

/ etc / fstab

# See /etc/udev/rules.d/5-usb-disk.rules
/dev/backup     /vol/backup     ext4    defaults,errors=remount-ro 0       1

cat /etc/udev/rules.d/5-usb-stick.rules

#
# the next line creates a symlink to this disk drive called /dev/backup 
# i.e.
#   root:# ls -la /dev/backup 
#   lrwxrwxrwx 1 root root 3 Jul 22 19:33 /dev/backup -> sg0

# Backup usb stick - create /dev/backup
# ATTRS{model}=="Cruzer Blade    "
ACTION=="add", ATTRS{model}=="Cruzer Blade    ", SYMLINK+="backup"

# Clean up after removal  
ACTION=="remove", ATTRS{model}=="Cruzer Blade    ", RUN+="/bin/umount /vol/backup"

ดังนั้นหลังจากใส่แท่ง usb ของฉันฉันได้รับ:

root:# mount | grep sd
/dev/sda1 on /vol/backup type ext4 (rw,relatime,errors=remount-ro,data=ordered)
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.