1 /* $NetBSD: loadfile_ecoff.c,v 1.4 2002/02/11 20:25:56 reinoud Exp $ */ 2 3 /*- 4 * Copyright (c) 1997 The NetBSD Foundation, Inc. 5 * All rights reserved. 6 * 7 * This code is derived from software contributed to The NetBSD Foundation 8 * by Jason R. Thorpe of the Numerical Aerospace Simulation Facility, 9 * NASA Ames Research Center and by Christos Zoulas. 10 * 11 * Redistribution and use in source and binary forms, with or without 12 * modification, are permitted provided that the following conditions 13 * are met: 14 * 1. Redistributions of source code must retain the above copyright 15 * notice, this list of conditions and the following disclaimer. 16 * 2. Redistributions in binary form must reproduce the above copyright 17 * notice, this list of conditions and the following disclaimer in the 18 * documentation and/or other materials provided with the distribution. 19 * 3. All advertising materials mentioning features or use of this software 20 * must display the following acknowledgement: 21 * This product includes software developed by the NetBSD 22 * Foundation, Inc. and its contributors. 23 * 4. Neither the name of The NetBSD Foundation nor the names of its 24 * contributors may be used to endorse or promote products derived 25 * from this software without specific prior written permission. 26 * 27 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 28 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 29 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 30 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 31 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 32 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 33 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 34 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 35 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 36 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 37 * POSSIBILITY OF SUCH DAMAGE. 38 */ 39 40 #ifdef _STANDALONE 41 #include <lib/libsa/stand.h> 42 #include <lib/libkern/libkern.h> 43 #else 44 #include <stdio.h> 45 #include <string.h> 46 #include <errno.h> 47 #include <stdlib.h> 48 #include <unistd.h> 49 #include <fcntl.h> 50 #include <err.h> 51 #endif 52 53 #include <sys/param.h> 54 #include <sys/exec.h> 55 56 #include "loadfile.h" 57 58 #ifdef BOOT_ECOFF 59 60 int 61 loadfile_coff(fd, coff, marks, flags) 62 int fd; 63 struct ecoff_exechdr *coff; 64 u_long *marks; 65 int flags; 66 { 67 paddr_t offset = marks[MARK_START]; 68 paddr_t minp = ~0, maxp = 0, pos; 69 70 /* some ports dont use the offset */ 71 offset = offset; 72 73 /* Read in text. */ 74 if (lseek(fd, ECOFF_TXTOFF(coff), SEEK_SET) == -1) { 75 WARN(("lseek text")); 76 return 1; 77 } 78 79 if (coff->a.tsize != 0) { 80 if (flags & LOAD_TEXT) { 81 PROGRESS(("%lu", coff->a.tsize)); 82 if (READ(fd, coff->a.text_start, coff->a.tsize) != 83 coff->a.tsize) { 84 return 1; 85 } 86 } 87 else { 88 if (lseek(fd, coff->a.tsize, SEEK_CUR) == -1) { 89 WARN(("read text")); 90 return 1; 91 } 92 } 93 if (flags & (COUNT_TEXT|LOAD_TEXT)) { 94 pos = coff->a.text_start; 95 if (minp > pos) 96 minp = pos; 97 pos += coff->a.tsize; 98 if (maxp < pos) 99 maxp = pos; 100 } 101 } 102 103 /* Read in data. */ 104 if (coff->a.dsize != 0) { 105 if (flags & LOAD_DATA) { 106 PROGRESS(("+%lu", coff->a.dsize)); 107 if (READ(fd, coff->a.data_start, coff->a.dsize) != 108 coff->a.dsize) { 109 WARN(("read data")); 110 return 1; 111 } 112 } 113 if (flags & (COUNT_DATA|LOAD_DATA)) { 114 pos = coff->a.data_start; 115 if (minp > pos) 116 minp = pos; 117 pos += coff->a.dsize; 118 if (maxp < pos) 119 maxp = pos; 120 } 121 } 122 123 /* Zero out bss. */ 124 if (coff->a.bsize != 0) { 125 if (flags & LOAD_BSS) { 126 PROGRESS(("+%lu", coff->a.bsize)); 127 BZERO(coff->a.bss_start, coff->a.bsize); 128 } 129 if (flags & (COUNT_BSS|LOAD_BSS)) { 130 pos = coff->a.bss_start; 131 if (minp > pos) 132 minp = pos; 133 pos = coff->a.bsize; 134 if (maxp < pos) 135 maxp = pos; 136 } 137 } 138 139 marks[MARK_START] = LOADADDR(minp); 140 marks[MARK_ENTRY] = LOADADDR(coff->a.entry); 141 marks[MARK_NSYM] = 1; /* XXX: Kernel needs >= 0 */ 142 marks[MARK_SYM] = LOADADDR(maxp); 143 marks[MARK_END] = LOADADDR(maxp); 144 return 0; 145 } 146 147 #endif /* BOOT_ECOFF */ 148