diff --git a/src/Makefile b/src/Makefile index 968f82ef..4c93d005 100644 --- a/src/Makefile +++ b/src/Makefile @@ -59,7 +59,7 @@ override T = $(basename $@) # these use exceptions & RTTI OBJECTS1 = \ compress$o except$o file$o lefile$o \ - filter$o mem$o msg$o stdcxx$o work$o ui$o \ + filter$o linker$o mem$o msg$o stdcxx$o work$o ui$o \ packer$o packhead$o packmast$o \ p_com$o p_djgpp2$o p_elks$o p_exe$o \ p_lx_elf$o p_lx_exc$o p_lx_sep$o p_lx_sh$o \ @@ -68,7 +68,7 @@ OBJECTS1 = \ # no exceptions or RTTI OBJECTS2 = \ - filteri$o help$o main$o mygetopt$o util$o linker$o \ + filteri$o help$o main$o mygetopt$o util$o \ c_init$o c_file$o c_none$o c_screen$o \ s_object$o s_djgpp2$o s_vcsa$o s_win32$o diff --git a/src/linker.cpp b/src/linker.cpp index 403f565b..0f93e3ce 100644 --- a/src/linker.cpp +++ b/src/linker.cpp @@ -60,12 +60,12 @@ Linker::Linker(const void *pdata, int plen, int pinfo) sections = new section[200]; char *p = iloader + info; - while (get_le32(p) != (unsigned)(-1)) + while (get32(p) != (unsigned)(-1)) { - if (get_le32(p)) + if (get32(p)) { memcpy(sections[nsections].name,p,8); - sections[nsections].istart = get_le32(p+8); + sections[nsections].istart = get32(p+8); sections[nsections++].ostart = -1; p += 12; assert(nsections < 200); @@ -73,13 +73,13 @@ Linker::Linker(const void *pdata, int plen, int pinfo) else { int l; - for (l = get_le32(p+4) - 1; iloader[l] == 0; l--) + for (l = get32(p+4) - 1; iloader[l] == 0; l--) ; jumps[njumps].pos = l+1; - jumps[njumps].len = get_le32(p+4)-jumps[njumps].pos; + jumps[njumps].len = get32(p+4)-jumps[njumps].pos; memcpy(jumps[njumps].tsect,p+8,8); - jumps[njumps++].toffs = get_le32(p+16); + jumps[njumps++].toffs = get32(p+16); p += 20; assert(njumps < 200); } @@ -177,7 +177,7 @@ const char *Linker::getLoader(int *llen) if (jumps[ic].len == 1) assert(-128 <= offs && offs <= 127); - set_le32(&offs,offs); + set32(&offs,offs); memcpy(oloader+sections[jc].ostart+jumps[ic].pos-sections[jc].istart,&offs,jumps[ic].len); } frozen=1; diff --git a/src/linker.h b/src/linker.h index 02597d52..19445237 100644 --- a/src/linker.h +++ b/src/linker.h @@ -34,12 +34,17 @@ class Linker { public: Linker(const void *pdata, int plen, int pinfo); - ~Linker(); + virtual ~Linker(); void addSection(const char *sect); void addSection(const char *sname, const void *sdata, unsigned len); const char *getLoader(int *llen); int getSection(const char *name, int *slen) const; +protected: + // little endian + virtual unsigned get32(const void *b) const { return get_le32(b); } + virtual void set32(void *b, unsigned v) const { set_le32(b, v); } + private: struct section; struct jump; @@ -61,6 +66,25 @@ private: }; +class BeLinker : public Linker +{ + typedef Linker super; +public: + BeLinker(const void *pdata, int plen, int pinfo) : + super(pdata, plen, pinfo) { } + +protected: + // big endian + virtual unsigned get32(const void *b) const { return get_be32(b); } + virtual void set32(void *b, unsigned v) const { set_be32(b, v); } + +private: + // disable copy and assignment + BeLinker(BeLinker const &); // {} + BeLinker& operator= (BeLinker const &); // { return *this; } +}; + + #endif /* already included */ diff --git a/src/packer.cpp b/src/packer.cpp index ce9229b2..9b4e1d89 100644 --- a/src/packer.cpp +++ b/src/packer.cpp @@ -925,10 +925,14 @@ unsigned Packer::unoptimizeReloc32(upx_byte **in, upx_byte *image, void Packer::initLoader(const void *pdata, int plen, int pinfo) { - delete linker; if (pinfo < 0) pinfo = ~3 & (3 + get_le16(pdata, plen - 2)); - linker = new Linker(pdata,plen,pinfo); + + delete linker; + if (getFormat() < 128) + linker = new Linker(pdata, plen, pinfo); // little endian + else + linker = new BeLinker(pdata, plen, pinfo); // big endian static const char identbig[] = "\n\0"