aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/scsi/scsi.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/scsi/scsi.c')
-rw-r--r--drivers/scsi/scsi.c58
1 files changed, 42 insertions, 16 deletions
diff --git a/drivers/scsi/scsi.c b/drivers/scsi/scsi.c
index b332caddd5b3..c51b5769eac8 100644
--- a/drivers/scsi/scsi.c
+++ b/drivers/scsi/scsi.c
@@ -96,24 +96,40 @@ unsigned int scsi_logging_level;
96EXPORT_SYMBOL(scsi_logging_level); 96EXPORT_SYMBOL(scsi_logging_level);
97#endif 97#endif
98 98
99const char *const scsi_device_types[MAX_SCSI_DEVICE_CODE] = { 99static const char *const scsi_device_types[] = {
100 "Direct-Access ", 100 "Direct access ",
101 "Sequential-Access", 101 "Sequential access",
102 "Printer ", 102 "Printer ",
103 "Processor ", 103 "Processor ",
104 "WORM ", 104 "WORM ",
105 "CD-ROM ", 105 "CD/DVD ",
106 "Scanner ", 106 "Scanner ",
107 "Optical Device ", 107 "Optical memory ",
108 "Medium Changer ", 108 "Media changer ",
109 "Communications ", 109 "Communications ",
110 "Unknown ", 110 "ASC IT8 ",
111 "Unknown ", 111 "ASC IT8 ",
112 "RAID ", 112 "RAID ",
113 "Enclosure ", 113 "Enclosure ",
114 "Direct-Access-RBC", 114 "Direct access RBC",
115 "Optical card ",
116 "Bridge controller",
117 "Object storage ",
118 "Automation/Drive ",
115}; 119};
116EXPORT_SYMBOL(scsi_device_types); 120
121const char * scsi_device_type(unsigned type)
122{
123 if (type == 0x1e)
124 return "Well-known LUN ";
125 if (type == 0x1f)
126 return "No Device ";
127 if (type > ARRAY_SIZE(scsi_device_types))
128 return "Unknown ";
129 return scsi_device_types[type];
130}
131
132EXPORT_SYMBOL(scsi_device_type);
117 133
118struct scsi_host_cmd_pool { 134struct scsi_host_cmd_pool {
119 kmem_cache_t *slab; 135 kmem_cache_t *slab;
@@ -835,14 +851,14 @@ EXPORT_SYMBOL(scsi_track_queue_full);
835 */ 851 */
836int scsi_device_get(struct scsi_device *sdev) 852int scsi_device_get(struct scsi_device *sdev)
837{ 853{
838 if (sdev->sdev_state == SDEV_DEL || sdev->sdev_state == SDEV_CANCEL) 854 if (sdev->sdev_state == SDEV_DEL)
839 return -ENXIO; 855 return -ENXIO;
840 if (!get_device(&sdev->sdev_gendev)) 856 if (!get_device(&sdev->sdev_gendev))
841 return -ENXIO; 857 return -ENXIO;
842 if (!try_module_get(sdev->host->hostt->module)) { 858 /* We can fail this if we're doing SCSI operations
843 put_device(&sdev->sdev_gendev); 859 * from module exit (like cache flush) */
844 return -ENXIO; 860 try_module_get(sdev->host->hostt->module);
845 } 861
846 return 0; 862 return 0;
847} 863}
848EXPORT_SYMBOL(scsi_device_get); 864EXPORT_SYMBOL(scsi_device_get);
@@ -857,7 +873,14 @@ EXPORT_SYMBOL(scsi_device_get);
857 */ 873 */
858void scsi_device_put(struct scsi_device *sdev) 874void scsi_device_put(struct scsi_device *sdev)
859{ 875{
860 module_put(sdev->host->hostt->module); 876 struct module *module = sdev->host->hostt->module;
877
878#ifdef CONFIG_MODULE_UNLOAD
879 /* The module refcount will be zero if scsi_device_get()
880 * was called from a module removal routine */
881 if (module && module_refcount(module) != 0)
882 module_put(module);
883#endif
861 put_device(&sdev->sdev_gendev); 884 put_device(&sdev->sdev_gendev);
862} 885}
863EXPORT_SYMBOL(scsi_device_put); 886EXPORT_SYMBOL(scsi_device_put);
@@ -1099,6 +1122,8 @@ static int __init init_scsi(void)
1099 for_each_possible_cpu(i) 1122 for_each_possible_cpu(i)
1100 INIT_LIST_HEAD(&per_cpu(scsi_done_q, i)); 1123 INIT_LIST_HEAD(&per_cpu(scsi_done_q, i));
1101 1124
1125 scsi_netlink_init();
1126
1102 printk(KERN_NOTICE "SCSI subsystem initialized\n"); 1127 printk(KERN_NOTICE "SCSI subsystem initialized\n");
1103 return 0; 1128 return 0;
1104 1129
@@ -1119,6 +1144,7 @@ cleanup_queue:
1119 1144
1120static void __exit exit_scsi(void) 1145static void __exit exit_scsi(void)
1121{ 1146{
1147 scsi_netlink_exit();
1122 scsi_sysfs_unregister(); 1148 scsi_sysfs_unregister();
1123 scsi_exit_sysctl(); 1149 scsi_exit_sysctl();
1124 scsi_exit_hosts(); 1150 scsi_exit_hosts();