ses.c 20 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865
  1. /*
  2. * SCSI Enclosure Services
  3. *
  4. * Copyright (C) 2008 James Bottomley <James.Bottomley@HansenPartnership.com>
  5. *
  6. **-----------------------------------------------------------------------------
  7. **
  8. ** This program is free software; you can redistribute it and/or
  9. ** modify it under the terms of the GNU General Public License
  10. ** version 2 as published by the Free Software Foundation.
  11. **
  12. ** This program is distributed in the hope that it will be useful,
  13. ** but WITHOUT ANY WARRANTY; without even the implied warranty of
  14. ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  15. ** GNU General Public License for more details.
  16. **
  17. ** You should have received a copy of the GNU General Public License
  18. ** along with this program; if not, write to the Free Software
  19. ** Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  20. **
  21. **-----------------------------------------------------------------------------
  22. */
  23. #include <linux/slab.h>
  24. #include <linux/module.h>
  25. #include <linux/kernel.h>
  26. #include <linux/enclosure.h>
  27. #include <asm/unaligned.h>
  28. #include <scsi/scsi.h>
  29. #include <scsi/scsi_cmnd.h>
  30. #include <scsi/scsi_dbg.h>
  31. #include <scsi/scsi_device.h>
  32. #include <scsi/scsi_driver.h>
  33. #include <scsi/scsi_host.h>
  34. struct ses_device {
  35. unsigned char *page1;
  36. unsigned char *page1_types;
  37. unsigned char *page2;
  38. unsigned char *page10;
  39. short page1_len;
  40. short page1_num_types;
  41. short page2_len;
  42. short page10_len;
  43. };
  44. struct ses_component {
  45. u64 addr;
  46. };
  47. static int ses_probe(struct device *dev)
  48. {
  49. struct scsi_device *sdev = to_scsi_device(dev);
  50. int err = -ENODEV;
  51. if (sdev->type != TYPE_ENCLOSURE)
  52. goto out;
  53. err = 0;
  54. sdev_printk(KERN_NOTICE, sdev, "Attached Enclosure device\n");
  55. out:
  56. return err;
  57. }
  58. #define SES_TIMEOUT (30 * HZ)
  59. #define SES_RETRIES 3
  60. static void init_device_slot_control(unsigned char *dest_desc,
  61. struct enclosure_component *ecomp,
  62. unsigned char *status)
  63. {
  64. memcpy(dest_desc, status, 4);
  65. dest_desc[0] = 0;
  66. /* only clear byte 1 for ENCLOSURE_COMPONENT_DEVICE */
  67. if (ecomp->type == ENCLOSURE_COMPONENT_DEVICE)
  68. dest_desc[1] = 0;
  69. dest_desc[2] &= 0xde;
  70. dest_desc[3] &= 0x3c;
  71. }
  72. static int ses_recv_diag(struct scsi_device *sdev, int page_code,
  73. void *buf, int bufflen)
  74. {
  75. int ret;
  76. unsigned char cmd[] = {
  77. RECEIVE_DIAGNOSTIC,
  78. 1, /* Set PCV bit */
  79. page_code,
  80. bufflen >> 8,
  81. bufflen & 0xff,
  82. 0
  83. };
  84. unsigned char recv_page_code;
  85. ret = scsi_execute_req(sdev, cmd, DMA_FROM_DEVICE, buf, bufflen,
  86. NULL, SES_TIMEOUT, SES_RETRIES, NULL);
  87. if (unlikely(!ret))
  88. return ret;
  89. recv_page_code = ((unsigned char *)buf)[0];
  90. if (likely(recv_page_code == page_code))
  91. return ret;
  92. /* successful diagnostic but wrong page code. This happens to some
  93. * USB devices, just print a message and pretend there was an error */
  94. sdev_printk(KERN_ERR, sdev,
  95. "Wrong diagnostic page; asked for %d got %u\n",
  96. page_code, recv_page_code);
  97. return -EINVAL;
  98. }
  99. static int ses_send_diag(struct scsi_device *sdev, int page_code,
  100. void *buf, int bufflen)
  101. {
  102. u32 result;
  103. unsigned char cmd[] = {
  104. SEND_DIAGNOSTIC,
  105. 0x10, /* Set PF bit */
  106. 0,
  107. bufflen >> 8,
  108. bufflen & 0xff,
  109. 0
  110. };
  111. result = scsi_execute_req(sdev, cmd, DMA_TO_DEVICE, buf, bufflen,
  112. NULL, SES_TIMEOUT, SES_RETRIES, NULL);
  113. if (result)
  114. sdev_printk(KERN_ERR, sdev, "SEND DIAGNOSTIC result: %8x\n",
  115. result);
  116. return result;
  117. }
  118. static int ses_set_page2_descriptor(struct enclosure_device *edev,
  119. struct enclosure_component *ecomp,
  120. unsigned char *desc)
  121. {
  122. int i, j, count = 0, descriptor = ecomp->number;
  123. struct scsi_device *sdev = to_scsi_device(edev->edev.parent);
  124. struct ses_device *ses_dev = edev->scratch;
  125. unsigned char *type_ptr = ses_dev->page1_types;
  126. unsigned char *desc_ptr = ses_dev->page2 + 8;
  127. /* Clear everything */
  128. memset(desc_ptr, 0, ses_dev->page2_len - 8);
  129. for (i = 0; i < ses_dev->page1_num_types; i++, type_ptr += 4) {
  130. for (j = 0; j < type_ptr[1]; j++) {
  131. desc_ptr += 4;
  132. if (type_ptr[0] != ENCLOSURE_COMPONENT_DEVICE &&
  133. type_ptr[0] != ENCLOSURE_COMPONENT_ARRAY_DEVICE)
  134. continue;
  135. if (count++ == descriptor) {
  136. memcpy(desc_ptr, desc, 4);
  137. /* set select */
  138. desc_ptr[0] |= 0x80;
  139. /* clear reserved, just in case */
  140. desc_ptr[0] &= 0xf0;
  141. }
  142. }
  143. }
  144. return ses_send_diag(sdev, 2, ses_dev->page2, ses_dev->page2_len);
  145. }
  146. static unsigned char *ses_get_page2_descriptor(struct enclosure_device *edev,
  147. struct enclosure_component *ecomp)
  148. {
  149. int i, j, count = 0, descriptor = ecomp->number;
  150. struct scsi_device *sdev = to_scsi_device(edev->edev.parent);
  151. struct ses_device *ses_dev = edev->scratch;
  152. unsigned char *type_ptr = ses_dev->page1_types;
  153. unsigned char *desc_ptr = ses_dev->page2 + 8;
  154. ses_recv_diag(sdev, 2, ses_dev->page2, ses_dev->page2_len);
  155. for (i = 0; i < ses_dev->page1_num_types; i++, type_ptr += 4) {
  156. for (j = 0; j < type_ptr[1]; j++) {
  157. desc_ptr += 4;
  158. if (type_ptr[0] != ENCLOSURE_COMPONENT_DEVICE &&
  159. type_ptr[0] != ENCLOSURE_COMPONENT_ARRAY_DEVICE)
  160. continue;
  161. if (count++ == descriptor)
  162. return desc_ptr;
  163. }
  164. }
  165. return NULL;
  166. }
  167. /* For device slot and array device slot elements, byte 3 bit 6
  168. * is "fault sensed" while byte 3 bit 5 is "fault reqstd". As this
  169. * code stands these bits are shifted 4 positions right so in
  170. * sysfs they will appear as bits 2 and 1 respectively. Strange. */
  171. static void ses_get_fault(struct enclosure_device *edev,
  172. struct enclosure_component *ecomp)
  173. {
  174. unsigned char *desc;
  175. desc = ses_get_page2_descriptor(edev, ecomp);
  176. if (desc)
  177. ecomp->fault = (desc[3] & 0x60) >> 4;
  178. }
  179. static int ses_set_fault(struct enclosure_device *edev,
  180. struct enclosure_component *ecomp,
  181. enum enclosure_component_setting val)
  182. {
  183. unsigned char desc[4];
  184. unsigned char *desc_ptr;
  185. desc_ptr = ses_get_page2_descriptor(edev, ecomp);
  186. if (!desc_ptr)
  187. return -EIO;
  188. init_device_slot_control(desc, ecomp, desc_ptr);
  189. switch (val) {
  190. case ENCLOSURE_SETTING_DISABLED:
  191. desc[3] &= 0xdf;
  192. break;
  193. case ENCLOSURE_SETTING_ENABLED:
  194. desc[3] |= 0x20;
  195. break;
  196. default:
  197. /* SES doesn't do the SGPIO blink settings */
  198. return -EINVAL;
  199. }
  200. return ses_set_page2_descriptor(edev, ecomp, desc);
  201. }
  202. static void ses_get_status(struct enclosure_device *edev,
  203. struct enclosure_component *ecomp)
  204. {
  205. unsigned char *desc;
  206. desc = ses_get_page2_descriptor(edev, ecomp);
  207. if (desc)
  208. ecomp->status = (desc[0] & 0x0f);
  209. }
  210. static void ses_get_locate(struct enclosure_device *edev,
  211. struct enclosure_component *ecomp)
  212. {
  213. unsigned char *desc;
  214. desc = ses_get_page2_descriptor(edev, ecomp);
  215. if (desc)
  216. ecomp->locate = (desc[2] & 0x02) ? 1 : 0;
  217. }
  218. static int ses_set_locate(struct enclosure_device *edev,
  219. struct enclosure_component *ecomp,
  220. enum enclosure_component_setting val)
  221. {
  222. unsigned char desc[4];
  223. unsigned char *desc_ptr;
  224. desc_ptr = ses_get_page2_descriptor(edev, ecomp);
  225. if (!desc_ptr)
  226. return -EIO;
  227. init_device_slot_control(desc, ecomp, desc_ptr);
  228. switch (val) {
  229. case ENCLOSURE_SETTING_DISABLED:
  230. desc[2] &= 0xfd;
  231. break;
  232. case ENCLOSURE_SETTING_ENABLED:
  233. desc[2] |= 0x02;
  234. break;
  235. default:
  236. /* SES doesn't do the SGPIO blink settings */
  237. return -EINVAL;
  238. }
  239. return ses_set_page2_descriptor(edev, ecomp, desc);
  240. }
  241. static int ses_set_active(struct enclosure_device *edev,
  242. struct enclosure_component *ecomp,
  243. enum enclosure_component_setting val)
  244. {
  245. unsigned char desc[4];
  246. unsigned char *desc_ptr;
  247. desc_ptr = ses_get_page2_descriptor(edev, ecomp);
  248. if (!desc_ptr)
  249. return -EIO;
  250. init_device_slot_control(desc, ecomp, desc_ptr);
  251. switch (val) {
  252. case ENCLOSURE_SETTING_DISABLED:
  253. desc[2] &= 0x7f;
  254. ecomp->active = 0;
  255. break;
  256. case ENCLOSURE_SETTING_ENABLED:
  257. desc[2] |= 0x80;
  258. ecomp->active = 1;
  259. break;
  260. default:
  261. /* SES doesn't do the SGPIO blink settings */
  262. return -EINVAL;
  263. }
  264. return ses_set_page2_descriptor(edev, ecomp, desc);
  265. }
  266. static int ses_show_id(struct enclosure_device *edev, char *buf)
  267. {
  268. struct ses_device *ses_dev = edev->scratch;
  269. unsigned long long id = get_unaligned_be64(ses_dev->page1+8+4);
  270. return sprintf(buf, "%#llx\n", id);
  271. }
  272. static void ses_get_power_status(struct enclosure_device *edev,
  273. struct enclosure_component *ecomp)
  274. {
  275. unsigned char *desc;
  276. desc = ses_get_page2_descriptor(edev, ecomp);
  277. if (desc)
  278. ecomp->power_status = (desc[3] & 0x10) ? 0 : 1;
  279. }
  280. static int ses_set_power_status(struct enclosure_device *edev,
  281. struct enclosure_component *ecomp,
  282. int val)
  283. {
  284. unsigned char desc[4];
  285. unsigned char *desc_ptr;
  286. desc_ptr = ses_get_page2_descriptor(edev, ecomp);
  287. if (!desc_ptr)
  288. return -EIO;
  289. init_device_slot_control(desc, ecomp, desc_ptr);
  290. switch (val) {
  291. /* power = 1 is device_off = 0 and vice versa */
  292. case 0:
  293. desc[3] |= 0x10;
  294. break;
  295. case 1:
  296. desc[3] &= 0xef;
  297. break;
  298. default:
  299. return -EINVAL;
  300. }
  301. ecomp->power_status = val;
  302. return ses_set_page2_descriptor(edev, ecomp, desc);
  303. }
  304. static struct enclosure_component_callbacks ses_enclosure_callbacks = {
  305. .get_fault = ses_get_fault,
  306. .set_fault = ses_set_fault,
  307. .get_status = ses_get_status,
  308. .get_locate = ses_get_locate,
  309. .set_locate = ses_set_locate,
  310. .get_power_status = ses_get_power_status,
  311. .set_power_status = ses_set_power_status,
  312. .set_active = ses_set_active,
  313. .show_id = ses_show_id,
  314. };
  315. struct ses_host_edev {
  316. struct Scsi_Host *shost;
  317. struct enclosure_device *edev;
  318. };
  319. #if 0
  320. int ses_match_host(struct enclosure_device *edev, void *data)
  321. {
  322. struct ses_host_edev *sed = data;
  323. struct scsi_device *sdev;
  324. if (!scsi_is_sdev_device(edev->edev.parent))
  325. return 0;
  326. sdev = to_scsi_device(edev->edev.parent);
  327. if (sdev->host != sed->shost)
  328. return 0;
  329. sed->edev = edev;
  330. return 1;
  331. }
  332. #endif /* 0 */
  333. static void ses_process_descriptor(struct enclosure_component *ecomp,
  334. unsigned char *desc)
  335. {
  336. int eip = desc[0] & 0x10;
  337. int invalid = desc[0] & 0x80;
  338. enum scsi_protocol proto = desc[0] & 0x0f;
  339. u64 addr = 0;
  340. int slot = -1;
  341. struct ses_component *scomp = ecomp->scratch;
  342. unsigned char *d;
  343. if (invalid)
  344. return;
  345. switch (proto) {
  346. case SCSI_PROTOCOL_FCP:
  347. if (eip) {
  348. d = desc + 4;
  349. slot = d[3];
  350. }
  351. break;
  352. case SCSI_PROTOCOL_SAS:
  353. if (eip) {
  354. d = desc + 4;
  355. slot = d[3];
  356. d = desc + 8;
  357. } else
  358. d = desc + 4;
  359. /* only take the phy0 addr */
  360. addr = (u64)d[12] << 56 |
  361. (u64)d[13] << 48 |
  362. (u64)d[14] << 40 |
  363. (u64)d[15] << 32 |
  364. (u64)d[16] << 24 |
  365. (u64)d[17] << 16 |
  366. (u64)d[18] << 8 |
  367. (u64)d[19];
  368. break;
  369. default:
  370. /* FIXME: Need to add more protocols than just SAS */
  371. break;
  372. }
  373. ecomp->slot = slot;
  374. scomp->addr = addr;
  375. }
  376. struct efd {
  377. u64 addr;
  378. struct device *dev;
  379. };
  380. static int ses_enclosure_find_by_addr(struct enclosure_device *edev,
  381. void *data)
  382. {
  383. struct efd *efd = data;
  384. int i;
  385. struct ses_component *scomp;
  386. if (!edev->component[0].scratch)
  387. return 0;
  388. for (i = 0; i < edev->components; i++) {
  389. scomp = edev->component[i].scratch;
  390. if (scomp->addr != efd->addr)
  391. continue;
  392. if (enclosure_add_device(edev, i, efd->dev) == 0)
  393. kobject_uevent(&efd->dev->kobj, KOBJ_CHANGE);
  394. return 1;
  395. }
  396. return 0;
  397. }
  398. #define INIT_ALLOC_SIZE 32
  399. static void ses_enclosure_data_process(struct enclosure_device *edev,
  400. struct scsi_device *sdev,
  401. int create)
  402. {
  403. u32 result;
  404. unsigned char *buf = NULL, *type_ptr, *desc_ptr, *addl_desc_ptr = NULL;
  405. int i, j, page7_len, len, components;
  406. struct ses_device *ses_dev = edev->scratch;
  407. int types = ses_dev->page1_num_types;
  408. unsigned char *hdr_buf = kzalloc(INIT_ALLOC_SIZE, GFP_KERNEL);
  409. if (!hdr_buf)
  410. goto simple_populate;
  411. /* re-read page 10 */
  412. if (ses_dev->page10)
  413. ses_recv_diag(sdev, 10, ses_dev->page10, ses_dev->page10_len);
  414. /* Page 7 for the descriptors is optional */
  415. result = ses_recv_diag(sdev, 7, hdr_buf, INIT_ALLOC_SIZE);
  416. if (result)
  417. goto simple_populate;
  418. page7_len = len = (hdr_buf[2] << 8) + hdr_buf[3] + 4;
  419. /* add 1 for trailing '\0' we'll use */
  420. buf = kzalloc(len + 1, GFP_KERNEL);
  421. if (!buf)
  422. goto simple_populate;
  423. result = ses_recv_diag(sdev, 7, buf, len);
  424. if (result) {
  425. simple_populate:
  426. kfree(buf);
  427. buf = NULL;
  428. desc_ptr = NULL;
  429. len = 0;
  430. page7_len = 0;
  431. } else {
  432. desc_ptr = buf + 8;
  433. len = (desc_ptr[2] << 8) + desc_ptr[3];
  434. /* skip past overall descriptor */
  435. desc_ptr += len + 4;
  436. }
  437. if (ses_dev->page10)
  438. addl_desc_ptr = ses_dev->page10 + 8;
  439. type_ptr = ses_dev->page1_types;
  440. components = 0;
  441. for (i = 0; i < types; i++, type_ptr += 4) {
  442. for (j = 0; j < type_ptr[1]; j++) {
  443. char *name = NULL;
  444. struct enclosure_component *ecomp;
  445. if (desc_ptr) {
  446. if (desc_ptr >= buf + page7_len) {
  447. desc_ptr = NULL;
  448. } else {
  449. len = (desc_ptr[2] << 8) + desc_ptr[3];
  450. desc_ptr += 4;
  451. /* Add trailing zero - pushes into
  452. * reserved space */
  453. desc_ptr[len] = '\0';
  454. name = desc_ptr;
  455. }
  456. }
  457. if (type_ptr[0] == ENCLOSURE_COMPONENT_DEVICE ||
  458. type_ptr[0] == ENCLOSURE_COMPONENT_ARRAY_DEVICE) {
  459. if (create)
  460. ecomp = enclosure_component_alloc(
  461. edev,
  462. components++,
  463. type_ptr[0],
  464. name);
  465. else
  466. ecomp = &edev->component[components++];
  467. if (!IS_ERR(ecomp)) {
  468. if (addl_desc_ptr)
  469. ses_process_descriptor(
  470. ecomp,
  471. addl_desc_ptr);
  472. if (create)
  473. enclosure_component_register(
  474. ecomp);
  475. }
  476. }
  477. if (desc_ptr)
  478. desc_ptr += len;
  479. if (addl_desc_ptr &&
  480. /* only find additional descriptions for specific devices */
  481. (type_ptr[0] == ENCLOSURE_COMPONENT_DEVICE ||
  482. type_ptr[0] == ENCLOSURE_COMPONENT_ARRAY_DEVICE ||
  483. type_ptr[0] == ENCLOSURE_COMPONENT_SAS_EXPANDER ||
  484. /* these elements are optional */
  485. type_ptr[0] == ENCLOSURE_COMPONENT_SCSI_TARGET_PORT ||
  486. type_ptr[0] == ENCLOSURE_COMPONENT_SCSI_INITIATOR_PORT ||
  487. type_ptr[0] == ENCLOSURE_COMPONENT_CONTROLLER_ELECTRONICS))
  488. addl_desc_ptr += addl_desc_ptr[1] + 2;
  489. }
  490. }
  491. kfree(buf);
  492. kfree(hdr_buf);
  493. }
  494. static void ses_match_to_enclosure(struct enclosure_device *edev,
  495. struct scsi_device *sdev)
  496. {
  497. unsigned char *desc;
  498. struct efd efd = {
  499. .addr = 0,
  500. };
  501. ses_enclosure_data_process(edev, to_scsi_device(edev->edev.parent), 0);
  502. if (!sdev->vpd_pg83_len)
  503. return;
  504. desc = sdev->vpd_pg83 + 4;
  505. while (desc < sdev->vpd_pg83 + sdev->vpd_pg83_len) {
  506. enum scsi_protocol proto = desc[0] >> 4;
  507. u8 code_set = desc[0] & 0x0f;
  508. u8 piv = desc[1] & 0x80;
  509. u8 assoc = (desc[1] & 0x30) >> 4;
  510. u8 type = desc[1] & 0x0f;
  511. u8 len = desc[3];
  512. if (piv && code_set == 1 && assoc == 1
  513. && proto == SCSI_PROTOCOL_SAS && type == 3 && len == 8)
  514. efd.addr = get_unaligned_be64(&desc[4]);
  515. desc += len + 4;
  516. }
  517. if (efd.addr) {
  518. efd.dev = &sdev->sdev_gendev;
  519. enclosure_for_each_device(ses_enclosure_find_by_addr, &efd);
  520. }
  521. }
  522. static int ses_intf_add(struct device *cdev,
  523. struct class_interface *intf)
  524. {
  525. struct scsi_device *sdev = to_scsi_device(cdev->parent);
  526. struct scsi_device *tmp_sdev;
  527. unsigned char *buf = NULL, *hdr_buf, *type_ptr;
  528. struct ses_device *ses_dev;
  529. u32 result;
  530. int i, types, len, components = 0;
  531. int err = -ENOMEM;
  532. int num_enclosures;
  533. struct enclosure_device *edev;
  534. struct ses_component *scomp = NULL;
  535. if (!scsi_device_enclosure(sdev)) {
  536. /* not an enclosure, but might be in one */
  537. struct enclosure_device *prev = NULL;
  538. while ((edev = enclosure_find(&sdev->host->shost_gendev, prev)) != NULL) {
  539. ses_match_to_enclosure(edev, sdev);
  540. prev = edev;
  541. }
  542. return -ENODEV;
  543. }
  544. /* TYPE_ENCLOSURE prints a message in probe */
  545. if (sdev->type != TYPE_ENCLOSURE)
  546. sdev_printk(KERN_NOTICE, sdev, "Embedded Enclosure Device\n");
  547. ses_dev = kzalloc(sizeof(*ses_dev), GFP_KERNEL);
  548. hdr_buf = kzalloc(INIT_ALLOC_SIZE, GFP_KERNEL);
  549. if (!hdr_buf || !ses_dev)
  550. goto err_init_free;
  551. result = ses_recv_diag(sdev, 1, hdr_buf, INIT_ALLOC_SIZE);
  552. if (result)
  553. goto recv_failed;
  554. len = (hdr_buf[2] << 8) + hdr_buf[3] + 4;
  555. buf = kzalloc(len, GFP_KERNEL);
  556. if (!buf)
  557. goto err_free;
  558. result = ses_recv_diag(sdev, 1, buf, len);
  559. if (result)
  560. goto recv_failed;
  561. types = 0;
  562. /* we always have one main enclosure and the rest are referred
  563. * to as secondary subenclosures */
  564. num_enclosures = buf[1] + 1;
  565. /* begin at the enclosure descriptor */
  566. type_ptr = buf + 8;
  567. /* skip all the enclosure descriptors */
  568. for (i = 0; i < num_enclosures && type_ptr < buf + len; i++) {
  569. types += type_ptr[2];
  570. type_ptr += type_ptr[3] + 4;
  571. }
  572. ses_dev->page1_types = type_ptr;
  573. ses_dev->page1_num_types = types;
  574. for (i = 0; i < types && type_ptr < buf + len; i++, type_ptr += 4) {
  575. if (type_ptr[0] == ENCLOSURE_COMPONENT_DEVICE ||
  576. type_ptr[0] == ENCLOSURE_COMPONENT_ARRAY_DEVICE)
  577. components += type_ptr[1];
  578. }
  579. ses_dev->page1 = buf;
  580. ses_dev->page1_len = len;
  581. buf = NULL;
  582. result = ses_recv_diag(sdev, 2, hdr_buf, INIT_ALLOC_SIZE);
  583. if (result)
  584. goto recv_failed;
  585. len = (hdr_buf[2] << 8) + hdr_buf[3] + 4;
  586. buf = kzalloc(len, GFP_KERNEL);
  587. if (!buf)
  588. goto err_free;
  589. /* make sure getting page 2 actually works */
  590. result = ses_recv_diag(sdev, 2, buf, len);
  591. if (result)
  592. goto recv_failed;
  593. ses_dev->page2 = buf;
  594. ses_dev->page2_len = len;
  595. buf = NULL;
  596. /* The additional information page --- allows us
  597. * to match up the devices */
  598. result = ses_recv_diag(sdev, 10, hdr_buf, INIT_ALLOC_SIZE);
  599. if (!result) {
  600. len = (hdr_buf[2] << 8) + hdr_buf[3] + 4;
  601. buf = kzalloc(len, GFP_KERNEL);
  602. if (!buf)
  603. goto err_free;
  604. result = ses_recv_diag(sdev, 10, buf, len);
  605. if (result)
  606. goto recv_failed;
  607. ses_dev->page10 = buf;
  608. ses_dev->page10_len = len;
  609. buf = NULL;
  610. }
  611. scomp = kzalloc(sizeof(struct ses_component) * components, GFP_KERNEL);
  612. if (!scomp)
  613. goto err_free;
  614. edev = enclosure_register(cdev->parent, dev_name(&sdev->sdev_gendev),
  615. components, &ses_enclosure_callbacks);
  616. if (IS_ERR(edev)) {
  617. err = PTR_ERR(edev);
  618. goto err_free;
  619. }
  620. kfree(hdr_buf);
  621. edev->scratch = ses_dev;
  622. for (i = 0; i < components; i++)
  623. edev->component[i].scratch = scomp + i;
  624. ses_enclosure_data_process(edev, sdev, 1);
  625. /* see if there are any devices matching before
  626. * we found the enclosure */
  627. shost_for_each_device(tmp_sdev, sdev->host) {
  628. if (tmp_sdev->lun != 0 || scsi_device_enclosure(tmp_sdev))
  629. continue;
  630. ses_match_to_enclosure(edev, tmp_sdev);
  631. }
  632. return 0;
  633. recv_failed:
  634. sdev_printk(KERN_ERR, sdev, "Failed to get diagnostic page 0x%x\n",
  635. result);
  636. err = -ENODEV;
  637. err_free:
  638. kfree(buf);
  639. kfree(scomp);
  640. kfree(ses_dev->page10);
  641. kfree(ses_dev->page2);
  642. kfree(ses_dev->page1);
  643. err_init_free:
  644. kfree(ses_dev);
  645. kfree(hdr_buf);
  646. sdev_printk(KERN_ERR, sdev, "Failed to bind enclosure %d\n", err);
  647. return err;
  648. }
  649. static int ses_remove(struct device *dev)
  650. {
  651. return 0;
  652. }
  653. static void ses_intf_remove_component(struct scsi_device *sdev)
  654. {
  655. struct enclosure_device *edev, *prev = NULL;
  656. while ((edev = enclosure_find(&sdev->host->shost_gendev, prev)) != NULL) {
  657. prev = edev;
  658. if (!enclosure_remove_device(edev, &sdev->sdev_gendev))
  659. break;
  660. }
  661. if (edev)
  662. put_device(&edev->edev);
  663. }
  664. static void ses_intf_remove_enclosure(struct scsi_device *sdev)
  665. {
  666. struct enclosure_device *edev;
  667. struct ses_device *ses_dev;
  668. /* exact match to this enclosure */
  669. edev = enclosure_find(&sdev->sdev_gendev, NULL);
  670. if (!edev)
  671. return;
  672. ses_dev = edev->scratch;
  673. edev->scratch = NULL;
  674. kfree(ses_dev->page10);
  675. kfree(ses_dev->page1);
  676. kfree(ses_dev->page2);
  677. kfree(ses_dev);
  678. kfree(edev->component[0].scratch);
  679. put_device(&edev->edev);
  680. enclosure_unregister(edev);
  681. }
  682. static void ses_intf_remove(struct device *cdev,
  683. struct class_interface *intf)
  684. {
  685. struct scsi_device *sdev = to_scsi_device(cdev->parent);
  686. if (!scsi_device_enclosure(sdev))
  687. ses_intf_remove_component(sdev);
  688. else
  689. ses_intf_remove_enclosure(sdev);
  690. }
  691. static struct class_interface ses_interface = {
  692. .add_dev = ses_intf_add,
  693. .remove_dev = ses_intf_remove,
  694. };
  695. static struct scsi_driver ses_template = {
  696. .gendrv = {
  697. .name = "ses",
  698. .owner = THIS_MODULE,
  699. .probe = ses_probe,
  700. .remove = ses_remove,
  701. },
  702. };
  703. static int __init ses_init(void)
  704. {
  705. int err;
  706. err = scsi_register_interface(&ses_interface);
  707. if (err)
  708. return err;
  709. err = scsi_register_driver(&ses_template.gendrv);
  710. if (err)
  711. goto out_unreg;
  712. return 0;
  713. out_unreg:
  714. scsi_unregister_interface(&ses_interface);
  715. return err;
  716. }
  717. static void __exit ses_exit(void)
  718. {
  719. scsi_unregister_driver(&ses_template.gendrv);
  720. scsi_unregister_interface(&ses_interface);
  721. }
  722. module_init(ses_init);
  723. module_exit(ses_exit);
  724. MODULE_ALIAS_SCSI_DEVICE(TYPE_ENCLOSURE);
  725. MODULE_AUTHOR("James Bottomley");
  726. MODULE_DESCRIPTION("SCSI Enclosure Services (ses) driver");
  727. MODULE_LICENSE("GPL v2");