在驱动程序中,当要读取硬件数据时可以使用轮询和中的的方式来实现。当应用程序使用阻塞操作的read去读取数据时,驱动程序使用轮询方式时,需要cpu在一定时间内不断地重复监测是否有数据到达,中断机制时则是当硬件有数据到达时得到数据而使read函数返回数据。这两种操作都是应用程序主动去读取数据,若读取数据操作发出后未能读取到数据则会一直阻塞(不考虑非阻塞操作)。而异步通知机制fasync则是由驱动程序主动去通知应用程序,就如同在应用程序中的信号操作一样,给应用程序发送数据到达的信号。

    设备驱动要使用异步通知机制,则需要做好三个事情

  1. 支持F_SETOWN命令。能在这个命令中设置对应的ID。

  2. 支持F_SETFL命令。每当FASYNC标志改变时候,都会调用到驱动程序中的fasync函数,所以要实现好file_operations中的fasync对应函数。

  3. 在有资源到达时,调用kill_fasync()函数给应用程序发送命令。

在应用程序中要做的事情。

  1. fcntl(fd,F_SETOWN,getpid());//告诉驱动程序发给谁,ID

  2. int flags=fcntl(fd,F_GETFL);//获取权限标志

  3. fcntl(fd,F_SETFL,flags|FASYNC);//改变fasync标志,当应用程序执行这一个操作时,驱动程序会调用fasycn->fasync_helper函数对fasync_struct结构体进行初始化/释放

驱动程序要做的事情:

定义一个fasync_struct 结构体,在file_operations中实现fasync对应的函数如my_fasync,在my_fasync调用fasync_helper()函数对应fasync_struct结构体初始化。在需要发送信号的地方调用kill_fasynnc()函数给应用程序发送信号。

例:

wKioL1Z2o7TyC9lZAABaVRRYYGM763.png

wKiom1Z2o-LSQVfgAAE4IATPw4o980.png

在应用程序中

wKioL1Z2pFHglf_HAABHrNcdqzg493.png

wKioL1Z2pIOjcnYAAACRGljjHnE204.png