예제 #1
0
파일: map.c 프로젝트: 1stMaster/syslinux
addr_t map_string(const char *string)
{
    if (!string)
	return 0;
    else
	return map_data(string, strlen(string) + 1, 1, 0);
}
예제 #2
0
파일: mem.c 프로젝트: 1stMaster/syslinux
void mboot_make_memmap(void)
{
    int i, nmap;
    struct AddrRangeDesc *ard;
    uint32_t lowmem, highmem;
    uint32_t highrsvd;

    /* Always report DOS memory as "lowmem", this may be overly conservative
       (e.g. if we're dropping PXE), but it should be *safe*... */

    nmap = mboot_scan_memory(&ard, &lowmem);

    highmem = 0x100000;
    highrsvd = 0xfff00000;

again:
    for (i = 0; i < nmap; i++) {
	uint64_t start, end;

	start = ard[i].BaseAddr;
	end = start + ard[i].Length;

	if (end < start)
	    end = ~0ULL;

	if (start & 0xffffffff00000000ULL)
	    continue;		/* Not interested in 64-bit memory */

	if (start < highmem)
	    start = highmem;

	if (end <= start)
	    continue;

	if (ard[i].Type == 1 && start == highmem) {
	    highmem = end;
	    goto again;
	} else if (ard[i].Type != 1 && start < highrsvd)
	    highrsvd = start;
    }

    if (highmem > highrsvd)
	highmem = highrsvd;

    mbinfo.mem_lower = lowmem >> 10;
    mbinfo.mem_upper = (highmem - 0x100000) >> 10;
    mbinfo.flags |= MB_INFO_MEMORY;

    /* The spec says this address should be +4, but Grub disagrees */
    mbinfo.mmap_addr = map_data(ard, nmap * sizeof *ard, 4, false);
    if (mbinfo.mmap_addr) {
	mbinfo.mmap_length = nmap * sizeof *ard;
	mbinfo.flags |= MB_INFO_MEM_MAP;
    }
}
예제 #3
0
void mboot_solaris_dhcp_hack(void)
{
    void *dhcpdata;
    size_t dhcplen;

    if (syslinux_derivative_info()->c.filesystem != SYSLINUX_FS_PXELINUX)
	return;
    
    if (!pxe_get_cached_info(PXENV_PACKET_TYPE_DHCP_ACK, &dhcpdata, &dhcplen)) {
	mbinfo.drives_addr = map_data(dhcpdata, dhcplen, 4, 0);
	if (mbinfo.drives_addr) {
	    mbinfo.drives_length = dhcplen;
	    mbinfo.boot_device = 0x20ffffff;
	    mbinfo.flags =
		(mbinfo.flags & ~MB_INFO_DRIVE_INFO) | MB_INFO_BOOTDEV;
	}
    }
}
예제 #4
0
int main(int argc, char** argv) {
	if (argc < 5) {
		printf("Usage: %s <image> <database> <x> <y>\n", argv[0]);
		return 1;
	}

	int bounds[4];
	unsigned int x, y;
	x = atoi(argv[3]);
	y = atoi(argv[4]);
	
	img_t* img = img_new(argv[1]);
	map_t* map = map_data(argv[2]);

	img_t* edge = img_edge(img, 3*6*6);
	img_fill_gaps(edge, 3);
	img_find_bounds(edge, x, y, 50, 50, bounds);
	img_t* sub = img_sub(img, bounds);
	//img_flood_fill(edge, x, y);
	img_to_bmp(edge, "/tmp/edge");
	img_to_bmp(sub, "/tmp/sub");

	return 0;
}
예제 #5
0
파일: fontda.c 프로젝트: LarBob/executor
OSErr AddToMasterFile(INTEGER from_file_rn, INTEGER master_file_rn)
{
  OSErr err;
  mapping_t mapping;
  INTEGER type_num, type_num_max;
  ResType type;
  Handle h;
  Str255 name;
  BOOLEAN save_resload;

  err = setup_map (from_file_rn, master_file_rn, &mapping);
  if (err == noEErr)
    {
      type_num_max = CountTypesRN (from_file_rn);
      save_resload = ResLoad;
      SetResLoad (false);
      for (type_num = 1; type_num <= type_num_max; ++type_num)
	{
	  GetIndTypeRN (from_file_rn, &type, type_num);
	  res_num_max = CountResourcesRN (from_file_rn, type);
	  for (res_num = 1; res_num <= res_num_max; ++res_num)
	    {
	      h = GetIndResourceRN (from_file_rn, type, res_num);
	      GetResInfo (h, &id, &t, name);
	      if (map_id (&id, from_file_rn, master_file_rn, &mapping))
		{
		  LoadResource(h);
		  DetachResource(h);
		  map_data (h, &mapping);
		  AddResourceRN (master_file_rn, h, type, id, name);
		}
	    }
	}
      SetResLoad (save_resload);
    }
}
int main(int argc, char *argv[])
	{
	char	fn_src[500+1], fn_dst[500+1], *opt_src, *opt_dst;
	int	fd, ft_src, ft_dst, i, stride, bytes, flag, m;
	GBM_ERR	rc;
	GBMFT	gbmft;
	GBM	gbm;
	GBMRGB	gbmrgb[0x100];
	byte	*data;
	char	*map = "none";
	byte	remap[0x100];
	double gam = 2.1, shelf = 0.0;

/*...scommand line arguments:8:*/
for ( i = 1; i < argc; i++ )
	{
	if ( argv[i][0] != '-' )
		break;
	switch ( argv[i][1] )
		{
		case 'm':
			if ( ++i == argc )
				fatal("expected map argument");
			map = argv[i];
			break;
		case 'g':
			if ( ++i == argc ) usage();
			gam = get_opt_double(argv[i], "gam");
			if ( gam < 0.1 || gam > 10.0 )
				fatal("only gammas in the range 0.1 to 10.0 are sensible");
			break;
		case 's':
			if ( ++i == argc ) usage();
			shelf = get_opt_double(argv[i], "shelf");
			break;
		default:
			usage();
			break;
		}
	}
/*...e*/

/*...sdeduce mapping and bits per pixel etc\46\:8:*/
{
int	j;

for ( j = 0; j < N_MAPINFOS; j++ )
	if ( same(map, mapinfos[j].name, strlen(map) + 1) )
		break;
if ( j == N_MAPINFOS )
	fatal("unrecognised mapping %s", map);
m = mapinfos[j].m;
}
/*...e*/

	if ( i == argc )
		usage();
	strcpy(fn_src, argv[i++]);
	strcpy(fn_dst, ( i == argc ) ? fn_src : argv[i++]);
	if ( i < argc )
		usage();

	if ( (opt_src = strchr(fn_src, ',')) != NULL )
		*opt_src++ = '\0';
	else
		opt_src = "";

	if ( (opt_dst = strchr(fn_dst, ',')) != NULL )
		*opt_dst++ = '\0';
	else
		opt_dst = "";

	gbm_init();

	if ( gbm_guess_filetype(fn_src, &ft_src) != GBM_ERR_OK )
		fatal("can't guess bitmap file format for %s", fn_src);

	if ( gbm_guess_filetype(fn_dst, &ft_dst) != GBM_ERR_OK )
		fatal("can't guess bitmap file format for %s", fn_dst);

	if ( (fd = open(fn_src, O_RDONLY | O_BINARY)) == -1 )
		fatal("can't open %s", fn_src);

	if ( (rc = gbm_read_header(fn_src, fd, ft_src, &gbm, opt_src)) != GBM_ERR_OK )
		{
		close(fd);
		fatal("can't read header of %s: %s", fn_src, gbm_err(rc));
		}

	gbm_query_filetype(ft_dst, &gbmft);
	switch ( gbm.bpp )
		{
		case 24:	flag = GBM_FT_W24;	break;
		case 8:		flag = GBM_FT_W8;	break;
		case 4:		flag = GBM_FT_W4;	break;
		case 1:		flag = GBM_FT_W1;	break;
		}
	if ( (gbmft.flags & flag) == 0 )
		{
		close(fd);
		fatal("output bitmap format %s does not support writing %d bpp data",
			gbmft.short_name, gbm.bpp);
		}

	if ( (rc = gbm_read_palette(fd, ft_src, &gbm, gbmrgb)) != GBM_ERR_OK )
		{
		close(fd);
		fatal("can't read palette of %s: %s", fn_src, gbm_err(rc));
		}

	stride = ( ((gbm.w * gbm.bpp + 31)/32) * 4 );
	bytes = stride * gbm.h;
	if ( (data = malloc(bytes)) == NULL )
		{
		close(fd);
		fatal("out of memory allocating %d bytes for bitmap", bytes);
		}

	if ( (rc = gbm_read_data(fd, ft_src, &gbm, data)) != GBM_ERR_OK )
		{
		close(fd);
		fatal("can't read bitmap data of %s: %s", fn_src, gbm_err(rc));
		}

	close(fd);

	map_compute(m, remap, gam, shelf);

	if ( gbm.bpp == 24 )
		map_data(data, gbm.w, gbm.h, remap);
	else
		map_palette(gbmrgb, 1 << gbm.bpp, remap);

	if ( (fd = open(fn_dst, O_CREAT | O_TRUNC | O_WRONLY | O_BINARY, S_IREAD | S_IWRITE)) == -1 )
		fatal("can't create %s", fn_dst);

	if ( (rc = gbm_write(fn_dst, fd, ft_dst, &gbm, gbmrgb, data, opt_dst)) != GBM_ERR_OK )
		{
		close(fd);
		remove(fn_dst);
		fatal("can't write %s: %s", fn_dst, gbm_err(rc));
		}

	close(fd);

	free(data);

	gbm_deinit();

	return 0;
	}
예제 #7
0
파일: map.c 프로젝트: 1stMaster/syslinux
struct multiboot_header *map_image(void *ptr, size_t len)
{
    struct multiboot_header *mbh;
    int mbh_len;
    char *cptr = ptr;
    Elf32_Ehdr *eh = ptr;
    Elf32_Phdr *ph;
    Elf32_Shdr *sh;
    unsigned int i, mbh_offset;
    uint32_t bad_flags;

    /*
     * Search for the multiboot header...
     */
    mbh_len = 0;
    for (mbh_offset = 0; mbh_offset < MULTIBOOT_SEARCH; mbh_offset += 4) {
	mbh = (struct multiboot_header *)((char *)ptr + mbh_offset);
	if (mbh->magic != MULTIBOOT_MAGIC)
	    continue;
	if (mbh->magic + mbh->flags + mbh->checksum)
	    continue;
	if (mbh->flags & MULTIBOOT_VIDEO_MODE)
	    mbh_len = 48;
	else if (mbh->flags & MULTIBOOT_AOUT_KLUDGE)
	    mbh_len = 32;
	else
	    mbh_len = 12;

	if (mbh_offset + mbh_len > len)
	    mbh_len = 0;	/* Invalid... */
	else
	    break;		/* Found something... */
    }

    if (mbh_len) {
	bad_flags = mbh->flags & MULTIBOOT_UNSUPPORTED;
	if (bad_flags) {
	    printf("Unsupported Multiboot flags set: %#x\n", bad_flags);
	    return NULL;
	}
    }

    if (len < sizeof(Elf32_Ehdr) ||
	memcmp(eh->e_ident, "\x7f" "ELF\1\1\1", 6) ||
	(eh->e_machine != EM_386 && eh->e_machine != EM_486 &&
	 eh->e_machine != EM_X86_64) ||
	eh->e_version != EV_CURRENT ||
	eh->e_ehsize < sizeof(Elf32_Ehdr) || eh->e_ehsize >= len ||
	eh->e_phentsize < sizeof(Elf32_Phdr) ||
	!eh->e_phnum || eh->e_phoff + eh->e_phentsize * eh->e_phnum > len)
	eh = NULL;		/* No valid ELF header found */

    /* Is this a Solaris kernel? */
    if (!set.solaris && eh && kernel_is_solaris(eh))
	opt.solaris = true;

    /*
     * Note: the Multiboot Specification implies that AOUT_KLUDGE should
     * have precedence over the ELF header.  However, Grub disagrees, and
     * Grub is "the reference bootloader" for the Multiboot Specification.
     * This is insane, since it makes the AOUT_KLUDGE bit functionally
     * useless, but at least Solaris apparently depends on this behavior.
     */
    if (eh && !(opt.aout && mbh_len && (mbh->flags & MULTIBOOT_AOUT_KLUDGE))) {
	regs.eip = eh->e_entry;	/* Can be overridden further down... */

	ph = (Elf32_Phdr *) (cptr + eh->e_phoff);

	for (i = 0; i < eh->e_phnum; i++) {
	    if (ph->p_type == PT_LOAD || ph->p_type == PT_PHDR) {
		/*
		 * This loads at p_paddr, which matches Grub.  However, if
		 * e_entry falls within the p_vaddr range of this PHDR, then
		 * adjust it to match the p_paddr range... this is how Grub
		 * behaves, so it's by definition correct (it doesn't have to
		 * make sense...)
		 */
		addr_t addr = ph->p_paddr;
		addr_t msize = ph->p_memsz;
		addr_t dsize = min(msize, ph->p_filesz);

		if (eh->e_entry >= ph->p_vaddr
		    && eh->e_entry < ph->p_vaddr + msize)
		    regs.eip = eh->e_entry + (ph->p_paddr - ph->p_vaddr);

		dprintf("Segment at 0x%08x data 0x%08x len 0x%08x\n",
			addr, dsize, msize);

		if (syslinux_memmap_type(amap, addr, msize) != SMT_FREE) {
		    printf
			("Memory segment at 0x%08x (len 0x%08x) is unavailable\n",
			 addr, msize);
		    return NULL;	/* Memory region unavailable */
		}

		/* Mark this region as allocated in the available map */
		if (syslinux_add_memmap(&amap, addr, msize, SMT_ALLOC)) {
		    error("Overlapping segments found in ELF header\n");
		    return NULL;
		}

		if (ph->p_filesz) {
		    /* Data present region.  Create a move entry for it. */
		    if (syslinux_add_movelist
			(&ml, addr, (addr_t) cptr + ph->p_offset, dsize)) {
			error("Failed to map PHDR data\n");
			return NULL;
		    }
		}
		if (msize > dsize) {
		    /* Zero-filled region.  Mark as a zero region in the memory map. */
		    if (syslinux_add_memmap
			(&mmap, addr + dsize, msize - dsize, SMT_ZERO)) {
			error("Failed to map PHDR zero region\n");
			return NULL;
		    }
		}
		if (addr + msize > mboot_high_water_mark)
		    mboot_high_water_mark = addr + msize;
	    } else {
		/* Ignore this program header */
	    }

	    ph = (Elf32_Phdr *) ((char *)ph + eh->e_phentsize);
	}

	/* Load the ELF symbol table */
	if (eh->e_shoff) {
	    addr_t addr, len;

	    sh = (Elf32_Shdr *) ((char *)eh + eh->e_shoff);

	    len = eh->e_shentsize * eh->e_shnum;
	    /*
	     * Align this, but don't pad -- in general this means a bunch of
	     * smaller sections gets packed into a single page.
	     */
	    addr = map_data(sh, len, 4096, MAP_HIGH | MAP_NOPAD);
	    if (!addr) {
		error("Failed to map symbol table\n");
		return NULL;
	    }

	    mbinfo.flags |= MB_INFO_ELF_SHDR;
	    mbinfo.syms.e.addr = addr;
	    mbinfo.syms.e.num = eh->e_shnum;
	    mbinfo.syms.e.size = eh->e_shentsize;
	    mbinfo.syms.e.shndx = eh->e_shstrndx;

	    for (i = 0; i < eh->e_shnum; i++) {
		addr_t align;

		if (!sh[i].sh_size)
		    continue;	/* Empty section */
		if (sh[i].sh_flags & SHF_ALLOC)
		    continue;	/* SHF_ALLOC sections should have PHDRs */

		align = sh[i].sh_addralign ? sh[i].sh_addralign : 0;
		addr = map_data((char *)ptr + sh[i].sh_offset, sh[i].sh_size,
				align, MAP_HIGH);
		if (!addr) {
		    error("Failed to map symbol section\n");
		    return NULL;
		}
		sh[i].sh_addr = addr;
	    }
	}
    } else if (mbh_len && (mbh->flags & MULTIBOOT_AOUT_KLUDGE)) {
	/*
	 * a.out kludge thing...
	 */
	char *data_ptr;
	addr_t data_len, bss_len;
	addr_t bss_addr;

	regs.eip = mbh->entry_addr;

	data_ptr = (char *)mbh - (mbh->header_addr - mbh->load_addr);

	if (mbh->load_end_addr)
	    data_len = mbh->load_end_addr - mbh->load_addr;
	else
	    data_len = len - mbh_offset + (mbh->header_addr - mbh->load_addr);

	bss_addr = mbh->load_addr + data_len;

	if (mbh->bss_end_addr)
	    bss_len = mbh->bss_end_addr - mbh->load_end_addr;
	else
	    bss_len = 0;

	if (syslinux_memmap_type(amap, mbh->load_addr, data_len + bss_len)
	    != SMT_FREE) {
	    printf("Memory segment at 0x%08x (len 0x%08x) is unavailable\n",
		   mbh->load_addr, data_len + bss_len);
	    return NULL;		/* Memory region unavailable */
	}
	if (syslinux_add_memmap(&amap, mbh->load_addr,
				data_len + bss_len, SMT_ALLOC)) {
	    error("Failed to claim a.out address space!\n");
	    return NULL;
	}
	if (data_len)
	    if (syslinux_add_movelist(&ml, mbh->load_addr, (addr_t) data_ptr,
				      data_len)) {
		error("Failed to map a.out data\n");
		return NULL;
	    }
	if (bss_len)
	    if (syslinux_add_memmap
		(&mmap, bss_addr, bss_len, SMT_ZERO)) {
		error("Failed to map a.out bss\n");
		return NULL;
	    }
	if (bss_addr + bss_len > mboot_high_water_mark)
	    mboot_high_water_mark = bss_addr + bss_len;
    } else {
	error
	    ("Invalid Multiboot image: neither ELF header nor a.out kludge found\n");
	return NULL;
    }

    return mbh;
}
예제 #8
0
void set_graphics_mode(const struct multiboot_header *mbh,
		       struct multiboot_info *mbi)
{
    com32sys_t rm;
    uint16_t mode, bestmode, *mode_ptr;
    struct vesa_general_info *gi;
    struct vesa_mode_info *mi;
    int pxf, bestpxf;
    int wantx, wanty;
    int err, besterr;
    bool better;
    addr_t viaddr;

    /* Only do this if requested by the OS image */
    if (!(mbh->flags & MULTIBOOT_VIDEO_MODE) || mbh->mode_type != 0)
	return;

    gi = lmalloc(sizeof *gi);
    if (!gi)
	return;

    mi = lmalloc(sizeof *mi);
    if (!mi)
	goto out;

    memset(&rm, 0, sizeof rm);
    memset(gi, 0, sizeof *gi);

    gi->signature = VBE2_MAGIC;	/* Get VBE2 extended data */
    rm.eax.w[0] = 0x4F00;	/* Get SVGA general information */
    rm.edi.w[0] = OFFS(gi);
    rm.es = SEG(gi);
    __intcall(0x10, &rm, &rm);

    if (rm.eax.w[0] != 0x004F)
	goto out;		/* Function call failed */
    if (gi->signature != VESA_MAGIC)
	goto out;		/* No magic */
    if (gi->version < 0x0102)
	goto out;		/* VESA 1.2+ required */

    memcpy(&vesa_info.gi, gi, sizeof *gi);

    /* Search for a suitable mode with a suitable color and memory model... */

    mode_ptr = GET_PTR(gi->video_mode_ptr);
    bestmode = 0;
    bestpxf = 0;
    wantx = mbh->width  ? mbh->width  : 0xffff;
    wanty = mbh->height ? mbh->height : 0xffff;
    besterr = wantx + wanty;

    while ((mode = *mode_ptr++) != 0xFFFF) {
	mode &= 0x1FF;		/* The rest are attributes of sorts */

        memset(&rm, 0, sizeof rm);
	memset(mi, 0, sizeof *mi);
	rm.eax.w[0] = 0x4F01;	/* Get SVGA mode information */
	rm.ecx.w[0] = mode;
	rm.edi.w[0] = OFFS(mi);
	rm.es = SEG(mi);
	__intcall(0x10, &rm, &rm);

	/* Must be a supported mode */
	if (rm.eax.w[0] != 0x004f)
	    continue;

	/* Must be an LFB color graphics mode supported by the hardware.

	   The bits tested are:
	   7 - linear frame buffer
	   4 - graphics mode
	   3 - color mode
	   1 - mode information available (mandatory in VBE 1.2+)
	   0 - mode supported by hardware
	 */
	if ((mi->mode_attr & 0x009b) != 0x009b)
	    continue;

	/* We don't support multibank (interlaced memory) modes */
	/*
	 *  Note: The Bochs VESA BIOS (vbe.c 1.58 2006/08/19) violates the
	 * specification which states that banks == 1 for unbanked modes;
	 * fortunately it does report bank_size == 0 for those.
	 */
	if (mi->banks > 1 && mi->bank_size)
	    continue;

	/* Must either be a packed-pixel mode or a direct color mode
	   (depending on VESA version ); must be a supported pixel format */

	if (mi->bpp == 32 &&
	    (mi->memory_layout == 4 ||
	     (mi->memory_layout == 6 && mi->rpos == 16 && mi->gpos == 8 &&
	      mi->bpos == 0)))
	    pxf = 32;
	else if (mi->bpp == 24 &&
		 (mi->memory_layout == 4 ||
		  (mi->memory_layout == 6 && mi->rpos == 16 && mi->gpos == 8 &&
		   mi->bpos == 0)))
	    pxf = 24;
	else if (mi->bpp == 16 &&
		 (mi->memory_layout == 4 ||
		  (mi->memory_layout == 6 && mi->rpos == 11 && mi->gpos == 5 &&
		   mi->bpos == 0)))
	    pxf = 16;
	else if (mi->bpp == 15 &&
		 (mi->memory_layout == 4 ||
		  (mi->memory_layout == 6 && mi->rpos == 10 && mi->gpos == 5 &&
		   mi->bpos == 0)))
	    pxf = 15;
	else
	    continue;

	better = false;
	err = abs(mi->h_res - wantx) + abs(mi->v_res - wanty);

#define IS_GOOD(mi, bestx, besty) \
	((mi)->h_res >= (bestx) && (mi)->v_res >= (besty))

	if (!bestpxf)
	    better = true;
	else if (!IS_GOOD(&vesa_info.mi, wantx, wanty) &&
		 IS_GOOD(mi, wantx, wanty))
	    /* This matches criteria, which the previous one didn't */
	    better = true;
	else if (IS_GOOD(&vesa_info.mi, wantx, wanty) &&
		 !IS_GOOD(mi, wantx, wanty))
	    /* This doesn't match criteria, and the previous one did */
	    better = false;
	else if (err < besterr)
	    better = true;
	else if (err == besterr && (pxf == (int)mbh->depth || pxf > bestpxf))
	    better = true;

	if (better) {
	    bestmode = mode;
	    bestpxf = pxf;
	    memcpy(&vesa_info.mi, mi, sizeof *mi);
	}
    }

    if (!bestpxf)
	goto out;		/* No mode found */

    mi = &vesa_info.mi;
    mode = bestmode;

    /* Now set video mode */
    memset(&rm, 0, sizeof rm);
    rm.eax.w[0] = 0x4F02;	/* Set SVGA video mode */
    mode |= 0x4000;		/* Request linear framebuffer */
    rm.ebx.w[0] = mode;
    __intcall(0x10, &rm, &rm);
    if (rm.eax.w[0] != 0x004F)
	goto out;		/* Failed to set mode */

    mbi->flags |= MB_INFO_VIDEO_INFO;
    mbi->vbe_mode = mode;
    viaddr = map_data(&vesa_info, sizeof vesa_info, 4, 0);
    mbi->vbe_control_info = viaddr + offsetof(struct vesa_info, gi);
    mbi->vbe_mode_info = viaddr + offsetof(struct vesa_info, mi);

    /* Get the VBE 2.x PM entry point if supported */
    rm.eax.w[0] = 0x4F0A;
    rm.ebx.w[0] = 0;
    __intcall(0x10, &rm, &rm);
    if (rm.eax.w[0] == 0x004F) {
	mbi->vbe_interface_seg = rm.es;
	mbi->vbe_interface_off = rm.edi.w[0];
	mbi->vbe_interface_len = rm.ecx.w[0];
    }

    /* In theory this should be:
     *
     * UsingVga = (mi->mode_attr & 4) ? 0x0007 : 0x000f;
     *
     * However, that would assume all systems that claim to handle text
     * output in VESA modes actually do that...
     */
    graphics_using_vga(0x0F, vesa_info.mi.h_res, vesa_info.mi.v_res);

out:
    lfree(mi);
    lfree(gi);
}