void efi_getsmap(void) { UINTN size, desc_size, key; EFI_MEMORY_DESCRIPTOR *efi_mmap, *p; EFI_PHYSICAL_ADDRESS addr; EFI_STATUS status; STAILQ_HEAD(smap_head, smap_buf) head = STAILQ_HEAD_INITIALIZER(head); struct smap_buf *cur, *next; int i, n, ndesc; int type = -1; size = 0; efi_mmap = NULL; status = BS->GetMemoryMap(&size, efi_mmap, &key, &desc_size, NULL); efi_mmap = malloc(size); status = BS->GetMemoryMap(&size, efi_mmap, &key, &desc_size, NULL); if (EFI_ERROR(status)) { printf("GetMemoryMap: error %lu\n", EFI_ERROR_CODE(status)); free(efi_mmap); return; } STAILQ_INIT(&head); n = 0; i = 0; p = efi_mmap; next = NULL; ndesc = size / desc_size; while (i < ndesc) { if (next == NULL) { next = malloc(sizeof(*next)); if (next == NULL) break; next->sb_smap.base = p->PhysicalStart; next->sb_smap.length = p->NumberOfPages << EFI_PAGE_SHIFT; /* * ACPI 6.1 tells the lower memory should be * reported as normal memory, so we enforce * page 0 type even as vmware maps it as * acpi reclaimable. */ if (next->sb_smap.base == 0) type = SMAP_TYPE_MEMORY; else type = smap_type(p->Type); next->sb_smap.type = type; STAILQ_INSERT_TAIL(&head, next, sb_bufs); n++; p = NextMemoryDescriptor(p, desc_size); i++; continue; } addr = next->sb_smap.base + next->sb_smap.length; if ((smap_type(p->Type) == type) && (p->PhysicalStart == addr)) { next->sb_smap.length += (p->NumberOfPages << EFI_PAGE_SHIFT); p = NextMemoryDescriptor(p, desc_size); i++; } else next = NULL; } smaplen = n; if (smaplen > 0) { smapbase = malloc(smaplen * sizeof(*smapbase)); if (smapbase != NULL) { n = 0; STAILQ_FOREACH(cur, &head, sb_bufs) smapbase[n++] = cur->sb_smap; } cur = STAILQ_FIRST(&head); while (cur != NULL) { next = STAILQ_NEXT(cur, sb_bufs); free(cur); cur = next; } } free(efi_mmap); }
int main(int argc, char *argv[]) { FILE *in, *out; char *str; int i; size_t len; char *strp; char *modules[MAXMODULES]; int num_modules = 0; STAILQ_HEAD(includehead, include) includes = STAILQ_HEAD_INITIALIZER(includes); include *inc; int isam = 0; int linecont = 0; if (argc != 3) { fprintf(stderr, "Usage: %s <module.in> <Makefile[.am]>\n", argv[0]); return EXIT_FAILURE; } str = malloc(MAXLINE); /* Starting with initial input Makefile, look for include <file> or * YASM_MODULES += <module>. Note this currently doesn't handle * a relative starting path. */ len = strlen(argv[2]); inc = malloc(sizeof(include)); inc->filename = malloc(len+1); strcpy(inc->filename, argv[2]); STAILQ_INSERT_TAIL(&includes, inc, link); isam = argv[2][len-2] == 'a' && argv[2][len-1] == 'm'; while (!STAILQ_EMPTY(&includes)) { inc = STAILQ_FIRST(&includes); STAILQ_REMOVE_HEAD(&includes, link); in = fopen(inc->filename, "rt"); if (!in) { fprintf(stderr, "Could not open `%s'.\n", inc->filename); return EXIT_FAILURE; } free(inc->filename); free(inc); while (fgets(str, MAXLINE, in)) { /* Strip off any trailing whitespace */ len = strlen(str); if (len > 0) { strp = &str[len-1]; while (len > 0 && isspace(*strp)) { *strp-- = '\0'; len--; } } strp = str; /* Skip whitespace */ while (isspace(*strp)) strp++; /* Skip comments */ if (*strp == '#') continue; /* If line continuation, skip to continue copy */ if (linecont) goto keepgoing; /* Check for include if original input is .am file */ if (isam && strncmp(strp, "include", 7) == 0 && isspace(strp[7])) { strp += 7; while (isspace(*strp)) strp++; /* Build new include and add to end of list */ inc = malloc(sizeof(include)); inc->filename = malloc(strlen(strp)+1); strcpy(inc->filename, strp); STAILQ_INSERT_TAIL(&includes, inc, link); continue; } /* Check for YASM_MODULES = or += */ if (strncmp(strp, "YASM_MODULES", 12) != 0) continue; strp += 12; while (isspace(*strp)) strp++; if (strncmp(strp, "+=", 2) != 0 && *strp != '=') continue; if (*strp == '+') strp++; strp++; while (isspace(*strp)) strp++; keepgoing: /* Check for continuation */ if (len > 0 && str[len-1] == '\\') { str[len-1] = '\0'; while (isspace(*strp)) *strp-- = '\0'; linecont = 1; } else linecont = 0; while (*strp != '\0') { /* Copy module name */ modules[num_modules] = malloc(MAXNAME); len = 0; while (*strp != '\0' && !isspace(*strp)) modules[num_modules][len++] = *strp++; modules[num_modules][len] = '\0'; num_modules++; while (isspace(*strp)) strp++; } } fclose(in); } out = fopen(OUTPUT, "wt"); if (!out) { fprintf(stderr, "Could not open `%s'.\n", OUTPUT); return EXIT_FAILURE; } fprintf(out, "/* This file auto-generated by genmodule.c" " - don't edit it */\n\n"); in = fopen(argv[1], "rt"); if (!in) { fprintf(stderr, "Could not open `%s'.\n", argv[1]); fclose(out); remove(OUTPUT); return EXIT_FAILURE; } len = 0; while (fgets(str, MAXLINE, in)) { if (strncmp(str, "MODULES_", 8) == 0) { len = 0; strp = str+8; while (*strp != '\0' && *strp != '_') { len++; strp++; } *strp = '\0'; for (i=0; i<num_modules; i++) { if (strncmp(modules[i], str+8, len) == 0) { fprintf(out, " {\"%s\", &yasm_%s_LTX_%s},\n", modules[i]+len+1, modules[i]+len+1, str+8); } } } else if (strncmp(str, "EXTERN_LIST", 11) == 0) { for (i=0; i<num_modules; i++) { strcpy(str, modules[i]); strp = str; while (*strp != '\0' && *strp != '_') strp++; *strp++ = '\0'; fprintf(out, "extern yasm_%s_module yasm_%s_LTX_%s;\n", str, strp, str); } } else fputs(str, out); } fclose(in); fclose(out); for (i=0; i<num_modules; i++) free(modules[i]); free(str); return EXIT_SUCCESS; }
void bios_getsmap(void) { struct smap_buf buf; STAILQ_HEAD(smap_head, smap_buf) head = STAILQ_HEAD_INITIALIZER(head); struct smap_buf *cur, *next; u_int n, x; STAILQ_INIT(&head); n = 0; x = 0; v86.ebx = 0; do { v86.ctl = V86_FLAGS; v86.addr = 0x15; v86.eax = 0xe820; /* int 0x15 function 0xe820 */ v86.ecx = SMAP_BUFSIZE; v86.edx = SMAP_SIG; v86.es = VTOPSEG(&buf); v86.edi = VTOPOFF(&buf); v86int(); if (V86_CY(v86.efl) || v86.eax != SMAP_SIG || v86.ecx < sizeof(buf.smap) || v86.ecx > SMAP_BUFSIZE) break; next = malloc(sizeof(*next)); if (next == NULL) break; next->smap = buf.smap; if (v86.ecx == SMAP_BUFSIZE) { next->xattr = buf.xattr; x++; } STAILQ_INSERT_TAIL(&head, next, bufs); n++; } while (v86.ebx != 0); smaplen = n; if (smaplen > 0) { smapbase = malloc(smaplen * sizeof(*smapbase)); if (smapbase != NULL) { n = 0; STAILQ_FOREACH(cur, &head, bufs) smapbase[n++] = cur->smap; } if (smaplen == x) { smapattr = malloc(smaplen * sizeof(*smapattr)); if (smapattr != NULL) { n = 0; STAILQ_FOREACH(cur, &head, bufs) smapattr[n++] = cur->xattr & SMAP_XATTR_MASK; } } else smapattr = NULL; cur = STAILQ_FIRST(&head); while (cur != NULL) { next = STAILQ_NEXT(cur, bufs); free(cur); cur = next; } } }