Можно ли с помощью Fuse (Filesystem in Userspace) "переопределить" работу стандартных команд чтения\записи?
Чуть конкретнее: есть программа, которая отправляет файлы по сети с помощью sendfile.
Хотелось бы иметь возможность изменять содержание потока байт, не меняя функцию передачи файла.
Пример:
while( send() != finish ){
}
send(){ // эту функция я не могу изменитьif(offset != file_size){
offset += sendfile(file, socks, offset, size) // на некоторой итерации хотелось бы чтобы sendfile return offset // отправлял вместо данных из файла что нибудь другое
}
return finish
}
Здравствуйте, dronsmr, Вы писали:
D>Можно ли с помощью Fuse (Filesystem in Userspace) "переопределить" работу стандартных команд чтения\записи?
FUSE это скорее "доопределить" чем "переопределить"... fuse это создание собственной "файловой системы" в userspace, а не переопределение существующих...
D>Чуть конкретнее: есть программа, которая отправляет файлы по сети с помощью sendfile.
при использовании FUSE нужно будет заботиться о том, чтобы файлы которые отправляет твоя программа брались именно с твоей "файловой системы" (откуда они там возьмутся это уже вопрос твоего "драйвера" FS) -- в этот момент, да, ты имеешь возможность контролировать весь I/O с твой "FS", и можешь подсовывать все что захочешь... -- но это IMHO сложный и не факт что тебе подходящий way (ибо если твоя прога получает файлы, допустим, из command line то ей можно будет запихать что угодно, а не только то, что "хранится" в твоей FS (котору кстати еще надо примонтировать перед тем как начать работу твой проги))
D>Хотелось бы иметь возможность изменять содержание потока байт, не меняя функцию передачи файла.
IMHO, наиболее простой way сделать библу в которой написать свою версию интерисумоей функции (sendfile к примеру) и грузить ее preload'ом -- таким образом твоя прога ничего не заметит, но вызываться будет уже твоя функция, в которой ты можешь делать все что тебе нужно, и затем уже вызывать настоящий sendfile
Спасибо за ответ.
Вариант с fuse мне подойдет, т.к. файлы могу заранее расположить где угодно.
Своя версия sendfile — не вариант, потому что она ещё используется и для других целей,
а внутри переопределеного sendfile нельзя будет понять по какой схеме работать (стандартной или измененной).
Здравствуйте, dronsmr, Вы писали:
D>Спасибо за ответ. D>Вариант с fuse мне подойдет, т.к. файлы могу заранее расположить где угодно.
да сложность то не в том, где расположить файлы!!! а в том, что реальные файлы будут лежать /где/то/там/*, юзерспейсный драйвер "файловой системы" должен будет "знать" это место (параметр при монтировании), но в своей точке монтирования (/где/то/тут/*) должен будет повторить всю ту иерархию файлов + внести свои какие-то "изменения" (на лету при чтении из "файла") в некоторые (или все) из них...
D>Своя версия sendfile — не вариант, потому что она ещё используется и для других целей, D>а внутри переопределеного sendfile нельзя будет понять по какой схеме работать (стандартной или измененной).
вот уж тут вариантов полно как своему sendfile() "сказать" по какой схеме работать...
* в "глобальной" (ну да, фиговастенько но что делать) переменной
* в TLSной памяти
* переменной окружения
* шареной памяти
* etc...
Z>вот уж тут вариантов полно как своему sendfile() "сказать" по какой схеме работать... Z>* в "глобальной" (ну да, фиговастенько но что делать) переменной Z>* в TLSной памяти Z>* переменной окружения Z>* шареной памяти Z>* etc...
в частности нужно будет обрабатывать ситуацию когда один файл читают "по разному" несколько клиентов.
с fuse планируется монтировать для каждого клиента свою версию файла,
а вот с preload'ом непонятно как управлять 'версиями' sendfile
ну, ещё подумаю над этим вариантом
способ с fuse кажется более гибким (хотя и более сложным)...
Здравствуйте, zaufi, Вы писали:
Z>ты уверен что хочешь писать "драйвер" FS?
Чего там писать, стандартный пример из fuse повторяет рут в точке монтирования. Пара модификаций для поддержки /proc и /sys и можно делать chroot в точку монтирования.
Здравствуйте, dronsmr, Вы писали:
D>Можно ли с помощью Fuse (Filesystem in Userspace) "переопределить" работу стандартных команд чтения\записи? D>Чуть конкретнее: есть программа, которая отправляет файлы по сети с помощью sendfile. D>Хотелось бы иметь возможность изменять содержание потока байт, не меняя функцию передачи файла. D>Пример: D>
D>while( send() != finish ){
D>}
D>send(){ // эту функция я не могу изменить
D> if(offset != file_size){
D> offset += sendfile(file, socks, offset, size) // на некоторой итерации хотелось бы чтобы sendfile
D> return offset // отправлял вместо данных из файла что нибудь другое
D> }
D> return finish
D>}
D>
Можно для этих целей попробывать для этих целей вызов ptrace, через него можно изменить поток байт процесса.