16ba9413bSMike Smith /*- 26ba9413bSMike Smith * Copyright (c) 1998 Michael Smith 36ba9413bSMike Smith * All rights reserved. 46ba9413bSMike Smith * 56ba9413bSMike Smith * Redistribution and use in source and binary forms, with or without 66ba9413bSMike Smith * modification, are permitted provided that the following conditions 76ba9413bSMike Smith * are met: 86ba9413bSMike Smith * 1. Redistributions of source code must retain the above copyright 96ba9413bSMike Smith * notice, this list of conditions and the following disclaimer. 106ba9413bSMike Smith * 2. Redistributions in binary form must reproduce the above copyright 116ba9413bSMike Smith * notice, this list of conditions and the following disclaimer in the 126ba9413bSMike Smith * documentation and/or other materials provided with the distribution. 136ba9413bSMike Smith * 146ba9413bSMike Smith * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 156ba9413bSMike Smith * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 166ba9413bSMike Smith * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 176ba9413bSMike Smith * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 186ba9413bSMike Smith * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 196ba9413bSMike Smith * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 206ba9413bSMike Smith * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 216ba9413bSMike Smith * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 226ba9413bSMike Smith * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 236ba9413bSMike Smith * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 246ba9413bSMike Smith * SUCH DAMAGE. 256ba9413bSMike Smith * 266ba9413bSMike Smith * $Id$ 276ba9413bSMike Smith */ 286ba9413bSMike Smith 296ba9413bSMike Smith #include <sys/param.h> 306ba9413bSMike Smith #include <sys/kernel.h> 316ba9413bSMike Smith #include <sys/systm.h> 326ba9413bSMike Smith #include <sys/linker.h> 336ba9413bSMike Smith 346ba9413bSMike Smith /* 356ba9413bSMike Smith * Preloaded module support 366ba9413bSMike Smith */ 376ba9413bSMike Smith 386ba9413bSMike Smith caddr_t module_metadata; 396ba9413bSMike Smith 406ba9413bSMike Smith /* 416ba9413bSMike Smith * Search for the preloaded module (name) 426ba9413bSMike Smith */ 436ba9413bSMike Smith caddr_t 446ba9413bSMike Smith module_search_by_name(const char *name) 456ba9413bSMike Smith { 466ba9413bSMike Smith caddr_t curp; 476ba9413bSMike Smith u_int32_t *hdr; 486ba9413bSMike Smith 496ba9413bSMike Smith if (module_metadata != NULL) { 506ba9413bSMike Smith 516ba9413bSMike Smith curp = module_metadata; 526ba9413bSMike Smith for (;;) { 536ba9413bSMike Smith hdr = (u_int32_t *)curp; 546ba9413bSMike Smith if (hdr[0] == 0) 556ba9413bSMike Smith break; 566ba9413bSMike Smith 576ba9413bSMike Smith /* Search for a MODINFO_NAME field */ 586ba9413bSMike Smith if ((hdr[0] == MODINFO_NAME) && 596ba9413bSMike Smith !strcmp(name, curp + sizeof(u_int32_t) * 2)) 606ba9413bSMike Smith return(curp); 616ba9413bSMike Smith 626ba9413bSMike Smith /* skip to next field */ 636ba9413bSMike Smith curp += sizeof(u_int32_t) * 2 + hdr[1]; 646ba9413bSMike Smith } 656ba9413bSMike Smith } 666ba9413bSMike Smith return(NULL); 676ba9413bSMike Smith } 686ba9413bSMike Smith 696ba9413bSMike Smith /* 706ba9413bSMike Smith * Search for the first preloaded module of (type) 716ba9413bSMike Smith */ 726ba9413bSMike Smith caddr_t 736ba9413bSMike Smith module_search_by_type(const char *type) 746ba9413bSMike Smith { 756ba9413bSMike Smith caddr_t curp, lname; 766ba9413bSMike Smith u_int32_t *hdr; 776ba9413bSMike Smith 786ba9413bSMike Smith if (module_metadata != NULL) { 796ba9413bSMike Smith 806ba9413bSMike Smith curp = module_metadata; 816ba9413bSMike Smith lname = NULL; 826ba9413bSMike Smith for (;;) { 836ba9413bSMike Smith hdr = (u_int32_t *)curp; 846ba9413bSMike Smith if (hdr[0] == 0) 856ba9413bSMike Smith break; 866ba9413bSMike Smith 876ba9413bSMike Smith /* remember the start of each record */ 886ba9413bSMike Smith if (hdr[0] == MODINFO_NAME) 896ba9413bSMike Smith lname = curp; 906ba9413bSMike Smith 916ba9413bSMike Smith /* Search for a MODINFO_TYPE field */ 926ba9413bSMike Smith if ((hdr[0] == MODINFO_TYPE) && 936ba9413bSMike Smith !strcmp(type, curp + sizeof(u_int32_t) * 2)) 946ba9413bSMike Smith return(lname); 956ba9413bSMike Smith 966ba9413bSMike Smith /* skip to next field */ 976ba9413bSMike Smith curp += sizeof(u_int32_t) * 2 + hdr[1]; 986ba9413bSMike Smith } 996ba9413bSMike Smith } 1006ba9413bSMike Smith return(NULL); 1016ba9413bSMike Smith } 1026ba9413bSMike Smith 1036ba9413bSMike Smith /* 1046ba9413bSMike Smith * Given a preloaded module handle (mod), return a pointer 1056ba9413bSMike Smith * to the data for the attribute (inf). 1066ba9413bSMike Smith */ 1076ba9413bSMike Smith caddr_t 1086ba9413bSMike Smith module_search_info(caddr_t mod, int inf) 1096ba9413bSMike Smith { 1106ba9413bSMike Smith caddr_t curp; 1116ba9413bSMike Smith u_int32_t *hdr; 1126ba9413bSMike Smith u_int32_t type = 0; 1136ba9413bSMike Smith 1146ba9413bSMike Smith curp = mod; 1156ba9413bSMike Smith for (;;) { 1166ba9413bSMike Smith hdr = (u_int32_t *)curp; 1176ba9413bSMike Smith /* end of module data? */ 1186ba9413bSMike Smith if (hdr[0] == 0) 1196ba9413bSMike Smith break; 1206ba9413bSMike Smith /* 1216ba9413bSMike Smith * We give up once we've looped back to what we were looking at 1226ba9413bSMike Smith * first - this should normally be a MODINFO_NAME field. 1236ba9413bSMike Smith */ 1246ba9413bSMike Smith if (type == 0) { 1256ba9413bSMike Smith type = hdr[0]; 1266ba9413bSMike Smith } else { 1276ba9413bSMike Smith if (hdr[0] == type) 1286ba9413bSMike Smith break; 1296ba9413bSMike Smith } 1306ba9413bSMike Smith 1316ba9413bSMike Smith /* 1326ba9413bSMike Smith * Attribute match? Return pointer to data. 1336ba9413bSMike Smith * Consumer may safely assume that size value preceeds 1346ba9413bSMike Smith * data. 1356ba9413bSMike Smith */ 1366ba9413bSMike Smith if (hdr[0] == inf) 1376ba9413bSMike Smith return(curp + (sizeof(u_int32_t) * 2)); 1386ba9413bSMike Smith 1396ba9413bSMike Smith /* skip to next field */ 1406ba9413bSMike Smith curp += sizeof(u_int32_t) * 2 + hdr[1]; 1416ba9413bSMike Smith } 1426ba9413bSMike Smith return(NULL); 1436ba9413bSMike Smith } 1446ba9413bSMike Smith 145