| .. | .. |
|---|
| 2266 | 2266 | return index; |
|---|
| 2267 | 2267 | } |
|---|
| 2268 | 2268 | |
|---|
| 2269 | +static enum cif_reg_index get_reg_index_of_frm_num(int channel_id) |
|---|
| 2270 | +{ |
|---|
| 2271 | + enum cif_reg_index index; |
|---|
| 2272 | + |
|---|
| 2273 | + switch (channel_id) { |
|---|
| 2274 | + case 0: |
|---|
| 2275 | + index = CIF_REG_MIPI_FRAME_NUM_VC0; |
|---|
| 2276 | + break; |
|---|
| 2277 | + case 1: |
|---|
| 2278 | + index = CIF_REG_MIPI_FRAME_NUM_VC1; |
|---|
| 2279 | + break; |
|---|
| 2280 | + case 2: |
|---|
| 2281 | + index = CIF_REG_MIPI_FRAME_NUM_VC2; |
|---|
| 2282 | + break; |
|---|
| 2283 | + case 3: |
|---|
| 2284 | + index = CIF_REG_MIPI_FRAME_NUM_VC3; |
|---|
| 2285 | + break; |
|---|
| 2286 | + default: |
|---|
| 2287 | + index = CIF_REG_MIPI_FRAME_NUM_VC0; |
|---|
| 2288 | + break; |
|---|
| 2289 | + } |
|---|
| 2290 | + |
|---|
| 2291 | + return index; |
|---|
| 2292 | +} |
|---|
| 2293 | + |
|---|
| 2269 | 2294 | static enum cif_reg_index get_reg_index_of_frm1_y_addr(int channel_id) |
|---|
| 2270 | 2295 | { |
|---|
| 2271 | 2296 | enum cif_reg_index index; |
|---|
| .. | .. |
|---|
| 2758 | 2783 | VEHICLE_DG("%s, LINE=%d, channel->fmt_val = 0x%x", __func__, __LINE__, channel->fmt_val); |
|---|
| 2759 | 2784 | if (cfg->input_format == CIF_INPUT_FORMAT_PAL || |
|---|
| 2760 | 2785 | cfg->input_format == CIF_INPUT_FORMAT_NTSC) { |
|---|
| 2761 | | - VEHICLE_DG("CVBS IN PAL or NTSC config."); |
|---|
| 2786 | + VEHICLE_INFO("CVBS IN PAL or NTSC config."); |
|---|
| 2762 | 2787 | channel->virtual_width *= 2; |
|---|
| 2763 | 2788 | cif->interlaced_enable = true; |
|---|
| 2764 | 2789 | cif->interlaced_offset = channel->width; |
|---|
| 2765 | 2790 | cif->interlaced_counts = 0; |
|---|
| 2766 | 2791 | cif->interlaced_buffer = 0; |
|---|
| 2767 | 2792 | channel->height /= 2; |
|---|
| 2768 | | - VEHICLE_DG("do denterlaced.\n"); |
|---|
| 2793 | + VEHICLE_INFO("do denterlaced.\n"); |
|---|
| 2769 | 2794 | } |
|---|
| 2770 | 2795 | |
|---|
| 2771 | 2796 | channel->data_type = get_data_type(cfg->mbus_code, |
|---|
| .. | .. |
|---|
| 3930 | 3955 | static unsigned long temp_y_addr, temp_uv_addr; |
|---|
| 3931 | 3956 | int commit_buf = 0; |
|---|
| 3932 | 3957 | struct vehicle_rkcif_dummy_buffer *dummy_buf = &cif->dummy_buf; |
|---|
| 3933 | | - |
|---|
| 3958 | + u32 frm_num_reg, frame_id = 0; |
|---|
| 3934 | 3959 | VEHICLE_DG("@%s, enter, mipi_id(%d)\n", __func__, mipi_id); |
|---|
| 3935 | 3960 | |
|---|
| 3936 | 3961 | if ((frame_ready > 1) || (cif->cif_cfg.buf_num < 2) || |
|---|
| .. | .. |
|---|
| 3946 | 3971 | frm0_addr_uv = get_reg_index_of_frm0_uv_addr(mipi_id); |
|---|
| 3947 | 3972 | frm1_addr_y = get_reg_index_of_frm1_y_addr(mipi_id); |
|---|
| 3948 | 3973 | frm1_addr_uv = get_reg_index_of_frm1_uv_addr(mipi_id); |
|---|
| 3974 | + frm_num_reg = get_reg_index_of_frm_num(mipi_id); |
|---|
| 3975 | + frame_id = rkcif_read_reg(cif, frm_num_reg); |
|---|
| 3976 | + VEHICLE_DG("@%s, frm_num_reg(0x%x), frame_id:0x%x\n", __func__, |
|---|
| 3977 | + frm_num_reg, frame_id); |
|---|
| 3949 | 3978 | } else { |
|---|
| 3950 | 3979 | frm0_addr_y = get_dvp_reg_index_of_frm0_y_addr(mipi_id); |
|---|
| 3951 | 3980 | frm0_addr_uv = get_dvp_reg_index_of_frm0_uv_addr(mipi_id); |
|---|
| .. | .. |
|---|
| 3979 | 4008 | uv_addr = temp_uv_addr; |
|---|
| 3980 | 4009 | commit_buf = 0; |
|---|
| 3981 | 4010 | } else { |
|---|
| 3982 | | - if ((cif->interlaced_counts % 2) == 0) { |
|---|
| 4011 | + if ((frame_id != 0 && (frame_id & 0xffff) % 2 == 0) || |
|---|
| 4012 | + (frame_id == 0 && (cif->interlaced_counts % 2 == 0))) { |
|---|
| 3983 | 4013 | temp_y_addr = vehicle_flinger_request_cif_buffer(); |
|---|
| 3984 | 4014 | if (temp_y_addr == 0) { |
|---|
| 3985 | | - VEHICLE_INFO("%s,warnning request buffer failed\n", __func__); |
|---|
| 4015 | + VEHICLE_DGERR("%s,warnning request buffer failed\n", __func__); |
|---|
| 3986 | 4016 | spin_unlock(&cif->vbq_lock); |
|---|
| 3987 | 4017 | return -1; |
|---|
| 3988 | 4018 | } |
|---|
| .. | .. |
|---|
| 3995 | 4025 | //uv_addr = temp_uv_addr; |
|---|
| 3996 | 4026 | uv_addr = temp_uv_addr + cif->interlaced_offset; |
|---|
| 3997 | 4027 | commit_buf = 0; //even & odd field add |
|---|
| 4028 | + if (temp_y_addr == 0) { |
|---|
| 4029 | + VEHICLE_DGERR("%s,warnning temp_y_addr is NULL!\n", __func__); |
|---|
| 4030 | + spin_unlock(&cif->vbq_lock); |
|---|
| 4031 | + return -1; |
|---|
| 4032 | + } |
|---|
| 3998 | 4033 | } |
|---|
| 3999 | 4034 | WARN_ON(y_addr == cif->interlaced_offset); |
|---|
| 4000 | 4035 | WARN_ON(uv_addr == cif->interlaced_offset); |
|---|
| .. | .. |
|---|
| 4453 | 4488 | return IRQ_HANDLED; |
|---|
| 4454 | 4489 | } |
|---|
| 4455 | 4490 | |
|---|
| 4491 | +#define vehicle_csi2_err_strncat(dst_str, src_str) {\ |
|---|
| 4492 | + if (strlen(dst_str) + strlen(src_str) < CSI_ERRSTR_LEN)\ |
|---|
| 4493 | + strncat(dst_str, src_str, strlen(src_str)); } |
|---|
| 4494 | + |
|---|
| 4495 | +static void vehicle_csi2_find_err_vc(int val, char *vc_info) |
|---|
| 4496 | +{ |
|---|
| 4497 | + int i; |
|---|
| 4498 | + char cur_str[CSI_VCINFO_LEN] = {0}; |
|---|
| 4499 | + |
|---|
| 4500 | + memset(vc_info, 0, sizeof(*vc_info)); |
|---|
| 4501 | + for (i = 0; i < 4; i++) { |
|---|
| 4502 | + if ((val >> i) & 0x1) { |
|---|
| 4503 | + snprintf(cur_str, CSI_VCINFO_LEN, " %d", i); |
|---|
| 4504 | + if (strlen(vc_info) + strlen(cur_str) < CSI_VCINFO_LEN) |
|---|
| 4505 | + strncat(vc_info, cur_str, strlen(cur_str)); |
|---|
| 4506 | + } |
|---|
| 4507 | + } |
|---|
| 4508 | +} |
|---|
| 4509 | + |
|---|
| 4510 | +static void vehicle_csi2_err_print_work(struct work_struct *work) |
|---|
| 4511 | +{ |
|---|
| 4512 | + struct vehicle_csi2_err_state_work *err_state = container_of(work, |
|---|
| 4513 | + struct vehicle_csi2_err_state_work, |
|---|
| 4514 | + work); |
|---|
| 4515 | + |
|---|
| 4516 | + pr_err("mipi_csi2: ERR%d:0x%x %s\n", err_state->err_num, |
|---|
| 4517 | + err_state->err_val, err_state->err_str); |
|---|
| 4518 | + if (err_state->err_num == 1) |
|---|
| 4519 | + pr_info("mipi_csi2: err_stat:0x%x\n", err_state->err_stat); |
|---|
| 4520 | +} |
|---|
| 4521 | + |
|---|
| 4456 | 4522 | static irqreturn_t vehicle_csirx_irq1(int irq, void *data) |
|---|
| 4457 | 4523 | { |
|---|
| 4458 | 4524 | struct vehicle_cif *cif = (struct vehicle_cif *)data; |
|---|
| .. | .. |
|---|
| 4460 | 4526 | struct csi2_err_stats *err_list = NULL; |
|---|
| 4461 | 4527 | unsigned long err_stat = 0; |
|---|
| 4462 | 4528 | u32 val; |
|---|
| 4529 | + char err_str[CSI_ERRSTR_LEN] = {0}; |
|---|
| 4530 | + char cur_str[CSI_ERRSTR_LEN] = {0}; |
|---|
| 4531 | + char vc_info[CSI_VCINFO_LEN] = {0}; |
|---|
| 4463 | 4532 | |
|---|
| 4464 | 4533 | val = read_reg(hw->csi2_base, CSIHOST_ERR1); |
|---|
| 4465 | 4534 | if (val) { |
|---|
| .. | .. |
|---|
| 4469 | 4538 | if (val & CSIHOST_ERR1_PHYERR_SPTSYNCHS) { |
|---|
| 4470 | 4539 | err_list = &hw->err_list[RK_CSI2_ERR_SOTSYN]; |
|---|
| 4471 | 4540 | err_list->cnt++; |
|---|
| 4472 | | - VEHICLE_DGERR( |
|---|
| 4473 | | - "ERR1: start of transmission error, reg: 0x%x,cnt:%d\n", |
|---|
| 4474 | | - val, err_list->cnt); |
|---|
| 4541 | + |
|---|
| 4542 | + vehicle_csi2_find_err_vc(val & 0xf, vc_info); |
|---|
| 4543 | + snprintf(cur_str, CSI_ERRSTR_LEN, "(sot sync,lane:%s) ", vc_info); |
|---|
| 4544 | + vehicle_csi2_err_strncat(err_str, cur_str); |
|---|
| 4475 | 4545 | } |
|---|
| 4476 | 4546 | |
|---|
| 4477 | 4547 | if (val & CSIHOST_ERR1_ERR_BNDRY_MATCH) { |
|---|
| 4478 | 4548 | err_list = &hw->err_list[RK_CSI2_ERR_FS_FE_MIS]; |
|---|
| 4479 | 4549 | err_list->cnt++; |
|---|
| 4480 | | - VEHICLE_DGERR( |
|---|
| 4481 | | - "ERR1: error matching frame start with frame end, reg: 0x%x,cnt:%d\n", |
|---|
| 4482 | | - val, err_list->cnt); |
|---|
| 4550 | + vehicle_csi2_find_err_vc((val >> 4) & 0xf, vc_info); |
|---|
| 4551 | + snprintf(cur_str, CSI_ERRSTR_LEN, "(fs/fe miss,vc:%s) ", vc_info); |
|---|
| 4552 | + vehicle_csi2_err_strncat(err_str, cur_str); |
|---|
| 4553 | + |
|---|
| 4483 | 4554 | } |
|---|
| 4484 | 4555 | |
|---|
| 4485 | 4556 | if (val & CSIHOST_ERR1_ERR_SEQ) { |
|---|
| 4486 | 4557 | err_list = &hw->err_list[RK_CSI2_ERR_FRM_SEQ_ERR]; |
|---|
| 4487 | 4558 | err_list->cnt++; |
|---|
| 4488 | | - VEHICLE_DGERR("ERR1: incorrect frame sequence detected, reg: 0x%x,cnt:%d\n", |
|---|
| 4489 | | - val, err_list->cnt); |
|---|
| 4559 | + vehicle_csi2_find_err_vc((val >> 8) & 0xf, vc_info); |
|---|
| 4560 | + snprintf(cur_str, CSI_ERRSTR_LEN, "(f_seq,vc:%s) ", vc_info); |
|---|
| 4561 | + vehicle_csi2_err_strncat(err_str, cur_str); |
|---|
| 4562 | + |
|---|
| 4490 | 4563 | } |
|---|
| 4491 | 4564 | |
|---|
| 4492 | 4565 | if (val & CSIHOST_ERR1_ERR_FRM_DATA) { |
|---|
| 4493 | 4566 | err_list = &hw->err_list[RK_CSI2_ERR_CRC_ONCE]; |
|---|
| 4494 | 4567 | err_list->cnt++; |
|---|
| 4495 | | - VEHICLE_DGERR("ERR1: at least one crc error, reg: 0x%x\n,cnt:%d", |
|---|
| 4496 | | - val, err_list->cnt); |
|---|
| 4568 | + vehicle_csi2_find_err_vc((val >> 12) & 0xf, vc_info); |
|---|
| 4569 | + snprintf(cur_str, CSI_ERRSTR_LEN, "(err_data,vc:%s) ", vc_info); |
|---|
| 4570 | + vehicle_csi2_err_strncat(err_str, cur_str); |
|---|
| 4571 | + |
|---|
| 4497 | 4572 | } |
|---|
| 4498 | 4573 | |
|---|
| 4499 | 4574 | if (val & CSIHOST_ERR1_ERR_CRC) { |
|---|
| 4500 | 4575 | err_list = &hw->err_list[RK_CSI2_ERR_CRC]; |
|---|
| 4501 | 4576 | err_list->cnt++; |
|---|
| 4502 | | - VEHICLE_DGERR("ERR1: crc errors, reg: 0x%x, cnt:%d\n", |
|---|
| 4503 | | - val, err_list->cnt); |
|---|
| 4577 | + vehicle_csi2_find_err_vc((val >> 24) & 0xf, vc_info); |
|---|
| 4578 | + snprintf(cur_str, CSI_ERRSTR_LEN, "(crc,vc:%s) ", vc_info); |
|---|
| 4579 | + vehicle_csi2_err_strncat(err_str, cur_str); |
|---|
| 4580 | + |
|---|
| 4504 | 4581 | } |
|---|
| 4505 | 4582 | |
|---|
| 4506 | 4583 | if (val & CSIHOST_ERR1_ERR_ECC2) { |
|---|
| 4507 | 4584 | err_list = &hw->err_list[RK_CSI2_ERR_CRC]; |
|---|
| 4508 | 4585 | err_list->cnt++; |
|---|
| 4509 | | - VEHICLE_DGERR("ERR1: ecc errors, reg: 0x%x, cnt:%d\n", |
|---|
| 4510 | | - val, err_list->cnt); |
|---|
| 4511 | | - } |
|---|
| 4512 | | - if (val & CSIHOST_ERR1_ERR_CTRL) |
|---|
| 4513 | | - VEHICLE_DGERR("ERR1: ctrl errors, reg: 0x%x\n", val); |
|---|
| 4586 | + snprintf(cur_str, CSI_ERRSTR_LEN, "(ecc2) "); |
|---|
| 4587 | + vehicle_csi2_err_strncat(err_str, cur_str); |
|---|
| 4514 | 4588 | |
|---|
| 4589 | + } |
|---|
| 4590 | + if (val & CSIHOST_ERR1_ERR_CTRL) { |
|---|
| 4591 | + vehicle_csi2_find_err_vc((val >> 16) & 0xf, vc_info); |
|---|
| 4592 | + snprintf(cur_str, CSI_ERRSTR_LEN, "(ctrl,vc:%s) ", vc_info); |
|---|
| 4593 | + vehicle_csi2_err_strncat(err_str, cur_str); |
|---|
| 4594 | + } |
|---|
| 4515 | 4595 | hw->err_list[RK_CSI2_ERR_ALL].cnt++; |
|---|
| 4516 | 4596 | err_stat = ((hw->err_list[RK_CSI2_ERR_FS_FE_MIS].cnt & 0xff) << 8) | |
|---|
| 4517 | 4597 | ((hw->err_list[RK_CSI2_ERR_ALL].cnt) & 0xff); |
|---|
| 4518 | | - VEHICLE_INFO("%s: err_stat: %x\n", err_stat); |
|---|
| 4598 | + |
|---|
| 4599 | + cif->err_state.err_val = val; |
|---|
| 4600 | + cif->err_state.err_num = 1; |
|---|
| 4601 | + cif->err_state.err_stat = err_stat; |
|---|
| 4602 | + strscpy(cif->err_state.err_str, err_str, CSI_ERRSTR_LEN); |
|---|
| 4603 | + queue_work(cif->err_state.err_print_wq, &cif->err_state.work); |
|---|
| 4519 | 4604 | |
|---|
| 4520 | 4605 | } |
|---|
| 4521 | 4606 | |
|---|
| .. | .. |
|---|
| 4527 | 4612 | struct vehicle_cif *cif = (struct vehicle_cif *)data; |
|---|
| 4528 | 4613 | struct csi2_dphy_hw *hw = cif->dphy_hw; |
|---|
| 4529 | 4614 | u32 val; |
|---|
| 4615 | + char cur_str[CSI_ERRSTR_LEN] = {0}; |
|---|
| 4616 | + char err_str[CSI_ERRSTR_LEN] = {0}; |
|---|
| 4617 | + char vc_info[CSI_VCINFO_LEN] = {0}; |
|---|
| 4530 | 4618 | |
|---|
| 4531 | 4619 | val = read_reg(hw->csi2_base, CSIHOST_ERR2); |
|---|
| 4532 | 4620 | if (val) { |
|---|
| 4533 | | - if (val & CSIHOST_ERR2_PHYERR_ESC) |
|---|
| 4534 | | - VEHICLE_DGERR("ERR2: escape entry error(ULPM), reg: 0x%x\n", val); |
|---|
| 4535 | | - if (val & CSIHOST_ERR2_PHYERR_SOTHS) |
|---|
| 4536 | | - VEHICLE_DGERR( |
|---|
| 4537 | | - "ERR2: start of transmission error, reg: 0x%x\n", val); |
|---|
| 4538 | | - if (val & CSIHOST_ERR2_ECC_CORRECTED) |
|---|
| 4539 | | - VEHICLE_DGERR( |
|---|
| 4540 | | - "ERR2: header error detected and corrected, reg: 0x%x\n", val); |
|---|
| 4541 | | - if (val & CSIHOST_ERR2_ERR_ID) |
|---|
| 4542 | | - VEHICLE_DGERR( |
|---|
| 4543 | | - "ERR2: unrecognized data type detected, reg: 0x%x\n", val); |
|---|
| 4544 | | - if (val & CSIHOST_ERR2_PHYERR_CODEHS) |
|---|
| 4545 | | - VEHICLE_DGERR("ERR2: receive error code, reg: 0x%x\n", val); |
|---|
| 4621 | + if (val & CSIHOST_ERR2_PHYERR_ESC) { |
|---|
| 4622 | + vehicle_csi2_find_err_vc(val & 0xf, vc_info); |
|---|
| 4623 | + snprintf(cur_str, CSI_ERRSTR_LEN, "(ULPM,lane:%s) ", vc_info); |
|---|
| 4624 | + vehicle_csi2_err_strncat(err_str, cur_str); |
|---|
| 4625 | + } |
|---|
| 4626 | + if (val & CSIHOST_ERR2_PHYERR_SOTHS) { |
|---|
| 4627 | + vehicle_csi2_find_err_vc((val >> 4) & 0xf, vc_info); |
|---|
| 4628 | + snprintf(cur_str, CSI_ERRSTR_LEN, "(sot,lane:%s) ", vc_info); |
|---|
| 4629 | + vehicle_csi2_err_strncat(err_str, cur_str); |
|---|
| 4630 | + } |
|---|
| 4631 | + if (val & CSIHOST_ERR2_ECC_CORRECTED) { |
|---|
| 4632 | + vehicle_csi2_find_err_vc((val >> 8) & 0xf, vc_info); |
|---|
| 4633 | + snprintf(cur_str, CSI_ERRSTR_LEN, "(ecc,vc:%s) ", vc_info); |
|---|
| 4634 | + vehicle_csi2_err_strncat(err_str, cur_str); |
|---|
| 4635 | + } |
|---|
| 4636 | + if (val & CSIHOST_ERR2_ERR_ID) { |
|---|
| 4637 | + vehicle_csi2_find_err_vc((val >> 12) & 0xf, vc_info); |
|---|
| 4638 | + snprintf(cur_str, CSI_ERRSTR_LEN, "(err id,vc:%s) ", vc_info); |
|---|
| 4639 | + vehicle_csi2_err_strncat(err_str, cur_str); |
|---|
| 4640 | + } |
|---|
| 4641 | + if (val & CSIHOST_ERR2_PHYERR_CODEHS) { |
|---|
| 4642 | + snprintf(cur_str, CSI_ERRSTR_LEN, "(err code) "); |
|---|
| 4643 | + vehicle_csi2_err_strncat(err_str, cur_str); |
|---|
| 4644 | + } |
|---|
| 4645 | + cif->err_state.err_val = val; |
|---|
| 4646 | + cif->err_state.err_num = 2; |
|---|
| 4647 | + strscpy(cif->err_state.err_str, err_str, CSI_ERRSTR_LEN); |
|---|
| 4648 | + queue_work(cif->err_state.err_print_wq, &cif->err_state.work); |
|---|
| 4649 | + |
|---|
| 4546 | 4650 | } |
|---|
| 4547 | 4651 | |
|---|
| 4548 | 4652 | return IRQ_HANDLED; |
|---|
| .. | .. |
|---|
| 4661 | 4765 | cif->stopping = true; |
|---|
| 4662 | 4766 | cancel_delayed_work_sync(&(cif->work)); |
|---|
| 4663 | 4767 | flush_delayed_work(&(cif->work)); |
|---|
| 4768 | + cancel_work_sync(&cif->err_state.work); |
|---|
| 4664 | 4769 | |
|---|
| 4665 | 4770 | ret = wait_event_timeout(cif->wq_stopped, |
|---|
| 4666 | 4771 | cif->state != RKCIF_STATE_STREAMING, |
|---|
| .. | .. |
|---|
| 5118 | 5223 | if (inf_id == RKCIF_MIPI_LVDS) { |
|---|
| 5119 | 5224 | /* 5. set csi2-mipi-dphy reg */ |
|---|
| 5120 | 5225 | if (cif->dphy_hw->chip_id == CHIP_ID_RK3588 || |
|---|
| 5226 | + cif->dphy_hw->chip_id == CHIP_ID_RK3568 || |
|---|
| 5121 | 5227 | cif->dphy_hw->chip_id == CHIP_ID_RK3562) |
|---|
| 5122 | 5228 | cif->dphy_hw->csi2_dphy_base = cif->csi2_dphy_base; |
|---|
| 5123 | 5229 | |
|---|
| .. | .. |
|---|
| 5140 | 5246 | init_waitqueue_head(&cif->wq_stopped); |
|---|
| 5141 | 5247 | |
|---|
| 5142 | 5248 | spin_lock_init(&cif->vbq_lock); |
|---|
| 5249 | + |
|---|
| 5250 | + INIT_WORK(&cif->err_state.work, vehicle_csi2_err_print_work); |
|---|
| 5251 | + cif->err_state.err_print_wq = create_workqueue("cis2_err_print_queue"); |
|---|
| 5252 | + if (cif->err_state.err_print_wq == NULL) { |
|---|
| 5253 | + dev_err(dev, "%s: %s create failed.\n", __func__, |
|---|
| 5254 | + "csi2_err_print_wq"); |
|---|
| 5255 | + } |
|---|
| 5143 | 5256 | |
|---|
| 5144 | 5257 | return 0; |
|---|
| 5145 | 5258 | } |
|---|
| .. | .. |
|---|
| 5211 | 5324 | free_irq(cif->csi2_irq1, cif); |
|---|
| 5212 | 5325 | free_irq(cif->csi2_irq2, cif); |
|---|
| 5213 | 5326 | } |
|---|
| 5327 | + if (cif->err_state.err_print_wq) { |
|---|
| 5328 | + flush_workqueue(cif->err_state.err_print_wq); |
|---|
| 5329 | + destroy_workqueue(cif->err_state.err_print_wq); |
|---|
| 5330 | + } |
|---|
| 5214 | 5331 | |
|---|
| 5215 | 5332 | return 0; |
|---|
| 5216 | 5333 | } |
|---|