Merge tag 'modules-next-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git...
[firefly-linux-kernel-4.4.55.git] / scripts / mod / modpost.c
index 8247979e8f64dd2eef5671544d3b39e8ed3487fc..17855761e6b77c4c5c13600b76c8cf95fcb82c00 100644 (file)
@@ -17,6 +17,7 @@
 #include <string.h>
 #include <limits.h>
 #include <stdbool.h>
+#include <errno.h>
 #include "modpost.h"
 #include "../../include/generated/autoconf.h"
 #include "../../include/linux/license.h"
@@ -37,6 +38,8 @@ static int warn_unresolved = 0;
 /* How a symbol is exported */
 static int sec_mismatch_count = 0;
 static int sec_mismatch_verbose = 1;
+/* ignore missing files */
+static int ignore_missing_files;
 
 enum export {
        export_plain,      export_unused,     export_gpl,
@@ -161,7 +164,7 @@ struct symbol {
        unsigned int vmlinux:1;    /* 1 if symbol is defined in vmlinux */
        unsigned int kernel:1;     /* 1 if symbol is from kernel
                                    *  (only for external modules) **/
-       unsigned int preloaded:1;  /* 1 if symbol from Module.symvers */
+       unsigned int preloaded:1;  /* 1 if symbol from Module.symvers, or crc */
        enum export  export;       /* Type of export */
        char name[0];
 };
@@ -329,8 +332,11 @@ static void sym_update_crc(const char *name, struct module *mod,
 {
        struct symbol *s = find_symbol(name);
 
-       if (!s)
+       if (!s) {
                s = new_symbol(name, mod, export);
+               /* Don't complain when we find it later. */
+               s->preloaded = 1;
+       }
        s->crc = crc;
        s->crc_valid = 1;
 }
@@ -407,6 +413,11 @@ static int parse_elf(struct elf_info *info, const char *filename)
 
        hdr = grab_file(filename, &info->size);
        if (!hdr) {
+               if (ignore_missing_files) {
+                       fprintf(stderr, "%s: %s (ignored)\n", filename,
+                               strerror(errno));
+                       return 0;
+               }
                perror(filename);
                exit(1);
        }
@@ -599,18 +610,17 @@ static void handle_modversions(struct module *mod, struct elf_info *info,
        else
                export = export_from_sec(info, get_secindex(info, sym));
 
+       /* CRC'd symbol */
+       if (strncmp(symname, CRC_PFX, strlen(CRC_PFX)) == 0) {
+               crc = (unsigned int) sym->st_value;
+               sym_update_crc(symname + strlen(CRC_PFX), mod, crc,
+                               export);
+       }
+
        switch (sym->st_shndx) {
        case SHN_COMMON:
                warn("\"%s\" [%s] is COMMON symbol\n", symname, mod->name);
                break;
-       case SHN_ABS:
-               /* CRC'd symbol */
-               if (strncmp(symname, CRC_PFX, strlen(CRC_PFX)) == 0) {
-                       crc = (unsigned int) sym->st_value;
-                       sym_update_crc(symname + strlen(CRC_PFX), mod, crc,
-                                       export);
-               }
-               break;
        case SHN_UNDEF:
                /* undefined symbol */
                if (ELF_ST_BIND(sym->st_info) != STB_GLOBAL &&
@@ -1853,7 +1863,7 @@ static void add_header(struct buffer *b, struct module *mod)
        buf_printf(b, "\n");
        buf_printf(b, "MODULE_INFO(vermagic, VERMAGIC_STRING);\n");
        buf_printf(b, "\n");
-       buf_printf(b, "struct module __this_module\n");
+       buf_printf(b, "__visible struct module __this_module\n");
        buf_printf(b, "__attribute__((section(\".gnu.linkonce.this_module\"))) = {\n");
        buf_printf(b, "\t.name = KBUILD_MODNAME,\n");
        if (mod->has_init)
@@ -2119,7 +2129,7 @@ int main(int argc, char **argv)
        struct ext_sym_list *extsym_iter;
        struct ext_sym_list *extsym_start = NULL;
 
-       while ((opt = getopt(argc, argv, "i:I:e:msST:o:awM:K:")) != -1) {
+       while ((opt = getopt(argc, argv, "i:I:e:mnsST:o:awM:K:")) != -1) {
                switch (opt) {
                case 'i':
                        kernel_read = optarg;
@@ -2139,6 +2149,9 @@ int main(int argc, char **argv)
                case 'm':
                        modversions = 1;
                        break;
+               case 'n':
+                       ignore_missing_files = 1;
+                       break;
                case 'o':
                        dump_write = optarg;
                        break;