receive和process的过程

(一)

receive最终在fuse_kern_chan.c中的fuse_kern_chan_receive函数实现,使用系统调用读取

        res = read(fuse_chan_fd(ch), buf, size);

其中fuse_chan_fd(ch)就是/dev/fuse, buf和size在fuse_loop_mt.c中fuse_do_work中定义。      

struct fuse_buf fbuf = {
  .mem = w->buf,
  .size = w->bufsize,
};

其中的fbuf->mem就是buf,fbuf->size就是size。

size的值为 135168

这些值在 fuse_loop_mt.c::fuse_loop_start_thread中被赋值。

w->bufsize = fuse_chan_bufsize(mt->prevch);

w->buf = malloc(w->bufsize); 

receive完成后,就是process。process函数最终是fuse_lowlevel.c中的fuse_ll_process_buf 。

 

-------process应该和receive类似,最终在fuse_kern_chan.c的fuse_kern_chan_send函数中调用 :

      ssize_t res = writev(fuse_chan_fd(ch), iov, count);

writev也是一个系统调用 http://man7.org/linux/man-pages/man2/readv.2.html

 

(二)

执行ls dir1命令,fuse_ll_process_buf 会收到这些操作码:

  3  FUSE_GETATTR

[getattr] Called
  Attributes of / requested

  27  FUSE_OPENDIR

  28  FUSE_READDIR

--> Getting The List of Files of /

  1  FUSE_LOOKUP

[getattr] Called
  Attributes of /file54 requested

  1

[getattr] Called
  Attributes of /file349 requested

  28  FUSE_READDIR

  29  FUSE_RELEASEDIR

  42  FUSE_BATCH_FORGET

每一个操作码都耗费fuse_do_work(fuse_lootp_mt.c)的一个循环。即一个receive,一个process。

最终按照操作码调用对应函数:   

    fuse_ll_ops[in->opcode].func(req, in->nodeid, inarg);

in根据fuse_ll_process_buf中的参数buf得来。

func函数也在fuse_lowlevel.c中,比如do_getattr函数,该函数调用:

     req->f->op.getattr(req, nodeid, fip);

去执行用户定义的函数。 这里的op类型是struct fuse_lowlevel_ops,定义在fuse_lowlevel.c。

最终应该会去往fuse.c中的fuse_fs_getattr函数,在里面调用fs->op.getattr(path, buf);这个getattr函数在用户程序ssfs.c中定义。

 

op是在用户程序ssfs.c中定义,由fuse_main函数传递而来。

 

(三)

由于用户程序ssfs.c中只定义了三种操作,所以只会接受到三种操作。没有定义的操作,在fuse_lowlevel.c中进行对应的判断如if (req->f->op.setxattr)不成立于是调用fuse_reply_err(req, ENOSYS);进行回应。

(四)接上面(二)的结尾

static struct fuse_lowlevel_ops fuse_path_ops 在fuse.c中定义,有一句 

  .getattr = fuse_lib_getattr,

全局搜索只有这一处比较像lowlevel的getattr函数指针。

在fuse.c中,有

  static void fuse_lib_getattr(fuse_req_t req, fuse_ino_t ino,struct fuse_file_info *fi)

这与fuse_lowlevel.c中的getattr函数里面的调用是一致的。

  fuse_lib_getattr函数调用fuse_fs_fgetattr(f->fs, path, &buf, fi);, 里面调用fs->op.getattr(path, buf);

        这里应该就是用户定义的getattr了。

这里fs->op正是struct fuse_operations类型的。这个变量由用户程序ssfs.c的fuse_main传入。

转载于:https://www.cnblogs.com/bettersky/p/6771372.html

HAL_UART_Receive_IT 是一个 HAL 库中的函数,其作用是开启 UART 接收中断并启动接收过程。该函数的代码如下: ``` HAL_StatusTypeDef HAL_UART_Receive_IT(UART_HandleTypeDef *huart, uint8_t *pData, uint16_t Size) { uint32_t tmp1 = 0; /* Check that a Rx process is not already ongoing */ if(huart->RxState == HAL_UART_STATE_READY) { if((pData == NULL) || (Size == 0)) { return HAL_ERROR; } /* Process Locked */ __HAL_LOCK(huart); huart->pRxBuffPtr = pData; huart->RxXferSize = Size; huart->RxXferCount = Size; huart->ErrorCode = HAL_UART_ERROR_NONE; huart->RxState = HAL_UART_STATE_BUSY_RX; /* Enable the UART Error Interrupt: (Frame error, noise error, overrun error) */ __HAL_UART_ENABLE_IT(huart, UART_IT_ERR); /* Enable the UART Data Register not empty Interrupt */ __HAL_UART_ENABLE_IT(huart, UART_IT_RXNE); /* Enable the UART Parity Error and Data Register not empty Interrupts */ __HAL_UART_ENABLE_IT(huart, UART_IT_PE | UART_IT_RXNE); /* Process Unlocked */ __HAL_UNLOCK(huart); /* Check if a transmit Process is ongoing or not */ tmp1 = huart->Instance->CR1; if((tmp1 & USART_CR1_TXEIE) == RESET) { /* Enable the UART Transmit data register empty Interrupt */ __HAL_UART_ENABLE_IT(huart, UART_IT_TXE); } return HAL_OK; } else { return HAL_BUSY; } } ``` 该函数的参数包括: - huart:UART_HandleTypeDef 类型的指针,表示 UART 句柄。 - pData:uint8_t 类型的指针,表示接收数据缓冲区的起始地址。 - Size:uint16_t 类型的整数,表示接收数据缓冲区的大小。 该函数的主要流程如下: 1. 检查是否有接收进程正在进行,如果没有则进行接收过程。 2. 对 UART 句柄进行锁定,以防止多个进程同时访问它。 3. 将接收数据缓冲区的起始地址、大小等信息保存到 UART 句柄中。 4. 启用 UART 的错误中断和接收中断。 5. 检查是否有发送进程正在进行,如果没有则启用 UART 的发送中断。 6. 返回函数执行状态。 总之,该函数是用于实现 UART 接收中断的函数,通过该函数可以启动接收过程并在数据接收完成后通过中断方式通知应用程序。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值