1/* 2 * Copyright (c) 1991, 1992 Paul Kranenburg <pk@cs.few.eur.nl> 3 * Copyright (c) 1993 Branko Lankester <branko@hacktic.nl> 4 * Copyright (c) 1993, 1994, 1995, 1996 Rick Sladkey <jrs@world.std.com> 5 * Copyright (c) 1996-1999 Wichert Akkerman <wichert@cistron.nl> 6 * All rights reserved. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions 10 * are met: 11 * 1. Redistributions of source code must retain the above copyright 12 * notice, this list of conditions and the following disclaimer. 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 31#include "defs.h" 32#include <fcntl.h> 33#include <sys/stat.h> 34#include <sys/wait.h> 35#include <sys/resource.h> 36#include <sys/utsname.h> 37#include <sys/user.h> 38 39/* Bits of module.flags. */ 40 41#define MOD_UNINITIALIZED 0 42#define MOD_RUNNING 1 43#define MOD_DELETED 2 44#define MOD_AUTOCLEAN 4 45#define MOD_VISITED 8 46#define MOD_USED_ONCE 16 47#define MOD_JUST_FREED 32 48#define MOD_INITIALIZING 64 49 50/* Values for query_module's which. */ 51 52#define QM_MODULES 1 53#define QM_DEPS 2 54#define QM_REFS 3 55#define QM_SYMBOLS 4 56#define QM_INFO 5 57 58struct module_symbol 59{ 60 unsigned long value; 61 const char *name; 62}; 63 64struct module_info 65{ 66 unsigned long addr; 67 unsigned long size; 68 unsigned long flags; 69 long usecount; 70}; 71 72#include "xlat/qm_which.h" 73#include "xlat/modflags.h" 74#include "xlat/delete_module_flags.h" 75 76int 77sys_query_module(struct tcb *tcp) 78{ 79 if (entering(tcp)) { 80 printstr(tcp, tcp->u_arg[0], -1); 81 tprints(", "); 82 printxval(qm_which, tcp->u_arg[1], "QM_???"); 83 tprints(", "); 84 } else { 85 size_t ret; 86 87 if (!verbose(tcp) || syserror(tcp) || 88 umove(tcp, tcp->u_arg[4], &ret) < 0) { 89 tprintf("%#lx, %lu, %#lx", tcp->u_arg[2], 90 tcp->u_arg[3], tcp->u_arg[4]); 91 } else if (tcp->u_arg[1]==QM_INFO) { 92 struct module_info mi; 93 if (umove(tcp, tcp->u_arg[2], &mi) < 0) { 94 tprintf("%#lx, ", tcp->u_arg[2]); 95 } else { 96 tprintf("{address=%#lx, size=%lu, flags=", 97 mi.addr, mi.size); 98 printflags(modflags, mi.flags, "MOD_???"); 99 tprintf(", usecount=%lu}, ", mi.usecount); 100 } 101 tprintf("%lu", (unsigned long)ret); 102 } else if ((tcp->u_arg[1]==QM_MODULES) || 103 (tcp->u_arg[1]==QM_DEPS) || 104 (tcp->u_arg[1]==QM_REFS)) { 105 tprints("{"); 106 if (!abbrev(tcp)) { 107 char* data = malloc(tcp->u_arg[3]); 108 char* mod = data; 109 size_t idx; 110 111 if (!data) { 112 fprintf(stderr, "out of memory\n"); 113 tprintf(" /* %lu entries */ ", (unsigned long)ret); 114 } else { 115 if (umoven(tcp, tcp->u_arg[2], 116 tcp->u_arg[3], data) < 0) { 117 tprintf(" /* %lu entries */ ", (unsigned long)ret); 118 } else { 119 for (idx = 0; idx < ret; idx++) { 120 tprintf("%s%s", 121 (idx ? ", " : ""), 122 mod); 123 mod += strlen(mod)+1; 124 } 125 } 126 free(data); 127 } 128 } else 129 tprintf(" /* %lu entries */ ", (unsigned long)ret); 130 tprintf("}, %lu", (unsigned long)ret); 131 } else if (tcp->u_arg[1]==QM_SYMBOLS) { 132 tprints("{"); 133 if (!abbrev(tcp)) { 134 char* data = malloc(tcp->u_arg[3]); 135 struct module_symbol* sym = (struct module_symbol*)data; 136 size_t idx; 137 138 if (!data) { 139 fprintf(stderr, "out of memory\n"); 140 tprintf(" /* %lu entries */ ", (unsigned long)ret); 141 } else { 142 if (umoven(tcp, tcp->u_arg[2], 143 tcp->u_arg[3], data) < 0) { 144 tprintf(" /* %lu entries */ ", (unsigned long)ret); 145 } else { 146 for (idx = 0; idx < ret; idx++) { 147 tprintf("%s{name=%s, value=%lu}", 148 (idx ? " " : ""), 149 data+(long)sym->name, 150 sym->value); 151 sym++; 152 } 153 } 154 free(data); 155 } 156 } else 157 tprintf(" /* %lu entries */ ", (unsigned long)ret); 158 tprintf("}, %ld", (unsigned long)ret); 159 } else { 160 printstr(tcp, tcp->u_arg[2], tcp->u_arg[3]); 161 tprintf(", %#lx", tcp->u_arg[4]); 162 } 163 } 164 return 0; 165} 166 167int 168sys_create_module(struct tcb *tcp) 169{ 170 if (entering(tcp)) { 171 printpath(tcp, tcp->u_arg[0]); 172 tprintf(", %lu", tcp->u_arg[1]); 173 } 174 return RVAL_HEX; 175} 176 177int 178sys_delete_module(struct tcb *tcp) 179{ 180 if (entering(tcp)) { 181 printstr(tcp, tcp->u_arg[0], -1); 182 tprints(", "); 183 printflags(delete_module_flags, tcp->u_arg[1], "O_???"); 184 } 185 return 0; 186} 187 188int 189sys_init_module(struct tcb *tcp) 190{ 191 if (entering(tcp)) { 192 tprintf("%#lx, %lu, ", tcp->u_arg[0], tcp->u_arg[1]); 193 printstr(tcp, tcp->u_arg[2], -1); 194 } 195 return 0; 196} 197 198#define MODULE_INIT_IGNORE_MODVERSIONS 1 199#define MODULE_INIT_IGNORE_VERMAGIC 2 200 201#include "xlat/module_init_flags.h" 202 203int 204sys_finit_module(struct tcb *tcp) 205{ 206 if (exiting(tcp)) 207 return 0; 208 209 /* file descriptor */ 210 printfd(tcp, tcp->u_arg[0]); 211 tprints(", "); 212 /* param_values */ 213 printstr(tcp, tcp->u_arg[1], -1); 214 tprints(", "); 215 /* flags */ 216 printflags(module_init_flags, tcp->u_arg[2], "MODULE_INIT_???"); 217 218 return 0; 219} 220