kernel ELF: Reimplement Elf Branding, .note.ABI-tag
[dragonfly.git] / sys / kern / imgact_elf.c
1 /*-
2  * Copyright (c) 2000 David O'Brien
3  * Copyright (c) 1995-1996 Søren Schmidt
4  * Copyright (c) 1996 Peter Wemm
5  * All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  * 1. Redistributions of source code must retain the above copyright
11  *    notice, this list of conditions and the following disclaimer
12  *    in this position and unchanged.
13  * 2. Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in the
15  *    documentation and/or other materials provided with the distribution.
16  * 3. The name of the author may not be used to endorse or promote products
17  *    derived from this software without specific prior written permission
18  *
19  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
20  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
21  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
22  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
23  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
24  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
28  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29  *
30  * $FreeBSD: src/sys/kern/imgact_elf.c,v 1.73.2.13 2002/12/28 19:49:41 dillon Exp $
31  */
32
33 #include <sys/param.h>
34 #include <sys/exec.h>
35 #include <sys/fcntl.h>
36 #include <sys/file.h>
37 #include <sys/imgact.h>
38 #include <sys/imgact_elf.h>
39 #include <sys/kernel.h>
40 #include <sys/malloc.h>
41 #include <sys/mman.h>
42 #include <sys/systm.h>
43 #include <sys/proc.h>
44 #include <sys/nlookup.h>
45 #include <sys/pioctl.h>
46 #include <sys/procfs.h>
47 #include <sys/resourcevar.h>
48 #include <sys/signalvar.h>
49 #include <sys/stat.h>
50 #include <sys/syscall.h>
51 #include <sys/sysctl.h>
52 #include <sys/sysent.h>
53 #include <sys/vnode.h>
54 #include <sys/eventhandler.h>
55
56 #include <cpu/lwbuf.h>
57
58 #include <vm/vm.h>
59 #include <vm/vm_kern.h>
60 #include <vm/vm_param.h>
61 #include <vm/pmap.h>
62 #include <sys/lock.h>
63 #include <vm/vm_map.h>
64 #include <vm/vm_object.h>
65 #include <vm/vm_extern.h>
66
67 #include <machine/elf.h>
68 #include <machine/md_var.h>
69 #include <sys/mount.h>
70 #include <sys/ckpt.h>
71
72 #define OLD_EI_BRAND    8
73 #define truncps(va,ps)  ((va) & ~(ps - 1))
74 #define aligned(a,t)    (truncps((u_long)(a), sizeof(t)) == (u_long)(a))
75
76 static int __elfN(check_header)(const Elf_Ehdr *hdr);
77 static Elf_Brandinfo *__elfN(get_brandinfo)(struct image_params *imgp,
78     const char *interp, int32_t *osrel);
79 static int __elfN(load_file)(struct proc *p, const char *file, u_long *addr,
80     u_long *entry);
81 static int __elfN(load_section)(struct proc *p,
82     struct vmspace *vmspace, struct vnode *vp,
83     vm_offset_t offset, caddr_t vmaddr, size_t memsz, size_t filsz,
84     vm_prot_t prot);
85 static int __CONCAT(exec_, __elfN(imgact))(struct image_params *imgp);
86 static boolean_t __elfN(check_note)(struct image_params *imgp,
87     Elf_Brandnote *checknote, int32_t *osrel);
88
89 static int elf_legacy_coredump = 0;
90 static int __elfN(fallback_brand) = -1;
91 #if defined(__x86_64__)
92 SYSCTL_NODE(_kern, OID_AUTO, elf64, CTLFLAG_RW, 0, "");
93 SYSCTL_INT(_debug, OID_AUTO, elf64_legacy_coredump, CTLFLAG_RW,
94     &elf_legacy_coredump, 0, "legacy coredump mode");
95 SYSCTL_INT(_kern_elf64, OID_AUTO, fallback_brand, CTLFLAG_RW,
96     &elf64_fallback_brand, 0, "ELF64 brand of last resort");
97 TUNABLE_INT("kern.elf64.fallback_brand", &elf64_fallback_brand);
98 #else /* i386 assumed */
99 SYSCTL_NODE(_kern, OID_AUTO, elf32, CTLFLAG_RW, 0, "");
100 SYSCTL_INT(_debug, OID_AUTO, elf32_legacy_coredump, CTLFLAG_RW,
101     &elf_legacy_coredump, 0, "legacy coredump mode");
102 SYSCTL_INT(_kern_elf32, OID_AUTO, fallback_brand, CTLFLAG_RW,
103     &elf32_fallback_brand, 0, "ELF32 brand of last resort");
104 TUNABLE_INT("kern.elf32.fallback_brand", &elf32_fallback_brand);
105 #endif
106
107 static Elf_Brandinfo *elf_brand_list[MAX_BRANDS];
108
109 static const char DRAGONFLY_ABI_VENDOR[] = "DragonFly";
110
111 Elf_Brandnote __elfN(dragonfly_brandnote) = {
112         .hdr.n_namesz   = sizeof(DRAGONFLY_ABI_VENDOR),
113         .hdr.n_descsz   = sizeof(int32_t),
114         .hdr.n_type     = 1,
115         .vendor         = DRAGONFLY_ABI_VENDOR,
116         .flags          = BN_CAN_FETCH_OSREL,
117 };
118
119 int
120 __elfN(insert_brand_entry)(Elf_Brandinfo *entry)
121 {
122         int i;
123
124         for (i = 0; i < MAX_BRANDS; i++) {
125                 if (elf_brand_list[i] == NULL) {
126                         elf_brand_list[i] = entry;
127                         break;
128                 }
129         }
130         if (i == MAX_BRANDS) {
131                 uprintf("WARNING: %s: could not insert brandinfo entry: %p\n",
132                         __func__, entry);
133                 return (-1);
134         }
135         return (0);
136 }
137
138 int
139 __elfN(remove_brand_entry)(Elf_Brandinfo *entry)
140 {
141         int i;
142
143         for (i = 0; i < MAX_BRANDS; i++) {
144                 if (elf_brand_list[i] == entry) {
145                         elf_brand_list[i] = NULL;
146                         break;
147                 }
148         }
149         if (i == MAX_BRANDS)
150                 return (-1);
151         return (0);
152 }
153
154 /*
155  * Check if an elf brand is being used anywhere in the system.
156  *
157  * Used by the linux emulation module unloader.  This isn't safe from
158  * races.
159  */
160 struct elf_brand_inuse_info {
161         int rval;
162         Elf_Brandinfo *entry;
163 };
164
165 static int elf_brand_inuse_callback(struct proc *p, void *data);
166
167 int
168 __elfN(brand_inuse)(Elf_Brandinfo *entry)
169 {
170         struct elf_brand_inuse_info info;
171
172         info.rval = FALSE;
173         info.entry = entry;
174         allproc_scan(elf_brand_inuse_callback, entry);
175         return (info.rval);
176 }
177
178 static
179 int
180 elf_brand_inuse_callback(struct proc *p, void *data)
181 {
182         struct elf_brand_inuse_info *info = data;
183
184         if (p->p_sysent == info->entry->sysvec) {
185                 info->rval = TRUE;
186                 return (-1);
187         }
188         return (0);
189 }
190
191 static int
192 __elfN(check_header)(const Elf_Ehdr *hdr)
193 {
194         Elf_Brandinfo *bi;
195         int i;
196
197         if (!IS_ELF(*hdr) ||
198             hdr->e_ident[EI_CLASS] != ELF_TARG_CLASS ||
199             hdr->e_ident[EI_DATA] != ELF_TARG_DATA ||
200             hdr->e_ident[EI_VERSION] != EV_CURRENT ||
201             hdr->e_phentsize != sizeof(Elf_Phdr) ||
202             hdr->e_ehsize != sizeof(Elf_Ehdr) ||
203             hdr->e_version != ELF_TARG_VER)
204                 return (ENOEXEC);
205
206         /*
207          * Make sure we have at least one brand for this machine.
208          */
209
210         for (i = 0; i < MAX_BRANDS; i++) {
211                 bi = elf_brand_list[i];
212                 if (bi != NULL && bi->machine == hdr->e_machine)
213                         break;
214         }
215         if (i == MAX_BRANDS)
216                 return (ENOEXEC);
217
218         return (0);
219 }
220
221 static int
222 __elfN(load_section)(struct proc *p, struct vmspace *vmspace, struct vnode *vp,
223                  vm_offset_t offset, caddr_t vmaddr, size_t memsz,
224                  size_t filsz, vm_prot_t prot)
225 {
226         size_t map_len;
227         vm_offset_t map_addr;
228         int error, rv, cow;
229         int count;
230         size_t copy_len;
231         vm_object_t object;
232         vm_offset_t file_addr;
233
234         object = vp->v_object;
235         error = 0;
236
237         /*
238          * It's necessary to fail if the filsz + offset taken from the
239          * header is greater than the actual file pager object's size.
240          * If we were to allow this, then the vm_map_find() below would
241          * walk right off the end of the file object and into the ether.
242          *
243          * While I'm here, might as well check for something else that
244          * is invalid: filsz cannot be greater than memsz.
245          */
246         if ((off_t)filsz + offset > vp->v_filesize || filsz > memsz) {
247                 uprintf("elf_load_section: truncated ELF file\n");
248                 return (ENOEXEC);
249         }
250
251         map_addr = trunc_page((vm_offset_t)vmaddr);
252         file_addr = trunc_page(offset);
253
254         /*
255          * We have two choices.  We can either clear the data in the last page
256          * of an oversized mapping, or we can start the anon mapping a page
257          * early and copy the initialized data into that first page.  We
258          * choose the second..
259          */
260         if (memsz > filsz)
261                 map_len = trunc_page(offset+filsz) - file_addr;
262         else
263                 map_len = round_page(offset+filsz) - file_addr;
264
265         if (map_len != 0) {
266                 vm_object_reference(object);
267
268                 /* cow flags: don't dump readonly sections in core */
269                 cow = MAP_COPY_ON_WRITE | MAP_PREFAULT |
270                     (prot & VM_PROT_WRITE ? 0 : MAP_DISABLE_COREDUMP);
271
272                 count = vm_map_entry_reserve(MAP_RESERVE_COUNT);
273                 vm_map_lock(&vmspace->vm_map);
274                 rv = vm_map_insert(&vmspace->vm_map, &count,
275                                       object,
276                                       file_addr,        /* file offset */
277                                       map_addr,         /* virtual start */
278                                       map_addr + map_len,/* virtual end */
279                                       VM_MAPTYPE_NORMAL,
280                                       prot, VM_PROT_ALL,
281                                       cow);
282                 vm_map_unlock(&vmspace->vm_map);
283                 vm_map_entry_release(count);
284                 if (rv != KERN_SUCCESS) {
285                         vm_object_deallocate(object);
286                         return (EINVAL);
287                 }
288
289                 /* we can stop now if we've covered it all */
290                 if (memsz == filsz) {
291                         return (0);
292                 }
293         }
294
295
296         /*
297          * We have to get the remaining bit of the file into the first part
298          * of the oversized map segment.  This is normally because the .data
299          * segment in the file is extended to provide bss.  It's a neat idea
300          * to try and save a page, but it's a pain in the behind to implement.
301          */
302         copy_len = (offset + filsz) - trunc_page(offset + filsz);
303         map_addr = trunc_page((vm_offset_t)vmaddr + filsz);
304         map_len = round_page((vm_offset_t)vmaddr + memsz) - map_addr;
305
306         /* This had damn well better be true! */
307         if (map_len != 0) {
308                 count = vm_map_entry_reserve(MAP_RESERVE_COUNT);
309                 vm_map_lock(&vmspace->vm_map);
310                 rv = vm_map_insert(&vmspace->vm_map, &count,
311                                         NULL, 0,
312                                         map_addr, map_addr + map_len,
313                                         VM_MAPTYPE_NORMAL,
314                                         VM_PROT_ALL, VM_PROT_ALL,
315                                         0);
316                 vm_map_unlock(&vmspace->vm_map);
317                 vm_map_entry_release(count);
318                 if (rv != KERN_SUCCESS) {
319                         return (EINVAL);
320                 }
321         }
322
323         if (copy_len != 0) {
324                 vm_page_t m;
325                 struct lwbuf *lwb;
326                 struct lwbuf lwb_cache;
327
328                 m = vm_fault_object_page(object, trunc_page(offset + filsz),
329                                          VM_PROT_READ, 0, &error);
330                 if (m) {
331                         lwb = lwbuf_alloc(m, &lwb_cache);
332                         error = copyout((caddr_t)lwbuf_kva(lwb),
333                                         (caddr_t)map_addr, copy_len);
334                         lwbuf_free(lwb);
335                         vm_page_unhold(m);
336                 }
337                 if (error) {
338                         return (error);
339                 }
340         }
341
342         /*
343          * set it to the specified protection
344          */
345         vm_map_protect(&vmspace->vm_map, map_addr, map_addr + map_len,  prot,
346                        FALSE);
347
348         return (error);
349 }
350
351 /*
352  * Load the file "file" into memory.  It may be either a shared object
353  * or an executable.
354  *
355  * The "addr" reference parameter is in/out.  On entry, it specifies
356  * the address where a shared object should be loaded.  If the file is
357  * an executable, this value is ignored.  On exit, "addr" specifies
358  * where the file was actually loaded.
359  *
360  * The "entry" reference parameter is out only.  On exit, it specifies
361  * the entry point for the loaded file.
362  */
363 static int
364 __elfN(load_file)(struct proc *p, const char *file, u_long *addr, u_long *entry)
365 {
366         struct {
367                 struct nlookupdata nd;
368                 struct vattr attr;
369                 struct image_params image_params;
370         } *tempdata;
371         const Elf_Ehdr *hdr = NULL;
372         const Elf_Phdr *phdr = NULL;
373         struct nlookupdata *nd;
374         struct vmspace *vmspace = p->p_vmspace;
375         struct vattr *attr;
376         struct image_params *imgp;
377         struct mount *topmnt;
378         vm_prot_t prot;
379         u_long rbase;
380         u_long base_addr = 0;
381         int error, i, numsegs;
382
383         tempdata = kmalloc(sizeof(*tempdata), M_TEMP, M_WAITOK);
384         nd = &tempdata->nd;
385         attr = &tempdata->attr;
386         imgp = &tempdata->image_params;
387
388         /*
389          * Initialize part of the common data
390          */
391         imgp->proc = p;
392         imgp->attr = attr;
393         imgp->firstpage = NULL;
394         imgp->image_header = NULL;
395         imgp->vp = NULL;
396
397         error = nlookup_init(nd, file, UIO_SYSSPACE, NLC_FOLLOW);
398         if (error == 0)
399                 error = nlookup(nd);
400         if (error == 0)
401                 error = cache_vget(&nd->nl_nch, nd->nl_cred, LK_EXCLUSIVE, &imgp->vp);
402         topmnt = nd->nl_nch.mount;
403         nlookup_done(nd);
404         if (error)
405                 goto fail;
406
407         /*
408          * Check permissions, modes, uid, etc on the file, and "open" it.
409          */
410         error = exec_check_permissions(imgp, topmnt);
411         if (error) {
412                 vn_unlock(imgp->vp);
413                 goto fail;
414         }
415
416         error = exec_map_first_page(imgp);
417         /*
418          * Also make certain that the interpreter stays the same, so set
419          * its VTEXT flag, too.
420          */
421         if (error == 0)
422                 vsetflags(imgp->vp, VTEXT);
423         vn_unlock(imgp->vp);
424         if (error)
425                 goto fail;
426
427         hdr = (const Elf_Ehdr *)imgp->image_header;
428         if ((error = __elfN(check_header)(hdr)) != 0)
429                 goto fail;
430         if (hdr->e_type == ET_DYN)
431                 rbase = *addr;
432         else if (hdr->e_type == ET_EXEC)
433                 rbase = 0;
434         else {
435                 error = ENOEXEC;
436                 goto fail;
437         }
438
439         /* Only support headers that fit within first page for now      */
440         /*    (multiplication of two Elf_Half fields will not overflow) */
441         if ((hdr->e_phoff > PAGE_SIZE) ||
442             (hdr->e_phentsize * hdr->e_phnum) > PAGE_SIZE - hdr->e_phoff) {
443                 error = ENOEXEC;
444                 goto fail;
445         }
446
447         phdr = (const Elf_Phdr *)(imgp->image_header + hdr->e_phoff);
448
449         for (i = 0, numsegs = 0; i < hdr->e_phnum; i++) {
450                 if (phdr[i].p_type == PT_LOAD) {        /* Loadable segment */
451                         prot = 0;
452                         if (phdr[i].p_flags & PF_X)
453                                 prot |= VM_PROT_EXECUTE;
454                         if (phdr[i].p_flags & PF_W)
455                                 prot |= VM_PROT_WRITE;
456                         if (phdr[i].p_flags & PF_R)
457                                 prot |= VM_PROT_READ;
458
459                         error = __elfN(load_section)(
460                                     p, vmspace, imgp->vp,
461                                     phdr[i].p_offset,
462                                     (caddr_t)phdr[i].p_vaddr +
463                                     rbase,
464                                     phdr[i].p_memsz,
465                                     phdr[i].p_filesz, prot);
466                         if (error != 0)
467                                 goto fail;
468                         /*
469                          * Establish the base address if this is the
470                          * first segment.
471                          */
472                         if (numsegs == 0)
473                                 base_addr = trunc_page(phdr[i].p_vaddr + rbase);
474                         numsegs++;
475                 }
476         }
477         *addr = base_addr;
478         *entry = (unsigned long)hdr->e_entry + rbase;
479
480 fail:
481         if (imgp->firstpage)
482                 exec_unmap_first_page(imgp);
483         if (imgp->vp) {
484                 vrele(imgp->vp);
485                 imgp->vp = NULL;
486         }
487         kfree(tempdata, M_TEMP);
488
489         return (error);
490 }
491
492 static Elf_Brandinfo *
493 __elfN(get_brandinfo)(struct image_params *imgp, const char *interp,
494     int32_t *osrel)
495 {
496         const Elf_Ehdr *hdr = (const Elf_Ehdr *)imgp->image_header;
497         Elf_Brandinfo *bi;
498         boolean_t ret;
499         int i;
500
501         /* We support four types of branding -- (1) the ELF EI_OSABI field
502          * that SCO added to the ELF spec, (2) FreeBSD 3.x's traditional string
503          * branding within the ELF header, (3) path of the `interp_path' field,
504          * and (4) the ".note.ABI-tag" ELF section.
505          */
506
507         /* Look for an ".note.ABI-tag" ELF section */
508         for (i = 0; i < MAX_BRANDS; i++) {
509                 bi = elf_brand_list[i];
510
511                 if (bi == NULL)
512                         continue;
513                 if (hdr->e_machine == bi->machine && (bi->flags &
514                     (BI_BRAND_NOTE|BI_BRAND_NOTE_MANDATORY)) != 0) {
515                         ret = __elfN(check_note)(imgp, bi->brand_note, osrel);
516                         if (ret)
517                                 return (bi);
518                 }
519         }
520
521         /* If the executable has a brand, search for it in the brand list. */
522         for (i = 0;  i < MAX_BRANDS;  i++) {
523                 bi = elf_brand_list[i];
524
525                 if (bi == NULL || bi->flags & BI_BRAND_NOTE_MANDATORY)
526                         continue;
527                 if (hdr->e_machine == bi->machine &&
528                     (hdr->e_ident[EI_OSABI] == bi->brand ||
529                     strncmp((const char *)&hdr->e_ident[OLD_EI_BRAND],
530                     bi->compat_3_brand, strlen(bi->compat_3_brand)) == 0))
531                         return (bi);
532         }
533
534         /* Lacking a known brand, search for a recognized interpreter. */
535         if (interp != NULL) {
536                 for (i = 0;  i < MAX_BRANDS;  i++) {
537                         bi = elf_brand_list[i];
538
539                         if (bi == NULL || bi->flags & BI_BRAND_NOTE_MANDATORY)
540                                 continue;
541                         if (hdr->e_machine == bi->machine &&
542                             strcmp(interp, bi->interp_path) == 0)
543                                 return (bi);
544                 }
545         }
546
547         /* Lacking a recognized interpreter, try the default brand */
548         for (i = 0; i < MAX_BRANDS; i++) {
549                 bi = elf_brand_list[i];
550
551                 if (bi == NULL || bi->flags & BI_BRAND_NOTE_MANDATORY)
552                         continue;
553                 if (hdr->e_machine == bi->machine &&
554                     __elfN(fallback_brand) == bi->brand)
555                         return (bi);
556         }
557         return (NULL);
558 }
559
560 static int
561 __CONCAT(exec_,__elfN(imgact))(struct image_params *imgp)
562 {
563         const Elf_Ehdr *hdr = (const Elf_Ehdr *) imgp->image_header;
564         const Elf_Phdr *phdr;
565         Elf_Auxargs *elf_auxargs = NULL;
566         struct vmspace *vmspace;
567         vm_prot_t prot;
568         u_long text_size = 0, data_size = 0, total_size = 0;
569         u_long text_addr = 0, data_addr = 0;
570         u_long seg_size, seg_addr;
571         u_long addr, entry = 0, proghdr = 0;
572         int32_t osrel = 0;
573         int error, i;
574         const char *interp = NULL, *newinterp = NULL;
575         Elf_Brandinfo *brand_info;
576         char *path;
577
578         error = 0;
579
580         /*
581          * Do we have a valid ELF header ?
582          *
583          * Only allow ET_EXEC & ET_DYN here, reject ET_DYN later if a particular
584          * brand doesn't support it.  Both DragonFly platforms do by default.
585          */
586         if (__elfN(check_header)(hdr) != 0 ||
587             (hdr->e_type != ET_EXEC && hdr->e_type != ET_DYN))
588                 return (-1);
589
590         /*
591          * From here on down, we return an errno, not -1, as we've
592          * detected an ELF file.
593          */
594
595         if ((hdr->e_phoff > PAGE_SIZE) ||
596             (hdr->e_phoff + hdr->e_phentsize * hdr->e_phnum) > PAGE_SIZE) {
597                 /* Only support headers in first page for now */
598                 return (ENOEXEC);
599         }
600         phdr = (const Elf_Phdr*)(imgp->image_header + hdr->e_phoff);
601         for (i = 0; i < hdr->e_phnum; i++) {
602             if (phdr[i].p_type == PT_INTERP) {
603                 /* Path to interpreter */
604                 if (phdr[i].p_filesz > MAXPATHLEN ||
605                     phdr[i].p_offset + phdr[i].p_filesz > PAGE_SIZE)
606                         return (ENOEXEC);
607                 interp = imgp->image_header + phdr[i].p_offset;
608                 break;
609             }
610         }
611         
612         brand_info = __elfN(get_brandinfo)(imgp, interp, &osrel);
613         if (brand_info == NULL) {
614             uprintf("ELF binary type \"%u\" not known.\n",
615                 hdr->e_ident[EI_OSABI]);
616             return (ENOEXEC);
617         }
618         if (hdr->e_type == ET_DYN &&
619             (brand_info->flags & BI_CAN_EXEC_DYN) == 0) {
620             return (ENOEXEC);
621         }
622
623         if (interp != NULL && brand_info->interp_newpath != NULL)
624                 newinterp = brand_info->interp_newpath;
625
626         exec_new_vmspace(imgp, NULL);
627
628         /*
629          * Yeah, I'm paranoid.  There is every reason in the world to get
630          * VTEXT now since from here on out, there are places we can have
631          * a context switch.  Better safe than sorry; I really don't want
632          * the file to change while it's being loaded.
633          */
634         vsetflags(imgp->vp, VTEXT);
635
636         vmspace = imgp->proc->p_vmspace;
637
638         for (i = 0; i < hdr->e_phnum; i++) {
639                 switch (phdr[i].p_type) {
640
641                 case PT_LOAD:   /* Loadable segment */
642                         prot = 0;
643                         if (phdr[i].p_flags & PF_X)
644                                 prot |= VM_PROT_EXECUTE;
645                         if (phdr[i].p_flags & PF_W)
646                                 prot |= VM_PROT_WRITE;
647                         if (phdr[i].p_flags & PF_R)
648                                 prot |= VM_PROT_READ;
649
650                         if ((error = __elfN(load_section)(
651                                         imgp->proc,
652                                         vmspace, imgp->vp,
653                                         phdr[i].p_offset,
654                                         (caddr_t)phdr[i].p_vaddr,
655                                         phdr[i].p_memsz,
656                                         phdr[i].p_filesz, prot)) != 0)
657                                 return (error);
658
659                         /*
660                          * If this segment contains the program headers,
661                          * remember their virtual address for the AT_PHDR
662                          * aux entry. Static binaries don't usually include
663                          * a PT_PHDR entry.
664                          */
665                         if (phdr[i].p_offset == 0 &&
666                             hdr->e_phoff + hdr->e_phnum * hdr->e_phentsize
667                                 <= phdr[i].p_filesz)
668                                 proghdr = phdr[i].p_vaddr + hdr->e_phoff;
669
670                         seg_addr = trunc_page(phdr[i].p_vaddr);
671                         seg_size = round_page(phdr[i].p_memsz +
672                                 phdr[i].p_vaddr - seg_addr);
673
674                         /*
675                          * Is this .text or .data?  We can't use
676                          * VM_PROT_WRITE or VM_PROT_EXEC, it breaks the
677                          * alpha terribly and possibly does other bad
678                          * things so we stick to the old way of figuring
679                          * it out:  If the segment contains the program
680                          * entry point, it's a text segment, otherwise it
681                          * is a data segment.
682                          *
683                          * Note that obreak() assumes that data_addr + 
684                          * data_size == end of data load area, and the ELF
685                          * file format expects segments to be sorted by
686                          * address.  If multiple data segments exist, the
687                          * last one will be used.
688                          */
689                         if (hdr->e_entry >= phdr[i].p_vaddr &&
690                             hdr->e_entry < (phdr[i].p_vaddr +
691                             phdr[i].p_memsz)) {
692                                 text_size = seg_size;
693                                 text_addr = seg_addr;
694                                 entry = (u_long)hdr->e_entry;
695                         } else {
696                                 data_size = seg_size;
697                                 data_addr = seg_addr;
698                         }
699                         total_size += seg_size;
700
701                         /*
702                          * Check limits.  It should be safe to check the
703                          * limits after loading the segment since we do
704                          * not actually fault in all the segment's pages.
705                          */
706                         if (data_size >
707                             imgp->proc->p_rlimit[RLIMIT_DATA].rlim_cur ||
708                             text_size > maxtsiz ||
709                             total_size >
710                             imgp->proc->p_rlimit[RLIMIT_VMEM].rlim_cur) {
711                                 error = ENOMEM;
712                                 return (error);
713                         }
714                         break;
715                 case PT_PHDR:   /* Program header table info */
716                         proghdr = phdr[i].p_vaddr;
717                         break;
718                 default:
719                         break;
720                 }
721         }
722
723         vmspace->vm_tsize = text_size >> PAGE_SHIFT;
724         vmspace->vm_taddr = (caddr_t)(uintptr_t)text_addr;
725         vmspace->vm_dsize = data_size >> PAGE_SHIFT;
726         vmspace->vm_daddr = (caddr_t)(uintptr_t)data_addr;
727
728         addr = ELF_RTLD_ADDR(vmspace);
729
730         imgp->entry_addr = entry;
731
732         imgp->proc->p_sysent = brand_info->sysvec;
733         EVENTHANDLER_INVOKE(process_exec, imgp);
734
735         if (interp != NULL) {
736                 int have_interp = FALSE;
737                 if (brand_info->emul_path != NULL &&
738                     brand_info->emul_path[0] != '\0') {
739                         path = kmalloc(MAXPATHLEN, M_TEMP, M_WAITOK);
740                         ksnprintf(path, MAXPATHLEN, "%s%s",
741                             brand_info->emul_path, interp);
742                         error = __elfN(load_file)(imgp->proc, path, &addr,
743                             &imgp->entry_addr);
744                         kfree(path, M_TEMP);
745                         if (error == 0)
746                             have_interp = TRUE;
747                 }
748                 if (!have_interp && newinterp != NULL) {
749                         error = __elfN(load_file)(imgp->proc, newinterp,
750                             &addr, &imgp->entry_addr);
751                         if (error == 0)
752                             have_interp = TRUE;
753                 }
754                 if (!have_interp) {
755                         error = __elfN(load_file)(imgp->proc, interp, &addr,
756                             &imgp->entry_addr);
757                 }
758                 if (error != 0) {
759                         uprintf("ELF interpreter %s not found\n", interp);
760                         return (error);
761                 }
762         } else
763                 addr = 0;
764
765         /*
766          * Construct auxargs table (used by the fixup routine)
767          */
768         elf_auxargs = kmalloc(sizeof(Elf_Auxargs), M_TEMP, M_WAITOK);
769         elf_auxargs->execfd = -1;
770         elf_auxargs->phdr = proghdr;
771         elf_auxargs->phent = hdr->e_phentsize;
772         elf_auxargs->phnum = hdr->e_phnum;
773         elf_auxargs->pagesz = PAGE_SIZE;
774         elf_auxargs->base = addr;
775         elf_auxargs->flags = 0;
776         elf_auxargs->entry = entry;
777
778         imgp->auxargs = elf_auxargs;
779         imgp->interpreted = 0;
780         imgp->proc->p_osrel = osrel;
781
782         return (error);
783 }
784
785 int
786 __elfN(dragonfly_fixup)(register_t **stack_base, struct image_params *imgp)
787 {
788         Elf_Auxargs *args = (Elf_Auxargs *)imgp->auxargs;
789         Elf_Addr *base;
790         Elf_Addr *pos;
791
792         base = (Elf_Addr *)*stack_base;
793         pos = base + (imgp->args->argc + imgp->args->envc + 2);
794
795         if (args->execfd != -1)
796                 AUXARGS_ENTRY(pos, AT_EXECFD, args->execfd);
797         AUXARGS_ENTRY(pos, AT_PHDR, args->phdr);
798         AUXARGS_ENTRY(pos, AT_PHENT, args->phent);
799         AUXARGS_ENTRY(pos, AT_PHNUM, args->phnum);
800         AUXARGS_ENTRY(pos, AT_PAGESZ, args->pagesz);
801         AUXARGS_ENTRY(pos, AT_FLAGS, args->flags);
802         AUXARGS_ENTRY(pos, AT_ENTRY, args->entry);
803         AUXARGS_ENTRY(pos, AT_BASE, args->base);
804         if (imgp->execpathp != 0)
805                 AUXARGS_ENTRY(pos, AT_EXECPATH, imgp->execpathp);
806         AUXARGS_ENTRY(pos, AT_NULL, 0);
807
808         kfree(imgp->auxargs, M_TEMP);
809         imgp->auxargs = NULL;
810
811         base--;
812         suword(base, (long)imgp->args->argc);
813         *stack_base = (register_t *)base;
814         return (0);
815 }
816
817 /*
818  * Code for generating ELF core dumps.
819  */
820
821 typedef int (*segment_callback) (vm_map_entry_t, void *);
822
823 /* Closure for cb_put_phdr(). */
824 struct phdr_closure {
825         Elf_Phdr *phdr;         /* Program header to fill in (incremented) */
826         Elf_Phdr *phdr_max;     /* Pointer bound for error check */
827         Elf_Off offset;         /* Offset of segment in core file */
828 };
829
830 /* Closure for cb_size_segment(). */
831 struct sseg_closure {
832         int count;              /* Count of writable segments. */
833         size_t vsize;           /* Total size of all writable segments. */
834 };
835
836 /* Closure for cb_put_fp(). */
837 struct fp_closure {
838         struct vn_hdr *vnh;
839         struct vn_hdr *vnh_max;
840         int count;
841         struct stat *sb;
842 };
843
844 typedef struct elf_buf {
845         char    *buf;
846         size_t  off;
847         size_t  off_max;
848 } *elf_buf_t;
849
850 static void *target_reserve(elf_buf_t target, size_t bytes, int *error);
851
852 static int cb_put_phdr (vm_map_entry_t, void *);
853 static int cb_size_segment (vm_map_entry_t, void *);
854 static int cb_fpcount_segment(vm_map_entry_t, void *);
855 static int cb_put_fp(vm_map_entry_t, void *);
856
857
858 static int each_segment (struct proc *, segment_callback, void *, int);
859 static int __elfN(corehdr)(struct lwp *, int, struct file *, struct ucred *,
860                         int, elf_buf_t);
861 enum putmode { WRITE, DRYRUN };
862 static int __elfN(puthdr)(struct lwp *, elf_buf_t, int sig, enum putmode,
863                         int, struct file *);
864 static int elf_putallnotes(struct lwp *, elf_buf_t, int, enum putmode);
865 static int __elfN(putnote)(elf_buf_t, const char *, int, const void *, size_t);
866
867 static int elf_putsigs(struct lwp *, elf_buf_t);
868 static int elf_puttextvp(struct proc *, elf_buf_t);
869 static int elf_putfiles(struct proc *, elf_buf_t, struct file *);
870
871 int
872 __elfN(coredump)(struct lwp *lp, int sig, struct vnode *vp, off_t limit)
873 {
874         struct file *fp; 
875         int error;
876
877         if ((error = falloc(NULL, &fp, NULL)) != 0)
878                 return (error);
879         fsetcred(fp, lp->lwp_proc->p_ucred);
880
881         /*
882          * XXX fixme.
883          */
884         fp->f_type = DTYPE_VNODE;
885         fp->f_flag = O_CREAT|O_WRONLY|O_NOFOLLOW;
886         fp->f_ops = &vnode_fileops;
887         fp->f_data = vp;
888         vn_unlock(vp);
889         
890         error = generic_elf_coredump(lp, sig, fp, limit);
891
892         fp->f_type = 0;
893         fp->f_flag = 0;
894         fp->f_ops = &badfileops;
895         fp->f_data = NULL;
896         fdrop(fp);
897         return (error);
898 }
899
900 int
901 generic_elf_coredump(struct lwp *lp, int sig, struct file *fp, off_t limit)
902 {
903         struct proc *p = lp->lwp_proc;
904         struct ucred *cred = p->p_ucred;
905         int error = 0;
906         struct sseg_closure seginfo;
907         struct elf_buf target;
908
909         if (!fp)
910                 kprintf("can't dump core - null fp\n");
911
912         /*
913          * Size the program segments
914          */
915         seginfo.count = 0;
916         seginfo.vsize = 0;
917         each_segment(p, cb_size_segment, &seginfo, 1);
918
919         /*
920          * Calculate the size of the core file header area by making
921          * a dry run of generating it.  Nothing is written, but the
922          * size is calculated.
923          */
924         bzero(&target, sizeof(target));
925         __elfN(puthdr)(lp, &target, sig, DRYRUN, seginfo.count, fp);
926
927         if (target.off + seginfo.vsize >= limit)
928                 return (EFAULT);
929
930         /*
931          * Allocate memory for building the header, fill it up,
932          * and write it out.
933          */
934         target.off_max = target.off;
935         target.off = 0;
936         target.buf = kmalloc(target.off_max, M_TEMP, M_WAITOK|M_ZERO);
937
938         error = __elfN(corehdr)(lp, sig, fp, cred, seginfo.count, &target);
939
940         /* Write the contents of all of the writable segments. */
941         if (error == 0) {
942                 Elf_Phdr *php;
943                 int i;
944                 ssize_t nbytes;
945
946                 php = (Elf_Phdr *)(target.buf + sizeof(Elf_Ehdr)) + 1;
947                 for (i = 0; i < seginfo.count; i++) {
948                         error = fp_write(fp, (caddr_t)php->p_vaddr,
949                                         php->p_filesz, &nbytes, UIO_USERSPACE);
950                         if (error != 0)
951                                 break;
952                         php++;
953                 }
954         }
955         kfree(target.buf, M_TEMP);
956         
957         return (error);
958 }
959
960 /*
961  * A callback for each_segment() to write out the segment's
962  * program header entry.
963  */
964 static int
965 cb_put_phdr(vm_map_entry_t entry, void *closure)
966 {
967         struct phdr_closure *phc = closure;
968         Elf_Phdr *phdr = phc->phdr;
969
970         if (phc->phdr == phc->phdr_max)
971                 return (EINVAL);
972
973         phc->offset = round_page(phc->offset);
974
975         phdr->p_type = PT_LOAD;
976         phdr->p_offset = phc->offset;
977         phdr->p_vaddr = entry->start;
978         phdr->p_paddr = 0;
979         phdr->p_filesz = phdr->p_memsz = entry->end - entry->start;
980         phdr->p_align = PAGE_SIZE;
981         phdr->p_flags = 0;
982         if (entry->protection & VM_PROT_READ)
983                 phdr->p_flags |= PF_R;
984         if (entry->protection & VM_PROT_WRITE)
985                 phdr->p_flags |= PF_W;
986         if (entry->protection & VM_PROT_EXECUTE)
987                 phdr->p_flags |= PF_X;
988
989         phc->offset += phdr->p_filesz;
990         ++phc->phdr;
991         return (0);
992 }
993
994 /*
995  * A callback for each_writable_segment() to gather information about
996  * the number of segments and their total size.
997  */
998 static int
999 cb_size_segment(vm_map_entry_t entry, void *closure)
1000 {
1001         struct sseg_closure *ssc = closure;
1002
1003         ++ssc->count;
1004         ssc->vsize += entry->end - entry->start;
1005         return (0);
1006 }
1007
1008 /*
1009  * A callback for each_segment() to gather information about
1010  * the number of text segments.
1011  */
1012 static int
1013 cb_fpcount_segment(vm_map_entry_t entry, void *closure)
1014 {
1015         int *count = closure;
1016         struct vnode *vp;
1017
1018         if (entry->object.vm_object->type == OBJT_VNODE) {
1019                 vp = (struct vnode *)entry->object.vm_object->handle;
1020                 if ((vp->v_flag & VCKPT) && curproc->p_textvp == vp)
1021                         return (0);
1022                 ++*count;
1023         }
1024         return (0);
1025 }
1026
1027 static int
1028 cb_put_fp(vm_map_entry_t entry, void *closure) 
1029 {
1030         struct fp_closure *fpc = closure;
1031         struct vn_hdr *vnh = fpc->vnh;
1032         Elf_Phdr *phdr = &vnh->vnh_phdr;
1033         struct vnode *vp;
1034         int error;
1035
1036         /*
1037          * If an entry represents a vnode then write out a file handle.
1038          *
1039          * If we are checkpointing a checkpoint-restored program we do
1040          * NOT record the filehandle for the old checkpoint vnode (which
1041          * is mapped all over the place).  Instead we rely on the fact
1042          * that a checkpoint-restored program does not mmap() the checkpt
1043          * vnode NOCORE, so its contents will be written out to the
1044          * new checkpoint file.  This is necessary because the 'old'
1045          * checkpoint file is typically destroyed when a new one is created
1046          * and thus cannot be used to restore the new checkpoint.
1047          *
1048          * Theoretically we could create a chain of checkpoint files and
1049          * operate the checkpointing operation kinda like an incremental
1050          * checkpoint, but a checkpoint restore would then likely wind up
1051          * referencing many prior checkpoint files and that is a bit over
1052          * the top for the purpose of the checkpoint API.
1053          */
1054         if (entry->object.vm_object->type == OBJT_VNODE) {
1055                 vp = (struct vnode *)entry->object.vm_object->handle;
1056                 if ((vp->v_flag & VCKPT) && curproc->p_textvp == vp)
1057                         return (0);
1058                 if (vnh == fpc->vnh_max)
1059                         return (EINVAL);
1060
1061                 if (vp->v_mount)
1062                         vnh->vnh_fh.fh_fsid = vp->v_mount->mnt_stat.f_fsid;
1063                 error = VFS_VPTOFH(vp, &vnh->vnh_fh.fh_fid);
1064                 if (error) {
1065                         char *freepath, *fullpath;
1066
1067                         if (vn_fullpath(curproc, vp, &fullpath, &freepath, 0)) {
1068                                 kprintf("Warning: coredump, error %d: cannot store file handle for vnode %p\n", error, vp);
1069                         } else {
1070                                 kprintf("Warning: coredump, error %d: cannot store file handle for %s\n", error, fullpath);
1071                                 kfree(freepath, M_TEMP);
1072                         }
1073                         error = 0;
1074                 }
1075
1076                 phdr->p_type = PT_LOAD;
1077                 phdr->p_offset = 0;        /* not written to core */
1078                 phdr->p_vaddr = entry->start;
1079                 phdr->p_paddr = 0;
1080                 phdr->p_filesz = phdr->p_memsz = entry->end - entry->start;
1081                 phdr->p_align = PAGE_SIZE;
1082                 phdr->p_flags = 0;
1083                 if (entry->protection & VM_PROT_READ)
1084                         phdr->p_flags |= PF_R;
1085                 if (entry->protection & VM_PROT_WRITE)
1086                         phdr->p_flags |= PF_W;
1087                 if (entry->protection & VM_PROT_EXECUTE)
1088                         phdr->p_flags |= PF_X;
1089                 ++fpc->vnh;
1090                 ++fpc->count;
1091         }
1092         return (0);
1093 }
1094
1095 /*
1096  * For each writable segment in the process's memory map, call the given
1097  * function with a pointer to the map entry and some arbitrary
1098  * caller-supplied data.
1099  */
1100 static int
1101 each_segment(struct proc *p, segment_callback func, void *closure, int writable)
1102 {
1103         int error = 0;
1104         vm_map_t map = &p->p_vmspace->vm_map;
1105         vm_map_entry_t entry;
1106
1107         for (entry = map->header.next; error == 0 && entry != &map->header;
1108             entry = entry->next) {
1109                 vm_object_t obj;
1110
1111                 /*
1112                  * Don't dump inaccessible mappings, deal with legacy
1113                  * coredump mode.
1114                  *
1115                  * Note that read-only segments related to the elf binary
1116                  * are marked MAP_ENTRY_NOCOREDUMP now so we no longer
1117                  * need to arbitrarily ignore such segments.
1118                  */
1119                 if (elf_legacy_coredump) {
1120                         if (writable && (entry->protection & VM_PROT_RW) != VM_PROT_RW)
1121                                 continue;
1122                 } else {
1123                         if (writable && (entry->protection & VM_PROT_ALL) == 0)
1124                                 continue;
1125                 }
1126
1127                 /*
1128                  * Dont include memory segment in the coredump if
1129                  * MAP_NOCORE is set in mmap(2) or MADV_NOCORE in
1130                  * madvise(2).
1131                  *
1132                  * Currently we only dump normal VM object maps.  We do
1133                  * not dump submaps or virtual page tables.
1134                  */
1135                 if (writable && (entry->eflags & MAP_ENTRY_NOCOREDUMP))
1136                         continue;
1137                 if (entry->maptype != VM_MAPTYPE_NORMAL)
1138                         continue;
1139                 if ((obj = entry->object.vm_object) == NULL)
1140                         continue;
1141
1142                 /* Find the deepest backing object. */
1143                 while (obj->backing_object != NULL)
1144                         obj = obj->backing_object;
1145
1146                 /* Ignore memory-mapped devices and such things. */
1147                 if (obj->type != OBJT_DEFAULT &&
1148                     obj->type != OBJT_SWAP &&
1149                     obj->type != OBJT_VNODE)
1150                         continue;
1151
1152                 error = (*func)(entry, closure);
1153         }
1154         return (error);
1155 }
1156
1157 static
1158 void *
1159 target_reserve(elf_buf_t target, size_t bytes, int *error)
1160 {
1161     void *res = NULL;
1162
1163     if (target->buf) {
1164             if (target->off + bytes > target->off_max)
1165                     *error = EINVAL;
1166             else
1167                     res = target->buf + target->off;
1168     }
1169     target->off += bytes;
1170     return (res);
1171 }
1172
1173 /*
1174  * Write the core file header to the file, including padding up to
1175  * the page boundary.
1176  */
1177 static int
1178 __elfN(corehdr)(struct lwp *lp, int sig, struct file *fp, struct ucred *cred,
1179             int numsegs, elf_buf_t target)
1180 {
1181         int error;
1182         ssize_t nbytes;
1183
1184         /*
1185          * Fill in the header.  The fp is passed so we can detect and flag
1186          * a checkpoint file pointer within the core file itself, because
1187          * it may not be restored from the same file handle.
1188          */
1189         error = __elfN(puthdr)(lp, target, sig, WRITE, numsegs, fp);
1190
1191         /* Write it to the core file. */
1192         if (error == 0) {
1193                 error = fp_write(fp, target->buf, target->off, &nbytes,
1194                                  UIO_SYSSPACE);
1195         }
1196         return (error);
1197 }
1198
1199 static int
1200 __elfN(puthdr)(struct lwp *lp, elf_buf_t target, int sig, enum putmode mode,
1201     int numsegs, struct file *fp)
1202 {
1203         struct proc *p = lp->lwp_proc;
1204         int error = 0;
1205         size_t phoff;
1206         size_t noteoff;
1207         size_t notesz;
1208         Elf_Ehdr *ehdr;
1209         Elf_Phdr *phdr;
1210
1211         ehdr = target_reserve(target, sizeof(Elf_Ehdr), &error);
1212
1213         phoff = target->off;
1214         phdr = target_reserve(target, (numsegs + 1) * sizeof(Elf_Phdr), &error);
1215
1216         noteoff = target->off;
1217         if (error == 0)
1218                 elf_putallnotes(lp, target, sig, mode);
1219         notesz = target->off - noteoff;
1220
1221         /*
1222          * put extra cruft for dumping process state here 
1223          *  - we really want it be before all the program 
1224          *    mappings
1225          *  - we just need to update the offset accordingly
1226          *    and GDB will be none the wiser.
1227          */
1228         if (error == 0)
1229                 error = elf_puttextvp(p, target);
1230         if (error == 0)
1231                 error = elf_putsigs(lp, target);
1232         if (error == 0)
1233                 error = elf_putfiles(p, target, fp);
1234
1235         /*
1236          * Align up to a page boundary for the program segments.  The
1237          * actual data will be written to the outptu file, not to elf_buf_t,
1238          * so we do not have to do any further bounds checking.
1239          */
1240         target->off = round_page(target->off);
1241         if (error == 0 && ehdr != NULL) {
1242                 /*
1243                  * Fill in the ELF header.
1244                  */
1245                 ehdr->e_ident[EI_MAG0] = ELFMAG0;
1246                 ehdr->e_ident[EI_MAG1] = ELFMAG1;
1247                 ehdr->e_ident[EI_MAG2] = ELFMAG2;
1248                 ehdr->e_ident[EI_MAG3] = ELFMAG3;
1249                 ehdr->e_ident[EI_CLASS] = ELF_CLASS;
1250                 ehdr->e_ident[EI_DATA] = ELF_DATA;
1251                 ehdr->e_ident[EI_VERSION] = EV_CURRENT;
1252                 ehdr->e_ident[EI_OSABI] = ELFOSABI_NONE;
1253                 ehdr->e_ident[EI_ABIVERSION] = 0;
1254                 ehdr->e_ident[EI_PAD] = 0;
1255                 ehdr->e_type = ET_CORE;
1256                 ehdr->e_machine = ELF_ARCH;
1257                 ehdr->e_version = EV_CURRENT;
1258                 ehdr->e_entry = 0;
1259                 ehdr->e_phoff = phoff;
1260                 ehdr->e_flags = 0;
1261                 ehdr->e_ehsize = sizeof(Elf_Ehdr);
1262                 ehdr->e_phentsize = sizeof(Elf_Phdr);
1263                 ehdr->e_phnum = numsegs + 1;
1264                 ehdr->e_shentsize = sizeof(Elf_Shdr);
1265                 ehdr->e_shnum = 0;
1266                 ehdr->e_shstrndx = SHN_UNDEF;
1267         }
1268         if (error == 0 && phdr != NULL) {
1269                 /*
1270                  * Fill in the program header entries.
1271                  */
1272                 struct phdr_closure phc;
1273
1274                 /* The note segement. */
1275                 phdr->p_type = PT_NOTE;
1276                 phdr->p_offset = noteoff;
1277                 phdr->p_vaddr = 0;
1278                 phdr->p_paddr = 0;
1279                 phdr->p_filesz = notesz;
1280                 phdr->p_memsz = 0;
1281                 phdr->p_flags = 0;
1282                 phdr->p_align = 0;
1283                 ++phdr;
1284
1285                 /* All the writable segments from the program. */
1286                 phc.phdr = phdr;
1287                 phc.phdr_max = phdr + numsegs;
1288                 phc.offset = target->off;
1289                 each_segment(p, cb_put_phdr, &phc, 1);
1290         }
1291         return (error);
1292 }
1293
1294 /*
1295  * Append core dump notes to target ELF buffer or simply update target size
1296  * if dryrun selected.
1297  */
1298 static int
1299 elf_putallnotes(struct lwp *corelp, elf_buf_t target, int sig,
1300     enum putmode mode)
1301 {
1302         struct proc *p = corelp->lwp_proc;
1303         int error;
1304         struct {
1305                 prstatus_t status;
1306                 prfpregset_t fpregs;
1307                 prpsinfo_t psinfo;
1308         } *tmpdata;
1309         prstatus_t *status;
1310         prfpregset_t *fpregs;
1311         prpsinfo_t *psinfo;
1312         struct lwp *lp;
1313
1314         /*
1315          * Allocate temporary storage for notes on heap to avoid stack overflow.
1316          */
1317         if (mode != DRYRUN) {
1318                 tmpdata = kmalloc(sizeof(*tmpdata), M_TEMP, M_ZERO | M_WAITOK);
1319                 status = &tmpdata->status;
1320                 fpregs = &tmpdata->fpregs;
1321                 psinfo = &tmpdata->psinfo;
1322         } else {
1323                 tmpdata = NULL;
1324                 status = NULL;
1325                 fpregs = NULL;
1326                 psinfo = NULL;
1327         }
1328
1329         /*
1330          * Append LWP-agnostic note.
1331          */
1332         if (mode != DRYRUN) {
1333                 psinfo->pr_version = PRPSINFO_VERSION;
1334                 psinfo->pr_psinfosz = sizeof(prpsinfo_t);
1335                 strlcpy(psinfo->pr_fname, p->p_comm,
1336                         sizeof(psinfo->pr_fname));
1337                 /*
1338                  * XXX - We don't fill in the command line arguments
1339                  * properly yet.
1340                  */
1341                 strlcpy(psinfo->pr_psargs, p->p_comm,
1342                         sizeof(psinfo->pr_psargs));
1343         }
1344         error =
1345             __elfN(putnote)(target, "CORE", NT_PRPSINFO, psinfo, sizeof *psinfo);
1346         if (error)
1347                 goto exit;
1348
1349         /*
1350          * Append first note for LWP that triggered core so that it is
1351          * the selected one when the debugger starts.
1352          */
1353         if (mode != DRYRUN) {
1354                 status->pr_version = PRSTATUS_VERSION;
1355                 status->pr_statussz = sizeof(prstatus_t);
1356                 status->pr_gregsetsz = sizeof(gregset_t);
1357                 status->pr_fpregsetsz = sizeof(fpregset_t);
1358                 status->pr_osreldate = osreldate;
1359                 status->pr_cursig = sig;
1360                 /*
1361                  * XXX GDB needs unique pr_pid for each LWP and does not
1362                  * not support pr_pid==0 but lwp_tid can be 0, so hack unique
1363                  * value.
1364                  */
1365                 status->pr_pid = corelp->lwp_tid;
1366                 fill_regs(corelp, &status->pr_reg);
1367                 fill_fpregs(corelp, fpregs);
1368         }
1369         error =
1370             __elfN(putnote)(target, "CORE", NT_PRSTATUS, status, sizeof *status);
1371         if (error)
1372                 goto exit;
1373         error =
1374             __elfN(putnote)(target, "CORE", NT_FPREGSET, fpregs, sizeof *fpregs);
1375         if (error)
1376                 goto exit;
1377
1378         /*
1379          * Then append notes for other LWPs.
1380          */
1381         FOREACH_LWP_IN_PROC(lp, p) {
1382                 if (lp == corelp)
1383                         continue;
1384                 /* skip lwps being created */
1385                 if (lp->lwp_thread == NULL)
1386                         continue;
1387                 if (mode != DRYRUN) {
1388                         status->pr_pid = lp->lwp_tid;
1389                         fill_regs(lp, &status->pr_reg);
1390                         fill_fpregs(lp, fpregs);
1391                 }
1392                 error = __elfN(putnote)(target, "CORE", NT_PRSTATUS,
1393                                         status, sizeof *status);
1394                 if (error)
1395                         goto exit;
1396                 error = __elfN(putnote)(target, "CORE", NT_FPREGSET,
1397                                         fpregs, sizeof *fpregs);
1398                 if (error)
1399                         goto exit;
1400         }
1401
1402 exit:
1403         if (tmpdata != NULL)
1404                 kfree(tmpdata, M_TEMP);
1405         return (error);
1406 }
1407
1408 /*
1409  * Generate a note sub-structure.
1410  *
1411  * NOTE: 4-byte alignment.
1412  */
1413 static int
1414 __elfN(putnote)(elf_buf_t target, const char *name, int type,
1415             const void *desc, size_t descsz)
1416 {
1417         int error = 0;
1418         char *dst;
1419         Elf_Note note;
1420
1421         note.n_namesz = strlen(name) + 1;
1422         note.n_descsz = descsz;
1423         note.n_type = type;
1424         dst = target_reserve(target, sizeof(note), &error);
1425         if (dst != NULL)
1426                 bcopy(&note, dst, sizeof note);
1427         dst = target_reserve(target, note.n_namesz, &error);
1428         if (dst != NULL)
1429                 bcopy(name, dst, note.n_namesz);
1430         target->off = roundup2(target->off, sizeof(Elf_Word));
1431         dst = target_reserve(target, note.n_descsz, &error);
1432         if (dst != NULL)
1433                 bcopy(desc, dst, note.n_descsz);
1434         target->off = roundup2(target->off, sizeof(Elf_Word));
1435         return (error);
1436 }
1437
1438
1439 static int
1440 elf_putsigs(struct lwp *lp, elf_buf_t target)
1441 {
1442         /* XXX lwp handle more than one lwp */
1443         struct proc *p = lp->lwp_proc;
1444         int error = 0;
1445         struct ckpt_siginfo *csi;
1446
1447         csi = target_reserve(target, sizeof(struct ckpt_siginfo), &error);
1448         if (csi) {
1449                 csi->csi_ckptpisz = sizeof(struct ckpt_siginfo);
1450                 bcopy(p->p_sigacts, &csi->csi_sigacts, sizeof(*p->p_sigacts));
1451                 bcopy(&p->p_realtimer, &csi->csi_itimerval, sizeof(struct itimerval));
1452                 bcopy(&lp->lwp_sigmask, &csi->csi_sigmask,
1453                         sizeof(sigset_t));
1454                 csi->csi_sigparent = p->p_sigparent;
1455         }
1456         return (error);
1457 }
1458
1459 static int
1460 elf_putfiles(struct proc *p, elf_buf_t target, struct file *ckfp)
1461 {
1462         int error = 0;
1463         int i;
1464         struct ckpt_filehdr *cfh = NULL;
1465         struct ckpt_fileinfo *cfi;
1466         struct file *fp;        
1467         struct vnode *vp;
1468         /*
1469          * the duplicated loop is gross, but it was the only way
1470          * to eliminate uninitialized variable warnings 
1471          */
1472         cfh = target_reserve(target, sizeof(struct ckpt_filehdr), &error);
1473         if (cfh) {
1474                 cfh->cfh_nfiles = 0;            
1475         }
1476
1477         /*
1478          * ignore STDIN/STDERR/STDOUT.
1479          */
1480         for (i = 3; error == 0 && i < p->p_fd->fd_nfiles; i++) {
1481                 fp = holdfp(p->p_fd, i, -1);
1482                 if (fp == NULL)
1483                         continue;
1484                 /* 
1485                  * XXX Only checkpoint vnodes for now.
1486                  */
1487                 if (fp->f_type != DTYPE_VNODE) {
1488                         fdrop(fp);
1489                         continue;
1490                 }
1491                 cfi = target_reserve(target, sizeof(struct ckpt_fileinfo),
1492                                         &error);
1493                 if (cfi == NULL) {
1494                         fdrop(fp);
1495                         continue;
1496                 }
1497                 cfi->cfi_index = -1;
1498                 cfi->cfi_type = fp->f_type;
1499                 cfi->cfi_flags = fp->f_flag;
1500                 cfi->cfi_offset = fp->f_offset;
1501                 cfi->cfi_ckflags = 0;
1502
1503                 if (fp == ckfp)
1504                         cfi->cfi_ckflags |= CKFIF_ISCKPTFD;
1505                 /* f_count and f_msgcount should not be saved/restored */
1506                 /* XXX save cred info */
1507
1508                 switch(fp->f_type) {
1509                 case DTYPE_VNODE:
1510                         vp = (struct vnode *)fp->f_data;
1511                         /*
1512                          * it looks like a bug in ptrace is marking 
1513                          * a non-vnode as a vnode - until we find the 
1514                          * root cause this will at least prevent
1515                          * further panics from truss
1516                          */
1517                         if (vp == NULL || vp->v_mount == NULL)
1518                                 break;
1519                         cfh->cfh_nfiles++;
1520                         cfi->cfi_index = i;
1521                         cfi->cfi_fh.fh_fsid = vp->v_mount->mnt_stat.f_fsid;
1522                         error = VFS_VPTOFH(vp, &cfi->cfi_fh.fh_fid);
1523                         break;
1524                 default:
1525                         break;
1526                 }
1527                 fdrop(fp);
1528         }
1529         return (error);
1530 }
1531
1532 static int
1533 elf_puttextvp(struct proc *p, elf_buf_t target)
1534 {
1535         int error = 0;
1536         int *vn_count;
1537         struct fp_closure fpc;
1538         struct ckpt_vminfo *vminfo;
1539
1540         vminfo = target_reserve(target, sizeof(struct ckpt_vminfo), &error);
1541         if (vminfo != NULL) {
1542                 vminfo->cvm_dsize = p->p_vmspace->vm_dsize;
1543                 vminfo->cvm_tsize = p->p_vmspace->vm_tsize;
1544                 vminfo->cvm_daddr = p->p_vmspace->vm_daddr;
1545                 vminfo->cvm_taddr = p->p_vmspace->vm_taddr;
1546         }
1547
1548         fpc.count = 0;
1549         vn_count = target_reserve(target, sizeof(int), &error);
1550         if (target->buf != NULL) {
1551                 fpc.vnh = (struct vn_hdr *)(target->buf + target->off);
1552                 fpc.vnh_max = fpc.vnh + 
1553                         (target->off_max - target->off) / sizeof(struct vn_hdr);
1554                 error = each_segment(p, cb_put_fp, &fpc, 0);
1555                 if (vn_count)
1556                         *vn_count = fpc.count;
1557         } else {
1558                 error = each_segment(p, cb_fpcount_segment, &fpc.count, 0);
1559         }
1560         target->off += fpc.count * sizeof(struct vn_hdr);
1561         return (error);
1562 }
1563
1564 /*
1565  * Try to find the appropriate ABI-note section for checknote,
1566  * fetch the osreldate for binary from the ELF OSABI-note. Only the
1567  * first page of the image is searched, the same as for headers.
1568  */
1569 static boolean_t
1570 __elfN(check_note)(struct image_params *imgp, Elf_Brandnote *checknote,
1571     int32_t *osrel)
1572 {
1573         const Elf_Note *note, *note0, *note_end;
1574         const Elf_Phdr *phdr, *pnote;
1575         const Elf_Ehdr *hdr;
1576         const char *note_name;
1577         int i;
1578
1579         pnote = NULL;
1580         hdr = (const Elf_Ehdr *)imgp->image_header;
1581         phdr = (const Elf_Phdr *)(imgp->image_header + hdr->e_phoff);
1582
1583         for (i = 0; i < hdr->e_phnum; i++) {
1584                 if (phdr[i].p_type == PT_NOTE) {
1585                         pnote = &phdr[i];
1586                         break;
1587                 }
1588         }
1589
1590         if (pnote == NULL || pnote->p_offset >= PAGE_SIZE ||
1591             pnote->p_offset + pnote->p_filesz >= PAGE_SIZE)
1592                 return (FALSE);
1593
1594         note = note0 = (const Elf_Note *)(imgp->image_header + pnote->p_offset);
1595         note_end = (const Elf_Note *)(imgp->image_header +
1596             pnote->p_offset + pnote->p_filesz);
1597         for (i = 0; i < 100 && note >= note0 && note < note_end; i++) {
1598                 if (!aligned(note, Elf32_Addr))
1599                         return (FALSE);
1600                 if (note->n_namesz != checknote->hdr.n_namesz ||
1601                     note->n_descsz != checknote->hdr.n_descsz ||
1602                     note->n_type != checknote->hdr.n_type)
1603                         goto nextnote;
1604                 note_name = (const char *)(note + 1);
1605                 if (strncmp(checknote->vendor, note_name,
1606                     checknote->hdr.n_namesz) != 0)
1607                         goto nextnote;
1608
1609                 /*
1610                  * Fetch the osreldate for binary
1611                  * from the ELF OSABI-note if necessary.
1612                  */
1613                 if ((checknote->flags & BN_CAN_FETCH_OSREL) != 0 &&
1614                     osrel != NULL)
1615                         *osrel = *(const int32_t *) (note_name +
1616                             roundup2(checknote->hdr.n_namesz,
1617                             sizeof(Elf32_Addr)));
1618                 return (TRUE);
1619
1620 nextnote:
1621                 note = (const Elf_Note *)((const char *)(note + 1) +
1622                     roundup2(note->n_namesz, sizeof(Elf32_Addr)) +
1623                     roundup2(note->n_descsz, sizeof(Elf32_Addr)));
1624         }
1625
1626         return (FALSE);
1627 }
1628
1629 /*
1630  * Tell kern_execve.c about it, with a little help from the linker.
1631  */
1632 #if defined(__x86_64__)
1633 static struct execsw elf_execsw = {exec_elf64_imgact, "ELF64"};
1634 EXEC_SET_ORDERED(elf64, elf_execsw, SI_ORDER_FIRST);
1635 #else /* i386 assumed */
1636 static struct execsw elf_execsw = {exec_elf32_imgact, "ELF32"};
1637 EXEC_SET_ORDERED(elf32, elf_execsw, SI_ORDER_FIRST);
1638 #endif