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