diff options
Diffstat (limited to 'kernel/module.c')
| -rw-r--r-- | kernel/module.c | 53 | 
1 files changed, 25 insertions, 28 deletions
| diff --git a/kernel/module.c b/kernel/module.c index 38d4270925d4..3d8f126208e3 100644 --- a/kernel/module.c +++ b/kernel/module.c @@ -389,16 +389,16 @@ extern const struct kernel_symbol __start___ksymtab_gpl[];  extern const struct kernel_symbol __stop___ksymtab_gpl[];  extern const struct kernel_symbol __start___ksymtab_gpl_future[];  extern const struct kernel_symbol __stop___ksymtab_gpl_future[]; -extern const unsigned long __start___kcrctab[]; -extern const unsigned long __start___kcrctab_gpl[]; -extern const unsigned long __start___kcrctab_gpl_future[]; +extern const s32 __start___kcrctab[]; +extern const s32 __start___kcrctab_gpl[]; +extern const s32 __start___kcrctab_gpl_future[];  #ifdef CONFIG_UNUSED_SYMBOLS  extern const struct kernel_symbol __start___ksymtab_unused[];  extern const struct kernel_symbol __stop___ksymtab_unused[];  extern const struct kernel_symbol __start___ksymtab_unused_gpl[];  extern const struct kernel_symbol __stop___ksymtab_unused_gpl[]; -extern const unsigned long __start___kcrctab_unused[]; -extern const unsigned long __start___kcrctab_unused_gpl[]; +extern const s32 __start___kcrctab_unused[]; +extern const s32 __start___kcrctab_unused_gpl[];  #endif  #ifndef CONFIG_MODVERSIONS @@ -497,7 +497,7 @@ struct find_symbol_arg {  	/* Output */  	struct module *owner; -	const unsigned long *crc; +	const s32 *crc;  	const struct kernel_symbol *sym;  }; @@ -563,7 +563,7 @@ static bool find_symbol_in_section(const struct symsearch *syms,   * (optional) module which owns it.  Needs preempt disabled or module_mutex. */  const struct kernel_symbol *find_symbol(const char *name,  					struct module **owner, -					const unsigned long **crc, +					const s32 **crc,  					bool gplok,  					bool warn)  { @@ -1249,23 +1249,17 @@ static int try_to_force_load(struct module *mod, const char *reason)  }  #ifdef CONFIG_MODVERSIONS -/* If the arch applies (non-zero) relocations to kernel kcrctab, unapply it. */ -static unsigned long maybe_relocated(unsigned long crc, -				     const struct module *crc_owner) + +static u32 resolve_rel_crc(const s32 *crc)  { -#ifdef ARCH_RELOCATES_KCRCTAB -	if (crc_owner == NULL) -		return crc - (unsigned long)reloc_start; -#endif -	return crc; +	return *(u32 *)((void *)crc + *crc);  }  static int check_version(Elf_Shdr *sechdrs,  			 unsigned int versindex,  			 const char *symname,  			 struct module *mod, -			 const unsigned long *crc, -			 const struct module *crc_owner) +			 const s32 *crc)  {  	unsigned int i, num_versions;  	struct modversion_info *versions; @@ -1283,13 +1277,19 @@ static int check_version(Elf_Shdr *sechdrs,  		/ sizeof(struct modversion_info);  	for (i = 0; i < num_versions; i++) { +		u32 crcval; +  		if (strcmp(versions[i].name, symname) != 0)  			continue; -		if (versions[i].crc == maybe_relocated(*crc, crc_owner)) +		if (IS_ENABLED(CONFIG_MODULE_REL_CRCS)) +			crcval = resolve_rel_crc(crc); +		else +			crcval = *crc; +		if (versions[i].crc == crcval)  			return 1; -		pr_debug("Found checksum %lX vs module %lX\n", -		       maybe_relocated(*crc, crc_owner), versions[i].crc); +		pr_debug("Found checksum %X vs module %lX\n", +			 crcval, versions[i].crc);  		goto bad_version;  	} @@ -1307,7 +1307,7 @@ static inline int check_modstruct_version(Elf_Shdr *sechdrs,  					  unsigned int versindex,  					  struct module *mod)  { -	const unsigned long *crc; +	const s32 *crc;  	/*  	 * Since this should be found in kernel (which can't be removed), no @@ -1321,8 +1321,7 @@ static inline int check_modstruct_version(Elf_Shdr *sechdrs,  	}  	preempt_enable();  	return check_version(sechdrs, versindex, -			     VMLINUX_SYMBOL_STR(module_layout), mod, crc, -			     NULL); +			     VMLINUX_SYMBOL_STR(module_layout), mod, crc);  }  /* First part is kernel version, which we ignore if module has crcs. */ @@ -1340,8 +1339,7 @@ static inline int check_version(Elf_Shdr *sechdrs,  				unsigned int versindex,  				const char *symname,  				struct module *mod, -				const unsigned long *crc, -				const struct module *crc_owner) +				const s32 *crc)  {  	return 1;  } @@ -1368,7 +1366,7 @@ static const struct kernel_symbol *resolve_symbol(struct module *mod,  {  	struct module *owner;  	const struct kernel_symbol *sym; -	const unsigned long *crc; +	const s32 *crc;  	int err;  	/* @@ -1383,8 +1381,7 @@ static const struct kernel_symbol *resolve_symbol(struct module *mod,  	if (!sym)  		goto unlock; -	if (!check_version(info->sechdrs, info->index.vers, name, mod, crc, -			   owner)) { +	if (!check_version(info->sechdrs, info->index.vers, name, mod, crc)) {  		sym = ERR_PTR(-EINVAL);  		goto getname;  	} | 
