Автомонтаж USB-флешек в Debian

10

Я запускаю Debian Squeeze на подключаемом компьютере (только SSH, без графического интерфейса), и я пытаюсь сделать так, чтобы при подключении USB-накопителя он автоматически монтировался.

Что я сделал, так это установил, autofsкоторый из того, что я собираю, обрабатывает автомонтирование, если оно знает, где находится устройство /dev.

Проблема в том, что флешка не всегда на одном и том же имени устройства. Иногда это /dev/sdc1, иногда /dev/sdd1и т. Д.

Я понимаю, что для исправления этой ситуации мне нужно udevубедиться, что USB-накопителю всегда присваивается одно и то же имя.

Я получил следующую информацию из udevadm:

Udevadm info starts with the device specified by the devpath and then
walks up the chain of parent devices. It prints for every device
found, all possible attributes in the udev rules key format.
A rule to match, can be composed by the attributes of the device
and the attributes from one single parent device.

  looking at device '/block/sdd/sdd1':
    KERNEL=="sdd1"
    SUBSYSTEM=="block"
    DRIVER==""
    ATTR{partition}=="1"
    ATTR{start}=="63"
    ATTR{size}=="129339"
    ATTR{ro}=="0"
    ATTR{alignment_offset}=="0"
    ATTR{discard_alignment}=="0"
    ATTR{stat}=="      31      244      275      190        0        0        0        0        0      190      190"
    ATTR{inflight}=="       0        0"

  looking at parent device '/devices/platform/orion-ehci.0/usb1/1-1/1-1.2/1-1.2:1.0/host8/target8:0:0/8:0:0:0/block/sdd':
    KERNELS=="sdd"
    SUBSYSTEMS=="block"
    DRIVERS==""
    ATTRS{range}=="16"
    ATTRS{ext_range}=="256"
    ATTRS{removable}=="1"
    ATTRS{ro}=="0"
    ATTRS{size}=="129439"
    ATTRS{alignment_offset}=="0"
    ATTRS{discard_alignment}=="0"
    ATTRS{capability}=="51"
    ATTRS{stat}=="      56      727      783      520        0        0        0        0        0      520      520"
    ATTRS{inflight}=="       0        0"
    ATTRS{events}=="media_change"
    ATTRS{events_async}==""
    ATTRS{events_poll_msecs}=="-1"

  looking at parent device '/devices/platform/orion-ehci.0/usb1/1-1/1-1.2/1-1.2:1.0/host8/target8:0:0/8:0:0:0':
    KERNELS=="8:0:0:0"
    SUBSYSTEMS=="scsi"
    DRIVERS=="sd"
    ATTRS{device_blocked}=="0"
    ATTRS{type}=="0"
    ATTRS{scsi_level}=="3"
    ATTRS{vendor}=="        "
    ATTRS{model}=="Flash Disk      "
    ATTRS{rev}=="2.00"
    ATTRS{state}=="running"
    ATTRS{timeout}=="30"
    ATTRS{iocounterbits}=="32"
    ATTRS{iorequest_cnt}=="0x90"
    ATTRS{iodone_cnt}=="0x90"
    ATTRS{ioerr_cnt}=="0x0"
    ATTRS{modalias}=="scsi:t-0x00"
    ATTRS{evt_media_change}=="0"
    ATTRS{queue_depth}=="1"
    ATTRS{queue_type}=="none"
    ATTRS{max_sectors}=="240"

  looking at parent device '/devices/platform/orion-ehci.0/usb1/1-1/1-1.2/1-1.2:1.0/host8/target8:0:0':
    KERNELS=="target8:0:0"
    SUBSYSTEMS=="scsi"
    DRIVERS==""

  looking at parent device '/devices/platform/orion-ehci.0/usb1/1-1/1-1.2/1-1.2:1.0/host8':
    KERNELS=="host8"
    SUBSYSTEMS=="scsi"
    DRIVERS==""

  looking at parent device '/devices/platform/orion-ehci.0/usb1/1-1/1-1.2/1-1.2:1.0':
    KERNELS=="1-1.2:1.0"
    SUBSYSTEMS=="usb"
    DRIVERS=="usb-storage"
    ATTRS{bInterfaceNumber}=="00"
    ATTRS{bAlternateSetting}==" 0"
    ATTRS{bNumEndpoints}=="02"
    ATTRS{bInterfaceClass}=="08"
    ATTRS{bInterfaceSubClass}=="06"
    ATTRS{bInterfaceProtocol}=="50"
    ATTRS{modalias}=="usb:v1976p6025d0100dc00dsc00dp00ic08isc06ip50"
    ATTRS{supports_autosuspend}=="1"

  looking at parent device '/devices/platform/orion-ehci.0/usb1/1-1/1-1.2':
    KERNELS=="1-1.2"
    SUBSYSTEMS=="usb"
    DRIVERS=="usb"
    ATTRS{configuration}==""
    ATTRS{bNumInterfaces}==" 1"
    ATTRS{bConfigurationValue}=="1"
    ATTRS{bmAttributes}=="80"
    ATTRS{bMaxPower}=="100mA"
    ATTRS{urbnum}=="383"
    ATTRS{idVendor}=="1976"
    ATTRS{idProduct}=="6025"
    ATTRS{bcdDevice}=="0100"
    ATTRS{bDeviceClass}=="00"
    ATTRS{bDeviceSubClass}=="00"
    ATTRS{bDeviceProtocol}=="00"
    ATTRS{bNumConfigurations}=="1"
    ATTRS{bMaxPacketSize0}=="64"
    ATTRS{speed}=="12"
    ATTRS{busnum}=="1"
    ATTRS{devnum}=="11"
    ATTRS{devpath}=="1.2"
    ATTRS{version}==" 1.10"
    ATTRS{maxchild}=="0"
    ATTRS{quirks}=="0x0"
    ATTRS{avoid_reset_quirk}=="0"
    ATTRS{authorized}=="1"

  looking at parent device '/devices/platform/orion-ehci.0/usb1/1-1':
    KERNELS=="1-1"
    SUBSYSTEMS=="usb"
    DRIVERS=="usb"
    ATTRS{configuration}==""
    ATTRS{bNumInterfaces}==" 1"
    ATTRS{bConfigurationValue}=="1"
    ATTRS{bmAttributes}=="e0"
    ATTRS{bMaxPower}=="100mA"
    ATTRS{urbnum}=="197"
    ATTRS{idVendor}=="1a40"
    ATTRS{idProduct}=="0101"
    ATTRS{bcdDevice}=="0111"
    ATTRS{bDeviceClass}=="09"
    ATTRS{bDeviceSubClass}=="00"
    ATTRS{bDeviceProtocol}=="01"
    ATTRS{bNumConfigurations}=="1"
    ATTRS{bMaxPacketSize0}=="64"
    ATTRS{speed}=="480"
    ATTRS{busnum}=="1"
    ATTRS{devnum}=="2"
    ATTRS{devpath}=="1"
    ATTRS{version}==" 2.00"
    ATTRS{maxchild}=="4"
    ATTRS{quirks}=="0x0"
    ATTRS{avoid_reset_quirk}=="0"
    ATTRS{authorized}=="1"
    ATTRS{product}=="USB 2.0 Hub"

  looking at parent device '/devices/platform/orion-ehci.0/usb1':
    KERNELS=="usb1"
    SUBSYSTEMS=="usb"
    DRIVERS=="usb"
    ATTRS{configuration}==""
    ATTRS{bNumInterfaces}==" 1"
    ATTRS{bConfigurationValue}=="1"
    ATTRS{bmAttributes}=="e0"
    ATTRS{bMaxPower}=="  0mA"
    ATTRS{urbnum}=="24"
    ATTRS{idVendor}=="1d6b"
    ATTRS{idProduct}=="0002"
    ATTRS{bcdDevice}=="0206"
    ATTRS{bDeviceClass}=="09"
    ATTRS{bDeviceSubClass}=="00"
    ATTRS{bDeviceProtocol}=="01"
    ATTRS{bNumConfigurations}=="1"
    ATTRS{bMaxPacketSize0}=="64"
    ATTRS{speed}=="480"
    ATTRS{busnum}=="1"
    ATTRS{devnum}=="1"
    ATTRS{devpath}=="0"
    ATTRS{version}==" 2.00"
    ATTRS{maxchild}=="1"
    ATTRS{quirks}=="0x0"
    ATTRS{avoid_reset_quirk}=="0"
    ATTRS{authorized}=="1"
    ATTRS{manufacturer}=="Linux 2.6.38.8 ehci_hcd"
    ATTRS{product}=="Marvell Orion EHCI"
    ATTRS{serial}=="orion-ehci.0"
    ATTRS{authorized_default}=="1"

  looking at parent device '/devices/platform/orion-ehci.0':
    KERNELS=="orion-ehci.0"
    SUBSYSTEMS=="platform"
    DRIVERS=="orion-ehci"
    ATTRS{modalias}=="platform:orion-ehci"

  looking at parent device '/devices/platform':
    KERNELS=="platform"
    SUBSYSTEMS==""
    DRIVERS==""

Я пытался написать udevправила, чтобы заставить USB-флешку взять имя, /dev/usbstickно пока не увенчался успехом.

Может ли кто-нибудь помочь с тем правилом, которое мне нужно указать в файле правил, чтобы эта флешка всегда получала одно и то же имя?

- Или есть ли гораздо более простой способ автоматического подключения USB-накопителя, который мне не хватает полностью?

ОБНОВИТЬ

Хорошо, поэтому я добился определенного прогресса. Я добавил следующее правило:

SUBSYSTEMS=="scsi", ATTRS{model}=="Flash Disk ", DRIVERS=="sd", NAME="usbstick-%k" RUN+="mkdir /mnt/usbstick-%k; mount /dev/usbstick-%k /mnt/usbstick-%k"

Я знаю, что это все еще требует некоторой работы с точки зрения обработки добавления / удаления, но пока это просто базовый тест.

Результатом этого является то, что мне теперь удается получить три новых узла устройства /dev, а именно /dev/usbstick-sdc, /dev/usbstick-sdc1и usbstick-sg2.

Однако я обнаружил, что код в RUNразделе выполняется только один раз и просто создает каталог mnt/usbstick-sdc. Я также обнаружил, что каталог всегда пуст, поэтому что-то явно идет не так! (хотя я делаю успехи).

джон
источник
Эта секунда /dev/sdc1должна была быть sdd1? И вы можете использовать blkidдля уникальной идентификации диска (ну, на самом деле, раздел; он изменится, если вы переформатируете).
Кевин
Правильно, только что исправил это. Все, что я хочу, это чтобы USB-карта была подключена к какой-либо директории. Я почти уверен, что должен использовать udevправило для создания узлов устройств для каждого раздела, но я не уверен, для какого уровня udevadmвывода будут создаваться правила!
джон
Ваше правило выглядит слишком сложным. Попробуйте сделать простой, с одним ACTION==, одним KERNEL==и одним ATTRS{something}==(это вполне выполнимо - это то, что я использую). Кроме того, рассмотрите возможность запуска единственного сценария из цепочки команд в RUN+=.
rozcietrzewiacz 16.11.11
Спасибо за совет, но остается вопрос: на какой уровень дерева устройств я должен ориентироваться со своим правилом? Все это кажется очень запутанным, и на самом деле не так много информации в Интернете, чтобы объяснить это. Я действительно ценю время, которое вы потратили, чтобы объяснить это мне до сих пор, я чувствую, что я почти на месте, но мне просто не хватает уровня для таргетинга.
джон
Сейчас я попробовал это очень простое правило: KERNEL=="sd??", NAME="%k", RUN+="mkdir /mnt/usbstick-%k; mount /dev/usbstick-%k /mnt/usbstick-%k"- но нет, конечно, это тоже не работает. Теперь я все больше расстраиваюсь, проведя почти целый день, пытаясь понять, как подключить USB-флешку для подключения. Должны ли вещи быть такими сложными? Вывод из udevadm test /sys/block/sdd- конечно - практически не читается, поэтому у меня нет возможности узнать, где я иду не так. Кто-нибудь может указать мне правильное направление на это?
джон

Ответы:

13

Я полагаю, что должен быть гораздо более простой способ решения такой распространенной проблемы, и он есть. Вот что я попробовал на своем сервере wheezy / sid:

sudo apt-get install usbmount

Подключите USB-накопитель, готово! Моя флешка теперь доступна через /media/usb.

Кстати, у usbmount нет страницы руководства, пожалуйста, прочитайте /usr/share/doc/usbmount/README.gzвместо этого. Похоже, usbmount монтирует вашу флешку с опцией синхронизации по умолчанию. Для вашей флешки может быть намного лучше смонтировать ее асинхронно и запустить syncили umountперед ее отключением. Это настраивается.

Арджан Дриман
источник
смотрите такжеpumount
Алекс
Обратите внимание, что usbmountбольше не поддерживает NTFS, так как debian jessie: bugs.debian.org/774149
малат
Запустив это на Debian Jessie, usbmount никогда не монтирует его. На странице пакета сказано, что он не поддерживается, и я использую systemd. Интересно, этот пакет больше не работает с изменениями systemd?
Трэвис Григгс
Действительно, у меня не сработало на Джесси, посмотрите мой ответ (это: ddumont.wordpress.com/2015/09/27/… сработало)
Пол
2

Обратите внимание, что вы не можете просто иметь один узел устройства для представления любого возможного присоединенного pendrive. Что делать, если вы подключите два из них? Или когда Pendrive имеет более одного раздела?

Как правило, то, что вы используете для создания пользовательского узла устройства, это SYMLINK+=. Grep для этого в правилах , чтобы увидеть , как он используется: grep SYMLINK /etc/udev/rules.d/*. Как и во всех командах, запускаемых udev, вы можете использовать некоторые значимые переменные, которые описаны в man udev. Вы можете понять, что на самом деле вам не нужно присваивать пользовательское имя устройству, поскольку вы можете передать его имя в скрипт (через %kпеременную).

Что касается решения с автоматическим монтированием, взгляните на UAM , который я немного описал в ответе на этот вопрос .

rozcietrzewiacz
источник
Я понимаю эти ограничения. Так получилось, что мне нужно всего лишь поддерживать один USB-накопитель, подключенный к этой конкретной системе. Однако мне потребуется поддержка нескольких разделов на USB-накопителе (было бы неплохо, если бы их можно было подключить к подпапкам из точки монтирования). Учитывая эти требования, есть ли у вас какие-либо советы для потенциального решения? Из-за характера проекта, мне нужно избегать использования дополнительного стороннего программного обеспечения, если это вообще возможно.
джон
Затем посмотрите на редактирование, которое я только что сделал (средняя часть). Этого будет достаточно?
rozcietrzewiacz
Также обратите внимание, что UAM на самом деле не программа - это набор хороших udevправил с сопровождающими скриптами. Вы можете взглянуть на правила и легко адаптировать их к вашим потребностям.
rozcietrzewiacz
Спасибо за совет. Еще одна вещь: вы думаете, что вы могли бы посмотреть на мой вывод udevadmи сказать мне, какое устройство является устройством, на которое я должен нацеливаться с моим правилом? Различные примеры, которые я видел в Интернете, похоже, включают в себя гораздо более короткие деревья, и каждый пример, похоже, нацелен на другой уровень устройства, без объяснения того, на какой объект следует ориентироваться и почему.
джон
Только что добавил обновление выше, есть идеи? Спасибо!
джон
2

Вот как я недавно это сделал, и теперь я вполне доволен этим подходом. Это для Ubuntu 12.04 + Gentoo, но я думаю, что любой дистрибутив, который позволяет установить udev и автозапуск должен работать.

Предварительные условия: Вы должны установить udev + autofs.

Шаг 1)

Создайте следующий файл "/etc/udev/rules.d/90-usbsd-auto.rules" (конечно, вы можете использовать любое имя, если оно оканчивается на ".rules"). :

# Add symlink /dev/usbdisks/<label> to /dev/sd[a-z][1-9] 
# for automounter support

ACTION=="add", KERNEL=="sd*", ENV{DEVTYPE}=="partition", \
    ENV{ID_BUS}=="usb", \
    SYMLINK+="usbdisks/%k", MODE:="0660", \
    RUN+="/bin/rm /media/usb/%k", \
    RUN+="/bin/ln -sf /media/autousb/%k /media/usb/%k"

# Some FileSystems emit a "change" event when they are unmounted.
# UDEV seems to delete the device symlink in this case :-(
# So we need to re-create it here
ACTION=="change", KERNEL=="sd*", ENV{DEVTYPE}=="partition", \
    ENV{ID_BUS}=="usb", \
    SYMLINK+="usbdisks/%k", MODE:="0660"


# When device is removed, also remove /media/usb/<...>
ACTION=="remove", KERNEL=="sd*", ENV{DEVTYPE}=="partition", \
    ENV{ID_BUS}=="usb", \
    RUN+="/bin/rm /media/usb/%k"

Что это делает: создает две символические ссылки, одну для раздела запоминающего устройства USB в «/ dev / usbdisks / <...>».

Вторая символическая ссылка будет ссылаться с "/ media / usb / <...>" на "/ media / autousb / <...>", это делается для поддержки автомонтирования (см. Шаг 2).

Чтобы убедиться, что udev читает эти правила, используйте

sudo udevadm control --reload-rules

Примечание: То же имя для той же карты памяти USB: возможно, но может быть и опасно: вы можете использовать, например, «$ env {ID_FS_LABEL_ENC}» вместо «% k» в вышеприведенных правилах UDEV. При этом будет использоваться метка тома для создания / media / usb / <...>, но что произойдет, если вы подключите два USB-накопителя и оба будете использовать одну и ту же метку тома ...

С этим файлом правил udev все настроено для автоматического монтирования раздела USB-накопителя. Обратите внимание, что прямо сейчас устройство НЕ будет автоматически подключено (намеренно). Он будет автоматически смонтирован, как только вы используете его

Шаг 2)

Настройте autofs для autoount / media / autousb / <...>: я добавил следующую строку в мой файл /etc/auto.master (для Ubuntu 12.04):

/media/autousb /etc/auto.usb --timeout=60

Это означает, что AutoFS отключит устройство после 60 секунд бездействия. Вы можете использовать меньше или больше, в зависимости от вашего вкуса.

Для Gentoo вы должны изменить "/etc/autofs/auto.master", чтобы имело смысл использовать

/media/autousb /etc/autofs/auto.usb --timeout=60

Теперь я создал "auto.usb" со следующим содержимым:

#!/bin/bash

key=${1}
fstype=$(/sbin/blkid -o value -s TYPE /dev/usbdisks/${key})
if [ "${fstype}" = "vfat" ] ; then
  echo "-fstype=vfat,sync,uid=0,gid=plugdev,umask=007 :/dev/usbdisks/${key}"
  exit 0
fi
if [ "${fstype}" = "ntfs" ] ; then
  echo "-fstype=fuse.ntfs-3g,sync,uid=0,gid=plugdev,umask=007 :/dev/usbdisks/${key}"
  exit 0
fi
if [ "${fstype}" = "ext4" ] ; then
  echo "-fstype=ext4,sync,nocheck :/dev/usbdisks/${key}"
  exit 0
fi

exit 1

Этот auto.usb должен быть исполняемым, чтобы autofs использовал его как (bash) скрипт. Так например

sudo chmod 0755 /etc/auto.usb

Что это делает? Этот скрипт сообщит AutoFS (/ usr / sbin / automount), как монтировать раздел устройства хранения USB.

Сначала сценарий будет использовать «/ sbin / blkid», чтобы выяснить, какая файловая система находится в разделе.

Затем скрипт предоставит правильные параметры монтирования в зависимости от раздела устройства.

Примечание: я включил пример кода для файловых систем vfat (вероятно, наиболее распространенных для usb-флешек), ntfs и ext4. Конечно, это довольно легко расширить для поддержки большего количества файловых систем.

Шаг 3)

Необязательно ... Чтобы "извлечь" == размонтировать ваши флешки (или разделы на флешке), создайте скрипт в / sbin / usbeject:

#!/bin/bash
# make sure everything is written to USB disk(s)
sync
# sending SIUGSR1 to automount will unmount the media
killall -s SIGUSR1 /usr/sbin/automount

С помощью этого сценария вы можете использовать «sudo usbeject» для размонтирования всех подключенных разделов USB-устройств (указав автомонтированию отключить их).

Конечно, вы можете просто убедиться, что раздел нигде не используется; Затем автомонтировщик размонтирует раздел после 60 секундного ожидания ...

Настоящий трюк здесь заключается в использовании символических ссылок из "/ media / usb" в "/ media / autousb":

  • Символьные ссылки "/ media / usb" будут созданы udev, чтобы дать пользователю простой обзор того, какие разделы устройства хранения USB есть.
  • AutoFS затем автоматически смонтирует раздел, если вы используете его через / media / usb
  • С помощью скриптового файла "auto.usb" вы можете поддерживать любую файловую систему и, кроме того, вы также можете поддерживать любую схему именования.
  • Этот подход поддерживает использование USB-накопителей с несколькими разделами, даже если эти разделы используют разные типы файловых систем.
Инго Блэкман
источник
Могу ли я показать вам, как подсказка autofs разрушает мой каталог / home / frank? Спасибо.
Фрэнк
1

Извините, что отвечаю на мой собственный вопрос, и огромное спасибо rozcietrzewiacz за помощь, но в итоге мне удалось добиться значительного прогресса, используя следующее правило после нескольких часов чтения в Интернете:

SUBSYSTEMS=="scsi", KERNEL=="sd[a-h]1", SYMLINK+="removable", RUN+="/bin/mount /dev/removable /path/to/mount"

Это смонтирует первый раздел любого устройства SCSI. Я думаю, что следующий вопрос будет состоять в том, как смонтировать несколько разделов, но это еще одна проблема для другого дня.

джон
источник
1
Это не очень хорошее правило. Это будет соответствовать также разделам жестких дисков . есть removableатрибут, который вы должны проверить, а не blockвместо scsi.
rozcietrzewiacz
1

Я обнаружил, что лучший ответ на самом деле стал устаревшим, так как он не поддерживается и не работает с Джесси (см. Комментарий Малата)

Для меня (на Джесси) решение в этом блоге работало как шарм.

Кредиты "ddumont", но выкладываю обзор своего блога / ответа здесь, чтобы справиться с возможной гнилью ссылок в будущем.

Добавьте следующую строку в /etc/fstab

/dev/sr0 /media/bluray auto defaults,nofail,x-systemd.automount 0 2

Вы можете сделать это используя nano:

sudo nano /etc/fstab

Объяснение:

/dev/sr0это файл устройства. Вы также можете использовать одну из символических ссылок, настроенную udev в / dev / disk / by-id. Вам нужно будет изменить это в соответствии с файлом вашего устройства ( sudo fdisk -lчтобы получить список устройств)

/media/blurayэто точка монтирования. Вы можете выбрать другую точку монтирования

nofail требуется, чтобы избежать сообщения об ошибке при загрузке без диска в оптическом приводе

x-systemd.automount это опция для настройки systemd для автоматического монтирования вставленного диска

Не указывайте noauto: это помешает systemd автоматически смонтировать диск, что противоречит цели.

Контрольная работа

Запустите команду journalctl -x -fв терминале, чтобы проверить, что происходит с systemd

Перезагрузите конфигурацию systemd с помощью sudo systemctl daemon-reload.

загрузите диск в свой оптический привод

Затем journalctl должен показать что-то вроде:

Sept. 27 16:07:01 frodo systemd[1]: Mounted /media/bluray.

Дальше

Чтобы успешно смонтировать диски NTFS, мне пришлось установить ntfs-3g (старые ntfsprogs)

sudo apt-get install ntfs-3g

Мне не нужно было устанавливать hfsprogs, чтобы заставить работать usb в формате OSX, но вы должны проверить это сами.

Павел
источник
Он не монтируется автоматически на моей Debian jessie с USB-HDD.
Buhtz
@buhtz, но монтаж вручную работает? Описанные выше шаги на самом деле работали только для дисков, которые были в системе при запуске, а не для «динамической» вставки и извлечения USB во время работы системы.
Пол