Как получить доступ к данным, если био было клонировано ?
- Привет !
Я пишу драйвер устройства Linux, который должен работать поверх драйверов устройств existen, поэтому я пытаюсь использовать процедуру ввода-вывода bi_end_io() complition для доступа к буферам данных, считанным с дискового устройства, смотрите следующий фрагмент кода:
static void dua_bio_end_io ( struct bio * iob ) { IOB_ARGS * iob_args; $TRACE("Entering to %s completion I/O, bio=%p ...", bio_data_dir(iob) == WRITE ? "WRITE" : "READ", iob); $SHOW_UNSIGNED(iob->bi_flags); $SHOW_INT(iob->bi_vcnt); $SHOW_BOOL(bio_has_data(iob)); iob_args = iob->bi_private; iob->bi_end_io = iob_args->bi_end_io; iob->bi_private = iob_args->bi_private; bio_put(iob); __ret_iob_args (iob_args); /* In case of READ request - we should decrypt data buffer right now */ if ( bio_data_dir(iob) == READ ) __iob_enc_dec(iob); bio_endio (iob); } static blk_qc_t dua_make_request_fn ( struct request_queue * ioq, struct bio * iob ) { int status = 0; $TRACE("Starting (%s), bio=%p, op=%d ...", bio_data_dir(iob) == WRITE ? "WRITE" : "READ", iob, bio_op(iob)); $SHOW_UNSIGNED(iob->bi_flags); $SHOW_INT(iob->bi_vcnt); $SHOW_BOOL(bio_has_data(iob)); /* In case of WRITE request - we can encrypt data buffer right now */ if ( bio_data_dir(iob) == WRITE ) __iob_enc_dec(iob); /* * A handling of the READ request is require 'enqueue read request' & 'wait for read completion' paradigm, * so we need to allocate IOB_ARGS block to carry data to the "Read Completion I/O" routine. */ else if ( bio_data_dir(iob) == READ ) { IOB_ARGS *iob_args = NULL; if ( __get_iob_args (&iob_args) ) { printk(KERN_ERR __MODULE__ ": Buffered I/O quota limit has been exhausted\n"); iob->bi_error = -EBUSY; bio_endio(iob); } iob_args->bi_end_io = iob->bi_end_io; iob_args->bi_private = iob->bi_private; /* * Replace an address of the Completion I/O routine for 'read' operation, * save original address. */ iob->bi_private = iob_args; iob->bi_end_io = dua_bio_end_io; bio_get(iob); } /* Just for sanity check ... */ else { printk(KERN_WARNING __MODULE__ ": Unhandled I/O request %d\n", bio_data_dir(iob) ); } /* Call original make_reques_fn() to performs a main work ... */ status = backend_make_request_fn(ioq, iob); return status; }
...
6463.418222] [DUDRIVER\dua_make_request_fn:479] Starting (READ), bio=ffff95c5f9552100, op=0 ... [ 6463.418222] [DUDRIVER\dua_make_request_fn:482] : iob->bi_flags = 0x00000000 [ 6463.418223] [DUDRIVER\dua_make_request_fn:483] : iob->bi_vcnt = 1 [ 6463.418223] [DUDRIVER\dua_make_request_fn:485] : bio_has_data(iob) = ENABLED(TRUE) [ 6463.418266] [DUDRIVER\dua_bio_end_io:445] Entering to READ completion I/O, bio=ffff95c5f9552100 ... [ 6463.418266] [DUDRIVER\dua_bio_end_io:447] : iob->bi_flags = 0x00000102 [ 6463.418267] [DUDRIVER\dua_bio_end_io:448] : iob->bi_vcnt = 1 [ 6463.418267] [DUDRIVER\dua_bio_end_io:450] : bio_has_data(iob) = DISABLED(FALSE)
Итак, есть ли способ получить доступ к уже прочитанным данным в клонированной биографии ?
Или, может быть, мне нужно использовать какую-то другую тактику, чтобы сохранить доступ к оригинальным биовекам ?
Что я уже пробовал:
I read LDD3, and check the a lot of examples. I working with the Linux kernel 4.10.y
Заранее спасибо!