int cpu_get_info(struct udevice *dev, struct cpu_info *info) { struct cpu_ops *ops = cpu_get_ops(dev); if (!ops->get_desc) return -ENOSYS; return ops->get_info(dev, info); }
int cpu_get_desc(struct udevice *dev, char *buf, int size) { struct cpu_ops *ops = cpu_get_ops(dev); if (!ops->get_desc) return -ENOSYS; return ops->get_desc(dev, buf, size); }
int cpu_get_count(struct udevice *dev) { struct cpu_ops *ops = cpu_get_ops(dev); if (!ops->get_count) return -ENOSYS; return ops->get_count(dev); }
/* * Read a cpu's enable method and record it in cpu_ops. */ int __init cpu_read_ops(int cpu) { const char *enable_method = cpu_read_enable_method(cpu); if (!enable_method) return -ENODEV; cpu_ops[cpu] = cpu_get_ops(enable_method); if (!cpu_ops[cpu]) { pr_warn("Unsupported enable-method: %s\n", enable_method); return -EOPNOTSUPP; } return 0; }
/* * Read a cpu's enable method from the device tree and record it in cpu_ops. */ int __init cpu_read_ops(struct device_node *dn, int cpu) { const char *enable_method = of_get_property(dn, "enable-method", NULL); if (!enable_method) { /* * The boot CPU may not have an enable method (e.g. when * spin-table is used for secondaries). Don't warn spuriously. */ if (cpu != 0) pr_err("%s: missing enable-method property\n", dn->full_name); return -ENOENT; } cpu_ops[cpu] = cpu_get_ops(enable_method); if (!cpu_ops[cpu]) { pr_warn("%s: unsupported enable-method property: %s\n", dn->full_name, enable_method); return -EOPNOTSUPP; } return 0; }
/** * acpi_map_gic_cpu_interface - generates a logical cpu number * and map to MPIDR represented by GICC structure */ static void __init acpi_map_gic_cpu_interface(struct acpi_madt_generic_interrupt *processor) { int i; u64 mpidr = processor->arm_mpidr & MPIDR_HWID_BITMASK; bool enabled = !!(processor->flags & ACPI_MADT_ENABLED); if (mpidr == INVALID_HWID) { pr_info("Skip MADT cpu entry with invalid MPIDR\n"); return; } total_cpus++; if (!enabled) return; if (enabled_cpus >= NR_CPUS) { pr_warn("NR_CPUS limit of %d reached, Processor %d/0x%llx ignored.\n", NR_CPUS, total_cpus, mpidr); return; } /* Check if GICC structure of boot CPU is available in the MADT */ if (cpu_logical_map(0) == mpidr) { if (bootcpu_valid) { pr_err("Firmware bug, duplicate CPU MPIDR: 0x%llx in MADT\n", mpidr); return; } bootcpu_valid = true; } /* * Duplicate MPIDRs are a recipe for disaster. Scan * all initialized entries and check for * duplicates. If any is found just ignore the CPU. */ for (i = 1; i < enabled_cpus; i++) { if (cpu_logical_map(i) == mpidr) { pr_err("Firmware bug, duplicate CPU MPIDR: 0x%llx in MADT\n", mpidr); return; } } if (!acpi_psci_present()) return; cpu_ops[enabled_cpus] = cpu_get_ops("psci"); /* CPU 0 was already initialized */ if (enabled_cpus) { if (!cpu_ops[enabled_cpus]) return; if (cpu_ops[enabled_cpus]->cpu_init(NULL, enabled_cpus)) return; /* map the logical cpu id to cpu MPIDR */ cpu_logical_map(enabled_cpus) = mpidr; } enabled_cpus++; }