Как итерация всех монтированных файловых систем на OSX

StackOverflow https://stackoverflow.com/questions/19843238

Вопрос

Я заинтересован в итерации всех монтированных файловых систем на OSX (в настоящее время работает 10,9 Mavericks). Я ищу что -то похожее на getMntent () или вывод команды Mount Shell (хотя я хочу сделать это из Objective C, поэтому анализ вывода команды оболочки, очевидно, не оптимальный).

Я немного смотрел на арбитражную структуру диска, и кажется, что я могу быть уведомлен о событиях Mount и Unmount, используя эту структуру. Я могу что -то упустить там, но мне не ясно, есть ли способ обратить внимание на существующие монтажные файловые системы с помощью дискового арбитража.

Я исследовал использование getFsent (), который, казалось, это обеспечит решение, но после тестирования я обнаружил, что не получаю более одной записи от итерационного getFsent (). Смотрите следующий код:

struct fstab* fsentry;
setfsent();
fsentry = getfsent();
while(fsentry)
{
    //do something with fsentry
    fsentry = getfsent();
}
endfsent();

Единственная запись, которую я получаю здесь, - это / файловая система. Во второй раз, когда я называю getFsent (), он возвращает NULL, как будто нет записей. Команда Mount показывает мне несколько других, включая установленную файловую систему CIFS/SMB:

/dev/disk0s2 on / (hfs, local, journaled)
devfs on /dev (devfs, local, nobrowse)
map -hosts on /net (autofs, nosuid, automounted, nobrowse)
map auto_home on /home (autofs, automounted, nobrowse)
//user@<ip address>/public on /Volumes/public (smbfs, nodev, nosuid, mounted by user)

Так кажется, что getFsent () начинает делать то, что я ожидаю, но по какой -то причине останавливается?

В резюме мой вопрос: как лучше всего использовать файловые системы на OSX?

Если у кого -то есть ответ на то, почему я получаю только один результат от getFsent (), мне также было бы интересно.

Это было полезно?

Решение

Существует несколько различных способов перечисления монтированных объемов на OS X, каждый из которых использует различный набор API. На самом высоком (и легком) уровне вы можете использовать NSFileManager's mountedVolumeURLsIncludingResourceValuesForKeys:options:. Анкет Вот сокращенный пример:

NSArray *urls = [[NSFileManager defaultManager] mountedVolumeURLsIncludingResourceValuesForKeys:@[NSURLVolumeNameKey] options:0];
for (NSURL *url in urls) {
  NSLog(@"Volume mounted at: %@", [url path]);
}

Следующий вариант возвращает нас на территорию C - и вы были так близки к своему первоначальному подходу. На OS X (и BSD) нет getmntent(); Вместо этого есть getmntinfo(), что поразительно похожа. Чтобы перечислить монтированные объемы через getmntinfo(), вы можете сделать следующее:

struct statfs* mounts;
int num_mounts = getmntinfo(&mounts, MNT_WAIT);
if (num_mounts < 0) {
  // do something with the error
}

for (int i = 0; i < num_mounts; i++) {
  NSLog(@"Disk type '%s' mounted at: %s", mounts[i].f_fstypename, mounts[i].f_mntonname);
}

Я использовал оба эти APIS бок о бок с момента выпуска 10.6. getmntinfo() всегда более полным, чем [NSFileManager mountedVolumeURLsIncludingResourceValuesForKeys:options:]: Последний отфильтровал /dev и другие файловые системы, о которых вы можете или не можете знать. Однако, как правило, надежно для дисков, которые вы подключаете к своей системе.

Как вы заметили, цель, лежащая в основе рамки дискарбита, отличается. Дискарбит - это мониторинг и управление дисковыми активами. С DA вас могут вызвать всякий раз, когда новый диск монтируется или не установлен. Вы также можете управлять этими дисками, переименовав, устанавливая, подчинившись или вытесняя их, а также вставив себя в процесс крепления/непредубегаемости - и потенциально приостанавливая запросы на то же самое. Но, как вы указали, он не предоставляет интерфейс для перечисления существующих дисков. Как только вы получите свой список монтированных объемов, DA станет отличной следующей остановкой (в зависимости, конечно, по вашей причине получить этот список!).

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top