--- e/drivers/scsi/hosts.c 2023-03-13 16:36:31.771360300 +0800 +++ f/drivers/scsi/hosts.c 2023-03-13 19:55:41.210607500 +0800 @@ -180,8 +180,14 @@ void scsi_remove_host(struct Scsi_Host * flush_workqueue(shost->tmf_work_q); scsi_forget_host(shost); mutex_unlock(&shost->scan_mutex); - scsi_proc_host_rm(shost); - scsi_proc_hostdir_rm(shost->hostt); + if (shost->has_proc_entry) { + shost->has_proc_entry = 0; + scsi_proc_host_rm(shost); + } + if (shost->has_proc_dir) { + shost->has_proc_dir = 0; + scsi_proc_hostdir_rm(shost->hostt); + } /* * New SCSI devices cannot be attached anymore because of the SCSI host @@ -308,7 +314,7 @@ int scsi_add_host_with_dma(struct Scsi_H if (error) goto out_del_dev; - scsi_proc_host_add(shost); + shost->has_proc_entry = scsi_proc_host_add(shost) ? 0 : 1; scsi_autopm_put_host(shost); return error; @@ -342,7 +348,8 @@ static void scsi_host_dev_release(struct struct device *parent = dev->parent; /* In case scsi_remove_host() has not been called. */ - scsi_proc_hostdir_rm(shost->hostt); + if (shost->has_proc_dir) + scsi_proc_hostdir_rm(shost->hostt); /* Wait for functions invoked through call_rcu(&scmd->rcu, ...) */ rcu_barrier(); @@ -521,8 +528,10 @@ struct Scsi_Host *scsi_host_alloc(struct "failed to create tmf workq\n"); goto fail; } + shost->has_proc_dir = 0; if (scsi_proc_hostdir_add(shost->hostt) < 0) goto fail; + shost->has_proc_dir = 1; return shost; fail: /* --- e/drivers/scsi/scsi_priv.h 2023-03-13 16:35:13.115863300 +0800 +++ f/drivers/scsi/scsi_priv.h 2023-03-13 16:42:38.599849800 +0800 @@ -113,14 +113,14 @@ extern void scsi_evt_thread(struct work_ #ifdef CONFIG_SCSI_PROC_FS extern int scsi_proc_hostdir_add(const struct scsi_host_template *); extern void scsi_proc_hostdir_rm(const struct scsi_host_template *); -extern void scsi_proc_host_add(struct Scsi_Host *); +extern int scsi_proc_host_add(struct Scsi_Host *); extern void scsi_proc_host_rm(struct Scsi_Host *); extern int scsi_init_procfs(void); extern void scsi_exit_procfs(void); #else # define scsi_proc_hostdir_add(sht) 0 # define scsi_proc_hostdir_rm(sht) do { } while (0) -# define scsi_proc_host_add(shost) do { } while (0) +# define scsi_proc_host_add(shost) (0) # define scsi_proc_host_rm(shost) do { } while (0) # define scsi_init_procfs() (0) # define scsi_exit_procfs() do { } while (0) --- e/drivers/scsi/scsi_proc.c 2023-03-13 16:44:34.303439700 +0800 +++ f/drivers/scsi/scsi_proc.c 2023-03-13 16:50:16.629024700 +0800 @@ -215,7 +215,7 @@ void scsi_proc_hostdir_rm(const struct s * scsi_proc_host_add - Add entry for this host to appropriate /proc dir * @shost: host to add */ -void scsi_proc_host_add(struct Scsi_Host *shost) +int scsi_proc_host_add(struct Scsi_Host *shost) { const struct scsi_host_template *sht = shost->hostt; struct scsi_proc_entry *e; @@ -223,7 +223,7 @@ void scsi_proc_host_add(struct Scsi_Host char name[10]; if (!sht->show_info) - return; + return -ENXIO; e = scsi_lookup_proc_entry(sht); if (!e) @@ -234,12 +234,13 @@ void scsi_proc_host_add(struct Scsi_Host &proc_scsi_ops, shost); if (!p) goto err; - return; + return 0; err: shost_printk(KERN_ERR, shost, "%s: Failed to register host (%s failed)\n", __func__, e ? "proc_create_data()" : "scsi_proc_hostdir_add()"); + return -ENXIO; } /** --- e/include/scsi/scsi_host.h 2023-03-13 16:33:13.890534300 +0800 +++ f/include/scsi/scsi_host.h 2023-03-13 19:52:24.441709800 +0800 @@ -659,6 +659,8 @@ struct Scsi_Host { /* The transport requires the LUN bits NOT to be stored in CDB[1] */ unsigned no_scsi2_lun_in_cdb:1; + unsigned has_proc_entry:1; + unsigned has_proc_dir:1; /* * Optional work queue to be utilized by the transport */