Example #1
0
int		main(int argc, char **argv)
{
  elfshobj_t	*host;
  elfshobj_t	*rel;
  elfshsect_t	*txtsect;
  elfsh_Sym	*puts_troj;
  elfsh_Sym	*hook_func;
  int		idx;
  u_long	addr;

  /* Map host file and relocatable file */
  rel = elfsh_map_obj(RELOC_FILE);
  if (NULL == rel)
    goto err;
  host = elfsh_map_obj(TROJANED_FILE);
  if (NULL == host)
    goto err;

  /* Inject etrel */
  idx = elfsh_inject_etrel(host, rel);
  if (idx < 0)
    goto err;

  /* Get injected's section info */
  txtsect = elfsh_get_section_by_name(host, RELOC_FILE".text", NULL, NULL, NULL);
  if (txtsect == NULL)
    goto err;

  puts_troj = elfsh_get_symbol_by_name(host, "puts_troj");
  idx = elfsh_hijack_function_by_name(host, ELFSH_HIJACK_TYPE_PLT,
				      "puts", puts_troj->st_value, 
				      NULL);
  if (idx < 0)
    goto err;

  hook_func = elfsh_get_symbol_by_name(host, "hook_func");
  idx = elfsh_hijack_function_by_name(host, ELFSH_HIJACK_TYPE_FLOW,
				      "legit_func", hook_func->st_value, 
				      NULL);
  if (idx < 0)
    goto err;


  /* Save it */
  idx = elfsh_save_obj(host, OUTPUT_FILE);
  if (idx < 0)
    goto err;

  puts("[*] ET_REL injected");
  return (0);
 err:
  elfsh_error();
  return (-1);
}
Example #2
0
/**
 * like revm_lookup_addr - Get address value 
 * @param file host file
 * @param param name to search
 * @return addresse found or 0
 */
eresi_Addr		edfmt_lookup_addr(elfshobj_t *file, char *param)
{
  elfsh_Sym		*sym;
  char			eol;
  int			ret;
  eresi_Addr	       	val;

  PROFILER_IN(__FILE__, __FUNCTION__, __LINE__);

  /* Lookup .symtab */
  sym = elfsh_get_symbol_by_name(file, param);
  if (sym != NULL && sym->st_value > 0)
    {
      PROFILER_ROUT(__FILE__, __FUNCTION__, __LINE__, sym->st_value);
    }

  /* Lookup .dynsym */
  sym = elfsh_get_dynsymbol_by_name(file, param);
  if (sym != NULL && sym->st_value > 0)
    {
      PROFILER_ROUT(__FILE__, __FUNCTION__, __LINE__, sym->st_value);
    }

  /* Lookup hexadecimal numeric value */
  ret = sscanf(param, XFMT "%c", &val, &eol);
  if (ret == 1)
    {
      PROFILER_ROUT(__FILE__, __FUNCTION__, __LINE__, val);
    }

  /* No match -- returns ERR */
  PROFILER_ERR(__FILE__, __FUNCTION__, __LINE__, 
		    "Unable to lookup address object", (eresi_Addr) 0);
}
Example #3
0
eresi_Addr dl_auxv_offset(char *lib){
  elfshobj_t *f;
  f = elfutils_read_elf_file(lib);
  if (NULL == f){
    return -1;
  }
  elfsh_Sym *s;
  s = elfsh_get_symbol_by_name(f, "_dl_auxv");
  return s->st_value;
}
Example #4
0
/**
 * Remove a symbol
 * This function is not e2dbg safe
 * @param symtab
 * @param name
 * @return
 */
int		elfsh_remove_symbol(elfshsect_t *symtab, char *name)
{
  elfsh_Sym	*ret;
  elfsh_Sym	*tab;
  elfsh_Sym	*enew;
  u_int   	off;
  u_int		movedsz;
  hash_t 	*uptable = NULL;

  PROFILER_IN(__FILE__, __FUNCTION__, __LINE__);

  /* Sanity checks */
  if (symtab == NULL || name == NULL)
    PROFILER_ERR(__FILE__, __FUNCTION__, __LINE__, 
		      "Invalid parameters", -1);
  ret = elfsh_get_symbol_by_name(symtab->parent, name);
  if (ret == NULL)
    PROFILER_ERR(__FILE__, __FUNCTION__, __LINE__, 
		      "Unknown symbol", -1);

  /* Do it */
  tab = symtab->data;
  off = (u_long) ret - (u_long) tab;
  movedsz = symtab->shdr->sh_size - off - sizeof(elfsh_Sym);
  if (movedsz)
    memcpy((char *) symtab->data + off, 
	   (char *) symtab->data + off + sizeof(elfsh_Sym),
	   movedsz);
  symtab->shdr->sh_size -= sizeof(elfsh_Sym);
  symtab->curend -= sizeof(elfsh_Sym);
  XALLOC(__FILE__, __FUNCTION__, __LINE__,enew, symtab->shdr->sh_size, -1);
  memcpy(enew, tab, symtab->shdr->sh_size);
  XFREE(__FILE__, __FUNCTION__, __LINE__,tab);
  symtab->data = enew;

  /* We just cant remove the string because of ELF string table format */
  elfsh_sync_sorted_symtab(symtab);

  /* Update hashtable */
  switch(symtab->shdr->sh_type)
    {
    case SHT_SYMTAB:
      uptable = &symtab->parent->symhash;
      break;
    case SHT_DYNSYM:
      uptable = &symtab->parent->dynsymhash;
      break;
    }

  if (uptable && uptable->ent)
    hash_del(uptable, name);

  PROFILER_ROUT(__FILE__, __FUNCTION__, __LINE__, 0);
}
Example #5
0
/**
 * Shift usual symbols (mandatory on solaris)
 * @param sect
 * @param sym
 */
void		elfsh_shift_usualsyms(elfshsect_t *sect, elfsh_Sym *sym)
{
  elfsh_Sym	*end;

  PROFILER_IN(__FILE__, __FUNCTION__, __LINE__);

  //fprintf(stderr, "Calling shift usual syms ! \n");

  /* Change _end in the symbol table */
  end = elfsh_get_symbol_by_name(sect->parent, "_end");
  if (end != NULL && sym->st_value + sym->st_size > end->st_value)
    {
      //printf("Shift _end! \n");
      end->st_value = sym->st_value + sym->st_size;
    }

  /* Change _end if necessary (solaris) */
  end = elfsh_get_dynsymbol_by_name(sect->parent, "_end");
  if (end != NULL && sym->st_value + sym->st_size > end->st_value)
    {
      //printf("Shift _end! \n");
      end->st_value = sym->st_value + sym->st_size;
    }

  /* Change _END_ if necessary (solaris) */
  end = elfsh_get_dynsymbol_by_name(sect->parent, "_END_");
  if (end != NULL && sym->st_value + sym->st_size > end->st_value)
    {
      //printf("Shift _END_! \n");
      end->st_value = sym->st_value + sym->st_size;
    }

  /* Change _edata if necessary (solaris) */
  if (elfsh_get_ostype(sect->parent) == ELFSH_OS_SOLARIS)
    {
      end = elfsh_get_dynsymbol_by_name(sect->parent, "_edata");
      if (end != NULL && sym->st_value + sym->st_size > end->st_value)
	{
	  //printf("Shift _edata! \n");
	  end->st_value = sym->st_value + sym->st_size;
	}
    }
  PROFILER_OUT(__FILE__, __FUNCTION__, __LINE__);
}
Example #6
0
/** 
 * Load linkmap 
 * @param name
 * @return
 */
int			e2dbg_linkmap_load(char *name)
{
  static int		done	= 0;
  elfshsect_t		*got;
  eresi_Addr		*linkmap_entry;
  void			*data;
#if defined(sun)
  Link_map		*actual;
#else
  elfshlinkmap_t	*actual;
#endif
  char			*gotname;
  char			*ename;
  elfsh_Ehdr		*hdr;
  u_int			elftypenum;
  elfsh_Sym		*endsym;
  char			buff[64];

  PROFILER_IN(__FILE__, __FUNCTION__, __LINE__);
  if (done)
    PROFILER_ROUT(__FILE__, __FUNCTION__, __LINE__, 0);    

#if __DEBUG_LINKMAP__
  fprintf(stderr, "[e2dbg] Starting Loading LINKMAP !! \n");
#endif

  e2dbg_user_hooks_install();
  revm_config(E2DBG_CONFIG);

  /* Load debugged file */
  if (name)
    {

      /* No need to fill ET_EXEC base addr */
      if (!revm_is_loaded(name) && revm_file_load(name, 0, NULL) < 0)
	PROFILER_ERR(__FILE__, __FUNCTION__, __LINE__, 
			  "Cannot load file", -1);
      
#if __DEBUG_LINKMAP__
      fprintf(stderr, "[e2dbg_linkmap_load] file %s loaded\n", name);
#endif
      
      world.curjob->curfile->linkmap = E2DBG_DYNAMIC_LINKMAP;
      world.curjob->curfile->iotype  = ELFSH_IOTYPE_EMBEDDED;
      world.curjob->curfile->running = 0;
    }
  
#if __DEBUG_LINKMAP__
  fprintf(stderr, "[e2dbg_linkmap_load] Before switch\n");
#endif
  
  /* Switch to obj 1 */
  if (revm_doswitch(1) < 0)
    PROFILER_ERR(__FILE__, __FUNCTION__, __LINE__, 
		 "Cannot switch on object 1", -1);    
  
#if __DEBUG_LINKMAP__
  fprintf(stderr, "[e2dbg_linkmap_load] After switch \n");
#endif
  
  /* Base address for PIE binaries have to be imported */
  if (world.curjob->curfile->hdr->e_type == ET_DYN &&
      !world.curjob->curfile->rhdr.base)
    {
#if __DEBUG_LINKMAP__
      fprintf(stderr, "[e2dbg_linkmap_load] Inside ET_DYN condition\n");
#endif

      endsym = elfsh_get_symbol_by_name(world.curjob->curfile, "_end");

      fprintf(stderr, "endsym = " AFMT " \n", (eresi_Addr) endsym);
      sleep(1);

#if __DEBUG_LINKMAP__
      fprintf(stderr, "[e2dbg_linkmap_load] Filling PIE base"
	      " (_end ondisk = " AFMT " / _end in memory = " AFMT ") ! \n",
	      endsym->st_value, e2dbgworld.syms.piebase);
#endif 

      world.curjob->curfile->rhdr.base = e2dbgworld.syms.piebase -
	endsym->st_value;
    }

  /* Get ALTGOT or GOT if we used LD_PRELOAD */
  if (!e2dbgworld.preloaded)
    {
      gotname = ELFSH_SECTION_NAME_ALTGOT;
      got = elfsh_get_section_by_name(world.curjob->curfile, 
				      gotname, NULL, NULL, NULL);
    }
  else
    got = elfsh_get_gotsct(world.curjob->curfile);

#if __DEBUG_LINKMAP__
  fprintf(stderr, "[e2dbg_linkmap_load] %s section at " XFMT "\n",
	  got->name, got->shdr->sh_addr);
  fprintf(stderr, "[e2dbg_linkmap_load] BASE = %08x\n", 
	  world.curjob->curfile->rhdr.base);
#endif
  
  
  /* Fix first file linkmap entry */
  if (world.curjob->curfile->linkmap == E2DBG_DYNAMIC_LINKMAP)
    {
      /* Fix first file linkmap entry */
      hdr = elfsh_get_hdr(world.curjob->curfile);
      if (!hdr)
	PROFILER_ERR(__FILE__, __FUNCTION__, __LINE__, 
			  "Cannot get ELF header", -1);    
      elftypenum = elfsh_get_objtype(hdr);
      
      //fprintf(stderr, "[e2dbg_linkmap_load] after ELF header \n");

      /* Get ALTGOT entry */
      data          = elfsh_readmem(got);

      //fprintf(stderr, "[e2dbg_linkmap_load] after get_raw (data = %08X) \n", data);

      linkmap_entry = elfsh_get_got_entry_by_index(data, 1);
      
      //fprintf(stderr, "[e2dbg_linkmap_load] after entry_by_index (linkmap_entry = %08x)\n",
      //      linkmap_entry);

#if defined(__FreeBSD__) || defined(__NetBSD__)
      world.curjob->curfile->linkmap = (elfshlinkmap_t *)
	&((Obj_Entry *) elfsh_get_got_val(linkmap_entry))->linkmap;
#elif defined(sun)
      world.curjob->curfile->linkmap = e2dbgworld.syms.map;
#else
      world.curjob->curfile->linkmap = (elfshlinkmap_t *) elfsh_get_got_val(linkmap_entry);
#endif
      
    }
  
#if __DEBUG_LINKMAP__
  else
    fprintf(stderr, "[e2dbg_linkmap_load] Linkmap was -NOT- dynamic\n");

  fprintf(stderr, "[e2dbg_linkmap_load] LINKMAP Found at " XFMT "\n", 
	 world.curjob->curfile->linkmap);
#endif

  revm_doswitch(1);
  
  /* now load all linkmap's files */
  for (actual = elfsh_linkmap_get_lprev(world.curjob->curfile->linkmap);
       actual != NULL; 
       actual = elfsh_linkmap_get_lprev(actual))
    {
      
#if __DEBUG_LINKMAP__
      fprintf(stderr, "[e2dbg_linkmap_load] Running on LINKMAP PREV " XFMT "\n", 
	     actual);
#endif
      
      ename = elfsh_linkmap_get_lname(actual);
      if (ename && *ename && !revm_is_loaded(ename))
	{
	  if (revm_file_load(ename,
			     elfsh_linkmap_get_laddr(actual), 
			     world.curjob->curfile->linkmap) < 0)
	    e2dbg_output(" [EE] Loading failed");
	  world.curjob->curfile->iotype  = ELFSH_IOTYPE_EMBEDDED;
	}      
    }

#if __DEBUG_LINKMAP__
  fprintf(stderr, "[e2dbg_linkmap_load] Running on LINKMAP NEXT\n");
#endif
  
  for (actual = elfsh_linkmap_get_lnext(world.curjob->curfile->linkmap);
       actual != NULL; 
       actual = elfsh_linkmap_get_lnext(actual))
    {

      ename = elfsh_linkmap_get_lname(actual);
     
#if __DEBUG_LINKMAP__
      fprintf(stderr, "[e2dbg_linkmap_load] Running on LINKMAP NEXT " XFMT " (%s baseaddr %08X) \n", 
	      actual, ename, actual->laddr);
#endif

      if (ename && *ename && !revm_is_loaded(ename))
	{
	  if (revm_file_load(ename, elfsh_linkmap_get_laddr(actual), 
			     world.curjob->curfile->linkmap) < 0)
	    e2dbg_output(" [EE] Loading failed");
	  world.curjob->curfile->iotype  = ELFSH_IOTYPE_EMBEDDED;
	}      
    }

  /* Everything was OK */
  e2dbg_output("\n");
  //elfsh_set_runtime_mode();
  revm_doswitch(1);

  snprintf(buff, sizeof(buff), " [*] Target PID = %u \n", getpid());
  e2dbg_output(buff);

  done = 1;
  PROFILER_ROUT(__FILE__, __FUNCTION__, __LINE__, 0);
}
Example #7
0
/**
 * Insert a symbol in the given symbol table 
 * This function is not e2dbg safe 
 * @param sect
 * @param sym
 * @param name
 * @return
 */
int		elfsh_insert_symbol(elfshsect_t *sect,
				    elfsh_Sym	*sym,
				    char	*name)
{
  elfsh_Sym	*orig;
  int		index;
  int		mode;
  hash_t	*uptable;

  PROFILER_IN(__FILE__, __FUNCTION__, __LINE__);

  //fprintf(stderr, "Adding symbol %s \n", name);

  /* Sanity checks */
  if (sect == NULL || sect->shdr == NULL ||
      (sect->shdr->sh_type != SHT_SYMTAB &&
       sect->shdr->sh_type != SHT_DYNSYM))
    PROFILER_ERR(__FILE__, __FUNCTION__, __LINE__, 
		      "Input section is not SYMTAB", -1);
  if (name == NULL)
    name = ELFSH_NULL_STRING;

  /* Check if symbol already exists */
  orig = elfsh_get_symbol_by_name(sect->parent, name);
  if (orig != NULL && sym->st_value == orig->st_value)
    PROFILER_ROUT(__FILE__, __FUNCTION__, __LINE__, 
		       (((char *) orig - (char *) sect->data) /
			ELFSH_SYMTAB_ENTRY_SIZE));

  /* Shift some special symbols */
  //if (sect->shdr->sh_type == SHT_DYNSYM)
  //fprintf(stderr, "Shifting usual symbols\n");
  mode = elfsh_get_mode();
  elfsh_set_static_mode();
  elfsh_shift_usualsyms(sect, sym);
  elfsh_set_mode(mode);
  //fprintf(stderr, "Shifted usual symbols\n");

  /* Insert symbol name in .shstrtab */
  index = elfsh_insert_in_strtab(sect->parent, name);
  if (index < 0)
    PROFILER_ERR(__FILE__, __FUNCTION__, __LINE__,
		      "Unable to insert in SHSTRTAB", -1);

#if __DEBUG_RELADD__
  fprintf(stderr, "[DEBUG_RELADD] Injected symbol %-20s [" AFMT "] \n",
	  name, (eresi_Addr) sym->st_value);
#endif

  /* Insert symbol in .symtab */
  sym->st_name = index;
  index = elfsh_append_data_to_section(sect, sym, sizeof(elfsh_Sym));

  /* Update hashtable */
  switch(sect->shdr->sh_type)
    {
    case SHT_SYMTAB:
      uptable = &sect->parent->symhash;
      break;
    case SHT_DYNSYM:
      uptable = &sect->parent->dynsymhash;
      break;
    default:
      uptable = NULL;
      break;
    }

  if (uptable && uptable->ent)
    hash_add(uptable, strdup(name), (void *) index);

  PROFILER_ROUT(__FILE__, __FUNCTION__, __LINE__, sym->st_name);
}