我创建了一个IOBlockStorageDevice设备,该设备报告用户设置的块大小。它为磁盘创建一个/ dev / diskX条目。如果reportBlockSize返回4096,并尝试写入单个块,则它将只写入1个块。
如果使用512的块大小,则单个块写请求变为8块读,然后是8块写。 (如doAsyncReadWrite所示)。
我相信我已经将此问题追踪到spec_vnops.c spec_write()
543 devBlockSize = vp->v_specsize;
544 if (devBlockSize > PAGE_SIZE)
545 return(EINVAL);
546
547 bscale = PAGE_SIZE / devBlockSize;
548 blkmask = bscale - 1;
549 bsize = bscale * devBlockSize;
如果一个块小于PAGE_SIZE(4096),则将bsize设为4096,并在下面的条件语句中,它决定先调用read,然后再写。
更糟糕的是,如果您尝试将blockSize设置为大于4096,则它会直接失败。
这似乎相当有限,我想知道是否有一种避免使用specfs的方法。由于我是使用IOkit创建设备的,因此我假设它会将vnops设置为内部深处的specfs。因此,即使我要制作自己的specnos vnops,也无法设置它们?
将文件系统安装到设备上后,它将使用不同的vnops,一切都很好。但是很难对设备进行分区,例如,blocksize为8192。
最佳答案
在iokit调用的devfs blob中,bdevsw_add
调用将始终附加specfs vnops。达尔文不允许您更改vnode上的vnops。因此尝试这样做是不现实的/不希望的。 IOkit创建的/ dev /节点需要保持原样,并与GUI和块大小限制一起使用。
我要做的是创建第二组BLK和CHR设备(无论是否在/ dev内部或外部),并附加我自己的vnops,它可以处理任何块大小。这些节点将用于非GUI相关的事物。 (具体限制需求的应用程序量)。