⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 tfsloader.c

📁 umon bootloader source code, support mips cpu.
💻 C
📖 第 1 页 / 共 2 页
字号:
		/* If incoming section name is specified, then we only load the
		 * section with that name...
		 */
		if ((sname != 0) && (strcmp(sname,name) != 0))
			continue;
	
		if ((verbose) && (ehdr->e_shstrndx != SHN_UNDEF))
			showSection(shname_strings + shdr->sh_name);
	
		if (!(shdr->sh_flags & SHF_ALLOC)) {
			notproctot += size;
			if (verbose)
				printf("     %7ld bytes not processed (tot=%ld)\n",
					size,notproctot);
			continue;
		}

		sh_addr = shdr->sh_addr;

		/* Look to the program header to see if the destination address
		 * of this section needs to be adjusted.  If this section is
		 * within a program header and that program header's members
		 * p_vaddr & p_paddr are not equal, then adjust the section
		 * address based on the delta between p_vaddr and p_paddr...
		 */ 
		phdr = (ELFPHDR *)((int)ehdr + ehdr->e_phoff);
		for (j=0;j<ehdr->e_phnum;j++,phdr++) {
			if ((phdr->p_type == PT_LOAD) &&
				(sh_addr >= phdr->p_vaddr) &&
				(sh_addr < phdr->p_vaddr+phdr->p_filesz) &&
				(phdr->p_vaddr != phdr->p_paddr)) {
					sh_addr += (phdr->p_paddr - phdr->p_vaddr);
					break;
			}
		}
	
		if (shdr->sh_type == SHT_NOBITS) {
			if (s_memset((char *)(sh_addr),0,size,
				verbose,verifyonly) != 0)
				err++;
		}
		else {
#if INCLUDE_UNZIP
			if (TFS_ISCPRS(fp)) {
				int		outsize;

				outsize = decompress((char *)(ehdr)+shdr->sh_offset,size,
					(char *)sh_addr);
				if (outsize == -1) {
					err++;
					continue;
				}
				if (verbose) {
					printf("dcmp %7d bytes from 0x%08lx to 0x%08lx\n",
						outsize,(ulong)(ehdr)+shdr->sh_offset,sh_addr);
				}
			}
			else
#endif
			{
				if (tfsld_memcpy((char *)(sh_addr),
					(char *)((int)ehdr+shdr->sh_offset),
					size,verbose,verifyonly) != 0)
					err++;
			}
			/* Flush caches for each loadable section... */
			flushDcache((char *)sh_addr,size);
			invalidateIcache((char *)sh_addr,size);
		}
	}

	if (err)
		return(TFSERR_MEMFAIL);

	if (verbose && !verifyonly && !sname)
		showEntrypoint(ehdr->e_entry);

	/* Store entry point: */
	if (entrypoint)
		*entrypoint = (long)(ehdr->e_entry);

	return(TFS_OKAY);
}

#endif

#if TFS_EBIN_ELFMSBIN | TFS_EBIN_MSBIN

/* tfsloadmsbin():
 * This loader is a bit different than the others.
 * The model for AOUT, COFF & ELF is simply to load each section from
 * the stored location in flash to the location specifed by the section
 * header.  The sections may be compressed.
 * The MSBIN loader supports a few additional options because of the
 * fact that WinCE files can be formatted as .bin or .nbo.  When
 * the file is the ".bin" type, then this loader is used similar to
 * the AOUT, COFF & ELF loaders. When the file is the ".nbo" type, 
 * then it is simply loaded into the starting address of the target's
 * DRAM and the entrypoint is that base address.
 * To support this scheme, TFS uses both the 'c' flag (compressed)
 * and the extension on the filename as follows...
 * 
 * 1 filename.bin with 'c' flag inactive:
 *	 Load the file as specified by the sections within the file
 *	 header.
 * 2 filename.bin with 'c' flag active:
 *	 Load the file as specified by the sections within the file
 *	 header and assume each section is compressed.
 * 3 filename.nbo with 'c' flag inactive:
 *	 Copy the entire content of the file from TFS flash space to
 *	 APPRAMBASE and return the address APPRAMBASE as the entrypoint.
 * 4 filename.nbo with 'c' flag active:
 *	 Decompress the entire content of the file from TFS flash space
 *	 to APPRAMBASE and return the address APPRAMBASE as the entrypoint.
 *
 *	In three of the 4 cases above (1,2&3) some level of sanity checking
 *	can be done on the file prior to beginning the load.  For the 4th
 *	case there is no sanity check, this function assumes the file is
 *	compressed and is destined for the base of DRAM.
 */
int
tfsloadmsbin(TFILE *fp,int verbose,long *entrypoint,char *sname,int verifyonly)
{
	ulong		offset;
	MSBINFHDR	filhdr;
	MSBINSHDR	scnhdr;
	char		*dot;
	int			err, snum;

	if (tfsTrace)
		printf("tfsloadmsbin(%s)\n",TFS_NAME(fp));

	dot = strrchr(TFS_NAME(fp),'.');
	if (!dot)
		return(TFSERR_BADEXTENSION);
	
	/* Check the filename extension for ".bin" or ".nbo" and process
	 * accordingly...
	 */
	if (strcmp(dot,".bin") == 0) {
#if INCLUDE_UNZIP
		if (TFS_ISCPRS(fp)) {
			return(TFSERR_NOTAVAILABLE);
		}
#endif
		/* Verify basic file sanity... */
		if (memcmp((char *)TFS_BASE(fp),MSBIN_SYNC_DATA,MSBIN_SYNC_SIZE) != 0)
			return(TFSERR_BADHDR);

		/* The file header is at offset MSBIN_SYNC_SIZE in the 
		 * file, so copy it from the file to a local structure...
		 */
		memcpy((char *)&filhdr,(TFS_BASE(fp) + MSBIN_SYNC_SIZE),
			sizeof(MSBINFHDR));

		/* Start by clearing the entire image space to zero...
		 */
		if (verbose)
			printf("MsbinImage: ");
		s_memset((char *)filhdr.imageaddr,0,(int)filhdr.imagelen,verbose,
			verifyonly);

		err = snum = 0;
		offset = (ulong)(TFS_BASE(fp) + MSBIN_SYNC_SIZE + sizeof(MSBINFHDR));

		/* Walk through all sections within the file.  For each section,
		 * copy the structure out of TFS to local space, then process it.
		 */
		for(snum = 1;err==0;snum++) {
			memcpy((char *)&scnhdr,(char *)offset,sizeof(MSBINSHDR));
			offset += sizeof(MSBINSHDR);

			/* The image terminates with an image record header with the
			 * physical address and checksum set to zero...
			 */
			if ((scnhdr.addr == 0) && (scnhdr.csum == 0))
				break;
	
			if (verbose)
				printf("section %02d: ", snum);
	
			if (tfsld_memcpy((char *)(scnhdr.addr),
				(char *)offset,scnhdr.len,verbose,verifyonly) != 0)
				err++;
	
			/* Flush caches for each loadable section... */
			flushDcache((char *)scnhdr.addr,scnhdr.len);
			invalidateIcache((char *)scnhdr.addr,scnhdr.len);
	
			offset += scnhdr.len;
		}
	
		if (err)
			return(TFSERR_MEMFAIL);
	
		if (verbose && !verifyonly && !sname)
			showEntrypoint(filhdr.imageaddr);
	
		/* Store entry point: */
		if (entrypoint)
			*entrypoint = (long)(filhdr.imageaddr);
	}
	else if (strcmp(dot,".nb0") == 0) {
		char *drambase;

		drambase = (char *)getAppRamStart();

#if INCLUDE_UNZIP
		if (TFS_ISCPRS(fp)) {
			decompress((char *)TFS_BASE(fp), (int)TFS_SIZE(fp),drambase);
		}
		else 
#endif
		{
			memcpy(drambase,(char *)TFS_BASE(fp),(int)TFS_SIZE(fp));
		}

		/* Flush caches for each loadable section... */
		flushDcache(drambase,(int)TFS_SIZE(fp));
		invalidateIcache(drambase,(int)TFS_SIZE(fp));

		/* Store entry point: */
		if (entrypoint)
			*entrypoint = (long)(drambase);
	}
	else {
		return(TFSERR_BADEXTENSION);
	}

	return(TFS_OKAY);
}

#endif

int
tfsloadebin(TFILE *fp,int verbose,long *entrypoint,char *sname,int verifyonly)
{
#if TFS_EBIN_ELFMSBIN
	int	err;
#endif

#if !INCLUDE_UNZIP
	/* If the file is compressed, but decompression is not built into
	 * the monitor, then return an error that indicates that the 
	 * needed facility in TFS is not enabled...
	 */
	if (TFS_ISCPRS(fp))
		return(TFSERR_NOTAVAILABLE);
#endif

	/* If verbosity is greater than one and verifyonly is not set, then
	 * we are simply dumping a map, so start with an appropriate 
	 * header...
	 */
	if ((verbose > 1) && (verifyonly == 0))
		printf("Load map:\n");

#if TFS_EBIN_AOUT
	return(tfsloadaout(fp,verbose,entrypoint,sname,verifyonly));
#elif TFS_EBIN_COFF
	return(tfsloadcoff(fp,verbose,entrypoint,sname,verifyonly));
#elif TFS_EBIN_ELF
	return(tfsloadelf(fp,verbose,entrypoint,sname,verifyonly));
#elif TFS_EBIN_MSBIN
	return(tfsloadmsbin(fp,verbose,entrypoint,sname,verifyonly));
#elif TFS_EBIN_ELFMSBIN
	err = tfsloadelf(fp,verbose,entrypoint,sname,verifyonly);
	if (err == TFSERR_BADHDR)
		return(tfsloadmsbin(fp,verbose,entrypoint,sname,verifyonly));
	else
		return(err);
#else
#error Invalid TFS_EBIN type.
#endif
}


#endif	/* INCLUDE_TFS */

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -