linux/arch/powerpc/kernel/setup_64.c
<<
>>
Prefs
   1/*
   2 * 
   3 * Common boot and setup code.
   4 *
   5 * Copyright (C) 2001 PPC64 Team, IBM Corp
   6 *
   7 *      This program is free software; you can redistribute it and/or
   8 *      modify it under the terms of the GNU General Public License
   9 *      as published by the Free Software Foundation; either version
  10 *      2 of the License, or (at your option) any later version.
  11 */
  12
  13#undef DEBUG
  14
  15#include <linux/export.h>
  16#include <linux/string.h>
  17#include <linux/sched.h>
  18#include <linux/init.h>
  19#include <linux/kernel.h>
  20#include <linux/reboot.h>
  21#include <linux/delay.h>
  22#include <linux/initrd.h>
  23#include <linux/seq_file.h>
  24#include <linux/ioport.h>
  25#include <linux/console.h>
  26#include <linux/utsname.h>
  27#include <linux/tty.h>
  28#include <linux/root_dev.h>
  29#include <linux/notifier.h>
  30#include <linux/cpu.h>
  31#include <linux/unistd.h>
  32#include <linux/serial.h>
  33#include <linux/serial_8250.h>
  34#include <linux/bootmem.h>
  35#include <linux/pci.h>
  36#include <linux/lockdep.h>
  37#include <linux/memblock.h>
  38#include <linux/hugetlb.h>
  39
  40#include <asm/io.h>
  41#include <asm/kdump.h>
  42#include <asm/prom.h>
  43#include <asm/processor.h>
  44#include <asm/pgtable.h>
  45#include <asm/smp.h>
  46#include <asm/elf.h>
  47#include <asm/machdep.h>
  48#include <asm/paca.h>
  49#include <asm/time.h>
  50#include <asm/cputable.h>
  51#include <asm/sections.h>
  52#include <asm/btext.h>
  53#include <asm/nvram.h>
  54#include <asm/setup.h>
  55#include <asm/system.h>
  56#include <asm/rtas.h>
  57#include <asm/iommu.h>
  58#include <asm/serial.h>
  59#include <asm/cache.h>
  60#include <asm/page.h>
  61#include <asm/mmu.h>
  62#include <asm/firmware.h>
  63#include <asm/xmon.h>
  64#include <asm/udbg.h>
  65#include <asm/kexec.h>
  66#include <asm/mmu_context.h>
  67#include <asm/code-patching.h>
  68#include <asm/kvm_ppc.h>
  69#include <asm/hugetlb.h>
  70
  71#include "setup.h"
  72
  73#ifdef DEBUG
  74#define DBG(fmt...) udbg_printf(fmt)
  75#else
  76#define DBG(fmt...)
  77#endif
  78
  79int boot_cpuid = 0;
  80int __initdata spinning_secondaries;
  81u64 ppc64_pft_size;
  82
  83/* Pick defaults since we might want to patch instructions
  84 * before we've read this from the device tree.
  85 */
  86struct ppc64_caches ppc64_caches = {
  87        .dline_size = 0x40,
  88        .log_dline_size = 6,
  89        .iline_size = 0x40,
  90        .log_iline_size = 6
  91};
  92EXPORT_SYMBOL_GPL(ppc64_caches);
  93
  94/*
  95 * These are used in binfmt_elf.c to put aux entries on the stack
  96 * for each elf executable being started.
  97 */
  98int dcache_bsize;
  99int icache_bsize;
 100int ucache_bsize;
 101
 102#ifdef CONFIG_SMP
 103
 104static char *smt_enabled_cmdline;
 105
 106/* Look for ibm,smt-enabled OF option */
 107static void check_smt_enabled(void)
 108{
 109        struct device_node *dn;
 110        const char *smt_option;
 111
 112        /* Default to enabling all threads */
 113        smt_enabled_at_boot = threads_per_core;
 114
 115        /* Allow the command line to overrule the OF option */
 116        if (smt_enabled_cmdline) {
 117                if (!strcmp(smt_enabled_cmdline, "on"))
 118                        smt_enabled_at_boot = threads_per_core;
 119                else if (!strcmp(smt_enabled_cmdline, "off"))
 120                        smt_enabled_at_boot = 0;
 121                else {
 122                        long smt;
 123                        int rc;
 124
 125                        rc = strict_strtol(smt_enabled_cmdline, 10, &smt);
 126                        if (!rc)
 127                                smt_enabled_at_boot =
 128                                        min(threads_per_core, (int)smt);
 129                }
 130        } else {
 131                dn = of_find_node_by_path("/options");
 132                if (dn) {
 133                        smt_option = of_get_property(dn, "ibm,smt-enabled",
 134                                                     NULL);
 135
 136                        if (smt_option) {
 137                                if (!strcmp(smt_option, "on"))
 138                                        smt_enabled_at_boot = threads_per_core;
 139                                else if (!strcmp(smt_option, "off"))
 140                                        smt_enabled_at_boot = 0;
 141                        }
 142
 143                        of_node_put(dn);
 144                }
 145        }
 146}
 147
 148/* Look for smt-enabled= cmdline option */
 149static int __init early_smt_enabled(char *p)
 150{
 151        smt_enabled_cmdline = p;
 152        return 0;
 153}
 154early_param("smt-enabled", early_smt_enabled);
 155
 156#else
 157#define check_smt_enabled()
 158#endif /* CONFIG_SMP */
 159
 160/*
 161 * Early initialization entry point. This is called by head.S
 162 * with MMU translation disabled. We rely on the "feature" of
 163 * the CPU that ignores the top 2 bits of the address in real
 164 * mode so we can access kernel globals normally provided we
 165 * only toy with things in the RMO region. From here, we do
 166 * some early parsing of the device-tree to setup out MEMBLOCK
 167 * data structures, and allocate & initialize the hash table
 168 * and segment tables so we can start running with translation
 169 * enabled.
 170 *
 171 * It is this function which will call the probe() callback of
 172 * the various platform types and copy the matching one to the
 173 * global ppc_md structure. Your platform can eventually do
 174 * some very early initializations from the probe() routine, but
 175 * this is not recommended, be very careful as, for example, the
 176 * device-tree is not accessible via normal means at this point.
 177 */
 178
 179void __init early_setup(unsigned long dt_ptr)
 180{
 181        /* -------- printk is _NOT_ safe to use here ! ------- */
 182
 183        /* Identify CPU type */
 184        identify_cpu(0, mfspr(SPRN_PVR));
 185
 186        /* Assume we're on cpu 0 for now. Don't write to the paca yet! */
 187        initialise_paca(&boot_paca, 0);
 188        setup_paca(&boot_paca);
 189
 190        /* Initialize lockdep early or else spinlocks will blow */
 191        lockdep_init();
 192
 193        /* -------- printk is now safe to use ------- */
 194
 195        /* Enable early debugging if any specified (see udbg.h) */
 196        udbg_early_init();
 197
 198        DBG(" -> early_setup(), dt_ptr: 0x%lx\n", dt_ptr);
 199
 200        /*
 201         * Do early initialization using the flattened device
 202         * tree, such as retrieving the physical memory map or
 203         * calculating/retrieving the hash table size.
 204         */
 205        early_init_devtree(__va(dt_ptr));
 206
 207        /* Now we know the logical id of our boot cpu, setup the paca. */
 208        setup_paca(&paca[boot_cpuid]);
 209
 210        /* Fix up paca fields required for the boot cpu */
 211        get_paca()->cpu_start = 1;
 212
 213        /* Probe the machine type */
 214        probe_machine();
 215
 216        setup_kdump_trampoline();
 217
 218        DBG("Found, Initializing memory management...\n");
 219
 220        /* Initialize the hash table or TLB handling */
 221        early_init_mmu();
 222
 223        /*
 224         * Reserve any gigantic pages requested on the command line.
 225         * memblock needs to have been initialized by the time this is
 226         * called since this will reserve memory.
 227         */
 228        reserve_hugetlb_gpages();
 229
 230        DBG(" <- early_setup()\n");
 231}
 232
 233#ifdef CONFIG_SMP
 234void early_setup_secondary(void)
 235{
 236        /* Mark interrupts enabled in PACA */
 237        get_paca()->soft_enabled = 0;
 238
 239        /* Initialize the hash table or TLB handling */
 240        early_init_mmu_secondary();
 241}
 242
 243#endif /* CONFIG_SMP */
 244
 245#if defined(CONFIG_SMP) || defined(CONFIG_KEXEC)
 246void smp_release_cpus(void)
 247{
 248        unsigned long *ptr;
 249        int i;
 250
 251        DBG(" -> smp_release_cpus()\n");
 252
 253        /* All secondary cpus are spinning on a common spinloop, release them
 254         * all now so they can start to spin on their individual paca
 255         * spinloops. For non SMP kernels, the secondary cpus never get out
 256         * of the common spinloop.
 257         */
 258
 259        ptr  = (unsigned long *)((unsigned long)&__secondary_hold_spinloop
 260                        - PHYSICAL_START);
 261        *ptr = __pa(generic_secondary_smp_init);
 262
 263        /* And wait a bit for them to catch up */
 264        for (i = 0; i < 100000; i++) {
 265                mb();
 266                HMT_low();
 267                if (spinning_secondaries == 0)
 268                        break;
 269                udelay(1);
 270        }
 271        DBG("spinning_secondaries = %d\n", spinning_secondaries);
 272
 273        DBG(" <- smp_release_cpus()\n");
 274}
 275#endif /* CONFIG_SMP || CONFIG_KEXEC */
 276
 277/*
 278 * Initialize some remaining members of the ppc64_caches and systemcfg
 279 * structures
 280 * (at least until we get rid of them completely). This is mostly some
 281 * cache informations about the CPU that will be used by cache flush
 282 * routines and/or provided to userland
 283 */
 284static void __init initialize_cache_info(void)
 285{
 286        struct device_node *np;
 287        unsigned long num_cpus = 0;
 288
 289        DBG(" -> initialize_cache_info()\n");
 290
 291        for_each_node_by_type(np, "cpu") {
 292                num_cpus += 1;
 293
 294                /*
 295                 * We're assuming *all* of the CPUs have the same
 296                 * d-cache and i-cache sizes... -Peter
 297                 */
 298                if (num_cpus == 1) {
 299                        const u32 *sizep, *lsizep;
 300                        u32 size, lsize;
 301
 302                        size = 0;
 303                        lsize = cur_cpu_spec->dcache_bsize;
 304                        sizep = of_get_property(np, "d-cache-size", NULL);
 305                        if (sizep != NULL)
 306                                size = *sizep;
 307                        lsizep = of_get_property(np, "d-cache-block-size",
 308                                                 NULL);
 309                        /* fallback if block size missing */
 310                        if (lsizep == NULL)
 311                                lsizep = of_get_property(np,
 312                                                         "d-cache-line-size",
 313                                                         NULL);
 314                        if (lsizep != NULL)
 315                                lsize = *lsizep;
 316                        if (sizep == 0 || lsizep == 0)
 317                                DBG("Argh, can't find dcache properties ! "
 318                                    "sizep: %p, lsizep: %p\n", sizep, lsizep);
 319
 320                        ppc64_caches.dsize = size;
 321                        ppc64_caches.dline_size = lsize;
 322                        ppc64_caches.log_dline_size = __ilog2(lsize);
 323                        ppc64_caches.dlines_per_page = PAGE_SIZE / lsize;
 324
 325                        size = 0;
 326                        lsize = cur_cpu_spec->icache_bsize;
 327                        sizep = of_get_property(np, "i-cache-size", NULL);
 328                        if (sizep != NULL)
 329                                size = *sizep;
 330                        lsizep = of_get_property(np, "i-cache-block-size",
 331                                                 NULL);
 332                        if (lsizep == NULL)
 333                                lsizep = of_get_property(np,
 334                                                         "i-cache-line-size",
 335                                                         NULL);
 336                        if (lsizep != NULL)
 337                                lsize = *lsizep;
 338                        if (sizep == 0 || lsizep == 0)
 339                                DBG("Argh, can't find icache properties ! "
 340                                    "sizep: %p, lsizep: %p\n", sizep, lsizep);
 341
 342                        ppc64_caches.isize = size;
 343                        ppc64_caches.iline_size = lsize;
 344                        ppc64_caches.log_iline_size = __ilog2(lsize);
 345                        ppc64_caches.ilines_per_page = PAGE_SIZE / lsize;
 346                }
 347        }
 348
 349        DBG(" <- initialize_cache_info()\n");
 350}
 351
 352
 353/*
 354 * Do some initial setup of the system.  The parameters are those which 
 355 * were passed in from the bootloader.
 356 */
 357void __init setup_system(void)
 358{
 359        DBG(" -> setup_system()\n");
 360
 361        /* Apply the CPUs-specific and firmware specific fixups to kernel
 362         * text (nop out sections not relevant to this CPU or this firmware)
 363         */
 364        do_feature_fixups(cur_cpu_spec->cpu_features,
 365                          &__start___ftr_fixup, &__stop___ftr_fixup);
 366        do_feature_fixups(cur_cpu_spec->mmu_features,
 367                          &__start___mmu_ftr_fixup, &__stop___mmu_ftr_fixup);
 368        do_feature_fixups(powerpc_firmware_features,
 369                          &__start___fw_ftr_fixup, &__stop___fw_ftr_fixup);
 370        do_lwsync_fixups(cur_cpu_spec->cpu_features,
 371                         &__start___lwsync_fixup, &__stop___lwsync_fixup);
 372        do_final_fixups();
 373
 374        /*
 375         * Unflatten the device-tree passed by prom_init or kexec
 376         */
 377        unflatten_device_tree();
 378
 379        /*
 380         * Fill the ppc64_caches & systemcfg structures with informations
 381         * retrieved from the device-tree.
 382         */
 383        initialize_cache_info();
 384
 385#ifdef CONFIG_PPC_RTAS
 386        /*
 387         * Initialize RTAS if available
 388         */
 389        rtas_initialize();
 390#endif /* CONFIG_PPC_RTAS */
 391
 392        /*
 393         * Check if we have an initrd provided via the device-tree
 394         */
 395        check_for_initrd();
 396
 397        /*
 398         * Do some platform specific early initializations, that includes
 399         * setting up the hash table pointers. It also sets up some interrupt-mapping
 400         * related options that will be used by finish_device_tree()
 401         */
 402        if (ppc_md.init_early)
 403                ppc_md.init_early();
 404
 405        /*
 406         * We can discover serial ports now since the above did setup the
 407         * hash table management for us, thus ioremap works. We do that early
 408         * so that further code can be debugged
 409         */
 410        find_legacy_serial_ports();
 411
 412        /*
 413         * Register early console
 414         */
 415        register_early_udbg_console();
 416
 417        /*
 418         * Initialize xmon
 419         */
 420        xmon_setup();
 421
 422        smp_setup_cpu_maps();
 423        check_smt_enabled();
 424
 425#ifdef CONFIG_SMP
 426        /* Release secondary cpus out of their spinloops at 0x60 now that
 427         * we can map physical -> logical CPU ids
 428         */
 429        smp_release_cpus();
 430#endif
 431
 432        printk("Starting Linux PPC64 %s\n", init_utsname()->version);
 433
 434        printk("-----------------------------------------------------\n");
 435        printk("ppc64_pft_size                = 0x%llx\n", ppc64_pft_size);
 436        printk("physicalMemorySize            = 0x%llx\n", memblock_phys_mem_size());
 437        if (ppc64_caches.dline_size != 0x80)
 438                printk("ppc64_caches.dcache_line_size = 0x%x\n",
 439                       ppc64_caches.dline_size);
 440        if (ppc64_caches.iline_size != 0x80)
 441                printk("ppc64_caches.icache_line_size = 0x%x\n",
 442                       ppc64_caches.iline_size);
 443#ifdef CONFIG_PPC_STD_MMU_64
 444        if (htab_address)
 445                printk("htab_address                  = 0x%p\n", htab_address);
 446        printk("htab_hash_mask                = 0x%lx\n", htab_hash_mask);
 447#endif /* CONFIG_PPC_STD_MMU_64 */
 448        if (PHYSICAL_START > 0)
 449                printk("physical_start                = 0x%llx\n",
 450                       (unsigned long long)PHYSICAL_START);
 451        printk("-----------------------------------------------------\n");
 452
 453        DBG(" <- setup_system()\n");
 454}
 455
 456/* This returns the limit below which memory accesses to the linear
 457 * mapping are guarnateed not to cause a TLB or SLB miss. This is
 458 * used to allocate interrupt or emergency stacks for which our
 459 * exception entry path doesn't deal with being interrupted.
 460 */
 461static u64 safe_stack_limit(void)
 462{
 463#ifdef CONFIG_PPC_BOOK3E
 464        /* Freescale BookE bolts the entire linear mapping */
 465        if (mmu_has_feature(MMU_FTR_TYPE_FSL_E))
 466                return linear_map_top;
 467        /* Other BookE, we assume the first GB is bolted */
 468        return 1ul << 30;
 469#else
 470        /* BookS, the first segment is bolted */
 471        if (mmu_has_feature(MMU_FTR_1T_SEGMENT))
 472                return 1UL << SID_SHIFT_1T;
 473        return 1UL << SID_SHIFT;
 474#endif
 475}
 476
 477static void __init irqstack_early_init(void)
 478{
 479        u64 limit = safe_stack_limit();
 480        unsigned int i;
 481
 482        /*
 483         * Interrupt stacks must be in the first segment since we
 484         * cannot afford to take SLB misses on them.
 485         */
 486        for_each_possible_cpu(i) {
 487                softirq_ctx[i] = (struct thread_info *)
 488                        __va(memblock_alloc_base(THREAD_SIZE,
 489                                            THREAD_SIZE, limit));
 490                hardirq_ctx[i] = (struct thread_info *)
 491                        __va(memblock_alloc_base(THREAD_SIZE,
 492                                            THREAD_SIZE, limit));
 493        }
 494}
 495
 496#ifdef CONFIG_PPC_BOOK3E
 497static void __init exc_lvl_early_init(void)
 498{
 499        extern unsigned int interrupt_base_book3e;
 500        extern unsigned int exc_debug_debug_book3e;
 501
 502        unsigned int i;
 503
 504        for_each_possible_cpu(i) {
 505                critirq_ctx[i] = (struct thread_info *)
 506                        __va(memblock_alloc(THREAD_SIZE, THREAD_SIZE));
 507                dbgirq_ctx[i] = (struct thread_info *)
 508                        __va(memblock_alloc(THREAD_SIZE, THREAD_SIZE));
 509                mcheckirq_ctx[i] = (struct thread_info *)
 510                        __va(memblock_alloc(THREAD_SIZE, THREAD_SIZE));
 511        }
 512
 513        if (cpu_has_feature(CPU_FTR_DEBUG_LVL_EXC))
 514                patch_branch(&interrupt_base_book3e + (0x040 / 4) + 1,
 515                             (unsigned long)&exc_debug_debug_book3e, 0);
 516}
 517#else
 518#define exc_lvl_early_init()
 519#endif
 520
 521/*
 522 * Stack space used when we detect a bad kernel stack pointer, and
 523 * early in SMP boots before relocation is enabled.
 524 */
 525static void __init emergency_stack_init(void)
 526{
 527        u64 limit;
 528        unsigned int i;
 529
 530        /*
 531         * Emergency stacks must be under 256MB, we cannot afford to take
 532         * SLB misses on them. The ABI also requires them to be 128-byte
 533         * aligned.
 534         *
 535         * Since we use these as temporary stacks during secondary CPU
 536         * bringup, we need to get at them in real mode. This means they
 537         * must also be within the RMO region.
 538         */
 539        limit = min(safe_stack_limit(), ppc64_rma_size);
 540
 541        for_each_possible_cpu(i) {
 542                unsigned long sp;
 543                sp  = memblock_alloc_base(THREAD_SIZE, THREAD_SIZE, limit);
 544                sp += THREAD_SIZE;
 545                paca[i].emergency_sp = __va(sp);
 546        }
 547}
 548
 549/*
 550 * Called into from start_kernel this initializes bootmem, which is used
 551 * to manage page allocation until mem_init is called.
 552 */
 553void __init setup_arch(char **cmdline_p)
 554{
 555        ppc64_boot_msg(0x12, "Setup Arch");
 556
 557        *cmdline_p = cmd_line;
 558
 559        /*
 560         * Set cache line size based on type of cpu as a default.
 561         * Systems with OF can look in the properties on the cpu node(s)
 562         * for a possibly more accurate value.
 563         */
 564        dcache_bsize = ppc64_caches.dline_size;
 565        icache_bsize = ppc64_caches.iline_size;
 566
 567        /* reboot on panic */
 568        panic_timeout = 180;
 569
 570        if (ppc_md.panic)
 571                setup_panic();
 572
 573        init_mm.start_code = (unsigned long)_stext;
 574        init_mm.end_code = (unsigned long) _etext;
 575        init_mm.end_data = (unsigned long) _edata;
 576        init_mm.brk = klimit;
 577        
 578        irqstack_early_init();
 579        exc_lvl_early_init();
 580        emergency_stack_init();
 581
 582#ifdef CONFIG_PPC_STD_MMU_64
 583        stabs_alloc();
 584#endif
 585        /* set up the bootmem stuff with available memory */
 586        do_init_bootmem();
 587        sparse_init();
 588
 589#ifdef CONFIG_DUMMY_CONSOLE
 590        conswitchp = &dummy_con;
 591#endif
 592
 593        if (ppc_md.setup_arch)
 594                ppc_md.setup_arch();
 595
 596        paging_init();
 597
 598        /* Initialize the MMU context management stuff */
 599        mmu_context_init();
 600
 601        kvm_rma_init();
 602
 603        ppc64_boot_msg(0x15, "Setup Done");
 604}
 605
 606
 607/* ToDo: do something useful if ppc_md is not yet setup. */
 608#define PPC64_LINUX_FUNCTION 0x0f000000
 609#define PPC64_IPL_MESSAGE 0xc0000000
 610#define PPC64_TERM_MESSAGE 0xb0000000
 611
 612static void ppc64_do_msg(unsigned int src, const char *msg)
 613{
 614        if (ppc_md.progress) {
 615                char buf[128];
 616
 617                sprintf(buf, "%08X\n", src);
 618                ppc_md.progress(buf, 0);
 619                snprintf(buf, 128, "%s", msg);
 620                ppc_md.progress(buf, 0);
 621        }
 622}
 623
 624/* Print a boot progress message. */
 625void ppc64_boot_msg(unsigned int src, const char *msg)
 626{
 627        ppc64_do_msg(PPC64_LINUX_FUNCTION|PPC64_IPL_MESSAGE|src, msg);
 628        printk("[boot]%04x %s\n", src, msg);
 629}
 630
 631#ifdef CONFIG_SMP
 632#define PCPU_DYN_SIZE           ()
 633
 634static void * __init pcpu_fc_alloc(unsigned int cpu, size_t size, size_t align)
 635{
 636        return __alloc_bootmem_node(NODE_DATA(cpu_to_node(cpu)), size, align,
 637                                    __pa(MAX_DMA_ADDRESS));
 638}
 639
 640static void __init pcpu_fc_free(void *ptr, size_t size)
 641{
 642        free_bootmem(__pa(ptr), size);
 643}
 644
 645static int pcpu_cpu_distance(unsigned int from, unsigned int to)
 646{
 647        if (cpu_to_node(from) == cpu_to_node(to))
 648                return LOCAL_DISTANCE;
 649        else
 650                return REMOTE_DISTANCE;
 651}
 652
 653unsigned long __per_cpu_offset[NR_CPUS] __read_mostly;
 654EXPORT_SYMBOL(__per_cpu_offset);
 655
 656void __init setup_per_cpu_areas(void)
 657{
 658        const size_t dyn_size = PERCPU_MODULE_RESERVE + PERCPU_DYNAMIC_RESERVE;
 659        size_t atom_size;
 660        unsigned long delta;
 661        unsigned int cpu;
 662        int rc;
 663
 664        /*
 665         * Linear mapping is one of 4K, 1M and 16M.  For 4K, no need
 666         * to group units.  For larger mappings, use 1M atom which
 667         * should be large enough to contain a number of units.
 668         */
 669        if (mmu_linear_psize == MMU_PAGE_4K)
 670                atom_size = PAGE_SIZE;
 671        else
 672                atom_size = 1 << 20;
 673
 674        rc = pcpu_embed_first_chunk(0, dyn_size, atom_size, pcpu_cpu_distance,
 675                                    pcpu_fc_alloc, pcpu_fc_free);
 676        if (rc < 0)
 677                panic("cannot initialize percpu area (err=%d)", rc);
 678
 679        delta = (unsigned long)pcpu_base_addr - (unsigned long)__per_cpu_start;
 680        for_each_possible_cpu(cpu) {
 681                __per_cpu_offset[cpu] = delta + pcpu_unit_offsets[cpu];
 682                paca[cpu].data_offset = __per_cpu_offset[cpu];
 683        }
 684}
 685#endif
 686
 687
 688#ifdef CONFIG_PPC_INDIRECT_IO
 689struct ppc_pci_io ppc_pci_io;
 690EXPORT_SYMBOL(ppc_pci_io);
 691#endif /* CONFIG_PPC_INDIRECT_IO */
 692
 693
lxr.linux.no kindly hosted by Redpill Linpro AS, provider of Linux consulting and operations services since 1995.