浏览代码

[Kernel] More better support for module.

Bernard Xiong 10 年之前
父节点
当前提交
abd19b8dd7
共有 3 个文件被更改,包括 296 次插入222 次删除
  1. 4 1
      include/rtdef.h
  2. 280 221
      src/module.c
  3. 12 0
      src/module.h

+ 4 - 1
include/rtdef.h

@@ -892,7 +892,8 @@ enum
     RTGRAPHIC_PIXEL_FORMAT_BGR565 = RTGRAPHIC_PIXEL_FORMAT_RGB565P,
     RTGRAPHIC_PIXEL_FORMAT_RGB666,
     RTGRAPHIC_PIXEL_FORMAT_RGB888,
-    RTGRAPHIC_PIXEL_FORMAT_ARGB888
+    RTGRAPHIC_PIXEL_FORMAT_ARGB888,
+    RTGRAPHIC_PIXEL_FORMAT_ABGR888,
 };
 
 /**
@@ -965,6 +966,8 @@ struct rt_module
 {
     struct rt_object             parent;                /**< inherit from object */
 
+    rt_uint32_t                  vstart_addr;            /**< VMA base address for the
+                                                          first LOAD segment. */
     rt_uint8_t                  *module_space;          /**< module memory space */
 
     void                        *module_entry;          /**< the entry address of module */

+ 280 - 221
src/module.c

@@ -33,6 +33,10 @@
 #include <rtthread.h>
 #include <rtm.h>
 
+#ifdef RT_USING_FINSH
+#include <finsh.h>
+#endif
+
 #ifdef RT_USING_MODULE
 #include "module.h"
 
@@ -48,6 +52,18 @@
 #define IS_AX(s)          ((s.sh_flags & SHF_ALLOC) && (s.sh_flags & SHF_EXECINSTR))
 #define IS_AW(s)          ((s.sh_flags & SHF_ALLOC) && (s.sh_flags & SHF_WRITE))
 
+#ifdef RT_USING_MODULE_STKSZ
+#undef RT_USING_MODULE_STKSZ
+#endif
+
+#ifndef RT_USING_MODULE_STKSZ
+#define RT_USING_MODULE_STKSZ (4096 * 2)
+#endif
+
+#ifndef RT_USING_MODULE_PRIO
+#define RT_USING_MODULE_PRIO (RT_THREAD_PRIORITY_MAX - 2)
+#endif
+
 #ifdef RT_USING_SLAB
 #define PAGE_COUNT_MAX    256
 
@@ -75,6 +91,10 @@ static struct rt_semaphore mod_sem;
 static struct rt_module_symtab *_rt_module_symtab_begin = RT_NULL;
 static struct rt_module_symtab *_rt_module_symtab_end   = RT_NULL;
 
+#if defined(__IAR_SYSTEMS_ICC__) /* for IAR compiler */
+    #pragma section="RTMSymTab"
+#endif
+
 /**
  * @ingroup SystemInit
  *
@@ -94,16 +114,38 @@ int rt_system_module_init(void)
 
     _rt_module_symtab_begin = (struct rt_module_symtab *)&RTMSymTab$$Base;
     _rt_module_symtab_end   = (struct rt_module_symtab *)&RTMSymTab$$Limit;
+#elif defined (__IAR_SYSTEMS_ICC__)
+    _rt_module_symtab_begin = __section_begin("RTMSymTab");
+    _rt_module_symtab_end   = __section_begin("RTMSymTab");
 #endif
 
 #ifdef RT_USING_SLAB
     /* initialize heap semaphore */
     rt_sem_init(&mod_sem, "module", 1, RT_IPC_FLAG_FIFO);
 #endif
-	return 0;
+    return 0;
 }
 INIT_COMPONENT_EXPORT(rt_system_module_init);
 
+#ifdef RT_USING_FINSH
+void list_symbol(void)
+{
+    /* find in kernel symbol table */
+    struct rt_module_symtab *index;
+
+    for (index = _rt_module_symtab_begin;
+         index != _rt_module_symtab_end;
+         index ++)
+    {
+    	rt_kprintf("%s\n", index->name);
+    }
+
+    return ;
+}
+FINSH_FUNCTION_EXPORT(list_symbol, list symbol for module);
+MSH_CMD_EXPORT(list_symbol, list symbol for module);
+#endif
+
 static rt_uint32_t rt_module_symbol_find(const char *sym_str)
 {
     /* find in kernel symbol table */
@@ -145,7 +187,9 @@ static int rt_module_arm_relocate(struct rt_module *module,
     Elf32_Sword addend, offset;
     rt_uint32_t upper, lower, sign, j1, j2;
 
-    where = (Elf32_Addr *)((rt_uint8_t *)module->module_space + rel->r_offset);
+    where = (Elf32_Addr *)((rt_uint8_t *)module->module_space
+                           + rel->r_offset
+                           - module->vstart_addr);
     switch (ELF32_R_TYPE(rel->r_info))
     {
     case R_ARM_NONE:
@@ -206,10 +250,10 @@ static int rt_module_arm_relocate(struct rt_module *module,
         j1     = (lower >> 13) & 1;
         j2     = (lower >> 11) & 1;
         offset = (sign << 24) |
-                 ((~(j1 ^ sign) & 1) << 23) |
-                 ((~(j2 ^ sign) & 1) << 22) |
-                 ((upper & 0x03ff) << 12) |
-                 ((lower & 0x07ff) << 1);
+            ((~(j1 ^ sign) & 1) << 23) |
+            ((~(j2 ^ sign) & 1) << 22) |
+            ((upper & 0x03ff) << 12) |
+            ((lower & 0x07ff) << 1);
         if (offset & 0x01000000)
             offset -= 0x02000000;
         offset += sym_val - (Elf32_Addr)where;
@@ -227,11 +271,11 @@ static int rt_module_arm_relocate(struct rt_module *module,
         j1   = sign ^ (~(offset >> 23) & 1);
         j2   = sign ^ (~(offset >> 22) & 1);
         *(rt_uint16_t *)where = (rt_uint16_t)((upper & 0xf800) |
-                                (sign << 10) |
-                                ((offset >> 12) & 0x03ff));
+                                              (sign << 10) |
+                                              ((offset >> 12) & 0x03ff));
         *(rt_uint16_t *)(where + 2) = (rt_uint16_t)((lower & 0xd000) |
-                                      (j1 << 13) | (j2 << 11) |
-                                      ((offset >> 1) & 0x07ff));
+                                                    (j1 << 13) | (j2 << 11) |
+                                                    ((offset >> 1) & 0x07ff));
         upper = *(rt_uint16_t *)where;
         lower = *(rt_uint16_t *)((Elf32_Addr)where + 2);
         break;
@@ -351,10 +395,11 @@ void rt_module_unload_sethook(void (*hook)(rt_module_t module))
 static struct rt_module *_load_shared_object(const char *name,
                                              void       *module_ptr)
 {
-    rt_uint8_t *ptr    = RT_NULL;
     rt_module_t module = RT_NULL;
     rt_bool_t linked   = RT_FALSE;
     rt_uint32_t index, module_size = 0;
+    Elf32_Addr vstart_addr, vend_addr;
+    rt_bool_t has_vstart;
 
     RT_ASSERT(module_ptr != RT_NULL);
 
@@ -365,12 +410,62 @@ static struct rt_module *_load_shared_object(const char *name,
     }
 
     /* get the ELF image size */
+    has_vstart = RT_FALSE;
+    vstart_addr = vend_addr = RT_NULL;
     for (index = 0; index < elf_module->e_phnum; index++)
     {
-        if (phdr[index].p_type == PT_LOAD)
-            module_size += phdr[index].p_memsz;
+        if (phdr[index].p_type != PT_LOAD)
+            continue;
+
+        RT_DEBUG_LOG(RT_DEBUG_MODULE, ("LOAD segment: %d, 0x%p, 0x%08x\n",
+                                       index, phdr[index].p_vaddr, phdr[index].p_memsz));
+
+        if (phdr[index].p_memsz < phdr[index].p_filesz)
+        {
+            rt_kprintf("invalid elf: segment %d: p_memsz: %d, p_filesz: %d\n",
+                       index, phdr[index].p_memsz, phdr[index].p_filesz);
+            return RT_NULL;
+        }
+        if (!has_vstart)
+        {
+            vstart_addr = phdr[index].p_vaddr;
+            vend_addr = phdr[index].p_vaddr + phdr[index].p_memsz;
+            has_vstart = RT_TRUE;
+            if (vend_addr < vstart_addr)
+            {
+                rt_kprintf("invalid elf: segment %d: p_vaddr: %d, p_memsz: %d\n",
+                           index, phdr[index].p_vaddr, phdr[index].p_memsz);
+                return RT_NULL;
+            }
+        }
+        else
+        {
+            if (phdr[index].p_vaddr < vend_addr)
+            {
+                rt_kprintf("invalid elf: segment should be sorted and not overlapped\n");
+                return RT_NULL;
+            }
+            if (phdr[index].p_vaddr > vend_addr + 16)
+            {
+                /* There should not be too much padding in the object files. */
+                rt_kprintf("warning: too much padding before segment %d\n", index);
+            }
+
+            vend_addr = phdr[index].p_vaddr + phdr[index].p_memsz;
+            if (vend_addr < phdr[index].p_vaddr)
+            {
+                rt_kprintf("invalid elf: "
+                           "segment %d address overflow\n", index);
+                return RT_NULL;
+            }
+        }
     }
 
+    module_size = vend_addr - vstart_addr;
+
+    RT_DEBUG_LOG(RT_DEBUG_MODULE, ("module size: %d, vstart_addr: 0x%p\n",
+                                   module_size, vstart_addr));
+
     if (module_size == 0)
     {
         rt_kprintf("Module: size error\n");
@@ -384,6 +479,8 @@ static struct rt_module *_load_shared_object(const char *name,
     if (!module)
         return RT_NULL;
 
+    module->vstart_addr = vstart_addr;
+
     module->nref = 0;
 
     /* allocate module space */
@@ -397,21 +494,21 @@ static struct rt_module *_load_shared_object(const char *name,
     }
 
     /* zero all space */
-    ptr = module->module_space;
-    rt_memset(ptr, 0, module_size);
+    rt_memset(module->module_space, 0, module_size);
 
     for (index = 0; index < elf_module->e_phnum; index++)
     {
         if (phdr[index].p_type == PT_LOAD)
         {
-            rt_memcpy(ptr + phdr[index].p_paddr,
+            rt_memcpy(module->module_space + phdr[index].p_vaddr - vstart_addr,
                       (rt_uint8_t *)elf_module + phdr[index].p_offset,
                       phdr[index].p_filesz);
         }
     }
 
     /* set module entry */
-    module->module_entry = module->module_space + elf_module->e_entry;
+    module->module_entry = module->module_space
+        + elf_module->e_entry - vstart_addr;
 
     /* handle relocation section */
     for (index = 0; index < elf_module->e_shnum; index ++)
@@ -432,7 +529,7 @@ static struct rt_module *_load_shared_object(const char *name,
         symtab = (Elf32_Sym *)((rt_uint8_t *)module_ptr +
                                shdr[shdr[index].sh_link].sh_offset);
         strtab = (rt_uint8_t *)module_ptr +
-                 shdr[shdr[shdr[index].sh_link].sh_link].sh_offset;
+            shdr[shdr[shdr[index].sh_link].sh_link].sh_offset;
         nr_reloc = (rt_uint32_t)(shdr[index].sh_size / sizeof(Elf32_Rel));
 
         /* relocate every items */
@@ -448,7 +545,9 @@ static struct rt_module *_load_shared_object(const char *name,
                 (ELF_ST_BIND(sym->st_info) == STB_LOCAL))
             {
                 rt_module_arm_relocate(module, rel,
-                           (Elf32_Addr)(module->module_space + sym->st_value));
+                                       (Elf32_Addr)(module->module_space
+                                                    + sym->st_value
+                                                    - vstart_addr));
             }
             else if (!linked)
             {
@@ -485,7 +584,7 @@ static struct rt_module *_load_shared_object(const char *name,
         /* find .dynsym section */
         rt_uint8_t *shstrab;
         shstrab = (rt_uint8_t *)module_ptr +
-                  shdr[elf_module->e_shstrndx].sh_offset;
+            shdr[elf_module->e_shstrndx].sh_offset;
         if (rt_strcmp((const char *)(shstrab + shdr[index].sh_name), ELF_DYNSYM) == 0)
             break;
     }
@@ -500,7 +599,7 @@ static struct rt_module *_load_shared_object(const char *name,
         symtab =(Elf32_Sym *)((rt_uint8_t *)module_ptr + shdr[index].sh_offset);
         strtab = (rt_uint8_t *)module_ptr + shdr[shdr[index].sh_link].sh_offset;
 
-        for (i=0; i<shdr[index].sh_size/sizeof(Elf32_Sym); i++)
+        for (i = 0; i < shdr[index].sh_size/sizeof(Elf32_Sym); i++)
         {
             if ((ELF_ST_BIND(symtab[i].st_info) == STB_GLOBAL) &&
                 (ELF_ST_TYPE(symtab[i].st_info) == STT_FUNC))
@@ -508,9 +607,9 @@ static struct rt_module *_load_shared_object(const char *name,
         }
 
         module->symtab = (struct rt_module_symtab *)rt_malloc
-                         (count * sizeof(struct rt_module_symtab));
+            (count * sizeof(struct rt_module_symtab));
         module->nsym = count;
-        for (i=0, count=0; i<shdr[index].sh_size/sizeof(Elf32_Sym); i++)
+        for (i = 0, count = 0; i < shdr[index].sh_size/sizeof(Elf32_Sym); i++)
         {
             rt_size_t length;
 
@@ -574,10 +673,12 @@ static struct rt_module* _load_relocated_object(const char *name,
 
     /* allocate module */
     module = (struct rt_module *)
-             rt_object_allocate(RT_Object_Class_Module, (const char *)name);
+        rt_object_allocate(RT_Object_Class_Module, (const char *)name);
     if (module == RT_NULL)
         return RT_NULL;
 
+    module->vstart_addr = 0;
+
     /* allocate module space */
     module->module_space = rt_malloc(module_size);
     if (module->module_space == RT_NULL)
@@ -661,11 +762,11 @@ static struct rt_module* _load_relocated_object(const char *name,
 
         /* locate .dynsym and .dynstr */
         symtab   = (Elf32_Sym *)((rt_uint8_t *)module_ptr +
-                   shdr[shdr[index].sh_link].sh_offset);
+                                 shdr[shdr[index].sh_link].sh_offset);
         strtab   = (rt_uint8_t *)module_ptr +
-                   shdr[shdr[shdr[index].sh_link].sh_link].sh_offset;
+            shdr[shdr[shdr[index].sh_link].sh_link].sh_offset;
         shstrab  = (rt_uint8_t *)module_ptr +
-                   shdr[elf_module->e_shstrndx].sh_offset;
+            shdr[elf_module->e_shstrndx].sh_offset;
         nr_reloc = (rt_uint32_t)(shdr[index].sh_size / sizeof(Elf32_Rel));
 
         /* relocate every items */
@@ -682,7 +783,7 @@ static struct rt_module* _load_relocated_object(const char *name,
                     (ELF_ST_TYPE(sym->st_info) == STT_OBJECT))
                 {
                     if (rt_strncmp((const char *)(shstrab +
-                        shdr[sym->st_shndx].sh_name), ELF_RODATA, 8) == 0)
+                                                  shdr[sym->st_shndx].sh_name), ELF_RODATA, 8) == 0)
                     {
                         /* relocate rodata section */
                         RT_DEBUG_LOG(RT_DEBUG_MODULE, ("rodata\n"));
@@ -690,7 +791,7 @@ static struct rt_module* _load_relocated_object(const char *name,
                                                (Elf32_Addr)(rodata_addr + sym->st_value));
                     }
                     else if (rt_strncmp((const char*)
-                             (shstrab + shdr[sym->st_shndx].sh_name), ELF_BSS, 5) == 0)
+                                        (shstrab + shdr[sym->st_shndx].sh_name), ELF_BSS, 5) == 0)
                     {
                         /* relocate bss section */
                         RT_DEBUG_LOG(RT_DEBUG_MODULE, ("bss\n"));
@@ -698,7 +799,7 @@ static struct rt_module* _load_relocated_object(const char *name,
                                                (Elf32_Addr)bss_addr + sym->st_value);
                     }
                     else if (rt_strncmp((const char *)(shstrab + shdr[sym->st_shndx].sh_name),
-                             ELF_DATA, 6) == 0)
+                                        ELF_DATA, 6) == 0)
                     {
                         /* relocate data section */
                         RT_DEBUG_LOG(RT_DEBUG_MODULE, ("data\n"));
@@ -710,8 +811,11 @@ static struct rt_module* _load_relocated_object(const char *name,
             else if (ELF_ST_TYPE(sym->st_info) == STT_FUNC)
             {
                 /* relocate function */
-                rt_module_arm_relocate(module, rel, (Elf32_Addr)((rt_uint8_t *)
-                    module->module_space - module_addr + sym->st_value));
+                rt_module_arm_relocate(module, rel,
+                                       (Elf32_Addr)((rt_uint8_t *)
+                                                    module->module_space
+                                                    - module_addr
+                                                    + sym->st_value));
             }
             else
             {
@@ -736,8 +840,11 @@ static struct rt_module* _load_relocated_object(const char *name,
                 }
                 else
                 {
-                    rt_module_arm_relocate(module, rel, (Elf32_Addr)((rt_uint8_t*)
-                        module->module_space - module_addr + sym->st_value));
+                    rt_module_arm_relocate(module, rel,
+                                           (Elf32_Addr)((rt_uint8_t*)
+                                                        module->module_space
+                                                        - module_addr
+                                                        + sym->st_value));
                 }
             }
             rel ++;
@@ -747,21 +854,107 @@ static struct rt_module* _load_relocated_object(const char *name,
     return module;
 }
 
+#define RT_MODULE_ARG_MAX    8
+static int _rt_module_split_arg(char* cmd, rt_size_t length, char* argv[])
+{
+    int argc = 0;
+    char *ptr = cmd;
+
+    while ((ptr - cmd) < length)
+    {
+        /* strip bank and tab */
+        while ((*ptr == ' ' || *ptr == '\t') && (ptr -cmd)< length)
+            *ptr++ = '\0';
+        /* check whether it's the end of line */
+        if ((ptr - cmd)>= length) break;
+
+        /* handle string with quote */
+        if (*ptr == '"')
+        {
+            argv[argc++] = ++ptr;
+
+            /* skip this string */
+            while (*ptr != '"' && (ptr-cmd) < length)
+                if (*ptr ++ == '\\')  ptr ++;
+            if ((ptr - cmd) >= length) break;
+
+            /* skip '"' */
+            *ptr ++ = '\0';
+        }
+        else
+        {
+            argv[argc++] = ptr;
+            while ((*ptr != ' ' && *ptr != '\t') && (ptr - cmd) < length)
+                ptr ++;
+        }
+
+        if (argc >= RT_MODULE_ARG_MAX) break;
+    }
+
+    return argc;
+}
+
+/* module main thread entry */
+static void module_main_entry(void* parameter)
+{
+    int argc;
+    char *argv[RT_MODULE_ARG_MAX];
+    typedef int (*main_func_t)(int argc, char** argv);
+
+    rt_module_t module = (rt_module_t) parameter;
+    if (module == RT_NULL)
+        return;
+
+    if (module->module_cmd_line == RT_NULL && module->module_cmd_size != 0)
+        /* malloc for module_cmd_line failed. */
+        return;
+
+    /* FIXME: we should run some C++ initialize code before jump into the
+     * entry. */
+
+    if (module->module_cmd_line == RT_NULL)
+    {
+        RT_DEBUG_LOG(RT_DEBUG_MODULE, ("run bare entry: 0x%p\n",
+                                       module->module_entry));
+        ((main_func_t)module->module_entry)(0, RT_NULL);
+        return;
+    }
+
+    rt_memset(argv, 0x00, sizeof(argv));
+    argc = _rt_module_split_arg((char*)module->module_cmd_line,
+                                module->module_cmd_size, argv);
+    if (argc == 0)
+        return;
+
+    RT_DEBUG_LOG(RT_DEBUG_MODULE, ("run main entry: 0x%p with %s\n",
+                                   module->module_entry,
+                                   module->module_cmd_line));
+    /* do the main function */
+    ((main_func_t)module->module_entry)(argc, argv);
+    return;
+}
+
 /**
- * This function will load a module from memory and create a thread for it
+ * This function will load a module with a main function from memory and create a 
+ * main thread for it
  *
  * @param name the name of module, which shall be unique
  * @param module_ptr the memory address of module image
+ * @argc the count of argument
+ * @argd the argument data, which should be a 
  *
  * @return the module object
  */
-rt_module_t rt_module_load(const char *name, void *module_ptr)
+rt_module_t rt_module_do_main(const char *name,
+                              void *module_ptr,
+                              const char* cmd_line,
+                              int line_size)
 {
     rt_module_t module;
 
     RT_DEBUG_NOT_IN_INTERRUPT;
 
-    RT_DEBUG_LOG(RT_DEBUG_MODULE, ("rt_module_load: %s ,", name));
+    RT_DEBUG_LOG(RT_DEBUG_MODULE, ("rt_module_load: %s\n", name));
 
     /* check ELF header */
     if (rt_memcmp(elf_module->e_ident, RTMMAG, SELFMAG) != 0 &&
@@ -801,10 +994,24 @@ rt_module_t rt_module_load(const char *name, void *module_ptr)
     /* init module object container */
     rt_module_init_object_container(module);
 
-	/* initialize an empty command */
-	module->module_cmd_line = RT_NULL;
-	module->module_cmd_size = 0;
-	
+    if (line_size && cmd_line)
+    {
+        /* set module argument */
+        module->module_cmd_line = (rt_uint8_t*)rt_malloc(line_size + 1);
+        if (module->module_cmd_line)
+        {
+            rt_memcpy(module->module_cmd_line, cmd_line, line_size);
+            module->module_cmd_line[line_size] = '\0';
+        }
+        module->module_cmd_size = line_size;
+    }
+    else
+    {
+        /* initialize an empty command */
+        module->module_cmd_line = RT_NULL;
+        module->module_cmd_size = 0;
+    }
+
     /* increase module reference count */
     module->nref ++;
 
@@ -822,8 +1029,9 @@ rt_module_t rt_module_load(const char *name, void *module_ptr)
 
         /* create module thread */
         module->module_thread = rt_thread_create(name,
-                             (void(*)(void *))module->module_entry, RT_NULL,
-                             2048, RT_THREAD_PRIORITY_MAX - 2, 10);
+                                                 module_main_entry, module,
+                                                 RT_USING_MODULE_STKSZ,
+                                                 RT_USING_MODULE_PRIO, 10);
 
         RT_DEBUG_LOG(RT_DEBUG_MODULE, ("thread entry 0x%x\n",
                                        module->module_entry));
@@ -851,166 +1059,17 @@ rt_module_t rt_module_load(const char *name, void *module_ptr)
     return module;
 }
 
-#define RT_MODULE_ARG_MAX    8
-static int _rt_module_split_arg(char* cmd, rt_size_t length, char* argv[])
-{
-	int argc = 0;
-	char *ptr = cmd;
-
-	while ((ptr - cmd) < length)
-	{
-		/* strip bank and tab */
-		while ((*ptr == ' ' || *ptr == '\t') && (ptr -cmd)< length)
-			*ptr++ = '\0';
-		/* check whether it's the end of line */
-		if ((ptr - cmd)>= length) break;
-
-		/* handle string with quote */
-		if (*ptr == '"')
-		{
-			argv[argc++] = ++ptr;
-
-			/* skip this string */
-			while (*ptr != '"' && (ptr-cmd) < length)
-				if (*ptr ++ == '\\')  ptr ++;
-			if ((ptr - cmd) >= length) break;
-
-			/* skip '"' */
-			*ptr ++ = '\0';
-		}
-		else
-		{
-			argv[argc++] = ptr;
-			while ((*ptr != ' ' && *ptr != '\t') && (ptr - cmd) < length)
-				ptr ++;
-		}
-
-		if (argc >= RT_MODULE_ARG_MAX) break;
-	}
-
-	return argc;
-}
-/* module main thread entry */
-static void module_main_entry(void* parameter)
-{
-    int argc;
-    char *argv[RT_MODULE_ARG_MAX];
-	typedef int (*main_func_t)(int argc, char** argv);
-
-	rt_module_t module = (rt_module_t) parameter;
-	if (module == RT_NULL || module->module_cmd_line == RT_NULL) return;
-
-    rt_memset(argv, 0x00, sizeof(argv));
-    argc = _rt_module_split_arg((char*)module->module_cmd_line, module->module_cmd_size, argv);
-    if (argc == 0) return ;
-
-	/* do the main function */
-	((main_func_t)module->module_entry)(argc, argv);
-	return;
-}
-
 /**
- * This function will load a module with a main function from memory and create a 
- * main thread for it
+ * This function will load a module from memory and create a thread for it
  *
  * @param name the name of module, which shall be unique
  * @param module_ptr the memory address of module image
- * @argc the count of argument
- * @argd the argument data, which should be a 
  *
  * @return the module object
  */
-rt_module_t rt_module_do_main(const char *name, void *module_ptr, const char* cmd_line, int line_size)
+rt_module_t rt_module_load(const char *name, void *module_ptr)
 {
-	rt_module_t module;
-
-	RT_DEBUG_NOT_IN_INTERRUPT;
-
-	RT_DEBUG_LOG(RT_DEBUG_MODULE, ("rt_module_load: %s ,", name));
-
-	/* check ELF header */
-	if (rt_memcmp(elf_module->e_ident, RTMMAG, SELFMAG) != 0 &&
-		rt_memcmp(elf_module->e_ident, ELFMAG, SELFMAG) != 0)
-	{
-		rt_kprintf("Module: magic error\n");
-
-		return RT_NULL;
-	}
-
-	/* check ELF class */
-	if (elf_module->e_ident[EI_CLASS] != ELFCLASS32)
-	{
-		rt_kprintf("Module: ELF class error\n");
-		return RT_NULL;
-	}
-
-	if (elf_module->e_type == ET_REL)
-	{
-		module = _load_relocated_object(name, module_ptr);
-	}
-	else if (elf_module->e_type == ET_DYN)
-	{
-		module = _load_shared_object(name, module_ptr);
-	}
-	else
-	{
-		rt_kprintf("Module: unsupported excutable program\n");
-		return RT_NULL;
-	}
-
-	if (module == RT_NULL)
-		return RT_NULL;
-
-	/* init module object container */
-	rt_module_init_object_container(module);
-
-	/* increase module reference count */
-	module->nref ++;
-
-	if (elf_module->e_entry != 0)
-	{
-#ifdef RT_USING_SLAB
-		/* init module memory allocator */
-		module->mem_list = RT_NULL;
-
-		/* create page array */
-		module->page_array =
-			(void *)rt_malloc(PAGE_COUNT_MAX * sizeof(struct rt_page_info));
-		module->page_cnt = 0;
-#endif
-
-		/* set module argument */
-		module->module_cmd_line = (rt_uint8_t*)rt_malloc(line_size + 1);
-		rt_memcpy(module->module_cmd_line, cmd_line, line_size);
-		module->module_cmd_line[line_size] = '\0';
-		module->module_cmd_size = line_size;
-
-		/* create module thread */
-		module->module_thread =	rt_thread_create(name,
-							 module_main_entry, module,
-							 2048, RT_THREAD_PRIORITY_MAX - 2, 10);
-
-		/* set module id */
-		module->module_thread->module_id = (void *)module;
-		module->parent.flag = RT_MODULE_FLAG_WITHENTRY;
-
-		/* startup main thread */
-		rt_thread_startup(module->module_thread);
-	}
-	else
-	{
-		/* without entry point */
-		module->parent.flag |= RT_MODULE_FLAG_WITHOUTENTRY;
-	}
-
-#ifdef RT_USING_HOOK
-	if (rt_module_load_hook != RT_NULL)
-	{
-		rt_module_load_hook(module);
-	}
-#endif
-
-	return module;
+    return rt_module_do_main(name, module_ptr, RT_NULL, 0);
 }
 
 #ifdef RT_USING_DFS
@@ -1132,33 +1191,33 @@ rt_module_t rt_module_exec_cmd(const char *path, const char* cmd_line, int size)
     char *name, *buffer, *offset_ptr;
     struct rt_module *module = RT_NULL;
 
-	name = buffer = RT_NULL;
+    name = buffer = RT_NULL;
 
     RT_DEBUG_NOT_IN_INTERRUPT;
 
     /* check parameters */
     RT_ASSERT(path != RT_NULL);
 
-	/* get file size */
+    /* get file size */
     if (stat(path, &s) !=0)
     {
         rt_kprintf("Module: access %s failed\n", path);
         goto __exit;
     }
 
-	/* allocate buffer to save program */
+    /* allocate buffer to save program */
     offset_ptr = buffer = (char *)rt_malloc(s.st_size);
     if (buffer == RT_NULL)
     {
         rt_kprintf("Module: out of memory\n");
-		goto __exit;
+        goto __exit;
     }
 
     fd = open(path, O_RDONLY, 0);
     if (fd < 0)
     {
         rt_kprintf("Module: open %s failed\n", path);
-		goto __exit;
+        goto __exit;
     }
 
     do
@@ -1175,12 +1234,12 @@ rt_module_t rt_module_exec_cmd(const char *path, const char* cmd_line, int size)
     if ((rt_uint32_t)offset_ptr - (rt_uint32_t)buffer != s.st_size)
     {
         rt_kprintf("Module: read file failed\n");
-		goto __exit;
+        goto __exit;
     }
 
-	/* get module */
+    /* get module */
     name   = _module_name(path);
-	/* execute module */
+    /* execute module */
     module = rt_module_do_main(name, (void *)buffer, cmd_line, size);
 
 __exit:
@@ -1224,7 +1283,7 @@ rt_err_t rt_module_destroy(rt_module_t module)
     {
 #ifdef RT_USING_SEMAPHORE
         /* delete semaphores */
-        list = &module->module_object[RT_Object_Class_Thread].object_list;
+        list = &module->module_object[RT_Object_Class_Semaphore].object_list;
         while (list->next != list)
         {
             object = rt_list_entry(list->next, struct rt_object, list);
@@ -1362,12 +1421,12 @@ rt_err_t rt_module_destroy(rt_module_t module)
                 rt_timer_delete((rt_timer_t)object);
             }
         }
-		
-		/* delete command line */
-		if (module->module_cmd_line != RT_NULL)
-		{
-			rt_free(module->module_cmd_line);
-		}
+
+        /* delete command line */
+        if (module->module_cmd_line != RT_NULL)
+        {
+            rt_free(module->module_cmd_line);
+        }
     }
 
 #ifdef RT_USING_SLAB
@@ -1615,8 +1674,8 @@ void *rt_module_malloc(rt_size_t size)
     RT_DEBUG_NOT_IN_INTERRUPT;
 
     nunits = (size + sizeof(struct rt_mem_head) - 1) /
-             sizeof(struct rt_mem_head)
-             + 1;
+        sizeof(struct rt_mem_head)
+        + 1;
 
     RT_ASSERT(size != 0);
     RT_ASSERT(nunits != 0);
@@ -1659,7 +1718,7 @@ void *rt_module_malloc(rt_size_t size)
 
     /* allocate pages from system heap */
     npage = (size + sizeof(struct rt_mem_head) + RT_MM_PAGE_SIZE - 1) /
-            RT_MM_PAGE_SIZE;
+        RT_MM_PAGE_SIZE;
     if ((up = (struct rt_mem_head *)rt_module_malloc_page(npage)) == RT_NULL)
         return RT_NULL;
 
@@ -1725,8 +1784,8 @@ void rt_module_free(rt_module_t module, void *addr)
                     if ((b->size * sizeof(struct rt_page_info) % RT_MM_PAGE_SIZE) != 0)
                     {
                         rt_size_t nunits = npage *
-                                           RT_MM_PAGE_SIZE /
-                                           sizeof(struct rt_mem_head);
+                            RT_MM_PAGE_SIZE /
+                            sizeof(struct rt_mem_head);
                         /* split memory */
                         r       = b + nunits;
                         r->next = b->next;
@@ -1762,8 +1821,8 @@ void rt_module_free(rt_module_t module, void *addr)
                     if ((n->size * sizeof(struct rt_page_info) % RT_MM_PAGE_SIZE) != 0)
                     {
                         rt_size_t nunits = npage *
-                                           RT_MM_PAGE_SIZE /
-                                           sizeof(struct rt_mem_head);
+                            RT_MM_PAGE_SIZE /
+                            sizeof(struct rt_mem_head);
                         /* split memory */
                         r       = n + nunits;
                         r->next = n->next;
@@ -1848,8 +1907,8 @@ void *rt_module_realloc(void *ptr, rt_size_t size)
     }
 
     nunits = (size + sizeof(struct rt_mem_head) - 1) /
-             sizeof(struct rt_mem_head)
-             +1;
+        sizeof(struct rt_mem_head)
+        +1;
     b = (struct rt_mem_head *)ptr - 1;
 
     if (nunits <= b->size)
@@ -1959,8 +2018,8 @@ void list_mempage(const char *name)
     }
 }
 FINSH_FUNCTION_EXPORT(list_mempage, list module using memory page information)
-#endif
+#endif /* RT_USING_FINSH */
 
-#endif
+#endif /* RT_USING_SLAB */
 
 #endif

+ 12 - 0
src/module.h

@@ -222,7 +222,19 @@ typedef struct
 } Elf32_Phdr;
 
 /* p_type */
+#define PT_NULL                 0
 #define PT_LOAD                 1
+#define PT_DYNAMIC              2
+#define PT_INTERP               3
+#define PT_NOTE                 4
+#define PT_SHLIB                5
+#define PT_PHDR                 6
+#define PT_TLS                  7
+#define PT_NUM                  8
+#define PT_LOOS                 0x60000000
+#define PT_HIOS                 0x6fffffff
+#define PT_LOPROC               0x70000000
+#define PT_HIPROC               0x7fffffff
 
 /* p_flags */
 #define PF_X                    1