diff --git a/irdb-libs/ir_builders/fix_calls.cpp b/irdb-libs/ir_builders/fix_calls.cpp
index f9b24351e9c0263b9b48a7eb71e1fbec968f536d..c66480b7e4f6f7416cb8edd8ec0ce4e57fd0cd3a 100644
--- a/irdb-libs/ir_builders/fix_calls.cpp
+++ b/irdb-libs/ir_builders/fix_calls.cpp
@@ -369,9 +369,9 @@ string adjust_esp_offset(string newbits, int offset)
         }
 
         /* 8-bit offset */
-        else if ( (unsigned char)newbits[0] == 0xff &&                           	/* ff */
-             ((unsigned char)newbits[1] == 0x54 || (unsigned char)newbits[1]==0xa4) &&    		/* /3 or /5 */
-             sib_base == 0x4 )                                          /* base==esp */
+        else if ( (unsigned char)newbits[0] == 0xff &&                                  //   ff 
+             ((unsigned char)newbits[1] == 0x54 || (unsigned char)newbits[1]==0xa4) &&  //   /3 or /5 
+             sib_base == 0x4 )                                                          //   base==esp 
         {
                 /* We need to add 4 to the offset, but this may overflow an 8-bit quantity
                  * (note:  there's no 16-bit offset for this insn.  Only 8-bit or 32-bit offsets exist for this instr)
@@ -540,16 +540,7 @@ void fix_call(Instruction_t* insn, FileIR_t *firp, bool can_unpin)
 	VirtualOffset_t next_addr=insn->getAddress()->getVirtualOffset() + insn->getDataBits().length();
 
 	/* create a new instruction and a new addresss for it that do not correspond to any original program address */
-	/*
-	 Instruction_t *callinsn=new Instruction_t();
-	 firp->getInstructions().insert(callinsn);
-	 */
 	auto callinsn=firp->addNewInstruction();
-	/*
-	 AddressID_t *calladdr=new AddressID_t;
-	 firp->getAddresses().insert(calladdr);
-       	 calladdr->setFileID(insn->getAddress()->getFileID());
-	*/
 	auto calladdr=firp->addNewAddress(insn->getAddress()->getFileID(),0);
 
 	/* set the fields in the new instruction */
@@ -599,21 +590,8 @@ void fix_call(Instruction_t* insn, FileIR_t *firp, bool can_unpin)
 	insn->setComment(insn->getComment()+" Push part");
 
 	/* create a relocation for this instruction */
-	/*
-	Relocation_t* reloc=new Relocation_t;
-	insn->getRelocations().insert(reloc);
-	firp->getRelocations().insert(reloc);
-	*/
 	auto reloc= firp->getArchitectureBitWidth()==32 ? firp->addNewRelocation(insn, 1, "32-bit") :
-		/*
-		reloc->setOffset(1);
-		reloc->setType("32-bit");
-		*/
 		    firp->getArchitectureBitWidth()==64 ? firp->addNewRelocation(insn, 0, "push64") :
-		/*
-		reloc->setOffset(0);
-		reloc->setType("push64");
-		*/
 		    throw invalid_argument("odd bit width?");
 
 
@@ -622,13 +600,6 @@ void fix_call(Instruction_t* insn, FileIR_t *firp, bool can_unpin)
 	if(newindirtarg && !newindirtarg->getIndirectBranchTargetAddress())
 	{
 		/* create a new address for the IBTA */
-		/*
-		AddressID_t* newaddr = new AddressID_t;
-		assert(newaddr);
-		newaddr->setFileID(newindirtarg->getAddress()->getFileID());
-		newaddr->setVirtualOffset(newindirtarg->getAddress()->getVirtualOffset());
-		firp->getAddresses().insert(newaddr);
-		*/
 		auto newaddr=firp->addNewAddress(newindirtarg->getAddress()->getFileID(), newindirtarg->getAddress()->getVirtualOffset());
 
 		/* set the instruction and include this address in the list of addrs */
@@ -650,18 +621,8 @@ void fix_call(Instruction_t* insn, FileIR_t *firp, bool can_unpin)
 
 
 	// mark in the IR what the fallthrough of this insn is.
-	/* 
-	Relocation_t* fix_call_reloc=new Relocation_t(); 
-	callinsn->getRelocations().insert(fix_call_reloc);
-	firp->getRelocations().insert(fix_call_reloc);
-	*/
 	auto fix_call_reloc=firp->addNewRelocation(callinsn, 0, "fix_call_fallthrough", newindirtarg);
 	(void)fix_call_reloc; // not used, just give to IR
-	/*
-	fix_call_reloc->setOffset(0);
-	fix_call_reloc->setType("fix_call_fallthrough");
-	fix_call_reloc->setWRT(newindirtarg);
-	*/
 }
 
 
@@ -703,9 +664,12 @@ bool can_skip_safe_function(Instruction_t *call_insn)
 }
 
 
-template <class T> struct insn_less : binary_function <T,T,bool> {
-  bool operator() (const T& x, const T& y) const {
-        return  x->getBaseID()  <   y->getBaseID()  ;}
+template <class T> struct insn_less : binary_function <T,T,bool> 
+{
+	bool operator() (const T& x, const T& y) const 
+	{
+		return  make_tuple(x->getBaseID(),x) < make_tuple(y->getBaseID(),y);
+	}
 };
 
 
@@ -717,14 +681,6 @@ void mark_as_unpinned_ibt(FileIR_t* firp, Instruction_t* ret_point)
 	if( ret_point == NULL ) return;
 	if( ret_point->getIndirectBranchTargetAddress() != NULL ) return;
 	
-	/*
-	auto newaddr = new AddressID_t;
-	assert(newaddr);
-	newaddr->setFileID(ret_point->getAddress()->getFileID());
-	newaddr->setVirtualOffset(0);	// unpinne
-	
-	firp->getAddresses().insert(newaddr);
-	*/
 	auto newaddr=firp->addNewAddress(ret_point->getAddress()->getFileID(),0);
 	ret_point->setIndirectBranchTargetAddress(newaddr);
 	
@@ -859,9 +815,9 @@ void fix_other_pcrel(FileIR_t* firp, Instruction_t *insn, uintptr_t virt_offset)
 			memcpy(cstr,data.c_str(), data.length());
 			void *offsetptr=&cstr[offset];
 
-			uintptr_t disp=the_arg.getMemoryDisplacement(); 
-			uintptr_t oldpc=virt_offset;
-			uintptr_t newdisp=disp+oldpc;
+			auto disp=the_arg.getMemoryDisplacement(); 
+			auto oldpc=virt_offset;
+			auto newdisp=disp+oldpc-firp->getArchitecture()->getFileBase();
 
 			assert((uintptr_t)(offset+size)<=(uintptr_t)(data.length()));
 			
@@ -894,11 +850,6 @@ void fix_other_pcrel(FileIR_t* firp, Instruction_t *insn, uintptr_t virt_offset)
 		}
 
 		// now that we've done the rewriting, go ahead and add the reloc.
-		/*
-		auto reloc=new Relocation_t(BaseObj_t::NOT_IN_DATABASE, 0,"pcrel");
-		insn->getRelocations().insert(reloc);
-		firp->getRelocations().insert(reloc);
-		*/
 		auto reloc=firp->addNewRelocation(insn,0,"pcrel");
 		(void)reloc; // not used, only given to the IR
 
@@ -916,10 +867,6 @@ void fix_safefr(FileIR_t* firp, Instruction_t *insn, uintptr_t virt_offset)
 		assert(reloc);
 		if( reloc->getType() == "safefr" )
 		{
-			/*
-			auto addr=new AddressID_t(BaseObj_t::NOT_IN_DATABASE, insn->getAddress()->getFileID(), 0);
-			firp->getAddresses().insert(addr);
-			*/
 			auto addr=firp->addNewAddress(insn->getAddress()->getFileID(), 0);
 			insn->setAddress(addr);
 		}
@@ -929,7 +876,6 @@ void fix_safefr(FileIR_t* firp, Instruction_t *insn, uintptr_t virt_offset)
 
 void fix_other_pcrel(FileIR_t* firp)
 {
-
 	for(auto insn : firp->getInstructions())
 	{
 		fix_other_pcrel(firp,insn, insn->getAddress()->getVirtualOffset());
@@ -1008,7 +954,6 @@ int parseArgs(const vector<string> step_args)
 	if(getenv("FIX_CALLS_FIX_ALL_CALLS"))
 		fix_all=true;
 
-//	variant_id=stoi(step_args[0]);
 	return 0;
 }
 
@@ -1169,8 +1114,6 @@ shared_ptr<TransformStep_t> getTransformStep(void)
 {
         curInvocation.reset(new FixCalls_t());
         return curInvocation;
-
-        //return shared_ptr<Transform_SDK::TransformStep_t>(new FixCalls_t());
 }
 
 
diff --git a/irdb-libs/libEXEIO/src/exeio_pe.h b/irdb-libs/libEXEIO/src/exeio_pe.h
index 868ddeec9e26f2bd578b7e81b12130baa2394b3f..07162ee9cb71b761b7090d76f236fb1121a3a951 100644
--- a/irdb-libs/libEXEIO/src/exeio_pe.h
+++ b/irdb-libs/libEXEIO/src/exeio_pe.h
@@ -132,7 +132,15 @@ namespace EXEIO
 			}
 			virtual MachineType_t getMachineType() const
 			{
-				assert(0);
+				assert(e);
+                                switch(e->get_machine())
+                                {
+                                        case 0x14c  : return mtI386;
+                                        case 0x8664 : return mtX86_64;
+                                        default: assert(0);
+                                }
+                                assert(0);
+
 			}
 
                         virtual execlass_t get_class() 
diff --git a/irdb-libs/libIRDB-core/include/archdesc.hpp b/irdb-libs/libIRDB-core/include/archdesc.hpp
index e7299d450190a189b6929b41a957db00170aba93..d1a98ba67a6bcf9d974fdd2b3ce42d3ac1b23bdd 100644
--- a/irdb-libs/libIRDB-core/include/archdesc.hpp
+++ b/irdb-libs/libIRDB-core/include/archdesc.hpp
@@ -41,11 +41,15 @@ class ArchitectureDescription_t : virtual public IRDB_SDK::ArchitectureDescripti
 		ADMachineType_t getMachineType() const 		{ return mt; }	
 		void setMachineType(const ADMachineType_t t) 	{ mt=t; }
 
+		IRDB_SDK::VirtualOffset_t getFileBase() const   { return file_base; }
+		void setFileBase(virtual_offset_t _file_base)   { file_base=_file_base; }
+
 	private:
 
 		size_t bits;
 		ADFileType_t ft;
 		ADMachineType_t mt;
+		IRDB_SDK::VirtualOffset_t file_base;
 };
 
 }
diff --git a/irdb-libs/libIRDB-core/src/fileir.cpp b/irdb-libs/libIRDB-core/src/fileir.cpp
index 14502548e6d95423ff93e52ecd9b2a9c28e7bce9..e1d3fd15af335622c37f1b68ee956ec5e09ea92a 100644
--- a/irdb-libs/libIRDB-core/src/fileir.cpp
+++ b/irdb-libs/libIRDB-core/src/fileir.cpp
@@ -977,6 +977,8 @@ void FileIR_t::setArchitecture(const int width, const ADMachineType_t mt)
 		archdesc=new ArchitectureDescription_t;
 	archdesc->setBitWidth(width); 
 	archdesc->setMachineType(mt); 
+
+	archdesc->setFileBase(0);	// maybe not rght for PE files?
 }	
 
 void FileIR_t::setArchitecture()
@@ -1025,12 +1027,85 @@ void FileIR_t::setArchitecture()
 	}
 
 
-	if (is_pe) // libIRDB::FileIR_t::archdesc->getFileType() == IRDB_SDK::adftPE)
+	if (is_pe) 
 	{
+		// set machine/file types
 		libIRDB::FileIR_t::archdesc->setFileType(IRDB_SDK::adftPE);
 		// just assume x86-64 bit for Windows, o/w could also extract from file
 		libIRDB::FileIR_t::archdesc->setBitWidth(64);
 		libIRDB::FileIR_t::archdesc->setMachineType(IRDB_SDK::admtX86_64);
+
+		// now we need to read the image base from the exe file
+
+		//DOS .EXE header
+		struct irdb_dos_header
+		{
+			uint16_t e_magic;                     // Magic number
+			uint16_t e_cblp;                      // Bytes on last page of file
+			uint16_t e_cp;                        // Pages in file
+			uint16_t e_crlc;                      // Relocations
+			uint16_t e_cparhdr;                   // Size of header in paragraphs
+			uint16_t e_minalloc;                  // Minimum extra paragraphs needed
+			uint16_t e_maxalloc;                  // Maximum extra paragraphs needed
+			uint16_t e_ss;                        // Initial (relative) SS value
+			uint16_t e_sp;                        // Initial SP value
+			uint16_t e_csum;                      // Checksum
+			uint16_t e_ip;                        // Initial IP value
+			uint16_t e_cs;                        // Initial (relative) CS value
+			uint16_t e_lfarlc;                    // File address of relocation table
+			uint16_t e_ovno;                      // Overlay number
+			uint16_t e_res[4];                    // Reserved words
+			uint16_t e_oemid;                     // OEM identifier (for e_oeminfo)
+			uint16_t e_oeminfo;                   // OEM information; e_oemid specific
+			uint16_t e_res2[10];                  // Reserved words
+			int32_t  e_lfanew;                    // File address of new exe header
+		};
+
+		struct irdb_image_pe_headers64
+		{
+			uint32_t Signature;
+			uint16_t Machine;
+			uint16_t NumberOfSections;
+			uint32_t TimeDateStamp;
+			uint32_t PointerToSymbolTable;
+			uint32_t NumberOfSymbols;
+			uint16_t SizeOfOptionalHeader;
+			uint16_t Characteristics;
+			uint16_t Magic;
+			uint8_t  MajorLinkerVersion;
+			uint8_t  MinorLinkerVersion;
+			uint32_t SizeOfCode;
+			uint32_t SizeOfInitializedData;
+			uint32_t SizeOfUninitializedData;
+			uint32_t AddressOfEntryPoint;
+			uint32_t BaseOfCode;
+
+			// ImageBase is a uint32_t for 32-bit code.
+			uint64_t ImageBase;
+
+		};
+
+
+		// declare and init a dos header.
+                struct irdb_dos_header idh;
+                memset(&idh,0,sizeof(idh));
+                struct irdb_image_pe_headers64 pe_and_opt_headers;
+                memset(&pe_and_opt_headers,0,sizeof(pe_and_opt_headers));
+
+                loa.seek(0, ios::beg);
+                loa.cread((char*)&idh, sizeof(idh));
+
+                loa.seek(idh.e_lfanew, ios::beg);
+                loa.cread((char*)&pe_and_opt_headers, sizeof(pe_and_opt_headers));
+
+                assert(pe_and_opt_headers.Signature ==0x4550 /* "PE" means pe file */);
+                assert(pe_and_opt_headers.Magic ==0x20b /* "8664" means 64-bits */);
+                /* note: if pe_and_opt_headers.Magic==0x10b that means "8632" or intel 32-bit file.  not supporting yet. */
+
+                if(getenv("IRDB_VERBOSE"))
+                        cout<<"Determined PE32+ file has image base: "<<hex<<pe_and_opt_headers.ImageBase<<endl;
+
+                archdesc->setFileBase(pe_and_opt_headers.ImageBase);
 	}
 	else if(is_elf)
 	{
diff --git a/irdb-libs/third_party/pebliss b/irdb-libs/third_party/pebliss
index d1474211e317b243786ec06b383fd4edb2c8cca8..c8a66676b446db15e431fd53de1e2ae50ca7afd8 160000
--- a/irdb-libs/third_party/pebliss
+++ b/irdb-libs/third_party/pebliss
@@ -1 +1 @@
-Subproject commit d1474211e317b243786ec06b383fd4edb2c8cca8
+Subproject commit c8a66676b446db15e431fd53de1e2ae50ca7afd8
diff --git a/irdb-sdk b/irdb-sdk
index 5e547d1dfb046cf5d353c95c46bb86f06271deaf..653c5df9d09af46808330375a87bab2414fc3a02 160000
--- a/irdb-sdk
+++ b/irdb-sdk
@@ -1 +1 @@
-Subproject commit 5e547d1dfb046cf5d353c95c46bb86f06271deaf
+Subproject commit 653c5df9d09af46808330375a87bab2414fc3a02
diff --git a/tools/ps_analyze.sh b/tools/ps_analyze.sh
index fd060ce2220aaf3cd5c7bdc5936c6dc6aedc05d1..22254af900e0943ad26876ffc9b76eecdf539331 100755
--- a/tools/ps_analyze.sh
+++ b/tools/ps_analyze.sh
@@ -1038,17 +1038,17 @@ compatcheck()
 
 	file $1 |egrep  "ELF.*executable" > /dev/null 2>&1 
 	if [ $? = 0 ]; then
-		echo Detected ELF file.
+		echo "Detected ELF non-PIE executable."
 		return
 	fi
 	file $1 |egrep  "ELF.*shared object" > /dev/null 2>&1 
 	if [ $? = 0 ]; then
-		echo Detected ELF shared object.
+		echo "Detected ELF shared object."
 		return
 	fi
-	file $1 |egrep  "CGC.*executable" > /dev/null 2>&1 
+	file $1 |egrep  "PE32\+ executable" > /dev/null 2>&1 
 	if [ $? = 0 ]; then
-		echo Detected CGCEF file.
+		echo "Detected PE32+ file"
 		return
 	fi