linux-old/drivers/ieee1394/nodemgr.c
<<
>>
Prefs
   1/*
   2 * Node information (ConfigROM) collection and management.
   3 *
   4 * Copyright (C) 2000           Andreas E. Bombe
   5 *               2001-2003      Ben Collins <bcollins@debian.net>
   6 *
   7 * This code is licensed under the GPL.  See the file COPYING in the root
   8 * directory of the kernel sources for details.
   9 */
  10
  11#include <linux/kernel.h>
  12#include <linux/config.h>
  13#include <linux/list.h>
  14#include <linux/slab.h>
  15#include <linux/smp_lock.h>
  16#include <linux/interrupt.h>
  17#include <linux/kmod.h>
  18#include <linux/completion.h>
  19#include <linux/delay.h>
  20#ifdef CONFIG_PROC_FS
  21#include <linux/proc_fs.h>
  22#endif
  23
  24#include "ieee1394_types.h"
  25#include "ieee1394.h"
  26#include "nodemgr.h"
  27#include "hosts.h"
  28#include "ieee1394_transactions.h"
  29#include "highlevel.h"
  30#include "csr.h"
  31#include "nodemgr.h"
  32
  33
  34
  35static char *nodemgr_find_oui_name(int oui)
  36{
  37#ifdef CONFIG_IEEE1394_OUI_DB
  38        extern struct oui_list_struct {
  39                int oui;
  40                char *name;
  41        } oui_list[];
  42        int i;
  43
  44        for (i = 0; oui_list[i].name; i++)
  45                if (oui_list[i].oui == oui)
  46                        return oui_list[i].name;
  47#endif
  48        return NULL;
  49}
  50
  51
  52/* 
  53 * Basically what we do here is start off retrieving the bus_info block.
  54 * From there will fill in some info about the node, verify it is of IEEE
  55 * 1394 type, and that the crc checks out ok. After that we start off with
  56 * the root directory, and subdirectories. To do this, we retrieve the
  57 * quadlet header for a directory, find out the length, and retrieve the
  58 * complete directory entry (be it a leaf or a directory). We then process
  59 * it and add the info to our structure for that particular node.
  60 *
  61 * We verify CRC's along the way for each directory/block/leaf. The entire
  62 * node structure is generic, and simply stores the information in a way
  63 * that's easy to parse by the protocol interface.
  64 */
  65
  66/* The nodemgr maintains a number of data structures: the node list,
  67 * the driver list, unit directory list and the host info list.  The
  68 * first three lists are accessed from process context only: /proc
  69 * readers, insmod and rmmod, and the nodemgr thread.  Access to these
  70 * lists are serialized by means of the nodemgr_serialize mutex, which
  71 * must be taken before accessing the structures and released
  72 * afterwards.  The host info list is only accessed during insmod,
  73 * rmmod and from interrupt and allways only for a short period of
  74 * time, so a spinlock is used to protect this list.
  75 */
  76
  77static DECLARE_MUTEX(nodemgr_serialize);
  78static LIST_HEAD(node_list);
  79static LIST_HEAD(driver_list);
  80static LIST_HEAD(unit_directory_list);
  81
  82
  83struct host_info {
  84        struct hpsb_host *host;
  85        struct completion exited;
  86        struct semaphore reset_sem;
  87        int pid;
  88        char daemon_name[15];
  89};
  90
  91static struct hpsb_highlevel nodemgr_highlevel;
  92
  93#ifdef CONFIG_PROC_FS
  94
  95#define PUTF(fmt, args...)                              \
  96do {                                                    \
  97        len += sprintf(page + len, fmt, ## args);       \
  98        pos = begin + len;                              \
  99        if (pos < off) {                                \
 100                len = 0;                                \
 101                begin = pos;                            \
 102        }                                               \
 103        if (pos > off + count)                          \
 104                goto done_proc;                         \
 105} while (0)
 106
 107
 108static int raw1394_read_proc(char *page, char **start, off_t off,
 109                             int count, int *eof, void *data)
 110{
 111        struct list_head *lh;
 112        struct node_entry *ne;
 113        off_t begin = 0, pos = 0;
 114        int len = 0;
 115
 116        if (down_interruptible(&nodemgr_serialize))
 117                return -EINTR;
 118
 119        list_for_each(lh, &node_list) {
 120                struct list_head *l;
 121                int ud_count = 0, lud_count = 0;
 122
 123                ne = list_entry(lh, struct node_entry, list);
 124                if (!ne)
 125                        continue;
 126
 127                PUTF("Node[" NODE_BUS_FMT "]  GUID[%016Lx]:\n",
 128                     NODE_BUS_ARGS(ne->host, ne->nodeid), (unsigned long long)ne->guid);
 129
 130                /* Generic Node information */
 131                PUTF("  Vendor ID: `%s' [0x%06x]\n",
 132                     ne->vendor_name ?: "Unknown", ne->vendor_id);
 133                PUTF("  Capabilities: 0x%06x\n", ne->capabilities);
 134                PUTF("  Bus Options:\n");
 135                PUTF("    IRMC(%d) CMC(%d) ISC(%d) BMC(%d) PMC(%d) GEN(%d)\n"
 136                     "    LSPD(%d) MAX_REC(%d) CYC_CLK_ACC(%d)\n",
 137                     ne->busopt.irmc, ne->busopt.cmc, ne->busopt.isc, ne->busopt.bmc,
 138                     ne->busopt.pmc, ne->busopt.generation, ne->busopt.lnkspd,
 139                     ne->busopt.max_rec, ne->busopt.cyc_clk_acc);
 140
 141                /* If this is the host entry, output some info about it aswell */
 142                if (ne->host != NULL && ne->host->node_id == ne->nodeid) {
 143                        PUTF("  Host Node Status:\n");
 144                        PUTF("    Host Driver     : %s\n", ne->host->driver->name);
 145                        PUTF("    Nodes connected : %d\n", ne->host->node_count);
 146                        PUTF("    Nodes active    : %d\n", ne->host->nodes_active);
 147                        PUTF("    SelfIDs received: %d\n", ne->host->selfid_count);
 148                        PUTF("    Irm ID          : [" NODE_BUS_FMT "]\n",
 149                             NODE_BUS_ARGS(ne->host, ne->host->irm_id));
 150                        PUTF("    BusMgr ID       : [" NODE_BUS_FMT "]\n",
 151                             NODE_BUS_ARGS(ne->host, ne->host->busmgr_id));
 152                        PUTF("    In Bus Reset    : %s\n", ne->host->in_bus_reset ? "yes" : "no");
 153                        PUTF("    Root            : %s\n", ne->host->is_root ? "yes" : "no");
 154                        PUTF("    Cycle Master    : %s\n", ne->host->is_cycmst ? "yes" : "no");
 155                        PUTF("    IRM             : %s\n", ne->host->is_irm ? "yes" : "no");
 156                        PUTF("    Bus Manager     : %s\n", ne->host->is_busmgr ? "yes" : "no");
 157                }
 158
 159                /* Now the unit directories */
 160                list_for_each (l, &ne->unit_directories) {
 161                        struct unit_directory *ud = list_entry (l, struct unit_directory, node_list);
 162                        int printed = 0; // small hack
 163
 164                        if (ud->parent == NULL)
 165                                PUTF("  Unit Directory %d:\n", lud_count++);
 166                        else
 167                                PUTF("  Logical Unit Directory %d:\n", ud_count++);
 168                        if (ud->flags & UNIT_DIRECTORY_VENDOR_ID) {
 169                                PUTF("    Vendor/Model ID: %s [%06x]",
 170                                     ud->vendor_name ?: "Unknown", ud->vendor_id);
 171                                printed = 1;
 172                        }
 173                        if (ud->flags & UNIT_DIRECTORY_MODEL_ID) {
 174                                if (!printed)
 175                                        PUTF("    Vendor/Model ID: %s [%06x]",
 176                                             ne->vendor_name ?: "Unknown", ne->vendor_id);
 177                                PUTF(" / %s [%06x]", ud->model_name ?: "Unknown", ud->model_id);
 178                                printed = 1;
 179                        }
 180                        if (printed)
 181                                PUTF("\n");
 182
 183                        if (ud->flags & UNIT_DIRECTORY_SPECIFIER_ID)
 184                                PUTF("    Software Specifier ID: %06x\n", ud->specifier_id);
 185                        if (ud->flags & UNIT_DIRECTORY_VERSION)
 186                                PUTF("    Software Version: %06x\n", ud->version);
 187                        if (ud->driver)
 188                                PUTF("    Driver: %s\n", ud->driver->name);
 189                        PUTF("    Length (in quads): %d\n", ud->length);
 190                }
 191
 192        }
 193
 194done_proc:
 195        up(&nodemgr_serialize);
 196
 197        *start = page + (off - begin);
 198        len -= (off - begin);
 199        if (len > count)
 200                len = count;
 201        else {
 202                *eof = 1;
 203                if (len <= 0)
 204                        return 0;
 205        }
 206
 207        return len;
 208}
 209
 210#undef PUTF
 211#endif /* CONFIG_PROC_FS */
 212
 213static void nodemgr_process_config_rom(struct node_entry *ne, 
 214                                       quadlet_t busoptions);
 215
 216static int nodemgr_read_quadlet(struct hpsb_host *host,
 217                                nodeid_t nodeid, unsigned int generation,
 218                                octlet_t address, quadlet_t *quad)
 219{
 220        int i;
 221        int ret = 0;
 222
 223        for (i = 0; i < 3; i++) {
 224                ret = hpsb_read(host, nodeid, generation, address, quad, 4);
 225                if (!ret)
 226                        break;
 227
 228                set_current_state(TASK_INTERRUPTIBLE);
 229                if (schedule_timeout (HZ/3))
 230                        return -1;
 231        }
 232        *quad = be32_to_cpu(*quad);
 233
 234        return ret;
 235}
 236
 237static int nodemgr_size_text_leaf(struct hpsb_host *host,
 238                                  nodeid_t nodeid, unsigned int generation,
 239                                  octlet_t address)
 240{
 241        quadlet_t quad;
 242        int size = 0;
 243
 244        if (nodemgr_read_quadlet(host, nodeid, generation, address, &quad))
 245                return -1;
 246
 247        if (CONFIG_ROM_KEY(quad) == CONFIG_ROM_DESCRIPTOR_LEAF) {
 248                /* This is the offset.  */
 249                address += 4 * CONFIG_ROM_VALUE(quad); 
 250                if (nodemgr_read_quadlet(host, nodeid, generation, address, &quad))
 251                        return -1;
 252                /* Now we got the size of the text descriptor leaf. */
 253                size = CONFIG_ROM_LEAF_LENGTH(quad);
 254        }
 255
 256        return size;
 257}
 258
 259static int nodemgr_read_text_leaf(struct node_entry *ne,
 260                                  octlet_t address,
 261                                  quadlet_t *quadp)
 262{
 263        quadlet_t quad;
 264        int i, size, ret;
 265
 266        if (nodemgr_read_quadlet(ne->host, ne->nodeid, ne->generation, address, &quad)
 267            || CONFIG_ROM_KEY(quad) != CONFIG_ROM_DESCRIPTOR_LEAF)
 268                return -1;
 269
 270        /* This is the offset.  */
 271        address += 4 * CONFIG_ROM_VALUE(quad);
 272        if (nodemgr_read_quadlet(ne->host, ne->nodeid, ne->generation, address, &quad))
 273                return -1;
 274
 275        /* Now we got the size of the text descriptor leaf. */
 276        size = CONFIG_ROM_LEAF_LENGTH(quad) - 2;
 277        if (size <= 0)
 278                return -1;
 279
 280        address += 4;
 281        for (i = 0; i < 2; i++, address += 4, quadp++) {
 282                if (nodemgr_read_quadlet(ne->host, ne->nodeid, ne->generation, address, quadp))
 283                        return -1;
 284        }
 285
 286        /* Now read the text string.  */
 287        ret = -ENXIO;
 288        for (; size > 0; size--, address += 4, quadp++) {
 289                for (i = 0; i < 3; i++) {
 290                        ret = hpsb_node_read(ne, address, quadp, 4);
 291                        if (ret != -EAGAIN)
 292                                break;
 293                }
 294                if (ret)
 295                        break;
 296        }
 297
 298        return ret;
 299}
 300
 301static struct node_entry *nodemgr_scan_root_directory
 302        (struct hpsb_host *host, nodeid_t nodeid, unsigned int generation)
 303{
 304        octlet_t address;
 305        quadlet_t quad;
 306        int length;
 307        int code, size, total_size;
 308        struct node_entry *ne;
 309
 310        address = CSR_REGISTER_BASE + CSR_CONFIG_ROM;
 311        
 312        if (nodemgr_read_quadlet(host, nodeid, generation, address, &quad))
 313                return NULL;
 314
 315        if (CONFIG_ROM_BUS_INFO_LENGTH(quad) == 1)  /* minimal config rom */
 316                return NULL;
 317
 318        address += 4 + CONFIG_ROM_BUS_INFO_LENGTH(quad) * 4;
 319
 320        if (nodemgr_read_quadlet(host, nodeid, generation, address, &quad))
 321                return NULL;
 322        length = CONFIG_ROM_ROOT_LENGTH(quad);
 323        address += 4;
 324
 325        size = 0;
 326        total_size = sizeof(struct node_entry);
 327        for (; length > 0; length--, address += 4) {
 328                if (nodemgr_read_quadlet(host, nodeid, generation, address, &quad))
 329                        return NULL;
 330                code = CONFIG_ROM_KEY(quad);
 331
 332                if (code == CONFIG_ROM_VENDOR_ID && length > 0) {
 333                        /* Check if there is a text descriptor leaf
 334                           immediately after this.  */
 335                        size = nodemgr_size_text_leaf(host, nodeid, generation,
 336                                                      address + 4);
 337                        if (size > 0) {
 338                                address += 4;
 339                                length--;
 340                                total_size += (size + 1) * sizeof (quadlet_t);
 341                        } else if (size < 0)
 342                                return NULL;
 343                }
 344        }
 345        ne = kmalloc(total_size, GFP_KERNEL);
 346
 347        if (!ne)
 348                return NULL;
 349
 350        memset(ne, 0, total_size);
 351
 352        if (size != 0) {
 353                ne->vendor_name = (const char *) &(ne->quadlets[2]);
 354                ne->quadlets[size] = 0;
 355        } else {
 356                ne->vendor_name = NULL;
 357        }
 358
 359        return ne; 
 360}
 361
 362static struct node_entry *nodemgr_create_node(octlet_t guid, quadlet_t busoptions,
 363                                              struct host_info *hi,
 364                                              nodeid_t nodeid, unsigned int generation)
 365{
 366        struct hpsb_host *host = hi->host;
 367        struct node_entry *ne;
 368
 369        ne = nodemgr_scan_root_directory (host, nodeid, generation);
 370        if (!ne) return NULL;
 371
 372        INIT_LIST_HEAD(&ne->list);
 373        INIT_LIST_HEAD(&ne->unit_directories);
 374        ne->host = host;
 375        ne->nodeid = nodeid;
 376        ne->generation = generation;
 377        ne->guid = guid;
 378        ne->guid_vendor_id = (guid >> 40) & 0xffffff;
 379        ne->guid_vendor_oui = nodemgr_find_oui_name(ne->guid_vendor_id);
 380
 381        list_add_tail(&ne->list, &node_list);
 382
 383        nodemgr_process_config_rom (ne, busoptions);
 384
 385        HPSB_DEBUG("%s added: ID:BUS[" NODE_BUS_FMT "]  GUID[%016Lx]",
 386                   (host->node_id == nodeid) ? "Host" : "Node",
 387                   NODE_BUS_ARGS(host, nodeid), (unsigned long long)guid);
 388
 389        return ne;
 390}
 391
 392static struct node_entry *find_entry_by_guid(u64 guid)
 393{
 394        struct list_head *lh;
 395        struct node_entry *ne;
 396        
 397        list_for_each(lh, &node_list) {
 398                ne = list_entry(lh, struct node_entry, list);
 399                if (ne->guid == guid) return ne;
 400        }
 401
 402        return NULL;
 403}
 404
 405static struct node_entry *find_entry_by_nodeid(struct hpsb_host *host, nodeid_t nodeid)
 406{
 407        struct list_head *lh;
 408        struct node_entry *ne;
 409
 410        list_for_each(lh, &node_list) {
 411                ne = list_entry(lh, struct node_entry, list);
 412                if (ne->nodeid == nodeid && ne->host == host)
 413                        return ne;
 414        }
 415
 416        return NULL;
 417}
 418
 419static struct unit_directory *nodemgr_scan_unit_directory
 420        (struct node_entry *ne, octlet_t address)
 421{
 422        struct unit_directory *ud;
 423        quadlet_t quad;
 424        u8 flags, todo;
 425        int length, size, total_size, count;
 426        int vendor_name_size, model_name_size;
 427
 428        if (nodemgr_read_quadlet(ne->host, ne->nodeid, ne->generation, address, &quad))
 429                return NULL;
 430        length = CONFIG_ROM_DIRECTORY_LENGTH(quad) ;
 431        address += 4;
 432
 433        size = 0;
 434        total_size = sizeof (struct unit_directory);
 435        flags = 0;
 436        count = 0;
 437        vendor_name_size = 0;
 438        model_name_size = 0;
 439        for (; length > 0; length--, address += 4) {
 440                int code;
 441                quadlet_t value;
 442
 443                if (nodemgr_read_quadlet(ne->host, ne->nodeid, ne->generation,
 444                                         address, &quad))
 445                        return NULL;
 446                code = CONFIG_ROM_KEY(quad);
 447                value = CONFIG_ROM_VALUE(quad);
 448
 449                todo = 0;
 450                switch (code) {
 451                case CONFIG_ROM_VENDOR_ID:
 452                        todo = UNIT_DIRECTORY_VENDOR_TEXT;
 453                        break;
 454
 455                case CONFIG_ROM_MODEL_ID:
 456                        todo = UNIT_DIRECTORY_MODEL_TEXT;
 457                        break;
 458
 459                case CONFIG_ROM_SPECIFIER_ID:
 460                case CONFIG_ROM_UNIT_SW_VERSION:
 461                        break;
 462
 463                case CONFIG_ROM_DESCRIPTOR_LEAF:
 464                case CONFIG_ROM_DESCRIPTOR_DIRECTORY:
 465                        /* TODO: read strings... icons? */
 466                        break;
 467
 468                default:
 469                        /* Which types of quadlets do we want to
 470                           store?  Only count immediate values and
 471                           CSR offsets for now.  */
 472                        code &= CONFIG_ROM_KEY_TYPE_MASK;
 473                        if ((code & CONFIG_ROM_KEY_TYPE_LEAF) == 0)
 474                                count++;
 475                        break;
 476                }
 477
 478                if (todo && length > 0) {
 479                        /* Check if there is a text descriptor leaf
 480                           immediately after this.  */
 481                        size = nodemgr_size_text_leaf(ne->host,
 482                                                      ne->nodeid,
 483                                                      ne->generation,
 484                                                      address + 4);
 485
 486                        if (todo == UNIT_DIRECTORY_VENDOR_TEXT)
 487                                vendor_name_size = size;
 488                        else
 489                                model_name_size = size;
 490
 491                        if (size > 0) {
 492                                address += 4;
 493                                length--;
 494                                flags |= todo;
 495                                total_size += (size + 1) * sizeof (quadlet_t);
 496                        }
 497                        else if (size < 0)
 498                                return NULL;
 499                }
 500        }
 501
 502        total_size += count * sizeof (quadlet_t);
 503        ud = kmalloc (total_size, GFP_KERNEL);
 504
 505        if (ud != NULL) {
 506                memset (ud, 0, total_size);
 507                ud->flags = flags;
 508                ud->length = count;
 509                ud->vendor_name_size = vendor_name_size;
 510                ud->model_name_size = model_name_size;
 511        }
 512
 513        return ud;
 514}
 515
 516
 517/* This implementation currently only scans the config rom and its
 518 * immediate unit directories looking for software_id and
 519 * software_version entries, in order to get driver autoloading working. */
 520static struct unit_directory * nodemgr_process_unit_directory
 521        (struct node_entry *ne, octlet_t address, struct unit_directory *parent)
 522{
 523        struct unit_directory *ud;
 524        quadlet_t quad;
 525        quadlet_t *infop;
 526        int length;
 527        struct unit_directory *ud_temp = NULL;
 528
 529        if (!(ud = nodemgr_scan_unit_directory(ne, address)))
 530                goto unit_directory_error;
 531
 532        ud->ne = ne;
 533        ud->address = address;
 534
 535        if (parent) {
 536                ud->flags |= UNIT_DIRECTORY_LUN_DIRECTORY;
 537                ud->parent = parent;
 538        }
 539
 540        if (nodemgr_read_quadlet(ne->host, ne->nodeid, ne->generation,
 541                                 address, &quad))
 542                goto unit_directory_error;
 543        length = CONFIG_ROM_DIRECTORY_LENGTH(quad) ;
 544        address += 4;
 545
 546        infop = (quadlet_t *) ud->quadlets;
 547        for (; length > 0; length--, address += 4) {
 548                int code;
 549                quadlet_t value;
 550                quadlet_t *quadp;
 551
 552                if (nodemgr_read_quadlet(ne->host, ne->nodeid, ne->generation,
 553                                         address, &quad))
 554                        goto unit_directory_error;
 555                code = CONFIG_ROM_KEY(quad) ;
 556                value = CONFIG_ROM_VALUE(quad);
 557
 558                switch (code) {
 559                case CONFIG_ROM_VENDOR_ID:
 560                        ud->vendor_id = value;
 561                        ud->flags |= UNIT_DIRECTORY_VENDOR_ID;
 562
 563                        if (ud->vendor_id)
 564                                ud->vendor_oui = nodemgr_find_oui_name(ud->vendor_id);
 565
 566                        if ((ud->flags & UNIT_DIRECTORY_VENDOR_TEXT) != 0) {
 567                                length--;
 568                                address += 4;
 569                                quadp = &(ud->quadlets[ud->length]);
 570                                if (nodemgr_read_text_leaf(ne, address, quadp) == 0
 571                                    && quadp[0] == 0 && quadp[1] == 0) {
 572                                        /* We only support minimal
 573                                           ASCII and English. */
 574                                        quadp[ud->vendor_name_size] = 0;
 575                                        ud->vendor_name
 576                                                = (const char *) &(quadp[2]);
 577                                }
 578                        }
 579                        break;
 580
 581                case CONFIG_ROM_MODEL_ID:
 582                        ud->model_id = value;
 583                        ud->flags |= UNIT_DIRECTORY_MODEL_ID;
 584                        if ((ud->flags & UNIT_DIRECTORY_MODEL_TEXT) != 0) {
 585                                length--;
 586                                address += 4;
 587                                quadp = &(ud->quadlets[ud->length + ud->vendor_name_size + 1]);
 588                                if (nodemgr_read_text_leaf(ne, address, quadp) == 0
 589                                    && quadp[0] == 0 && quadp[1] == 0) {
 590                                        /* We only support minimal
 591                                           ASCII and English. */
 592                                        quadp[ud->model_name_size] = 0;
 593                                        ud->model_name
 594                                                = (const char *) &(quadp[2]);
 595                                }
 596                        }
 597                        break;
 598
 599                case CONFIG_ROM_SPECIFIER_ID:
 600                        ud->specifier_id = value;
 601                        ud->flags |= UNIT_DIRECTORY_SPECIFIER_ID;
 602                        break;
 603
 604                case CONFIG_ROM_UNIT_SW_VERSION:
 605                        ud->version = value;
 606                        ud->flags |= UNIT_DIRECTORY_VERSION;
 607                        break;
 608
 609                case CONFIG_ROM_DESCRIPTOR_LEAF:
 610                case CONFIG_ROM_DESCRIPTOR_DIRECTORY:
 611                        /* TODO: read strings... icons? */
 612                        break;
 613
 614                case CONFIG_ROM_LOGICAL_UNIT_DIRECTORY:
 615                        ud->flags |= UNIT_DIRECTORY_HAS_LUN_DIRECTORY;
 616                        ud_temp = nodemgr_process_unit_directory(ne, address + value * 4, ud);
 617
 618                        if (ud_temp == NULL)
 619                                break;
 620
 621                        /* inherit unspecified values */
 622                        if ((ud->flags & UNIT_DIRECTORY_VENDOR_ID) &&
 623                                !(ud_temp->flags & UNIT_DIRECTORY_VENDOR_ID))
 624                        {
 625                                ud_temp->flags |=  UNIT_DIRECTORY_VENDOR_ID;
 626                                ud_temp->vendor_id = ud->vendor_id;
 627                        }
 628                        if ((ud->flags & UNIT_DIRECTORY_MODEL_ID) &&
 629                                !(ud_temp->flags & UNIT_DIRECTORY_MODEL_ID))
 630                        {
 631                                ud_temp->flags |=  UNIT_DIRECTORY_MODEL_ID;
 632                                ud_temp->model_id = ud->model_id;
 633                        }
 634                        if ((ud->flags & UNIT_DIRECTORY_SPECIFIER_ID) &&
 635                                !(ud_temp->flags & UNIT_DIRECTORY_SPECIFIER_ID))
 636                        {
 637                                ud_temp->flags |=  UNIT_DIRECTORY_SPECIFIER_ID;
 638                                ud_temp->specifier_id = ud->specifier_id;
 639                        }
 640                        if ((ud->flags & UNIT_DIRECTORY_VERSION) &&
 641                                !(ud_temp->flags & UNIT_DIRECTORY_VERSION))
 642                        {
 643                                ud_temp->flags |=  UNIT_DIRECTORY_VERSION;
 644                                ud_temp->version = ud->version;
 645                        }
 646
 647                        break;
 648
 649                default:
 650                        /* Which types of quadlets do we want to
 651                           store?  Only count immediate values and
 652                           CSR offsets for now.  */
 653                        code &= CONFIG_ROM_KEY_TYPE_MASK;
 654                        if ((code & CONFIG_ROM_KEY_TYPE_LEAF) == 0)
 655                                *infop++ = quad;
 656                        break;
 657                }
 658        }
 659
 660        list_add_tail(&ud->node_list, &ne->unit_directories);
 661        list_add_tail(&ud->driver_list, &unit_directory_list);
 662
 663        return ud;
 664
 665unit_directory_error:   
 666        if (ud != NULL)
 667                kfree(ud);
 668        return NULL;
 669}
 670
 671
 672static void nodemgr_process_root_directory(struct node_entry *ne)
 673{
 674        octlet_t address;
 675        quadlet_t quad;
 676        int length;
 677
 678        address = CSR_REGISTER_BASE + CSR_CONFIG_ROM;
 679        
 680        if (nodemgr_read_quadlet(ne->host, ne->nodeid, ne->generation,
 681                                 address, &quad))
 682                return;
 683        address += 4 + CONFIG_ROM_BUS_INFO_LENGTH(quad) * 4;
 684
 685        if (nodemgr_read_quadlet(ne->host, ne->nodeid, ne->generation,
 686                                 address, &quad))
 687                return;
 688        length = CONFIG_ROM_ROOT_LENGTH(quad);
 689        address += 4;
 690
 691        for (; length > 0; length--, address += 4) {
 692                int code, value;
 693
 694                if (nodemgr_read_quadlet(ne->host, ne->nodeid, ne->generation,
 695                                         address, &quad))
 696                        return;
 697                code = CONFIG_ROM_KEY(quad);
 698                value = CONFIG_ROM_VALUE(quad);
 699
 700                switch (code) {
 701                case CONFIG_ROM_VENDOR_ID:
 702                        ne->vendor_id = value;
 703
 704                        if (ne->vendor_id)
 705                                ne->vendor_oui = nodemgr_find_oui_name(ne->vendor_id);
 706
 707                        /* Now check if there is a vendor name text
 708                           string.  */
 709                        if (ne->vendor_name != NULL) {
 710                                length--;
 711                                address += 4;
 712                                if (nodemgr_read_text_leaf(ne, address, ne->quadlets) != 0
 713                                    || ne->quadlets[0] != 0 || ne->quadlets[1] != 0)
 714                                        /* We only support minimal
 715                                           ASCII and English. */
 716                                        ne->vendor_name = NULL;
 717                        }
 718                        break;
 719
 720                case CONFIG_ROM_NODE_CAPABILITES:
 721                        ne->capabilities = value;
 722                        break;
 723
 724                case CONFIG_ROM_UNIT_DIRECTORY:
 725                        nodemgr_process_unit_directory(ne, address + value * 4, NULL);
 726                        break;                  
 727
 728                case CONFIG_ROM_DESCRIPTOR_LEAF:
 729                case CONFIG_ROM_DESCRIPTOR_DIRECTORY:
 730                        /* TODO: read strings... icons? */
 731                        break;
 732                }
 733        }
 734}
 735
 736#ifdef CONFIG_HOTPLUG
 737
 738static void nodemgr_call_policy(char *verb, struct unit_directory *ud)
 739{
 740        char *argv [3], **envp, *buf, *scratch;
 741        int i = 0, value;
 742
 743        if (!hotplug_path [0])
 744                return;
 745        if (!current->fs->root)
 746                return;
 747        if (!(envp = (char **) kmalloc(20 * sizeof (char *), GFP_KERNEL))) {
 748                HPSB_DEBUG ("ENOMEM");
 749                return;
 750        }
 751        if (!(buf = kmalloc(256, GFP_KERNEL))) {
 752                kfree(envp);
 753                HPSB_DEBUG("ENOMEM2");
 754                return;
 755        }
 756
 757        /* only one standardized param to hotplug command: type */
 758        argv[0] = hotplug_path;
 759        argv[1] = "ieee1394";
 760        argv[2] = 0;
 761
 762        /* minimal command environment */
 763        envp[i++] = "HOME=/";
 764        envp[i++] = "PATH=/sbin:/bin:/usr/sbin:/usr/bin";
 765
 766#ifdef CONFIG_IEEE1394_VERBOSEDEBUG
 767        /* hint that policy agent should enter no-stdout debug mode */
 768        envp[i++] = "DEBUG=kernel";
 769#endif
 770        /* extensible set of named bus-specific parameters,
 771         * supporting multiple driver selection algorithms.
 772         */
 773        scratch = buf;
 774
 775        envp[i++] = scratch;
 776        scratch += sprintf(scratch, "ACTION=%s", verb) + 1;
 777        envp[i++] = scratch;
 778        scratch += sprintf(scratch, "VENDOR_ID=%06x", ud->vendor_id) + 1;
 779        envp[i++] = scratch;
 780        scratch += sprintf(scratch, "GUID=%016Lx", (long long unsigned)ud->ne->guid) + 1;
 781        envp[i++] = scratch;
 782        scratch += sprintf(scratch, "SPECIFIER_ID=%06x", ud->specifier_id) + 1;
 783        envp[i++] = scratch;
 784        scratch += sprintf(scratch, "VERSION=%06x", ud->version) + 1;
 785        envp[i++] = 0;
 786
 787        /* NOTE: user mode daemons can call the agents too */
 788        HPSB_VERBOSE("NodeMgr: %s %s %016Lx", argv[0], verb, (long long unsigned)ud->ne->guid);
 789
 790        value = call_usermodehelper(argv[0], argv, envp);
 791        kfree(buf);
 792        kfree(envp);
 793        if (value != 0)
 794                HPSB_DEBUG("NodeMgr: hotplug policy returned %d", value);
 795}
 796
 797#else
 798
 799static inline void
 800nodemgr_call_policy(char *verb, struct unit_directory *ud)
 801{
 802        HPSB_VERBOSE("NodeMgr: nodemgr_call_policy(): hotplug not enabled");
 803        return;
 804} 
 805
 806#endif /* CONFIG_HOTPLUG */
 807
 808static void nodemgr_claim_unit_directory(struct unit_directory *ud,
 809                                         struct hpsb_protocol_driver *driver)
 810{
 811        ud->driver = driver;
 812        list_move_tail(&ud->driver_list, &driver->unit_directories);
 813}
 814
 815static void nodemgr_release_unit_directory(struct unit_directory *ud)
 816{
 817        ud->driver = NULL;
 818        list_move_tail(&ud->driver_list, &unit_directory_list);
 819}
 820
 821void hpsb_release_unit_directory(struct unit_directory *ud)
 822{
 823        down(&nodemgr_serialize);
 824        nodemgr_release_unit_directory(ud);
 825        up(&nodemgr_serialize);
 826}
 827
 828static void nodemgr_free_unit_directories(struct node_entry *ne)
 829{
 830        struct list_head *lh, *next;
 831        struct unit_directory *ud;
 832
 833        list_for_each_safe(lh, next, &ne->unit_directories) {
 834                ud = list_entry(lh, struct unit_directory, node_list);
 835
 836                if (ud->driver && ud->driver->disconnect)
 837                        ud->driver->disconnect(ud);
 838
 839                nodemgr_release_unit_directory(ud);
 840                nodemgr_call_policy("remove", ud);
 841
 842                list_del(&ud->driver_list);
 843                list_del(&ud->node_list);
 844
 845                kfree(ud);
 846        }
 847}
 848
 849static struct ieee1394_device_id *
 850nodemgr_match_driver(struct hpsb_protocol_driver *driver, 
 851                     struct unit_directory *ud)
 852{
 853        struct ieee1394_device_id *id;
 854
 855        for (id = driver->id_table; id->match_flags != 0; id++) {
 856                if ((id->match_flags & IEEE1394_MATCH_VENDOR_ID) &&
 857                    id->vendor_id != ud->vendor_id)
 858                        continue;
 859
 860                if ((id->match_flags & IEEE1394_MATCH_MODEL_ID) &&
 861                    id->model_id != ud->model_id)
 862                        continue;
 863
 864                if ((id->match_flags & IEEE1394_MATCH_SPECIFIER_ID) &&
 865                    id->specifier_id != ud->specifier_id)
 866                        continue;
 867
 868                /* software version does a bitwise comparison instead of equality */
 869                if ((id->match_flags & IEEE1394_MATCH_VERSION) &&
 870                    !(id->version & ud->version))
 871                        continue;
 872
 873                return id;
 874        }
 875
 876        return NULL;
 877}
 878
 879static struct hpsb_protocol_driver *
 880nodemgr_find_driver(struct unit_directory *ud)
 881{
 882        struct list_head *l;
 883        struct hpsb_protocol_driver *match, *driver;
 884        struct ieee1394_device_id *device_id;
 885
 886        match = NULL;
 887        list_for_each(l, &driver_list) {
 888                driver = list_entry(l, struct hpsb_protocol_driver, list);
 889                device_id = nodemgr_match_driver(driver, ud);
 890
 891                if (device_id != NULL) {
 892                        match = driver;
 893                        break;
 894                }
 895        }
 896
 897        return match;
 898}
 899
 900static void nodemgr_bind_drivers (struct node_entry *ne)
 901{
 902        struct list_head *lh;
 903        struct hpsb_protocol_driver *driver;
 904        struct unit_directory *ud;
 905
 906        list_for_each(lh, &ne->unit_directories) {
 907                ud = list_entry(lh, struct unit_directory, node_list);
 908                driver = nodemgr_find_driver(ud);
 909                if (driver && (!driver->probe || driver->probe(ud) == 0))
 910                        nodemgr_claim_unit_directory(ud, driver);
 911                nodemgr_call_policy("add", ud);
 912        }
 913}
 914
 915
 916int hpsb_register_protocol(struct hpsb_protocol_driver *driver)
 917{
 918        struct unit_directory *ud;
 919        struct list_head *lh, *next;
 920
 921        if (down_interruptible(&nodemgr_serialize))
 922                return -EINTR;
 923
 924        list_add_tail(&driver->list, &driver_list);
 925
 926        INIT_LIST_HEAD(&driver->unit_directories);
 927
 928        list_for_each_safe (lh, next, &unit_directory_list) {
 929                ud = list_entry(lh, struct unit_directory, driver_list);
 930
 931                if (nodemgr_match_driver(driver, ud) &&
 932                    (!driver->probe || driver->probe(ud) == 0))
 933                        nodemgr_claim_unit_directory(ud, driver);
 934        }
 935
 936        up(&nodemgr_serialize);
 937
 938        /*
 939         * Right now registration always succeeds, but maybe we should
 940         * detect clashes in protocols handled by other drivers.
 941     * DRD> No because multiple drivers are needed to handle certain devices.
 942     * For example, a DV camera is an IEC 61883 device (dv1394) and AV/C (raw1394).
 943     * This will become less an issue with libiec61883 using raw1394.
 944     *
 945     * BenC: But can we handle this with an ALLOW_SHARED flag for a
 946     * protocol? When we get an SBP-3 driver, it will be nice if they were
 947     * mutually exclusive, since SBP-3 can handle SBP-2 protocol.
 948     *
 949     * Not to mention that we currently do not seem to support multiple
 950     * drivers claiming the same unitdirectory. If we implement both of
 951     * those, then we'll need to keep probing when a driver claims a
 952     * unitdirectory, but is sharable.
 953         */
 954
 955        return 0;
 956}
 957
 958void hpsb_unregister_protocol(struct hpsb_protocol_driver *driver)
 959{
 960        struct list_head *lh, *next;
 961        struct unit_directory *ud;
 962
 963        down(&nodemgr_serialize);
 964
 965        list_del(&driver->list);
 966
 967        list_for_each_safe (lh, next, &driver->unit_directories) {
 968                ud = list_entry(lh, struct unit_directory, driver_list);
 969
 970                if (ud->driver && ud->driver->disconnect)
 971                        ud->driver->disconnect(ud);
 972
 973                nodemgr_release_unit_directory(ud);
 974        }
 975
 976        up(&nodemgr_serialize);
 977}
 978
 979static void nodemgr_process_config_rom(struct node_entry *ne, 
 980                                       quadlet_t busoptions)
 981{
 982        ne->busopt.irmc         = (busoptions >> 31) & 1;
 983        ne->busopt.cmc          = (busoptions >> 30) & 1;
 984        ne->busopt.isc          = (busoptions >> 29) & 1;
 985        ne->busopt.bmc          = (busoptions >> 28) & 1;
 986        ne->busopt.pmc          = (busoptions >> 27) & 1;
 987        ne->busopt.cyc_clk_acc  = (busoptions >> 16) & 0xff;
 988        ne->busopt.max_rec      = 1 << (((busoptions >> 12) & 0xf) + 1);
 989        ne->busopt.generation   = (busoptions >> 4) & 0xf;
 990        ne->busopt.lnkspd       = busoptions & 0x7;
 991
 992        HPSB_VERBOSE("NodeMgr: raw=0x%08x irmc=%d cmc=%d isc=%d bmc=%d pmc=%d "
 993                     "cyc_clk_acc=%d max_rec=%d gen=%d lspd=%d",
 994                     busoptions, ne->busopt.irmc, ne->busopt.cmc,
 995                     ne->busopt.isc, ne->busopt.bmc, ne->busopt.pmc,
 996                     ne->busopt.cyc_clk_acc, ne->busopt.max_rec,
 997                     ne->busopt.generation, ne->busopt.lnkspd);
 998
 999        /*
1000         * When the config rom changes we disconnect all drivers and
1001         * free the cached unit directories and reread the whole
1002         * thing.  If this was a new device, the call to
1003         * nodemgr_disconnect_drivers is a no-op and all is well.
1004         */
1005        nodemgr_free_unit_directories(ne);
1006        nodemgr_process_root_directory(ne);
1007        nodemgr_bind_drivers(ne);
1008}
1009
1010/*
1011 * This function updates nodes that were present on the bus before the
1012 * reset and still are after the reset.  The nodeid and the config rom
1013 * may have changed, and the drivers managing this device must be
1014 * informed that this device just went through a bus reset, to allow
1015 * the to take whatever actions required.
1016 */
1017static void nodemgr_update_node(struct node_entry *ne, quadlet_t busoptions,
1018                                struct host_info *hi, nodeid_t nodeid,
1019                                unsigned int generation)
1020{
1021        struct list_head *lh;
1022        struct unit_directory *ud;
1023
1024        if (ne->nodeid != nodeid) {
1025                HPSB_DEBUG("Node changed: " NODE_BUS_FMT " -> " NODE_BUS_FMT,
1026                           NODE_BUS_ARGS(ne->host, ne->nodeid),
1027                           NODE_BUS_ARGS(ne->host, nodeid));
1028                ne->nodeid = nodeid;
1029        }
1030
1031        ne->generation = generation;
1032
1033        if (ne->busopt.generation != ((busoptions >> 4) & 0xf))
1034                nodemgr_process_config_rom (ne, busoptions);
1035
1036        list_for_each (lh, &ne->unit_directories) {
1037                ud = list_entry (lh, struct unit_directory, node_list);
1038                if (ud->driver && ud->driver->update != NULL)
1039                        ud->driver->update(ud);
1040        }
1041}
1042
1043static int read_businfo_block(struct hpsb_host *host, nodeid_t nodeid, unsigned int generation,
1044                              quadlet_t *buffer, int buffer_length)
1045{
1046        octlet_t addr = CSR_REGISTER_BASE + CSR_CONFIG_ROM;
1047        unsigned header_size;
1048        int i;
1049
1050        /* IEEE P1212 says that devices should support 64byte block
1051         * reads, aligned on 64byte boundaries. That doesn't seem to
1052         * work though, and we are forced to doing quadlet sized
1053         * reads.  */
1054
1055        HPSB_VERBOSE("Initiating ConfigROM request for node " NODE_BUS_FMT,
1056                     NODE_BUS_ARGS(host, nodeid));
1057
1058        /* 
1059         * Must retry a few times if config rom read returns zero (how long?). Will
1060         * not normally occur, but we should do the right thing. For example, with
1061         * some sbp2 devices, the bridge chipset cannot return valid config rom reads
1062         * immediately after power-on, since they need to detect the type of 
1063         * device attached (disk or CD-ROM).
1064         */
1065        for (i = 0; i < 4; i++) {
1066                if (nodemgr_read_quadlet(host, nodeid, generation,
1067                                         addr, &buffer[0]) < 0) {
1068                        HPSB_ERR("ConfigROM quadlet transaction error for node "
1069                                 NODE_BUS_FMT, NODE_BUS_ARGS(host, nodeid));
1070                        return -1;
1071                }
1072                if (buffer[0])
1073                        break;
1074
1075                set_current_state(TASK_INTERRUPTIBLE);
1076                if (schedule_timeout (HZ/4))
1077                        return -1;
1078        }
1079
1080        header_size = buffer[0] >> 24;
1081        addr += 4;
1082
1083        if (header_size == 1) {
1084                HPSB_INFO("Node " NODE_BUS_FMT " has a minimal ROM.  "
1085                          "Vendor is %08x",
1086                          NODE_BUS_ARGS(host, nodeid), buffer[0] & 0x00ffffff);
1087                return -1;
1088        }
1089
1090        if (header_size < 4) {
1091                HPSB_INFO("Node " NODE_BUS_FMT " has non-standard ROM "
1092                          "format (%d quads), cannot parse",
1093                          NODE_BUS_ARGS(host, nodeid), header_size);
1094                return -1;
1095        }
1096
1097        for (i = 1; i < buffer_length; i++, addr += 4) {
1098                if (nodemgr_read_quadlet(host, nodeid, generation,
1099                                         addr, &buffer[i]) < 0) {
1100                        HPSB_ERR("ConfigROM quadlet transaction "
1101                                 "error for node " NODE_BUS_FMT,
1102                                 NODE_BUS_ARGS(host, nodeid));
1103                        return -1;
1104                }
1105        }
1106
1107        return 0;
1108}               
1109
1110static void nodemgr_remove_node(struct node_entry *ne)
1111{
1112        HPSB_DEBUG("Node removed: ID:BUS[" NODE_BUS_FMT "]  GUID[%016Lx]",
1113                   NODE_BUS_ARGS(ne->host, ne->nodeid), (unsigned long long)ne->guid);
1114
1115        nodemgr_free_unit_directories(ne);
1116        list_del(&ne->list);
1117        kfree(ne);
1118
1119        return;
1120}
1121
1122/* This is where we probe the nodes for their information and provided
1123 * features.  */
1124static void nodemgr_node_probe_one(struct host_info *hi,
1125                                   nodeid_t nodeid, int generation)
1126{
1127        struct hpsb_host *host = hi->host;
1128        struct node_entry *ne;
1129        quadlet_t buffer[5];
1130        octlet_t guid;
1131
1132        /* We need to detect when the ConfigROM's generation has changed,
1133         * so we only update the node's info when it needs to be.  */
1134
1135        if (read_businfo_block (host, nodeid, generation,
1136                                buffer, sizeof(buffer) >> 2))
1137                return;
1138
1139        if (buffer[1] != IEEE1394_BUSID_MAGIC) {
1140                /* This isn't a 1394 device, but we let it slide. There
1141                 * was a report of a device with broken firmware which
1142                 * reported '2394' instead of '1394', which is obviously a
1143                 * mistake. One would hope that a non-1394 device never
1144                 * gets connected to Firewire bus. If someone does, we
1145                 * shouldn't be held responsible, so we'll allow it with a
1146                 * warning.  */
1147                HPSB_WARN("Node " NODE_BUS_FMT " has invalid busID magic [0x%08x]",
1148                         NODE_BUS_ARGS(host, nodeid), buffer[1]);
1149        }
1150
1151        guid = ((u64)buffer[3] << 32) | buffer[4];
1152        ne = find_entry_by_guid(guid);
1153
1154        if (!ne)
1155                nodemgr_create_node(guid, buffer[2], hi, nodeid, generation);
1156        else
1157                nodemgr_update_node(ne, buffer[2], hi, nodeid, generation);
1158
1159        return;
1160}
1161
1162static void nodemgr_node_probe_cleanup(struct hpsb_host *host, unsigned int generation)
1163{
1164        struct list_head *lh, *next;
1165        struct node_entry *ne;
1166
1167        /* Now check to see if we have any nodes that aren't referenced
1168         * any longer.  */
1169        list_for_each_safe(lh, next, &node_list) {
1170                ne = list_entry(lh, struct node_entry, list);
1171
1172                /* Only checking this host */
1173                if (ne->host != host)
1174                        continue;
1175
1176                /* If the generation didn't get updated, then either the
1177                 * node was removed, or it failed the above probe. Either
1178                 * way, we remove references to it, since they are
1179                 * invalid.  */
1180                if (ne->generation != generation)
1181                        nodemgr_remove_node(ne);
1182        }
1183
1184        return;
1185}
1186
1187static void nodemgr_node_probe(struct host_info *hi, int generation)
1188{
1189        int count;
1190        struct hpsb_host *host = hi->host;
1191        struct selfid *sid = (struct selfid *)host->topology_map;
1192        nodeid_t nodeid = LOCAL_BUS;
1193
1194        /* Scan each node on the bus */
1195        for (count = host->selfid_count; count; count--, sid++) {
1196                if (sid->extended)
1197                        continue;
1198
1199                if (!sid->link_active) {
1200                        nodeid++;
1201                        continue;
1202                }
1203                nodemgr_node_probe_one(hi, nodeid++, generation);
1204        }
1205
1206        /* If we had a bus reset while we were scanning the bus, it is
1207         * possible that we did not probe all nodes.  In that case, we
1208         * skip the clean up for now, since we could remove nodes that
1209         * were still on the bus.  The bus reset increased hi->reset_sem,
1210         * so there's a bus scan pending which will do the clean up
1211         * eventually. */
1212        if (generation == get_hpsb_generation(host))
1213                nodemgr_node_probe_cleanup(host, generation);
1214
1215        return;
1216}
1217
1218/* Because we are a 1394a-2000 compliant IRM, we need to inform all the other
1219 * nodes of the broadcast channel.  (Really we're only setting the validity
1220 * bit). Other IRM responsibilities go in here as well. */
1221static void nodemgr_do_irm_duties(struct hpsb_host *host)
1222{
1223        quadlet_t bc;
1224        
1225        if (!host->is_irm)
1226                return;
1227
1228        host->csr.broadcast_channel |= 0x40000000;  /* set validity bit */
1229
1230        bc = cpu_to_be32(host->csr.broadcast_channel);
1231
1232        hpsb_write(host, LOCAL_BUS | ALL_NODES, get_hpsb_generation(host),
1233                   (CSR_REGISTER_BASE | CSR_BROADCAST_CHANNEL),
1234                   &bc, sizeof(quadlet_t));
1235
1236        /* If there is no bus manager then we should set the root node's
1237         * force_root bit to promote bus stability per the 1394
1238         * spec. (8.4.2.6) */
1239        if (host->busmgr_id == 0xffff && host->node_count > 1)
1240        {
1241                u16 root_node = host->node_count - 1;
1242                struct node_entry *ne = find_entry_by_nodeid(host, root_node | LOCAL_BUS);
1243
1244                if (ne && ne->busopt.cmc)
1245                        hpsb_send_phy_config(host, root_node, -1);
1246                else {
1247                        HPSB_DEBUG("The root node is not cycle master capable; "
1248                                   "selecting a new root node and resetting...");
1249                        hpsb_send_phy_config(host, NODEID_TO_NODE(host->node_id), -1);
1250                        hpsb_reset_bus(host, LONG_RESET_FORCE_ROOT);
1251                }
1252        }
1253}
1254
1255/* We need to ensure that if we are not the IRM, that the IRM node is capable of
1256 * everything we can do, otherwise issue a bus reset and try to become the IRM
1257 * ourselves. */
1258static int nodemgr_check_irm_capability(struct hpsb_host *host, int cycles)
1259{
1260        quadlet_t bc;
1261        int status;
1262
1263        if (host->is_irm)
1264                return 1;
1265
1266        status = hpsb_read(host, LOCAL_BUS | (host->irm_id),
1267                           get_hpsb_generation(host),
1268                           (CSR_REGISTER_BASE | CSR_BROADCAST_CHANNEL),
1269                           &bc, sizeof(quadlet_t));
1270
1271        if (status < 0 || !(be32_to_cpu(bc) & 0x80000000)) {
1272                /* The current irm node does not have a valid BROADCAST_CHANNEL
1273                 * register and we do, so reset the bus with force_root set */
1274                HPSB_DEBUG("Current remote IRM is not 1394a-2000 compliant, resetting...");
1275
1276                if (cycles >= 5) {
1277                        /* Oh screw it! Just leave the bus as it is */
1278                        HPSB_DEBUG("Stopping reset loop for IRM sanity");
1279                        return 1;
1280                }
1281
1282                hpsb_send_phy_config(host, NODEID_TO_NODE(host->node_id), -1);
1283                hpsb_reset_bus(host, LONG_RESET_FORCE_ROOT);
1284
1285                return 0;
1286        }
1287
1288        return 1;
1289}
1290
1291static int nodemgr_host_thread(void *__hi)
1292{
1293        struct host_info *hi = (struct host_info *)__hi;
1294        struct hpsb_host *host = hi->host;
1295        int reset_cycles = 0;
1296
1297        /* No userlevel access needed */
1298        daemonize();
1299
1300        strcpy(current->comm, hi->daemon_name);
1301        
1302        /* Sit and wait for a signal to probe the nodes on the bus. This
1303         * happens when we get a bus reset. */
1304        while (!down_interruptible(&hi->reset_sem) &&
1305               !down_interruptible(&nodemgr_serialize)) {
1306                unsigned int generation = 0;
1307                int i;
1308
1309                /* Pause for 1/4 second in 1/16 second intervals,
1310                 * to make sure things settle down. */
1311                for (i = 0; i < 4 ; i++) {
1312                        set_current_state(TASK_INTERRUPTIBLE);
1313                        if (schedule_timeout(HZ/16)) {
1314                                up(&nodemgr_serialize);
1315                                goto caught_signal;
1316                        }
1317
1318                        /* Now get the generation in which the node ID's we collect
1319                         * are valid.  During the bus scan we will use this generation
1320                         * for the read transactions, so that if another reset occurs
1321                         * during the scan the transactions will fail instead of
1322                         * returning bogus data. */
1323                        generation = get_hpsb_generation(host);
1324
1325                        /* If we get a reset before we are done waiting, then
1326                         * start the the waiting over again */
1327                        while (!down_trylock(&hi->reset_sem))
1328                                i = 0;
1329                }
1330
1331                if (!nodemgr_check_irm_capability(host, reset_cycles++)) {
1332                        /* Do nothing, we are resetting */
1333                        up(&nodemgr_serialize);
1334                        continue;
1335                }
1336
1337                reset_cycles = 0;
1338
1339                nodemgr_node_probe(hi, generation);
1340                nodemgr_do_irm_duties(host);
1341
1342                up(&nodemgr_serialize);
1343        }
1344
1345caught_signal:
1346        HPSB_VERBOSE("NodeMgr: Exiting thread");
1347
1348        complete_and_exit(&hi->exited, 0);
1349}
1350
1351struct node_entry *hpsb_guid_get_entry(u64 guid)
1352{
1353        struct node_entry *ne;
1354
1355        down(&nodemgr_serialize);
1356        ne = find_entry_by_guid(guid);
1357        up(&nodemgr_serialize);
1358
1359        return ne;
1360}
1361
1362struct node_entry *hpsb_nodeid_get_entry(struct hpsb_host *host, nodeid_t nodeid)
1363{
1364        struct node_entry *ne;
1365
1366        down(&nodemgr_serialize);
1367        ne = find_entry_by_nodeid(host, nodeid);
1368        up(&nodemgr_serialize);
1369
1370        return ne;
1371}
1372
1373/* The following four convenience functions use a struct node_entry
1374 * for addressing a node on the bus.  They are intended for use by any
1375 * process context, not just the nodemgr thread, so we need to be a
1376 * little careful when reading out the node ID and generation.  The
1377 * thing that can go wrong is that we get the node ID, then a bus
1378 * reset occurs, and then we read the generation.  The node ID is
1379 * possibly invalid, but the generation is current, and we end up
1380 * sending a packet to a the wrong node.
1381 *
1382 * The solution is to make sure we read the generation first, so that
1383 * if a reset occurs in the process, we end up with a stale generation
1384 * and the transactions will fail instead of silently using wrong node
1385 * ID's.
1386 */
1387
1388void hpsb_node_fill_packet(struct node_entry *ne, struct hpsb_packet *pkt)
1389{
1390        pkt->host = ne->host;
1391        pkt->generation = ne->generation;
1392        barrier();
1393        pkt->node_id = ne->nodeid;
1394}
1395
1396int hpsb_node_read(struct node_entry *ne, u64 addr,
1397                   quadlet_t *buffer, size_t length)
1398{
1399        unsigned int generation = ne->generation;
1400
1401        barrier();
1402        return hpsb_read(ne->host, ne->nodeid, generation,
1403                         addr, buffer, length);
1404}
1405
1406int hpsb_node_write(struct node_entry *ne, u64 addr, 
1407                    quadlet_t *buffer, size_t length)
1408{
1409        unsigned int generation = ne->generation;
1410
1411        barrier();
1412        return hpsb_write(ne->host, ne->nodeid, generation,
1413                          addr, buffer, length);
1414}
1415
1416int hpsb_node_lock(struct node_entry *ne, u64 addr, 
1417                   int extcode, quadlet_t *data, quadlet_t arg)
1418{
1419        unsigned int generation = ne->generation;
1420
1421        barrier();
1422        return hpsb_lock(ne->host, ne->nodeid, generation,
1423                         addr, extcode, data, arg);
1424}
1425
1426static void nodemgr_add_host(struct hpsb_host *host)
1427{
1428        struct host_info *hi;
1429
1430        hi = hpsb_create_hostinfo(&nodemgr_highlevel, host, sizeof(*hi));
1431
1432        if (!hi) {
1433                HPSB_ERR ("NodeMgr: out of memory in add host");
1434                return;
1435        }
1436
1437        hi->host = host;
1438        init_completion(&hi->exited);
1439        sema_init(&hi->reset_sem, 0);
1440
1441        sprintf(hi->daemon_name, "knodemgrd_%d", host->id);
1442
1443        hi->pid = kernel_thread(nodemgr_host_thread, hi,
1444                                CLONE_FS | CLONE_FILES | CLONE_SIGHAND);
1445
1446        if (hi->pid < 0) {
1447                HPSB_ERR ("NodeMgr: failed to start %s thread for %s",
1448                          hi->daemon_name, host->driver->name);
1449                hpsb_destroy_hostinfo(&nodemgr_highlevel, host);
1450                return;
1451        }
1452
1453        return;
1454}
1455
1456static void nodemgr_host_reset(struct hpsb_host *host)
1457{
1458        struct host_info *hi = hpsb_get_hostinfo(&nodemgr_highlevel, host);
1459
1460        if (hi != NULL) {
1461                HPSB_VERBOSE("NodeMgr: Processing host reset for %s", hi->daemon_name);
1462                up(&hi->reset_sem);
1463        } else
1464                HPSB_ERR ("NodeMgr: could not process reset of unused host");
1465
1466        return;
1467}
1468
1469static void nodemgr_remove_host(struct hpsb_host *host)
1470{
1471        struct list_head *lh, *next;
1472        struct node_entry *ne;
1473        struct host_info *hi = hpsb_get_hostinfo(&nodemgr_highlevel, host);
1474
1475        if (hi) {
1476                if (hi->pid >= 0) {
1477                        kill_proc(hi->pid, SIGTERM, 1);
1478                        wait_for_completion(&hi->exited);
1479                }
1480        } else
1481                HPSB_ERR("NodeMgr: host %s does not exist, cannot remove",
1482                         host->driver->name);
1483
1484        down(&nodemgr_serialize);
1485
1486        /* Even if we fail the host_info part, remove all the node
1487         * entries.  */
1488        list_for_each_safe(lh, next, &node_list) {
1489                ne = list_entry(lh, struct node_entry, list);
1490
1491                if (ne->host == host)
1492                        nodemgr_remove_node(ne);
1493        }
1494
1495        up(&nodemgr_serialize);
1496
1497        return;
1498}
1499
1500static struct hpsb_highlevel nodemgr_highlevel = {
1501        .name =         "Node manager",
1502        .add_host =     nodemgr_add_host,
1503        .host_reset =   nodemgr_host_reset,
1504        .remove_host =  nodemgr_remove_host,
1505};
1506
1507#define PROC_ENTRY "devices"
1508
1509void init_ieee1394_nodemgr(void)
1510{
1511#ifdef CONFIG_PROC_FS
1512        if (!create_proc_read_entry(PROC_ENTRY, 0444, ieee1394_procfs_entry, raw1394_read_proc, NULL))
1513                HPSB_ERR("Can't create devices procfs entry");
1514#endif
1515        hpsb_register_highlevel(&nodemgr_highlevel);
1516}
1517
1518void cleanup_ieee1394_nodemgr(void)
1519{
1520        hpsb_unregister_highlevel(&nodemgr_highlevel);
1521#ifdef CONFIG_PROC_FS
1522        remove_proc_entry(PROC_ENTRY, ieee1394_procfs_entry);
1523#endif
1524}
1525
lxr.linux.no kindly hosted by Redpill Linpro AS, provider of Linux consulting and operations services since 1995.