On Tue, 1 Jun 1999, Wes Peters wrote:

> 
> ???
> 
> dd verifies the behavior you report:
> 
> r...@homer# dd if=/dev/rwd0s2b of=/dev/null bs=1
> dd: /dev/rwd0s2b: Invalid argument
> ...
> r...@homer# dd if=/dev/rwd0s2b of=/dev/null bs=512
> ^C18805+0 records in
> ...
> 
> w...@homer$ ls -l /dev/*wd0s2a
> crw-r-----  1 root  operator    3, 0x00030000 Apr  1 11:10 /dev/rwd0s2a
> brw-r-----  1 root  operator    0, 0x00030000 Apr  1 11:10 /dev/wd0s2a
> 
> The rwd device is clearly a character-special device, the wd device a
> block special.  Character devices can always be read byte-at-a-time,
> by definition.  When did the semantics of this change?
> 

I have verified the requirement that character device must be read in
multiples of 512 from the source code point of view (the disk involved in
an IDE drive): 

When we call read(int d, void *buf, size_t nbytes) system call, the
argument nbytes is passed on to the iov_len field of an iov structure (see
file sys_generic.c). Later, the routine vn_read() in file vfs_vnops.c is
called via the structure fileops, the uio structure is passed along.
vn_read() will call spec_read() via VOP_READ() because we are talking
about raw device file name. spec_read() will call wdread() via the cdevsw
table.  wdread() will call physio() where b_bcount of a buffer is set to
be iov_len.  The routine wdstrategy() invoked by physio() will check if
bp->b_bcount % DEV_BSIZE != 0.  If it detects an request size that is not
a multiple of 512, it will set b_error = EINVAL. This error will be picked
up by physio() and returned. 

Thanks for your help.

-Zhihui



To Unsubscribe: send mail to majord...@freebsd.org
with "unsubscribe freebsd-hackers" in the body of the message

Reply via email to