Paulo da Silva escreveu:
I further simplified this ...
Now, everything I have is reading a page after sector 1 (sector 0 also
fails).
Why does err come with -5?
What am I doing wrong?
/*
* ptm_bio01.c
* Using bio:
* Read data.
*/
#include <linux/module.h> /* Needed by all modules */
#include <linux/kernel.h> /* Needed for KERN_INFO */
#include <linux/init.h> /* Needed for the macros */
#include <linux/blkdev.h>
#define MY_BLOCK_SIZE PAGE_SIZE
#define MODEFLAGS FMODE_READ
#define DEV "/dev/loop2"
MODULE_LICENSE("Dual BSD/GPL");
static struct bio *bio;
static struct page *page;
static struct block_device *bdev;
static void end_bio_read_sync(struct bio *bio, int err)
{ printk(KERN_INFO "Entering end_bio_read_sync ...\n");
bio_put(bio);
SetPageUptodate(page);
unlock_page(page);
if (err)
printk(KERN_INFO "end_bio_read_sync: Error n. %d\n",err);
printk(KERN_INFO "Exiting end_bio_read_sync ...\n");
}
/* static int __init ptm_bio01_init(void) */
/* I removed "__init" because initialization is all this module does */
static int ptm_bio01_init(void)
{ int err=0;
int flags=MODEFLAGS;
short *page_data;
int secsperpage=PAGE_SIZE/MY_BLOCK_SIZE;
int i;
/* Get a block device */
bdev = open_bdev_exclusive(DEV, flags, NULL);
if (IS_ERR(bdev))
{ err=PTR_ERR(bdev);
printk(KERN_INFO "Could not open_bdev_exclusive\n");
goto fail1;
}
/* Alloc a page */
page=alloc_page(GFP_NOFS);
if (!page)
{ err=-ENOMEM;
printk(KERN_INFO "Could not alloc_page\n");
goto fail2;
}
bio=bio_alloc(GFP_KERNEL, secsperpage);
if (!bio)
{ err=-ENOMEM;
printk(KERN_INFO "Could not allocate a bio R\n");
goto fail3;
}
/* Read the page */
bio->bi_sector=1; /* Device address in 512 bytes sectors.
1 -> 512 bytes from beginning of disk. */
bio->bi_bdev=bdev;
for (i=0;i<secsperpage;++i)
{ bio->bi_io_vec[i].bv_page=page;
bio->bi_io_vec[i].bv_len=MY_BLOCK_SIZE;
bio->bi_io_vec[i].bv_offset=i*MY_BLOCK_SIZE;
}
bio->bi_vcnt=secsperpage; /* how many bio_vec's */
bio->bi_idx=0; /* current index into bvl_vec */
bio->bi_size=PAGE_SIZE; /* residual I/O count */
bio->bi_end_io=end_bio_read_sync;
bio->bi_rw=0;
clear_bit(BIO_UPTODATE,&bio->bi_flags);
bio_get(bio);
lock_page(page);
page_data=page_address(page);
if (!page_data)
{ unlock_page(page);
err=-1;
printk(KERN_INFO "Could not get the address of the page!!! Use
kmap(?)\n");
goto fail4;
}
ClearPageUptodate(page);
submit_bio(READ, bio);
if (bio_flagged(bio, BIO_EOPNOTSUPP))
{ err=-EOPNOTSUPP;
printk(KERN_INFO "Could not submit_bio R\n");
goto fail4;
}
lock_page(page);
page_data=page_address(page);
if (!page_data)
{ err=-1;
printk(KERN_INFO "Could not get the address of the page!!! Use
kmap(?)\n");
goto fail4;
}
unlock_page(page);
printk(KERN_INFO "Ending init!\n");
return 0;
fail4:
bio_put(bio);
fail3:
__free_page(page);
page=NULL;
fail2:
close_bdev_exclusive(bdev,flags);
bdev=NULL;
fail1:
if (err)
printk(KERN_INFO "Error n. %d\n",err);
return err;
}
static void __exit ptm_bio01_exit(void)
{ int flags=MODEFLAGS; /* Must be the same as in init */
if (atomic_read(&bio->bi_cnt))
{ bio_put(bio);
}
if (page && atomic_read(&page->_count))
{ __free_page(page);
}
if (bdev)
close_bdev_exclusive(bdev,flags);
printk(KERN_INFO "Going out ...\n");
}
module_init(ptm_bio01_init);
module_exit(ptm_bio01_exit);
--
To unsubscribe from this list: send an email with
"unsubscribe kernelnewbies" to [email protected]
Please read the FAQ at http://kernelnewbies.org/FAQ