summaryrefslogtreecommitdiffstats
path: root/sys/ia64
diff options
context:
space:
mode:
authorjeff <jeff@FreeBSD.org>2009-06-23 22:42:39 +0000
committerjeff <jeff@FreeBSD.org>2009-06-23 22:42:39 +0000
commit5bc3a65e406b90cd9e2a47b79117e453bdb56413 (patch)
tree5644c551dea0298e335cc77383345323c6eb3662 /sys/ia64
parentd8bf8e1e8ad280542b4de90763d6d552c4f27b3a (diff)
downloadFreeBSD-src-5bc3a65e406b90cd9e2a47b79117e453bdb56413.zip
FreeBSD-src-5bc3a65e406b90cd9e2a47b79117e453bdb56413.tar.gz
Implement a facility for dynamic per-cpu variables.
- Modules and kernel code alike may use DPCPU_DEFINE(), DPCPU_GET(), DPCPU_SET(), etc. akin to the statically defined PCPU_*. Requires only one extra instruction more than PCPU_* and is virtually the same as __thread for builtin and much faster for shared objects. DPCPU variables can be initialized when defined. - Modules are supported by relocating the module's per-cpu linker set over space reserved in the kernel. Modules may fail to load if there is insufficient space available. - Track space available for modules with a one-off extent allocator. Free may block for memory to allocate space for an extent. Reviewed by: jhb, rwatson, kan, sam, grehan, marius, marcel, stas
Diffstat (limited to 'sys/ia64')
-rw-r--r--sys/ia64/ia64/elf_machdep.c2
-rw-r--r--sys/ia64/ia64/machdep.c32
-rw-r--r--sys/ia64/ia64/mp_machdep.c3
3 files changed, 21 insertions, 16 deletions
diff --git a/sys/ia64/ia64/elf_machdep.c b/sys/ia64/ia64/elf_machdep.c
index a100671..31765cc 100644
--- a/sys/ia64/ia64/elf_machdep.c
+++ b/sys/ia64/ia64/elf_machdep.c
@@ -211,7 +211,7 @@ elf_reloc_internal(linker_file_t lf, Elf_Addr relocbase, const void *data,
if (local) {
if (rtype == R_IA_64_REL64LSB)
- *where = relocbase + addend;
+ *where = elf_relocaddr(lf, relocbase + addend);
return (0);
}
diff --git a/sys/ia64/ia64/machdep.c b/sys/ia64/ia64/machdep.c
index dda1a08..b1e7298 100644
--- a/sys/ia64/ia64/machdep.c
+++ b/sys/ia64/ia64/machdep.c
@@ -647,6 +647,21 @@ ia64_init(void)
bootverbose = 1;
/*
+ * Find the beginning and end of the kernel.
+ */
+ kernstart = trunc_page(kernel_text);
+#ifdef DDB
+ ksym_start = bootinfo.bi_symtab;
+ ksym_end = bootinfo.bi_esymtab;
+ kernend = (vm_offset_t)round_page(ksym_end);
+#else
+ kernend = (vm_offset_t)round_page(_end);
+#endif
+ /* But if the bootstrap tells us otherwise, believe it! */
+ if (bootinfo.bi_kernend)
+ kernend = round_page(bootinfo.bi_kernend);
+
+ /*
* Setup the PCPU data for the bootstrap processor. It is needed
* by printf(). Also, since printf() has critical sections, we
* need to initialize at least pc_curthread.
@@ -654,6 +669,8 @@ ia64_init(void)
pcpup = &pcpu0;
ia64_set_k4((u_int64_t)pcpup);
pcpu_init(pcpup, 0, sizeof(pcpu0));
+ dpcpu_init((void *)kernend, 0);
+ kernend += DPCPU_SIZE;
PCPU_SET(curthread, &thread0);
/*
@@ -682,21 +699,6 @@ ia64_init(void)
ia64_sal_init();
calculate_frequencies();
- /*
- * Find the beginning and end of the kernel.
- */
- kernstart = trunc_page(kernel_text);
-#ifdef DDB
- ksym_start = bootinfo.bi_symtab;
- ksym_end = bootinfo.bi_esymtab;
- kernend = (vm_offset_t)round_page(ksym_end);
-#else
- kernend = (vm_offset_t)round_page(_end);
-#endif
-
- /* But if the bootstrap tells us otherwise, believe it! */
- if (bootinfo.bi_kernend)
- kernend = round_page(bootinfo.bi_kernend);
if (metadata_missing)
printf("WARNING: loader(8) metadata is missing!\n");
diff --git a/sys/ia64/ia64/mp_machdep.c b/sys/ia64/ia64/mp_machdep.c
index 6dba43a..e94acad 100644
--- a/sys/ia64/ia64/mp_machdep.c
+++ b/sys/ia64/ia64/mp_machdep.c
@@ -207,6 +207,7 @@ cpu_mp_add(u_int acpiid, u_int apicid, u_int apiceid)
{
struct pcpu *pc;
u_int64_t lid;
+ void *dpcpu;
/* Ignore any processor numbers outside our range */
if (acpiid > mp_maxid)
@@ -224,7 +225,9 @@ cpu_mp_add(u_int acpiid, u_int apicid, u_int apiceid)
if (acpiid != 0) {
pc = (struct pcpu *)malloc(sizeof(*pc), M_SMP, M_WAITOK);
+ dpcpu = (void *)kmem_alloc(kernel_map, DPCPU_SIZE);
pcpu_init(pc, acpiid, sizeof(*pc));
+ dpcpu_init(dpcpu, acpiid);
} else
pc = pcpup;
OpenPOWER on IntegriCloud