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.

Merge patch series "scsi: ufs: Remove overzealous memory barriers"

Andrew Halaney <ahalaney@redhat.com> says:

Please review with care as I'm not all that confident in this subject.
UFS has a lot of mb() variants used, most with comments saying "ensure
this takes effect before continuing". mb()'s aren't really the way to
guarantee that, a read back is the best method.

Some of these though I think could go a step further and remove the
mb() variant without a read back. As far as I can tell there's no real
reason to ensure it takes effect in most cases (there's no delay() or
anything afterwards, and eventually another readl()/writel() happens
which is by definition ordered). Some of the patches in this series do
that if I was confident it was safe (or a reviewer pointed out prior
that they thought it was safe to do so).

Thanks in advance for the help,
Andrew

Link: https://lore.kernel.org/r/20240329-ufs-reset-ensure-effect-before-delay-v5-0-181252004586@redhat.com
Signed-off-by: Martin K. Petersen <martin.petersen@oracle.com>

+12 -29
+3 -12
drivers/ufs/core/ufshcd.c
··· 4305 4305 * Make sure UIC command completion interrupt is disabled before 4306 4306 * issuing UIC command. 4307 4307 */ 4308 - wmb(); 4308 + ufshcd_readl(hba, REG_INTERRUPT_ENABLE); 4309 4309 reenable_intr = true; 4310 4310 } 4311 4311 spin_unlock_irqrestore(hba->host->host_lock, flags); ··· 4786 4786 REG_UTP_TASK_REQ_LIST_BASE_L); 4787 4787 ufshcd_writel(hba, upper_32_bits(hba->utmrdl_dma_addr), 4788 4788 REG_UTP_TASK_REQ_LIST_BASE_H); 4789 - 4790 - /* 4791 - * Make sure base address and interrupt setup are updated before 4792 - * enabling the run/stop registers below. 4793 - */ 4794 - wmb(); 4795 4789 4796 4790 /* 4797 4791 * UCRDY, UTMRLDY and UTRLRDY bits must be 1 ··· 7102 7108 7103 7109 /* send command to the controller */ 7104 7110 __set_bit(task_tag, &hba->outstanding_tasks); 7105 - 7106 7111 ufshcd_writel(hba, 1 << task_tag, REG_UTP_TASK_REQ_DOOR_BELL); 7107 - /* Make sure that doorbell is committed immediately */ 7108 - wmb(); 7109 7112 7110 7113 spin_unlock_irqrestore(host->host_lock, flags); 7111 7114 ··· 10354 10363 * are updated with the latest queue addresses. Only after 10355 10364 * updating these addresses, we can queue the new commands. 10356 10365 */ 10357 - mb(); 10366 + ufshcd_readl(hba, REG_UTP_TASK_REQ_LIST_BASE_H); 10358 10367 10359 10368 /* Resuming from hibernate, assume that link was OFF */ 10360 10369 ufshcd_set_link_off(hba); ··· 10575 10584 * Make sure that UFS interrupts are disabled and any pending interrupt 10576 10585 * status is cleared before registering UFS interrupt handler. 10577 10586 */ 10578 - mb(); 10587 + ufshcd_readl(hba, REG_INTERRUPT_ENABLE); 10579 10588 10580 10589 /* IRQ registration */ 10581 10590 err = devm_request_irq(dev, irq, ufshcd_intr, IRQF_SHARED, UFSHCD, hba);
+1 -1
drivers/ufs/host/cdns-pltfrm.c
··· 136 136 * Make sure the register was updated, 137 137 * UniPro layer will not work with an incorrect value. 138 138 */ 139 - mb(); 139 + ufshcd_readl(hba, CDNS_UFS_REG_HCLKDIV); 140 140 141 141 return 0; 142 142 }
+2 -10
drivers/ufs/host/ufs-qcom.c
··· 278 278 279 279 if (host->hw_ver.major >= 0x05) 280 280 ufshcd_rmwl(host->hba, QUNIPRO_G4_SEL, 0, REG_UFS_CFG0); 281 - 282 - /* make sure above configuration is applied before we return */ 283 - mb(); 284 281 } 285 282 286 283 /* ··· 406 409 REG_UFS_CFG2); 407 410 408 411 /* Ensure that HW clock gating is enabled before next operations */ 409 - mb(); 412 + ufshcd_readl(hba, REG_UFS_CFG2); 410 413 } 411 414 412 415 static int ufs_qcom_hce_enable_notify(struct ufs_hba *hba, ··· 498 501 * make sure above write gets applied before we return from 499 502 * this function. 500 503 */ 501 - mb(); 504 + ufshcd_readl(hba, REG_UFS_SYS1CLK_1US); 502 505 } 503 506 504 507 return 0; ··· 1442 1445 (u32)host->testbus.select_minor << offset, 1443 1446 reg); 1444 1447 ufs_qcom_enable_test_bus(host); 1445 - /* 1446 - * Make sure the test bus configuration is 1447 - * committed before returning. 1448 - */ 1449 - mb(); 1450 1448 1451 1449 return 0; 1452 1450 }
+6 -6
drivers/ufs/host/ufs-qcom.h
··· 151 151 ufshcd_rmwl(hba, UFS_PHY_SOFT_RESET, UFS_PHY_SOFT_RESET, REG_UFS_CFG1); 152 152 153 153 /* 154 - * Make sure assertion of ufs phy reset is written to 155 - * register before returning 154 + * Dummy read to ensure the write takes effect before doing any sort 155 + * of delay 156 156 */ 157 - mb(); 157 + ufshcd_readl(hba, REG_UFS_CFG1); 158 158 } 159 159 160 160 static inline void ufs_qcom_deassert_reset(struct ufs_hba *hba) ··· 162 162 ufshcd_rmwl(hba, UFS_PHY_SOFT_RESET, 0, REG_UFS_CFG1); 163 163 164 164 /* 165 - * Make sure de-assertion of ufs phy reset is written to 166 - * register before returning 165 + * Dummy read to ensure the write takes effect before doing any sort 166 + * of delay 167 167 */ 168 - mb(); 168 + ufshcd_readl(hba, REG_UFS_CFG1); 169 169 } 170 170 171 171 /* Host controller hardware version: major.minor.step */