Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

i3c: mipi-i3c-hci: Factor out core initialization into helper

Prepare for future reuse. Move core initialization logic from
i3c_hci_init() into a dedicated helper function,
i3c_hci_reset_and_init().

Signed-off-by: Adrian Hunter <adrian.hunter@intel.com>
Reviewed-by: Frank Li <Frank.Li@nxp.com>
Link: https://patch.msgid.link/20260113072702.16268-17-adrian.hunter@intel.com
Signed-off-by: Alexandre Belloni <alexandre.belloni@bootlin.com>

authored by

Adrian Hunter and committed by
Alexandre Belloni
7f91e0e6 e4269df5

+75 -67
+75 -67
drivers/i3c/master/mipi-i3c-hci/core.c
··· 639 639 return 0; 640 640 } 641 641 642 + static int i3c_hci_reset_and_init(struct i3c_hci *hci) 643 + { 644 + u32 regval; 645 + int ret; 646 + 647 + ret = i3c_hci_software_reset(hci); 648 + if (ret) 649 + return -ENXIO; 650 + 651 + /* Disable all interrupts */ 652 + reg_write(INTR_SIGNAL_ENABLE, 0x0); 653 + /* 654 + * Only allow bit 31:10 signal updates because 655 + * Bit 0:9 are reserved in IP version >= 0.8 656 + * Bit 0:5 are defined in IP version < 0.8 but not handled by PIO code 657 + */ 658 + reg_write(INTR_STATUS_ENABLE, GENMASK(31, 10)); 659 + 660 + /* Make sure our data ordering fits the host's */ 661 + regval = reg_read(HC_CONTROL); 662 + if (IS_ENABLED(CONFIG_CPU_BIG_ENDIAN)) { 663 + if (!(regval & HC_CONTROL_DATA_BIG_ENDIAN)) { 664 + regval |= HC_CONTROL_DATA_BIG_ENDIAN; 665 + reg_write(HC_CONTROL, regval); 666 + regval = reg_read(HC_CONTROL); 667 + if (!(regval & HC_CONTROL_DATA_BIG_ENDIAN)) { 668 + dev_err(&hci->master.dev, "cannot set BE mode\n"); 669 + return -EOPNOTSUPP; 670 + } 671 + } 672 + } else { 673 + if (regval & HC_CONTROL_DATA_BIG_ENDIAN) { 674 + regval &= ~HC_CONTROL_DATA_BIG_ENDIAN; 675 + reg_write(HC_CONTROL, regval); 676 + regval = reg_read(HC_CONTROL); 677 + if (regval & HC_CONTROL_DATA_BIG_ENDIAN) { 678 + dev_err(&hci->master.dev, "cannot clear BE mode\n"); 679 + return -EOPNOTSUPP; 680 + } 681 + } 682 + } 683 + 684 + /* Try activating DMA operations first */ 685 + if (hci->RHS_regs) { 686 + ret = i3c_hci_set_io_mode(hci, true); 687 + if (!ret) { 688 + hci->io = &mipi_i3c_hci_dma; 689 + dev_dbg(&hci->master.dev, "Using DMA\n"); 690 + } 691 + } 692 + 693 + /* If no DMA, try PIO */ 694 + if (!hci->io && hci->PIO_regs) { 695 + ret = i3c_hci_set_io_mode(hci, false); 696 + if (!ret) { 697 + hci->io = &mipi_i3c_hci_pio; 698 + dev_dbg(&hci->master.dev, "Using PIO\n"); 699 + } 700 + } 701 + 702 + if (!hci->io) { 703 + dev_err(&hci->master.dev, "neither DMA nor PIO can be used\n"); 704 + ret = ret ?: -EINVAL; 705 + } 706 + if (ret) 707 + return ret; 708 + 709 + /* Configure OD and PP timings for AMD platforms */ 710 + if (hci->quirks & HCI_QUIRK_OD_PP_TIMING) 711 + amd_set_od_pp_timing(hci); 712 + 713 + return 0; 714 + } 715 + 642 716 static int i3c_hci_init(struct i3c_hci *hci) 643 717 { 644 718 bool size_in_dwords; ··· 782 708 if (ret) 783 709 return ret; 784 710 785 - ret = i3c_hci_software_reset(hci); 786 - if (ret) 787 - return -ENXIO; 788 - 789 - /* Disable all interrupts */ 790 - reg_write(INTR_SIGNAL_ENABLE, 0x0); 791 - /* 792 - * Only allow bit 31:10 signal updates because 793 - * Bit 0:9 are reserved in IP version >= 0.8 794 - * Bit 0:5 are defined in IP version < 0.8 but not handled by PIO code 795 - */ 796 - reg_write(INTR_STATUS_ENABLE, GENMASK(31, 10)); 797 - 798 - /* Make sure our data ordering fits the host's */ 799 - regval = reg_read(HC_CONTROL); 800 - if (IS_ENABLED(CONFIG_CPU_BIG_ENDIAN)) { 801 - if (!(regval & HC_CONTROL_DATA_BIG_ENDIAN)) { 802 - regval |= HC_CONTROL_DATA_BIG_ENDIAN; 803 - reg_write(HC_CONTROL, regval); 804 - regval = reg_read(HC_CONTROL); 805 - if (!(regval & HC_CONTROL_DATA_BIG_ENDIAN)) { 806 - dev_err(&hci->master.dev, "cannot set BE mode\n"); 807 - return -EOPNOTSUPP; 808 - } 809 - } 810 - } else { 811 - if (regval & HC_CONTROL_DATA_BIG_ENDIAN) { 812 - regval &= ~HC_CONTROL_DATA_BIG_ENDIAN; 813 - reg_write(HC_CONTROL, regval); 814 - regval = reg_read(HC_CONTROL); 815 - if (regval & HC_CONTROL_DATA_BIG_ENDIAN) { 816 - dev_err(&hci->master.dev, "cannot clear BE mode\n"); 817 - return -EOPNOTSUPP; 818 - } 819 - } 820 - } 821 - 822 711 /* Select our command descriptor model */ 823 712 switch (FIELD_GET(HC_CAP_CMD_SIZE, hci->caps)) { 824 713 case 0: ··· 799 762 if (hci->quirks & HCI_QUIRK_PIO_MODE) 800 763 hci->RHS_regs = NULL; 801 764 802 - /* Try activating DMA operations first */ 803 - if (hci->RHS_regs) { 804 - ret = i3c_hci_set_io_mode(hci, true); 805 - if (!ret) { 806 - hci->io = &mipi_i3c_hci_dma; 807 - dev_dbg(&hci->master.dev, "Using DMA\n"); 808 - } 809 - } 810 - 811 - /* If no DMA, try PIO */ 812 - if (!hci->io && hci->PIO_regs) { 813 - ret = i3c_hci_set_io_mode(hci, false); 814 - if (!ret) { 815 - hci->io = &mipi_i3c_hci_pio; 816 - dev_dbg(&hci->master.dev, "Using PIO\n"); 817 - } 818 - } 819 - 820 - if (!hci->io) { 821 - dev_err(&hci->master.dev, "neither DMA nor PIO can be used\n"); 822 - if (!ret) 823 - ret = -EINVAL; 824 - return ret; 825 - } 826 - 827 - /* Configure OD and PP timings for AMD platforms */ 828 - if (hci->quirks & HCI_QUIRK_OD_PP_TIMING) 829 - amd_set_od_pp_timing(hci); 830 - 831 - return 0; 765 + return i3c_hci_reset_and_init(hci); 832 766 } 833 767 834 768 static int i3c_hci_probe(struct platform_device *pdev)